キー自体を削除せずに、Windowsレジストリ内のキーのすべてのサブキーを削除する簡単な(自動化された)方法はありますか?
ありがとう
事前にサブキーを知っていますか?もしそうなら、次のようなものを使用して.regファイルでそれを行うことができ、Testのすべてのサブキーを削除します。
Windows Registry Editor Version 5.00
[-HKEY_LOCAL_MACHINE\Software\Test\Key1]
[-HKEY_LOCAL_MACHINE\Software\Test\Key2]
[-HKEY_LOCAL_MACHINE\Software\Test\Key3]
[-HKEY_LOCAL_MACHINE\Software\Test\Key4]
行の先頭のマイナス記号は、そのキーを完全に削除するように指示します。完全な構文は次のとおりです: http://support.Microsoft.com/kb/310516
そうでない場合は、すべてのサブキーを列挙し、それらを1つずつ削除するスクリプトを探しています。仕事でこれをする人がいますが、家にいるので行けません!
Windows7またはVistaでは、ファイルシステムパスを参照するのと同じ方法でレジストリパスを参照して、次のようなPowershellコマンドを使用できます。
Remove-Item -Path HKLM:\Software\Test\Key1 -Recurse
Remove-Item -Path HKLM:\Software\Test\Key2 -Recurse
Remove-Item -Path HKLM:\Software\Test\Key3 -Recurse
Remove-Item -Path HKLM:\Software\Test\Key4 -Recurse
レジストリキーの操作 :からの抜粋
HKCU:\ CurrentVersion内のすべてのアイテムを削除したいが、ではないHKCU:\ CurrentVersion自体、代わりに以下を使用できます。
#Requires -Version 3.0
Remove-Item -Path HKCU:\CurrentVersion\* -Recurse
注:HKCU:\ CurrentVersionに属するレジストリ値は削除されません。
レジストリキーのすべてのサブキーを削除するPowerShellの方法を次に示します。
$path = "Any valid Path ..."
(gci $path).PsPath | foreach { if($_){Remove-Item $_ -Force} }
例えば :
$path = "HKLM:\Software\Policies\Microsoft\Windows\RemovableStorageDevices"
(gci $path).PsPath | foreach { if($_){Remove-Item $_ -Force} }
次のコマンドを実行できます。
for /f "tokens=*" %A in ('reg query HKLM\Software\policies\Microsoft\') do reg delete %A /f
for /f "tokens=*" %A in ('reg query HKLM\Software\Microsoft\windows\CurrentVersion\policies\') do reg delete %A /f
バッチとして使用する場合は、%Aを%% Aに変更してください。この例では、コンピューターポリシーを削除します。
元の投稿者は、ツリーの実際のルートキーではなくツリーを削除することを要求することを示して質問を明確にしました。そのため、ルートを含むツリー全体が削除されるため、これはquite回答ではありません。それでも、質問タイトルへの回答を検索すると、検索結果の上位に表示されるため、この回答を投稿しておくと参考になりました。
<#
.SYNOPSIS
Give ownership of a file, folder, or registry key to the specified user.
.DESCRIPTION
Give the current process the SeTakeOwnershipPrivilege" and "SeRestorePrivilege" rights which allows it
to reset ownership of an object. The script will then set the owner to be the specified user.
.PARAMETER Path (Required)
The path to the object on which you wish to change ownership. It can be a file, folder, or registry key
.PARAMETER User (Required)
The user whom you want to be the owner of the specified object. The user should be in the format
<domain>\<username>. Other user formats will not work. For system accounts, such as System, the user
should be specified as "NT AUTHORITY\System". If the domain is missing, the local machine will be assumed.
.PARAMETER Recurse (switch)
Causes the function to parse through the Path recursively.
.INPUTS
None. You cannot pipe objects to Take-Ownership
.OUTPUTS
None
.NOTES
Name: Take-Ownership.ps1
Author: Jason Eberhardt
Date: 2017-07-20
#>
function Take-Ownership {
[CmdletBinding(SupportsShouldProcess=$false)]
Param([Parameter(Mandatory=$true, ValueFromPipeline=$false)] [ValidateNotNullOrEmpty()] [string]$Path,
[Parameter(Mandatory=$true, ValueFromPipeline=$false)] [ValidateNotNullOrEmpty()] [string]$User,
[Parameter(Mandatory=$false, ValueFromPipeline=$false)] [switch]$Recurse)
Begin {
$AdjustTokenPrivileges=@"
using System;
using System.Runtime.InteropServices;
public class TokenManipulator {
[DllImport("kernel32.dll", ExactSpelling = true)]
internal static extern IntPtr GetCurrentProcess();
[DllImport("advapi32.dll", ExactSpelling = true, SetLastError = true)]
internal static extern bool AdjustTokenPrivileges(IntPtr htok, bool disall, ref TokPriv1Luid newst, int len, IntPtr prev, IntPtr relen);
[DllImport("advapi32.dll", ExactSpelling = true, SetLastError = true)]
internal static extern bool OpenProcessToken(IntPtr h, int acc, ref IntPtr phtok);
[DllImport("advapi32.dll", SetLastError = true)]
internal static extern bool LookupPrivilegeValue(string Host, string name, ref long pluid);
[StructLayout(LayoutKind.Sequential, Pack = 1)]
internal struct TokPriv1Luid {
public int Count;
public long Luid;
public int Attr;
}
internal const int SE_PRIVILEGE_DISABLED = 0x00000000;
internal const int SE_PRIVILEGE_ENABLED = 0x00000002;
internal const int TOKEN_QUERY = 0x00000008;
internal const int TOKEN_ADJUST_PRIVILEGES = 0x00000020;
public static bool AddPrivilege(string privilege) {
bool retVal;
TokPriv1Luid tp;
IntPtr hproc = GetCurrentProcess();
IntPtr htok = IntPtr.Zero;
retVal = OpenProcessToken(hproc, TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, ref htok);
tp.Count = 1;
tp.Luid = 0;
tp.Attr = SE_PRIVILEGE_ENABLED;
retVal = LookupPrivilegeValue(null, privilege, ref tp.Luid);
retVal = AdjustTokenPrivileges(htok, false, ref tp, 0, IntPtr.Zero, IntPtr.Zero);
return retVal;
}
public static bool RemovePrivilege(string privilege) {
bool retVal;
TokPriv1Luid tp;
IntPtr hproc = GetCurrentProcess();
IntPtr htok = IntPtr.Zero;
retVal = OpenProcessToken(hproc, TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, ref htok);
tp.Count = 1;
tp.Luid = 0;
tp.Attr = SE_PRIVILEGE_DISABLED;
retVal = LookupPrivilegeValue(null, privilege, ref tp.Luid);
retVal = AdjustTokenPrivileges(htok, false, ref tp, 0, IntPtr.Zero, IntPtr.Zero);
return retVal;
}
}
"@
}
Process {
$Item=Get-Item $Path
Write-Verbose "Giving current process token ownership rights"
Add-Type $AdjustTokenPrivileges -PassThru > $null
[void][TokenManipulator]::AddPrivilege("SeTakeOwnershipPrivilege")
[void][TokenManipulator]::AddPrivilege("SeRestorePrivilege")
# Change ownership
$Account=$User.Split("\")
if ($Account.Count -eq 1) { $Account+=$Account[0]; $Account[0]=$env:COMPUTERNAME }
$Owner=New-Object System.Security.Principal.NTAccount($Account[0],$Account[1])
Write-Verbose "Change ownership to '$($Account[0])\$($Account[1])'"
$Provider=$Item.PSProvider.Name
if ($Item.PSIsContainer) {
switch ($Provider) {
"FileSystem" { $ACL=[System.Security.AccessControl.DirectorySecurity]::new() }
"Registry" { $ACL=[System.Security.AccessControl.RegistrySecurity]::new()
# Get-Item doesn't open the registry in a way that we can write to it.
switch ($Item.Name.Split("\")[0]) {
"HKEY_CLASSES_ROOT" { $rootKey=[Microsoft.Win32.Registry]::ClassesRoot; break }
"HKEY_LOCAL_MACHINE" { $rootKey=[Microsoft.Win32.Registry]::LocalMachine; break }
"HKEY_CURRENT_USER" { $rootKey=[Microsoft.Win32.Registry]::CurrentUser; break }
"HKEY_USERS" { $rootKey=[Microsoft.Win32.Registry]::Users; break }
"HKEY_CURRENT_CONFIG" { $rootKey=[Microsoft.Win32.Registry]::CurrentConfig; break }
}
$Key=$Item.Name.Replace(($Item.Name.Split("\")[0]+"\"),"")
$Item=$rootKey.OpenSubKey($Key,[Microsoft.Win32.RegistryKeyPermissionCheck]::ReadWriteSubTree,[System.Security.AccessControl.RegistryRights]::TakeOwnership) }
default { throw "Unknown provider: $($Item.PSProvider.Name)" }
}
$ACL.SetOwner($Owner)
Write-Verbose "Setting owner on $Path"
$Item.SetAccessControl($ACL)
if ($Provider -eq "Registry") { $Item.Close() }
if ($Recurse.IsPresent) {
# You can't set ownership on Registry Values
if ($Provider -eq "Registry") { $Items=Get-ChildItem -Path $Path -Recurse -Force | Where-Object { $_.PSIsContainer } }
else { $Items=Get-ChildItem -Path $Path -Recurse -Force }
$Items=@($Items)
for ($i=0; $i -lt $Items.Count; $i++) {
switch ($Provider) {
"FileSystem" { $Item=Get-Item $Items[$i].FullName
if ($Item.PSIsContainer) { $ACL=[System.Security.AccessControl.DirectorySecurity]::new() }
else { $ACL=[System.Security.AccessControl.FileSecurity]::new() } }
"Registry" { $Item=Get-Item $Items[$i].PSPath
$ACL=[System.Security.AccessControl.RegistrySecurity]::new()
# Get-Item doesn't open the registry in a way that we can write to it.
switch ($Item.Name.Split("\")[0]) {
"HKEY_CLASSES_ROOT" { $rootKey=[Microsoft.Win32.Registry]::ClassesRoot; break }
"HKEY_LOCAL_MACHINE" { $rootKey=[Microsoft.Win32.Registry]::LocalMachine; break }
"HKEY_CURRENT_USER" { $rootKey=[Microsoft.Win32.Registry]::CurrentUser; break }
"HKEY_USERS" { $rootKey=[Microsoft.Win32.Registry]::Users; break }
"HKEY_CURRENT_CONFIG" { $rootKey=[Microsoft.Win32.Registry]::CurrentConfig; break }
}
$Key=$Item.Name.Replace(($Item.Name.Split("\")[0]+"\"),"")
$Item=$rootKey.OpenSubKey($Key,[Microsoft.Win32.RegistryKeyPermissionCheck]::ReadWriteSubTree,[System.Security.AccessControl.RegistryRights]::TakeOwnership) }
default { throw "Unknown provider: $($Item.PSProvider.Name)" }
}
$ACL.SetOwner($Owner)
Write-Verbose "Setting owner on $($Item.Name)"
$Item.SetAccessControl($ACL)
if ($Provider -eq "Registry") { $Item.Close() }
}
} # Recursion
}
else {
if ($Recurse.IsPresent) { Write-Warning "Object specified is neither a folder nor a registry key. Recursion is not possible." }
switch ($Provider) {
"FileSystem" { $ACL=[System.Security.AccessControl.FileSecurity]::new() }
"Registry" { throw "You cannot set ownership on a registry value" }
default { throw "Unknown provider: $($Item.PSProvider.Name)" }
}
$ACL.SetOwner($Owner)
Write-Verbose "Setting owner on $Path"
$Item.SetAccessControl($ACL)
}
}
}
<#
.SYNOPSIS
Deletes a registry key recursively
.DESCRIPTION
This function will delete the specified registry key and all its values and subkeys
.INPUTS
None. You cannot pipe objects to Delete-RegistryKeyTree.
.EXAMPLE
Delete-RegistryKeyTree -Hive HKCR -Key "CLSID\squid" -User $env:USERNAME
.OUTPUTS
System.String
.NOTES
Name: Delete-RegistryKeyTree
Author: Jason Eberhardt
Date: 2017-07-20
#>
function Delete-RegistryKeyTree {
[CmdletBinding(SupportsShouldProcess=$false)]
Param([Parameter(Mandatory=$true, ValueFromPipeline=$false)] [ValidateSet("HKCR","HKLM","HKCU","HKU","HKCC")] [string]$Hive,
[Parameter(Mandatory=$true, ValueFromPipeline=$false)] [ValidateNotNullOrEmpty()] [string]$Key,
[Parameter(Mandatory=$true, ValueFromPipeline=$false)] [ValidateNotNullOrEmpty()] [string]$User)
Process {
switch ($Hive) {
"HKCR" { $rootKey=[Microsoft.Win32.RegistryHive]::ClassesRoot; break }
"HKLM" { $rootKey=[Microsoft.Win32.RegistryHive]::LocalMachine; break }
"HKCU" { $rootKey=[Microsoft.Win32.RegistryHive]::CurrentUser; break }
"HKU" { $rootKey=[Microsoft.Win32.RegistryHive]::Users; break }
"HKCC" { $rootKey=[Microsoft.Win32.RegistryHive]::CurrentConfig; break }
}
$Reg=[Microsoft.Win32.RegistryKey]::OpenBaseKey($rootKey,[Microsoft.Win32.RegistryView]::Default)
$RegKey=$Reg.OpenSubKey($Key,[Microsoft.Win32.RegistryKeyPermissionCheck]::ReadWriteSubTree,[System.Security.AccessControl.RegistryRights]::FullControl)
if ($RegKey -eq $null) { Write-Warning "Registry key is already deleted." }
else {
Write-Verbose "Deleting key $Key"
Take-Ownership -Path "Registry::$Hive\$Key" -User $User -Recurse
Write-Verbose "Resetting permissions on $Key"
$ACL=New-Object System.Security.AccessControl.RegistrySecurity
$ACL.SetAccessRuleProtection($false,$false)
$FSR=New-Object System.Security.AccessControl.RegistryAccessRule($User, [System.Security.AccessControl.RegistryRights]::FullControl, ([System.Security.AccessControl.InheritanceFlags]::ContainerInherit -bor [System.Security.AccessControl.InheritanceFlags]::ObjectInherit), [System.Security.AccessControl.PropagationFlags]::None, [System.Security.AccessControl.AccessControlType]::Allow)
$ACL.ResetAccessRule($FSR)
$RegKey.Close()
$RegKey=$Reg.OpenSubKey($Key,[Microsoft.Win32.RegistryKeyPermissionCheck]::ReadWriteSubTree,[System.Security.AccessControl.RegistryRights]::ChangePermissions)
$RegKey.SetAccessControl($ACL)
$RegKey.Close()
$Reg.Close()
Write-Verbose "Deleting $Key"
$result=& cmd /c "reg delete $Hive\$Key /f"
Write-Verbose $result[0]
}
}
}
New-Item $path -Force
-Force
引数は仕事をします。