xref: /reactos/sdk/include/xdk/arm/ke.h (revision 84344399)
1 $if (_WDMDDK_)
2 /** Kernel definitions for ARM **/
3 
4 /* Interrupt request levels */
5 #define PASSIVE_LEVEL           0
6 #define LOW_LEVEL               0
7 #define APC_LEVEL               1
8 #define DISPATCH_LEVEL          2
9 #define CLOCK_LEVEL             13
10 #define IPI_LEVEL               14
11 #define DRS_LEVEL               14
12 #define POWER_LEVEL             14
13 #define PROFILE_LEVEL           15
14 #define HIGH_LEVEL              15
15 
16 #define KIP0PCRADDRESS          0xFFDFF000
17 #define KI_USER_SHARED_DATA     0xFFFF9000
18 #define SharedUserData          ((KUSER_SHARED_DATA * const)KI_USER_SHARED_DATA)
19 
20 #define PAGE_SIZE               0x1000
21 #define PAGE_SHIFT              12L
22 
23 typedef struct _KFLOATING_SAVE
24 {
25     ULONG Reserved;
26 } KFLOATING_SAVE, *PKFLOATING_SAVE;
27 
28 extern NTKERNELAPI volatile KSYSTEM_TIME KeTickCount;
29 
30 FORCEINLINE
31 VOID
32 YieldProcessor(
33     VOID)
34 {
35     __dmb(_ARM_BARRIER_ISHST);
36     __yield();
37 }
38 
39 #define MemoryBarrier()         __dmb(_ARM_BARRIER_SY)
40 #define PreFetchCacheLine(l,a)  __prefetch((const void *) (a))
41 #define PrefetchForWrite(p)     __prefetch((const void *) (p))
42 #define ReadForWriteAccess(p)   (*(p))
43 
44 FORCEINLINE
45 VOID
46 KeMemoryBarrier(
47     VOID)
48 {
49     _ReadWriteBarrier();
50     MemoryBarrier();
51 }
52 
53 #define KeMemoryBarrierWithoutFence() _ReadWriteBarrier()
54 
55 _IRQL_requires_max_(HIGH_LEVEL)
56 _IRQL_saves_
57 NTHALAPI
58 KIRQL
59 NTAPI
60 KeGetCurrentIrql(
61     VOID);
62 
63 _IRQL_requires_max_(HIGH_LEVEL)
64 NTHALAPI
65 VOID
66 FASTCALL
67 KfLowerIrql(
68     _In_ _IRQL_restores_ _Notliteral_ KIRQL NewIrql);
69 #define KeLowerIrql(a) KfLowerIrql(a)
70 
71 _IRQL_requires_max_(HIGH_LEVEL)
72 _IRQL_raises_(NewIrql)
73 _IRQL_saves_
74 NTHALAPI
75 KIRQL
76 FASTCALL
77 KfRaiseIrql(
78     _In_ KIRQL NewIrql);
79 #define KeRaiseIrql(a,b) *(b) = KfRaiseIrql(a)
80 
81 _IRQL_requires_max_(DISPATCH_LEVEL)
82 _IRQL_saves_
83 _IRQL_raises_(DISPATCH_LEVEL)
84 NTHALAPI
85 KIRQL
86 NTAPI
87 KeRaiseIrqlToDpcLevel(VOID);
88 
89 NTHALAPI
90 KIRQL
91 NTAPI
92 KeRaiseIrqlToSynchLevel(VOID);
93 
94 _Requires_lock_not_held_(*SpinLock)
95 _Acquires_lock_(*SpinLock)
96 _IRQL_requires_max_(DISPATCH_LEVEL)
97 _IRQL_saves_
98 _IRQL_raises_(DISPATCH_LEVEL)
99 NTHALAPI
100 KIRQL
101 FASTCALL
102 KfAcquireSpinLock(
103   _Inout_ PKSPIN_LOCK SpinLock);
104 #define KeAcquireSpinLock(a,b) *(b) = KfAcquireSpinLock(a)
105 
106 _Requires_lock_held_(*SpinLock)
107 _Releases_lock_(*SpinLock)
108 _IRQL_requires_(DISPATCH_LEVEL)
109 NTHALAPI
110 VOID
111 FASTCALL
112 KfReleaseSpinLock(
113   _Inout_ PKSPIN_LOCK SpinLock,
114   _In_ _IRQL_restores_ KIRQL NewIrql);
115 #define KeReleaseSpinLock(a,b) KfReleaseSpinLock(a,b)
116 
117 _Requires_lock_not_held_(*SpinLock)
118 _Acquires_lock_(*SpinLock)
119 _IRQL_requires_min_(DISPATCH_LEVEL)
120 NTKERNELAPI
121 VOID
122 FASTCALL
123 KefAcquireSpinLockAtDpcLevel(
124   _Inout_ PKSPIN_LOCK SpinLock);
125 #define KeAcquireSpinLockAtDpcLevel(SpinLock) KefAcquireSpinLockAtDpcLevel(SpinLock)
126 
127 _Requires_lock_held_(*SpinLock)
128 _Releases_lock_(*SpinLock)
129 _IRQL_requires_min_(DISPATCH_LEVEL)
130 NTKERNELAPI
131 VOID
132 FASTCALL
133 KefReleaseSpinLockFromDpcLevel(
134   _Inout_ PKSPIN_LOCK SpinLock);
135 #define KeReleaseSpinLockFromDpcLevel(SpinLock) KefReleaseSpinLockFromDpcLevel(SpinLock)
136 
137 NTSYSAPI
138 PKTHREAD
139 NTAPI
140 KeGetCurrentThread(VOID);
141 
142 _Always_(_Post_satisfies_(return<=0))
143 _Must_inspect_result_
144 _IRQL_requires_max_(DISPATCH_LEVEL)
145 _Kernel_float_saved_
146 _At_(*FloatSave, _Kernel_requires_resource_not_held_(FloatState) _Kernel_acquires_resource_(FloatState))
147 FORCEINLINE
148 NTSTATUS
149 KeSaveFloatingPointState(
150     _Out_ PKFLOATING_SAVE FloatSave)
151 {
152     UNREFERENCED_PARAMETER(FloatSave);
153     return STATUS_SUCCESS;
154 }
155 
156 _Success_(1)
157 _Kernel_float_restored_
158 _At_(*FloatSave, _Kernel_requires_resource_held_(FloatState) _Kernel_releases_resource_(FloatState))
159 FORCEINLINE
160 NTSTATUS
161 KeRestoreFloatingPointState(
162     _In_ PKFLOATING_SAVE FloatSave)
163 {
164     UNREFERENCED_PARAMETER(FloatSave);
165     return STATUS_SUCCESS;
166 }
167 
168 VOID
169 KeFlushIoBuffers(
170     _In_ PMDL Mdl,
171     _In_ BOOLEAN ReadOperation,
172     _In_ BOOLEAN DmaOperation);
173 
174 #define DbgRaiseAssertionFailure() __emit(0xdefc)
175 
176 FORCEINLINE
177 VOID
178 _KeQueryTickCount(
179   OUT PLARGE_INTEGER CurrentCount)
180 {
181   for (;;) {
182 #ifdef NONAMELESSUNION
183     CurrentCount->s.HighPart = KeTickCount.High1Time;
184     CurrentCount->s.LowPart = KeTickCount.LowPart;
185     if (CurrentCount->s.HighPart == KeTickCount.High2Time) break;
186 #else
187     CurrentCount->HighPart = KeTickCount.High1Time;
188     CurrentCount->LowPart = KeTickCount.LowPart;
189     if (CurrentCount->HighPart == KeTickCount.High2Time) break;
190 #endif
191     YieldProcessor();
192   }
193 }
194 #define KeQueryTickCount(CurrentCount) _KeQueryTickCount(CurrentCount)
195 
196 #define CP15_PMSELR     15, 0,  9, 12, 5 /* Event Counter Selection Register */
197 #define CP15_PMXEVCNTR  15, 0,  9, 13, 2 /* Event Count Register */
198 #define CP15_TPIDRURW   15, 0, 13,  0, 2 /* Software Thread ID Register, UsRW */
199 #define CP15_TPIDRURO   15, 0, 13,  0, 3 /* Software Thread ID Register, UsRO */
200 #define CP15_TPIDRPRW   15, 0, 13,  0, 4 /* Software Thread ID Register, Kernel */
201 
202 $endif (_WDMDDK_)
203 $if (_NTDDK_)
204 
205 #define PAUSE_PROCESSOR __yield();
206 
207 #define KERNEL_STACK_SIZE         0x3000
208 #define KERNEL_LARGE_STACK_SIZE   0xF000
209 #define KERNEL_LARGE_STACK_COMMIT KERNEL_STACK_SIZE
210 
211 #define KERNEL_MCA_EXCEPTION_STACK_SIZE 0x2000
212 
213 #define EXCEPTION_READ_FAULT    0
214 #define EXCEPTION_WRITE_FAULT   1
215 #define EXCEPTION_EXECUTE_FAULT 8
216 
217 /* The following flags control the contents of the CONTEXT structure. */
218 #define CONTEXT_ARM             0x200000L
219 #define CONTEXT_CONTROL         (CONTEXT_ARM | 0x00000001L)
220 #define CONTEXT_INTEGER         (CONTEXT_ARM | 0x00000002L)
221 #define CONTEXT_FLOATING_POINT  (CONTEXT_ARM | 0x00000004L)
222 #define CONTEXT_DEBUG_REGISTERS (CONTEXT_ARM | 0x00000008L)
223 #define CONTEXT_FULL            (CONTEXT_CONTROL | CONTEXT_INTEGER | CONTEXT_FLOATING_POINT)
224 
225 typedef struct _NEON128
226 {
227     ULONGLONG Low;
228     LONGLONG High;
229 } NEON128, *PNEON128;
230 
231 #define ARM_MAX_BREAKPOINTS 8
232 #define ARM_MAX_WATCHPOINTS 1
233 
234 typedef struct _CONTEXT
235 {
236     /* The flags values within this flag control the contents of
237        a CONTEXT record.
238 
239        If the context record is used as an input parameter, then
240        for each portion of the context record controlled by a flag
241        whose value is set, it is assumed that that portion of the
242        context record contains valid context. If the context record
243        is being used to modify a thread's context, then only that
244        portion of the threads context will be modified.
245 
246        If the context record is used as an IN OUT parameter to capture
247        the context of a thread, then only those portions of the thread's
248        context corresponding to set flags will be returned.
249 
250        The context record is never used as an OUT only parameter. */
251     ULONG ContextFlags;
252 
253     /* This section is specified/returned if the ContextFlags word contains
254        the flag CONTEXT_INTEGER. */
255     ULONG R0;
256     ULONG R1;
257     ULONG R2;
258     ULONG R3;
259     ULONG R4;
260     ULONG R5;
261     ULONG R6;
262     ULONG R7;
263     ULONG R8;
264     ULONG R9;
265     ULONG R10;
266     ULONG R11;
267     ULONG R12;
268 
269     ULONG Sp;
270     ULONG Lr;
271     ULONG Pc;
272     ULONG Cpsr;
273 
274     /* Floating Point/NEON Registers */
275     ULONG Fpscr;
276     ULONG Padding;
277     union
278     {
279         NEON128 Q[16];
280         ULONGLONG D[32];
281         ULONG S[32];
282     } DUMMYUNIONNAME;
283 
284     /* Debug registers */
285     ULONG Bvr[ARM_MAX_BREAKPOINTS];
286     ULONG Bcr[ARM_MAX_BREAKPOINTS];
287     ULONG Wvr[ARM_MAX_WATCHPOINTS];
288     ULONG Wcr[ARM_MAX_WATCHPOINTS];
289 
290     ULONG Padding2[2];
291 } CONTEXT;
292 
293 #define PCR_MINOR_VERSION 1
294 #define PCR_MAJOR_VERSION 1
295 
296 typedef struct _KPCR
297 {
298     _ANONYMOUS_UNION union
299     {
300         NT_TIB NtTib;
301         _ANONYMOUS_STRUCT struct
302         {
303             ULONG TibPad0[2];
304             PVOID Spare1;
305             struct _KPCR *Self;
306             struct _KPRCB *CurrentPrcb;
307             PKSPIN_LOCK_QUEUE LockArray;
308             PVOID Used_Self;
309         };
310     };
311     KIRQL CurrentIrql;
312     UCHAR SecondLevelCacheAssociativity;
313     ULONG Unused0[3];
314     USHORT MajorVersion;
315     USHORT MinorVersion;
316     ULONG StallScaleFactor;
317     PVOID Unused1[3];
318     ULONG KernelReserved[15];
319     ULONG SecondLevelCacheSize;
320     _ANONYMOUS_UNION union
321     {
322         USHORT SoftwareInterruptPending; // Software Interrupt Pending Flag
323         struct
324         {
325             UCHAR ApcInterrupt;          // 0x01 if APC int pending
326             UCHAR DispatchInterrupt;     // 0x01 if dispatch int pending
327         };
328     };
329     USHORT InterruptPad;
330     ULONG HalReserved[32];
331     PVOID KdVersionBlock;
332     PVOID Unused3;
333     ULONG PcrAlign1[8];
334 } KPCR, *PKPCR;
335 
336 #define CP15_PCR_RESERVED_MASK 0xFFF
337 #define KIPCR() (((ULONG_PTR)_MoveFromCoprocessor(CP15_TPIDRPRW)) & ~CP15_PCR_RESERVED_MASK)
338 
339 FORCEINLINE
340 PKPCR
341 KeGetPcr(VOID)
342 {
343     return (PKPCR)KIPCR();
344 }
345 
346 #if (NTDDI_VERSION < NTDDI_WIN7) || !defined(NT_PROCESSOR_GROUPS)
347 FORCEINLINE
348 ULONG
349 KeGetCurrentProcessorNumber(VOID)
350 {
351     return (ULONG)*((PUCHAR)KIPCR() + 0x580);
352 }
353 #endif /* (NTDDI_VERSION < NTDDI_WIN7) || !defined(NT_PROCESSOR_GROUPS) */
354 
355 $endif (_NTDDK_)
356