00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
#include "sep.h"
00031
#include "sertlp.h"
00032
#include <zwapi.h>
00033
#include "tokenp.h"
00034
00035
#ifdef ALLOC_PRAGMA
00036
#pragma alloc_text(INIT,SepTokenInitialization)
00037
#pragma alloc_text(INIT,SeMakeSystemToken)
00038
#pragma alloc_text(INIT,SeMakeAnonymousToken)
00039
#pragma alloc_text(PAGE,SeTokenType)
00040
#pragma alloc_text(PAGE,SeTokenIsAdmin)
00041
#pragma alloc_text(PAGE,SepCreateToken)
00042
#pragma alloc_text(PAGE,SeTokenImpersonationLevel)
00043
#pragma alloc_text(PAGE,SeAssignPrimaryToken)
00044
#pragma alloc_text(PAGE,SeDeassignPrimaryToken)
00045
#pragma alloc_text(PAGE,SeExchangePrimaryToken)
00046
#pragma alloc_text(PAGE,SeGetTokenControlInformation)
00047
#pragma alloc_text(PAGE,SeSubProcessToken)
00048
#pragma alloc_text(PAGE,NtCreateToken)
00049
#pragma alloc_text(PAGE,SepTokenDeleteMethod)
00050
#pragma alloc_text(PAGE,SepIdAssignableAsOwner)
00051
#pragma alloc_text(PAGE,SeIsChildToken)
00052
#pragma alloc_text(PAGE,SeIsChildTokenByPointer)
00053
#pragma alloc_text(PAGE,NtImpersonateAnonymousToken)
00054
#endif
00055
00056
00058
00059
00060
00062
00063
00064
00065
00066
00067 GENERIC_MAPPING
SepTokenMapping = { TOKEN_READ,
00068 TOKEN_WRITE,
00069 TOKEN_EXECUTE,
00070 TOKEN_ALL_ACCESS
00071 };
00072
00073
00074
00075
00076
00077 POBJECT_TYPE SepTokenObjectType;
00078
00079
00080
00081
00082
00083
00084
#if DBG
00085
BOOLEAN SystemTokenCreated =
FALSE;
00086
#endif //DBG
00087
00088
00089
00090
00091
00092
00093 ERESOURCE SepTokenLock;
00094
00095
00096
00097
00098
00099
00100
00101
00102
#ifdef TOKEN_DIAGNOSTICS_ENABLED
00103
ULONG TokenGlobalFlag = 0;
00104
#endif // TOKEN_DIAGNOSTICS_ENABLED
00105
00106
00107
00109
00110
00111
00113
00114
00115
00116
00117 TOKEN_TYPE
00118 SeTokenType(
00119 IN PACCESS_TOKEN Token
00120 )
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140 {
00141
PAGED_CODE();
00142
00143
return (((
PTOKEN)
Token)->TokenType);
00144 }
00145
00146
00147
00148
NTKERNELAPI
00149 BOOLEAN
00150 SeTokenIsAdmin(
00151 IN PACCESS_TOKEN Token
00152 )
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171 {
00172
PAGED_CODE();
00173
00174
return ((((
PTOKEN)
Token)->TokenFlags &
TOKEN_HAS_ADMIN_GROUP) != 0 );
00175 }
00176
00177
00178
00179
NTKERNELAPI
00180 BOOLEAN
00181 SeTokenIsRestricted(
00182 IN PACCESS_TOKEN Token
00183 )
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202 {
00203
PAGED_CODE();
00204
00205
return ((((
PTOKEN)
Token)->TokenFlags &
TOKEN_IS_RESTRICTED) != 0 );
00206 }
00207
00208
00209
00210 SECURITY_IMPERSONATION_LEVEL
00211 SeTokenImpersonationLevel(
00212 IN PACCESS_TOKEN Token
00213 )
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233 {
00234
PAGED_CODE();
00235
00236
return ((
PTOKEN)
Token)->ImpersonationLevel;
00237 }
00238
00239
00240
VOID
00241 SeAssignPrimaryToken(
00242 IN
PEPROCESS Process,
00243 IN PACCESS_TOKEN Token
00244 )
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263 {
00264
00265
NTSTATUS
00266
Status;
00267
00268
PTOKEN
00269 NewToken = (
PTOKEN)
Token;
00270
00271
PAGED_CODE();
00272
00273
ASSERT(NewToken->TokenType == TokenPrimary);
00274
ASSERT( !NewToken->TokenInUse );
00275
00276
00277
00278
00279
00280
00281
00282
00283
00284
00285
00286
00287
00288
if (Process->Token !=
NULL) {
00289
SeDeassignPrimaryToken( Process );
00290 }
00291
00292
00293 Process->Token=
Token;
00294 NewToken->TokenInUse =
TRUE;
00295
ObReferenceObject(NewToken);
00296
return;
00297 }
00298
00299
00300
00301
VOID
00302 SeDeassignPrimaryToken(
00303 IN
PEPROCESS Process
00304 )
00305
00306
00307
00308
00309
00310
00311
00312
00313
00314
00315
00316
00317
00318
00319
00320
00321
00322
00323
00324
00325
00326 {
00327
00328
PTOKEN
00329 OldToken = (
PTOKEN)(Process->Token);
00330
00331
PAGED_CODE();
00332
00333
ASSERT(OldToken->TokenType == TokenPrimary);
00334
ASSERT(OldToken->TokenInUse);
00335
00336 OldToken->TokenInUse =
FALSE;
00337
ObDereferenceObject( OldToken );
00338
00339
00340
return;
00341 }
00342
00343
00344
00345
NTSTATUS
00346 SeExchangePrimaryToken(
00347 IN
PEPROCESS Process,
00348 IN PACCESS_TOKEN NewAccessToken,
00349 OUT PACCESS_TOKEN *OldAccessToken
00350 )
00351
00352
00353
00354
00355
00356
00357
00358
00359
00360
00361
00362
00363
00364
00365
00366
00367
00368
00369
00370
00371
00372
00373
00374
00375
00376
00377
00378
00379
00380
00381
00382
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392
00393
00394
00395
00396
00397
00398
00399 {
00400
NTSTATUS
00401
Status;
00402
00403
PTOKEN
00404 OldToken = (
PTOKEN)(Process->Token);
00405
00406
PTOKEN
00407 NewToken = (
PTOKEN)NewAccessToken;
00408
00409
PAGED_CODE();
00410
00411
00412
00413
00414
00415
00416
00417
00418
ASSERT(OldToken->TokenType == TokenPrimary);
00419
ASSERT(OldToken->TokenInUse);
00420
00421
00422
00423
00424
00425
00426
if ( NewToken->TokenType != TokenPrimary ) {
00427
return(STATUS_BAD_TOKEN_TYPE);
00428 }
00429
00430
00431
00432
00433
00434
if (NewToken->TokenInUse) {
00435
return(STATUS_TOKEN_ALREADY_IN_USE);
00436 }
00437
00438
00439
00440
00441
00442 NewToken->SessionId = OldToken->SessionId ;
00443
00444
00445
00446
00447
00448
00449
00450 Process->Token=NewAccessToken;
00451 NewToken->TokenInUse =
TRUE;
00452
ObReferenceObject(NewToken);
00453
00454
00455
00456
00457
00458 OldToken->TokenInUse =
FALSE;
00459
00460
00461
00462
00463
00464
00465 (*OldAccessToken) = OldToken;
00466
00467
return (STATUS_SUCCESS);
00468 }
00469
00470
00471
00472
00473
00474
VOID
00475 SeGetTokenControlInformation (
00476 IN PACCESS_TOKEN Token,
00477 OUT PTOKEN_CONTROL TokenControl
00478 )
00479
00480
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499
00500
00501
00502
00503
00504
00505
00506
00507
00508
00509
00510
00511 {
00512
PAGED_CODE();
00513
00514
00515
00516
00517
00518
SepAcquireTokenReadLock( (
PTOKEN)
Token );
00519
00520
00521
00522
00523
00524 TokenControl->TokenId = ((
TOKEN *)
Token)->TokenId;
00525 TokenControl->AuthenticationId = ((
TOKEN *)
Token)->AuthenticationId;
00526 TokenControl->ModifiedId = ((
TOKEN *)
Token)->ModifiedId;
00527 TokenControl->TokenSource = ((
TOKEN *)
Token)->TokenSource;
00528
00529
SepReleaseTokenReadLock( (
PTOKEN)
Token );
00530
00531
return;
00532
00533 }
00534
00535 PACCESS_TOKEN
00536 SeMakeSystemToken ()
00537
00538
00539
00540
00541
00542
00543
00544
00545
00546
00547
00548
00549
00550
00551
00552
00553
00554
00555
00556
00557
00558
00559
00560
00561
00562
00563
00564
00565
00566
00567
00568
00569
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582
00583
00584
00585
00586
00587
00588
00589
00590
00591
00592 {
00593
NTSTATUS Status;
00594
00595 PVOID
Token;
00596
00597 SID_AND_ATTRIBUTES UserId;
00598 TOKEN_PRIMARY_GROUP PrimaryGroup;
00599 PSID_AND_ATTRIBUTES GroupIds;
00600 ULONG GroupIdsLength;
00601 LUID_AND_ATTRIBUTES Privileges[30];
00602 PACL TokenAcl;
00603 PSID
Owner;
00604 ULONG
NormalGroupAttributes;
00605 ULONG
OwnerGroupAttributes;
00606 ULONG Length;
00607 OBJECT_ATTRIBUTES TokenObjectAttributes;
00608 PSECURITY_DESCRIPTOR TokenSecurityDescriptor;
00609 ULONG BufferLength;
00610 PVOID
Buffer;
00611
00612 ULONG_PTR GroupIdsBuffer[128 *
sizeof(ULONG) /
sizeof(ULONG_PTR)];
00613
00614 TIME_FIELDS
TimeFields;
00615 LARGE_INTEGER
NoExpiration;
00616
00617
PAGED_CODE();
00618
00619
00620
00621
00622
00623
00624
#if DBG
00625
ASSERT( !SystemTokenCreated );
00626 SystemTokenCreated =
TRUE;
00627
#endif //DBG
00628
00629
00630
00631
00632
00633
00634
TimeFields.Year = 3000;
00635
TimeFields.Month = 1;
00636
TimeFields.Day = 1;
00637
TimeFields.Hour = 1;
00638
TimeFields.Minute = 1;
00639
TimeFields.Second = 1;
00640
TimeFields.Milliseconds = 1;
00641
TimeFields.Weekday = 1;
00642
00643
RtlTimeFieldsToTime( &
TimeFields, &
NoExpiration );
00644
00645
00646
00647
00648
00649
00650
00651
00652
00653 GroupIds = (PSID_AND_ATTRIBUTES)GroupIdsBuffer;
00654
00655
00656
00657
00658
00659
00660
NormalGroupAttributes = (SE_GROUP_MANDATORY |
00661 SE_GROUP_ENABLED_BY_DEFAULT |
00662 SE_GROUP_ENABLED
00663 );
00664
00665
OwnerGroupAttributes = (SE_GROUP_ENABLED_BY_DEFAULT |
00666 SE_GROUP_ENABLED |
00667 SE_GROUP_OWNER
00668 );
00669
00670
00671
00672
00673
00674 UserId.Sid =
SeLocalSystemSid;
00675 UserId.Attributes = 0;
00676
00677
00678
00679
00680
00681
00682 GroupIds->Sid =
SeAliasAdminsSid;
00683 (GroupIds+1)->Sid =
SeWorldSid;
00684 (GroupIds+2)->Sid =
SeAuthenticatedUsersSid;
00685
00686 GroupIds->Attributes =
OwnerGroupAttributes;
00687 (GroupIds+1)->Attributes =
NormalGroupAttributes;
00688 (GroupIds+2)->Attributes =
NormalGroupAttributes;
00689
00690 GroupIdsLength = (ULONG)LongAlignSize(
SeLengthSid(GroupIds->Sid)) +
00691 (ULONG)LongAlignSize(
SeLengthSid((GroupIds+1)->Sid)) +
00692 (ULONG)LongAlignSize(
SeLengthSid((GroupIds+2)->Sid)) +
00693
sizeof(SID_AND_ATTRIBUTES);
00694
00695
ASSERT( GroupIdsLength <= 128 *
sizeof(ULONG) );
00696
00697
00698
00699
00700
00701
00702
00703
00704
00705
00706
00707
00708
00709
00710
00711
00712
00713
00714
00715
00716
00717
00718
00719
00720
00721
00722
00723
00724
00725
00726
00727
00728
00729
00730
00731
00732
00733
00734
00735
00736
00737
00738
00739
00740 Privileges[0].Luid =
SeTcbPrivilege;
00741 Privileges[0].Attributes =
00742 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00743 SE_PRIVILEGE_ENABLED);
00744
00745 Privileges[1].Luid =
SeCreateTokenPrivilege;
00746 Privileges[1].Attributes = 0;
00747
00748 Privileges[2].Luid =
SeTakeOwnershipPrivilege;
00749 Privileges[2].Attributes = 0;
00750
00751 Privileges[3].Luid =
SeCreatePagefilePrivilege;
00752 Privileges[3].Attributes =
00753 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00754 SE_PRIVILEGE_ENABLED);
00755
00756 Privileges[4].Luid =
SeLockMemoryPrivilege;
00757 Privileges[4].Attributes =
00758 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00759 SE_PRIVILEGE_ENABLED);
00760
00761 Privileges[5].Luid =
SeAssignPrimaryTokenPrivilege;
00762 Privileges[5].Attributes = 0;
00763
00764 Privileges[6].Luid =
SeIncreaseQuotaPrivilege;
00765 Privileges[6].Attributes = 0;
00766
00767 Privileges[7].Luid =
SeIncreaseBasePriorityPrivilege;
00768 Privileges[7].Attributes =
00769 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00770 SE_PRIVILEGE_ENABLED);
00771
00772 Privileges[8].Luid =
SeCreatePermanentPrivilege;
00773 Privileges[8].Attributes =
00774 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00775 SE_PRIVILEGE_ENABLED);
00776
00777 Privileges[9].Luid =
SeDebugPrivilege;
00778 Privileges[9].Attributes =
00779 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00780 SE_PRIVILEGE_ENABLED);
00781
00782 Privileges[10].Luid =
SeAuditPrivilege;
00783 Privileges[10].Attributes =
00784 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00785 SE_PRIVILEGE_ENABLED);
00786
00787 Privileges[11].Luid =
SeSecurityPrivilege;
00788 Privileges[11].Attributes = 0;
00789
00790 Privileges[12].Luid =
SeSystemEnvironmentPrivilege;
00791 Privileges[12].Attributes = 0;
00792
00793 Privileges[13].Luid =
SeChangeNotifyPrivilege;
00794 Privileges[13].Attributes =
00795 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00796 SE_PRIVILEGE_ENABLED);
00797
00798
00799 Privileges[14].Luid =
SeBackupPrivilege;
00800 Privileges[14].Attributes = 0;
00801
00802 Privileges[15].Luid =
SeRestorePrivilege;
00803 Privileges[15].Attributes = 0;
00804
00805 Privileges[16].Luid =
SeShutdownPrivilege;
00806 Privileges[16].Attributes = 0;
00807
00808 Privileges[17].Luid =
SeLoadDriverPrivilege;
00809 Privileges[17].Attributes = 0;
00810
00811 Privileges[18].Luid =
SeProfileSingleProcessPrivilege;
00812 Privileges[18].Attributes =
00813 (SE_PRIVILEGE_ENABLED_BY_DEFAULT |
00814 SE_PRIVILEGE_ENABLED);
00815
00816 Privileges[19].Luid =
SeSystemtimePrivilege;
00817 Privileges[19].Attributes = 0;
00818
00819 Privileges[20].Luid =
SeUndockPrivilege ;
00820 Privileges[20].Attributes = 0 ;
00821
00822
00823
00824
00825
00826
00827
00828
00829
00830 PrimaryGroup.PrimaryGroup =
SeLocalSystemSid;
00831
Owner =
SeAliasAdminsSid;
00832
00833
00834
00835
00836
00837
00838
00839
00840
00841
00842
00843 Length = (ULONG)
sizeof(ACL) +
00844 ((ULONG)
sizeof(ACCESS_ALLOWED_ACE) -
sizeof(ULONG)) +
00845
SeLengthSid(
SeLocalSystemSid ) ;
00846
00847 TokenAcl = (PACL)
ExAllocatePoolWithTag(
PagedPool, Length, 'cAeS');
00848
00849
if ( TokenAcl ==
NULL ) {
00850
00851
return NULL ;
00852 }
00853
00854
Status =
RtlCreateAcl( TokenAcl, Length, ACL_REVISION2);
00855
ASSERT(
NT_SUCCESS(
Status) );
00856
00857
Status =
RtlAddAccessAllowedAce (
00858 TokenAcl,
00859 ACL_REVISION2,
00860 TOKEN_ALL_ACCESS,
00861
SeLocalSystemSid
00862 );
00863
ASSERT(
NT_SUCCESS(
Status) );
00864
00865 TokenSecurityDescriptor =
00866 (PSECURITY_DESCRIPTOR)
ExAllocatePoolWithTag(
00867
PagedPool,
00868
sizeof(SECURITY_DESCRIPTOR),
00869 'dSeS'
00870 );
00871
00872
if ( TokenSecurityDescriptor ==
NULL ) {
00873
00874
ExFreePool( TokenAcl );
00875
00876
return NULL ;
00877 }
00878
00879
Status =
RtlCreateSecurityDescriptor(
00880 TokenSecurityDescriptor,
00881 SECURITY_DESCRIPTOR_REVISION
00882 );
00883
ASSERT(
NT_SUCCESS(
Status) );
00884
00885
Status =
RtlSetDaclSecurityDescriptor (
00886 TokenSecurityDescriptor,
00887
TRUE,
00888 TokenAcl,
00889
FALSE
00890 );
00891
ASSERT(
NT_SUCCESS(
Status) );
00892
00893
00894
Status =
RtlSetOwnerSecurityDescriptor (
00895 TokenSecurityDescriptor,
00896
SeAliasAdminsSid,
00897
FALSE
00898 );
00899
ASSERT(
NT_SUCCESS(
Status) );
00900
00901
Status =
RtlSetGroupSecurityDescriptor (
00902 TokenSecurityDescriptor,
00903
SeAliasAdminsSid,
00904
FALSE
00905 );
00906
ASSERT(
NT_SUCCESS(
Status) );
00907
00908
00909
00910
00911
00912
00913
#ifdef TOKEN_DEBUG
00914
00915
00916
00917
DbgPrint(
"\n Creating system token...\n");
00918
00919
00921
#endif //TOKEN_DEBUG
00922
00923 InitializeObjectAttributes(
00924 &TokenObjectAttributes,
00925
NULL,
00926 0,
00927
NULL,
00928 TokenSecurityDescriptor
00929 );
00930
00931
00932
00933
ASSERT(
SeSystemDefaultDacl !=
NULL);
00934
Status =
SepCreateToken(
00935 (PHANDLE)&
Token,
00936
KernelMode,
00937 0,
00938 &TokenObjectAttributes,
00939 TokenPrimary,
00940 (SECURITY_IMPERSONATION_LEVEL)0,
00941 &
SeSystemAuthenticationId,
00942 &
NoExpiration,
00943 &UserId,
00944 3,
00945 GroupIds,
00946 GroupIdsLength,
00947 21,
00948 Privileges,
00949
sizeof(Privileges),
00950
Owner,
00951 PrimaryGroup.PrimaryGroup,
00952
SeSystemDefaultDacl,
00953 &
SeSystemTokenSource,
00954
TRUE,
00955
NULL,
00956
NULL
00957 );
00958
00959
ASSERT(
NT_SUCCESS(
Status));
00960
00961
00962
00963
00964
00965
00966 BufferLength = Length +
00967
sizeof(SECURITY_DESCRIPTOR_RELATIVE) +
00968 2 *
SeLengthSid(
SeAliasAdminsSid);
00969
00970
Buffer = (PSECURITY_DESCRIPTOR)
ExAllocatePoolWithTag(
PagedPool,
00971 BufferLength,
00972 'dSeS'
00973 );
00974
00975
if (
Buffer ) {
00976
00977
Status =
RtlAbsoluteToSelfRelativeSD( TokenSecurityDescriptor,
00978
Buffer,
00979 &BufferLength
00980 );
00981
ASSERT(
NT_SUCCESS(
Status));
00982
00983
Status =
ObAssignObjectSecurityDescriptor(
Token,
00984
Buffer,
00985
PagedPool
00986 );
00987
ASSERT(
NT_SUCCESS(
Status));
00988
00989 }
else {
00990
00991
ObDereferenceObject(
Token );
00992
00993
Token =
NULL ;
00994
00995 }
00996
00997
00998
00999
01000
01001
ExFreePool( TokenAcl );
01002
ExFreePool( TokenSecurityDescriptor );
01003
01004
return (PACCESS_TOKEN)
Token;
01005
01006 }
01007
01008
01009 PACCESS_TOKEN
01010 SeMakeAnonymousLogonToken (
01011 VOID
01012 )
01013
01014
01015
01016
01017
01018
01019
01020
01021
01022
01023
01024
01025
01026
01027
01028
01029
01030
01031
01032
01033
01034
01035
01036
01037
01038
01039
01040
01041
01042
01043
01044
01045
01046
01047
01048
01049
01050
01051
01052
01053
01054
01055
01056
01057
01058 {
01059
NTSTATUS Status;
01060
01061 PVOID
Token;
01062
01063 SID_AND_ATTRIBUTES UserId;
01064 PSID_AND_ATTRIBUTES GroupIds;
01065 TOKEN_PRIMARY_GROUP PrimaryGroup;
01066 ULONG GroupIdsLength;
01067 PACL TokenAcl;
01068 PSID
Owner;
01069 ULONG
NormalGroupAttributes;
01070 ULONG Length;
01071 OBJECT_ATTRIBUTES TokenObjectAttributes;
01072 PSECURITY_DESCRIPTOR TokenSecurityDescriptor;
01073 ULONG BufferLength;
01074 PVOID
Buffer;
01075
01076 ULONG_PTR GroupIdsBuffer[128 *
sizeof(ULONG) /
sizeof(ULONG_PTR)];
01077
01078 TIME_FIELDS
TimeFields;
01079 LARGE_INTEGER
NoExpiration;
01080
01081
PAGED_CODE();
01082
01083
01084
01085
01086
01087
01088
01089
TimeFields.Year = 3000;
01090
TimeFields.Month = 1;
01091
TimeFields.Day = 1;
01092
TimeFields.Hour = 1;
01093
TimeFields.Minute = 1;
01094
TimeFields.Second = 1;
01095
TimeFields.Milliseconds = 1;
01096
TimeFields.Weekday = 1;
01097
01098
RtlTimeFieldsToTime( &
TimeFields, &
NoExpiration );
01099
01100
01101
01102 GroupIds = (PSID_AND_ATTRIBUTES)GroupIdsBuffer;
01103
01104
01105
01106
01107
01108
01109
NormalGroupAttributes = (SE_GROUP_MANDATORY |
01110 SE_GROUP_ENABLED_BY_DEFAULT |
01111 SE_GROUP_ENABLED
01112 );
01113
01114
01115
01116
01117
01118
01119 UserId.Sid =
SeAnonymousLogonSid;
01120 UserId.Attributes = 0;
01121
01122
01123
01124
01125
01126
01127 GroupIds->Sid =
SeWorldSid;
01128 GroupIds->Attributes =
NormalGroupAttributes;
01129
01130
01131 GroupIdsLength = (ULONG)LongAlignSize(
SeLengthSid(GroupIds->Sid)) +
01132
sizeof(SID_AND_ATTRIBUTES);
01133
01134
ASSERT( GroupIdsLength <= 128 *
sizeof(ULONG) );
01135
01136
01137
01138
01139
01140
01141
01142
01143
01144
01145
01146 PrimaryGroup.PrimaryGroup =
SeAnonymousLogonSid;
01147
01148
01149
01150
01151
01152
01153
01154
01155
01156
01157
01158 Length = (ULONG)
sizeof(ACL) +
01159 (ULONG)
sizeof(ACCESS_ALLOWED_ACE) +
01160
SeLengthSid(
SeWorldSid ) +
01161 8;
01162
ASSERT( Length < 200 );
01163
01164 TokenAcl = (PACL)
ExAllocatePoolWithTag(
PagedPool, 200, 'cAeS');
01165
01166
if ( !TokenAcl ) {
01167
01168
return NULL ;
01169 }
01170
01171
Status =
RtlCreateAcl( TokenAcl, Length, ACL_REVISION2);
01172
ASSERT(
NT_SUCCESS(
Status) );
01173
01174
Status =
RtlAddAccessAllowedAce (
01175 TokenAcl,
01176 ACL_REVISION2,
01177 TOKEN_ALL_ACCESS,
01178
SeWorldSid
01179 );
01180
ASSERT(
NT_SUCCESS(
Status) );
01181
01182 TokenSecurityDescriptor =
01183 (PSECURITY_DESCRIPTOR)
ExAllocatePoolWithTag(
01184
PagedPool,
01185 SECURITY_DESCRIPTOR_MIN_LENGTH,
01186 'dSeS'
01187 );
01188
01189
if ( !TokenSecurityDescriptor ) {
01190
01191
ExFreePool( TokenAcl );
01192
01193
return NULL ;
01194 }
01195
01196
01197
Status =
RtlCreateSecurityDescriptor(
01198 TokenSecurityDescriptor,
01199 SECURITY_DESCRIPTOR_REVISION
01200 );
01201
ASSERT(
NT_SUCCESS(
Status) );
01202
01203
Status =
RtlSetDaclSecurityDescriptor (
01204 TokenSecurityDescriptor,
01205
TRUE,
01206 TokenAcl,
01207
FALSE
01208 );
01209
ASSERT(
NT_SUCCESS(
Status) );
01210
01211
01212
Status =
RtlSetOwnerSecurityDescriptor (
01213 TokenSecurityDescriptor,
01214
SeWorldSid,
01215
FALSE
01216 );
01217
ASSERT(
NT_SUCCESS(
Status) );
01218
01219
Status =
RtlSetGroupSecurityDescriptor (
01220 TokenSecurityDescriptor,
01221
SeWorldSid,
01222
FALSE
01223 );
01224
ASSERT(
NT_SUCCESS(
Status) );
01225
01226
01227
01228
01229
01230
01231
#ifdef TOKEN_DEBUG
01232
01233
01234
01235
DbgPrint(
"\n Creating system token...\n");
01236
01237
01239
#endif //TOKEN_DEBUG
01240
01241 InitializeObjectAttributes(
01242 &TokenObjectAttributes,
01243
NULL,
01244 0,
01245
NULL,
01246 TokenSecurityDescriptor
01247 );
01248
01249
01250
01251
Status =
SepCreateToken(
01252 (PHANDLE)&
Token,
01253
KernelMode,
01254 0,
01255 &TokenObjectAttributes,
01256 TokenPrimary,
01257 (SECURITY_IMPERSONATION_LEVEL)0,
01258 &
SeAnonymousAuthenticationId,
01259 &
NoExpiration,
01260 &UserId,
01261 1,
01262 GroupIds,
01263 GroupIdsLength,
01264 0,
01265
NULL,
01266 0,
01267
NULL,
01268 PrimaryGroup.PrimaryGroup,
01269 TokenAcl,
01270 &
SeSystemTokenSource,
01271
TRUE,
01272
NULL,
01273
NULL
01274 );
01275
01276
ASSERT(
NT_SUCCESS(
Status));
01277
01278
01279
01280
01281
01282
01283 BufferLength = Length +
01284
sizeof(SECURITY_DESCRIPTOR) +
01285 2 *
SeLengthSid(
SeAliasAdminsSid);
01286
01287
Buffer = (PSECURITY_DESCRIPTOR)
ExAllocatePoolWithTag(
PagedPool,
01288 BufferLength,
01289 'dSeS'
01290 );
01291
01292
if (
Buffer ) {
01293
01294
Status =
RtlAbsoluteToSelfRelativeSD( TokenSecurityDescriptor,
01295
Buffer,
01296 &BufferLength
01297 );
01298
ASSERT(
NT_SUCCESS(
Status));
01299
01300
Status =
ObAssignObjectSecurityDescriptor(
Token,
01301
Buffer,
01302
PagedPool
01303 );
01304
ASSERT(
NT_SUCCESS(
Status));
01305
01306 }
else {
01307
01308
ObDereferenceObject(
Token );
01309
01310
Token =
NULL ;
01311 }
01312
01313
01314
01315
01316
01317
01318
ExFreePool( TokenAcl );
01319
ExFreePool( TokenSecurityDescriptor );
01320
01321
return (PACCESS_TOKEN)
Token;
01322
01323 }
01324
01325
01326
NTSTATUS
01327 SeSubProcessToken (
01328 IN
PEPROCESS ParentProcess,
01329 OUT PACCESS_TOKEN *ChildToken
01330 )
01331
01332
01333
01334
01335
01336
01337
01338
01339
01340
01341
01342
01343
01344
01345
01346
01347
01348
01349
01350
01351
01352
01353
01354
01355
01356
01357
01358
01359
01360
01361
01362 {
01363
01364
01365
01366
01367
01368
01369
01370
01371
01372
01373
01374
KPROCESSOR_MODE PreviousMode;
01375
PTOKEN ParentToken;
01376
PTOKEN NewToken;
01377 HANDLE NewTokenHandle;
01378 OBJECT_ATTRIBUTES
PrimaryTokenAttributes;
01379
01380
PTOKEN InsertedToken;
01381
01382
NTSTATUS Status;
01383
NTSTATUS IgnoreStatus;
01384
01385
PAGED_CODE();
01386
01387 PreviousMode = KeGetPreviousMode();
01388
01389 InitializeObjectAttributes(
01390 &
PrimaryTokenAttributes,
01391
NULL,
01392 0,
01393
NULL,
01394
NULL
01395 );
01396
01397
#ifdef TOKEN_DEBUG
01398
DbgPrint(
"\nCreating sub-process token...\n");
01399
DbgPrint(
"Parent token address = 0x%lx\n", ParentProcess->Token);
01400
#endif //TOKEN_DEBUG
01401
01402 ParentToken = (
PTOKEN)
PsReferencePrimaryToken( ParentProcess );
01403
01404
Status =
SepDuplicateToken(
01405 ParentToken,
01406 &
PrimaryTokenAttributes,
01407
FALSE,
01408 TokenPrimary,
01409 (SECURITY_IMPERSONATION_LEVEL)0,
01410
KernelMode,
01411 &NewToken
01412 );
01413
01414
PsDereferencePrimaryToken( (PACCESS_TOKEN)ParentToken );
01415
01416
if (
NT_SUCCESS(
Status)) {
01417
01418
01419
01420
01421
01422
01423
Status =
ObInsertObject(
01424 NewToken,
01425
NULL,
01426 0,
01427 1,
01428 (PVOID *)&InsertedToken,
01429 &NewTokenHandle
01430 );
01431
01432
if (
NT_SUCCESS(
Status)) {
01433
01434 *ChildToken = InsertedToken;
01435 InsertedToken->TokenInUse =
TRUE;
01436 IgnoreStatus = ZwClose( NewTokenHandle );
01437
01438
01439
01440
01441
01442
01443
01444
01445 }
else {
01446
01447
01448
01449
01450
01451
01452 }
01453 }
01454
01455
return Status;
01456 }
01457
01458
01459 BOOLEAN
01460 SepTokenInitialization ( VOID )
01461
01462
01463
01464
01465
01466
01467
01468
01469
01470
01471
01472
01473
01474
01475
01476
01477
01478
01479
01480
01481
01482
01483
01484
01485 {
01486
01487
OBJECT_TYPE_INITIALIZER ObjectTypeInitializer;
01488
NTSTATUS Status;
01489 UNICODE_STRING TypeName;
01490
01491
PAGED_CODE();
01492
01493
01494
01495
01496
01497
RtlInitUnicodeString(&TypeName,
L"Token");
01498
01499
01500
01501
01502
01503
01504
ExInitializeResource(&
SepTokenLock);
01505
01506
01507
#if 0
01508
BUG, BUG Need to get system
default ACL to protect token object
01509
#endif
01510
01511
01512
01513
01514
01515 RtlZeroMemory(&ObjectTypeInitializer,
sizeof(ObjectTypeInitializer));
01516 ObjectTypeInitializer.Length =
sizeof(ObjectTypeInitializer);
01517 ObjectTypeInitializer.InvalidAttributes = OBJ_OPENLINK;
01518 ObjectTypeInitializer.GenericMapping =
SepTokenMapping;
01519 ObjectTypeInitializer.SecurityRequired =
TRUE;
01520 ObjectTypeInitializer.UseDefaultObject =
TRUE;
01521 ObjectTypeInitializer.PoolType =
PagedPool;
01522 ObjectTypeInitializer.ValidAccessMask = TOKEN_ALL_ACCESS;
01523 ObjectTypeInitializer.DeleteProcedure =
SepTokenDeleteMethod;
01524
01525
Status =
ObCreateObjectType(&TypeName,
01526 &ObjectTypeInitializer,
01527 (PSECURITY_DESCRIPTOR)
NULL,
01528 &
SepTokenObjectType
01529 );
01530
01531
01532
#if 0
01533
BUG, BUG Now track down all pseudo tokens used during system initialization
01534 BUG, BUG and replace them with real ones.
01535 #endif
01536
01537
01538
01539
01540
01541
01542
return (BOOLEAN)
NT_SUCCESS(
Status);
01543 }
01544
01546
01547
01548
01550
#ifdef TOKEN_DEBUG
01551
VOID
01552 SepDumpToken(
01553 IN PTOKEN T
01554 )
01555
01556 {
01557 ULONG
Index;
01558
01559
01560
01561
01562
01563
DbgPrint(
"\n");
01564
01565
DbgPrint(
" address: 0x%lx \n", ((ULONG)T) );
01566
01567
DbgPrint(
" TokenId: (0x%lx, 0x%lx) \n",
01568 T->TokenId.HighPart, T->TokenId.LowPart );
01569
01570
if ( (T->AuthenticationId.Data[0] ==
SeSystemAuthenticationId.Data[0]) &&
01571 (T->AuthenticationId.Data[1] ==
SeSystemAuthenticationId.Data[1]) &&
01572 (T->AuthenticationId.Data[2] ==
SeSystemAuthenticationId.Data[2]) &&
01573 (T->AuthenticationId.Data[3] ==
SeSystemAuthenticationId.Data[3]) ) {
01574
01575
DbgPrint(
" AuthenticationId: SeSystemAuthenticationId \n");
01576
01577 }
else {
01578
01579
DbgPrint(
" AuthenticationId: (0x%lx, 0x%lx, 0x%lx, 0x%lx) \n",
01580 T->AuthenticationId.Data[0],
01581 T->AuthenticationId.Data[1],
01582 T->AuthenticationId.Data[2],
01583 T->AuthenticationId.Data[3] );
01584 }
01585
01586
DbgPrint(
" ExpirationTime: 0x%lx, 0x%lx \n",
01587 T->ExpirationTime.HighPart,
01588 T->ExpirationTime.LowPart );
01589
01590
if (T->TokenType == TokenPrimary) {
01591
DbgPrint(
" TokenType: Primary \n");
01592 }
else {
01593
if (T->TokenType == TokenImpersonation) {
01594
DbgPrint(
" TokenType: Impersonation \n");
01595 }
else {
01596
DbgPrint(
" TokenType: (Unknown type, value = 0x%lx) \n",
01597 ((ULONG)T-TokenType) );
01598 }
01599 }
01600
01601
DbgPrint(
" ImpersonationLevel: 0x%lx \n",
01602 ((ULONG)T->ImpersonationLevel) );
01603
01604
DbgPrint(
" TokenSource: (not yet provided) \n");
01605
DbgPrint(
" DynamicCharged: 0x%lx \n", T->DynamicCharged);
01606
DbgPrint(
" UserAndGroupCount: 0x%lx \n", T->UserAndGroupCount);
01607
DbgPrint(
" PrivilegeCount: 0x%lx \n", T->PrivilegeCount);
01608
DbgPrint(
" VariableLength: 0x%lx \n", T->VariableLength);
01609
01610
01611
DbgPrint(
" ModifiedId: (0x%lx, 0x%lx) \n",
01612 T->ModifiedId.HighPart,
01613 T->ModifiedId.LowPart );
01614
DbgPrint(
" DynamicAvailable: 0x%lx \n", T->DynamicAvailable);
01615
DbgPrint(
" DefaultOwnerIndex: 0x%lx \n", T->DefaultOwnerIndex);
01616
01617
01618
DbgPrint(
" Address of DynamicPart: 0x%lx \n",
01619 (* (PULONG)((PVOID)(&(T->DynamicPart)))) );
01620
DbgPrint(
" Address of Default DACL: 0x%lx \n",
01621 (* (PULONG)((PVOID)(&(T->DefaultDacl)))) );
01622
01623
DbgPrint(
" Address Of Variable Part: 0x%lx \n",
01624 &(T->VariablePart) );
01625
01626
DbgPrint(
"\n");
01627
DbgPrint(
" PrimaryGroup:\n");
01628
DbgPrint(
" Address: 0x%lx \n",
01629 (* (PULONG)((PVOID)(&(T->PrimaryGroup)))) );
01630
DbgPrint(
" Length: 0x%lx \n",
01631
SeLengthSid((T->PrimaryGroup)) );
01632
DbgPrint(
"\n");
01633
DbgPrint(
" UserAndGroups: 0x%lx \n",
01634 (* (PULONG)((PVOID)(&(T->UserAndGroups)))) );
01635
DbgPrint(
" User ID - \n");
01636
DbgPrint(
" Address: 0x%lx \n",
01637 (* (PULONG)((PVOID)(&(T->UserAndGroups[0].Sid)))) );
01638
DbgPrint(
" Attributes: 0x%lx \n",
01639 (T->UserAndGroups[0].Attributes) );
01640
DbgPrint(
" Length: 0x%lx \n",
01641
SeLengthSid((T->UserAndGroups[0].Sid)) );
01642
Index = 1;
01643
while (
Index < T->UserAndGroupCount) {
01644
DbgPrint(
" Group 0x%lx - \n", Index );
01645
DbgPrint(
" Address: 0x%lx \n",
01646 (* (PULONG)((PVOID)(&(T->UserAndGroups[Index].Sid)))) );
01647
DbgPrint(
" Attributes: 0x%lx \n",
01648 (T->UserAndGroups[Index].Attributes) );
01649
DbgPrint(
" Length: 0x%lx \n",
01650
SeLengthSid((T->UserAndGroups[Index].Sid)) );
01651
Index += 1;
01652 }
01653
01654
Index = 0;
01655
while (
Index < T->RestrictedSidCount) {
01656
DbgPrint(
" Sid 0x%lx - \n", Index );
01657
DbgPrint(
" Address: 0x%lx \n",
01658 (* (PULONG)((PVOID)(&(T->RestrictedSids[Index].Sid)))) );
01659
DbgPrint(
" Attributes: 0x%lx \n",
01660 (T->RestrictedSids[Index].Attributes) );
01661
DbgPrint(
" Length: 0x%lx \n",
01662
SeLengthSid((T->RestrictedSids[Index].Sid)) );
01663
Index += 1;
01664 }
01665
01666
01667
DbgPrint(
"\n");
01668
DbgPrint(
" Privileges: 0x%lx\n",
01669 (* (PULONG)((PVOID)(&(T->Privileges)))) );
01670
Index = 0;
01671
while (
Index < T->PrivilegeCount) {
01672
DbgPrint(
" Privilege 0x%lx - \n", Index );
01673
DbgPrint(
" Address: 0x%lx \n",
01674 (&(T->Privileges[Index])) );
01675
DbgPrint(
" LUID: (0x%lx, 0x%lx) \n",
01676 T->Privileges[Index].Luid.HighPart,
01677 T->Privileges[Index].Luid.LowPart );
01678
DbgPrint(
" Attributes: 0x%lx \n",
01679 T->Privileges[Index].Attributes );
01680
01681
Index += 1;
01682 }
01683
01684
return;
01685
01686 }
01687
#endif //TOKEN_DEBUG
01688
01689
NTSTATUS
01690 NtCreateToken(
01691 OUT PHANDLE TokenHandle,
01692 IN ACCESS_MASK DesiredAccess,
01693 IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL,
01694 IN TOKEN_TYPE TokenType,
01695 IN PLUID AuthenticationId,
01696 IN PLARGE_INTEGER ExpirationTime,
01697 IN PTOKEN_USER User,
01698 IN PTOKEN_GROUPS Groups,
01699 IN PTOKEN_PRIVILEGES Privileges,
01700 IN PTOKEN_OWNER Owner OPTIONAL,
01701 IN PTOKEN_PRIMARY_GROUP PrimaryGroup,
01702 IN PTOKEN_DEFAULT_DACL DefaultDacl OPTIONAL,
01703 IN PTOKEN_SOURCE TokenSource
01704 )
01705
01706
01707
01708
01709
01710
01711
01712
01713
01714
01715
01716
01717
01718
01719
01720
01721
01722
01723
01724
01725
01726
01727
01728
01729
01730
01731
01732
01733
01734
01735
01736
01737
01738
01739
01740
01741
01742
01743
01744
01745
01746
01747
01748
01749
01750
01751
01752
01753
01754
01755
01756
01757
01758
01759
01760
01761
01762
01763
01764
01765
01766
01767
01768
01769
01770
01771
01772
01773
01774
01775 {
01776
01777
KPROCESSOR_MODE PreviousMode;
01778
NTSTATUS Status;
01779 ULONG Ignore;
01780
01781
01782 HANDLE LocalHandle;
01783
01784 BOOLEAN SecurityQosPresent =
FALSE;
01785 SECURITY_ADVANCED_QUALITY_OF_SERVICE CapturedSecurityQos;
01786
01787 LUID CapturedAuthenticationId;
01788 LARGE_INTEGER CapturedExpirationTime;
01789
01790 PSID_AND_ATTRIBUTES CapturedUser =
NULL;
01791 ULONG CapturedUserLength;
01792
01793 ULONG CapturedGroupCount;
01794 PSID_AND_ATTRIBUTES CapturedGroups =
NULL;
01795 ULONG CapturedGroupsLength;
01796
01797 ULONG CapturedPrivilegeCount;
01798 PLUID_AND_ATTRIBUTES CapturedPrivileges =
NULL;
01799 ULONG CapturedPrivilegesLength;
01800
01801 PSID CapturedOwner =
NULL;
01802
01803 PSID CapturedPrimaryGroup =
NULL;
01804
01805 PACL CapturedDefaultDacl =
NULL;
01806
01807 TOKEN_SOURCE CapturedTokenSource;
01808
01809 PVOID CapturedAddress;
01810
01811
PAGED_CODE();
01812
01813 PreviousMode = KeGetPreviousMode();
01814
01815
if (PreviousMode !=
KernelMode) {
01816
01817
01818
01819
01820
01821
try {
01822
01823
ProbeForWriteHandle(TokenHandle);
01824
01825
01826
ProbeForRead( ExpirationTime,
sizeof(LARGE_INTEGER),
sizeof(ULONG) );
01827
ProbeForRead( Groups,
sizeof(TOKEN_GROUPS),
sizeof(ULONG) );
01828
ProbeForRead( Privileges,
sizeof(TOKEN_PRIVILEGES),
sizeof(ULONG) );
01829
ProbeForRead( TokenSource,
sizeof(TOKEN_SOURCE),
sizeof(ULONG) );
01830
01831
01832
if ( ARGUMENT_PRESENT(
Owner) ) {
01833
ProbeForRead(
Owner,
sizeof(TOKEN_OWNER),
sizeof(ULONG) );
01834 }
01835
01836
01837
ProbeForRead(
01838 PrimaryGroup,
01839
sizeof(TOKEN_PRIMARY_GROUP),
01840
sizeof(ULONG)
01841 );
01842
01843
01844
if ( ARGUMENT_PRESENT(DefaultDacl) ) {
01845
ProbeForRead(
01846 DefaultDacl,
01847
sizeof(TOKEN_DEFAULT_DACL),
01848
sizeof(ULONG)
01849 );
01850 }
01851
01852
ProbeForRead(
01853 AuthenticationId,
01854
sizeof(LUID),
01855
sizeof(ULONG)
01856 );
01857
01858 } except(
EXCEPTION_EXECUTE_HANDLER) {
01859
return GetExceptionCode();
01860 }
01861
01862 }
01863
01864
01865
01866
01867
01868
01869
Status =
SeCaptureSecurityQos(
01870
ObjectAttributes,
01871 PreviousMode,
01872 &SecurityQosPresent,
01873 &CapturedSecurityQos
01874 );
01875
01876
if (!
NT_SUCCESS(
Status)) {
01877
return Status;
01878 }
01879
01880
if (TokenType == TokenImpersonation) {
01881
01882
if (!SecurityQosPresent) {
01883
return STATUS_BAD_IMPERSONATION_LEVEL;
01884 }
01885
01886 }
01887
01888
01889
01890
01891
01892
01893
01894
try {
01895
01896
Status = STATUS_SUCCESS;
01897
01898
01899
01900
01901
01902
RtlCopyLuid( &CapturedAuthenticationId, AuthenticationId );
01903
01904
01905
01906
01907
01908 CapturedExpirationTime = (*ExpirationTime);
01909
01910
01911
01912
01913
01914
if (
NT_SUCCESS(
Status)) {
01915
Status =
SeCaptureSidAndAttributesArray(
01916 &(User->User),
01917 1,
01918 PreviousMode,
01919
NULL, 0,
01920
PagedPool,
01921
TRUE,
01922 &CapturedUser,
01923 &CapturedUserLength
01924 );
01925 }
01926
01927
01928
01929
01930
01931
01932
if (
NT_SUCCESS(
Status)) {
01933 CapturedGroupCount = Groups->GroupCount;
01934
Status =
SeCaptureSidAndAttributesArray(
01935 (Groups->Groups),
01936 CapturedGroupCount,
01937 PreviousMode,
01938
NULL, 0,
01939
PagedPool,
01940
TRUE,
01941 &CapturedGroups,
01942 &CapturedGroupsLength
01943 );
01944 }
01945
01946
01947
01948
01949
01950
01951
if (
NT_SUCCESS(
Status)) {
01952 CapturedPrivilegeCount = Privileges->PrivilegeCount;
01953
Status =
SeCaptureLuidAndAttributesArray(
01954 (Privileges->Privileges),
01955 CapturedPrivilegeCount,
01956 PreviousMode,
01957
NULL, 0,
01958
PagedPool,
01959
TRUE,
01960 &CapturedPrivileges,
01961 &CapturedPrivilegesLength
01962 );
01963 }
01964
01965
01966
01967
01968
01969
01970
if ( ARGUMENT_PRESENT(
Owner) &&
NT_SUCCESS(
Status)) {
01971 CapturedAddress =
Owner->Owner;
01972
Status =
SeCaptureSid(
01973 (PSID)CapturedAddress,
01974 PreviousMode,
01975
NULL, 0,
01976
PagedPool,
01977
TRUE,
01978 &CapturedOwner
01979 );
01980 }
01981
01982
01983
01984
01985
01986
if (
NT_SUCCESS(
Status)) {
01987 CapturedAddress = PrimaryGroup->PrimaryGroup;
01988
Status =
SeCaptureSid(
01989 (PSID)CapturedAddress,
01990 PreviousMode,
01991
NULL, 0,
01992
PagedPool,
01993
TRUE,
01994 &CapturedPrimaryGroup
01995 );
01996 }
01997
01998
01999
02000
02001
02002
02003
if ( ARGUMENT_PRESENT(DefaultDacl) &&
NT_SUCCESS(
Status) ) {
02004 CapturedAddress = DefaultDacl->DefaultDacl;
02005
if (CapturedAddress !=
NULL) {
02006
Status =
SeCaptureAcl(
02007 (PACL)CapturedAddress,
02008 PreviousMode,
02009
NULL, 0,
02010
NonPagedPool,
02011
TRUE,
02012 &CapturedDefaultDacl,
02013 &Ignore
02014 );
02015 }
02016 }
02017
02018
02019
02020
02021
02022 CapturedTokenSource = (*TokenSource);
02023
02024
02025 } except(
EXCEPTION_EXECUTE_HANDLER) {
02026
02027
if (CapturedUser !=
NULL) {
02028
SeReleaseSidAndAttributesArray(
02029 CapturedUser,
02030 PreviousMode,
02031
TRUE
02032 );
02033 }
02034
02035
if (CapturedGroups !=
NULL) {
02036
SeReleaseSidAndAttributesArray(
02037 CapturedGroups,
02038 PreviousMode,
02039
TRUE
02040 );
02041 }
02042
02043
if (CapturedPrivileges !=
NULL) {
02044
SeReleaseLuidAndAttributesArray(
02045 CapturedPrivileges,
02046 PreviousMode,
02047
TRUE
02048 );
02049 }
02050
02051
if (CapturedOwner !=
NULL) {
02052
SeReleaseSid( CapturedOwner, PreviousMode,
TRUE);
02053 }
02054
02055
if (CapturedPrimaryGroup !=
NULL) {
02056
SeReleaseSid( CapturedPrimaryGroup, PreviousMode,
TRUE);
02057 }
02058
02059
if (CapturedDefaultDacl !=
NULL) {
02060
SeReleaseAcl( CapturedDefaultDacl, PreviousMode,
TRUE);
02061 }
02062
02063
if (SecurityQosPresent ==
TRUE) {
02064
SeFreeCapturedSecurityQos( &CapturedSecurityQos );
02065 }
02066
02067
return GetExceptionCode();
02068
02069 }
02070
02071
02072
02073
02074
02075
if (
NT_SUCCESS(
Status)) {
02076
Status =
SepCreateToken(
02077 &LocalHandle,
02078 PreviousMode,
02079 DesiredAccess,
02080
ObjectAttributes,
02081 TokenType,
02082 CapturedSecurityQos.ImpersonationLevel,
02083 &CapturedAuthenticationId,
02084 &CapturedExpirationTime,
02085 CapturedUser,
02086 CapturedGroupCount,
02087 CapturedGroups,
02088 CapturedGroupsLength,
02089 CapturedPrivilegeCount,
02090 CapturedPrivileges,
02091 CapturedPrivilegesLength,
02092 CapturedOwner,
02093 CapturedPrimaryGroup,
02094 CapturedDefaultDacl,
02095 &CapturedTokenSource,
02096
FALSE,
02097 SecurityQosPresent ? CapturedSecurityQos.ProxyData :
NULL,
02098 SecurityQosPresent ? CapturedSecurityQos.AuditData :
NULL
02099 );
02100 }
02101
02102
02103
02104
02105
02106
if (CapturedUser !=
NULL) {
02107
SeReleaseSidAndAttributesArray( CapturedUser, PreviousMode,
TRUE);
02108 }
02109
if (CapturedGroups !=
NULL) {
02110
SeReleaseSidAndAttributesArray( CapturedGroups, PreviousMode,
TRUE);
02111 }
02112
02113
if (CapturedPrivileges !=
NULL) {
02114
SeReleaseLuidAndAttributesArray( CapturedPrivileges, PreviousMode,
TRUE);
02115 }
02116
02117
if (CapturedOwner !=
NULL) {
02118
SeReleaseSid( CapturedOwner, PreviousMode,
TRUE);
02119 }
02120
02121
if (CapturedPrimaryGroup !=
NULL) {
02122
SeReleaseSid( CapturedPrimaryGroup, PreviousMode,
TRUE);
02123 }
02124
02125
if (CapturedDefaultDacl !=
NULL) {
02126
SeReleaseAcl( CapturedDefaultDacl, PreviousMode,
TRUE);
02127 }
02128
02129
if (SecurityQosPresent ==
TRUE) {
02130
SeFreeCapturedSecurityQos( &CapturedSecurityQos );
02131 }
02132
02133
02134
02135
02136
02137
if (
NT_SUCCESS(
Status)) {
02138
try { *TokenHandle = LocalHandle; }
02139 except(
EXCEPTION_EXECUTE_HANDLER) {
return GetExceptionCode(); }
02140 }
02141
02142
return Status;
02143
02144 }
02145
02146
02147
02149
02150
02151
02153
02154
02155
VOID
02156 SepTokenDeleteMethod (
02157 IN PVOID Token
02158 )
02159
02160
02161
02162
02163
02164
02165
02166
02167
02168
02169
02170
02171
02172
02173
02174
02175
02176
02177
02178 {
02179
PAGED_CODE();
02180
02181
02182
02183
02184
02185
SepDeReferenceLogonSession( &(((
TOKEN *)
Token)->AuthenticationId) );
02186
02187
02188
02189
02190
02191
02192
if (ARGUMENT_PRESENT( ((
TOKEN *)
Token)->DynamicPart)) {
02193
ExFreePool( ((
TOKEN *)
Token)->DynamicPart );
02194 }
02195
02196
02197
02198
02199
02200
if (ARGUMENT_PRESENT(((
TOKEN *)
Token)->ProxyData)) {
02201
SepFreeProxyData( ((
TOKEN *)
Token)->ProxyData );
02202 }
02203
02204
if (ARGUMENT_PRESENT(((
TOKEN *)
Token)->AuditData )) {
02205
ExFreePool( (((
TOKEN *)
Token)->AuditData) );
02206 }
02207
02208
02209
return;
02210 }
02211
02212
NTSTATUS
02213 SepCreateToken(
02214 OUT PHANDLE TokenHandle,
02215 IN KPROCESSOR_MODE RequestorMode,
02216 IN ACCESS_MASK DesiredAccess,
02217 IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL,
02218 IN TOKEN_TYPE TokenType,
02219 IN SECURITY_IMPERSONATION_LEVEL ImpersonationLevel OPTIONAL,
02220 IN PLUID AuthenticationId,
02221 IN PLARGE_INTEGER ExpirationTime,
02222 IN PSID_AND_ATTRIBUTES User,
02223 IN ULONG GroupCount,
02224 IN PSID_AND_ATTRIBUTES Groups,
02225 IN ULONG GroupsLength,
02226 IN ULONG PrivilegeCount,
02227 IN PLUID_AND_ATTRIBUTES Privileges,
02228 IN ULONG PrivilegesLength,
02229 IN PSID Owner OPTIONAL,
02230 IN PSID PrimaryGroup,
02231 IN PACL DefaultDacl OPTIONAL,
02232 IN PTOKEN_SOURCE TokenSource,
02233 IN BOOLEAN SystemToken,
02234 IN PSECURITY_TOKEN_PROXY_DATA ProxyData OPTIONAL,
02235 IN PSECURITY_TOKEN_AUDIT_DATA AuditData OPTIONAL
02236 )
02237
02238
02239
02240
02241
02242
02243
02244
02245
02246
02247
02248
02249
02250
02251
02252
02253
02254
02255
02256
02257
02258
02259
02260
02261
02262
02263
02264
02265
02266
02267
02268
02269
02270
02271
02272
02273
02274
02275
02276
02277
02278
02279
02280
02281
02282
02283
02284
02285
02286
02287
02288
02289
02290
02291
02292
02293
02294
02295
02296
02297
02298
02299
02300
02301
02302
02303
02304
02305
02306
02307
02308
02309
02310
02311
02312
02313
02314
02315
02316
02317
02318
02319
02320
02321
02322
02323
02324
02325
02326
02327
02328
02329
02330
02331
02332
02333
02334
02335
02336
02337
02338
02339
02340
02341
02342
02343
02344
02345 {
02346
02347
PTOKEN Token;
02348
NTSTATUS Status;
02349
02350 ULONG PagedPoolSize;
02351
02352 ULONG PrimaryGroupLength;
02353
02354 ULONG TokenBodyLength;
02355 ULONG VariableLength;
02356
02357 ULONG DefaultOwnerIndex;
02358 PUCHAR Where ;
02359 ULONG ComputedPrivLength ;
02360
02361
02362 PSID NextSidFree;
02363
02364 ULONG DynamicLength =
TOKEN_DEFAULT_DYNAMIC_CHARGE;
02365 ULONG DynamicLengthUsed;
02366
02367 ULONG SubAuthorityCount;
02368 ULONG GroupIndex;
02369 ULONG PrivilegeIndex;
02370 BOOLEAN OwnerFound;
02371
02372 UCHAR TokenFlags = 0;
02373
02374
ACCESS_STATE AccessState;
02375
AUX_ACCESS_DATA AuxData;
02376 LUID NewModifiedId;
02377
02378
PAGED_CODE();
02379
02380
ASSERT(
sizeof(SECURITY_IMPERSONATION_LEVEL) <=
sizeof(ULONG) );
02381
02382
02383
02384
02385
02386
02387
02388
02389
02390
for (GroupIndex=0; GroupIndex < GroupCount; GroupIndex++) {
02391
if (Groups[GroupIndex].Attributes & SE_GROUP_MANDATORY) {
02392 Groups[GroupIndex].Attributes |= (SE_GROUP_ENABLED | SE_GROUP_ENABLED_BY_DEFAULT);
02393 }
02394
if (
RtlEqualSid(
SeAliasAdminsSid, Groups[GroupIndex].Sid ) )
02395 {
02396 TokenFlags |=
TOKEN_HAS_ADMIN_GROUP ;
02397 }
02398 }
02399
02400
02401
02402
02403
02404
02405
02406
for (PrivilegeIndex = 0; PrivilegeIndex < PrivilegeCount; PrivilegeIndex++) {
02407
02408
if (((
RtlEqualLuid(&Privileges[PrivilegeIndex].Luid,&
SeChangeNotifyPrivilege))
02409 &&
02410 (Privileges[PrivilegeIndex].Attributes & SE_PRIVILEGE_ENABLED))) {
02411
02412 TokenFlags |=
TOKEN_HAS_TRAVERSE_PRIVILEGE;
02413
break;
02414 }
02415 }
02416
02417
02418
02419
02420
02421
02422
ExAllocateLocallyUniqueId( &NewModifiedId );
02423
02424
02425
02426
02427
02428
02429
if (!ARGUMENT_PRESENT(
Owner)) {
02430
02431 DefaultOwnerIndex = 0;
02432
02433 }
else {
02434
02435
02436
if (
RtlEqualSid(
Owner, User->Sid ) ) {
02437
02438 DefaultOwnerIndex = 0;
02439
02440 }
else {
02441
02442 GroupIndex = 0;
02443 OwnerFound =
FALSE;
02444
02445
while ((GroupIndex < GroupCount) && (!OwnerFound)) {
02446
02447
if (
RtlEqualSid(
Owner, (Groups[GroupIndex].Sid) ) ) {
02448
02449
02450
02451
02452
02453
if (
SepArrayGroupAttributes( Groups, GroupIndex ) &
02454 SE_GROUP_OWNER ) {
02455
02456 DefaultOwnerIndex = GroupIndex + 1;
02457 OwnerFound =
TRUE;
02458
02459 }
else {
02460
02461
return STATUS_INVALID_OWNER;
02462
02463 }
02464
02465 }
02466
02467 GroupIndex += 1;
02468
02469 }
02470
02471
if (!OwnerFound) {
02472
02473
return STATUS_INVALID_OWNER;
02474
02475 }
02476 }
02477 }
02478
02479
02480
02481
02482
02483
02484
02485
02486
Status =
SepReferenceLogonSession( AuthenticationId );
02487
if ( !
NT_SUCCESS(
Status) ) {
02488
return Status;
02489 }
02490
02491
02492
02493
02494
02495
02496
02497
02498
02499
02500
02501
02502
02503
02504 ComputedPrivLength = PrivilegeCount *
sizeof( LUID_AND_ATTRIBUTES ) ;
02505
02506 ComputedPrivLength =
ALIGN_UP( ComputedPrivLength, PVOID );
02507
02508 GroupsLength =
ALIGN_UP( GroupsLength, PVOID );
02509
02510
02511 VariableLength = GroupsLength + ComputedPrivLength +
02512
ALIGN_UP( (GroupCount *
sizeof( SID_AND_ATTRIBUTES )), PVOID ) ;
02513
02514 SubAuthorityCount = ((SID *)(User->Sid))->SubAuthorityCount;
02515 VariableLength +=
sizeof(SID_AND_ATTRIBUTES) +
02516 (ULONG)LongAlignSize(
RtlLengthRequiredSid( SubAuthorityCount ));
02517
02518
02519
02520
02521
02522
02523
02524
02525 SubAuthorityCount = ((SID *)PrimaryGroup)->SubAuthorityCount;
02526 DynamicLengthUsed = (ULONG)LongAlignSize(
RtlLengthRequiredSid( SubAuthorityCount ));
02527
02528
if (ARGUMENT_PRESENT(DefaultDacl)) {
02529 DynamicLengthUsed += (ULONG)LongAlignSize(DefaultDacl->AclSize);
02530 }
02531
02532
if (DynamicLengthUsed > DynamicLength) {
02533 DynamicLength = DynamicLengthUsed;
02534 }
02535
02536
02537
02538
02539
02540 TokenBodyLength =
sizeof(
TOKEN) + VariableLength;
02541 PagedPoolSize = TokenBodyLength + DynamicLength;
02542
02543
02544
Status =
ObCreateObject(
02545 RequestorMode,
02546
SepTokenObjectType,
02547
ObjectAttributes,
02548
UserMode,
02549
NULL,
02550 TokenBodyLength,
02551 PagedPoolSize,
02552 0,
02553 (PVOID *)&
Token
02554 );
02555
02556
if (!
NT_SUCCESS(
Status)) {
02557
SepDeReferenceLogonSession( AuthenticationId );
02558
return Status;
02559 }
02560
02561
02562
02563
02564
02565
02566
02567
02568
02569
02570
02571
02572
ExAllocateLocallyUniqueId( &(
Token->TokenId) );
02573
Token->ParentTokenId = RtlConvertLongToLuid(0);
02574
Token->AuthenticationId = (*AuthenticationId);
02575
Token->TokenInUse =
FALSE;
02576
Token->ModifiedId = NewModifiedId;
02577
Token->ExpirationTime = (*ExpirationTime);
02578
Token->TokenType = TokenType;
02579
Token->ImpersonationLevel = ImpersonationLevel;
02580
Token->TokenSource = (*TokenSource);
02581
02582
Token->TokenFlags = TokenFlags;
02583
Token->SessionId = 0;
02584
02585
Token->DynamicCharged = DynamicLength;
02586
Token->DynamicAvailable = DynamicLength - DynamicLengthUsed;
02587
02588
Token->DefaultOwnerIndex = DefaultOwnerIndex;
02589
Token->DefaultDacl =
NULL;
02590
02591
Token->VariableLength = VariableLength;
02592
02593
02594
Token->ProxyData =
NULL;
02595
Token->AuditData =
NULL;
02596
Token->DynamicPart =
NULL;
02597
02598
if (ARGUMENT_PRESENT( ProxyData )) {
02599
02600
Status =
SepCopyProxyData(
02601 &
Token->ProxyData,
02602 ProxyData
02603 );
02604
02605
if (!
NT_SUCCESS(
Status)) {
02606
ObDereferenceObject(
Token );
02607
return( STATUS_NO_MEMORY );
02608 }
02609
02610 }
else {
02611
02612
Token->ProxyData =
NULL;
02613 }
02614
02615
if (ARGUMENT_PRESENT( AuditData )) {
02616
02617
Token->AuditData =
ExAllocatePool(
PagedPool,
sizeof( SECURITY_TOKEN_AUDIT_DATA ));
02618
02619
if (
Token->AuditData ==
NULL) {
02620
ObDereferenceObject(
Token );
02621
return( STATUS_NO_MEMORY );
02622 }
02623
02624 *(
Token->AuditData) = *AuditData;
02625
02626 }
else {
02627
02628
Token->AuditData =
NULL;
02629 }
02630
02631
02632
02633
02634
02635
02636
02637
02638
02639
02640
02641
02642
02643 Where = (PUCHAR) &
Token->VariablePart ;
02644
02645
Token->Privileges = (PLUID_AND_ATTRIBUTES) Where ;
02646
Token->PrivilegeCount = PrivilegeCount ;
02647
02648 RtlCopyMemory(
02649 Where,
02650 Privileges,
02651 PrivilegeCount *
sizeof(LUID_AND_ATTRIBUTES) );
02652
02653
ASSERT( ComputedPrivLength >= PrivilegeCount *
sizeof( LUID_AND_ATTRIBUTES ) );
02654
02655 Where += ComputedPrivLength ;
02656 VariableLength -= ComputedPrivLength ;
02657
02658
ASSERT( (((ULONG_PTR) Where ) & (
sizeof(PVOID) - 1)) == 0 );
02659
02660
02661
02662
02663
02664 NextSidFree = (PSID) (Where + (
sizeof( SID_AND_ATTRIBUTES ) *
02665 (GroupCount + 1) ) );
02666
02667
Token->UserAndGroups = (PSID_AND_ATTRIBUTES) Where ;
02668
Token->UserAndGroupCount = GroupCount + 1 ;
02669
02670
02671
ASSERT(VariableLength >= ((GroupCount + 1) * (ULONG)
sizeof(SID_AND_ATTRIBUTES)));
02672
02673 VariableLength -= ((GroupCount + 1) * (ULONG)
sizeof(SID_AND_ATTRIBUTES));
02674
Status =
RtlCopySidAndAttributesArray(
02675 1,
02676 User,
02677 VariableLength,
02678 (PSID_AND_ATTRIBUTES)Where,
02679 NextSidFree,
02680 &NextSidFree,
02681 &VariableLength
02682 );
02683
02684 Where +=
sizeof( SID_AND_ATTRIBUTES );
02685
02686
ASSERT( (((ULONG_PTR) Where ) & (
sizeof(PVOID) - 1)) == 0 );
02687
02688
Status =
RtlCopySidAndAttributesArray(
02689 GroupCount,
02690 Groups,
02691 VariableLength,
02692 (PSID_AND_ATTRIBUTES)Where,
02693 NextSidFree,
02694 &NextSidFree,
02695 &VariableLength
02696 );
02697
02698
02699
ASSERT(
NT_SUCCESS(
Status));
02700
02701
02702
Token->RestrictedSids =
NULL;
02703
Token->RestrictedSidCount = 0;
02704
02705
02706
02707
02708
02709
02710
02711
02712
02713
02714
Token->DynamicPart = (PULONG)
ExAllocatePoolWithTag(
PagedPool, DynamicLength, 'dTeS' );
02715
02716
02717
02718
02719
02720
02721
if (
Token->DynamicPart ==
NULL) {
02722
ObDereferenceObject(
Token );
02723
return( STATUS_NO_MEMORY );
02724 }
02725
02726
02727 Where = (PUCHAR)
Token->DynamicPart;
02728
02729
Token->PrimaryGroup = (PSID) Where;
02730 PrimaryGroupLength =
RtlLengthRequiredSid( ((SID *)PrimaryGroup)->SubAuthorityCount );
02731
RtlCopySid( PrimaryGroupLength, (PSID)Where, PrimaryGroup );
02732 Where += (ULONG)LongAlignSize(PrimaryGroupLength);
02733
02734
if (ARGUMENT_PRESENT(DefaultDacl)) {
02735
Token->DefaultDacl = (PACL)Where;
02736
02737 RtlCopyMemory( (PVOID)Where,
02738 (PVOID)DefaultDacl,
02739 DefaultDacl->AclSize
02740 );
02741 }
02742
02743
#ifdef TOKEN_DEBUG
02744
02745
02746
02747 SepDumpToken(
Token );
02748
02749
02751
#endif //TOKEN_DEBUG
02752
02753
02754
02755
02756
02757
02758
if (!SystemToken) {
02759
02760
Status =
SeCreateAccessState(
02761 &AccessState,
02762 &AuxData,
02763 DesiredAccess,
02764 &
SepTokenObjectType->
TypeInfo.
GenericMapping
02765 );
02766
02767
if (
NT_SUCCESS(
Status) ) {
02768 BOOLEAN PrivilegeHeld;
02769
02770 PrivilegeHeld =
SeSinglePrivilegeCheck(
02771
SeCreateTokenPrivilege,
02772 KeGetPreviousMode()
02773 );
02774
02775
if (PrivilegeHeld) {
02776
02777
Status =
ObInsertObject(
Token,
02778 &AccessState,
02779 0,
02780 0,
02781 (PVOID *)
NULL,
02782 TokenHandle
02783 );
02784
02785 }
else {
02786
02787
Status = STATUS_PRIVILEGE_NOT_HELD;
02788
ObDereferenceObject(
Token );
02789 }
02790
02791
SeDeleteAccessState( &AccessState );
02792
02793 }
else {
02794
02795
ObDereferenceObject(
Token );
02796 }
02797 }
else {
02798
02799
ASSERT(
NT_SUCCESS(
Status ) );
02800
ObDeleteCapturedInsertInfo(
Token);
02801
02802
02803
02804
02805 (*TokenHandle) = (HANDLE)
Token;
02806 }
02807
02808
return Status;
02809
02810 }
02811
02812 BOOLEAN
02813 SepIdAssignableAsOwner(
02814 IN PTOKEN Token,
02815 IN ULONG Index
02816 )
02817
02818
02819
02820
02821
02822
02823
02824
02825
02826
02827
02828
02829
02830
02831
02832
02833
02834
02835
02836
02837
02838
02839
02840
02841
02842
02843
02844
02845
02846
02847
02848
02849 {
02850
PAGED_CODE();
02851
02852
if (
Index == 0) {
02853
02854
return TRUE;
02855
02856 }
else {
02857
02858
return (BOOLEAN)
02859 ( (
SepTokenGroupAttributes(
Token,
Index) & SE_GROUP_OWNER)
02860 != 0
02861 );
02862 }
02863 }
02864
02865
02866
NTSTATUS
02867 SeIsChildToken(
02868 IN HANDLE Token,
02869 OUT PBOOLEAN IsChild
02870 )
02871
02872
02873
02874
02875
02876
02877
02878
02879
02880
02881
02882
02883
02884
02885
02886
02887
02888
02889
02890
02891
02892
02893
02894 {
02895
PTOKEN CallerToken;
02896
PTOKEN SuppliedToken;
02897 LUID CallerTokenId;
02898 LUID SuppliedParentTokenId;
02899
NTSTATUS Status = STATUS_SUCCESS;
02900
02901 *
IsChild =
FALSE;
02902
02903
02904
02905
02906
02907 CallerToken = (
PTOKEN)
PsReferencePrimaryToken(
PsGetCurrentProcess());
02908
02909
02910
SepAcquireTokenReadLock( CallerToken );
02911
02912 CallerTokenId = CallerToken->TokenId;
02913
02914
SepReleaseTokenReadLock( CallerToken );
02915
02916
PsDereferencePrimaryToken(CallerToken);
02917
02918
02919
02920
02921
02922
Status =
ObReferenceObjectByHandle(
02923
Token,
02924 0,
02925
SepTokenObjectType,
02926 KeGetPreviousMode(),
02927 (PVOID *)&SuppliedToken,
02928
NULL
02929 );
02930
02931
if (
NT_SUCCESS(
Status))
02932 {
02933
SepAcquireTokenReadLock( SuppliedToken );
02934
02935 SuppliedParentTokenId = SuppliedToken->ParentTokenId;
02936
02937
SepReleaseTokenReadLock( SuppliedToken );
02938
02939
ObDereferenceObject(SuppliedToken);
02940
02941
02942
02943
02944
02945
02946
if (
RtlEqualLuid(
02947 &SuppliedParentTokenId,
02948 &CallerTokenId
02949 )) {
02950
02951 *
IsChild =
TRUE;
02952 }
02953
02954 }
02955
return(
Status);
02956 }
02957
02958
02959
NTSTATUS
02960 SeIsChildTokenByPointer(
02961 IN PACCESS_TOKEN Token,
02962 OUT PBOOLEAN IsChild
02963 )
02964
02965
02966
02967
02968
02969
02970
02971
02972
02973
02974
02975
02976
02977
02978
02979
02980
02981
02982
02983
02984
02985
02986 {
02987
SECURITY_SUBJECT_CONTEXT SubjectSecurityContext;
02988
PTOKEN CallerToken;
02989
PTOKEN SuppliedToken;
02990 LUID CallerTokenId;
02991 LUID SuppliedParentTokenId;
02992
NTSTATUS Status = STATUS_SUCCESS;
02993
02994 *
IsChild =
FALSE;
02995
02996
02997
02998
02999
03000 CallerToken = (
PTOKEN)
PsReferencePrimaryToken(
PsGetCurrentProcess());
03001
03002
03003
SepAcquireTokenReadLock( CallerToken );
03004
03005 CallerTokenId = CallerToken->TokenId;
03006
03007
SepReleaseTokenReadLock( CallerToken );
03008
03009
PsDereferencePrimaryToken(CallerToken);
03010
03011 SuppliedToken = (
PTOKEN)
Token ;
03012
03013
SepAcquireTokenReadLock( SuppliedToken );
03014
03015 SuppliedParentTokenId = SuppliedToken->ParentTokenId;
03016
03017
SepReleaseTokenReadLock( SuppliedToken );
03018
03019
03020
03021
03022
03023
03024
if (
RtlEqualLuid(
03025 &SuppliedParentTokenId,
03026 &CallerTokenId
03027 )) {
03028
03029 *
IsChild =
TRUE;
03030 }
03031
03032
03033
03034
return(
Status);
03035 }
03036
03037
NTSTATUS
03038 NtImpersonateAnonymousToken(
03039 IN HANDLE ThreadHandle
03040 )
03041
03042
03043
03044
03045
03046
03047
03048
03049
03050
03051
03052
03053
03054
03055
03056
03057
03058
03059
03060
03061 {
03062
PETHREAD CallerThread =
NULL;
03063
NTSTATUS Status = STATUS_SUCCESS;
03064
03065
03066
03067
03068
03069
Status =
ObReferenceObjectByHandle(
03070
ThreadHandle,
03071 THREAD_IMPERSONATE,
03072
PsThreadType,
03073 KeGetPreviousMode(),
03074 (PVOID *)&CallerThread,
03075
NULL
03076 );
03077
if (!
NT_SUCCESS(
Status)) {
03078
goto Cleanup;
03079 }
03080
03081
03082
03083
03084
03085
03086
Status =
ObReferenceObjectByPointer(
03087
SeAnonymousLogonToken,
03088 TOKEN_IMPERSONATE,
03089
SepTokenObjectType,
03090 KeGetPreviousMode()
03091 );
03092
if (!
NT_SUCCESS(
Status))
03093 {
03094
goto Cleanup;
03095 }
03096
03097
ObDereferenceObject(
SeAnonymousLogonToken);
03098
03099
03100
03101
03102
03103
03104
Status =
PsImpersonateClient(
03105 CallerThread,
03106
SeAnonymousLogonToken,
03107
TRUE,
03108
FALSE,
03109 SecurityImpersonation
03110 );
03111 Cleanup:
03112
03113
if (CallerThread !=
NULL) {
03114
ObDereferenceObject(CallerThread);
03115 }
03116
return(
Status);
03117 }