EFIAPI InterlockedCompareExchangePointer ( IN OUT VOID **Value, IN VOID *CompareValue, IN VOID *ExchangeValue ) { UINT8 SizeOfValue; SizeOfValue = sizeof (*Value); switch (SizeOfValue) { case sizeof (UINT32): return (VOID*)(UINTN)InterlockedCompareExchange32 ( (UINT32*)Value, (UINT32)(UINTN)CompareValue, (UINT32)(UINTN)ExchangeValue ); case sizeof (UINT64): return (VOID*)(UINTN)InterlockedCompareExchange64 ( (UINT64*)Value, (UINT64)(UINTN)CompareValue, (UINT64)(UINTN)ExchangeValue ); default: ASSERT (FALSE); return NULL; } }
/** Performs an atomic compare exchange operation to lock semaphore. The compare exchange operation must be performed using MP safe mechanisms. @param Sem IN: 32-bit unsigned integer OUT: -1 @return Original integer **/ UINT32 LockdownSemaphore ( IN OUT volatile UINT32 *Sem ) { UINT32 Value; do { Value = *Sem; } while (InterlockedCompareExchange32 ( (UINT32*)Sem, Value, (UINT32)-1 ) != Value); return Value; }
/** Performs an atomic compare exchange operation to release semaphore. The compare exchange operation must be performed using MP safe mechanisms. @param Sem IN: 32-bit unsigned integer OUT: original integer + 1 @return Original integer + 1 **/ UINT32 ReleaseSemaphore ( IN OUT volatile UINT32 *Sem ) { UINT32 Value; do { Value = *Sem; } while (Value + 1 != 0 && InterlockedCompareExchange32 ( (UINT32*)Sem, Value, Value + 1 ) != Value); return Value + 1; }
/** Performs an atomic compare exchange operation to get semaphore. The compare exchange operation must be performed using MP safe mechanisms. @param Sem IN: 32-bit unsigned integer OUT: original integer - 1 @return Original integer - 1 **/ UINT32 WaitForSemaphore ( IN OUT volatile UINT32 *Sem ) { UINT32 Value; do { Value = *Sem; } while (Value == 0 || InterlockedCompareExchange32 ( (UINT32*)Sem, Value, Value - 1 ) != Value); return Value - 1; }