Einzelnen Beitrag anzeigen

Benutzerbild von RWarnecke
RWarnecke

Registriert seit: 31. Dez 2004
Ort: Stuttgart
4.408 Beiträge
 
Delphi XE8 Enterprise
 
#1

WinAPI Problem mit Rechten setzen in der Registry

  Alt 21. Dez 2006, 11:10
Hallo,

ich habe mir diesen Beitrag genommen. Das funktioniert auch sehr gut. Nun möchte ich aber keinen Registry-Key erstellen sondern einen vorhandenen öffnen und dort einen Wert löschen. Mit dem User, womit ich das Programm ausführe, hat nur Lese-Rechte auf den Schlüssel.

Der Code ist folgender :
Delphi-Quellcode:
type
  TAccessMode = (
    NOT_USED_ACCESS,
    GRANT_ACCESS,
    SET_ACCESS,
    DENY_ACCESS,
    REVOKE_ACCESS,
    SET_AUDIT_SUCCESS,
    SET_AUDIT_FAILURE
  );

type
  PObjectsAndSid = ^TObjectsAndSid;
  TObjectsAndSid = record
    ObjectsPresent: DWORD;
    ObjectTypeGuid: TGUID;
    InheritedObjectTypeGuid: TGUID;
    pSid: PSID;
  end;

type

  TSeObjectType = (
    SE_UNKNOWN_OBJECT_TYPE,
    SE_FILE_OBJECT,
    SE_SERVICE,
    SE_PRINTER,
    SE_REGISTRY_KEY,
    SE_LMSHARE,
    SE_KERNEL_OBJECT,
    SE_WINDOW_OBJECT,
    SE_DS_OBJECT,
    SE_DS_OBJECT_ALL,
    SE_PROVIDER_DEFINED_OBJECT,
    SE_WMIGUID_OBJECT
  );
  PObjectsAndNameA = ^TObjectsAndNameA;
  TObjectsAndNameA = record
    ObjectsPresent: DWORD;
    ObjectType: TSeObjectType;
    ObjectTypeName: PAnsiChar;
    InheritedObjectTypeName: PAnsiChar;
    ptstrName: PAnsiChar;
  end;

  PObjectsAndNameW = ^TObjectsAndNameW;
  TObjectsAndNameW = record
    ObjectsPresent: DWORD;
    ObjectType: TSeObjectType;
    ObjectTypeName: PWideChar;
    InheritedObjectTypeName: PWideChar;
    ptstrName: PWideChar;
  end;
  PObjectsAndName = ^TObjectsAndName;
  TObjectsAndName = TObjectsAndNameA;

type
  TMultipleTrusteeOperation = (
    NO_MULTIPLE_TRUSTEE,
    TRUSTEE_IS_IMPERSONATE
  );

  TTrusteeForm = (
    TRUSTEE_IS_SID,
    TRUSTEE_IS_NAME,
    TRUSTEE_BAD_FORM,
    TRUSTEE_IS_OBJECTS_AND_SID,
    TRUSTEE_IS_OBJECTS_AND_NAME
  );

  TTrusteeType = (
    TRUSTEE_IS_UNKNOWN,
    TRUSTEE_IS_USER,
    TRUSTEE_IS_GROUP,
    TRUSTEE_IS_DOMAIN,
    TRUSTEE_IS_ALIAS,
    TRUSTEE_IS_WELL_KNOWN_GROUP,
    TRUSTEE_IS_DELETED,
    TRUSTEE_IS_INVALID,
    TRUSTEE_IS_COMPUTER
  );
  PTrusteeA = ^TTrusteeA;
  TTrusteeA = packed record
    pMultipleTrustee: PTrusteeA;
    MultipleTrusteeOperation: TMultipleTrusteeOperation;
    TrusteeForm: TTrusteeForm;
    TrusteeType: TTrusteeType;
    case TTrusteeForm of
      TRUSTEE_IS_SID: (
        pSid: PSID);
      TRUSTEE_IS_OBJECTS_AND_SID: (
        pObjectsAndSid: PObjectsAndSid);
      TRUSTEE_IS_OBJECTS_AND_NAME: (
        pObjectsAndName: PObjectsAndNameA);
   { else }
      TRUSTEE_IS_NAME, TRUSTEE_BAD_FORM: (
        ptstrName: PAnsiChar);
   { end; }
  end;
  PTrusteeW = ^TTrusteeW;
  TTrusteeW = packed record
    pMultipleTrustee: PTrusteeW;
    MultipleTrusteeOperation: TMultipleTrusteeOperation;
    TrusteeForm: TTrusteeForm;
    TrusteeType: TTrusteeType;
    case TTrusteeForm of
      TRUSTEE_IS_SID: (
        pSid: PSID);
      TRUSTEE_IS_OBJECTS_AND_SID: (
        pObjectsAndSid: PObjectsAndSid);
      TRUSTEE_IS_OBJECTS_AND_NAME: (
        pObjectsAndName: PObjectsAndNameW);
   { else }
      TRUSTEE_IS_NAME, TRUSTEE_BAD_FORM: (
        ptstrName: PWideChar);
   { end; }
  end;
  PTrustee = ^TTrustee;
  TTrustee = TTrusteeA;

type
  PExplicitAccessA = ^TExplicitAccessA;
  TExplicitAccessA = packed record
    grfAccessPermissions: DWORD;
    grfAccessMode: TAccessMode;
    grfInheritance: DWORD;
    Trustee: TTrusteeA;
  end;

  PExplicitAccessW = ^TExplicitAccessW;
  TExplicitAccessW = packed record
    grfAccessPermissions: DWORD;
    grfAccessMode: TAccessMode;
    grfInheritance: DWORD;
    Trustee: TTrusteeW;
  end;
  PExplicitAccess = ^TExplicitAccess;
  TExplicitAccess = TExplicitAccessA;

function SetEntriesInAclA(cCountOfExplicitEntries: ULONG; pListOfExplicitEntries: PExplicitAccessA;
         OldAcl: PACL; var NewAcl: ACL): DWORD; stdcall; {use localfree to release NewAcl}
  external advapi32 name 'SetEntriesInAclA';
function SetEntriesInAclW(cCountOfExplicitEntries: ULONG; pListOfExplicitEntries: PExplicitAccessW;
         OldAcl: PACL; var NewAcl: ACL): DWORD; stdcall; {use localfree to release NewAcl}
  external advapi32 name 'SetEntriesInAclW';
function SetEntriesInAcl(cCountOfExplicitEntries: ULONG; pListOfExplicitEntries: PExplicitAccess;
         OldAcl: PACL; var NewAcl: ACL): DWORD; stdcall; {use localfree to release NewAcl}
  external advapi32 name 'SetEntriesInAclA';
{------------------------------------------------------------------------------}
const
  SECURITY_WORLD_SID_AUTHORITY: TSIDIdentifierAuthority = (
    Value: (0, 0, 0, 0, 0, 1);
  );

  SECURITY_NT_AUTHORITY: TSIDIdentifierAuthority = (
    Value: (0, 0, 0, 0, 0, 5);
  );

  SECURITY_WORLD_RID = $00000000;
  SECURITY_BUILTIN_DOMAIN_RID = $00000020;
  DOMAIN_ALIAS_RID_ADMINS = $00000220;
  DOMAIN_ALIAS_RID_POWER_USERS = $00000223;
  NO_INHERITANCE = $0;

function RegKeyWithFullAccess(Key: HKEY; SubKey: PChar): LongBool; stdcall;
var
  EveryoneSID: PSID;
  AdminSID: PSID;
  PowerUserSID: PSID;
  ExplicitAccesses: array [0..2] of TExplicitAccess;
  Acl: PACL;
  SecurityDescriptor: PSecurityDescriptor;
  SecurityAttributes: TSecurityAttributes;
  Disposition: DWORD;
  KeyHandle: HKEY;
begin
  Result := False;
  EveryoneSID := nil;
  AdminSID := nil;
  PowerUserSID := nil;
  ACL := nil;
  SecurityDescriptor := nil;
  KeyHandle := 0;
  {  Bekannte SID fr die "Jeder"-Gruppe erzeugen. }
  if AllocateAndInitializeSid(SECURITY_WORLD_SID_AUTHORITY, 1,
    SECURITY_WORLD_RID, 0, 0, 0, 0, 0, 0, 0, EveryoneSID) then
  begin
    { Der ACE wird "Jeder" Vollzugriff erlauben. }
    FillChar(ExplicitAccesses, 2 * SizeOf(TExplicitAccess), 0);
    ExplicitAccesses[0].grfAccessPermissions := KEY_ALL_ACCESS;
    ExplicitAccesses[0].grfAccessMode := SET_ACCESS;
    ExplicitAccesses[0].grfInheritance := NO_INHERITANCE;
    ExplicitAccesses[0].Trustee.TrusteeForm := TRUSTEE_IS_SID;
    ExplicitAccesses[0].Trustee.TrusteeType := TRUSTEE_IS_WELL_KNOWN_GROUP;
    ExplicitAccesses[0].Trustee.pSid := EveryoneSID;
  end;
  {  Bekannte SID für die "Administratoren"-Gruppe erzeugen. }
  if AllocateAndInitializeSid(SECURITY_NT_AUTHORITY, 2,
    SECURITY_BUILTIN_DOMAIN_RID, DOMAIN_ALIAS_RID_ADMINS, 0, 0, 0, 0, 0, 0,
    AdminSID) then
  begin
    { Der ACE wird "Administratoren" Vollzugriff erlauben. }
    ExplicitAccesses[1].grfAccessPermissions := KEY_ALL_ACCESS;
    ExplicitAccesses[1].grfAccessMode := SET_ACCESS;
    ExplicitAccesses[1].grfInheritance := NO_INHERITANCE;
    ExplicitAccesses[1].Trustee.TrusteeForm := TRUSTEE_IS_SID;
    ExplicitAccesses[1].Trustee.TrusteeType := TRUSTEE_IS_GROUP;
    ExplicitAccesses[1].Trustee.pSid := AdminSID;
  end;
  {  Bekannte SID für die "Hauptbenutzer"-Gruppe erzeugen. }
  if AllocateAndInitializeSid(SECURITY_NT_AUTHORITY, 2,
    SECURITY_BUILTIN_DOMAIN_RID, DOMAIN_ALIAS_RID_POWER_USERS, 0, 0, 0, 0, 0, 0,
    PowerUserSID) then
  begin
    { Der ACE wird "Hauptbenutzern" Vollzugriff erlauben. }
    ExplicitAccesses[2].grfAccessPermissions := KEY_ALL_ACCESS;
    ExplicitAccesses[2].grfAccessMode := SET_ACCESS;
    ExplicitAccesses[2].grfInheritance := NO_INHERITANCE;
    ExplicitAccesses[2].Trustee.TrusteeForm := TRUSTEE_IS_SID;
    ExplicitAccesses[2].Trustee.TrusteeType := TRUSTEE_IS_GROUP;
    ExplicitAccesses[2].Trustee.pSid := PowerUserSID;
  end;
  try
    { Neue ACL erzeugen, die den neuen ACE enthlt. }
    if SetEntriesInAcl(3, @ExplicitAccesses, nil, PACL(@Acl)^) = ERROR_SUCCESS then
    begin
      { Security Descriptor initialisieren. }
      SecurityDescriptor := PSecurityDescriptor(LocalAlloc(LPTR, SECURITY_DESCRIPTOR_MIN_LENGTH));
      if Assigned(SecurityDescriptor) then
        if InitializeSecurityDescriptor(SecurityDescriptor, SECURITY_DESCRIPTOR_REVISION) then
          { Die ACL zum Security Descriptor hinzufgen. }
          if SetSecurityDescriptorDacl(SecurityDescriptor, True, ACL, False) then
          begin
            { Eine Sicherheits-Attribute-Struktur initialisieren. }
            SecurityAttributes.nLength := SizeOf(TSecurityAttributes);
            SecurityAttributes.lpSecurityDescriptor := SecurityDescriptor;
            SecurityAttributes.bInheritHandle := False;
            { Die Sicherheits-Attribute benutzen um den Schlssel anzulegen. }
// RegCreateKeyEx(Key, SubKey, 0, '', 0, KEY_READ or KEY_WRITE or WRITE_DAC, @SecurityAttributes, KeyHandle, @Disposition);
            RegOpenKeyEx(Key, SubKey, 0, KEY_READ or KEY_WRITE or WRITE_DAC, KeyHandle);
            if RegSetKeySecurity(KeyHandle, DACL_SECURITY_INFORMATION, SecurityDescriptor) = ERROR_SUCCESS then
              if RegSetValue(key, SubKey, REG_SZ, 'Test', 0 ) = ERROR_SUCCESS then
              begin
                RegDeleteValue(Key, 'Test');
                RegCloseKey(Key);
              end;
            if KeyHandle <> 0 then
              Result := RegSetKeySecurity(KeyHandle, DACL_SECURITY_INFORMATION, SecurityDescriptor) = ERROR_SUCCESS;
          end;
    end;
  finally
    if Assigned(EveryoneSID) then
      FreeSid(EveryoneSID);
    if Assigned(AdminSID) then
      FreeSid(AdminSID);
    if Assigned(PowerUserSID) then
      FreeSid(PowerUserSID);
    if Assigned(Acl) then
      LocalFree(HLOCAL(Acl));
    if Assigned(SecurityDescriptor) then
      LocalFree(HLOCAL(SecurityDescriptor));
    if KeyHandle <> 0 then
      RegCloseKey(KeyHandle);
  end;
end;
Was ist jetzt falsch an dem Code ? Ich möchte ja lediglich nur einen Registrykey öffnen um dort einen Schlüssel oder Key zu erstellen oder zu ändern mit ganz normalen Hauptbenutzerrechten. Es kann auch sein, dass ich das ganze bis jetzt falsch verstanden habe. Wenn dieses der Fall ist, da bitte ich um eine Erklärung.
Rolf Warnecke
App4Mission
  Mit Zitat antworten Zitat