Изменение прав ACL реестра для всех пользователей - PullRequest
1 голос
/ 29 октября 2011

Несколько лет назад мы столкнулись с проблемами, когда администратор устанавливал наше приложение на компьютере пользователя. Наше приложение создавало записи реестра во время установки, но затем отказывало из-за прав реестра, когда отличается пользователь запустил наше приложение.

Код ниже был написан предшественником. Похоже, исправлена ​​вышеуказанная проблема. Но недавно код ниже сам по себе начал изящно проваливаться, сообщая об ошибке Windows: «Ошибка ключа» при вызове SetSecurityDescriptorDacl.

Это, кажется, происходит на сетевых машинах, которые имеют корпоративную групповую политику. Мы подозреваем, что звонок на SetSecurityDescriptorDacl с nil может быть не разрешен на этих машинах, даже если у пользователя есть права администратора.

Это не та область, в которой мы имеем какой-либо опыт, поэтому я надеюсь, что у кого-нибудь будут какие-то идеи или альтернативный фрагмент кода, который позволит нам обойти эту проблему ...

    class function TQPWindowsRegistry.GiveEveryoneFullAccessToRegistryKey(  const RootKey: HKey;
                                                                            const RegPath : string;
                                                                            out ErrorMsg : string): boolean;
    var
      Access : LongWord;
      WinResult : LongWord;
      SD : PSecurity_Descriptor;
      LastError : DWORD;
      Reg : TRegistry;
    begin
      Result := TRUE;
      ErrorMsg := '';
      if (Win32Platform = VER_PLATFORM_WIN32_NT) then
        begin
          if TOOLS.UserHasAdminToken then
            Access := KEY_ALL_ACCESS
          else
            Access := KEY_READ OR KEY_WRITE;

          Reg := TRegistry.Create(Access);
          try
            Reg.RootKey := RootKey;
            if NOT Reg.OpenKey(RegPath, TRUE) then
              Exit;
            GetMem(SD, SECURITY_DESCRIPTOR_MIN_LENGTH);
            try
              Result := InitializeSecurityDescriptor(SD, SECURITY_DESCRIPTOR_REVISION);
              if Result then
                Result := SetSecurityDescriptorDacl(SD, TRUE, NIL, FALSE); // Fails here!
              if NOT Result then
                begin
                  LastError := WINDOWS.GetLastError;
                  if NOT Result then
                    ErrorMsg := SYSUTILS.SysErrorMessage(LastError);
                end
              else
                begin
                  WinResult := RegSetKeySecurity(Reg.CurrentKey, DACL_SECURITY_INFORMATION, SD);
                  Result := (WinResult = ERROR_SUCCESS);
                  ErrorMsg := SYSUTILS.SysErrorMessage(WinResult);
                end;
            finally
              FreeMem(SD);
            end;
            Reg.CloseKey;
          finally
            FreeAndNIL(Reg);
          end;
        end;
    end; {GiveEveryoneFullAccessToRegistryKey}
...