aboutsummaryrefslogtreecommitdiff
path: root/src/smcdeleg.adoc
blob: fd67d82258ef8a237dd025f1efd281dd2df2b1b0 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
[[smcdeleg]]
== "Smcdeleg" Counter Delegation Extension, Version 1.0.0

In modern “Rich OS” environments, hardware performance monitoring
resources are managed by the kernel, kernel driver, and/or hypervisor.
Counters may be configured with differing scopes, in some cases counting
events system-wide, while in others counting events on behalf of a
single virtual machine or application. In such environments, the latency
of counter writes has a direct impact on overall profiling overhead as a
result of frequent counter writes during:

. Sample collection, to clear overflow indication, and reload overflowed
counter(s)
. Context switch, between processes, threads, containers, or virtual
machines

This extension provides a means for M-mode to allow writing select
counters and event selectors from S/HS-mode. The purpose is to avert
transitions to and from M-mode that add latency to these performance
critical supervisor/hypervisor code sections. This extension also
defines one new CSR, scountinhibit.

For a Machine-level environment, extension *Smcdeleg* (‘Sm’ for
Privileged architecture and Machine-level extension, ‘cdeleg’ for
Counter Delegation) encompasses all added CSRs and all behavior
modifications for a hart, over all privilege levels. For a
Supervisor-level environment, extension *Ssccfg* (‘Ss’ for Privileged
architecture and Supervisor-level extension, ‘ccfg’ for Counter
Configuration) provides access to delegated counters, and to new
supervisor-level state.

=== Counter Delegation

The `mcounteren` register allows M-mode to provide the next-lower
privilege mode with read access to select counters. When the Smcdeleg/Ssccfg
extension is enabled (`menvcfg`.CDE=1), it further allows M-mode to delegate select
counters to S-mode.

The `siselect` (and `vsiselect`) index range 0x40-0x5F is reserved for
delegated counter access. When a counter _i_ is delegated
(`mcounteren`[_i_]=1 and `menvcfg`.CDE=1), the register state associated
with counter _i_ can be read or written via `sireg*`, while `siselect` holds
0x40+__i__. The counter state accessible via alias CSRs is shown in
the table below.

.Indirect HPM State Mappings
[#indirect-hpm-state-mappings]
[width="100%",cols="21%,20%,21%,18%,20%",options="header",]
|===
|*`siselect` value* |*`sireg*` |*`sireg4`* |*`sireg2`* |*`sireg5`*
|0x40 |`cycle`^1^ |`cycleh`^1^ |`cyclecfg`^14^ |`cyclecfgh`^14^
|0x41 4+^|_See below_ 
|0x42 |`instret`^1^ |`instreth`^1^ |`instretcfg`^14^ |`instretcfgh`^14^
|0x43 |`hpmcounter3`^2^ |`hpmcounter3h`^2^ |`hpmevent3`^2^ |`hpmevent3h`^23^
|… |… |… |… |…
|0x5F |`hpmcounter31`^2^ |`hpmcounter31h`^2^ |`hpmevent31`^2^ |`hpmevent31h`^23^
|===

^1^ Depends on Zicntr support +
^2^ Depends on Zihpm support +
^3^ Depends on Sscofpmf support +
^4^ Depends on Smcntrpmf support 

[NOTE]
====
`__hpmevent__i` _represents a subset of the state accessed by the_ `__mhpmevent__i` _register. Likewise, `cyclecfg` and `instretcfg` represent a subset of the state accessed by the `mcyclecfg` and `minstretcfg` registers, respectively. See below for subset details._
====

If extension Smstateen is implemented, refer to extension Smcsrind/Sscsrind (<<indirect-csr>>) for how setting bit 60 of CSR
`mstateen0` to zero prevents access to registers `siselect`, `sireg*`,
`vsiselect`, and `vsireg*` from privileged modes less privileged than
M-mode, and likewise how setting bit 60 of `hstateen0` to zero prevents
access to `siselect` and `sireg*` (really `vsiselect` and `vsireg*`) from
VS-mode.

The remaining rules of this section apply only when access to a CSR is
not blocked by `mstateen0`[60] = 0 or `hstateen0`[60] = 0.

While the privilege mode is M or S and `siselect` holds a value in the
range 0x40-0x5F, illegal instruction exceptions are raised for the
following cases:

* attempts to access any `sireg*` when `menvcfg`.CDE = 0;
* attempts to access `sireg3` or `sireg6`;
* attempts to access `sireg4` or `sireg5` when XLEN = 64;
* attempts to access `sireg*` when `siselect` = 0x41, or when the counter
selected by `siselect` is not delegated to S-mode (the corresponding bit
in `mcounteren` = 0).

NOTE: _The memory-mapped `mtime` register is not a performance monitoring
counter to be managed by supervisor software, hence the special
treatment of `siselect` value 0x41 described above._

For each `siselect` and `sireg*` combination defined in <<indirect-hpm-state-mappings>>, the table
further indicates the extensions upon which the underlying counter state
depends. If any extension upon which the underlying state depends is not
implemented, an attempt from M or S mode to access the given state
through `sireg*` raises an illegal instruction exception.

If the hypervisor (H) extension is also implemented, then as specified
by extension Smcsrind/Sscsrind, a virtual instruction exception is
raised for attempts from VS-mode or VU-mode to directly access `vsiselect`
or `vsireg*`, or attempts from VU-mode to access `siselect` or `sireg*`. Furthermore, while `vsiselect` holds a value in the range 0x40-0x5F:

* An attempt to access any `vsireg*` from M or S mode raises an illegal
instruction exception.
* An attempt from VS-mode to access any `sireg*` (really `vsireg*`) raises
either an illegal instruction exception if `menvcfg`.CDE = 0, or a virtual
instruction exception if `menvcfg`.CDE = 1.

If Sscofpmf is implemented, `sireg2` and `sireg5` provide access only to a
subset of the event selector registers. Specifically, event selector bit
62 (MINH) is read-only 0 when accessed through `sireg*`. Similarly, if
Smcntrpmf is implemented, `sireg2` and `sireg5` provide access only to a
subset of the counter configuration registers. Counter configuration
register bit 62 (MINH) is read-only 0 when accessed through `sireg*`.

=== Supervisor Counter Inhibit Register (`scountinhibit`)

Smcdeleg/Ssccfg defines a new `scountinhibit` register, a masked alias of
`mcountinhibit`. For counters delegated to S-mode, the associated
`mcountinhibit` bits can be accessed via `scountinhibit`. For counters not
delegated to S-mode, the associated bits in `scountinhibit` are read-only
zero.

When `menvcfg`.CDE=0, attempts to access `scountinhibit` raise an illegal
instruction exception. When the Supervisor Counter Delegation extension
is enabled, attempts to access `scountinhibit` from VS-mode or VU-mode
raise a virtual instruction exception.

=== Virtualizing `scountovf`

For implementations that support Smcdeleg/Ssccfg, Sscofpmf, and the H
extension, when `menvcfg`.CDE=1, attempts to access `scountovf` from VS-mode
or VU-mode raise a virtual instruction exception.

=== Virtualizing Local Counter Overflow Interrupts 

For implementations that support Smcdeleg, Smcofpmf, and Smaia, the
local counter overflow interrupt (LCOFI) bit (bit 13) in each of CSRs
`mvip` and `mvien` is implemented and writable.

For implementations that support Smcdeleg/Ssccfg, Smcofpmf/Sscofpmf,
Smaia/Ssaia, and the H extension, the LCOFI bit (bit 13) in each of `hvip`
and `hvien` is implemented and writable.

[NOTE]
====
_The `hvip` register is defined by the hypervisor (H) extension, while the `mvien` and `hvien` registers are defined by the Smaia/Ssaia extension._

_By virtue of implementing `hvip`.LCOFI, it is implicit that the LCOFI bit (bit 13) in each of `vsie` and `vsip` is also implemented._

_Requiring support for the LCOFI bits listed above ensures that virtual LCOFIs can be delivered to an OS running in S-mode, and to a guest OS running in VS-mode. It is optional whether the LCOFI bit (bit 13) in each of `mideleg` and `hideleg`, which allows all LCOFIs to be delegated to S-mode and VS-mode, respectively, is implemented and writable._
====