secure access to buffers in NtAllocateLocallyUniqueId
Modified: trunk/reactos/ntoskrnl/include/internal/ex.h
Modified: trunk/reactos/ntoskrnl/se/luid.c
Modified: trunk/reactos/ntoskrnl/se/token.c
_____
Modified: trunk/reactos/ntoskrnl/include/internal/ex.h
--- trunk/reactos/ntoskrnl/include/internal/ex.h 2005-02-13
23:10:36 UTC (rev 13551)
+++ trunk/reactos/ntoskrnl/include/internal/ex.h 2005-02-14
00:28:12 UTC (rev 13552)
@@ -120,6 +120,9 @@
NTSTATUS
ExpSetTimeZoneInformation(PTIME_ZONE_INFORMATION TimeZoneInformation);
+NTSTATUS
+ExpAllocateLocallyUniqueId(OUT LUID *LocallyUniqueId);;
+
#define InterlockedDecrementUL(Addend) \
(ULONG)InterlockedDecrement((PLONG)(Addend))
_____
Modified: trunk/reactos/ntoskrnl/se/luid.c
--- trunk/reactos/ntoskrnl/se/luid.c 2005-02-13 23:10:36 UTC (rev
13551)
+++ trunk/reactos/ntoskrnl/se/luid.c 2005-02-14 00:28:12 UTC (rev
13552)
@@ -15,7 +15,6 @@
/* GLOBALS
*******************************************************************/
-static KSPIN_LOCK LuidLock;
static LARGE_INTEGER LuidIncrement;
static LARGE_INTEGER LuidValue;
@@ -26,34 +25,79 @@
{
LUID DummyLuidValue = SYSTEM_LUID;
- KeInitializeSpinLock(&LuidLock);
LuidValue.u.HighPart = DummyLuidValue.HighPart;
LuidValue.u.LowPart = DummyLuidValue.LowPart;
LuidIncrement.QuadPart = 1;
}
+NTSTATUS
+ExpAllocateLocallyUniqueId(OUT LUID *LocallyUniqueId)
+{
+ LARGE_INTEGER NewLuid, PrevLuid;
+
+ /* atomically increment the luid */
+ do
+ {
+ PrevLuid = (volatile LARGE_INTEGER)LuidValue;
+ NewLuid = RtlLargeIntegerAdd(PrevLuid,
+ LuidIncrement);
+ } while(ExfInterlockedCompareExchange64(&LuidValue.QuadPart,
+ &NewLuid.QuadPart,
+ &PrevLuid.QuadPart) !=
PrevLuid.QuadPart);
+
+ LocallyUniqueId->LowPart = NewLuid.u.LowPart;
+ LocallyUniqueId->HighPart = NewLuid.u.HighPart;
+
+ return STATUS_SUCCESS;
+}
+
+
/*
* @implemented
*/
NTSTATUS STDCALL
NtAllocateLocallyUniqueId(OUT LUID *LocallyUniqueId)
{
- LARGE_INTEGER ReturnedLuid;
- KIRQL Irql;
+ LUID NewLuid;
+ KPROCESSOR_MODE PreviousMode;
+ NTSTATUS Status = STATUS_SUCCESS;
+
+ PreviousMode = ExGetPreviousMode();
+
+ if(PreviousMode != KernelMode)
+ {
+ _SEH_TRY
+ {
+ ProbeForWrite(LocallyUniqueId,
+ sizeof(LUID),
+ sizeof(ULONG));
+ }
+ _SEH_HANDLE
+ {
+ Status = _SEH_GetExceptionCode();
+ }
+ _SEH_END;
+
+ if(!NT_SUCCESS(Status))
+ {
+ return Status;
+ }
+ }
- KeAcquireSpinLock(&LuidLock,
- &Irql);
- ReturnedLuid = LuidValue;
- LuidValue = RtlLargeIntegerAdd(LuidValue,
- LuidIncrement);
- KeReleaseSpinLock(&LuidLock,
- Irql);
+ Status = ExpAllocateLocallyUniqueId(&NewLuid);
- LocallyUniqueId->LowPart = ReturnedLuid.u.LowPart;
- LocallyUniqueId->HighPart = ReturnedLuid.u.HighPart;
+ _SEH_TRY
+ {
+ *LocallyUniqueId = NewLuid;
+ }
+ _SEH_HANDLE
+ {
+ Status = _SEH_GetExceptionCode();
+ }
+ _SEH_END;
- return(STATUS_SUCCESS);
+ return Status;
}
_____
Modified: trunk/reactos/ntoskrnl/se/token.c
--- trunk/reactos/ntoskrnl/se/token.c 2005-02-13 23:10:36 UTC (rev
13551)
+++ trunk/reactos/ntoskrnl/se/token.c 2005-02-14 00:28:12 UTC (rev
13552)
@@ -1415,21 +1415,21 @@
return(Status);
}
- Status = NtAllocateLocallyUniqueId(&AccessToken->TokenId);
+ Status = ExpAllocateLocallyUniqueId(&AccessToken->TokenId);
if (!NT_SUCCESS(Status))
{
ObDereferenceObject(AccessToken);
return(Status);
}
- Status = NtAllocateLocallyUniqueId(&AccessToken->ModifiedId);
+ Status = ExpAllocateLocallyUniqueId(&AccessToken->ModifiedId);
if (!NT_SUCCESS(Status))
{
ObDereferenceObject(AccessToken);
return(Status);
}
- Status = NtAllocateLocallyUniqueId(&AccessToken->AuthenticationId);
+ Status = ExpAllocateLocallyUniqueId(&AccessToken->AuthenticationId);
if (!NT_SUCCESS(Status))
{
ObDereferenceObject(AccessToken);
Show replies by date