I've run into an interesting problem with running PowerShell via scripts through ConfigMgr(SCCM) clients. One of the relatively newer features of SCCM Current Branch is the ability to run PowerShell script on the target node through SCCM agent in real time. This agent runs in SYSTEM context and I have written a number of utility scripts which can be run from the SCCM Admin console on a number of machines simultaneously.

The PS script I am developing at the moment is supposed to GPUpdate both computer and logged-on user GPOs. The computer portion of the policy works fine through the SYSTEM context; however, to gpupdate the user portion of the GPO, I use task scheduler code to run it as the logged-on user.

It works as expected but the user GPUpdate process continues to stay in memory, which I was struggling to understand as to why.

It then occurred to me that it could be because of the logoff prompt (to complete the client side GPO extension processing) which users otherwise see on the cmd console at the end of GPUpdate when they try to run it manually. At least that's my hypothesis at this stage but I don't know how to dig deeper.

Since my script is running inside this SCCM agent "sandbox" which in turn spins up another Powershell which runs the user context GPupdate, I do not know if there is a way the "No" answer could be supplied to the logoff prompt of the gpupdate?

Any ideas?

Below is the full PowerShell script which runs on the target machine in system context.

# cmd /c gpupdate /target:computer /force | Out-Null $ExplorerProcess = Get-WmiObject win32_process | Where-Object { $_.name -Match 'explorer'} $LoggedOnUser = if($ExplorerProcess.getowner().user.count -gt 1){ $ExplorerProcess.getowner().user[0] }else{ $ExplorerProcess.getowner().user } If($LoggedOnUser.trim() -eq "") { "Computer GPUpdate Successful. No active user session" Return } $TaskName = "Run User GPUpdate - $((Get-Date).ToString('dd-MM-yyyy-HH-mm-ss'))" $ShedService = New-Object -comobject 'Schedule.Service' $ShedService.Connect() $Task = $ShedService.NewTask(0) $Task.RegistrationInfo.Description = 'Upser GPUpdate Description' $Task.Settings.Enabled = $true $Task.Settings.AllowDemandStart = $true $Task.Settings.DeleteExpiredTaskAfter = 'PT0S' $Task.Settings.StartWhenAvailable = $True $trigger = $task.triggers.Create(1) $trigger.StartBoundary = [DateTime]::Now.AddSeconds(5).ToString("yyyy-MM-dd'T'HH:mm:ss") $trigger.EndBoundary = [DateTime]::Now.AddSeconds(30).ToString("yyyy-MM-dd'T'HH:mm:ss") $trigger.Enabled = $true $ScriptCode = """ cmd /c gpupdate.exe /target:user /force """ $PwshArgument = "-ExecutionPolicy ByPass -NoProfile -WindowStyle Hidden -command $ScriptCode" $action = $Task.Actions.Create(0) $action.Path = 'Powershell.exe' $action.Arguments = $PwshArgument $taskFolder = $ShedService.GetFolder("\") try{ $taskFolder.RegisterTaskDefinition($TaskName, $Task , 6, 'Users' , $null, 4) | Out-Null "Computer GPO and User $LoggedOnUser GPO update Successful" } Catch { "GPUpdate Failed - $($_.Exception.Message)" } # 
6

1 Answer

Suppress gpupdate prompt

Consider incorporating the /wait:0 parameter and value in with the gpupdate command. This should suppress the prompt for confirmation allowing the GP to continue processing while allowing further script logic to continue without needing to "wait" on it to complete first.

I've used something such as gpupdate /force /wait:0 in the past with good success but there should be no problem running gpupdate /target:computer /force /wait:0 or gpupdate /target:user /force /wait:0 specifying which policy portion gets pushed to the machine and/or user.

gpupdate (Microsoft)

  • /wait:

    Sets the number of seconds to wait for policy processing to finish before returning to the command prompt. When the time limit is exceeded, the command prompt appears, but policy processing continues. The default value is 600 seconds. The value 0 means not to wait. The value -1 means to wait indefinitely.

    In a script, by using this command with a time limit specified, you can run gpupdate and continue with commands that do not depend upon the completion of gpupdate. Alternatively, you can use this command with no time limit specified to let gpupdate finish running before other commands that depend on it are run.

GPUPDATE (SS64)

  • /Wait:

    The number of seconds to wait for policy processing.

    • default = 600 (10 minutes)
    • 0 = do not wait
    • -1 = wait indefinitely

    If the time limit is exceeded, the command prompt returns, but policy processing continues.

5

Your Answer

Sign up or log in

Sign up using Google Sign up using Facebook Sign up using Email and Password

Post as a guest

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy