(******************************************************************************) 
(* SPGetSid - Retrieve the current user's SID in text format                  *) 
(*                                                                            *) 
(* Copyright (c) 2004 Shorter Path Software                                   *) 
(* http://www.shorterpath.com                                                 *) 
(******************************************************************************) 
 
 
{ 
  SID is a data structure of variable length that identifies user, group, 
  and computer accounts. 
  Every account on a network is issued a unique SID when the account is first created. 
  Internal processes in Windows refer to an account's SID 
  rather than the account's user or group name. 
} 
 
 
unit SPGetSid; 
 
interface 
 
uses 
  Windows, SysUtils; 
 
function GetCurrentUserSid: string; 
 
implementation 
 
const 
  HEAP_ZERO_MEMORY = $00000008; 
  SID_REVISION     = 1; // Current revision level 
 
type 
  PTokenUser = ^TTokenUser; 
  TTokenUser = packed record 
    User: TSidAndAttributes; 
  end; 
 
function ConvertSid(Sid: PSID; pszSidText: PChar; var dwBufferLen: DWORD): BOOL; 
var 
  psia: PSIDIdentifierAuthority; 
  dwSubAuthorities: DWORD; 
  dwSidRev: DWORD; 
  dwCounter: DWORD; 
  dwSidSize: DWORD; 
begin 
  Result := False; 
 
  dwSidRev := SID_REVISION; 
 
  if not IsValidSid(Sid) then Exit; 
 
  psia := GetSidIdentifierAuthority(Sid); 
 
  dwSubAuthorities := GetSidSubAuthorityCount(Sid)^; 
 
  dwSidSize := (15 + 12 + (12 * dwSubAuthorities) + 1) * SizeOf(Char); 
 
  if (dwBufferLen < dwSidSize) then 
  begin 
    dwBufferLen := dwSidSize; 
    SetLastError(ERROR_INSUFFICIENT_BUFFER); 
    Exit; 
  end; 
 
  StrFmt(pszSidText, 'S-%u-', [dwSidRev]); 
 
  if (psia.Value[0] <> 0) or (psia.Value[1] <> 0) then 
    StrFmt(pszSidText + StrLen(pszSidText), 
      '0x%.2x%.2x%.2x%.2x%.2x%.2x', 
      [psia.Value[0], psia.Value[1], psia.Value[2], 
      psia.Value[3], psia.Value[4], psia.Value[5]]) 
  else 
    StrFmt(pszSidText + StrLen(pszSidText), 
      '%u', 
      [DWORD(psia.Value[5]) + 
      DWORD(psia.Value[4] shl 8) + 
      DWORD(psia.Value[3] shl 16) + 
      DWORD(psia.Value[2] shl 24)]); 
 
  dwSidSize := StrLen(pszSidText); 
 
  for dwCounter := 0 to dwSubAuthorities - 1 do 
  begin 
    StrFmt(pszSidText + dwSidSize, '-%u', 
      [GetSidSubAuthority(Sid, dwCounter)^]); 
    dwSidSize := StrLen(pszSidText); 
  end; 
 
  Result := True; 
end; 
 
function ObtainTextSid(hToken: THandle; pszSid: PChar; 
  var dwBufferLen: DWORD): BOOL; 
var 
  dwReturnLength: DWORD; 
  dwTokenUserLength: DWORD; 
  tic: TTokenInformationClass; 
  ptu: Pointer; 
begin 
  Result := False; 
  dwReturnLength := 0; 
  dwTokenUserLength := 0; 
  tic := TokenUser; 
  ptu := nil; 
 
  if not GetTokenInformation(hToken, tic, ptu, dwTokenUserLength, 
    dwReturnLength) then 
  begin 
    if GetLastError = ERROR_INSUFFICIENT_BUFFER then 
    begin 
      ptu := HeapAlloc(GetProcessHeap, HEAP_ZERO_MEMORY, dwReturnLength); 
      if ptu = nil then Exit; 
      dwTokenUserLength := dwReturnLength; 
      dwReturnLength    := 0; 
 
      if not GetTokenInformation(hToken, tic, ptu, dwTokenUserLength, 
        dwReturnLength) then Exit; 
    end  
    else  
      Exit; 
  end; 
 
  if not ConvertSid((PTokenUser(ptu).User).Sid, pszSid, dwBufferLen) then Exit; 
 
  if not HeapFree(GetProcessHeap, 0, ptu) then Exit; 
 
  Result := True; 
end; 
 
function GetCurrentUserSid: string; 
var 
  hAccessToken: THandle; 
  bSuccess: BOOL; 
  dwBufferLen: DWORD; 
  szSid: array[0..260] of Char; 
begin 
  Result := ''; 
 
  bSuccess := OpenThreadToken(GetCurrentThread, TOKEN_QUERY, True, 
    hAccessToken); 
  if not bSuccess then 
  begin 
    if GetLastError = ERROR_NO_TOKEN then 
      bSuccess := OpenProcessToken(GetCurrentProcess, TOKEN_QUERY, 
        hAccessToken); 
  end; 
  if bSuccess then 
  begin 
    ZeroMemory(@szSid, SizeOf(szSid)); 
    dwBufferLen := SizeOf(szSid); 
 
    if ObtainTextSid(hAccessToken, szSid, dwBufferLen) then 
      Result := szSid; 
    CloseHandle(hAccessToken); 
  end; 
end; 
 
end. 
 
 
  
   
     
      
         
          | 
		     Bewerten Sie diesen Tipp: 
		  
		   | 
         
       
     | 
   
 
                      
                       |