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
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
//! Debug register definitions for ARMv8-A
use crate::{HaltReason, core::BreakpointCause, memory_mapped_bitfield_register};
memory_mapped_bitfield_register! {
/// EDSCR - Debug Status and Control Register
pub struct Edscr(u32);
0x088, "EDSCR",
impl From;
/// Trace Filter Override. Overrides the Trace Filter controls allowing the external debugger to trace any visible Exception level.
pub tfo, set_tfo: 31;
/// DTRRX full.
pub rxfull, set_rxfull: 30;
/// DTRTX full.
pub txfull, set_txfull: 29;
/// ITR overrun.
pub ito, _: 28;
/// DTRRX overrun.
pub rxo, _: 27;
/// DTRTX underrun.
pub txu, _: 26;
/// Pipeline Advance. Indicates that software execution is progressing.
pub pipeadv, _: 25;
/// ITR empty.
pub ite, set_ite: 24;
/// Interrupt disable. Disables taking interrupts in Non-debug state.
pub intdis, set_intdis: 23, 22;
/// Traps accesses to the following debug System registers:
///
/// AArch64: DBGBCR<n>_EL1, DBGBVR<n>_EL1, DBGWCR<n>_EL1, DBGWVR<n>_EL1.
/// AArch32: DBGBCR<n>, DBGBVR<n>, DBGBXVR<n>, DBGWCR<n>, DBGWVR<n>.
pub tda, set_tda: 21;
/// Memory access mode. Controls the use of memory-access mode for accessing ITR and the DCC.
pub ma, set_ma: 20;
/// Sample CONTEXTIDR_EL2. Controls whether the PC Sample-based Profiling Extension samples CONTEXTIDR_EL2 or VTTBR_EL2.VMID.
pub sc2, set_sc2: 19;
/// Non-secure status. In Debug state, gives the current Security state
pub ns, _: 18;
/// Secure debug disabled.
pub sdd, _: 16;
/// Halting debug enable.
pub hde, set_hde: 14;
/// Exception level Execution state status.
pub rw, set_rw: 13, 10;
/// Exception level.
pub el, _: 9, 8;
/// SError interrupt pending.
pub a, _: 7;
/// Cumulative error flag.
pub err, _: 6;
/// Debug status flags.
pub status, set_status: 5, 0;
}
impl Edscr {
/// Is the core currently in a 64-bit mode?
/// This is only accurate if inspected while halted
pub fn currently_64_bit(&self) -> bool {
// RW is a bitfield for each EL where bit n is ELn
// If the bit is 1, that EL is Aarch64
self.rw() & (1 << self.el()) > 0
}
/// Is the core halted?
pub fn halted(&self) -> bool {
match self.status() {
// PE is restarting, exiting Debug state.
0b000001 => false,
// PE is in Non-debug state.
0b000010 => false,
// Breakpoint
0b000111 => true,
// External debug request.
0b010011 => true,
// Halting step, normal.
0b011011 => true,
// Halting step, exclusive.
0b011111 => true,
// OS Unlock catch.
0b100011 => true,
// Reset catch.
0b100111 => true,
// Watchpoint
0b101011 => true,
// HLT instruction.
0b101111 => true,
// Software access to debug register.
0b110011 => true,
// Exception Catch.
0b110111 => true,
// Halting step, no syndrome.
0b111011 => true,
// Everything else is running
_ => false,
}
}
/// Decode the MOE register into HaltReason
pub fn halt_reason(&self) -> HaltReason {
match self.status() {
// Breakpoint debug event
// TODO: The DBGDSCR register will contain information about whether this was a Software or Hardware breakpoint.
0b000111 => HaltReason::Breakpoint(BreakpointCause::Unknown),
// External debug request.
0b010011 => HaltReason::Request,
// Halting step
0b011011 => HaltReason::Step,
0b011111 => HaltReason::Step,
0b111011 => HaltReason::Step,
// OS Unlock catch.
0b100011 => HaltReason::Exception,
// Reset catch.
0b100111 => HaltReason::Exception,
// Watchpoint
0b101011 => HaltReason::Watchpoint,
// HLT instruction - causes entry into Debug state.
0b101111 => HaltReason::Breakpoint(BreakpointCause::Software),
// Software access to debug register.
0b110011 => HaltReason::Exception,
// Exception Catch.
0b110111 => HaltReason::Exception,
// All other values are reserved or running
_ => HaltReason::Unknown,
}
}
}
memory_mapped_bitfield_register! {
/// EDLAR - Lock Access Register
pub struct Edlar(u32);
0xFB0,"EDLAR",
impl From;
/// Lock value
pub value, set_value : 31, 0;
}
memory_mapped_bitfield_register! {
/// OSLAR_EL1 - OS Lock Access Register
pub struct Oslar(u32);
0x300,"OSLAR_EL1",
impl From;
/// Lock value
pub oslk, set_oslk: 1, 0;
}
memory_mapped_bitfield_register! {
/// DBGBVR - Breakpoint Value Register
pub struct Dbgbvr(u32);
0x400, "DBGBVR",
impl From;
/// Breakpoint address
pub value, set_value : 31, 0;
}
memory_mapped_bitfield_register! {
/// DBGBCR - Breakpoint Control Register
pub struct Dbgbcr(u32);
0x408, "DBGBCR",
impl From;
/// Breakpoint type
pub bt, set_bt : 23, 20;
/// Linked breakpoint number
pub lbn, set_lbn : 19, 16;
/// Security state control
pub ssc, set_ssc : 15, 14;
/// Hyp mode control bit
pub hmc, set_hmc: 13;
/// Byte address select
pub bas, set_bas: 8, 5;
/// Privileged mode control
pub pmc, set_pmc: 2, 1;
/// Breakpoint enable
pub e, set_e: 0;
}
memory_mapped_bitfield_register! {
/// EDDFR - External Debug Feature Register
pub struct Eddfr(u32);
0xD28, "EDDFR",
impl From;
/// Number of breakpoints that are context-aware, minus 1.
pub ctx_cmps, _: 31, 28;
/// Number of watchpoints, minus 1.
pub wrps, _: 23, 20;
/// Number of breakpoints, minus 1
pub brps, set_brps: 15, 12;
/// PMU Version
pub pmuver, _: 11, 8;
/// Trace Version
pub tracever, _: 7, 4;
}
memory_mapped_bitfield_register! {
/// EDITR - External Debug Instruction Transfer Register
pub struct Editr(u32);
0x084, "EDITR",
impl From;
/// Instruction value
pub value, set_value: 31, 0;
}
memory_mapped_bitfield_register! {
/// EDRCR - External Debug Reserve Control Register
pub struct Edrcr(u32);
0x090, "EDRCR",
impl From;
/// Allow imprecise entry to Debug state.
pub cbrrq, set_cbrrq: 4;
/// Clear Sticky Pipeline Advance.
pub cpsa, set_cpsa: 3;
/// Clear Sticky Error.
pub cse, set_cse: 2;
}
memory_mapped_bitfield_register! {
/// EDECR - External Debug Execution Control Register
pub struct Edecr(u32);
0x024, "EDECR",
impl From;
/// Halting step enable.
pub ss, set_ss : 2;
/// Reset Catch Enable.
pub rce, set_rce : 1;
/// OS Unlock Catch Enable.
pub osuce, set_osuce : 0;
}
memory_mapped_bitfield_register! {
/// EDPRCR - External Debug Power/Reset Control Register
pub struct Edprcr(u32);
0x310, "EDPRCR",
impl From;
/// COREPURQ
pub corepurq, set_corepurq : 3;
/// Warm reset request.
pub cwrr, set_cwrr : 1;
/// Core no powerdown request.
pub corenpdrq, set_corenpdrq : 0;
}
memory_mapped_bitfield_register! {
/// DBGDTRTX - Debug Data Transfer Register, Transmit
pub struct Dbgdtrtx(u32);
0x08C, "DBGDTRTX",
impl From;
/// Instruction value
pub value, set_value: 31, 0;
}
memory_mapped_bitfield_register! {
/// DBGDTRRX - Debug Data Transfer Register, Receive
pub struct Dbgdtrrx(u32);
0x080, "DBGDTRRX",
impl From;
/// Instruction value
pub value, set_value: 31, 0;
}
memory_mapped_bitfield_register! {
/// EDPRSR - External Debug Processor Status Register
pub struct Edprsr(u32);
0x314, "EDPRSR",
impl From;
/// Sticky Debug Restart.
pub sdr, set_sdr: 11;
/// Sticky EPMAD error.
pub spmad, _: 10;
/// External Performance Monitors Non-secure Access Disable status.
pub epmad, _: 9;
/// Sticky EDAD error.
pub sdad, _: 8;
/// External Debug Access Disable status.
pub edad, _: 7;
/// Double Lock.
pub dlk, _: 6;
/// OS Lock status bit.
pub oslk, _: 5;
/// Halted status bit.
pub halted, _: 4;
/// Sticky core Reset status bit.
pub sr, _: 3;
/// PE Reset status bit.
pub r, _: 2;
/// Sticky core Powerdown status bit.
pub spd, _: 1;
/// Core powerup status bit.
pub pu, _: 0;
}
memory_mapped_bitfield_register! {
/// CTICONTROL - CTI control register
pub struct CtiControl(u32);
0x000, "CTICONTROL",
impl From;
/// Enables or disables the CTI mapping functions.
pub glben, set_glben : 0;
}
memory_mapped_bitfield_register! {
/// CTIGATE - CTI gate register
pub struct CtiGate(u32);
0x140, "CTIGATE",
impl From;
/// Enables or disables the CTI mapping functions.
pub en, set_en : 0, 0, 32;
}
memory_mapped_bitfield_register! {
/// CTIOUTEN<n> - CTI output enable register
pub struct CtiOuten(u32);
0x0A0, "CTIOUTEN",
impl From;
/// Enables or disables input <n> generating this output
pub outen, set_outen : 0, 0, 32;
}
memory_mapped_bitfield_register! {
/// CTIAPPPULSE - CTI application pulse register
pub struct CtiApppulse(u32);
0x01C, "CTIAPPPULSE",
impl From;
/// Generate a pulse on channel N
pub apppulse, set_apppulse : 0, 0, 32;
}
memory_mapped_bitfield_register! {
/// CTIINTACK - CTI Output Trigger Acknowledge register
pub struct CtiIntack(u32);
0x010, "CTIINTACK",
impl From;
/// Ack trigger on channel N
pub ack, set_ack : 0, 0, 32;
}
memory_mapped_bitfield_register! {
/// CTITRIGOUTSTATUS - CTI Trigger Out Status register
pub struct CtiTrigoutstatus(u32);
0x134, "CTITRIGOUTSTATUS",
impl From;
/// Status on channel N
pub status, _ : 0, 0, 32;
}