Just about every object in Windows can set who and what can access it. The registry is no different. Since PowerShell ties into the .NET Framework, you can change these restrictions with a script. In this post, you're going to learn how to change registry permissions with PowerShell using the
Changing registry permissions with PowerShell �is a four-step process.
- Capture the initial ACL.
- Create a RegistryAccessRule object representing permission
- Adding or overwriting the new rule to the existing ACL
- Committing the ACL back to the registry key
Let's find out how to follow these four steps!
What is a Registry Permission?
I'm calling a registry permission a set of access control entries (ACEs) that make up an access control list (ACL). These ACLs then apply to a registry key.
ACLs are a common term amongst many entities in IT and ACLs assigned to registry keys are no different. The ACL defines what and how an account can access that registry key.
A registry permission (ACL) defines what account can access a particular registry key and what kind of permissions that account has.
Finding Existing Registry Key Permissions
Start out by looking for a registry key you'd like to change permissions on. I'll randomly pick one with the path of HKCU:\AppEvents\EventLabels\ActivatingDocument. You can pick any key you'd like to try this out.
Before you change anything, it's a good idea to see what the current ACL is and to make a backup if things go awry. PowerShell provides a cmdlet called
Get-Acl that will do just that.
PS> $acl = Get-Acl 'HKCU:\AppEvents\EventLabels\ActivatingDocument' PS> $acl.Access RegistryRights : ReadKey AccessControlType : Allow IdentityReference : APPLICATION PACKAGE AUTHORITY\ALL APPLICATION PACKAGES IsInherited : False InheritanceFlags : ContainerInherit PropagationFlags : None --snip--
Now that you have the existing ACL captured, you can now change it. If you're concerned, you could even save the ACL to the file system using the
Export-CliXml cmdlet but that's for another day. You can see an example of using the
Export-CliXml cmdlet to save objects to disk here.
Creating an ACL
Since you're using the registry, this particular ACL we have captured only works with the registry. You'll need to add a rule (ACE) to the ACL that's meant for the registry. There are many different options when creating an ACL.
When defining permissions for the Windows registry with PowerShell, you'll need to create a
System.Security.AccessControl.RegistryAccessRule object. This object allows you to define criteria like the principal (user, group, etc.) that this ACE applies to, level of access and if you're going to allow or deny that access.
You'll need to figure out what kinds of rights to grant to the registry key. Those rights are below. Table found here.
NameBit ValueDescriptionChangePermissions262144The right to change the access rules and audit rules associated with a registry key.CreateSubKey4The right to create subkeys of a registry keyDelete65536The right to delete a registry key.EnumerateSubKeys8The right to list the subkeys of a registry key.FullControl983103The right to exert full control over a registry key, and to modify its access rules and audit rules.Notify16The right to request notification of changes on a registry key.QueryValues1The right to query the name/value pairs in a registry key.ReadKey131097The right to query the name/value pairs in a registry key, to request notification of changes, to enumerate its subkeys, and to read its access rules and audit rules.ReadPermissions131072The right to open and copy the access rules and audit rules for a registry key.SetValue2The right to create, delete, or set name/value pairs in a registry key.TakeOwnership524288The right to change the owner of a registry key.WriteKey131078The right to create, delete, and set the name/value pairs in a registry key, to create or delete subkeys, to request notification of changes, to enumerate its subkeys, and to read its access rules and audit rules.
Creating the RegistryAccessRule Object
Once you have the correct right name, you'll then need to create the RegistryAccessRule object. This object has three arguments you'll need to pass to it:
- An identity (a Windows account)
- The right (has multiple different objects to create this)
- Allow or Deny that right
First, create the identity by creating an System.Security.Principal.NTAccount object passing in the identity reference as shown below.
$idRef = [System.Security.Principal.NTAccount]("HOSTNAME\username")
Next, create a System.Security.AccessControl.RegistryRights object using one of the rights in the table above.
For a list of all available rights, type
[System.Security.AccessControl.RegistryRights]::and start hitting the tab key. It will cycle through all available rights. The same can be done for any objects that you create with
$regRights = [System.Security.AccessControl.RegistryRights]::FullControl
Next, define the inheritance. Here you can choose between:
You can find more information about these options here.
$inhFlags = [System.Security.AccessControl.InheritanceFlags]::None
Next is the propagation flags.
$prFlags = [System.Security.AccessControl.PropagationFlags]::None
Then the access control type enum.
$acType = [System.Security.AccessControl.AccessControlType]::Allow
Finally, you can create the RegistryAccessRule object using all of the objects you've just collected.
$rule = New-Object System.Security.AccessControl.RegistryAccessRule ($idRef, $regRights, $inhFlags, $prFlags, $acType)
Now that you have the RegistryAccessRule created, now you'll need to either overwrite the original ACL you grabbed or add another one.
Adding the ACL
If you'd like to add the ACL to the registry key, you can use the
AddAccessRule() method on the ACL object you grabbed earlier with the
Overwriting an Existing ACL
You could also overwrite the existing ACL on the registry by using
Assigning an ACL to a Registry Key
But you're not done yet! You haven't actually committed the new ACL to the registry key. To apply the new ACL to the registry key, use the
Set-Acl command. To use the
Set-Acl command, pass the saved ACL in
$acl directly to
Set-Acl while pointing to the key you'd like to apply it to.
You want to set the ACL on the same key that you gathered the original ACL from. Pass that key path to the
Path parameter of
Set-Acl to apply it.
$acl | Set-Acl -Path 'HKCU:\AppEvents\EventLabels\ActivatingDocument'
The ACL with the added registry access rule has been applied to the original registry key. You can now verify the change was made by again calling
Get-Acl and ensuring that the
AccessControlType properties are as you expect.
PS> (Get-Acl 'HKCU:\AppEvents\EventLabels\ActivatingDocument').Access RegistryRights : FullControl AccessControlType : Allow IdentityReference : <hostname>\Administrator IsInherited : False InheritanceFlags : None PropagationFlags : None
In this blog post, you learned how to capture, change and commit ACEs to registry key ACLs. You used the
Get-Acl PowerShell cmdlet to find existing ACLs and the
Set-Acl cmdlet to change them. Using these two cmdlets is just about all you need to work with registry permissions in PowerShell.
For more posts on working with the registry, check out How to Get Registry Values With PowerShell.
Join the Jar Tippers on Patreon
It takes a lot of time to write detailed blog posts like this one. In a single-income family, this blog is one way I depend on to keep the lights on. I'd be eternally grateful if you could become a Patreon patron today!Become a Patron!