Get-RegistryKey.ps1
<#PSScriptInfo
.VERSION 1.0.2 .GUID 3db94b5b-3f5c-46b5-b382-0e1ed1eb18e1 .AUTHOR /u/Pyprohly .TAGS Registry .RELEASENOTES 1.0.2 | 2018-11-12 Add more registry hives 1.0 | 2018-11-12 Initial release .DESCRIPTION Returns a read and writable Microsoft.Win32.RegistryKey object. The RegistryKey object that is returned by Get-Item isn’t open for writing. This cmdlet returns a RegistryKey object that is writable. No object is returned if the specified key could not be found or opened. #> param( [Parameter(ValueFromPipeline,ValueFromPipelineByPropertyName)] [Alias('PSPath', 'KeyName')] [string] $Path, [Microsoft.Win32.RegistryKeyPermissionCheck] $PermissionCheck = [Microsoft.Win32.RegistryKeyPermissionCheck]::ReadWriteSubTree, [System.Security.AccessControl.RegistryRights] [Alias('Rights')] $RegistryRights = [System.Security.AccessControl.RegistryRights]'ReadKey,WriteKey' ) function Get-RegistryKey { [CmdletBinding()] [OutputType('Microsoft.Win32.RegistryKey')] param( [Parameter(Mandatory,ValueFromPipeline,ValueFromPipelineByPropertyName)] [Alias('PSPath', 'KeyName')] [string] $Path, [Microsoft.Win32.RegistryKeyPermissionCheck] $PermissionCheck = [Microsoft.Win32.RegistryKeyPermissionCheck]::ReadWriteSubTree, [System.Security.AccessControl.RegistryRights] [Alias('Rights')] $RegistryRights = [System.Security.AccessControl.RegistryRights]'ReadKey,WriteKey' ) begin { $hives = @{ hkcr = [Microsoft.Win32.Registry]::ClassesRoot hkcu = [Microsoft.Win32.Registry]::CurrentUser hklm = [Microsoft.Win32.Registry]::LocalMachine hku = [Microsoft.Win32.Registry]::Users hkcc = [Microsoft.Win32.Registry]::CurrentConfig hkdd = [Microsoft.Win32.Registry]::DynData } $provider = Get-PSProvider -PSProvider Registry $providerString = $provider.ToString() foreach ($hive in $hives.GetEnumerator()) { $null = New-PSDrive -Name $hive.Name.ToUpper() -PSProvider Registry -Root $hive.Value.Name -ErrorAction SilentlyContinue } } process { foreach ($key in $Path) { if ($key.StartsWith($providerString)) { $key = $key.Substring($providerString.Length).TrimStart(':') } elseif ($key.StartsWith($provider.Name)) { $key = $key.Substring($provider.Name.Length).TrimStart(':') } $rh = $rk = $null :outer foreach ($rootKey in $hives.GetEnumerator()) { $rh = $rootKey.Value foreach ($prefix in ($rootKey.Name, $rootKey.Value.Name)) { if ($key.StartsWith($prefix, [System.StringComparison]::OrdinalIgnoreCase)) { $rk = $key.Substring($prefix.Length).TrimStart(':\') break outer } } } if (!$rk) { return } $o = $rh.OpenSubKey($rk, $PermissionCheck, $RegistryRights) if (!$o) { return } [string[]]$keyValueNames = try { $o.GetValueNames() } catch [System.UnauthorizedAccessException] { New-Object string[] 0 } $rootName, $keyName = $o.Name.Split('\')[0,-1] $keyPath = $o.Name.Substring(0, $o.Name.LastIndexOf('\')) $o | Add-Member -PassThru -MemberType NoteProperty -Name Property -Value $keyValueNames | Add-Member -PassThru -MemberType NoteProperty -Name PSChildName -Value $keyName | Add-Member -PassThru -MemberType NoteProperty -Name PSDrive -Value ( Get-PSDrive -PSProvider Registry | Where-Object Root -eq $rootName) | Add-Member -PassThru -MemberType NoteProperty -Name PSIsContainer -Value $true | Add-Member -PassThru -MemberType NoteProperty -Name PSParentPath -Value ( $providerString + '::' + $keyPath) | Add-Member -PassThru -MemberType NoteProperty -Name PSPath -Value ( $providerString + '::' + $o.Name) | Add-Member -PassThru -MemberType NoteProperty -Name PSProvider -Value $provider } } } if ($MyInvocation.InvocationName -ne '.') { if ($MyInvocation.ExpectingInput) { $null = $PSBoundParameters.Remove('Path') $input | Get-RegistryKey @PSBoundParameters } else { Get-RegistryKey @PSBoundParameters } } |