vendor/golang.org/x/sys/windows/security_windows.go
changeset 265 05c40b36d3b2
equal deleted inserted replaced
264:8f478162d991 265:05c40b36d3b2
       
     1 // Copyright 2012 The Go Authors. All rights reserved.
       
     2 // Use of this source code is governed by a BSD-style
       
     3 // license that can be found in the LICENSE file.
       
     4 
       
     5 package windows
       
     6 
       
     7 import (
       
     8 	"syscall"
       
     9 	"unsafe"
       
    10 
       
    11 	"golang.org/x/sys/internal/unsafeheader"
       
    12 )
       
    13 
       
    14 const (
       
    15 	NameUnknown          = 0
       
    16 	NameFullyQualifiedDN = 1
       
    17 	NameSamCompatible    = 2
       
    18 	NameDisplay          = 3
       
    19 	NameUniqueId         = 6
       
    20 	NameCanonical        = 7
       
    21 	NameUserPrincipal    = 8
       
    22 	NameCanonicalEx      = 9
       
    23 	NameServicePrincipal = 10
       
    24 	NameDnsDomain        = 12
       
    25 )
       
    26 
       
    27 // This function returns 1 byte BOOLEAN rather than the 4 byte BOOL.
       
    28 // http://blogs.msdn.com/b/drnick/archive/2007/12/19/windows-and-upn-format-credentials.aspx
       
    29 //sys	TranslateName(accName *uint16, accNameFormat uint32, desiredNameFormat uint32, translatedName *uint16, nSize *uint32) (err error) [failretval&0xff==0] = secur32.TranslateNameW
       
    30 //sys	GetUserNameEx(nameFormat uint32, nameBuffre *uint16, nSize *uint32) (err error) [failretval&0xff==0] = secur32.GetUserNameExW
       
    31 
       
    32 // TranslateAccountName converts a directory service
       
    33 // object name from one format to another.
       
    34 func TranslateAccountName(username string, from, to uint32, initSize int) (string, error) {
       
    35 	u, e := UTF16PtrFromString(username)
       
    36 	if e != nil {
       
    37 		return "", e
       
    38 	}
       
    39 	n := uint32(50)
       
    40 	for {
       
    41 		b := make([]uint16, n)
       
    42 		e = TranslateName(u, from, to, &b[0], &n)
       
    43 		if e == nil {
       
    44 			return UTF16ToString(b[:n]), nil
       
    45 		}
       
    46 		if e != ERROR_INSUFFICIENT_BUFFER {
       
    47 			return "", e
       
    48 		}
       
    49 		if n <= uint32(len(b)) {
       
    50 			return "", e
       
    51 		}
       
    52 	}
       
    53 }
       
    54 
       
    55 const (
       
    56 	// do not reorder
       
    57 	NetSetupUnknownStatus = iota
       
    58 	NetSetupUnjoined
       
    59 	NetSetupWorkgroupName
       
    60 	NetSetupDomainName
       
    61 )
       
    62 
       
    63 type UserInfo10 struct {
       
    64 	Name       *uint16
       
    65 	Comment    *uint16
       
    66 	UsrComment *uint16
       
    67 	FullName   *uint16
       
    68 }
       
    69 
       
    70 //sys	NetUserGetInfo(serverName *uint16, userName *uint16, level uint32, buf **byte) (neterr error) = netapi32.NetUserGetInfo
       
    71 //sys	NetGetJoinInformation(server *uint16, name **uint16, bufType *uint32) (neterr error) = netapi32.NetGetJoinInformation
       
    72 //sys	NetApiBufferFree(buf *byte) (neterr error) = netapi32.NetApiBufferFree
       
    73 
       
    74 const (
       
    75 	// do not reorder
       
    76 	SidTypeUser = 1 + iota
       
    77 	SidTypeGroup
       
    78 	SidTypeDomain
       
    79 	SidTypeAlias
       
    80 	SidTypeWellKnownGroup
       
    81 	SidTypeDeletedAccount
       
    82 	SidTypeInvalid
       
    83 	SidTypeUnknown
       
    84 	SidTypeComputer
       
    85 	SidTypeLabel
       
    86 )
       
    87 
       
    88 type SidIdentifierAuthority struct {
       
    89 	Value [6]byte
       
    90 }
       
    91 
       
    92 var (
       
    93 	SECURITY_NULL_SID_AUTHORITY        = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 0}}
       
    94 	SECURITY_WORLD_SID_AUTHORITY       = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 1}}
       
    95 	SECURITY_LOCAL_SID_AUTHORITY       = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 2}}
       
    96 	SECURITY_CREATOR_SID_AUTHORITY     = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 3}}
       
    97 	SECURITY_NON_UNIQUE_AUTHORITY      = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 4}}
       
    98 	SECURITY_NT_AUTHORITY              = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 5}}
       
    99 	SECURITY_MANDATORY_LABEL_AUTHORITY = SidIdentifierAuthority{[6]byte{0, 0, 0, 0, 0, 16}}
       
   100 )
       
   101 
       
   102 const (
       
   103 	SECURITY_NULL_RID                   = 0
       
   104 	SECURITY_WORLD_RID                  = 0
       
   105 	SECURITY_LOCAL_RID                  = 0
       
   106 	SECURITY_CREATOR_OWNER_RID          = 0
       
   107 	SECURITY_CREATOR_GROUP_RID          = 1
       
   108 	SECURITY_DIALUP_RID                 = 1
       
   109 	SECURITY_NETWORK_RID                = 2
       
   110 	SECURITY_BATCH_RID                  = 3
       
   111 	SECURITY_INTERACTIVE_RID            = 4
       
   112 	SECURITY_LOGON_IDS_RID              = 5
       
   113 	SECURITY_SERVICE_RID                = 6
       
   114 	SECURITY_LOCAL_SYSTEM_RID           = 18
       
   115 	SECURITY_BUILTIN_DOMAIN_RID         = 32
       
   116 	SECURITY_PRINCIPAL_SELF_RID         = 10
       
   117 	SECURITY_CREATOR_OWNER_SERVER_RID   = 0x2
       
   118 	SECURITY_CREATOR_GROUP_SERVER_RID   = 0x3
       
   119 	SECURITY_LOGON_IDS_RID_COUNT        = 0x3
       
   120 	SECURITY_ANONYMOUS_LOGON_RID        = 0x7
       
   121 	SECURITY_PROXY_RID                  = 0x8
       
   122 	SECURITY_ENTERPRISE_CONTROLLERS_RID = 0x9
       
   123 	SECURITY_SERVER_LOGON_RID           = SECURITY_ENTERPRISE_CONTROLLERS_RID
       
   124 	SECURITY_AUTHENTICATED_USER_RID     = 0xb
       
   125 	SECURITY_RESTRICTED_CODE_RID        = 0xc
       
   126 	SECURITY_NT_NON_UNIQUE_RID          = 0x15
       
   127 )
       
   128 
       
   129 // Predefined domain-relative RIDs for local groups.
       
   130 // See https://msdn.microsoft.com/en-us/library/windows/desktop/aa379649(v=vs.85).aspx
       
   131 const (
       
   132 	DOMAIN_ALIAS_RID_ADMINS                         = 0x220
       
   133 	DOMAIN_ALIAS_RID_USERS                          = 0x221
       
   134 	DOMAIN_ALIAS_RID_GUESTS                         = 0x222
       
   135 	DOMAIN_ALIAS_RID_POWER_USERS                    = 0x223
       
   136 	DOMAIN_ALIAS_RID_ACCOUNT_OPS                    = 0x224
       
   137 	DOMAIN_ALIAS_RID_SYSTEM_OPS                     = 0x225
       
   138 	DOMAIN_ALIAS_RID_PRINT_OPS                      = 0x226
       
   139 	DOMAIN_ALIAS_RID_BACKUP_OPS                     = 0x227
       
   140 	DOMAIN_ALIAS_RID_REPLICATOR                     = 0x228
       
   141 	DOMAIN_ALIAS_RID_RAS_SERVERS                    = 0x229
       
   142 	DOMAIN_ALIAS_RID_PREW2KCOMPACCESS               = 0x22a
       
   143 	DOMAIN_ALIAS_RID_REMOTE_DESKTOP_USERS           = 0x22b
       
   144 	DOMAIN_ALIAS_RID_NETWORK_CONFIGURATION_OPS      = 0x22c
       
   145 	DOMAIN_ALIAS_RID_INCOMING_FOREST_TRUST_BUILDERS = 0x22d
       
   146 	DOMAIN_ALIAS_RID_MONITORING_USERS               = 0x22e
       
   147 	DOMAIN_ALIAS_RID_LOGGING_USERS                  = 0x22f
       
   148 	DOMAIN_ALIAS_RID_AUTHORIZATIONACCESS            = 0x230
       
   149 	DOMAIN_ALIAS_RID_TS_LICENSE_SERVERS             = 0x231
       
   150 	DOMAIN_ALIAS_RID_DCOM_USERS                     = 0x232
       
   151 	DOMAIN_ALIAS_RID_IUSERS                         = 0x238
       
   152 	DOMAIN_ALIAS_RID_CRYPTO_OPERATORS               = 0x239
       
   153 	DOMAIN_ALIAS_RID_CACHEABLE_PRINCIPALS_GROUP     = 0x23b
       
   154 	DOMAIN_ALIAS_RID_NON_CACHEABLE_PRINCIPALS_GROUP = 0x23c
       
   155 	DOMAIN_ALIAS_RID_EVENT_LOG_READERS_GROUP        = 0x23d
       
   156 	DOMAIN_ALIAS_RID_CERTSVC_DCOM_ACCESS_GROUP      = 0x23e
       
   157 )
       
   158 
       
   159 //sys	LookupAccountSid(systemName *uint16, sid *SID, name *uint16, nameLen *uint32, refdDomainName *uint16, refdDomainNameLen *uint32, use *uint32) (err error) = advapi32.LookupAccountSidW
       
   160 //sys	LookupAccountName(systemName *uint16, accountName *uint16, sid *SID, sidLen *uint32, refdDomainName *uint16, refdDomainNameLen *uint32, use *uint32) (err error) = advapi32.LookupAccountNameW
       
   161 //sys	ConvertSidToStringSid(sid *SID, stringSid **uint16) (err error) = advapi32.ConvertSidToStringSidW
       
   162 //sys	ConvertStringSidToSid(stringSid *uint16, sid **SID) (err error) = advapi32.ConvertStringSidToSidW
       
   163 //sys	GetLengthSid(sid *SID) (len uint32) = advapi32.GetLengthSid
       
   164 //sys	CopySid(destSidLen uint32, destSid *SID, srcSid *SID) (err error) = advapi32.CopySid
       
   165 //sys	AllocateAndInitializeSid(identAuth *SidIdentifierAuthority, subAuth byte, subAuth0 uint32, subAuth1 uint32, subAuth2 uint32, subAuth3 uint32, subAuth4 uint32, subAuth5 uint32, subAuth6 uint32, subAuth7 uint32, sid **SID) (err error) = advapi32.AllocateAndInitializeSid
       
   166 //sys	createWellKnownSid(sidType WELL_KNOWN_SID_TYPE, domainSid *SID, sid *SID, sizeSid *uint32) (err error) = advapi32.CreateWellKnownSid
       
   167 //sys	isWellKnownSid(sid *SID, sidType WELL_KNOWN_SID_TYPE) (isWellKnown bool) = advapi32.IsWellKnownSid
       
   168 //sys	FreeSid(sid *SID) (err error) [failretval!=0] = advapi32.FreeSid
       
   169 //sys	EqualSid(sid1 *SID, sid2 *SID) (isEqual bool) = advapi32.EqualSid
       
   170 //sys	getSidIdentifierAuthority(sid *SID) (authority *SidIdentifierAuthority) = advapi32.GetSidIdentifierAuthority
       
   171 //sys	getSidSubAuthorityCount(sid *SID) (count *uint8) = advapi32.GetSidSubAuthorityCount
       
   172 //sys	getSidSubAuthority(sid *SID, index uint32) (subAuthority *uint32) = advapi32.GetSidSubAuthority
       
   173 //sys	isValidSid(sid *SID) (isValid bool) = advapi32.IsValidSid
       
   174 
       
   175 // The security identifier (SID) structure is a variable-length
       
   176 // structure used to uniquely identify users or groups.
       
   177 type SID struct{}
       
   178 
       
   179 // StringToSid converts a string-format security identifier
       
   180 // SID into a valid, functional SID.
       
   181 func StringToSid(s string) (*SID, error) {
       
   182 	var sid *SID
       
   183 	p, e := UTF16PtrFromString(s)
       
   184 	if e != nil {
       
   185 		return nil, e
       
   186 	}
       
   187 	e = ConvertStringSidToSid(p, &sid)
       
   188 	if e != nil {
       
   189 		return nil, e
       
   190 	}
       
   191 	defer LocalFree((Handle)(unsafe.Pointer(sid)))
       
   192 	return sid.Copy()
       
   193 }
       
   194 
       
   195 // LookupSID retrieves a security identifier SID for the account
       
   196 // and the name of the domain on which the account was found.
       
   197 // System specify target computer to search.
       
   198 func LookupSID(system, account string) (sid *SID, domain string, accType uint32, err error) {
       
   199 	if len(account) == 0 {
       
   200 		return nil, "", 0, syscall.EINVAL
       
   201 	}
       
   202 	acc, e := UTF16PtrFromString(account)
       
   203 	if e != nil {
       
   204 		return nil, "", 0, e
       
   205 	}
       
   206 	var sys *uint16
       
   207 	if len(system) > 0 {
       
   208 		sys, e = UTF16PtrFromString(system)
       
   209 		if e != nil {
       
   210 			return nil, "", 0, e
       
   211 		}
       
   212 	}
       
   213 	n := uint32(50)
       
   214 	dn := uint32(50)
       
   215 	for {
       
   216 		b := make([]byte, n)
       
   217 		db := make([]uint16, dn)
       
   218 		sid = (*SID)(unsafe.Pointer(&b[0]))
       
   219 		e = LookupAccountName(sys, acc, sid, &n, &db[0], &dn, &accType)
       
   220 		if e == nil {
       
   221 			return sid, UTF16ToString(db), accType, nil
       
   222 		}
       
   223 		if e != ERROR_INSUFFICIENT_BUFFER {
       
   224 			return nil, "", 0, e
       
   225 		}
       
   226 		if n <= uint32(len(b)) {
       
   227 			return nil, "", 0, e
       
   228 		}
       
   229 	}
       
   230 }
       
   231 
       
   232 // String converts SID to a string format suitable for display, storage, or transmission.
       
   233 func (sid *SID) String() string {
       
   234 	var s *uint16
       
   235 	e := ConvertSidToStringSid(sid, &s)
       
   236 	if e != nil {
       
   237 		return ""
       
   238 	}
       
   239 	defer LocalFree((Handle)(unsafe.Pointer(s)))
       
   240 	return UTF16ToString((*[256]uint16)(unsafe.Pointer(s))[:])
       
   241 }
       
   242 
       
   243 // Len returns the length, in bytes, of a valid security identifier SID.
       
   244 func (sid *SID) Len() int {
       
   245 	return int(GetLengthSid(sid))
       
   246 }
       
   247 
       
   248 // Copy creates a duplicate of security identifier SID.
       
   249 func (sid *SID) Copy() (*SID, error) {
       
   250 	b := make([]byte, sid.Len())
       
   251 	sid2 := (*SID)(unsafe.Pointer(&b[0]))
       
   252 	e := CopySid(uint32(len(b)), sid2, sid)
       
   253 	if e != nil {
       
   254 		return nil, e
       
   255 	}
       
   256 	return sid2, nil
       
   257 }
       
   258 
       
   259 // IdentifierAuthority returns the identifier authority of the SID.
       
   260 func (sid *SID) IdentifierAuthority() SidIdentifierAuthority {
       
   261 	return *getSidIdentifierAuthority(sid)
       
   262 }
       
   263 
       
   264 // SubAuthorityCount returns the number of sub-authorities in the SID.
       
   265 func (sid *SID) SubAuthorityCount() uint8 {
       
   266 	return *getSidSubAuthorityCount(sid)
       
   267 }
       
   268 
       
   269 // SubAuthority returns the sub-authority of the SID as specified by
       
   270 // the index, which must be less than sid.SubAuthorityCount().
       
   271 func (sid *SID) SubAuthority(idx uint32) uint32 {
       
   272 	if idx >= uint32(sid.SubAuthorityCount()) {
       
   273 		panic("sub-authority index out of range")
       
   274 	}
       
   275 	return *getSidSubAuthority(sid, idx)
       
   276 }
       
   277 
       
   278 // IsValid returns whether the SID has a valid revision and length.
       
   279 func (sid *SID) IsValid() bool {
       
   280 	return isValidSid(sid)
       
   281 }
       
   282 
       
   283 // Equals compares two SIDs for equality.
       
   284 func (sid *SID) Equals(sid2 *SID) bool {
       
   285 	return EqualSid(sid, sid2)
       
   286 }
       
   287 
       
   288 // IsWellKnown determines whether the SID matches the well-known sidType.
       
   289 func (sid *SID) IsWellKnown(sidType WELL_KNOWN_SID_TYPE) bool {
       
   290 	return isWellKnownSid(sid, sidType)
       
   291 }
       
   292 
       
   293 // LookupAccount retrieves the name of the account for this SID
       
   294 // and the name of the first domain on which this SID is found.
       
   295 // System specify target computer to search for.
       
   296 func (sid *SID) LookupAccount(system string) (account, domain string, accType uint32, err error) {
       
   297 	var sys *uint16
       
   298 	if len(system) > 0 {
       
   299 		sys, err = UTF16PtrFromString(system)
       
   300 		if err != nil {
       
   301 			return "", "", 0, err
       
   302 		}
       
   303 	}
       
   304 	n := uint32(50)
       
   305 	dn := uint32(50)
       
   306 	for {
       
   307 		b := make([]uint16, n)
       
   308 		db := make([]uint16, dn)
       
   309 		e := LookupAccountSid(sys, sid, &b[0], &n, &db[0], &dn, &accType)
       
   310 		if e == nil {
       
   311 			return UTF16ToString(b), UTF16ToString(db), accType, nil
       
   312 		}
       
   313 		if e != ERROR_INSUFFICIENT_BUFFER {
       
   314 			return "", "", 0, e
       
   315 		}
       
   316 		if n <= uint32(len(b)) {
       
   317 			return "", "", 0, e
       
   318 		}
       
   319 	}
       
   320 }
       
   321 
       
   322 // Various types of pre-specified SIDs that can be synthesized and compared at runtime.
       
   323 type WELL_KNOWN_SID_TYPE uint32
       
   324 
       
   325 const (
       
   326 	WinNullSid                                    = 0
       
   327 	WinWorldSid                                   = 1
       
   328 	WinLocalSid                                   = 2
       
   329 	WinCreatorOwnerSid                            = 3
       
   330 	WinCreatorGroupSid                            = 4
       
   331 	WinCreatorOwnerServerSid                      = 5
       
   332 	WinCreatorGroupServerSid                      = 6
       
   333 	WinNtAuthoritySid                             = 7
       
   334 	WinDialupSid                                  = 8
       
   335 	WinNetworkSid                                 = 9
       
   336 	WinBatchSid                                   = 10
       
   337 	WinInteractiveSid                             = 11
       
   338 	WinServiceSid                                 = 12
       
   339 	WinAnonymousSid                               = 13
       
   340 	WinProxySid                                   = 14
       
   341 	WinEnterpriseControllersSid                   = 15
       
   342 	WinSelfSid                                    = 16
       
   343 	WinAuthenticatedUserSid                       = 17
       
   344 	WinRestrictedCodeSid                          = 18
       
   345 	WinTerminalServerSid                          = 19
       
   346 	WinRemoteLogonIdSid                           = 20
       
   347 	WinLogonIdsSid                                = 21
       
   348 	WinLocalSystemSid                             = 22
       
   349 	WinLocalServiceSid                            = 23
       
   350 	WinNetworkServiceSid                          = 24
       
   351 	WinBuiltinDomainSid                           = 25
       
   352 	WinBuiltinAdministratorsSid                   = 26
       
   353 	WinBuiltinUsersSid                            = 27
       
   354 	WinBuiltinGuestsSid                           = 28
       
   355 	WinBuiltinPowerUsersSid                       = 29
       
   356 	WinBuiltinAccountOperatorsSid                 = 30
       
   357 	WinBuiltinSystemOperatorsSid                  = 31
       
   358 	WinBuiltinPrintOperatorsSid                   = 32
       
   359 	WinBuiltinBackupOperatorsSid                  = 33
       
   360 	WinBuiltinReplicatorSid                       = 34
       
   361 	WinBuiltinPreWindows2000CompatibleAccessSid   = 35
       
   362 	WinBuiltinRemoteDesktopUsersSid               = 36
       
   363 	WinBuiltinNetworkConfigurationOperatorsSid    = 37
       
   364 	WinAccountAdministratorSid                    = 38
       
   365 	WinAccountGuestSid                            = 39
       
   366 	WinAccountKrbtgtSid                           = 40
       
   367 	WinAccountDomainAdminsSid                     = 41
       
   368 	WinAccountDomainUsersSid                      = 42
       
   369 	WinAccountDomainGuestsSid                     = 43
       
   370 	WinAccountComputersSid                        = 44
       
   371 	WinAccountControllersSid                      = 45
       
   372 	WinAccountCertAdminsSid                       = 46
       
   373 	WinAccountSchemaAdminsSid                     = 47
       
   374 	WinAccountEnterpriseAdminsSid                 = 48
       
   375 	WinAccountPolicyAdminsSid                     = 49
       
   376 	WinAccountRasAndIasServersSid                 = 50
       
   377 	WinNTLMAuthenticationSid                      = 51
       
   378 	WinDigestAuthenticationSid                    = 52
       
   379 	WinSChannelAuthenticationSid                  = 53
       
   380 	WinThisOrganizationSid                        = 54
       
   381 	WinOtherOrganizationSid                       = 55
       
   382 	WinBuiltinIncomingForestTrustBuildersSid      = 56
       
   383 	WinBuiltinPerfMonitoringUsersSid              = 57
       
   384 	WinBuiltinPerfLoggingUsersSid                 = 58
       
   385 	WinBuiltinAuthorizationAccessSid              = 59
       
   386 	WinBuiltinTerminalServerLicenseServersSid     = 60
       
   387 	WinBuiltinDCOMUsersSid                        = 61
       
   388 	WinBuiltinIUsersSid                           = 62
       
   389 	WinIUserSid                                   = 63
       
   390 	WinBuiltinCryptoOperatorsSid                  = 64
       
   391 	WinUntrustedLabelSid                          = 65
       
   392 	WinLowLabelSid                                = 66
       
   393 	WinMediumLabelSid                             = 67
       
   394 	WinHighLabelSid                               = 68
       
   395 	WinSystemLabelSid                             = 69
       
   396 	WinWriteRestrictedCodeSid                     = 70
       
   397 	WinCreatorOwnerRightsSid                      = 71
       
   398 	WinCacheablePrincipalsGroupSid                = 72
       
   399 	WinNonCacheablePrincipalsGroupSid             = 73
       
   400 	WinEnterpriseReadonlyControllersSid           = 74
       
   401 	WinAccountReadonlyControllersSid              = 75
       
   402 	WinBuiltinEventLogReadersGroup                = 76
       
   403 	WinNewEnterpriseReadonlyControllersSid        = 77
       
   404 	WinBuiltinCertSvcDComAccessGroup              = 78
       
   405 	WinMediumPlusLabelSid                         = 79
       
   406 	WinLocalLogonSid                              = 80
       
   407 	WinConsoleLogonSid                            = 81
       
   408 	WinThisOrganizationCertificateSid             = 82
       
   409 	WinApplicationPackageAuthoritySid             = 83
       
   410 	WinBuiltinAnyPackageSid                       = 84
       
   411 	WinCapabilityInternetClientSid                = 85
       
   412 	WinCapabilityInternetClientServerSid          = 86
       
   413 	WinCapabilityPrivateNetworkClientServerSid    = 87
       
   414 	WinCapabilityPicturesLibrarySid               = 88
       
   415 	WinCapabilityVideosLibrarySid                 = 89
       
   416 	WinCapabilityMusicLibrarySid                  = 90
       
   417 	WinCapabilityDocumentsLibrarySid              = 91
       
   418 	WinCapabilitySharedUserCertificatesSid        = 92
       
   419 	WinCapabilityEnterpriseAuthenticationSid      = 93
       
   420 	WinCapabilityRemovableStorageSid              = 94
       
   421 	WinBuiltinRDSRemoteAccessServersSid           = 95
       
   422 	WinBuiltinRDSEndpointServersSid               = 96
       
   423 	WinBuiltinRDSManagementServersSid             = 97
       
   424 	WinUserModeDriversSid                         = 98
       
   425 	WinBuiltinHyperVAdminsSid                     = 99
       
   426 	WinAccountCloneableControllersSid             = 100
       
   427 	WinBuiltinAccessControlAssistanceOperatorsSid = 101
       
   428 	WinBuiltinRemoteManagementUsersSid            = 102
       
   429 	WinAuthenticationAuthorityAssertedSid         = 103
       
   430 	WinAuthenticationServiceAssertedSid           = 104
       
   431 	WinLocalAccountSid                            = 105
       
   432 	WinLocalAccountAndAdministratorSid            = 106
       
   433 	WinAccountProtectedUsersSid                   = 107
       
   434 	WinCapabilityAppointmentsSid                  = 108
       
   435 	WinCapabilityContactsSid                      = 109
       
   436 	WinAccountDefaultSystemManagedSid             = 110
       
   437 	WinBuiltinDefaultSystemManagedGroupSid        = 111
       
   438 	WinBuiltinStorageReplicaAdminsSid             = 112
       
   439 	WinAccountKeyAdminsSid                        = 113
       
   440 	WinAccountEnterpriseKeyAdminsSid              = 114
       
   441 	WinAuthenticationKeyTrustSid                  = 115
       
   442 	WinAuthenticationKeyPropertyMFASid            = 116
       
   443 	WinAuthenticationKeyPropertyAttestationSid    = 117
       
   444 	WinAuthenticationFreshKeyAuthSid              = 118
       
   445 	WinBuiltinDeviceOwnersSid                     = 119
       
   446 )
       
   447 
       
   448 // Creates a SID for a well-known predefined alias, generally using the constants of the form
       
   449 // Win*Sid, for the local machine.
       
   450 func CreateWellKnownSid(sidType WELL_KNOWN_SID_TYPE) (*SID, error) {
       
   451 	return CreateWellKnownDomainSid(sidType, nil)
       
   452 }
       
   453 
       
   454 // Creates a SID for a well-known predefined alias, generally using the constants of the form
       
   455 // Win*Sid, for the domain specified by the domainSid parameter.
       
   456 func CreateWellKnownDomainSid(sidType WELL_KNOWN_SID_TYPE, domainSid *SID) (*SID, error) {
       
   457 	n := uint32(50)
       
   458 	for {
       
   459 		b := make([]byte, n)
       
   460 		sid := (*SID)(unsafe.Pointer(&b[0]))
       
   461 		err := createWellKnownSid(sidType, domainSid, sid, &n)
       
   462 		if err == nil {
       
   463 			return sid, nil
       
   464 		}
       
   465 		if err != ERROR_INSUFFICIENT_BUFFER {
       
   466 			return nil, err
       
   467 		}
       
   468 		if n <= uint32(len(b)) {
       
   469 			return nil, err
       
   470 		}
       
   471 	}
       
   472 }
       
   473 
       
   474 const (
       
   475 	// do not reorder
       
   476 	TOKEN_ASSIGN_PRIMARY = 1 << iota
       
   477 	TOKEN_DUPLICATE
       
   478 	TOKEN_IMPERSONATE
       
   479 	TOKEN_QUERY
       
   480 	TOKEN_QUERY_SOURCE
       
   481 	TOKEN_ADJUST_PRIVILEGES
       
   482 	TOKEN_ADJUST_GROUPS
       
   483 	TOKEN_ADJUST_DEFAULT
       
   484 	TOKEN_ADJUST_SESSIONID
       
   485 
       
   486 	TOKEN_ALL_ACCESS = STANDARD_RIGHTS_REQUIRED |
       
   487 		TOKEN_ASSIGN_PRIMARY |
       
   488 		TOKEN_DUPLICATE |
       
   489 		TOKEN_IMPERSONATE |
       
   490 		TOKEN_QUERY |
       
   491 		TOKEN_QUERY_SOURCE |
       
   492 		TOKEN_ADJUST_PRIVILEGES |
       
   493 		TOKEN_ADJUST_GROUPS |
       
   494 		TOKEN_ADJUST_DEFAULT |
       
   495 		TOKEN_ADJUST_SESSIONID
       
   496 	TOKEN_READ  = STANDARD_RIGHTS_READ | TOKEN_QUERY
       
   497 	TOKEN_WRITE = STANDARD_RIGHTS_WRITE |
       
   498 		TOKEN_ADJUST_PRIVILEGES |
       
   499 		TOKEN_ADJUST_GROUPS |
       
   500 		TOKEN_ADJUST_DEFAULT
       
   501 	TOKEN_EXECUTE = STANDARD_RIGHTS_EXECUTE
       
   502 )
       
   503 
       
   504 const (
       
   505 	// do not reorder
       
   506 	TokenUser = 1 + iota
       
   507 	TokenGroups
       
   508 	TokenPrivileges
       
   509 	TokenOwner
       
   510 	TokenPrimaryGroup
       
   511 	TokenDefaultDacl
       
   512 	TokenSource
       
   513 	TokenType
       
   514 	TokenImpersonationLevel
       
   515 	TokenStatistics
       
   516 	TokenRestrictedSids
       
   517 	TokenSessionId
       
   518 	TokenGroupsAndPrivileges
       
   519 	TokenSessionReference
       
   520 	TokenSandBoxInert
       
   521 	TokenAuditPolicy
       
   522 	TokenOrigin
       
   523 	TokenElevationType
       
   524 	TokenLinkedToken
       
   525 	TokenElevation
       
   526 	TokenHasRestrictions
       
   527 	TokenAccessInformation
       
   528 	TokenVirtualizationAllowed
       
   529 	TokenVirtualizationEnabled
       
   530 	TokenIntegrityLevel
       
   531 	TokenUIAccess
       
   532 	TokenMandatoryPolicy
       
   533 	TokenLogonSid
       
   534 	MaxTokenInfoClass
       
   535 )
       
   536 
       
   537 // Group attributes inside of Tokengroups.Groups[i].Attributes
       
   538 const (
       
   539 	SE_GROUP_MANDATORY          = 0x00000001
       
   540 	SE_GROUP_ENABLED_BY_DEFAULT = 0x00000002
       
   541 	SE_GROUP_ENABLED            = 0x00000004
       
   542 	SE_GROUP_OWNER              = 0x00000008
       
   543 	SE_GROUP_USE_FOR_DENY_ONLY  = 0x00000010
       
   544 	SE_GROUP_INTEGRITY          = 0x00000020
       
   545 	SE_GROUP_INTEGRITY_ENABLED  = 0x00000040
       
   546 	SE_GROUP_LOGON_ID           = 0xC0000000
       
   547 	SE_GROUP_RESOURCE           = 0x20000000
       
   548 	SE_GROUP_VALID_ATTRIBUTES   = SE_GROUP_MANDATORY | SE_GROUP_ENABLED_BY_DEFAULT | SE_GROUP_ENABLED | SE_GROUP_OWNER | SE_GROUP_USE_FOR_DENY_ONLY | SE_GROUP_LOGON_ID | SE_GROUP_RESOURCE | SE_GROUP_INTEGRITY | SE_GROUP_INTEGRITY_ENABLED
       
   549 )
       
   550 
       
   551 // Privilege attributes
       
   552 const (
       
   553 	SE_PRIVILEGE_ENABLED_BY_DEFAULT = 0x00000001
       
   554 	SE_PRIVILEGE_ENABLED            = 0x00000002
       
   555 	SE_PRIVILEGE_REMOVED            = 0x00000004
       
   556 	SE_PRIVILEGE_USED_FOR_ACCESS    = 0x80000000
       
   557 	SE_PRIVILEGE_VALID_ATTRIBUTES   = SE_PRIVILEGE_ENABLED_BY_DEFAULT | SE_PRIVILEGE_ENABLED | SE_PRIVILEGE_REMOVED | SE_PRIVILEGE_USED_FOR_ACCESS
       
   558 )
       
   559 
       
   560 // Token types
       
   561 const (
       
   562 	TokenPrimary       = 1
       
   563 	TokenImpersonation = 2
       
   564 )
       
   565 
       
   566 // Impersonation levels
       
   567 const (
       
   568 	SecurityAnonymous      = 0
       
   569 	SecurityIdentification = 1
       
   570 	SecurityImpersonation  = 2
       
   571 	SecurityDelegation     = 3
       
   572 )
       
   573 
       
   574 type LUID struct {
       
   575 	LowPart  uint32
       
   576 	HighPart int32
       
   577 }
       
   578 
       
   579 type LUIDAndAttributes struct {
       
   580 	Luid       LUID
       
   581 	Attributes uint32
       
   582 }
       
   583 
       
   584 type SIDAndAttributes struct {
       
   585 	Sid        *SID
       
   586 	Attributes uint32
       
   587 }
       
   588 
       
   589 type Tokenuser struct {
       
   590 	User SIDAndAttributes
       
   591 }
       
   592 
       
   593 type Tokenprimarygroup struct {
       
   594 	PrimaryGroup *SID
       
   595 }
       
   596 
       
   597 type Tokengroups struct {
       
   598 	GroupCount uint32
       
   599 	Groups     [1]SIDAndAttributes // Use AllGroups() for iterating.
       
   600 }
       
   601 
       
   602 // AllGroups returns a slice that can be used to iterate over the groups in g.
       
   603 func (g *Tokengroups) AllGroups() []SIDAndAttributes {
       
   604 	return (*[(1 << 28) - 1]SIDAndAttributes)(unsafe.Pointer(&g.Groups[0]))[:g.GroupCount:g.GroupCount]
       
   605 }
       
   606 
       
   607 type Tokenprivileges struct {
       
   608 	PrivilegeCount uint32
       
   609 	Privileges     [1]LUIDAndAttributes // Use AllPrivileges() for iterating.
       
   610 }
       
   611 
       
   612 // AllPrivileges returns a slice that can be used to iterate over the privileges in p.
       
   613 func (p *Tokenprivileges) AllPrivileges() []LUIDAndAttributes {
       
   614 	return (*[(1 << 27) - 1]LUIDAndAttributes)(unsafe.Pointer(&p.Privileges[0]))[:p.PrivilegeCount:p.PrivilegeCount]
       
   615 }
       
   616 
       
   617 type Tokenmandatorylabel struct {
       
   618 	Label SIDAndAttributes
       
   619 }
       
   620 
       
   621 func (tml *Tokenmandatorylabel) Size() uint32 {
       
   622 	return uint32(unsafe.Sizeof(Tokenmandatorylabel{})) + GetLengthSid(tml.Label.Sid)
       
   623 }
       
   624 
       
   625 // Authorization Functions
       
   626 //sys	checkTokenMembership(tokenHandle Token, sidToCheck *SID, isMember *int32) (err error) = advapi32.CheckTokenMembership
       
   627 //sys	isTokenRestricted(tokenHandle Token) (ret bool, err error) [!failretval] = advapi32.IsTokenRestricted
       
   628 //sys	OpenProcessToken(process Handle, access uint32, token *Token) (err error) = advapi32.OpenProcessToken
       
   629 //sys	OpenThreadToken(thread Handle, access uint32, openAsSelf bool, token *Token) (err error) = advapi32.OpenThreadToken
       
   630 //sys	ImpersonateSelf(impersonationlevel uint32) (err error) = advapi32.ImpersonateSelf
       
   631 //sys	RevertToSelf() (err error) = advapi32.RevertToSelf
       
   632 //sys	SetThreadToken(thread *Handle, token Token) (err error) = advapi32.SetThreadToken
       
   633 //sys	LookupPrivilegeValue(systemname *uint16, name *uint16, luid *LUID) (err error) = advapi32.LookupPrivilegeValueW
       
   634 //sys	AdjustTokenPrivileges(token Token, disableAllPrivileges bool, newstate *Tokenprivileges, buflen uint32, prevstate *Tokenprivileges, returnlen *uint32) (err error) = advapi32.AdjustTokenPrivileges
       
   635 //sys	AdjustTokenGroups(token Token, resetToDefault bool, newstate *Tokengroups, buflen uint32, prevstate *Tokengroups, returnlen *uint32) (err error) = advapi32.AdjustTokenGroups
       
   636 //sys	GetTokenInformation(token Token, infoClass uint32, info *byte, infoLen uint32, returnedLen *uint32) (err error) = advapi32.GetTokenInformation
       
   637 //sys	SetTokenInformation(token Token, infoClass uint32, info *byte, infoLen uint32) (err error) = advapi32.SetTokenInformation
       
   638 //sys	DuplicateTokenEx(existingToken Token, desiredAccess uint32, tokenAttributes *SecurityAttributes, impersonationLevel uint32, tokenType uint32, newToken *Token) (err error) = advapi32.DuplicateTokenEx
       
   639 //sys	GetUserProfileDirectory(t Token, dir *uint16, dirLen *uint32) (err error) = userenv.GetUserProfileDirectoryW
       
   640 //sys	getSystemDirectory(dir *uint16, dirLen uint32) (len uint32, err error) = kernel32.GetSystemDirectoryW
       
   641 //sys	getWindowsDirectory(dir *uint16, dirLen uint32) (len uint32, err error) = kernel32.GetWindowsDirectoryW
       
   642 //sys	getSystemWindowsDirectory(dir *uint16, dirLen uint32) (len uint32, err error) = kernel32.GetSystemWindowsDirectoryW
       
   643 
       
   644 // An access token contains the security information for a logon session.
       
   645 // The system creates an access token when a user logs on, and every
       
   646 // process executed on behalf of the user has a copy of the token.
       
   647 // The token identifies the user, the user's groups, and the user's
       
   648 // privileges. The system uses the token to control access to securable
       
   649 // objects and to control the ability of the user to perform various
       
   650 // system-related operations on the local computer.
       
   651 type Token Handle
       
   652 
       
   653 // OpenCurrentProcessToken opens an access token associated with current
       
   654 // process with TOKEN_QUERY access. It is a real token that needs to be closed.
       
   655 //
       
   656 // Deprecated: Explicitly call OpenProcessToken(CurrentProcess(), ...)
       
   657 // with the desired access instead, or use GetCurrentProcessToken for a
       
   658 // TOKEN_QUERY token.
       
   659 func OpenCurrentProcessToken() (Token, error) {
       
   660 	var token Token
       
   661 	err := OpenProcessToken(CurrentProcess(), TOKEN_QUERY, &token)
       
   662 	return token, err
       
   663 }
       
   664 
       
   665 // GetCurrentProcessToken returns the access token associated with
       
   666 // the current process. It is a pseudo token that does not need
       
   667 // to be closed.
       
   668 func GetCurrentProcessToken() Token {
       
   669 	return Token(^uintptr(4 - 1))
       
   670 }
       
   671 
       
   672 // GetCurrentThreadToken return the access token associated with
       
   673 // the current thread. It is a pseudo token that does not need
       
   674 // to be closed.
       
   675 func GetCurrentThreadToken() Token {
       
   676 	return Token(^uintptr(5 - 1))
       
   677 }
       
   678 
       
   679 // GetCurrentThreadEffectiveToken returns the effective access token
       
   680 // associated with the current thread. It is a pseudo token that does
       
   681 // not need to be closed.
       
   682 func GetCurrentThreadEffectiveToken() Token {
       
   683 	return Token(^uintptr(6 - 1))
       
   684 }
       
   685 
       
   686 // Close releases access to access token.
       
   687 func (t Token) Close() error {
       
   688 	return CloseHandle(Handle(t))
       
   689 }
       
   690 
       
   691 // getInfo retrieves a specified type of information about an access token.
       
   692 func (t Token) getInfo(class uint32, initSize int) (unsafe.Pointer, error) {
       
   693 	n := uint32(initSize)
       
   694 	for {
       
   695 		b := make([]byte, n)
       
   696 		e := GetTokenInformation(t, class, &b[0], uint32(len(b)), &n)
       
   697 		if e == nil {
       
   698 			return unsafe.Pointer(&b[0]), nil
       
   699 		}
       
   700 		if e != ERROR_INSUFFICIENT_BUFFER {
       
   701 			return nil, e
       
   702 		}
       
   703 		if n <= uint32(len(b)) {
       
   704 			return nil, e
       
   705 		}
       
   706 	}
       
   707 }
       
   708 
       
   709 // GetTokenUser retrieves access token t user account information.
       
   710 func (t Token) GetTokenUser() (*Tokenuser, error) {
       
   711 	i, e := t.getInfo(TokenUser, 50)
       
   712 	if e != nil {
       
   713 		return nil, e
       
   714 	}
       
   715 	return (*Tokenuser)(i), nil
       
   716 }
       
   717 
       
   718 // GetTokenGroups retrieves group accounts associated with access token t.
       
   719 func (t Token) GetTokenGroups() (*Tokengroups, error) {
       
   720 	i, e := t.getInfo(TokenGroups, 50)
       
   721 	if e != nil {
       
   722 		return nil, e
       
   723 	}
       
   724 	return (*Tokengroups)(i), nil
       
   725 }
       
   726 
       
   727 // GetTokenPrimaryGroup retrieves access token t primary group information.
       
   728 // A pointer to a SID structure representing a group that will become
       
   729 // the primary group of any objects created by a process using this access token.
       
   730 func (t Token) GetTokenPrimaryGroup() (*Tokenprimarygroup, error) {
       
   731 	i, e := t.getInfo(TokenPrimaryGroup, 50)
       
   732 	if e != nil {
       
   733 		return nil, e
       
   734 	}
       
   735 	return (*Tokenprimarygroup)(i), nil
       
   736 }
       
   737 
       
   738 // GetUserProfileDirectory retrieves path to the
       
   739 // root directory of the access token t user's profile.
       
   740 func (t Token) GetUserProfileDirectory() (string, error) {
       
   741 	n := uint32(100)
       
   742 	for {
       
   743 		b := make([]uint16, n)
       
   744 		e := GetUserProfileDirectory(t, &b[0], &n)
       
   745 		if e == nil {
       
   746 			return UTF16ToString(b), nil
       
   747 		}
       
   748 		if e != ERROR_INSUFFICIENT_BUFFER {
       
   749 			return "", e
       
   750 		}
       
   751 		if n <= uint32(len(b)) {
       
   752 			return "", e
       
   753 		}
       
   754 	}
       
   755 }
       
   756 
       
   757 // IsElevated returns whether the current token is elevated from a UAC perspective.
       
   758 func (token Token) IsElevated() bool {
       
   759 	var isElevated uint32
       
   760 	var outLen uint32
       
   761 	err := GetTokenInformation(token, TokenElevation, (*byte)(unsafe.Pointer(&isElevated)), uint32(unsafe.Sizeof(isElevated)), &outLen)
       
   762 	if err != nil {
       
   763 		return false
       
   764 	}
       
   765 	return outLen == uint32(unsafe.Sizeof(isElevated)) && isElevated != 0
       
   766 }
       
   767 
       
   768 // GetLinkedToken returns the linked token, which may be an elevated UAC token.
       
   769 func (token Token) GetLinkedToken() (Token, error) {
       
   770 	var linkedToken Token
       
   771 	var outLen uint32
       
   772 	err := GetTokenInformation(token, TokenLinkedToken, (*byte)(unsafe.Pointer(&linkedToken)), uint32(unsafe.Sizeof(linkedToken)), &outLen)
       
   773 	if err != nil {
       
   774 		return Token(0), err
       
   775 	}
       
   776 	return linkedToken, nil
       
   777 }
       
   778 
       
   779 // GetSystemDirectory retrieves the path to current location of the system
       
   780 // directory, which is typically, though not always, `C:\Windows\System32`.
       
   781 func GetSystemDirectory() (string, error) {
       
   782 	n := uint32(MAX_PATH)
       
   783 	for {
       
   784 		b := make([]uint16, n)
       
   785 		l, e := getSystemDirectory(&b[0], n)
       
   786 		if e != nil {
       
   787 			return "", e
       
   788 		}
       
   789 		if l <= n {
       
   790 			return UTF16ToString(b[:l]), nil
       
   791 		}
       
   792 		n = l
       
   793 	}
       
   794 }
       
   795 
       
   796 // GetWindowsDirectory retrieves the path to current location of the Windows
       
   797 // directory, which is typically, though not always, `C:\Windows`. This may
       
   798 // be a private user directory in the case that the application is running
       
   799 // under a terminal server.
       
   800 func GetWindowsDirectory() (string, error) {
       
   801 	n := uint32(MAX_PATH)
       
   802 	for {
       
   803 		b := make([]uint16, n)
       
   804 		l, e := getWindowsDirectory(&b[0], n)
       
   805 		if e != nil {
       
   806 			return "", e
       
   807 		}
       
   808 		if l <= n {
       
   809 			return UTF16ToString(b[:l]), nil
       
   810 		}
       
   811 		n = l
       
   812 	}
       
   813 }
       
   814 
       
   815 // GetSystemWindowsDirectory retrieves the path to current location of the
       
   816 // Windows directory, which is typically, though not always, `C:\Windows`.
       
   817 func GetSystemWindowsDirectory() (string, error) {
       
   818 	n := uint32(MAX_PATH)
       
   819 	for {
       
   820 		b := make([]uint16, n)
       
   821 		l, e := getSystemWindowsDirectory(&b[0], n)
       
   822 		if e != nil {
       
   823 			return "", e
       
   824 		}
       
   825 		if l <= n {
       
   826 			return UTF16ToString(b[:l]), nil
       
   827 		}
       
   828 		n = l
       
   829 	}
       
   830 }
       
   831 
       
   832 // IsMember reports whether the access token t is a member of the provided SID.
       
   833 func (t Token) IsMember(sid *SID) (bool, error) {
       
   834 	var b int32
       
   835 	if e := checkTokenMembership(t, sid, &b); e != nil {
       
   836 		return false, e
       
   837 	}
       
   838 	return b != 0, nil
       
   839 }
       
   840 
       
   841 // IsRestricted reports whether the access token t is a restricted token.
       
   842 func (t Token) IsRestricted() (isRestricted bool, err error) {
       
   843 	isRestricted, err = isTokenRestricted(t)
       
   844 	if !isRestricted && err == syscall.EINVAL {
       
   845 		// If err is EINVAL, this returned ERROR_SUCCESS indicating a non-restricted token.
       
   846 		err = nil
       
   847 	}
       
   848 	return
       
   849 }
       
   850 
       
   851 const (
       
   852 	WTS_CONSOLE_CONNECT        = 0x1
       
   853 	WTS_CONSOLE_DISCONNECT     = 0x2
       
   854 	WTS_REMOTE_CONNECT         = 0x3
       
   855 	WTS_REMOTE_DISCONNECT      = 0x4
       
   856 	WTS_SESSION_LOGON          = 0x5
       
   857 	WTS_SESSION_LOGOFF         = 0x6
       
   858 	WTS_SESSION_LOCK           = 0x7
       
   859 	WTS_SESSION_UNLOCK         = 0x8
       
   860 	WTS_SESSION_REMOTE_CONTROL = 0x9
       
   861 	WTS_SESSION_CREATE         = 0xa
       
   862 	WTS_SESSION_TERMINATE      = 0xb
       
   863 )
       
   864 
       
   865 const (
       
   866 	WTSActive       = 0
       
   867 	WTSConnected    = 1
       
   868 	WTSConnectQuery = 2
       
   869 	WTSShadow       = 3
       
   870 	WTSDisconnected = 4
       
   871 	WTSIdle         = 5
       
   872 	WTSListen       = 6
       
   873 	WTSReset        = 7
       
   874 	WTSDown         = 8
       
   875 	WTSInit         = 9
       
   876 )
       
   877 
       
   878 type WTSSESSION_NOTIFICATION struct {
       
   879 	Size      uint32
       
   880 	SessionID uint32
       
   881 }
       
   882 
       
   883 type WTS_SESSION_INFO struct {
       
   884 	SessionID         uint32
       
   885 	WindowStationName *uint16
       
   886 	State             uint32
       
   887 }
       
   888 
       
   889 //sys WTSQueryUserToken(session uint32, token *Token) (err error) = wtsapi32.WTSQueryUserToken
       
   890 //sys WTSEnumerateSessions(handle Handle, reserved uint32, version uint32, sessions **WTS_SESSION_INFO, count *uint32) (err error) = wtsapi32.WTSEnumerateSessionsW
       
   891 //sys WTSFreeMemory(ptr uintptr) = wtsapi32.WTSFreeMemory
       
   892 //sys WTSGetActiveConsoleSessionId() (sessionID uint32)
       
   893 
       
   894 type ACL struct {
       
   895 	aclRevision byte
       
   896 	sbz1        byte
       
   897 	aclSize     uint16
       
   898 	aceCount    uint16
       
   899 	sbz2        uint16
       
   900 }
       
   901 
       
   902 type SECURITY_DESCRIPTOR struct {
       
   903 	revision byte
       
   904 	sbz1     byte
       
   905 	control  SECURITY_DESCRIPTOR_CONTROL
       
   906 	owner    *SID
       
   907 	group    *SID
       
   908 	sacl     *ACL
       
   909 	dacl     *ACL
       
   910 }
       
   911 
       
   912 type SECURITY_QUALITY_OF_SERVICE struct {
       
   913 	Length              uint32
       
   914 	ImpersonationLevel  uint32
       
   915 	ContextTrackingMode byte
       
   916 	EffectiveOnly       byte
       
   917 }
       
   918 
       
   919 // Constants for the ContextTrackingMode field of SECURITY_QUALITY_OF_SERVICE.
       
   920 const (
       
   921 	SECURITY_STATIC_TRACKING  = 0
       
   922 	SECURITY_DYNAMIC_TRACKING = 1
       
   923 )
       
   924 
       
   925 type SecurityAttributes struct {
       
   926 	Length             uint32
       
   927 	SecurityDescriptor *SECURITY_DESCRIPTOR
       
   928 	InheritHandle      uint32
       
   929 }
       
   930 
       
   931 type SE_OBJECT_TYPE uint32
       
   932 
       
   933 // Constants for type SE_OBJECT_TYPE
       
   934 const (
       
   935 	SE_UNKNOWN_OBJECT_TYPE     = 0
       
   936 	SE_FILE_OBJECT             = 1
       
   937 	SE_SERVICE                 = 2
       
   938 	SE_PRINTER                 = 3
       
   939 	SE_REGISTRY_KEY            = 4
       
   940 	SE_LMSHARE                 = 5
       
   941 	SE_KERNEL_OBJECT           = 6
       
   942 	SE_WINDOW_OBJECT           = 7
       
   943 	SE_DS_OBJECT               = 8
       
   944 	SE_DS_OBJECT_ALL           = 9
       
   945 	SE_PROVIDER_DEFINED_OBJECT = 10
       
   946 	SE_WMIGUID_OBJECT          = 11
       
   947 	SE_REGISTRY_WOW64_32KEY    = 12
       
   948 	SE_REGISTRY_WOW64_64KEY    = 13
       
   949 )
       
   950 
       
   951 type SECURITY_INFORMATION uint32
       
   952 
       
   953 // Constants for type SECURITY_INFORMATION
       
   954 const (
       
   955 	OWNER_SECURITY_INFORMATION            = 0x00000001
       
   956 	GROUP_SECURITY_INFORMATION            = 0x00000002
       
   957 	DACL_SECURITY_INFORMATION             = 0x00000004
       
   958 	SACL_SECURITY_INFORMATION             = 0x00000008
       
   959 	LABEL_SECURITY_INFORMATION            = 0x00000010
       
   960 	ATTRIBUTE_SECURITY_INFORMATION        = 0x00000020
       
   961 	SCOPE_SECURITY_INFORMATION            = 0x00000040
       
   962 	BACKUP_SECURITY_INFORMATION           = 0x00010000
       
   963 	PROTECTED_DACL_SECURITY_INFORMATION   = 0x80000000
       
   964 	PROTECTED_SACL_SECURITY_INFORMATION   = 0x40000000
       
   965 	UNPROTECTED_DACL_SECURITY_INFORMATION = 0x20000000
       
   966 	UNPROTECTED_SACL_SECURITY_INFORMATION = 0x10000000
       
   967 )
       
   968 
       
   969 type SECURITY_DESCRIPTOR_CONTROL uint16
       
   970 
       
   971 // Constants for type SECURITY_DESCRIPTOR_CONTROL
       
   972 const (
       
   973 	SE_OWNER_DEFAULTED       = 0x0001
       
   974 	SE_GROUP_DEFAULTED       = 0x0002
       
   975 	SE_DACL_PRESENT          = 0x0004
       
   976 	SE_DACL_DEFAULTED        = 0x0008
       
   977 	SE_SACL_PRESENT          = 0x0010
       
   978 	SE_SACL_DEFAULTED        = 0x0020
       
   979 	SE_DACL_AUTO_INHERIT_REQ = 0x0100
       
   980 	SE_SACL_AUTO_INHERIT_REQ = 0x0200
       
   981 	SE_DACL_AUTO_INHERITED   = 0x0400
       
   982 	SE_SACL_AUTO_INHERITED   = 0x0800
       
   983 	SE_DACL_PROTECTED        = 0x1000
       
   984 	SE_SACL_PROTECTED        = 0x2000
       
   985 	SE_RM_CONTROL_VALID      = 0x4000
       
   986 	SE_SELF_RELATIVE         = 0x8000
       
   987 )
       
   988 
       
   989 type ACCESS_MASK uint32
       
   990 
       
   991 // Constants for type ACCESS_MASK
       
   992 const (
       
   993 	DELETE                   = 0x00010000
       
   994 	READ_CONTROL             = 0x00020000
       
   995 	WRITE_DAC                = 0x00040000
       
   996 	WRITE_OWNER              = 0x00080000
       
   997 	SYNCHRONIZE              = 0x00100000
       
   998 	STANDARD_RIGHTS_REQUIRED = 0x000F0000
       
   999 	STANDARD_RIGHTS_READ     = READ_CONTROL
       
  1000 	STANDARD_RIGHTS_WRITE    = READ_CONTROL
       
  1001 	STANDARD_RIGHTS_EXECUTE  = READ_CONTROL
       
  1002 	STANDARD_RIGHTS_ALL      = 0x001F0000
       
  1003 	SPECIFIC_RIGHTS_ALL      = 0x0000FFFF
       
  1004 	ACCESS_SYSTEM_SECURITY   = 0x01000000
       
  1005 	MAXIMUM_ALLOWED          = 0x02000000
       
  1006 	GENERIC_READ             = 0x80000000
       
  1007 	GENERIC_WRITE            = 0x40000000
       
  1008 	GENERIC_EXECUTE          = 0x20000000
       
  1009 	GENERIC_ALL              = 0x10000000
       
  1010 )
       
  1011 
       
  1012 type ACCESS_MODE uint32
       
  1013 
       
  1014 // Constants for type ACCESS_MODE
       
  1015 const (
       
  1016 	NOT_USED_ACCESS   = 0
       
  1017 	GRANT_ACCESS      = 1
       
  1018 	SET_ACCESS        = 2
       
  1019 	DENY_ACCESS       = 3
       
  1020 	REVOKE_ACCESS     = 4
       
  1021 	SET_AUDIT_SUCCESS = 5
       
  1022 	SET_AUDIT_FAILURE = 6
       
  1023 )
       
  1024 
       
  1025 // Constants for AceFlags and Inheritance fields
       
  1026 const (
       
  1027 	NO_INHERITANCE                     = 0x0
       
  1028 	SUB_OBJECTS_ONLY_INHERIT           = 0x1
       
  1029 	SUB_CONTAINERS_ONLY_INHERIT        = 0x2
       
  1030 	SUB_CONTAINERS_AND_OBJECTS_INHERIT = 0x3
       
  1031 	INHERIT_NO_PROPAGATE               = 0x4
       
  1032 	INHERIT_ONLY                       = 0x8
       
  1033 	INHERITED_ACCESS_ENTRY             = 0x10
       
  1034 	INHERITED_PARENT                   = 0x10000000
       
  1035 	INHERITED_GRANDPARENT              = 0x20000000
       
  1036 	OBJECT_INHERIT_ACE                 = 0x1
       
  1037 	CONTAINER_INHERIT_ACE              = 0x2
       
  1038 	NO_PROPAGATE_INHERIT_ACE           = 0x4
       
  1039 	INHERIT_ONLY_ACE                   = 0x8
       
  1040 	INHERITED_ACE                      = 0x10
       
  1041 	VALID_INHERIT_FLAGS                = 0x1F
       
  1042 )
       
  1043 
       
  1044 type MULTIPLE_TRUSTEE_OPERATION uint32
       
  1045 
       
  1046 // Constants for MULTIPLE_TRUSTEE_OPERATION
       
  1047 const (
       
  1048 	NO_MULTIPLE_TRUSTEE    = 0
       
  1049 	TRUSTEE_IS_IMPERSONATE = 1
       
  1050 )
       
  1051 
       
  1052 type TRUSTEE_FORM uint32
       
  1053 
       
  1054 // Constants for TRUSTEE_FORM
       
  1055 const (
       
  1056 	TRUSTEE_IS_SID              = 0
       
  1057 	TRUSTEE_IS_NAME             = 1
       
  1058 	TRUSTEE_BAD_FORM            = 2
       
  1059 	TRUSTEE_IS_OBJECTS_AND_SID  = 3
       
  1060 	TRUSTEE_IS_OBJECTS_AND_NAME = 4
       
  1061 )
       
  1062 
       
  1063 type TRUSTEE_TYPE uint32
       
  1064 
       
  1065 // Constants for TRUSTEE_TYPE
       
  1066 const (
       
  1067 	TRUSTEE_IS_UNKNOWN          = 0
       
  1068 	TRUSTEE_IS_USER             = 1
       
  1069 	TRUSTEE_IS_GROUP            = 2
       
  1070 	TRUSTEE_IS_DOMAIN           = 3
       
  1071 	TRUSTEE_IS_ALIAS            = 4
       
  1072 	TRUSTEE_IS_WELL_KNOWN_GROUP = 5
       
  1073 	TRUSTEE_IS_DELETED          = 6
       
  1074 	TRUSTEE_IS_INVALID          = 7
       
  1075 	TRUSTEE_IS_COMPUTER         = 8
       
  1076 )
       
  1077 
       
  1078 // Constants for ObjectsPresent field
       
  1079 const (
       
  1080 	ACE_OBJECT_TYPE_PRESENT           = 0x1
       
  1081 	ACE_INHERITED_OBJECT_TYPE_PRESENT = 0x2
       
  1082 )
       
  1083 
       
  1084 type EXPLICIT_ACCESS struct {
       
  1085 	AccessPermissions ACCESS_MASK
       
  1086 	AccessMode        ACCESS_MODE
       
  1087 	Inheritance       uint32
       
  1088 	Trustee           TRUSTEE
       
  1089 }
       
  1090 
       
  1091 // This type is the union inside of TRUSTEE and must be created using one of the TrusteeValueFrom* functions.
       
  1092 type TrusteeValue uintptr
       
  1093 
       
  1094 func TrusteeValueFromString(str string) TrusteeValue {
       
  1095 	return TrusteeValue(unsafe.Pointer(StringToUTF16Ptr(str)))
       
  1096 }
       
  1097 func TrusteeValueFromSID(sid *SID) TrusteeValue {
       
  1098 	return TrusteeValue(unsafe.Pointer(sid))
       
  1099 }
       
  1100 func TrusteeValueFromObjectsAndSid(objectsAndSid *OBJECTS_AND_SID) TrusteeValue {
       
  1101 	return TrusteeValue(unsafe.Pointer(objectsAndSid))
       
  1102 }
       
  1103 func TrusteeValueFromObjectsAndName(objectsAndName *OBJECTS_AND_NAME) TrusteeValue {
       
  1104 	return TrusteeValue(unsafe.Pointer(objectsAndName))
       
  1105 }
       
  1106 
       
  1107 type TRUSTEE struct {
       
  1108 	MultipleTrustee          *TRUSTEE
       
  1109 	MultipleTrusteeOperation MULTIPLE_TRUSTEE_OPERATION
       
  1110 	TrusteeForm              TRUSTEE_FORM
       
  1111 	TrusteeType              TRUSTEE_TYPE
       
  1112 	TrusteeValue             TrusteeValue
       
  1113 }
       
  1114 
       
  1115 type OBJECTS_AND_SID struct {
       
  1116 	ObjectsPresent          uint32
       
  1117 	ObjectTypeGuid          GUID
       
  1118 	InheritedObjectTypeGuid GUID
       
  1119 	Sid                     *SID
       
  1120 }
       
  1121 
       
  1122 type OBJECTS_AND_NAME struct {
       
  1123 	ObjectsPresent          uint32
       
  1124 	ObjectType              SE_OBJECT_TYPE
       
  1125 	ObjectTypeName          *uint16
       
  1126 	InheritedObjectTypeName *uint16
       
  1127 	Name                    *uint16
       
  1128 }
       
  1129 
       
  1130 //sys	getSecurityInfo(handle Handle, objectType SE_OBJECT_TYPE, securityInformation SECURITY_INFORMATION, owner **SID, group **SID, dacl **ACL, sacl **ACL, sd **SECURITY_DESCRIPTOR) (ret error) = advapi32.GetSecurityInfo
       
  1131 //sys	SetSecurityInfo(handle Handle, objectType SE_OBJECT_TYPE, securityInformation SECURITY_INFORMATION, owner *SID, group *SID, dacl *ACL, sacl *ACL) (ret error) = advapi32.SetSecurityInfo
       
  1132 //sys	getNamedSecurityInfo(objectName string, objectType SE_OBJECT_TYPE, securityInformation SECURITY_INFORMATION, owner **SID, group **SID, dacl **ACL, sacl **ACL, sd **SECURITY_DESCRIPTOR) (ret error) = advapi32.GetNamedSecurityInfoW
       
  1133 //sys	SetNamedSecurityInfo(objectName string, objectType SE_OBJECT_TYPE, securityInformation SECURITY_INFORMATION, owner *SID, group *SID, dacl *ACL, sacl *ACL) (ret error) = advapi32.SetNamedSecurityInfoW
       
  1134 //sys	SetKernelObjectSecurity(handle Handle, securityInformation SECURITY_INFORMATION, securityDescriptor *SECURITY_DESCRIPTOR) (err error) = advapi32.SetKernelObjectSecurity
       
  1135 
       
  1136 //sys	buildSecurityDescriptor(owner *TRUSTEE, group *TRUSTEE, countAccessEntries uint32, accessEntries *EXPLICIT_ACCESS, countAuditEntries uint32, auditEntries *EXPLICIT_ACCESS, oldSecurityDescriptor *SECURITY_DESCRIPTOR, sizeNewSecurityDescriptor *uint32, newSecurityDescriptor **SECURITY_DESCRIPTOR) (ret error) = advapi32.BuildSecurityDescriptorW
       
  1137 //sys	initializeSecurityDescriptor(absoluteSD *SECURITY_DESCRIPTOR, revision uint32) (err error) = advapi32.InitializeSecurityDescriptor
       
  1138 
       
  1139 //sys	getSecurityDescriptorControl(sd *SECURITY_DESCRIPTOR, control *SECURITY_DESCRIPTOR_CONTROL, revision *uint32) (err error) = advapi32.GetSecurityDescriptorControl
       
  1140 //sys	getSecurityDescriptorDacl(sd *SECURITY_DESCRIPTOR, daclPresent *bool, dacl **ACL, daclDefaulted *bool) (err error) = advapi32.GetSecurityDescriptorDacl
       
  1141 //sys	getSecurityDescriptorSacl(sd *SECURITY_DESCRIPTOR, saclPresent *bool, sacl **ACL, saclDefaulted *bool) (err error) = advapi32.GetSecurityDescriptorSacl
       
  1142 //sys	getSecurityDescriptorOwner(sd *SECURITY_DESCRIPTOR, owner **SID, ownerDefaulted *bool) (err error) = advapi32.GetSecurityDescriptorOwner
       
  1143 //sys	getSecurityDescriptorGroup(sd *SECURITY_DESCRIPTOR, group **SID, groupDefaulted *bool) (err error) = advapi32.GetSecurityDescriptorGroup
       
  1144 //sys	getSecurityDescriptorLength(sd *SECURITY_DESCRIPTOR) (len uint32) = advapi32.GetSecurityDescriptorLength
       
  1145 //sys	getSecurityDescriptorRMControl(sd *SECURITY_DESCRIPTOR, rmControl *uint8) (ret error) [failretval!=0] = advapi32.GetSecurityDescriptorRMControl
       
  1146 //sys	isValidSecurityDescriptor(sd *SECURITY_DESCRIPTOR) (isValid bool) = advapi32.IsValidSecurityDescriptor
       
  1147 
       
  1148 //sys	setSecurityDescriptorControl(sd *SECURITY_DESCRIPTOR, controlBitsOfInterest SECURITY_DESCRIPTOR_CONTROL, controlBitsToSet SECURITY_DESCRIPTOR_CONTROL) (err error) = advapi32.SetSecurityDescriptorControl
       
  1149 //sys	setSecurityDescriptorDacl(sd *SECURITY_DESCRIPTOR, daclPresent bool, dacl *ACL, daclDefaulted bool) (err error) = advapi32.SetSecurityDescriptorDacl
       
  1150 //sys	setSecurityDescriptorSacl(sd *SECURITY_DESCRIPTOR, saclPresent bool, sacl *ACL, saclDefaulted bool) (err error) = advapi32.SetSecurityDescriptorSacl
       
  1151 //sys	setSecurityDescriptorOwner(sd *SECURITY_DESCRIPTOR, owner *SID, ownerDefaulted bool) (err error) = advapi32.SetSecurityDescriptorOwner
       
  1152 //sys	setSecurityDescriptorGroup(sd *SECURITY_DESCRIPTOR, group *SID, groupDefaulted bool) (err error) = advapi32.SetSecurityDescriptorGroup
       
  1153 //sys	setSecurityDescriptorRMControl(sd *SECURITY_DESCRIPTOR, rmControl *uint8) = advapi32.SetSecurityDescriptorRMControl
       
  1154 
       
  1155 //sys	convertStringSecurityDescriptorToSecurityDescriptor(str string, revision uint32, sd **SECURITY_DESCRIPTOR, size *uint32) (err error) = advapi32.ConvertStringSecurityDescriptorToSecurityDescriptorW
       
  1156 //sys	convertSecurityDescriptorToStringSecurityDescriptor(sd *SECURITY_DESCRIPTOR, revision uint32, securityInformation SECURITY_INFORMATION, str **uint16, strLen *uint32) (err error) = advapi32.ConvertSecurityDescriptorToStringSecurityDescriptorW
       
  1157 
       
  1158 //sys	makeAbsoluteSD(selfRelativeSD *SECURITY_DESCRIPTOR, absoluteSD *SECURITY_DESCRIPTOR, absoluteSDSize *uint32, dacl *ACL, daclSize *uint32, sacl *ACL, saclSize *uint32, owner *SID, ownerSize *uint32, group *SID, groupSize *uint32) (err error) = advapi32.MakeAbsoluteSD
       
  1159 //sys	makeSelfRelativeSD(absoluteSD *SECURITY_DESCRIPTOR, selfRelativeSD *SECURITY_DESCRIPTOR, selfRelativeSDSize *uint32) (err error) = advapi32.MakeSelfRelativeSD
       
  1160 
       
  1161 //sys	setEntriesInAcl(countExplicitEntries uint32, explicitEntries *EXPLICIT_ACCESS, oldACL *ACL, newACL **ACL) (ret error) = advapi32.SetEntriesInAclW
       
  1162 
       
  1163 // Control returns the security descriptor control bits.
       
  1164 func (sd *SECURITY_DESCRIPTOR) Control() (control SECURITY_DESCRIPTOR_CONTROL, revision uint32, err error) {
       
  1165 	err = getSecurityDescriptorControl(sd, &control, &revision)
       
  1166 	return
       
  1167 }
       
  1168 
       
  1169 // SetControl sets the security descriptor control bits.
       
  1170 func (sd *SECURITY_DESCRIPTOR) SetControl(controlBitsOfInterest SECURITY_DESCRIPTOR_CONTROL, controlBitsToSet SECURITY_DESCRIPTOR_CONTROL) error {
       
  1171 	return setSecurityDescriptorControl(sd, controlBitsOfInterest, controlBitsToSet)
       
  1172 }
       
  1173 
       
  1174 // RMControl returns the security descriptor resource manager control bits.
       
  1175 func (sd *SECURITY_DESCRIPTOR) RMControl() (control uint8, err error) {
       
  1176 	err = getSecurityDescriptorRMControl(sd, &control)
       
  1177 	return
       
  1178 }
       
  1179 
       
  1180 // SetRMControl sets the security descriptor resource manager control bits.
       
  1181 func (sd *SECURITY_DESCRIPTOR) SetRMControl(rmControl uint8) {
       
  1182 	setSecurityDescriptorRMControl(sd, &rmControl)
       
  1183 }
       
  1184 
       
  1185 // DACL returns the security descriptor DACL and whether it was defaulted. The dacl return value may be nil
       
  1186 // if a DACL exists but is an "empty DACL", meaning fully permissive. If the DACL does not exist, err returns
       
  1187 // ERROR_OBJECT_NOT_FOUND.
       
  1188 func (sd *SECURITY_DESCRIPTOR) DACL() (dacl *ACL, defaulted bool, err error) {
       
  1189 	var present bool
       
  1190 	err = getSecurityDescriptorDacl(sd, &present, &dacl, &defaulted)
       
  1191 	if !present {
       
  1192 		err = ERROR_OBJECT_NOT_FOUND
       
  1193 	}
       
  1194 	return
       
  1195 }
       
  1196 
       
  1197 // SetDACL sets the absolute security descriptor DACL.
       
  1198 func (absoluteSD *SECURITY_DESCRIPTOR) SetDACL(dacl *ACL, present, defaulted bool) error {
       
  1199 	return setSecurityDescriptorDacl(absoluteSD, present, dacl, defaulted)
       
  1200 }
       
  1201 
       
  1202 // SACL returns the security descriptor SACL and whether it was defaulted. The sacl return value may be nil
       
  1203 // if a SACL exists but is an "empty SACL", meaning fully permissive. If the SACL does not exist, err returns
       
  1204 // ERROR_OBJECT_NOT_FOUND.
       
  1205 func (sd *SECURITY_DESCRIPTOR) SACL() (sacl *ACL, defaulted bool, err error) {
       
  1206 	var present bool
       
  1207 	err = getSecurityDescriptorSacl(sd, &present, &sacl, &defaulted)
       
  1208 	if !present {
       
  1209 		err = ERROR_OBJECT_NOT_FOUND
       
  1210 	}
       
  1211 	return
       
  1212 }
       
  1213 
       
  1214 // SetSACL sets the absolute security descriptor SACL.
       
  1215 func (absoluteSD *SECURITY_DESCRIPTOR) SetSACL(sacl *ACL, present, defaulted bool) error {
       
  1216 	return setSecurityDescriptorSacl(absoluteSD, present, sacl, defaulted)
       
  1217 }
       
  1218 
       
  1219 // Owner returns the security descriptor owner and whether it was defaulted.
       
  1220 func (sd *SECURITY_DESCRIPTOR) Owner() (owner *SID, defaulted bool, err error) {
       
  1221 	err = getSecurityDescriptorOwner(sd, &owner, &defaulted)
       
  1222 	return
       
  1223 }
       
  1224 
       
  1225 // SetOwner sets the absolute security descriptor owner.
       
  1226 func (absoluteSD *SECURITY_DESCRIPTOR) SetOwner(owner *SID, defaulted bool) error {
       
  1227 	return setSecurityDescriptorOwner(absoluteSD, owner, defaulted)
       
  1228 }
       
  1229 
       
  1230 // Group returns the security descriptor group and whether it was defaulted.
       
  1231 func (sd *SECURITY_DESCRIPTOR) Group() (group *SID, defaulted bool, err error) {
       
  1232 	err = getSecurityDescriptorGroup(sd, &group, &defaulted)
       
  1233 	return
       
  1234 }
       
  1235 
       
  1236 // SetGroup sets the absolute security descriptor owner.
       
  1237 func (absoluteSD *SECURITY_DESCRIPTOR) SetGroup(group *SID, defaulted bool) error {
       
  1238 	return setSecurityDescriptorGroup(absoluteSD, group, defaulted)
       
  1239 }
       
  1240 
       
  1241 // Length returns the length of the security descriptor.
       
  1242 func (sd *SECURITY_DESCRIPTOR) Length() uint32 {
       
  1243 	return getSecurityDescriptorLength(sd)
       
  1244 }
       
  1245 
       
  1246 // IsValid returns whether the security descriptor is valid.
       
  1247 func (sd *SECURITY_DESCRIPTOR) IsValid() bool {
       
  1248 	return isValidSecurityDescriptor(sd)
       
  1249 }
       
  1250 
       
  1251 // String returns the SDDL form of the security descriptor, with a function signature that can be
       
  1252 // used with %v formatting directives.
       
  1253 func (sd *SECURITY_DESCRIPTOR) String() string {
       
  1254 	var sddl *uint16
       
  1255 	err := convertSecurityDescriptorToStringSecurityDescriptor(sd, 1, 0xff, &sddl, nil)
       
  1256 	if err != nil {
       
  1257 		return ""
       
  1258 	}
       
  1259 	defer LocalFree(Handle(unsafe.Pointer(sddl)))
       
  1260 	return UTF16PtrToString(sddl)
       
  1261 }
       
  1262 
       
  1263 // ToAbsolute converts a self-relative security descriptor into an absolute one.
       
  1264 func (selfRelativeSD *SECURITY_DESCRIPTOR) ToAbsolute() (absoluteSD *SECURITY_DESCRIPTOR, err error) {
       
  1265 	control, _, err := selfRelativeSD.Control()
       
  1266 	if err != nil {
       
  1267 		return
       
  1268 	}
       
  1269 	if control&SE_SELF_RELATIVE == 0 {
       
  1270 		err = ERROR_INVALID_PARAMETER
       
  1271 		return
       
  1272 	}
       
  1273 	var absoluteSDSize, daclSize, saclSize, ownerSize, groupSize uint32
       
  1274 	err = makeAbsoluteSD(selfRelativeSD, nil, &absoluteSDSize,
       
  1275 		nil, &daclSize, nil, &saclSize, nil, &ownerSize, nil, &groupSize)
       
  1276 	switch err {
       
  1277 	case ERROR_INSUFFICIENT_BUFFER:
       
  1278 	case nil:
       
  1279 		// makeAbsoluteSD is expected to fail, but it succeeds.
       
  1280 		return nil, ERROR_INTERNAL_ERROR
       
  1281 	default:
       
  1282 		return nil, err
       
  1283 	}
       
  1284 	if absoluteSDSize > 0 {
       
  1285 		absoluteSD = (*SECURITY_DESCRIPTOR)(unsafe.Pointer(&make([]byte, absoluteSDSize)[0]))
       
  1286 	}
       
  1287 	var (
       
  1288 		dacl  *ACL
       
  1289 		sacl  *ACL
       
  1290 		owner *SID
       
  1291 		group *SID
       
  1292 	)
       
  1293 	if daclSize > 0 {
       
  1294 		dacl = (*ACL)(unsafe.Pointer(&make([]byte, daclSize)[0]))
       
  1295 	}
       
  1296 	if saclSize > 0 {
       
  1297 		sacl = (*ACL)(unsafe.Pointer(&make([]byte, saclSize)[0]))
       
  1298 	}
       
  1299 	if ownerSize > 0 {
       
  1300 		owner = (*SID)(unsafe.Pointer(&make([]byte, ownerSize)[0]))
       
  1301 	}
       
  1302 	if groupSize > 0 {
       
  1303 		group = (*SID)(unsafe.Pointer(&make([]byte, groupSize)[0]))
       
  1304 	}
       
  1305 	err = makeAbsoluteSD(selfRelativeSD, absoluteSD, &absoluteSDSize,
       
  1306 		dacl, &daclSize, sacl, &saclSize, owner, &ownerSize, group, &groupSize)
       
  1307 	return
       
  1308 }
       
  1309 
       
  1310 // ToSelfRelative converts an absolute security descriptor into a self-relative one.
       
  1311 func (absoluteSD *SECURITY_DESCRIPTOR) ToSelfRelative() (selfRelativeSD *SECURITY_DESCRIPTOR, err error) {
       
  1312 	control, _, err := absoluteSD.Control()
       
  1313 	if err != nil {
       
  1314 		return
       
  1315 	}
       
  1316 	if control&SE_SELF_RELATIVE != 0 {
       
  1317 		err = ERROR_INVALID_PARAMETER
       
  1318 		return
       
  1319 	}
       
  1320 	var selfRelativeSDSize uint32
       
  1321 	err = makeSelfRelativeSD(absoluteSD, nil, &selfRelativeSDSize)
       
  1322 	switch err {
       
  1323 	case ERROR_INSUFFICIENT_BUFFER:
       
  1324 	case nil:
       
  1325 		// makeSelfRelativeSD is expected to fail, but it succeeds.
       
  1326 		return nil, ERROR_INTERNAL_ERROR
       
  1327 	default:
       
  1328 		return nil, err
       
  1329 	}
       
  1330 	if selfRelativeSDSize > 0 {
       
  1331 		selfRelativeSD = (*SECURITY_DESCRIPTOR)(unsafe.Pointer(&make([]byte, selfRelativeSDSize)[0]))
       
  1332 	}
       
  1333 	err = makeSelfRelativeSD(absoluteSD, selfRelativeSD, &selfRelativeSDSize)
       
  1334 	return
       
  1335 }
       
  1336 
       
  1337 func (selfRelativeSD *SECURITY_DESCRIPTOR) copySelfRelativeSecurityDescriptor() *SECURITY_DESCRIPTOR {
       
  1338 	sdLen := int(selfRelativeSD.Length())
       
  1339 	const min = int(unsafe.Sizeof(SECURITY_DESCRIPTOR{}))
       
  1340 	if sdLen < min {
       
  1341 		sdLen = min
       
  1342 	}
       
  1343 
       
  1344 	var src []byte
       
  1345 	h := (*unsafeheader.Slice)(unsafe.Pointer(&src))
       
  1346 	h.Data = unsafe.Pointer(selfRelativeSD)
       
  1347 	h.Len = sdLen
       
  1348 	h.Cap = sdLen
       
  1349 
       
  1350 	const psize = int(unsafe.Sizeof(uintptr(0)))
       
  1351 
       
  1352 	var dst []byte
       
  1353 	h = (*unsafeheader.Slice)(unsafe.Pointer(&dst))
       
  1354 	alloc := make([]uintptr, (sdLen+psize-1)/psize)
       
  1355 	h.Data = (*unsafeheader.Slice)(unsafe.Pointer(&alloc)).Data
       
  1356 	h.Len = sdLen
       
  1357 	h.Cap = sdLen
       
  1358 
       
  1359 	copy(dst, src)
       
  1360 	return (*SECURITY_DESCRIPTOR)(unsafe.Pointer(&dst[0]))
       
  1361 }
       
  1362 
       
  1363 // SecurityDescriptorFromString converts an SDDL string describing a security descriptor into a
       
  1364 // self-relative security descriptor object allocated on the Go heap.
       
  1365 func SecurityDescriptorFromString(sddl string) (sd *SECURITY_DESCRIPTOR, err error) {
       
  1366 	var winHeapSD *SECURITY_DESCRIPTOR
       
  1367 	err = convertStringSecurityDescriptorToSecurityDescriptor(sddl, 1, &winHeapSD, nil)
       
  1368 	if err != nil {
       
  1369 		return
       
  1370 	}
       
  1371 	defer LocalFree(Handle(unsafe.Pointer(winHeapSD)))
       
  1372 	return winHeapSD.copySelfRelativeSecurityDescriptor(), nil
       
  1373 }
       
  1374 
       
  1375 // GetSecurityInfo queries the security information for a given handle and returns the self-relative security
       
  1376 // descriptor result on the Go heap.
       
  1377 func GetSecurityInfo(handle Handle, objectType SE_OBJECT_TYPE, securityInformation SECURITY_INFORMATION) (sd *SECURITY_DESCRIPTOR, err error) {
       
  1378 	var winHeapSD *SECURITY_DESCRIPTOR
       
  1379 	err = getSecurityInfo(handle, objectType, securityInformation, nil, nil, nil, nil, &winHeapSD)
       
  1380 	if err != nil {
       
  1381 		return
       
  1382 	}
       
  1383 	defer LocalFree(Handle(unsafe.Pointer(winHeapSD)))
       
  1384 	return winHeapSD.copySelfRelativeSecurityDescriptor(), nil
       
  1385 }
       
  1386 
       
  1387 // GetNamedSecurityInfo queries the security information for a given named object and returns the self-relative security
       
  1388 // descriptor result on the Go heap.
       
  1389 func GetNamedSecurityInfo(objectName string, objectType SE_OBJECT_TYPE, securityInformation SECURITY_INFORMATION) (sd *SECURITY_DESCRIPTOR, err error) {
       
  1390 	var winHeapSD *SECURITY_DESCRIPTOR
       
  1391 	err = getNamedSecurityInfo(objectName, objectType, securityInformation, nil, nil, nil, nil, &winHeapSD)
       
  1392 	if err != nil {
       
  1393 		return
       
  1394 	}
       
  1395 	defer LocalFree(Handle(unsafe.Pointer(winHeapSD)))
       
  1396 	return winHeapSD.copySelfRelativeSecurityDescriptor(), nil
       
  1397 }
       
  1398 
       
  1399 // BuildSecurityDescriptor makes a new security descriptor using the input trustees, explicit access lists, and
       
  1400 // prior security descriptor to be merged, any of which can be nil, returning the self-relative security descriptor
       
  1401 // result on the Go heap.
       
  1402 func BuildSecurityDescriptor(owner *TRUSTEE, group *TRUSTEE, accessEntries []EXPLICIT_ACCESS, auditEntries []EXPLICIT_ACCESS, mergedSecurityDescriptor *SECURITY_DESCRIPTOR) (sd *SECURITY_DESCRIPTOR, err error) {
       
  1403 	var winHeapSD *SECURITY_DESCRIPTOR
       
  1404 	var winHeapSDSize uint32
       
  1405 	var firstAccessEntry *EXPLICIT_ACCESS
       
  1406 	if len(accessEntries) > 0 {
       
  1407 		firstAccessEntry = &accessEntries[0]
       
  1408 	}
       
  1409 	var firstAuditEntry *EXPLICIT_ACCESS
       
  1410 	if len(auditEntries) > 0 {
       
  1411 		firstAuditEntry = &auditEntries[0]
       
  1412 	}
       
  1413 	err = buildSecurityDescriptor(owner, group, uint32(len(accessEntries)), firstAccessEntry, uint32(len(auditEntries)), firstAuditEntry, mergedSecurityDescriptor, &winHeapSDSize, &winHeapSD)
       
  1414 	if err != nil {
       
  1415 		return
       
  1416 	}
       
  1417 	defer LocalFree(Handle(unsafe.Pointer(winHeapSD)))
       
  1418 	return winHeapSD.copySelfRelativeSecurityDescriptor(), nil
       
  1419 }
       
  1420 
       
  1421 // NewSecurityDescriptor creates and initializes a new absolute security descriptor.
       
  1422 func NewSecurityDescriptor() (absoluteSD *SECURITY_DESCRIPTOR, err error) {
       
  1423 	absoluteSD = &SECURITY_DESCRIPTOR{}
       
  1424 	err = initializeSecurityDescriptor(absoluteSD, 1)
       
  1425 	return
       
  1426 }
       
  1427 
       
  1428 // ACLFromEntries returns a new ACL on the Go heap containing a list of explicit entries as well as those of another ACL.
       
  1429 // Both explicitEntries and mergedACL are optional and can be nil.
       
  1430 func ACLFromEntries(explicitEntries []EXPLICIT_ACCESS, mergedACL *ACL) (acl *ACL, err error) {
       
  1431 	var firstExplicitEntry *EXPLICIT_ACCESS
       
  1432 	if len(explicitEntries) > 0 {
       
  1433 		firstExplicitEntry = &explicitEntries[0]
       
  1434 	}
       
  1435 	var winHeapACL *ACL
       
  1436 	err = setEntriesInAcl(uint32(len(explicitEntries)), firstExplicitEntry, mergedACL, &winHeapACL)
       
  1437 	if err != nil {
       
  1438 		return
       
  1439 	}
       
  1440 	defer LocalFree(Handle(unsafe.Pointer(winHeapACL)))
       
  1441 	aclBytes := make([]byte, winHeapACL.aclSize)
       
  1442 	copy(aclBytes, (*[(1 << 31) - 1]byte)(unsafe.Pointer(winHeapACL))[:len(aclBytes):len(aclBytes)])
       
  1443 	return (*ACL)(unsafe.Pointer(&aclBytes[0])), nil
       
  1444 }