Implemented working REG_NONE support

This fixes #20343
This commit is contained in:
Dag Wieers 2017-01-25 20:40:57 +01:00
parent 454dde5dfd
commit 4c7715a4e5
2 changed files with 30 additions and 22 deletions

View file

@ -19,8 +19,6 @@
# WANT_JSON # WANT_JSON
# POWERSHELL_COMMON # POWERSHELL_COMMON
# TODO: Add missing REG_NONE support
$ErrorActionPreference = "Stop" $ErrorActionPreference = "Stop"
$params = Parse-Args $args -supports_check_mode $true $params = Parse-Args $args -supports_check_mode $true
@ -29,7 +27,7 @@ $check_mode = Get-AnsibleParam -obj $params -name "_ansible_check_mode" -type "b
$path = Get-AnsibleParam -obj $params -name "path" -type "string" -failifempty $true -aliases "key" $path = Get-AnsibleParam -obj $params -name "path" -type "string" -failifempty $true -aliases "key"
$name = Get-AnsibleParam -obj $params -name "name" -type "string" -aliases "entry","value" $name = Get-AnsibleParam -obj $params -name "name" -type "string" -aliases "entry","value"
$data = Get-AnsibleParam -obj $params -name "data" $data = Get-AnsibleParam -obj $params -name "data"
$type = Get-AnsibleParam -obj $params -name "type" -type "string" -validateSet "binary","dword","expandstring","multistring","string","qword" -aliases "datatype" -default "string" $type = Get-AnsibleParam -obj $params -name "type" -type "string" -validateSet "none","binary","dword","expandstring","multistring","string","qword" -aliases "datatype" -default "string"
$state = Get-AnsibleParam -obj $params -name "state" -type "string" -validateSet "present","absent" -default "present" $state = Get-AnsibleParam -obj $params -name "state" -type "string" -validateSet "present","absent" -default "present"
$result = @{ $result = @{
@ -42,10 +40,6 @@ $result = @{
warnings = @() warnings = @()
} }
if ($state -eq "present" -and $data -eq $null -and $name -ne $null) {
Fail-Json $result "missing required argument: data"
}
# Fix HCCC:\ PSDrive for pre-2.3 compatibility # Fix HCCC:\ PSDrive for pre-2.3 compatibility
if ($path -match "^HCCC:\\") { if ($path -match "^HCCC:\\") {
$result.warnings += "Please use path: HKCC:\... instead of path: $path\n" $result.warnings += "Please use path: HKCC:\... instead of path: $path\n"
@ -59,7 +53,7 @@ if (-not ($path -match "^HK(CC|CR|CU|LM|U):\\")) {
# Allow empty values as the "(default)" value # Allow empty values as the "(default)" value
if ($name -eq "") { if ($name -eq "") {
$registryValue = "(default)" $name = "(default)"
} }
Function Test-ValueData { Function Test-ValueData {
@ -80,11 +74,17 @@ Function Test-ValueData {
# Handles binary, integer(dword) and string registry data # Handles binary, integer(dword) and string registry data
Function Compare-Data { Function Compare-Data {
Param ( Param (
[parameter(Mandatory=$true)] [AllowEmptyString()] $ReferenceData, [parameter(Mandatory=$true)] [AllowEmptyString()] [AllowNull()] $ReferenceData,
[parameter(Mandatory=$true)] [AllowEmptyString()] $DifferenceData [parameter(Mandatory=$true)] [AllowEmptyString()] [AllowNull()] $DifferenceData
) )
if ($ReferenceData -is [String] -or $ReferenceData -is [int]) { if ($ReferenceData -eq $null) {
if ($DifferenceData -eq $null) {
return $true
} else {
return $false
}
} elseif ($ReferenceData -is [String] -or $ReferenceData -is [int]) {
if ($ReferenceData -eq $DifferenceData) { if ($ReferenceData -eq $DifferenceData) {
return $true return $true
} else { } else {
@ -158,6 +158,13 @@ if ($name.ToLower() -eq "(default)") {
$type = "string" $type = "string"
} }
# Support REG_NONE with empty value
# FIXME: REG_NONE support is not idempotent
if ($type -eq "none" -or $data -eq $null) {
$data = New-Object byte[] 0
# $data = ([byte[]] @())
}
if ($state -eq "present") { if ($state -eq "present") {
if ((Test-Path $path) -and $name -ne $null) { if ((Test-Path $path) -and $name -ne $null) {
@ -170,9 +177,9 @@ if ($state -eq "present") {
if ($name.ToLower() -eq "(default)") { if ($name.ToLower() -eq "(default)") {
# Special case handling for the path's default property. # Special case handling for the path's default property.
# Because .GetValueKind() doesn't work for the (default) path property # Because .GetValueKind() doesn't work for the (default) path property
$old_type = "String" $old_type = "String".ToLower()
} else { } else {
$old_type = (Get-Item $path).GetValueKind($name) $old_type = (Get-Item $path).GetValueKind($name).ToString().ToLower()
} }
if ($type -ne $old_type) { if ($type -ne $old_type) {
@ -197,12 +204,17 @@ if ($state -eq "present") {
-"$name" = "$old_type`:$data" -"$name" = "$old_type`:$data"
+"$name" = "$type`:$data" +"$name" = "$type`:$data"
"@ "@
# FIXME: Compare-Data fails to work for null-length byte arrays
} elseif (-not (Compare-Data -ReferenceData $old_data -DifferenceData $data)) { } elseif (-not (Compare-Data -ReferenceData $old_data -DifferenceData $data)) {
# Changes Only Data # Changes Only Data
if (-not $check_mode) { if (-not $check_mode) {
try { try {
if ($type -eq "none") {
Remove-ItemProperty -Path $path -Name $name
New-ItemProperty -Path $path -Name $name -Value $data -PropertyType $type -Force
} else {
Set-ItemProperty -Path $path -Name $name -Value $data Set-ItemProperty -Path $path -Name $name -Value $data
}
} catch { } catch {
Fail-Json $result $_.Exception.Message Fail-Json $result $_.Exception.Message
} }
@ -220,7 +232,7 @@ if ($state -eq "present") {
} }
} else { } else {
# Add missing entry
if (-not $check_mode) { if (-not $check_mode) {
try { try {
New-ItemProperty -Path $path -Name $name -Value $data -PropertyType $type New-ItemProperty -Path $path -Name $name -Value $data -PropertyType $type
@ -244,7 +256,6 @@ if ($state -eq "present") {
$new_path | New-ItemProperty -Name $name -Value $data -PropertyType $type -Force $new_path | New-ItemProperty -Name $name -Value $data -PropertyType $type -Force
} }
} catch { } catch {
throw
Fail-Json $result $_.Exception.Message Fail-Json $result $_.Exception.Message
} }
} }
@ -260,8 +271,6 @@ if ($state -eq "present") {
"@ "@
} }
} else {
# FIXME: Value is null, should we silently ignore this and do nothing ?
} }
} elseif ($state -eq "absent") { } elseif ($state -eq "absent") {

View file

@ -37,7 +37,7 @@ options:
path: path:
description: description:
- Name of registry path. - Name of registry path.
- Should be in one of the following registry hives: HKCC, HKCR, HKCU, HKLM, HKU. - 'Should be in one of the following registry hives: HKCC, HKCR, HKCU, HKLM, HKU.'
required: true required: true
aliases: [ key ] aliases: [ key ]
name: name:
@ -71,7 +71,6 @@ options:
default: present default: present
notes: notes:
- Check-mode C(-C/--check) and diff output (-D/--diff) are supported, so that you can test every change against the active configuration before applying changes. - Check-mode C(-C/--check) and diff output (-D/--diff) are supported, so that you can test every change against the active configuration before applying changes.
- At the moment REG_NONE support is missing because it is lacking from the Powershell API. Workarounds are possible but currently lacking.
- Beware that some registry hives (HKEY_USERS in particular) do not allow to create new registry paths. - Beware that some registry hives (HKEY_USERS in particular) do not allow to create new registry paths.
author: "Adam Keech (@smadam813), Josh Ludwig (@joshludwig)" author: "Adam Keech (@smadam813), Josh Ludwig (@joshludwig)"
''' '''