ReactOS  0.4.15-dev-4869-g35a816a
token.c
Go to the documentation of this file.
1 /*
2  * PROJECT: ReactOS Kernel
3  * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later)
4  * PURPOSE: Security access token implementation base support routines
5  * COPYRIGHT: Copyright David Welch <welch@cwcom.net>
6  * Copyright 2021-2022 George BiČ™oc <george.bisoc@reactos.org>
7  */
8 
9 /* INCLUDES *******************************************************************/
10 
11 #include <ntoskrnl.h>
12 #define NDEBUG
13 #include <debug.h>
14 
15 /* GLOBALS ********************************************************************/
16 
18 
19 TOKEN_SOURCE SeSystemTokenSource = {"*SYSTEM*", {0}};
22 
24  TOKEN_READ,
28 };
29 
30 /* PRIVATE FUNCTIONS *****************************************************************/
31 
47 {
48  PAGED_CODE();
49 
51  sizeof(ERESOURCE),
53  if (Token->TokenLock == NULL)
54  {
55  DPRINT1("SepCreateTokenLock(): Failed to allocate memory!\n");
57  }
58 
59  ExInitializeResourceLite(Token->TokenLock);
60  return STATUS_SUCCESS;
61 }
62 
73 VOID
76 {
77  PAGED_CODE();
78 
79  ExDeleteResourceLite(Token->TokenLock);
81 }
82 
105 static
106 BOOLEAN
108  _In_ PSID_AND_ATTRIBUTES SidArrayToken1,
109  _In_ ULONG CountSidArray1,
110  _In_ PSID_AND_ATTRIBUTES SidArrayToken2,
111  _In_ ULONG CountSidArray2)
112 {
113  ULONG FirstCount, SecondCount;
114  PSID_AND_ATTRIBUTES FirstSidArray, SecondSidArray;
115  PAGED_CODE();
116 
117  /* Bail out if index counters provided are not equal */
118  if (CountSidArray1 != CountSidArray2)
119  {
120  DPRINT("SepCompareSidAndAttributesFromTokens(): Index counters are not the same!\n");
121  return FALSE;
122  }
123 
124  /* Loop over the SID arrays and compare them */
125  for (FirstCount = 0; FirstCount < CountSidArray1; FirstCount++)
126  {
127  for (SecondCount = 0; SecondCount < CountSidArray2; SecondCount++)
128  {
129  FirstSidArray = &SidArrayToken1[FirstCount];
130  SecondSidArray = &SidArrayToken2[SecondCount];
131 
132  if (RtlEqualSid(FirstSidArray->Sid, SecondSidArray->Sid) &&
133  FirstSidArray->Attributes == SecondSidArray->Attributes)
134  {
135  break;
136  }
137  }
138 
139  /* We've exhausted the array of the second token without finding this one */
140  if (SecondCount == CountSidArray2)
141  {
142  DPRINT("SepCompareSidAndAttributesFromTokens(): No matching elements could be found in either token!\n");
143  return FALSE;
144  }
145  }
146 
147  return TRUE;
148 }
149 
172 static
173 BOOLEAN
175  _In_ PLUID_AND_ATTRIBUTES PrivArrayToken1,
176  _In_ ULONG CountPrivArray1,
177  _In_ PLUID_AND_ATTRIBUTES PrivArrayToken2,
178  _In_ ULONG CountPrivArray2)
179 {
180  ULONG FirstCount, SecondCount;
181  PLUID_AND_ATTRIBUTES FirstPrivArray, SecondPrivArray;
182  PAGED_CODE();
183 
184  /* Bail out if index counters provided are not equal */
185  if (CountPrivArray1 != CountPrivArray2)
186  {
187  DPRINT("SepComparePrivilegeAndAttributesFromTokens(): Index counters are not the same!\n");
188  return FALSE;
189  }
190 
191  /* Loop over the privilege arrays and compare them */
192  for (FirstCount = 0; FirstCount < CountPrivArray1; FirstCount++)
193  {
194  for (SecondCount = 0; SecondCount < CountPrivArray2; SecondCount++)
195  {
196  FirstPrivArray = &PrivArrayToken1[FirstCount];
197  SecondPrivArray = &PrivArrayToken2[SecondCount];
198 
199  if (RtlEqualLuid(&FirstPrivArray->Luid, &SecondPrivArray->Luid) &&
200  FirstPrivArray->Attributes == SecondPrivArray->Attributes)
201  {
202  break;
203  }
204  }
205 
206  /* We've exhausted the array of the second token without finding this one */
207  if (SecondCount == CountPrivArray2)
208  {
209  DPRINT("SepComparePrivilegeAndAttributesFromTokens(): No matching elements could be found in either token!\n");
210  return FALSE;
211  }
212  }
213 
214  return TRUE;
215 }
216 
241 static
242 NTSTATUS
244  _In_ PTOKEN FirstToken,
245  _In_ PTOKEN SecondToken,
246  _Out_ PBOOLEAN Equal)
247 {
249  PAGED_CODE();
250 
251  ASSERT(FirstToken != SecondToken);
252 
253  /* Lock the tokens */
254  SepAcquireTokenLockShared(FirstToken);
255  SepAcquireTokenLockShared(SecondToken);
256 
257  /* Check if every SID that is present in either token is also present in the other one */
258  if (!SepCompareSidAndAttributesFromTokens(FirstToken->UserAndGroups,
259  FirstToken->UserAndGroupCount,
260  SecondToken->UserAndGroups,
261  SecondToken->UserAndGroupCount))
262  {
263  goto Quit;
264  }
265 
266  /* Is one token restricted but the other isn't? */
267  Restricted = SeTokenIsRestricted(FirstToken);
268  if (Restricted != SeTokenIsRestricted(SecondToken))
269  {
270  /* If that's the case then bail out */
271  goto Quit;
272  }
273 
274  /*
275  * If both tokens are restricted check if every SID
276  * that is restricted in either token is also restricted
277  * in the other one.
278  */
279  if (Restricted)
280  {
281  if (!SepCompareSidAndAttributesFromTokens(FirstToken->RestrictedSids,
282  FirstToken->RestrictedSidCount,
283  SecondToken->RestrictedSids,
284  SecondToken->RestrictedSidCount))
285  {
286  goto Quit;
287  }
288  }
289 
290  /* Check if every privilege present in either token is also present in the other one */
291  if (!SepComparePrivilegeAndAttributesFromTokens(FirstToken->Privileges,
292  FirstToken->PrivilegeCount,
293  SecondToken->Privileges,
294  SecondToken->PrivilegeCount))
295  {
296  goto Quit;
297  }
298 
299  /* If we're here then the tokens are equal */
300  IsEqual = TRUE;
301  DPRINT("SepCompareTokens(): Tokens are equal!\n");
302 
303 Quit:
304  /* Unlock the tokens */
305  SepReleaseTokenLock(SecondToken);
306  SepReleaseTokenLock(FirstToken);
307 
308  *Equal = IsEqual;
309  return STATUS_SUCCESS;
310 }
311 
332 static
333 NTSTATUS
337 {
339  PTOKEN TokenToImpersonate, ProcessToken;
340  ULONG IncludeEveryoneValueData;
341  PAGED_CODE();
342 
343  /*
344  * We must check first which kind of token
345  * shall we assign for the thread to impersonate,
346  * the one with Everyone Group SID or the other
347  * without. Invoke the registry helper to
348  * return the data value for us.
349  */
350  Status = SepRegQueryHelper(L"\\Registry\\Machine\\SYSTEM\\CurrentControlSet\\Control\\Lsa",
351  L"EveryoneIncludesAnonymous",
352  REG_DWORD,
353  sizeof(IncludeEveryoneValueData),
354  &IncludeEveryoneValueData);
355  if (!NT_SUCCESS(Status))
356  {
357  DPRINT1("SepRegQueryHelper(): Failed to query the registry value (Status 0x%lx)\n", Status);
358  return Status;
359  }
360 
361  if (IncludeEveryoneValueData == 0)
362  {
363  DPRINT("SepImpersonateAnonymousToken(): Assigning the token not including the Everyone Group SID...\n");
364  TokenToImpersonate = SeAnonymousLogonTokenNoEveryone;
365  }
366  else
367  {
368  DPRINT("SepImpersonateAnonymousToken(): Assigning the token including the Everyone Group SID...\n");
369  TokenToImpersonate = SeAnonymousLogonToken;
370  }
371 
372  /*
373  * Tell the object manager that we're going to use this token
374  * object now by incrementing the reference count.
375  */
376  Status = ObReferenceObjectByPointer(TokenToImpersonate,
379  PreviousMode);
380  if (!NT_SUCCESS(Status))
381  {
382  DPRINT1("SepImpersonateAnonymousToken(): Couldn't be able to use the token, bail out...\n");
383  return Status;
384  }
385 
386  /*
387  * Reference the primary token of the current process that the anonymous
388  * logon token impersonation procedure is being performed. We'll be going
389  * to use the process' token to figure out if the process is actually
390  * restricted or not.
391  */
393  if (!ProcessToken)
394  {
395  DPRINT1("SepImpersonateAnonymousToken(): Couldn't be able to get the process' primary token, bail out...\n");
396  ObDereferenceObject(TokenToImpersonate);
397  return STATUS_UNSUCCESSFUL;
398  }
399 
400  /* Now, is the token from the current process restricted? */
401  if (SeTokenIsRestricted(ProcessToken))
402  {
403  DPRINT1("SepImpersonateAnonymousToken(): The process is restricted, can't do anything. Bail out...\n");
404  PsDereferencePrimaryToken(ProcessToken);
405  ObDereferenceObject(TokenToImpersonate);
406  return STATUS_ACCESS_DENIED;
407  }
408 
409  /*
410  * Finally it's time to impersonate! But first, fast dereference the
411  * process' primary token as we no longer need it.
412  */
415  if (!NT_SUCCESS(Status))
416  {
417  DPRINT1("SepImpersonateAnonymousToken(): Failed to impersonate, bail out...\n");
418  ObDereferenceObject(TokenToImpersonate);
419  return Status;
420  }
421 
422  return Status;
423 }
424 
441 VOID
444  _In_ ULONG Index)
445 {
446  ULONG TokenFlag;
447  ASSERT(Index < Token->PrivilegeCount);
448 
449  /* The high part of all values we are interested in is 0 */
450  if (Token->Privileges[Index].Luid.HighPart != 0)
451  {
452  return;
453  }
454 
455  /* Check for certain privileges to update flags */
456  if (Token->Privileges[Index].Luid.LowPart == SE_CHANGE_NOTIFY_PRIVILEGE)
457  {
458  TokenFlag = TOKEN_HAS_TRAVERSE_PRIVILEGE;
459  }
460  else if (Token->Privileges[Index].Luid.LowPart == SE_BACKUP_PRIVILEGE)
461  {
462  TokenFlag = TOKEN_HAS_BACKUP_PRIVILEGE;
463  }
464  else if (Token->Privileges[Index].Luid.LowPart == SE_RESTORE_PRIVILEGE)
465  {
466  TokenFlag = TOKEN_HAS_RESTORE_PRIVILEGE;
467  }
468  else if (Token->Privileges[Index].Luid.LowPart == SE_IMPERSONATE_PRIVILEGE)
469  {
471  }
472  else
473  {
474  /* Nothing to do */
475  return;
476  }
477 
478  /* Check if the specified privilege is enabled */
479  if (Token->Privileges[Index].Attributes & SE_PRIVILEGE_ENABLED)
480  {
481  /* It is enabled, so set the flag */
482  Token->TokenFlags |= TokenFlag;
483  }
484  else
485  {
486  /* Is is disabled, so remove the flag */
487  Token->TokenFlags &= ~TokenFlag;
488  }
489 }
490 
509 BOOLEAN
510 NTAPI
512  _In_ PACCESS_TOKEN _Token,
514  _In_ BOOLEAN TokenLocked)
515 {
516  PSID Sid;
517  BOOLEAN Result;
518  PTOKEN Token = _Token;
519 
520  /* Get the owner SID */
522  ASSERT(Sid != NULL);
523 
524  /* Lock the token if needed */
525  if (!TokenLocked) SepAcquireTokenLockShared(Token);
526 
527  /* Check if the owner SID is found, handling restricted case as well */
529  if ((Result) && (Token->TokenFlags & TOKEN_IS_RESTRICTED))
530  {
532  }
533 
534  /* Release the lock if we had acquired it */
535  if (!TokenLocked) SepReleaseTokenLock(Token);
536 
537  /* Return the result */
538  return Result;
539 }
540 
553 VOID
556 {
557  ULONG i;
558 
559  /* Loop all privileges */
560  for (i = 0; i < Token->PrivilegeCount; i++)
561  {
562  /* Updates the flags for this privilege */
564  }
565 }
566 
581 VOID
584  _In_ ULONG Index)
585 {
586  ULONG MoveCount;
587  ASSERT(Index < Token->PrivilegeCount);
588 
589  /* Calculate the number of trailing privileges */
590  MoveCount = Token->PrivilegeCount - Index - 1;
591  if (MoveCount != 0)
592  {
593  /* Move them one location ahead */
594  RtlMoveMemory(&Token->Privileges[Index],
595  &Token->Privileges[Index + 1],
596  MoveCount * sizeof(LUID_AND_ATTRIBUTES));
597  }
598 
599  /* Update privilege count */
600  Token->PrivilegeCount--;
601 }
602 
617 VOID
620  _In_ ULONG Index)
621 {
622  ULONG MoveCount;
623  ASSERT(Index < Token->UserAndGroupCount);
624 
625  /* Calculate the number of trailing groups */
626  MoveCount = Token->UserAndGroupCount - Index - 1;
627  if (MoveCount != 0)
628  {
629  /* Time to remove the group by moving one location ahead */
630  RtlMoveMemory(&Token->UserAndGroups[Index],
631  &Token->UserAndGroups[Index + 1],
632  MoveCount * sizeof(SID_AND_ATTRIBUTES));
633  }
634 
635  /* Remove one group count */
636  Token->UserAndGroupCount--;
637 }
638 
650 VOID
651 NTAPI
653  _Inout_ PVOID ProxyData)
654 {
656 }
657 
672 NTSTATUS
673 NTAPI
675  _Out_ PVOID* Dest,
676  _In_ PVOID Src)
677 {
679  return STATUS_NOT_IMPLEMENTED;
680 }
681 
703 NTSTATUS
704 NTAPI
707  _In_ PACCESS_TOKEN NewAccessToken,
708  _Out_ PACCESS_TOKEN* OldAccessToken)
709 {
710  PTOKEN OldToken;
711  PTOKEN NewToken = (PTOKEN)NewAccessToken;
712 
713  PAGED_CODE();
714 
715  if (NewToken->TokenType != TokenPrimary)
716  return STATUS_BAD_TOKEN_TYPE;
717 
718  if (NewToken->TokenInUse)
719  {
722 
723  /* Maybe we're trying to set the same token */
724  OldToken = PsReferencePrimaryToken(Process);
725  if (OldToken == NewToken)
726  {
727  /* So it's a nop. */
728  *OldAccessToken = OldToken;
729  return STATUS_SUCCESS;
730  }
731 
732  Status = SepCompareTokens(OldToken, NewToken, &IsEqual);
733  if (!NT_SUCCESS(Status))
734  {
735  PsDereferencePrimaryToken(OldToken);
736  *OldAccessToken = NULL;
737  return Status;
738  }
739 
740  if (!IsEqual)
741  {
742  PsDereferencePrimaryToken(OldToken);
743  *OldAccessToken = NULL;
745  }
746  /* Silently return STATUS_SUCCESS but do not set the new token,
747  * as it's already in use elsewhere. */
748  *OldAccessToken = OldToken;
749  return STATUS_SUCCESS;
750  }
751 
752  /* Lock the new token */
754 
755  /* Mark new token in use */
756  NewToken->TokenInUse = TRUE;
757 
758  /* Set the session ID for the new token */
759  NewToken->SessionId = MmGetSessionId(Process);
760 
761  /* Unlock the new token */
762  SepReleaseTokenLock(NewToken);
763 
764  /* Reference the new token */
765  ObReferenceObject(NewToken);
766 
767  /* Replace the old with the new */
768  OldToken = ObFastReplaceObject(&Process->Token, NewToken);
769 
770  /* Lock the old token */
772 
773  /* Mark the old token as free */
774  OldToken->TokenInUse = FALSE;
775 
776  /* Unlock the old token */
777  SepReleaseTokenLock(OldToken);
778 
779  *OldAccessToken = (PACCESS_TOKEN)OldToken;
780  return STATUS_SUCCESS;
781 }
782 
793 VOID
794 NTAPI
797 {
798  PTOKEN OldToken;
799 
800  /* Remove the Token */
801  OldToken = ObFastReplaceObject(&Process->Token, NULL);
802 
803  /* Mark the Old Token as free */
804  OldToken->TokenInUse = FALSE;
805 
806  /* Dereference the Token */
807  ObDereferenceObject(OldToken);
808 }
809 
823 ULONG
825  _In_ ULONG Count,
827 {
828  ULONG i;
829  ULONG uLength;
830 
831  PAGED_CODE();
832 
833  uLength = Count * sizeof(SID_AND_ATTRIBUTES);
834  for (i = 0; i < Count; i++)
835  uLength += RtlLengthSid(Src[i].Sid);
836 
837  return uLength;
838 }
839 
869 NTSTATUS
871  _In_ PTOKEN Token,
873  _In_opt_ PSID DefaultOwner,
874  _Out_opt_ PULONG PrimaryGroupIndex,
875  _Out_opt_ PULONG DefaultOwnerIndex)
876 {
877  ULONG i;
878 
879  /* We should return at least a search result */
880  if (!PrimaryGroupIndex && !DefaultOwnerIndex)
882 
883  if (PrimaryGroupIndex)
884  {
885  /* Initialize with an invalid index */
886  // Token->PrimaryGroup = NULL;
887  *PrimaryGroupIndex = Token->UserAndGroupCount;
888  }
889 
890  if (DefaultOwnerIndex)
891  {
892  if (DefaultOwner)
893  {
894  /* An owner is specified: check whether this is actually the user */
895  if (RtlEqualSid(Token->UserAndGroups[0].Sid, DefaultOwner))
896  {
897  /*
898  * It's the user (first element in array): set it
899  * as the owner and stop the search for it.
900  */
901  *DefaultOwnerIndex = 0;
902  DefaultOwnerIndex = NULL;
903  }
904  else
905  {
906  /* An owner is specified: initialize with an invalid index */
907  *DefaultOwnerIndex = Token->UserAndGroupCount;
908  }
909  }
910  else
911  {
912  /*
913  * No owner specified: set the user (first element in array)
914  * as the owner and stop the search for it.
915  */
916  *DefaultOwnerIndex = 0;
917  DefaultOwnerIndex = NULL;
918  }
919  }
920 
921  /* Validate and set the primary group and default owner indices */
922  for (i = 0; i < Token->UserAndGroupCount; i++)
923  {
924  /* Stop the search if we have found what we searched for */
925  if (!PrimaryGroupIndex && !DefaultOwnerIndex)
926  break;
927 
928  if (DefaultOwnerIndex && DefaultOwner &&
929  RtlEqualSid(Token->UserAndGroups[i].Sid, DefaultOwner) &&
930  (Token->UserAndGroups[i].Attributes & SE_GROUP_OWNER))
931  {
932  /* Owner is found, stop the search for it */
933  *DefaultOwnerIndex = i;
934  DefaultOwnerIndex = NULL;
935  }
936 
937  if (PrimaryGroupIndex &&
938  RtlEqualSid(Token->UserAndGroups[i].Sid, PrimaryGroup))
939  {
940  /* Primary group is found, stop the search for it */
941  // Token->PrimaryGroup = Token->UserAndGroups[i].Sid;
942  *PrimaryGroupIndex = i;
943  PrimaryGroupIndex = NULL;
944  }
945  }
946 
947  if (DefaultOwnerIndex)
948  {
949  if (*DefaultOwnerIndex == Token->UserAndGroupCount)
950  return STATUS_INVALID_OWNER;
951  }
952 
953  if (PrimaryGroupIndex)
954  {
955  if (*PrimaryGroupIndex == Token->UserAndGroupCount)
956  // if (Token->PrimaryGroup == NULL)
958  }
959 
960  return STATUS_SUCCESS;
961 }
962 
984 NTSTATUS
985 NTAPI
987  _In_ PTOKEN ParentToken,
988  _Out_ PTOKEN *Token,
989  _In_ BOOLEAN InUse,
991 {
992  PTOKEN NewToken;
995 
996  /* Initialize the attributes and duplicate it */
998  Status = SepDuplicateToken(ParentToken,
1000  FALSE,
1001  TokenPrimary,
1002  ParentToken->ImpersonationLevel,
1003  KernelMode,
1004  &NewToken);
1005  if (NT_SUCCESS(Status))
1006  {
1007  /* Insert it */
1008  Status = ObInsertObject(NewToken,
1009  NULL,
1010  0,
1011  0,
1012  NULL,
1013  NULL);
1014  if (NT_SUCCESS(Status))
1015  {
1016  /* Set the session ID */
1017  NewToken->SessionId = SessionId;
1018  NewToken->TokenInUse = InUse;
1019 
1020  /* Return the token */
1021  *Token = NewToken;
1022  }
1023  }
1024 
1025  /* Return status */
1026  return Status;
1027 }
1028 
1044 NTSTATUS
1045 NTAPI
1047  _In_ PTOKEN Token,
1049 {
1050  PTOKEN ProcessToken;
1051  LUID ProcessTokenId, CallerParentId;
1052 
1053  /* Assume failure */
1054  *IsChild = FALSE;
1055 
1056  /* Reference the process token */
1057  ProcessToken = PsReferencePrimaryToken(PsGetCurrentProcess());
1058  if (!ProcessToken)
1059  return STATUS_UNSUCCESSFUL;
1060 
1061  /* Get its token ID */
1062  ProcessTokenId = ProcessToken->TokenId;
1063 
1064  /* Dereference the token */
1066 
1067  /* Get our parent token ID */
1068  CallerParentId = Token->ParentTokenId;
1069 
1070  /* Compare the token IDs */
1071  if (RtlEqualLuid(&CallerParentId, &ProcessTokenId))
1072  *IsChild = TRUE;
1073 
1074  /* Return success */
1075  return STATUS_SUCCESS;
1076 }
1077 
1093 NTSTATUS
1094 NTAPI
1096  _In_ PTOKEN Token,
1097  _Out_ PBOOLEAN IsSibling)
1098 {
1099  PTOKEN ProcessToken;
1100  LUID ProcessParentId, ProcessAuthId;
1101  LUID CallerParentId, CallerAuthId;
1102 
1103  /* Assume failure */
1104  *IsSibling = FALSE;
1105 
1106  /* Reference the process token */
1107  ProcessToken = PsReferencePrimaryToken(PsGetCurrentProcess());
1108  if (!ProcessToken)
1109  return STATUS_UNSUCCESSFUL;
1110 
1111  /* Get its parent and authentication IDs */
1112  ProcessParentId = ProcessToken->ParentTokenId;
1113  ProcessAuthId = ProcessToken->AuthenticationId;
1114 
1115  /* Dereference the token */
1117 
1118  /* Get our parent and authentication IDs */
1119  CallerParentId = Token->ParentTokenId;
1120  CallerAuthId = Token->AuthenticationId;
1121 
1122  /* Compare the token IDs */
1123  if (RtlEqualLuid(&CallerParentId, &ProcessParentId) &&
1124  RtlEqualLuid(&CallerAuthId, &ProcessAuthId))
1125  {
1126  *IsSibling = TRUE;
1127  }
1128 
1129  /* Return success */
1130  return STATUS_SUCCESS;
1131 }
1132 
1153 NTSTATUS
1154 NTAPI
1159  _Out_ PACCESS_TOKEN* NewToken)
1160 {
1161  NTSTATUS Status;
1163 
1164  PAGED_CODE();
1165 
1167  NULL,
1168  0,
1169  NULL,
1170  NULL);
1171 
1174  FALSE,
1176  Level,
1177  PreviousMode,
1178  (PTOKEN*)NewToken);
1179 
1180  return Status;
1181 }
1182 
1194 BOOLEAN
1195 NTAPI
1197  _In_ PTOKEN Token)
1198 {
1199  PAGED_CODE();
1200 
1201  return (((PTOKEN)Token)->TokenFlags & TOKEN_SANDBOX_INERT) != 0;
1202 }
1203 
1216 VOID
1217 NTAPI
1219  _In_ PVOID ObjectBody)
1220 {
1221  NTSTATUS Status;
1222  PTOKEN AccessToken = (PTOKEN)ObjectBody;
1223 
1224  DPRINT("SepDeleteToken()\n");
1225 
1226  /* Remove the referenced logon session from token */
1227  if (AccessToken->LogonSession)
1228  {
1230  if (!NT_SUCCESS(Status))
1231  {
1232  /* Something seriously went wrong */
1233  DPRINT1("SepDeleteToken(): Failed to remove the logon session from token (Status: 0x%lx)\n", Status);
1234  return;
1235  }
1236  }
1237 
1238  /* Dereference the logon session */
1239  if ((AccessToken->TokenFlags & TOKEN_SESSION_NOT_REFERENCED) == 0)
1241 
1242  /* Delete the token lock */
1243  if (AccessToken->TokenLock)
1244  SepDeleteTokenLock(AccessToken);
1245 
1246  /* Delete the dynamic information area */
1247  if (AccessToken->DynamicPart)
1249 }
1250 
1259 CODE_SEG("INIT")
1260 VOID
1261 NTAPI
1263 {
1265  OBJECT_TYPE_INITIALIZER ObjectTypeInitializer;
1266 
1267  DPRINT("Creating Token Object Type\n");
1268 
1269  /* Initialize the Token type */
1270  RtlZeroMemory(&ObjectTypeInitializer, sizeof(ObjectTypeInitializer));
1271  RtlInitUnicodeString(&Name, L"Token");
1272  ObjectTypeInitializer.Length = sizeof(ObjectTypeInitializer);
1273  ObjectTypeInitializer.InvalidAttributes = OBJ_OPENLINK;
1274  ObjectTypeInitializer.SecurityRequired = TRUE;
1275  ObjectTypeInitializer.DefaultPagedPoolCharge = sizeof(TOKEN);
1276  ObjectTypeInitializer.GenericMapping = SepTokenMapping;
1277  ObjectTypeInitializer.PoolType = PagedPool;
1278  ObjectTypeInitializer.ValidAccessMask = TOKEN_ALL_ACCESS;
1279  ObjectTypeInitializer.UseDefaultObject = TRUE;
1280  ObjectTypeInitializer.DeleteProcedure = SepDeleteToken;
1281  ObCreateObjectType(&Name, &ObjectTypeInitializer, NULL, &SeTokenObjectType);
1282 }
1283 
1297 VOID
1298 NTAPI
1301  _In_ PTOKEN Token)
1302 {
1303  PAGED_CODE();
1304 
1305  /* Sanity checks */
1306  ASSERT(Token->TokenType == TokenPrimary);
1307  ASSERT(!Token->TokenInUse);
1308 
1309  /* Clean any previous token */
1310  if (Process->Token.Object) SeDeassignPrimaryToken(Process);
1311 
1312  /* Set the new token */
1314  Token->TokenInUse = TRUE;
1316 }
1317 
1331 VOID
1332 NTAPI
1334  _In_ PACCESS_TOKEN _Token,
1335  _Out_ PTOKEN_CONTROL TokenControl)
1336 {
1337  PTOKEN Token = _Token;
1338  PAGED_CODE();
1339 
1340  /* Capture the main fields */
1341  TokenControl->AuthenticationId = Token->AuthenticationId;
1342  TokenControl->TokenId = Token->TokenId;
1343  TokenControl->TokenSource = Token->TokenSource;
1344 
1345  /* Lock the token */
1347 
1348  /* Capture the modified ID */
1349  TokenControl->ModifiedId = Token->ModifiedId;
1350 
1351  /* Unlock it */
1353 }
1354 
1363 CODE_SEG("INIT")
1364 PTOKEN
1365 NTAPI
1367 {
1369  ULONG GroupAttributes, OwnerAttributes;
1371  LARGE_INTEGER Expiration;
1372  SID_AND_ATTRIBUTES UserSid;
1373  ULONG GroupsLength;
1376  PSID Owner;
1377  ULONG i;
1378  PTOKEN Token;
1379  NTSTATUS Status;
1380 
1381  /* Don't ever expire */
1382  Expiration.QuadPart = -1;
1383 
1384  /* All groups mandatory and enabled */
1387 
1388  /* User is Local System */
1389  UserSid.Sid = SeLocalSystemSid;
1390  UserSid.Attributes = 0;
1391 
1392  /* Primary group is Local System */
1394 
1395  /* Owner is Administrators */
1397 
1398  /* Groups are Administrators, World, and Authenticated Users */
1399  Groups[0].Sid = SeAliasAdminsSid;
1400  Groups[0].Attributes = OwnerAttributes;
1401  Groups[1].Sid = SeWorldSid;
1402  Groups[1].Attributes = GroupAttributes;
1404  Groups[2].Attributes = GroupAttributes;
1405  GroupsLength = sizeof(SID_AND_ATTRIBUTES) +
1406  SeLengthSid(Groups[0].Sid) +
1407  SeLengthSid(Groups[1].Sid) +
1408  SeLengthSid(Groups[2].Sid);
1409  ASSERT(GroupsLength <= sizeof(Groups));
1410 
1411  /* Setup the privileges */
1412  i = 0;
1414  Privileges[i++].Luid = SeTcbPrivilege;
1415 
1416  Privileges[i].Attributes = 0;
1418 
1419  Privileges[i].Attributes = 0;
1421 
1424 
1427 
1428  Privileges[i].Attributes = 0;
1430 
1431  Privileges[i].Attributes = 0;
1433 
1436 
1439 
1441  Privileges[i++].Luid = SeDebugPrivilege;
1442 
1444  Privileges[i++].Luid = SeAuditPrivilege;
1445 
1446  Privileges[i].Attributes = 0;
1447  Privileges[i++].Luid = SeSecurityPrivilege;
1448 
1449  Privileges[i].Attributes = 0;
1451 
1454 
1455  Privileges[i].Attributes = 0;
1456  Privileges[i++].Luid = SeBackupPrivilege;
1457 
1458  Privileges[i].Attributes = 0;
1459  Privileges[i++].Luid = SeRestorePrivilege;
1460 
1461  Privileges[i].Attributes = 0;
1462  Privileges[i++].Luid = SeShutdownPrivilege;
1463 
1464  Privileges[i].Attributes = 0;
1466 
1469 
1470  Privileges[i].Attributes = 0;
1472  ASSERT(i == 20);
1473 
1474  /* Setup the object attributes */
1477 
1478  /* Create the token */
1480  KernelMode,
1481  0,
1483  TokenPrimary,
1486  &Expiration,
1487  &UserSid,
1488  3,
1489  Groups,
1490  GroupsLength,
1491  20,
1492  Privileges,
1493  Owner,
1494  PrimaryGroup,
1497  TRUE);
1499 
1500  /* Return the token */
1501  return Token;
1502 }
1503 
1514 CODE_SEG("INIT")
1515 PTOKEN
1517 {
1518  SID_AND_ATTRIBUTES Groups[32], UserSid;
1520  PTOKEN Token;
1521  ULONG GroupsLength;
1522  LARGE_INTEGER Expiration;
1524  NTSTATUS Status;
1525 
1526  /* The token never expires */
1527  Expiration.QuadPart = -1;
1528 
1529  /* The user is the anonymous logon */
1530  UserSid.Sid = SeAnonymousLogonSid;
1531  UserSid.Attributes = 0;
1532 
1533  /* The primary group is also the anonymous logon */
1535 
1536  /* The only group for the token is the World */
1537  Groups[0].Sid = SeWorldSid;
1539  GroupsLength = sizeof(SID_AND_ATTRIBUTES) +
1540  SeLengthSid(Groups[0].Sid);
1541  ASSERT(GroupsLength <= sizeof(Groups));
1542 
1543  /* Initialise the object attributes for the token */
1546 
1547  /* Create token */
1549  KernelMode,
1550  0,
1552  TokenPrimary,
1555  &Expiration,
1556  &UserSid,
1557  1,
1558  Groups,
1559  GroupsLength,
1560  0,
1561  NULL,
1562  NULL,
1563  PrimaryGroup,
1566  TRUE);
1568 
1569  /* Return the anonymous logon token */
1570  return Token;
1571 }
1572 
1582 CODE_SEG("INIT")
1583 PTOKEN
1585 {
1586  SID_AND_ATTRIBUTES UserSid;
1588  PTOKEN Token;
1589  LARGE_INTEGER Expiration;
1591  NTSTATUS Status;
1592 
1593  /* The token never expires */
1594  Expiration.QuadPart = -1;
1595 
1596  /* The user is the anonymous logon */
1597  UserSid.Sid = SeAnonymousLogonSid;
1598  UserSid.Attributes = 0;
1599 
1600  /* The primary group is also the anonymous logon */
1602 
1603  /* Initialise the object attributes for the token */
1606 
1607  /* Create token */
1609  KernelMode,
1610  0,
1612  TokenPrimary,
1615  &Expiration,
1616  &UserSid,
1617  0,
1618  NULL,
1619  0,
1620  0,
1621  NULL,
1622  NULL,
1623  PrimaryGroup,
1626  TRUE);
1628 
1629  /* Return the anonymous (not including everyone) logon token */
1630  return Token;
1631 }
1632 
1633 /* PUBLIC FUNCTIONS ***********************************************************/
1634 
1648 NTSTATUS
1649 NTAPI
1652  _Out_ PULONG pSessionId)
1653 {
1654  PAGED_CODE();
1655 
1656  /* Lock the token */
1658 
1659  *pSessionId = ((PTOKEN)Token)->SessionId;
1660 
1661  /* Unlock the token */
1663 
1664  return STATUS_SUCCESS;
1665 }
1666 
1680 NTSTATUS
1681 NTAPI
1685 {
1686  PAGED_CODE();
1687 
1688  *LogonId = ((PTOKEN)Token)->AuthenticationId;
1689 
1690  return STATUS_SUCCESS;
1691 }
1692 
1704 NTAPI
1707 {
1708  PAGED_CODE();
1709 
1710  return ((PTOKEN)Token)->ImpersonationLevel;
1711 }
1712 
1724 TOKEN_TYPE
1725 NTAPI
1728 {
1729  PAGED_CODE();
1730 
1731  return ((PTOKEN)Token)->TokenType;
1732 }
1733 
1747 BOOLEAN
1748 NTAPI
1751 {
1752  PAGED_CODE();
1753 
1754  // NOTE: Win7+ instead really checks the list of groups in the token
1755  // (since TOKEN_HAS_ADMIN_GROUP == TOKEN_WRITE_RESTRICTED ...)
1756  return (((PTOKEN)Token)->TokenFlags & TOKEN_HAS_ADMIN_GROUP) != 0;
1757 }
1758 
1770 BOOLEAN
1771 NTAPI
1774 {
1775  PAGED_CODE();
1776 
1777  return (((PTOKEN)Token)->TokenFlags & TOKEN_IS_RESTRICTED) != 0;
1778 }
1779 
1795 BOOLEAN
1796 NTAPI
1799 {
1800  PAGED_CODE();
1801 
1802  // NOTE: NT 5.1 SP2 x86 checks the SE_BACKUP_PRIVILEGES_CHECKED flag
1803  // while Vista+ checks the TOKEN_WRITE_RESTRICTED flag as one expects.
1804  return (((PTOKEN)Token)->TokenFlags & SE_BACKUP_PRIVILEGES_CHECKED) != 0;
1805 }
1806 
1826 BOOLEAN
1827 NTAPI
1829  _In_ PTOKEN ProcessToken,
1830  _In_ PTOKEN TokenToImpersonate,
1832 {
1833  BOOLEAN CanImpersonate;
1834  PAGED_CODE();
1835 
1836  /*
1837  * SecurityAnonymous and SecurityIdentification levels do not
1838  * allow impersonation.
1839  */
1842  {
1843  return FALSE;
1844  }
1845 
1846  /* Time to lock our tokens */
1847  SepAcquireTokenLockShared(ProcessToken);
1848  SepAcquireTokenLockShared(TokenToImpersonate);
1849 
1850  /* What kind of authentication ID does the token have? */
1851  if (RtlEqualLuid(&TokenToImpersonate->AuthenticationId,
1853  {
1854  /*
1855  * OK, it looks like the token has an anonymous
1856  * authentication. Is that token created by the system?
1857  */
1858  if (TokenToImpersonate->TokenSource.SourceName != SeSystemTokenSource.SourceName &&
1859  !RtlEqualLuid(&TokenToImpersonate->TokenSource.SourceIdentifier, &SeSystemTokenSource.SourceIdentifier))
1860  {
1861  /* It isn't, we can't impersonate regular tokens */
1862  DPRINT("SeTokenCanImpersonate(): Token has an anonymous authentication ID, can't impersonate!\n");
1863  CanImpersonate = FALSE;
1864  goto Quit;
1865  }
1866  }
1867 
1868  /* Are the SID values from both tokens equal? */
1869  if (!RtlEqualSid(ProcessToken->UserAndGroups->Sid,
1870  TokenToImpersonate->UserAndGroups->Sid))
1871  {
1872  /* They aren't, bail out */
1873  DPRINT("SeTokenCanImpersonate(): Tokens SIDs are not equal!\n");
1874  CanImpersonate = FALSE;
1875  goto Quit;
1876  }
1877 
1878  /*
1879  * Make sure the tokens aren't diverged in terms of
1880  * restrictions, that is, one token is restricted
1881  * but the other one isn't.
1882  */
1883  if (SeTokenIsRestricted(ProcessToken) !=
1884  SeTokenIsRestricted(TokenToImpersonate))
1885  {
1886  /*
1887  * One token is restricted so we cannot
1888  * continue further at this point, bail out.
1889  */
1890  DPRINT("SeTokenCanImpersonate(): One token is restricted, can't continue!\n");
1891  CanImpersonate = FALSE;
1892  goto Quit;
1893  }
1894 
1895  /* If we've reached that far then we can impersonate! */
1896  DPRINT("SeTokenCanImpersonate(): We can impersonate.\n");
1897  CanImpersonate = TRUE;
1898 
1899 Quit:
1900  /* We're done, unlock the tokens now */
1901  SepReleaseTokenLock(ProcessToken);
1902  SepReleaseTokenLock(TokenToImpersonate);
1903 
1904  return CanImpersonate;
1905 }
1906 
1907 /* SYSTEM CALLS ***************************************************************/
1908 
1936 NTSTATUS
1937 NTAPI
1939  _In_ HANDLE ThreadHandle,
1944 {
1945  PETHREAD Thread;
1946  HANDLE hToken;
1947  PTOKEN Token, NewToken = NULL, PrimaryToken;
1953  PACL Dacl = NULL;
1955  NTSTATUS Status;
1956  BOOLEAN RestoreImpersonation = FALSE;
1957 
1958  PAGED_CODE();
1959 
1961 
1962  if (PreviousMode != KernelMode)
1963  {
1964  _SEH2_TRY
1965  {
1967  }
1969  {
1970  /* Return the exception code */
1972  }
1973  _SEH2_END;
1974  }
1975 
1976  /* Validate object attributes */
1978 
1979  /*
1980  * At first open the thread token for information access and verify
1981  * that the token associated with thread is valid.
1982  */
1983 
1986  NULL);
1987  if (!NT_SUCCESS(Status))
1988  {
1989  return Status;
1990  }
1991 
1994  if (Token == NULL)
1995  {
1997  return STATUS_NO_TOKEN;
1998  }
1999 
2001  {
2005  }
2006 
2007  /*
2008  * Revert to self if OpenAsSelf is specified.
2009  */
2010 
2011  if (OpenAsSelf)
2012  {
2013  RestoreImpersonation = PsDisableImpersonation(PsGetCurrentThread(),
2015  }
2016 
2017  if (CopyOnOpen)
2018  {
2019  PrimaryToken = PsReferencePrimaryToken(Thread->ThreadsProcess);
2020 
2021  Status = SepCreateImpersonationTokenDacl(Token, PrimaryToken, &Dacl);
2022 
2023  ObFastDereferenceObject(&Thread->ThreadsProcess->Token, PrimaryToken);
2024 
2025  if (NT_SUCCESS(Status))
2026  {
2027  if (Dacl)
2028  {
2031  if (!NT_SUCCESS(Status))
2032  {
2033  DPRINT1("NtOpenThreadTokenEx(): Failed to create a security descriptor (Status 0x%lx)\n", Status);
2034  }
2035 
2037  FALSE);
2038  if (!NT_SUCCESS(Status))
2039  {
2040  DPRINT1("NtOpenThreadTokenEx(): Failed to set a DACL to the security descriptor (Status 0x%lx)\n", Status);
2041  }
2042  }
2043 
2046 
2049  KernelMode, &NewToken);
2050  if (!NT_SUCCESS(Status))
2051  {
2052  DPRINT1("NtOpenThreadTokenEx(): Failed to duplicate the token (Status 0x%lx)\n", Status);
2053  }
2054 
2055  ObReferenceObject(NewToken);
2056  Status = ObInsertObject(NewToken, NULL, DesiredAccess, 0, NULL,
2057  &hToken);
2058  if (!NT_SUCCESS(Status))
2059  {
2060  DPRINT1("NtOpenThreadTokenEx(): Failed to insert the token object (Status 0x%lx)\n", Status);
2061  }
2062  }
2063  else
2064  {
2065  DPRINT1("NtOpenThreadTokenEx(): Failed to impersonate token from DACL (Status 0x%lx)\n", Status);
2066  }
2067  }
2068  else
2069  {
2072  PreviousMode, &hToken);
2073  if (!NT_SUCCESS(Status))
2074  {
2075  DPRINT1("NtOpenThreadTokenEx(): Failed to open the object (Status 0x%lx)\n", Status);
2076  }
2077  }
2078 
2080 
2081  if (RestoreImpersonation)
2082  {
2084  }
2085 
2087 
2088  if (NT_SUCCESS(Status) && CopyOnOpen)
2089  {
2091  if (!NT_SUCCESS(Status))
2092  {
2093  DPRINT1("NtOpenThreadTokenEx(): Failed to impersonate the client (Status 0x%lx)\n", Status);
2094  }
2095  }
2096 
2097  if (NewToken) ObDereferenceObject(NewToken);
2098 
2100 
2101  if (NT_SUCCESS(Status))
2102  {
2103  _SEH2_TRY
2104  {
2105  *TokenHandle = hToken;
2106  }
2108  {
2110  }
2111  _SEH2_END;
2112  }
2113 
2114  return Status;
2115 }
2116 
2138 NTSTATUS
2139 NTAPI
2141  _In_ HANDLE ThreadHandle,
2145 {
2146  return NtOpenThreadTokenEx(ThreadHandle, DesiredAccess, OpenAsSelf, 0,
2147  TokenHandle);
2148 }
2149 
2167 NTSTATUS
2168 NTAPI
2170  _In_ HANDLE FirstTokenHandle,
2171  _In_ HANDLE SecondTokenHandle,
2172  _Out_ PBOOLEAN Equal)
2173 {
2175  PTOKEN FirstToken, SecondToken;
2176  BOOLEAN IsEqual;
2177  NTSTATUS Status;
2178 
2179  PAGED_CODE();
2180 
2182 
2183  if (PreviousMode != KernelMode)
2184  {
2185  _SEH2_TRY
2186  {
2187  ProbeForWriteBoolean(Equal);
2188  }
2190  {
2191  /* Return the exception code */
2193  }
2194  _SEH2_END;
2195  }
2196 
2197  Status = ObReferenceObjectByHandle(FirstTokenHandle,
2198  TOKEN_QUERY,
2200  PreviousMode,
2201  (PVOID*)&FirstToken,
2202  NULL);
2203  if (!NT_SUCCESS(Status))
2204  {
2205  DPRINT1("ObReferenceObjectByHandle() failed (Status 0x%lx)\n", Status);
2206  return Status;
2207  }
2208 
2209  Status = ObReferenceObjectByHandle(SecondTokenHandle,
2210  TOKEN_QUERY,
2212  PreviousMode,
2213  (PVOID*)&SecondToken,
2214  NULL);
2215  if (!NT_SUCCESS(Status))
2216  {
2217  DPRINT1("ObReferenceObjectByHandle() failed (Status 0x%lx)\n", Status);
2218  ObDereferenceObject(FirstToken);
2219  return Status;
2220  }
2221 
2222  if (FirstToken != SecondToken)
2223  {
2224  Status = SepCompareTokens(FirstToken,
2225  SecondToken,
2226  &IsEqual);
2227  }
2228  else
2229  {
2230  IsEqual = TRUE;
2231  }
2232 
2233  ObDereferenceObject(SecondToken);
2234  ObDereferenceObject(FirstToken);
2235 
2236  if (NT_SUCCESS(Status))
2237  {
2238  _SEH2_TRY
2239  {
2240  *Equal = IsEqual;
2241  }
2243  {
2245  }
2246  _SEH2_END;
2247  }
2248 
2249  return Status;
2250 }
2251 
2276 NTSTATUS
2277 NTAPI
2279  _In_ HANDLE ThreadHandle)
2280 {
2281  PETHREAD Thread;
2283  NTSTATUS Status;
2284  PAGED_CODE();
2285 
2287 
2288  /* Obtain the thread object from the handle */
2289  Status = ObReferenceObjectByHandle(ThreadHandle,
2291  PsThreadType,
2292  PreviousMode,
2293  (PVOID*)&Thread,
2294  NULL);
2295  if (!NT_SUCCESS(Status))
2296  {
2297  DPRINT1("NtImpersonateAnonymousToken(): Failed to reference the object (Status 0x%lx)\n", Status);
2298  return Status;
2299  }
2300 
2301  /* Call the private routine to impersonate the token */
2303  if (!NT_SUCCESS(Status))
2304  {
2305  DPRINT1("NtImpersonateAnonymousToken(): Failed to impersonate the token (Status 0x%lx)\n", Status);
2306  }
2307 
2309  return Status;
2310 }
2311 
2312 /* EOF */
PTOKEN SeAnonymousLogonTokenNoEveryone
Definition: semgr.c:20
#define OBJ_OPENLINK
Definition: winternl.h:230
VOID SepDeleteTokenLock(_Inout_ PTOKEN Token)
Deletes a lock of a token.
Definition: token.c:74
TOKEN_TYPE TokenType
Definition: setypes.h:239
const LUID SeSystemEnvironmentPrivilege
Definition: priv.c:41
#define SepAcquireTokenLockExclusive(Token)
Definition: se.h:275
NTSTATUS NTAPI NtOpenThreadTokenEx(_In_ HANDLE ThreadHandle, _In_ ACCESS_MASK DesiredAccess, _In_ BOOLEAN OpenAsSelf, _In_ ULONG HandleAttributes, _Out_ PHANDLE TokenHandle)
Opens a token that is tied to a thread handle.
Definition: token.c:1938
IN PUNICODE_STRING IN POBJECT_ATTRIBUTES ObjectAttributes
Definition: conport.c:35
NTSTATUS NTAPI PsImpersonateClient(IN PETHREAD Thread, IN PACCESS_TOKEN Token, IN BOOLEAN CopyOnOpen, IN BOOLEAN EffectiveOnly, IN SECURITY_IMPERSONATION_LEVEL ImpersonationLevel)
Definition: security.c:610
_In_ HANDLE _In_opt_ HANDLE _Out_opt_ PHANDLE _In_ ACCESS_MASK _In_ ULONG HandleAttributes
Definition: obfuncs.h:429
NTSTATUS NTAPI SepRegQueryHelper(_In_ PCWSTR KeyName, _In_ PCWSTR ValueName, _In_ ULONG ValueType, _In_ ULONG DataLength, _Out_ PVOID ValueData)
A private registry helper that returns the desired value data based on the specifics requested by the...
Definition: srm.c:93
NTSTATUS NTAPI ObCreateObjectType(IN PUNICODE_STRING TypeName, IN POBJECT_TYPE_INITIALIZER ObjectTypeInitializer, IN PVOID Reserved, OUT POBJECT_TYPE *ObjectType)
Definition: oblife.c:1047
_Must_inspect_result_ _In_ WDFDEVICE _In_ ULONG _In_ ACCESS_MASK DesiredAccess
Definition: wdfdevice.h:2654
const LUID SeSystemtimePrivilege
Definition: priv.c:31
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
#define TOKEN_SANDBOX_INERT
Definition: setypes.h:1181
#define _In_opt_
Definition: ms_sal.h:309
BOOLEAN NTAPI SeTokenCanImpersonate(_In_ PTOKEN ProcessToken, _In_ PTOKEN TokenToImpersonate, _In_ SECURITY_IMPERSONATION_LEVEL ImpersonationLevel)
Ensures that client impersonation can occur by checking if the token we're going to assign as the imp...
Definition: token.c:1828
_Inout_ PSE_IMPERSONATION_STATE ImpersonationState
Definition: psfuncs.h:189
#define _Inout_
Definition: ms_sal.h:378
const LUID SeIncreaseQuotaPrivilege
Definition: priv.c:24
#define TOKEN_WRITE
Definition: setypes.h:949
#define PsGetCurrentThread()
Definition: env_spec_w32.h:81
NTSTATUS NTAPI SepCreateToken(_Out_ PHANDLE TokenHandle, _In_ KPROCESSOR_MODE PreviousMode, _In_ ACCESS_MASK DesiredAccess, _In_opt_ POBJECT_ATTRIBUTES ObjectAttributes, _In_ TOKEN_TYPE TokenType, _In_ SECURITY_IMPERSONATION_LEVEL ImpersonationLevel, _In_ PLUID AuthenticationId, _In_ PLARGE_INTEGER ExpirationTime, _In_ PSID_AND_ATTRIBUTES User, _In_ ULONG GroupCount, _In_ PSID_AND_ATTRIBUTES Groups, _In_ ULONG GroupsLength, _In_ ULONG PrivilegeCount, _In_ PLUID_AND_ATTRIBUTES Privileges, _In_opt_ PSID Owner, _In_ PSID PrimaryGroup, _In_opt_ PACL DefaultDacl, _In_ PTOKEN_SOURCE TokenSource, _In_ BOOLEAN SystemToken)
Internal function responsible for access token object creation in the kernel. A fully created token o...
Definition: tokenlif.c:93
#define THREAD_IMPERSONATE
Definition: pstypes.h:151
const LUID SeCreateTokenPrivilege
Definition: priv.c:21
#define _Out_
Definition: ms_sal.h:345
const LUID SeCreatePermanentPrivilege
Definition: priv.c:35
BOOLEAN NTAPI SepTokenIsOwner(_In_ PACCESS_TOKEN _Token, _In_ PSECURITY_DESCRIPTOR SecurityDescriptor, _In_ BOOLEAN TokenLocked)
Checks if a token belongs to the main user, being the owner.
Definition: token.c:511
const LUID SeDebugPrivilege
Definition: priv.c:39
const LUID SeBackupPrivilege
Definition: priv.c:36
#define TRUE
Definition: types.h:120
_In_ USHORT _In_ ULONG _In_ PSOCKADDR _In_ PSOCKADDR _Reserved_ ULONG _In_opt_ PVOID _In_opt_ const WSK_CLIENT_CONNECTION_DISPATCH _In_opt_ PEPROCESS _In_opt_ PETHREAD _In_opt_ PSECURITY_DESCRIPTOR SecurityDescriptor
Definition: wsk.h:182
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
PACL SeSystemDefaultDacl
Definition: acl.c:17
LUID AuthenticationId
Definition: setypes.h:219
ULONG SessionId
Definition: dllmain.c:28
VOID SepRemovePrivilegeToken(_Inout_ PTOKEN Token, _In_ ULONG Index)
Removes a privilege from the token.
Definition: token.c:582
#define STATUS_CANT_OPEN_ANONYMOUS
Definition: ntstatus.h:402
LONG NTSTATUS
Definition: precomp.h:26
_IRQL_requires_same_ _In_ PLSA_STRING _In_ SECURITY_LOGON_TYPE _In_ ULONG _In_ ULONG _In_opt_ PTOKEN_GROUPS _In_ PTOKEN_SOURCE _Out_ PVOID _Out_ PULONG _Inout_ PLUID _Out_ PHANDLE Token
#define SE_RESTORE_PRIVILEGE
Definition: security.c:672
static NTSTATUS SepImpersonateAnonymousToken(_In_ PETHREAD Thread, _In_ KPROCESSOR_MODE PreviousMode)
Private function that impersonates the system's anonymous logon token. The major bulk of the imperson...
Definition: token.c:334
NTSTATUS NTAPI NtCompareTokens(_In_ HANDLE FirstTokenHandle, _In_ HANDLE SecondTokenHandle, _Out_ PBOOLEAN Equal)
Compares tokens if they're equal or not.
Definition: token.c:2169
LUID SeSystemAuthenticationId
Definition: token.c:20
_Out_ PBOOLEAN CopyOnOpen
Definition: psfuncs.h:154
NTSTATUS ExInitializeResourceLite(PULONG res)
Definition: env_spec_w32.h:641
NTSTATUS NTAPI ExDeleteResourceLite(IN PERESOURCE Resource)
Definition: resource.c:1456
PVOID PACCESS_TOKEN
Definition: setypes.h:11
PTOKEN SeAnonymousLogonToken
Definition: semgr.c:19
#define TOKEN_HAS_TRAVERSE_PRIVILEGE
Definition: setypes.h:1174
KPROCESSOR_MODE NTAPI ExGetPreviousMode(VOID)
Definition: sysinfo.c:3063
_IRQL_requires_same_ typedef _In_ ULONG _In_ UCHAR Level
Definition: wmitypes.h:55
const LUID SeAssignPrimaryTokenPrivilege
Definition: priv.c:22
#define TOKEN_IMPERSONATE
Definition: setypes.h:923
NTSYSAPI NTSTATUS NTAPI RtlCreateSecurityDescriptor(_Out_ PSECURITY_DESCRIPTOR SecurityDescriptor, _In_ ULONG Revision)
FORCEINLINE PSID SepGetOwnerFromDescriptor(_Inout_ PVOID _Descriptor)
Definition: se.h:99
PSID SeAuthenticatedUsersSid
Definition: sid.c:49
TOpcodeData Groups[17][8]
SECURITY_IMPERSONATION_LEVEL NTAPI SeTokenImpersonationLevel(_In_ PACCESS_TOKEN Token)
Gathers the security impersonation level of an access token.
Definition: token.c:1705
NTSTATUS NTAPI ObOpenObjectByPointer(IN PVOID Object, IN ULONG HandleAttributes, IN PACCESS_STATE PassedAccessState, IN ACCESS_MASK DesiredAccess, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode, OUT PHANDLE Handle)
Definition: obhandle.c:2742
NTSYSAPI NTSTATUS WINAPI RtlSetDaclSecurityDescriptor(PSECURITY_DESCRIPTOR, BOOLEAN, PACL, BOOLEAN)
NTSTATUS NTAPI SeIsTokenSibling(_In_ PTOKEN Token, _Out_ PBOOLEAN IsSibling)
Checks if the token is a sibling of the other token of the current process that the calling thread is...
Definition: token.c:1095
#define RtlMoveMemory(Destination, Source, Length)
Definition: typedefs.h:264
_SEH2_TRY
Definition: create.c:4226
#define SECURITY_DESCRIPTOR_REVISION
Definition: setypes.h:58
ULONG TokenFlags
Definition: setypes.h:241
NTSTATUS NTAPI NtImpersonateAnonymousToken(_In_ HANDLE ThreadHandle)
Allows the calling thread to impersonate the system's anonymous logon token.
Definition: token.c:2278
NTSTATUS SepRmDereferenceLogonSession(_Inout_ PLUID LogonLuid)
return STATUS_NOT_IMPLEMENTED
#define SE_PRIVILEGE_ENABLED
Definition: setypes.h:63
LUID SourceIdentifier
Definition: imports.h:279
NTSTATUS NTAPI SeIsTokenChild(_In_ PTOKEN Token, _Out_ PBOOLEAN IsChild)
Checks if the token is a child of the other token of the current process that the calling thread is i...
Definition: token.c:1046
#define L(x)
Definition: ntvdm.h:50
NTSTATUS NTAPI ObReferenceObjectByHandle(IN HANDLE Handle, IN ACCESS_MASK DesiredAccess, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode, OUT PVOID *Object, OUT POBJECT_HANDLE_INFORMATION HandleInformation OPTIONAL)
Definition: obref.c:494
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
Definition: IoEaTest.cpp:117
#define SE_GROUP_OWNER
Definition: setypes.h:93
#define FALSE
Definition: types.h:117
LUID SeAnonymousAuthenticationId
Definition: token.c:21
NTSTATUS NTAPI SepCopyProxyData(_Out_ PVOID *Dest, _In_ PVOID Src)
Copies the proxy data from the source into the destination of a token.
Definition: token.c:674
#define RtlEqualLuid(Luid1, Luid2)
Definition: rtlfuncs.h:301
enum _SECURITY_IMPERSONATION_LEVEL SECURITY_IMPERSONATION_LEVEL
NTSTATUS SepCreateTokenLock(_Inout_ PTOKEN Token)
Creates a lock for the token.
Definition: token.c:45
struct NameRec_ * Name
Definition: cdprocs.h:459
#define PsGetCurrentProcess
Definition: psfuncs.h:17
PTOKEN NTAPI SepCreateSystemProcessToken(VOID)
Creates the system process token.
Definition: token.c:1366
VOID NTAPI PsRestoreImpersonation(IN PETHREAD Thread, IN PSE_IMPERSONATION_STATE ImpersonationState)
Definition: security.c:965
unsigned char BOOLEAN
#define STATUS_BAD_TOKEN_TYPE
Definition: ntstatus.h:404
VOID SepUpdatePrivilegeFlagsToken(_Inout_ PTOKEN Token)
Updates the token's flags based upon the privilege that the token has been granted....
Definition: token.c:554
const LUID SeLoadDriverPrivilege
Definition: priv.c:29
POBJECT_TYPE SeTokenObjectType
Definition: token.c:17
#define SE_GROUP_ENABLED_BY_DEFAULT
Definition: setypes.h:91
const LUID SeTakeOwnershipPrivilege
Definition: priv.c:28
_At_(*)(_In_ PWSK_CLIENT Client, _In_opt_ PUNICODE_STRING NodeName, _In_opt_ PUNICODE_STRING ServiceName, _In_opt_ ULONG NameSpace, _In_opt_ GUID *Provider, _In_opt_ PADDRINFOEXW Hints, _Outptr_ PADDRINFOEXW *Result, _In_opt_ PEPROCESS OwningProcess, _In_opt_ PETHREAD OwningThread, _Inout_ PIRP Irp Result)(Mem)) NTSTATUS(WSKAPI *PFN_WSK_GET_ADDRESS_INFO
Definition: wsk.h:426
#define _In_
Definition: ms_sal.h:308
LUID ParentTokenId
Definition: setypes.h:220
_In_ ULONG _In_ ACCESS_MASK _In_ PSID Sid
Definition: rtlfuncs.h:1103
_In_ ACCESS_MASK _In_ ULONG _Out_ PHANDLE TokenHandle
Definition: psfuncs.h:715
static BOOLEAN SepCompareSidAndAttributesFromTokens(_In_ PSID_AND_ATTRIBUTES SidArrayToken1, _In_ ULONG CountSidArray1, _In_ PSID_AND_ATTRIBUTES SidArrayToken2, _In_ ULONG CountSidArray2)
Compares the elements of SID arrays provided by tokens. The elements that are being compared for equa...
Definition: token.c:107
NTSTATUS NTAPI ObReferenceObjectByPointer(IN PVOID Object, IN ACCESS_MASK DesiredAccess, IN POBJECT_TYPE ObjectType, IN KPROCESSOR_MODE AccessMode)
Definition: obref.c:381
NTSYSAPI ULONG NTAPI RtlLengthSid(IN PSID Sid)
Definition: sid.c:150
ULONG RtlLengthSidAndAttributes(_In_ ULONG Count, _In_ PSID_AND_ATTRIBUTES Src)
Computes the length size of a SID.
Definition: token.c:824
ULONG SessionId
Definition: setypes.h:225
BOOLEAN NTAPI SeTokenIsAdmin(_In_ PACCESS_TOKEN Token)
Determines if a token is either an admin token or not. Such condition is checked based upon TOKEN_HAS...
Definition: token.c:1749
VOID SepUpdateSinglePrivilegeFlagToken(_Inout_ PTOKEN Token, _In_ ULONG Index)
Updates the token's flags based upon the privilege that the token has been granted....
Definition: token.c:442
#define ANONYMOUS_LOGON_LUID
Definition: setypes.h:701
BOOLEAN NTAPI PsDisableImpersonation(IN PETHREAD Thread, OUT PSE_IMPERSONATION_STATE ImpersonationState)
Definition: security.c:915
UNICODE_STRING Restricted
Definition: utils.c:24
PULONG DynamicPart
Definition: setypes.h:237
Status
Definition: gdiplustypes.h:24
_Out_writes_bytes_to_opt_ AbsoluteSecurityDescriptorSize PSECURITY_DESCRIPTOR _Inout_ PULONG _Out_writes_bytes_to_opt_ DaclSize PACL _Inout_ PULONG _Out_writes_bytes_to_opt_ SaclSize PACL _Inout_ PULONG _Out_writes_bytes_to_opt_ OwnerSize PSID _Inout_ PULONG _Out_writes_bytes_to_opt_ PrimaryGroupSize PSID PrimaryGroup
Definition: rtlfuncs.h:1558
#define SE_CHANGE_NOTIFY_PRIVILEGE
Definition: security.c:677
#define SE_PRIVILEGE_ENABLED_BY_DEFAULT
Definition: setypes.h:62
_In_ KPROCESSOR_MODE PreviousMode
Definition: sefuncs.h:103
int Count
Definition: noreturn.cpp:7
VOID NTAPI SeGetTokenControlInformation(_In_ PACCESS_TOKEN _Token, _Out_ PTOKEN_CONTROL TokenControl)
Retrieves token control information.
Definition: token.c:1333
#define STATUS_INVALID_PRIMARY_GROUP
Definition: ntstatus.h:327
#define TOKEN_HAS_RESTORE_PRIVILEGE
Definition: setypes.h:1176
const LUID SeCreatePagefilePrivilege
Definition: priv.c:34
NTSTATUS NTAPI NtOpenThreadToken(_In_ HANDLE ThreadHandle, _In_ ACCESS_MASK DesiredAccess, _In_ BOOLEAN OpenAsSelf, _Out_ PHANDLE TokenHandle)
Opens a token that is tied to a thread handle.
Definition: token.c:2140
#define TOKEN_QUERY
Definition: setypes.h:924
#define ASSERT(a)
Definition: mode.c:44
const LUID SeRestorePrivilege
Definition: priv.c:37
PVOID FASTCALL ObFastReplaceObject(IN PEX_FAST_REF FastRef, IN PVOID Object)
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define SE_GROUP_ENABLED
Definition: setypes.h:92
BOOLEAN TokenInUse
Definition: setypes.h:242
_In_ WDFCOLLECTION _In_ ULONG Index
#define EXCEPTION_EXECUTE_HANDLER
Definition: excpt.h:85
struct _SID_AND_ATTRIBUTES SID_AND_ATTRIBUTES
static NTSTATUS SepCompareTokens(_In_ PTOKEN FirstToken, _In_ PTOKEN SecondToken, _Out_ PBOOLEAN Equal)
Compares tokens if they're equal based on all the following properties. If all of the said conditions...
Definition: token.c:243
_Out_ PBOOLEAN _Out_ PBOOLEAN _Out_ PSECURITY_IMPERSONATION_LEVEL ImpersonationLevel
Definition: psfuncs.h:154
#define ObDereferenceObject
Definition: obfuncs.h:203
#define STATUS_TOKEN_ALREADY_IN_USE
Definition: ntstatus.h:535
#define TOKEN_ALL_ACCESS
Definition: setypes.h:942
#define ProbeForWriteHandle(Ptr)
Definition: probe.h:43
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2652
#define ProbeForWriteBoolean(Ptr)
Definition: probe.h:31
#define STATUS_ACCESS_DENIED
Definition: udferr_usr.h:145
static const LUID SeChangeNotifyPrivilege
Definition: authpackage.c:167
VOID FASTCALL ObInitializeFastReference(IN PEX_FAST_REF FastRef, IN PVOID Object)
Definition: obref.c:107
#define SE_GROUP_MANDATORY
Definition: setypes.h:90
#define STATUS_NO_TOKEN
Definition: ntstatus.h:360
CCHAR KPROCESSOR_MODE
Definition: ketypes.h:7
PTOKEN SepCreateSystemAnonymousLogonToken(VOID)
Creates the anonymous logon token for the system. The difference between this token and the other one...
Definition: token.c:1516
VOID NTAPI SepInitializeTokenImplementation(VOID)
Internal function that initializes critical kernel data for access token implementation in SRM.
Definition: token.c:1262
_In_ PSECURITY_SUBJECT_CONTEXT _In_ BOOLEAN _In_ ACCESS_MASK _In_ ACCESS_MASK _Outptr_opt_ PPRIVILEGE_SET * Privileges
Definition: sefuncs.h:13
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
_Out_writes_bytes_to_opt_ AbsoluteSecurityDescriptorSize PSECURITY_DESCRIPTOR _Inout_ PULONG _Out_writes_bytes_to_opt_ DaclSize PACL Dacl
Definition: rtlfuncs.h:1552
char * PBOOLEAN
Definition: retypes.h:11
POBJECT_TYPE PsThreadType
Definition: thread.c:20
BOOLEAN NTAPI SeTokenIsWriteRestricted(_In_ PACCESS_TOKEN Token)
Determines if a token is write restricted, that is, nobody can write anything to it.
Definition: token.c:1797
#define TAG_SE_TOKEN_LOCK
Definition: tag.h:159
PSID SeAliasAdminsSid
Definition: sid.c:41
#define TOKEN_READ
Definition: setypes.h:947
TOKEN_SOURCE SeSystemTokenSource
Definition: token.c:19
#define SepReleaseTokenLock(Token)
Definition: se.h:286
PVOID *typedef PHANDLE
Definition: ntsecpkg.h:454
static GENERIC_MAPPING SepTokenMapping
Definition: token.c:23
#define TAG_TOKEN_DYNAMIC
Definition: tag.h:155
BOOLEAN NTAPI SeTokenIsInert(_In_ PTOKEN Token)
Determines if a token is a sandbox inert token or not, based upon the token flags.
Definition: token.c:1196
PTOKEN SepCreateSystemAnonymousLogonTokenNoEveryone(VOID)
Creates the anonymous logon token for the system. This kind of token doesn't include the everyone SID...
Definition: token.c:1584
const LUID SeLockMemoryPrivilege
Definition: priv.c:23
static BOOLEAN SepComparePrivilegeAndAttributesFromTokens(_In_ PLUID_AND_ATTRIBUTES PrivArrayToken1, _In_ ULONG CountPrivArray1, _In_ PLUID_AND_ATTRIBUTES PrivArrayToken2, _In_ ULONG CountPrivArray2)
Compares the elements of privilege arrays provided by tokens. The elements that are being compared fo...
Definition: token.c:174
const LUID SeProfileSingleProcessPrivilege
Definition: priv.c:32
PACCESS_TOKEN NTAPI PsReferencePrimaryToken(PEPROCESS Process)
Definition: security.c:440
PSID SeWorldSid
Definition: sid.c:25
PSEP_LOGON_SESSION_REFERENCES LogonSession
Definition: setypes.h:245
const LUID SeIncreaseBasePriorityPrivilege
Definition: priv.c:33
enum _TOKEN_TYPE TOKEN_TYPE
#define SYSTEM_LUID
Definition: setypes.h:700
BOOLEAN NTAPI SepSidInTokenEx(_In_ PACCESS_TOKEN _Token, _In_ PSID PrincipalSelfSid, _In_ PSID _Sid, _In_ BOOLEAN Deny, _In_ BOOLEAN Restricted)
Checks if a SID is present in a token.
Definition: sid.c:443
CCHAR SourceName[TOKEN_SOURCE_LENGTH]
Definition: imports.h:278
PACCESS_TOKEN NTAPI PsReferenceImpersonationToken(IN PETHREAD Thread, OUT PBOOLEAN CopyOnOpen, OUT PBOOLEAN EffectiveOnly, OUT PSECURITY_IMPERSONATION_LEVEL ImpersonationLevel)
Definition: security.c:849
NTSTATUS NTAPI SepRmRemoveLogonSessionFromToken(_Inout_ PTOKEN Token)
Removes a logon session from an access token.
Definition: srm.c:449
const LUID SeTcbPrivilege
Definition: priv.c:26
FORCEINLINE ULONG ObpValidateAttributes(IN ULONG Attributes, IN KPROCESSOR_MODE PreviousMode)
Definition: ob_x.h:22
#define TAG_ACL
Definition: tag.h:148
#define SE_IMPERSONATE_PRIVILEGE
Definition: security.c:683
NTSTATUS NTAPI SeSubProcessToken(_In_ PTOKEN ParentToken, _Out_ PTOKEN *Token, _In_ BOOLEAN InUse, _In_ ULONG SessionId)
Subtracts a token in exchange of duplicating a new one.
Definition: token.c:986
const LUID SeShutdownPrivilege
Definition: priv.c:38
_SEH2_END
Definition: create.c:4400
PERESOURCE TokenLock
Definition: setypes.h:222
NTSTATUS NTAPI ObInsertObject(IN PVOID Object, IN PACCESS_STATE AccessState OPTIONAL, IN ACCESS_MASK DesiredAccess, IN ULONG ObjectPointerBias, OUT PVOID *NewObject OPTIONAL, OUT PHANDLE Handle)
Definition: obhandle.c:2935
LONG NTAPI ExSystemExceptionFilter(VOID)
Definition: harderr.c:349
GENERIC_MAPPING GenericMapping
Definition: obtypes.h:358
#define TOKEN_HAS_ADMIN_GROUP
Definition: setypes.h:1178
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
BOOLEAN NTAPI SeTokenIsRestricted(_In_ PACCESS_TOKEN Token)
Determines if a token is restricted or not, based upon the token flags.
Definition: token.c:1772
struct _TOKEN * PTOKEN
TOKEN_TYPE NTAPI SeTokenType(_In_ PACCESS_TOKEN Token)
Gathers the token type of an access token. A token ca be either a primary token or impersonation toke...
Definition: token.c:1726
#define SE_BACKUP_PRIVILEGES_CHECKED
Definition: setypes.h:1183
LUID TokenId
Definition: setypes.h:218
#define _Out_opt_
Definition: ms_sal.h:346
NTSTATUS NTAPI SeQueryAuthenticationIdToken(_In_ PACCESS_TOKEN Token, _Out_ PLUID LogonId)
Queries the authentication ID of an access token.
Definition: token.c:1682
unsigned int * PULONG
Definition: retypes.h:1
_Out_writes_bytes_to_opt_ AbsoluteSecurityDescriptorSize PSECURITY_DESCRIPTOR _Inout_ PULONG _Out_writes_bytes_to_opt_ DaclSize PACL _Inout_ PULONG _Out_writes_bytes_to_opt_ SaclSize PACL _Inout_ PULONG _Out_writes_bytes_to_opt_ OwnerSize PSID Owner
Definition: rtlfuncs.h:1556
#define NULL
Definition: types.h:112
_IRQL_requires_same_ _In_ PLSA_STRING _In_ SECURITY_LOGON_TYPE _In_ ULONG _In_ ULONG _In_opt_ PTOKEN_GROUPS _In_ PTOKEN_SOURCE _Out_ PVOID _Out_ PULONG _Inout_ PLUID LogonId
#define STATUS_INVALID_OWNER
Definition: ntstatus.h:326
VOID NTAPI PsDereferencePrimaryToken(IN PACCESS_TOKEN PrimaryToken)
Definition: security.c:902
#define DPRINT1
Definition: precomp.h:8
BOOL WINAPI IsChild(_In_ HWND, _In_ HWND)
const LUID SeSecurityPrivilege
Definition: priv.c:27
VOID NTAPI SepFreeProxyData(_Inout_ PVOID ProxyData)
Frees (de-allocates) the proxy data memory block of a token.
Definition: token.c:652
VOID FASTCALL ObFastDereferenceObject(IN PEX_FAST_REF FastRef, IN PVOID Object)
Definition: obref.c:167
PSID SeLocalSystemSid
Definition: sid.c:38
_Must_inspect_result_ _In_ PLARGE_INTEGER _In_ PLARGE_INTEGER _In_ ULONG _In_ PFILE_OBJECT _In_ PVOID Process
Definition: fsrtlfuncs.h:219
VOID NTAPI SepDeleteToken(_In_ PVOID ObjectBody)
Internal function that deals with access token object destruction and deletion. The function is used ...
Definition: token.c:1218
#define SepAcquireTokenLockShared(Token)
Definition: se.h:280
#define ObReferenceObject
Definition: obfuncs.h:204
BOOLEAN NTAPI SepSidInToken(_In_ PACCESS_TOKEN _Token, _In_ PSID Sid)
Checks if a SID is present in a token.
Definition: sid.c:547
NTSTATUS SepFindPrimaryGroupAndDefaultOwner(_In_ PTOKEN Token, _In_ PSID PrimaryGroup, _In_opt_ PSID DefaultOwner, _Out_opt_ PULONG PrimaryGroupIndex, _Out_opt_ PULONG DefaultOwnerIndex)
Finds the primary group and default owner entity based on the submitted primary group instance and an...
Definition: token.c:870
#define THREAD_QUERY_INFORMATION
Definition: pstypes.h:149
#define TOKEN_HAS_IMPERSONATE_PRIVILEGE
Definition: setypes.h:1182
ULONG ERESOURCE
Definition: env_spec_w32.h:594
unsigned int ULONG
Definition: retypes.h:1
#define SE_BACKUP_PRIVILEGE
Definition: security.c:671
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define UNIMPLEMENTED
Definition: debug.h:115
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
_In_ ACCESS_MASK _In_ BOOLEAN OpenAsSelf
Definition: zwfuncs.h:699
#define InitializeObjectAttributes(p, n, a, r, s)
Definition: reg.c:106
NTSTATUS NTAPI SeCopyClientToken(_In_ PACCESS_TOKEN Token, _In_ SECURITY_IMPERSONATION_LEVEL Level, _In_ KPROCESSOR_MODE PreviousMode, _Out_ PACCESS_TOKEN *NewToken)
Copies an existing access token (technically duplicating a new one).
Definition: token.c:1155
ULONG NTAPI MmGetSessionId(IN PEPROCESS Process)
Definition: session.c:179
PSID SeAnonymousLogonSid
Definition: se.h:203
VOID NTAPI SeDeassignPrimaryToken(_Inout_ PEPROCESS Process)
Removes the primary token of a process.
Definition: token.c:795
#define _SEH2_EXCEPT(...)
Definition: pseh2_64.h:40
#define STATUS_SUCCESS
Definition: shellext.h:65
#define _SEH2_GetExceptionCode()
Definition: pseh2_64.h:165
#define _SEH2_YIELD(__stmt)
Definition: pseh2_64.h:168
#define TOKEN_HAS_BACKUP_PRIVILEGE
Definition: setypes.h:1175
#define DPRINT
Definition: sndvol32.h:71
NTSTATUS NTAPI SeQuerySessionIdToken(_In_ PACCESS_TOKEN Token, _Out_ PULONG pSessionId)
Queries the session ID of an access token.
Definition: token.c:1650
_In_ ACCESS_MASK _In_opt_ POBJECT_ATTRIBUTES _In_ BOOLEAN EffectiveOnly
Definition: sefuncs.h:401
VOID SepRemoveUserGroupToken(_Inout_ PTOKEN Token, _In_ ULONG Index)
Removes a group from the token.
Definition: token.c:618
OB_DELETE_METHOD DeleteProcedure
Definition: obtypes.h:369
#define SeLengthSid(Sid)
Definition: sefuncs.h:570
#define REG_DWORD
Definition: sdbapi.c:596
#define ExFreePoolWithTag(_P, _T)
Definition: module.h:1099
#define TOKEN_SESSION_NOT_REFERENCED
Definition: setypes.h:1180
static CODE_SEG("PAGE")
Definition: isapnp.c:1482
NTSTATUS NTAPI SepDuplicateToken(_In_ PTOKEN Token, _In_opt_ POBJECT_ATTRIBUTES ObjectAttributes, _In_ BOOLEAN EffectiveOnly, _In_ TOKEN_TYPE TokenType, _In_ SECURITY_IMPERSONATION_LEVEL Level, _In_ KPROCESSOR_MODE PreviousMode, _Out_ PTOKEN *NewAccessToken)
Duplicates an access token, from an existing valid token.
Definition: tokenlif.c:423
struct _TOKEN TOKEN
const LUID SeAuditPrivilege
Definition: priv.c:40
NTSTATUS NTAPI SeExchangePrimaryToken(_In_ PEPROCESS Process, _In_ PACCESS_TOKEN NewAccessToken, _Out_ PACCESS_TOKEN *OldAccessToken)
Replaces the old access token of a process (pointed by the EPROCESS kernel structure) with a new acce...
Definition: token.c:705
PACL SeSystemAnonymousLogonDacl
Definition: acl.c:22
ULONG ACCESS_MASK
Definition: nt_native.h:40
#define TOKEN_EXECUTE
Definition: setypes.h:954
VOID NTAPI SeAssignPrimaryToken(_In_ PEPROCESS Process, _In_ PTOKEN Token)
Assigns a primary access token to a given process.
Definition: token.c:1299
NTSTATUS NTAPI SepCreateImpersonationTokenDacl(_In_ PTOKEN Token, _In_ PTOKEN PrimaryToken, _Out_ PACL *Dacl)
Allocates a discretionary access control list based on certain properties of a regular and primary ac...
Definition: acl.c:277
NTSYSAPI BOOLEAN NTAPI RtlEqualSid(_In_ PSID Sid1, _In_ PSID Sid2)
LONGLONG QuadPart
Definition: typedefs.h:114
#define TOKEN_IS_RESTRICTED
Definition: setypes.h:1179
#define PAGED_CODE()
VOID NTAPI PsDereferenceImpersonationToken(IN PACCESS_TOKEN ImpersonationToken)
Definition: security.c:888