none
split behavior and arrays in PowerShell RRS feed

  • Question

  • I'm attempting to write a script that parses out the contents of a multi-string registry key. Its behavior, however, seems to change based on the number of lines in a key. Here's the script:

    $key = 'hklm:\SYSTEM\CurrentControlSet\Control\Lsa'
    $attribute = 'Authentication Packages'
    $AuthPkgs = Get-ItemProperty -Path $key -Name $attribute | select -ExpandProperty $attribute
    $AuthPkgs -split("'n")
    $AuthPkgs[0]
    $AuthPkgs[1]

    This is fairly straight forward, it looks for the "Authentication Packages" attribute in "System\CurrentControlSet\Control\LSA"

    This is a multi-string value, so it is possible to have more than one line here (worth noting this does appear to split by line), though on a typical OS there is only one value (msv1_0). If I were to add a second value to this key, the script will work as intended:

    $AuthPkgs[0] will equal msv1_0

    $AuthPkgs[1] will equal whatever my new value is.

    If, however, I leave the key alone and run the script, I get the following results:

    $AuthPkgs[0] will equal m

    $AuthPkgs[1] will equal s

    It seems, in this case, that it splits the single value by the characters. I don't want it to do this. Is there a way to define my split so that it does not?


    Nathan Gau MCT, MCITP, MCTS, CEH, CISSP


    Monday, November 20, 2017 8:38 PM

Answers

  • The issue is that when the value you read from the registry is a single value, PowerShell will return it as a string; if it contains multiple values, it will be an array of strings.

    To ensure the value you read is always an array, read it this way:


    $AuthPkgs = @(Get-ItemProperty -Path $key -Name $attribute | Select-Object -ExpandProperty $attribute)

    Encapsulating in @() tells PowerShell to return as an array, even if it's a single value.


    -- Bill Stewart [Bill_Stewart]

    Monday, November 20, 2017 8:43 PM
    Moderator

All replies

  • The issue is that when the value you read from the registry is a single value, PowerShell will return it as a string; if it contains multiple values, it will be an array of strings.

    To ensure the value you read is always an array, read it this way:


    $AuthPkgs = @(Get-ItemProperty -Path $key -Name $attribute | Select-Object -ExpandProperty $attribute)

    Encapsulating in @() tells PowerShell to return as an array, even if it's a single value.


    -- Bill Stewart [Bill_Stewart]

    Monday, November 20, 2017 8:43 PM
    Moderator
  • wow, you guys rock.. that worked.

    Nathan Gau MCT, MCITP, MCTS, CEH, CISSP

    Monday, November 20, 2017 8:46 PM
  • Actually an MULTI_SZ is always and array.  The array is stored as null terminated strings with two null after the last entry.  PowerSHell always converts this to a [string[]] of length one or more.   There is never a need to do more than get the compnents like this

    $ms = get-itemproperty -Path HKCU:\Software\Test -name test
    $mc.Count
    $ms[0]
    


    \_(ツ)_/

    Monday, November 20, 2017 8:55 PM