3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: hal/halx86/up/spinlock.c
5 * PURPOSE: Spinlock and Queued Spinlock Support
6 * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org)
9 /* INCLUDES ******************************************************************/
11 /* This file is compiled twice. Once for UP and once for MP */
17 #include <internal/spinlock.h>
19 #undef KeAcquireSpinLock
20 #undef KeReleaseSpinLock
22 /* GLOBALS *******************************************************************/
24 ULONG_PTR HalpSystemHardwareFlags
;
25 KSPIN_LOCK HalpSystemHardwareLock
;
27 /* FUNCTIONS *****************************************************************/
36 KeAcquireSpinLockRaiseToSynch(PKSPIN_LOCK SpinLock
)
41 KeRaiseIrql(SYNCH_LEVEL
, &OldIrql
);
43 /* Acquire the lock and return */
44 KxAcquireSpinLock(SpinLock
);
53 KfAcquireSpinLock(PKSPIN_LOCK SpinLock
)
57 /* Raise to dispatch and acquire the lock */
58 KeRaiseIrql(DISPATCH_LEVEL
, &OldIrql
);
59 KxAcquireSpinLock(SpinLock
);
68 KfReleaseSpinLock(PKSPIN_LOCK SpinLock
,
71 /* Release the lock and lower IRQL back */
72 KxReleaseSpinLock(SpinLock
);
81 KeAcquireQueuedSpinLock(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber
)
85 /* Raise to dispatch */
86 KeRaiseIrql(DISPATCH_LEVEL
, &OldIrql
);
88 /* Acquire the lock */
89 KxAcquireSpinLock(KeGetCurrentPrcb()->LockQueue
[LockNumber
].Lock
); // HACK
98 KeAcquireQueuedSpinLockRaiseToSynch(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber
)
103 KeRaiseIrql(SYNCH_LEVEL
, &OldIrql
);
105 /* Acquire the lock */
106 KxAcquireSpinLock(KeGetCurrentPrcb()->LockQueue
[LockNumber
].Lock
); // HACK
115 KeAcquireInStackQueuedSpinLock(IN PKSPIN_LOCK SpinLock
,
116 IN PKLOCK_QUEUE_HANDLE LockHandle
)
118 /* Set up the lock */
119 LockHandle
->LockQueue
.Next
= NULL
;
120 LockHandle
->LockQueue
.Lock
= SpinLock
;
122 /* Raise to dispatch */
123 KeRaiseIrql(DISPATCH_LEVEL
, &LockHandle
->OldIrql
);
125 /* Acquire the lock */
126 KxAcquireSpinLock(LockHandle
->LockQueue
.Lock
); // HACK
134 KeAcquireInStackQueuedSpinLockRaiseToSynch(IN PKSPIN_LOCK SpinLock
,
135 IN PKLOCK_QUEUE_HANDLE LockHandle
)
137 /* Set up the lock */
138 LockHandle
->LockQueue
.Next
= NULL
;
139 LockHandle
->LockQueue
.Lock
= SpinLock
;
142 KeRaiseIrql(SYNCH_LEVEL
, &LockHandle
->OldIrql
);
144 /* Acquire the lock */
145 KxAcquireSpinLock(LockHandle
->LockQueue
.Lock
); // HACK
153 KeReleaseQueuedSpinLock(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber
,
156 /* Release the lock */
157 KxReleaseSpinLock(KeGetCurrentPrcb()->LockQueue
[LockNumber
].Lock
); // HACK
159 /* Lower IRQL back */
160 KeLowerIrql(OldIrql
);
168 KeReleaseInStackQueuedSpinLock(IN PKLOCK_QUEUE_HANDLE LockHandle
)
170 /* Simply lower IRQL back */
171 KxReleaseSpinLock(LockHandle
->LockQueue
.Lock
); // HACK
172 KeLowerIrql(LockHandle
->OldIrql
);
180 KeTryToAcquireQueuedSpinLockRaiseToSynch(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber
,
184 ASSERT(FALSE
); // FIXME: Unused
188 /* Simply raise to synch */
189 KeRaiseIrql(SYNCH_LEVEL
, OldIrql
);
191 /* Add an explicit memory barrier to prevent the compiler from reordering
192 memory accesses across the borders of spinlocks */
193 KeMemoryBarrierWithoutFence();
195 /* Always return true on UP Machines */
204 KeTryToAcquireQueuedSpinLock(IN KSPIN_LOCK_QUEUE_NUMBER LockNumber
,
208 ASSERT(FALSE
); // FIXME: Unused
212 /* Simply raise to dispatch */
213 KeRaiseIrql(DISPATCH_LEVEL
, OldIrql
);
215 /* Add an explicit memory barrier to prevent the compiler from reordering
216 memory accesses across the borders of spinlocks */
217 KeMemoryBarrierWithoutFence();
219 /* Always return true on UP Machines */
227 HalpAcquireCmosSpinLock(VOID
)
231 /* Get flags and disable interrupts */
232 Flags
= __readeflags();
235 /* Acquire the lock */
236 KxAcquireSpinLock(&HalpSystemHardwareLock
);
238 /* We have the lock, save the flags now */
239 HalpSystemHardwareFlags
= Flags
;
244 HalpReleaseCmosSpinLock(VOID
)
249 Flags
= HalpSystemHardwareFlags
;
251 /* Release the lock */
252 KxReleaseSpinLock(&HalpSystemHardwareLock
);
254 /* Restore the flags */
255 __writeeflags(Flags
);