调用 AddAccessDeniedAce 无效
function AddAccessRights(lpszFileName, UserName : String; dwAccessMask : DWORD) : Boolean;
type
ACE_HEADER = record
AceType : Byte;
AceFlags : Byte;
AceSize : Word;
end;
PACE_HEADER = ^ACE_HEADER;
ACCESS_ALLOWED_ACE = record
Header : ACE_HEADER;
Mask : ACCESS_MASK;
SidStart : DWORD;
end;
ACL_SIZE_INFORMATION = record
AceCount : DWORD;
AclBytesInUse : DWORD;
AclBytesFree : DWORD;
end;
ACCESS_DENIED_ACE = record
Header : ACE_HEADER;
Mask : ACCESS_MASK ;
SidStart : DWORD ;
end;
//PACCESS_DENIED_ACE = ^ACCESS_DENIED_ACE;
// SID variables
var
snuType : SID_NAME_USE;
szDomain : PChar;
cbDomain: DWORD;
pUserSID: Pointer;
cbUserSID: DWORD;
// File SD variables.
pFileSD: PSECURITY_DESCRIPTOR;
cbFileSD: DWORD;
// New SD variables.
pNewSD: PSECURITY_DESCRIPTOR;
// ACL variables.
p_ACL : PACL;
fDaclPresent, fDaclDefaulted : LongBool;
AclInfo: ACL_SIZE_INFORMATION;
PACCESS_DENIED_ACE_A : ACCESS_DENIED_ACE;
// New ACL variables.
pNewACL : PACL;
cbNewACL: DWORD;
// Temporary ACE.
pTempAce: Pointer;
CurrentAceIndex : Cardinal;
const
ACL_REVISION2 = 2;
ACL_REVISION = 2;
begin
szDomain := nil;
cbDomain := 0;
pUserSID := nil;
cbUserSID := 0;
pFileSD := nil;
cbFileSD := 0;
pNewSD := nil;
p_ACL := nil;
pNewACL := nil;
pTempAce := nil;
//
// STEP 1: Get SID for given user.
//
Result := LookupAccountName(nil, PChar(UserName),
pUserSID, cbUserSID, szDomain, cbDomain, snuType);
// API should have failed with insufficient buffer.
if (not Result) and (GetLastError <> ERROR_INSUFFICIENT_BUFFER) then
RaiseLastWin32Error;
pUserSID := AllocMem(cbUserSID);
szDomain := AllocMem(cbDomain);
try
Result := LookupAccountName(nil, PChar(UserName),
pUserSID, cbUserSID, szDomain, cbDomain, snuType);
if (not Result) then RaiseLastWin32Error;
// STEP 2: Get security descriptor (SD) for file.
Result := GetFileSecurity(PChar(lpszFileName),
DACL_SECURITY_INFORMATION, pFileSD, 0, cbFileSD);
if (not Result) and (GetLastError <> ERROR_INSUFFICIENT_BUFFER) then
RaiseLastWin32Error;
pFileSD := AllocMem(cbFileSD);
Result := GetFileSecurity(PChar(lpszFileName),
DACL_SECURITY_INFORMATION, pFileSD, cbFileSD, cbFileSD);
if (not Result) then RaiseLastWin32Error;
// STEP 3: Initialize new SD.
pNewSD := AllocMem(cbFileSD); // Should be same size as FileSD.
if (not InitializeSecurityDescriptor(pNewSD,
SECURITY_DESCRIPTOR_REVISION)) then
RaiseLastWin32Error;
// STEP 4: Get DACL from SD.
if (not GetSecurityDescriptorDacl(pFileSD, fDaclPresent, p_ACL,
fDaclDefaulted)) then
RaiseLastWin32Error;
// STEP 5: Get size information for DACL.
AclInfo.AceCount := 0; // Assume NULL DACL.
AclInfo.AclBytesFree := 0;
AclInfo.AclBytesInUse := SizeOf(ACL);
if (fDaclPresent and Assigned(p_ACL)) then
begin
if (not GetAclInformation(p_ACL^, @AclInfo,
SizeOf(ACL_SIZE_INFORMATION), AclSizeInformation)) then
RaiseLastWin32Error;
// STEP 6: Compute size needed for the new ACL.
cbNewACL := AclInfo.AclBytesInUse + SizeOf(ACCESS_DENIED_ACE)
+ GetLengthSid(pUserSID) - SizeOf(DWORD);
// STEP 7: Allocate memory for new ACL.
pNewACL := AllocMem(cbNewACL);
// STEP 8: Initialize the new ACL.
if (not InitializeAcl(pNewACL^, cbNewACL, ACL_REVISION2)) then
RaiseLastWin32Error;
// STEP 9: If DACL is present, copy it to a new DACL.
if (fDaclPresent) then
begin
// STEP 10: Copy the file's ACEs to the new ACL.
if (AclInfo.AceCount > 0) then
begin
for CurrentAceIndex := 0 to AclInfo.AceCount - 1 do
begin
// STEP 11: Get an ACE.
if (not GetAce(p_ACL^, CurrentAceIndex, pTempAce)) then RaiseLastWin32Error;
// STEP 12: Add the ACE to the new ACL.
if (not AddAce(pNewACL^, ACL_REVISION, MAXDWORD, pTempAce,
PACE_HEADER(pTempAce)^.AceSize)) then RaiseLastWin32Error;
end
end
end; // if (fDaclPresent) then
// STEP 13: Add the access-allowed ACE to the new DACL.
{if (not AddAccessAllowedAceEx(pNewACL^, ACL_REVISION2,3, dwAccessMask,
pUserSID)) then
RaiseLastWin32Error; }
if (not AddAccessDeniedAce(pNewACL^, ACL_REVISION, dwAccessMask,
pUserSID)) then
RaiseLastWin32Error;
// STEP 14: Set the new DACL to the file SD.
if (not SetSecurityDescriptorDacl(pNewSD, True, pNewACL, False)) then
RaiseLastWin32Error;
// STEP 15: Set the SD to the File.
if (not SetFileSecurity(PChar(lpszFileName), DACL_SECURITY_INFORMATION,
pNewSD)) then
RaiseLastWin32Error;
Result := True;
end;
finally
// STEP 16: Free allocated memory
if Assigned(pUserSID) then
FreeMem(pUserSID);
if Assigned(szDomain) then
FreeMem(szDomain);
if Assigned(pFileSD) then
FreeMem(pFileSD);
if Assigned(pNewSD) then
FreeMem(pNewSD);
if Assigned(pNewACL) then
FreeMem(pNewACL);
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
AddAccessRights('D:\Test', 'administrator', GENERIC_READ or GENERIC_WRITE);
end;
[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课