几年前,我们遇到了管理员在用户机器上安装我们的应用程序的问题我们的应用程序会在安装时创建注册表项,但是当不同时会因注册表注册表权限而失败用户运行我们的应用程序。
以下代码由前任编写。它似乎解决了上述问题。但最近,下面的代码开始优雅地失败,报告了一个Windows错误:SetSecurityDescriptorDacl
调用上的“Failed Key”。
这似乎发生在具有公司组策略的联网计算机上。我们怀疑使用nil调用SetSecurityDescriptorDacl
可能在这些计算机上不合法,即使用户具有管理员权限。
这不是我们有任何专业知识的领域,所以我希望有人会有一些想法或替代代码片段让我们绕过这个问题......
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}