2

I was trying to find a way to set "Apply policy" to "Deny" for a certain group in several GPOs (about 50), so I was looking for a way to do it automatically, when I came across this post at an (aparently) abandoned blog with the following script:

$strGroup = "my group" 
$strGPO = "my GPO"

$GroupObject = Get-ADGroup $strGroup 
$GroupSid = new-object System.Security.Principal.SecurityIdentifier $GroupObject.SID 
$GPOObject = Get-GPO $strGPO

$GPOPath = $GPOObject.path 
$GPOADObject = [ADSI]"LDAP://$GPOPath" 
$GPOObjSec = $GPOADObject.psbase.ObjectSecurity 
$GPOACLList = $GPOObjSec.GetAccessRules($true,$true,[System.Security.Principal.SecurityIdentifier])

$extRight = [system.guid]"edacfd8f-ffb3-11d1-b41d-00a0c968f939" 
$ace1 = new-object System.DirectoryServices.ActiveDirectoryAccessRule $GroupSid,"ReadProperty, GenericExecute","Deny","None" 
$ace2 = new-object System.DirectoryServices.ActiveDirectoryAccessRule $GroupSid,"ExtendedRight","Deny",$extRight,"All" 
$GPOADObject.psbase.get_objectSecurity().AddAccessRule($ace1) 
$GPOADObject.psbase.get_objectSecurity().AddAccessRule($ace2) 
$GPOADObject.psbase.CommitChanges()

$GPOGPTstr = "\\"+$GPOObject.DomainName+"\SYSVOL\"+$GPOObject.DomainName+"\Policies\{"+$GPOObject.Id+"}" 
$acl = Get-ACL $GPOGPTstr

$acl.SetAccessRuleProtection($True, $False) 
$rule = New-Object System.Security.AccessControl.FileSystemAccessRule($strGroup,"ReadAndExecute", "ContainerInherit, ObjectInherit", "None", "Deny") 
$acl.AddAccessRule($rule) 
Set-Acl $GPOGPTstr $acl

I've added it a foreach loop, to get my groups from a text file. It works, except for line 14:

$ace1 = new-object System.DirectoryServices.ActiveDirectoryAccessRule $GroupSid,"ReadProperty, GenericExecute","Deny","None" 

That throws the following error:

new-object : Multiple ambiguous overloads found for "ActiveDirectoryAccessRule" and the argument count: "4".
At .\denyApplyGPOtoGroup.ps1:16 char:10
+     $ace1 = new-object System.DirectoryServices.ActiveDirectoryAccessRule $GroupSid ...
+    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidOperation: (:) [New-Object], MethodException
    + FullyQualifiedErrorId : ConstructorInvokedThrowException,Microsoft.PowerShell.Commands.NewObjectCommand

Of course, line 16 fails, as $ace1 is $null. Nevertheless, the script kind of works: basically, permissions are applied correctly to the GPC, but not to the GPT, which makes sense with the code and the error thrown. So when I went to the GPMC, clicked on the GPO, and I got a message saying:

“The permissions for this GPO in the SYSVOL folder are inconsistent with those in Active Directory. It is recommended that these permissions be consistent. To change the permissions in SYSVOL to those in Active Directory, click OK.”

Clicking OK fixes the mess, but still looking for a solution to this workaround, though… Any ideas?

curropar
  • 631
  • 3
  • 18
  • Since you're working with powershell v4 I'll accept that your AD infrastructure is relatively current. I'd recommend you scrub that script entirely and look at the group policy cmdlets now available in powershell. Load the AD module and then issue the command `Get-Command *GPO*` to see them all. You can set access using these cmdlets. – Colyn1337 Nov 06 '15 at 15:57
  • Hi Colyn, The infrastructure isn't current, actually: I'm working as a external, full-time sysadmin for my client, and while my own PC is W8.1, my client has WS2008 as DCs, and 66% of the clients are still on XP (sigh...). So I'm actually running PS on my own computer against the DCs. – curropar Nov 09 '15 at 09:56
  • Not to mention AD is 2000 native!! Migration to WS2012 is on the roadmap. Still, permissions should not be an issue (fortunately, they're basically the same since W2000); I'll check the new cmdlets, though. Thanks! – curropar Nov 09 '15 at 10:04
  • I guess you meant to check `Set-GPPermissions`; but as per Microsoft documentation, there's no "Deny": -PermissionLevel Specifies the permission level to set for the security principal. The valid permission levels are: GpoRead, GpoApply, GpoEdit, GpoEditDeleteModifySecurity or None. [link](https://technet.microsoft.com/en-us/library/ee461038.aspx) – curropar Nov 09 '15 at 10:29

1 Answers1

2

Remove $ace1 and remove these lines;

$GPOGPTstr = "\\"+$GPOObject.DomainName+"\SYSVOL\"+$GPOObject.DomainName+"\Policies\{"+$GPOObject.Id+"}" 
$acl = Get-ACL $GPOGPTstr

$acl.SetAccessRuleProtection($True, $False) 
$rule = New-Object System.Security.AccessControl.FileSystemAccessRule($strGroup,"ReadAndExecute", "ContainerInherit, ObjectInherit", "None", "Deny") 
$acl.AddAccessRule($rule) 
Set-Acl $GPOGPTstr $acl

All you want is to add the Deny Apply right. So you don't need to change the ACL on the Sysvol policy folder and you also do not want to remove the Read rights.

$ace1 removes the Read policy rights.

Final code is this:

$strGroup = "Domain Admins" 
$strGPO = "RES Workspace Manager Shell"

$GroupObject = Get-ADGroup $strGroup 
$GroupSid = new-object System.Security.Principal.SecurityIdentifier $GroupObject.SID 
$GPOObject = Get-GPO $strGPO

$GPOPath = $GPOObject.path 
$GPOADObject = [ADSI]"LDAP://$GPOPath" 
$GPOObjSec = $GPOADObject.psbase.ObjectSecurity 
$GPOACLList = $GPOObjSec.GetAccessRules($true,$true,[System.Security.Principal.SecurityIdentifier])

$extRight = [system.guid]"edacfd8f-ffb3-11d1-b41d-00a0c968f939" 

$ace = new-object System.DirectoryServices.ActiveDirectoryAccessRule $GroupSid,"ExtendedRight","Deny",$extRight,"All" 

$GPOADObject.psbase.get_objectSecurity().AddAccessRule($ace) 
$GPOADObject.psbase.CommitChanges()
curropar
  • 631
  • 3
  • 18
  • I guess that "final code" have still some lines to be removed, according to your answer ;) I'm trying it right now, and will come back with the result. Thanks! – curropar Jan 11 '16 at 16:53
  • So it works!! Thanks a lot! Obviously, I'd to go ahead manually before your answer (I posted the question 2 months ago), but still I'm saving this for the future. Thanks! FYI, I edited your answer so the code block matches your explanation. – curropar Jan 11 '16 at 17:04