Writing Current User registry keys in SCCM as System

It is possible to write CurrentUser registry keys by deploying an application/package that runs as the System.  This could be useful when installing an application and wanting to set the personalisation registry keys for the logged in user at the same time.  The script I’ve used below also allows you to install it for all users on that machine, and also for the Default User so all future users get those settings.

 

You’ll need 3 things:

  1. A registry file that contains the settings you want to add.

1

  1. This script from TechNet https://gallery.technet.microsoft.com/scriptcenter/Write-to-HKCU-from-the-3eac1692

**this file looks to have been removed for some reason. I have included the script at the bottom of the page, just save it as WriteToHkcuFromsystem.ps1**

  1. A batch file similar to this.

It basically enables the powershell script to run, runs the script to add the registry key(s) for the Current User that is logged on, and then returns the powershell execution policy back to what it was.

2

PowerShell.exe Set-ExecutionPolicy -ExecutionPolicy Unrestricted

PowerShell.exe -File “%~dp0WriteToHkcuFromsystem.ps1” -RegFile “%~dp0DisableTaskBarThumbnails.reg” -CurrentUser

PowerShell.exe Set-ExecutionPolicy -ExecutionPolicy Restricted

 

I created a new package in SCCM containing the following files

3

 

Ensure that you choose “Only when a user is logged on”. This means it will be able to pick up the Current User and apply the registry settings to that user.

4

 

For the Command being run just choose the install.bat.   I made sure it runs hidden as well.

5

 

Deploy out to some test machines and you should find it populates the Current User hive of the registry.  Take a look at the script on TechNet as it shows how to add the registry key(s) to   -CurrentUser -AllUsers -DefaultProfile

WriteToHkcuFromsystem.ps1 contents

PARAM(

    [Parameter(Mandatory=$true)]
    [ValidatePattern('\.reg$')]
    [string]$RegFile,

    [switch]$CurrentUser,
    [switch]$AllUsers,
    [switch]$DefaultProfile
)


function Write-Registry {
    PARAM($RegFileContents)
    $tempFile = '{0}{1:yyyyMMddHHmmssff}.reg' -f [IO.Path]::GetTempPath(), (Get-Date)
    $RegFileContents | Out-File -FilePath $tempFile
    Write-Host ('Writing registry from file {0}' -f $tempFile)
    try { $p = Start-Process -FilePath C:\Windows\regedit.exe -ArgumentList "/s $tempFile" -PassThru -Wait } catch { }
    if($p -ne $null) { $exitCode = $p.ExitCode } else { $exitCode = 0 }
    if($exitCode -ne 0) {
        Write-Warning 'There was an error merging the reg file'
    } else {
        Remove-Item -Path $tempFile -Force -ErrorAction SilentlyContinue
    }
}

if(-not (Test-Path -Path $RegFile)) {
    Write-Warning "RegFile $RegFile doesn't exist. Operation aborted"
} else {

    if($CurrentUser -or $AllUsers -or $DefaultProfile) {

        Write-Host ('Reading the registry file {0}' -f $RegFile)
        $registryData = Get-Content -Path $RegFile -ReadCount 0

        if($CurrentUser) {
            Write-Host "Writing to the currenlty loggoed on user's registry"
            $explorers = Get-WmiObject -Namespace root\cimv2 -Class Win32_Process -Filter "Name='explorer.exe'"
            $explorers | ForEach-Object {
                $owner = $_.GetOwner()
                if($owner.ReturnValue -eq 0) {
                    $user = '{0}\{1}' -f $owner.Domain, $owner.User
                    $ntAccount = New-Object -TypeName System.Security.Principal.NTAccount($user)
                    $sid = $ntAccount.Translate([System.Security.Principal.SecurityIdentifier]).Value
                    $RegFileContents = $registryData -replace 'HKEY_CURRENT_USER', "HKEY_USERS\$sid"
                    Write-Registry -RegFileContents $RegFileContents
                }
            }
        }

        if($AllUsers) {
            Write-Host "Writing to every user's registry"
            $res = C:\Windows\system32\reg.exe query HKEY_USERS
            $res -notmatch 'S-1-5-18|S-1-5-19|S-1-5-20|DEFAULT|Classes' | ForEach-Object {
                if($_ -ne '') {
                    $sid = $_ -replace 'HKEY_USERS\\'
                    $RegFileContents = $registryData -replace 'HKEY_CURRENT_USER', "HKEY_USERS\$sid"
                    Write-Registry -RegFileContents $RegFileContents

                }
            }
        }

        if($DefaultProfile) {
            Write-Host "Writing to the default profile's registry (for future users)"
            C:\Windows\System32\reg.exe load 'HKU\DefaultUser' C:\Users\Default\NTUSER.DAT | Out-Null
            $RegFileContents = $registryData -replace 'HKEY_CURRENT_USER', 'HKEY_USERS\DefaultUser'
            Write-Registry -RegFileContents $RegFileContents
            C:\Windows\System32\reg.exe unload 'HKU\DefaultUser' | Out-Null
        }

    } else {
        Write-Warning 'No mode was selected. Operation aborted'
    }
}

4 thoughts on “Writing Current User registry keys in SCCM as System

  1. Thanks for the post, this helps me a lot.
    I was able to run the HKCU + .reg file directly from command line as oneliner, as a package. May it helps others too if you want to avoid creating an extra installer file.

    Here my line, which I use:
    “%SystemRoot%\system32\WindowsPowerShell\v1.0\powershell.exe” -ExecutionPolicy Bypass -Command .\WriteToHkcuFromSystem.ps1 -RegFile Registry-Settings.reg –CurrentUser –AllUsers –DefaultProfile

    Regards,
    Dan

    Liked by 1 person

  2. I can’t find the WriteToHkcuFromSystem.ps1 anywhere and the source link no longer works. Are you able to get this message on the forum? If you could send the file to me that would be great!

    Like

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s