#include <ddk/ntddk.h>
#include <internal/se.h>
+#define NDEBUG
#include <internal/debug.h>
/* FUNCTIONS ***************************************************************/
VOID
-SepInitPrivileges(VOID)
+SepInitPrivileges (VOID)
{
- SeCreateTokenPrivilege.QuadPart = SE_CREATE_TOKEN_PRIVILEGE;
- SeAssignPrimaryTokenPrivilege.QuadPart = SE_ASSIGNPRIMARYTOKEN_PRIVILEGE;
- SeLockMemoryPrivilege.QuadPart = SE_LOCK_MEMORY_PRIVILEGE;
- SeIncreaseQuotaPrivilege.QuadPart = SE_INCREASE_QUOTA_PRIVILEGE;
- SeUnsolicitedInputPrivilege.QuadPart = SE_UNSOLICITED_INPUT_PRIVILEGE;
- SeTcbPrivilege.QuadPart = SE_TCB_PRIVILEGE;
- SeSecurityPrivilege.QuadPart = SE_SECURITY_PRIVILEGE;
- SeTakeOwnershipPrivilege.QuadPart = SE_TAKE_OWNERSHIP_PRIVILEGE;
- SeLoadDriverPrivilege.QuadPart = SE_LOAD_DRIVER_PRIVILEGE;
- SeSystemProfilePrivilege.QuadPart = SE_SYSTEM_PROFILE_PRIVILEGE;
- SeSystemtimePrivilege.QuadPart = SE_SYSTEMTIME_PRIVILEGE;
- SeProfileSingleProcessPrivilege.QuadPart = SE_PROF_SINGLE_PROCESS_PRIVILEGE;
- SeIncreaseBasePriorityPrivilege.QuadPart = SE_INC_BASE_PRIORITY_PRIVILEGE;
- SeCreatePagefilePrivilege.QuadPart = SE_CREATE_PAGEFILE_PRIVILEGE;
- SeCreatePermanentPrivilege.QuadPart = SE_CREATE_PERMANENT_PRIVILEGE;
- SeBackupPrivilege.QuadPart = SE_BACKUP_PRIVILEGE;
- SeRestorePrivilege.QuadPart = SE_RESTORE_PRIVILEGE;
- SeShutdownPrivilege.QuadPart = SE_SHUTDOWN_PRIVILEGE;
- SeDebugPrivilege.QuadPart = SE_DEBUG_PRIVILEGE;
- SeAuditPrivilege.QuadPart = SE_AUDIT_PRIVILEGE;
- SeSystemEnvironmentPrivilege.QuadPart = SE_SYSTEM_ENVIRONMENT_PRIVILEGE;
- SeChangeNotifyPrivilege.QuadPart = SE_CHANGE_NOTIFY_PRIVILEGE;
- SeRemoteShutdownPrivilege.QuadPart = SE_REMOTE_SHUTDOWN_PRIVILEGE;
+ SeCreateTokenPrivilege.LowPart = SE_CREATE_TOKEN_PRIVILEGE;
+ SeCreateTokenPrivilege.HighPart = 0;
+ SeAssignPrimaryTokenPrivilege.LowPart = SE_ASSIGNPRIMARYTOKEN_PRIVILEGE;
+ SeAssignPrimaryTokenPrivilege.HighPart = 0;
+ SeLockMemoryPrivilege.LowPart = SE_LOCK_MEMORY_PRIVILEGE;
+ SeLockMemoryPrivilege.HighPart = 0;
+ SeIncreaseQuotaPrivilege.LowPart = SE_INCREASE_QUOTA_PRIVILEGE;
+ SeIncreaseQuotaPrivilege.HighPart = 0;
+ SeUnsolicitedInputPrivilege.LowPart = SE_UNSOLICITED_INPUT_PRIVILEGE;
+ SeUnsolicitedInputPrivilege.HighPart = 0;
+ SeTcbPrivilege.LowPart = SE_TCB_PRIVILEGE;
+ SeTcbPrivilege.HighPart = 0;
+ SeSecurityPrivilege.LowPart = SE_SECURITY_PRIVILEGE;
+ SeSecurityPrivilege.HighPart = 0;
+ SeTakeOwnershipPrivilege.LowPart = SE_TAKE_OWNERSHIP_PRIVILEGE;
+ SeTakeOwnershipPrivilege.HighPart = 0;
+ SeLoadDriverPrivilege.LowPart = SE_LOAD_DRIVER_PRIVILEGE;
+ SeLoadDriverPrivilege.HighPart = 0;
+ SeSystemProfilePrivilege.LowPart = SE_SYSTEM_PROFILE_PRIVILEGE;
+ SeSystemProfilePrivilege.HighPart = 0;
+ SeSystemtimePrivilege.LowPart = SE_SYSTEMTIME_PRIVILEGE;
+ SeSystemtimePrivilege.HighPart = 0;
+ SeProfileSingleProcessPrivilege.LowPart = SE_PROF_SINGLE_PROCESS_PRIVILEGE;
+ SeProfileSingleProcessPrivilege.HighPart = 0;
+ SeIncreaseBasePriorityPrivilege.LowPart = SE_INC_BASE_PRIORITY_PRIVILEGE;
+ SeIncreaseBasePriorityPrivilege.HighPart = 0;
+ SeCreatePagefilePrivilege.LowPart = SE_CREATE_PAGEFILE_PRIVILEGE;
+ SeCreatePagefilePrivilege.HighPart = 0;
+ SeCreatePermanentPrivilege.LowPart = SE_CREATE_PERMANENT_PRIVILEGE;
+ SeCreatePermanentPrivilege.HighPart = 0;
+ SeBackupPrivilege.LowPart = SE_BACKUP_PRIVILEGE;
+ SeBackupPrivilege.HighPart = 0;
+ SeRestorePrivilege.LowPart = SE_RESTORE_PRIVILEGE;
+ SeRestorePrivilege.HighPart = 0;
+ SeShutdownPrivilege.LowPart = SE_SHUTDOWN_PRIVILEGE;
+ SeShutdownPrivilege.HighPart = 0;
+ SeDebugPrivilege.LowPart = SE_DEBUG_PRIVILEGE;
+ SeDebugPrivilege.HighPart = 0;
+ SeAuditPrivilege.LowPart = SE_AUDIT_PRIVILEGE;
+ SeAuditPrivilege.HighPart = 0;
+ SeSystemEnvironmentPrivilege.LowPart = SE_SYSTEM_ENVIRONMENT_PRIVILEGE;
+ SeSystemEnvironmentPrivilege.HighPart = 0;
+ SeChangeNotifyPrivilege.LowPart = SE_CHANGE_NOTIFY_PRIVILEGE;
+ SeChangeNotifyPrivilege.HighPart = 0;
+ SeRemoteShutdownPrivilege.LowPart = SE_REMOTE_SHUTDOWN_PRIVILEGE;
+ SeRemoteShutdownPrivilege.HighPart = 0;
}
-BOOLEAN SepPrivilegeCheck(PACCESS_TOKEN Token,
- PLUID_AND_ATTRIBUTES Privileges,
- ULONG PrivilegeCount,
- ULONG PrivilegeControl,
- KPROCESSOR_MODE PreviousMode)
+BOOLEAN
+SepPrivilegeCheck (PACCESS_TOKEN Token,
+ PLUID_AND_ATTRIBUTES Privileges,
+ ULONG PrivilegeCount,
+ ULONG PrivilegeControl,
+ KPROCESSOR_MODE PreviousMode)
{
- ULONG i;
- PLUID_AND_ATTRIBUTES Current;
- ULONG j;
- ULONG k;
-
- if (PreviousMode == KernelMode)
- {
- return(TRUE);
- }
-
- j = 0;
- if (PrivilegeCount != 0)
- {
- k = PrivilegeCount;
- do
- {
- i = Token->PrivilegeCount;
- Current = Token->Privileges;
- for (i = 0; i < Token->PrivilegeCount; i++)
- {
- if (!(Current[i].Attributes & SE_PRIVILEGE_ENABLED) &&
- Privileges[i].Luid.u.LowPart ==
- Current[i].Luid.u.LowPart &&
- Privileges[i].Luid.u.HighPart ==
- Current[i].Luid.u.HighPart)
+ ULONG i;
+ ULONG j;
+ ULONG k;
+
+ DPRINT ("SepPrivilegeCheck() called\n");
+
+ if (PreviousMode == KernelMode)
+ {
+ return TRUE;
+ }
+
+ k = 0;
+ if (PrivilegeCount > 0)
+ {
+ for (i = 0; i < Token->PrivilegeCount; i++)
+ {
+ for (j = 0; j < PrivilegeCount; j++)
+ {
+ if (Token->Privileges[i].Luid.LowPart == Privileges[j].Luid.LowPart &&
+ Token->Privileges[i].Luid.HighPart == Privileges[j].Luid.HighPart)
+ {
+ DPRINT ("Found privilege\n");
+ DPRINT ("Privilege attributes %lx\n",
+ Token->Privileges[i].Attributes);
+
+ if (Token->Privileges[i].Attributes & SE_PRIVILEGE_ENABLED)
{
- Privileges[i].Attributes =
- Privileges[i].Attributes |
- SE_PRIVILEGE_USED_FOR_ACCESS;
- j++;
- break;
+ Privileges[j].Attributes |= SE_PRIVILEGE_USED_FOR_ACCESS;
+ k++;
}
- }
- k--;
- } while (k > 0);
- }
-
- if ((PrivilegeControl & PRIVILEGE_SET_ALL_NECESSARY) &&
- PrivilegeCount == j)
- {
- return(TRUE);
- }
-
- if (j > 0 &&
- !(PrivilegeControl & PRIVILEGE_SET_ALL_NECESSARY))
- {
- return(TRUE);
- }
-
- return(FALSE);
+ }
+ }
+ }
+ }
+
+ if ((PrivilegeControl & PRIVILEGE_SET_ALL_NECESSARY) &&
+ PrivilegeCount == k)
+ {
+ return TRUE;
+ }
+
+ if (k > 0 &&
+ !(PrivilegeControl & PRIVILEGE_SET_ALL_NECESSARY))
+ {
+ return TRUE;
+ }
+
+ return FALSE;
}
-NTSTATUS SeCaptureLuidAndAttributesArray(PLUID_AND_ATTRIBUTES Src,
- ULONG PrivilegeCount,
- KPROCESSOR_MODE PreviousMode,
- PLUID_AND_ATTRIBUTES AllocatedMem,
- ULONG AllocatedLength,
- POOL_TYPE PoolType,
- ULONG d,
- PLUID_AND_ATTRIBUTES* Dest,
- PULONG Length)
+NTSTATUS
+SeCaptureLuidAndAttributesArray (PLUID_AND_ATTRIBUTES Src,
+ ULONG PrivilegeCount,
+ KPROCESSOR_MODE PreviousMode,
+ PLUID_AND_ATTRIBUTES AllocatedMem,
+ ULONG AllocatedLength,
+ POOL_TYPE PoolType,
+ ULONG d,
+ PLUID_AND_ATTRIBUTES* Dest,
+ PULONG Length)
{
- PLUID_AND_ATTRIBUTES* NewMem;
- ULONG SrcLength;
-
- if (PrivilegeCount == 0)
- {
- *Dest = 0;
- *Length = 0;
- return(STATUS_SUCCESS);
- }
- if (PreviousMode == 0 && d == 0)
- {
- *Dest = Src;
- return(STATUS_SUCCESS);
- }
- SrcLength = ((PrivilegeCount * sizeof(LUID_AND_ATTRIBUTES)) + 3) & 0xfc;
- *Length = SrcLength;
- if (AllocatedMem == NULL)
- {
- NewMem = ExAllocatePool(PoolType, SrcLength);
- *Dest = (PLUID_AND_ATTRIBUTES)NewMem;
- if (NewMem == NULL)
- {
- return(STATUS_UNSUCCESSFUL);
- }
- }
- else
- {
- if (SrcLength > AllocatedLength)
- {
- return(STATUS_UNSUCCESSFUL);
- }
- *Dest = AllocatedMem;
- }
- memmove(*Dest, Src, SrcLength);
- return(STATUS_SUCCESS);
+ PLUID_AND_ATTRIBUTES* NewMem;
+ ULONG SrcLength;
+
+ if (PrivilegeCount == 0)
+ {
+ *Dest = 0;
+ *Length = 0;
+ return STATUS_SUCCESS;
+ }
+
+ if (PreviousMode == KernelMode && d == 0)
+ {
+ *Dest = Src;
+ return STATUS_SUCCESS;
+ }
+
+ SrcLength = ((PrivilegeCount * sizeof(LUID_AND_ATTRIBUTES)) + 3) & 0xfc;
+ *Length = SrcLength;
+ if (AllocatedMem == NULL)
+ {
+ NewMem = ExAllocatePool (PoolType,
+ SrcLength);
+ *Dest = (PLUID_AND_ATTRIBUTES)NewMem;
+ if (NewMem == NULL)
+ {
+ return STATUS_UNSUCCESSFUL;
+ }
+ }
+ else
+ {
+ if (SrcLength > AllocatedLength)
+ {
+ return STATUS_UNSUCCESSFUL;
+ }
+ *Dest = AllocatedMem;
+ }
+ memmove (*Dest, Src, SrcLength);
+
+ return STATUS_SUCCESS;
}
+
VOID
-SeReleaseLuidAndAttributesArray(PLUID_AND_ATTRIBUTES Privilege,
- KPROCESSOR_MODE PreviousMode,
- ULONG a)
+SeReleaseLuidAndAttributesArray (PLUID_AND_ATTRIBUTES Privilege,
+ KPROCESSOR_MODE PreviousMode,
+ ULONG a)
{
- ExFreePool(Privilege);
+ ExFreePool (Privilege);
}
+
NTSTATUS STDCALL
-NtPrivilegeCheck(IN HANDLE ClientToken,
- IN PPRIVILEGE_SET RequiredPrivileges,
- IN PBOOLEAN Result)
+NtPrivilegeCheck (IN HANDLE ClientToken,
+ IN PPRIVILEGE_SET RequiredPrivileges,
+ IN PBOOLEAN Result)
{
- NTSTATUS Status;
- PACCESS_TOKEN Token;
- ULONG PrivilegeCount;
- BOOLEAN TResult;
- ULONG PrivilegeControl;
- PLUID_AND_ATTRIBUTES Privilege;
- ULONG Length;
-
- Status = ObReferenceObjectByHandle(ClientToken,
+ PLUID_AND_ATTRIBUTES Privilege;
+ PACCESS_TOKEN Token;
+ ULONG PrivilegeCount;
+ ULONG PrivilegeControl;
+ ULONG Length;
+ NTSTATUS Status;
+
+ Status = ObReferenceObjectByHandle (ClientToken,
0,
SepTokenObjectType,
UserMode,
(PVOID*)&Token,
NULL);
- if (!NT_SUCCESS(Status))
- {
- return(Status);
- }
- if (Token->TokenType == TokenImpersonation &&
- Token->ImpersonationLevel < SecurityAnonymous)
- {
- ObDereferenceObject(Token);
- return(STATUS_UNSUCCESSFUL);
- }
- PrivilegeCount = RequiredPrivileges->PrivilegeCount;
- PrivilegeControl = RequiredPrivileges->Control;
- Privilege = 0;
- Status = SeCaptureLuidAndAttributesArray(RequiredPrivileges->Privilege,
+ if (!NT_SUCCESS(Status))
+ {
+ return Status;
+ }
+
+ if (Token->TokenType == TokenImpersonation &&
+ Token->ImpersonationLevel < SecurityAnonymous)
+ {
+ ObDereferenceObject (Token);
+ return STATUS_UNSUCCESSFUL;
+ }
+
+ PrivilegeCount = RequiredPrivileges->PrivilegeCount;
+ PrivilegeControl = RequiredPrivileges->Control;
+ Privilege = 0;
+ Status = SeCaptureLuidAndAttributesArray (RequiredPrivileges->Privilege,
PrivilegeCount,
1,
0,
1,
&Privilege,
&Length);
- if (!NT_SUCCESS(Status))
- {
- ObDereferenceObject(Token);
- return(STATUS_UNSUCCESSFUL);
- }
- TResult = SepPrivilegeCheck(Token,
+ if (!NT_SUCCESS(Status))
+ {
+ ObDereferenceObject (Token);
+ return STATUS_UNSUCCESSFUL;
+ }
+
+ *Result = SepPrivilegeCheck (Token,
Privilege,
PrivilegeCount,
PrivilegeControl,
UserMode);
- memmove(RequiredPrivileges->Privilege, Privilege, Length);
- *Result = TResult;
- SeReleaseLuidAndAttributesArray(Privilege, UserMode, 1);
- return(STATUS_SUCCESS);
+
+ memmove (RequiredPrivileges->Privilege,
+ Privilege,
+ Length);
+
+ SeReleaseLuidAndAttributesArray (Privilege,
+ UserMode,
+ 1);
+
+ return STATUS_SUCCESS;
}
+
+/*
+ * @implemented
+ */
BOOLEAN STDCALL
-SePrivilegeCheck(PPRIVILEGE_SET Privileges,
- PSECURITY_SUBJECT_CONTEXT SubjectContext,
- KPROCESSOR_MODE PreviousMode)
+SePrivilegeCheck (PPRIVILEGE_SET Privileges,
+ PSECURITY_SUBJECT_CONTEXT SubjectContext,
+ KPROCESSOR_MODE PreviousMode)
{
- PACCESS_TOKEN Token = NULL;
-
- if (SubjectContext->ClientToken == NULL)
- {
- Token = SubjectContext->PrimaryToken;
- }
- else
- {
- Token = SubjectContext->ClientToken;
- if (SubjectContext->ImpersonationLevel < 2)
- {
- return(FALSE);
- }
- }
-
- return(SepPrivilegeCheck(Token,
+ PACCESS_TOKEN Token = NULL;
+
+ if (SubjectContext->ClientToken == NULL)
+ {
+ Token = SubjectContext->PrimaryToken;
+ }
+ else
+ {
+ Token = SubjectContext->ClientToken;
+ if (SubjectContext->ImpersonationLevel < 2)
+ {
+ return FALSE;
+ }
+ }
+
+ return SepPrivilegeCheck (Token,
Privileges->Privilege,
Privileges->PrivilegeCount,
Privileges->Control,
- PreviousMode));
+ PreviousMode);
}
+
+/*
+ * @implemented
+ */
BOOLEAN STDCALL
-SeSinglePrivilegeCheck(IN LUID PrivilegeValue,
- IN KPROCESSOR_MODE PreviousMode)
+SeSinglePrivilegeCheck (IN LUID PrivilegeValue,
+ IN KPROCESSOR_MODE PreviousMode)
{
- SECURITY_SUBJECT_CONTEXT SubjectContext;
- BOOLEAN r;
- PRIVILEGE_SET Priv;
-
- SeCaptureSubjectContext(&SubjectContext);
-
- Priv.PrivilegeCount = 1;
- Priv.Control = 1;
- Priv.Privilege[0].Luid = PrivilegeValue;
- Priv.Privilege[0].Attributes = 0;
-
- r = SePrivilegeCheck(&Priv,
- &SubjectContext,
- PreviousMode);
-
- if (PreviousMode != KernelMode)
- {
+ SECURITY_SUBJECT_CONTEXT SubjectContext;
+ PRIVILEGE_SET Priv;
+ BOOLEAN Result;
+
+ SeCaptureSubjectContext (&SubjectContext);
+
+ Priv.PrivilegeCount = 1;
+ Priv.Control = PRIVILEGE_SET_ALL_NECESSARY;
+ Priv.Privilege[0].Luid = PrivilegeValue;
+ Priv.Privilege[0].Attributes = SE_PRIVILEGE_ENABLED;
+
+ Result = SePrivilegeCheck (&Priv,
+ &SubjectContext,
+ PreviousMode);
+
+ if (PreviousMode != KernelMode)
+ {
#if 0
- SePrivilegeServiceAuditAlarm(0,
+ SePrivilegedServiceAuditAlarm (0,
&SubjectContext,
&PrivilegeValue);
#endif
- }
- SeReleaseSubjectContext(&SubjectContext);
- return(r);
+ }
+
+ SeReleaseSubjectContext (&SubjectContext);
+
+ return Result;
}
+/* EOF */