Update 2021.06.09 – Based on a comment, I’ve moved over to using some code provided on sccmf12twice.com which I talk about in the post.
Function Restart-ComputerCMClient {
$time = [DateTimeOffset]::Now.ToUnixTimeSeconds()
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'RebootBy' -Value $time -PropertyType QWord -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'RebootValueInUTC' -Value 1 -PropertyType DWord -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'NotifyUI' -Value 1 -PropertyType DWord -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'HardReboot' -Value 0 -PropertyType DWord -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'OverrideRebootWindowTime' -Value 0 -PropertyType QWord -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'OverrideRebootWindow' -Value 0 -PropertyType DWord -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'PreferredRebootWindowTypes' -Value @("4") -PropertyType MultiString -Force -ea SilentlyContinue
New-ItemProperty -LiteralPath 'HKLM:\SOFTWARE\Microsoft\SMS\Mobile Client\Reboot Management\RebootData' -Name 'GraceSeconds' -Value 0 -PropertyType DWord -Force -ea SilentlyContinue
$CcmRestart = Start-Process -FilePath c:\windows\ccm\CcmRestart.exe -PassThru -Wait -WindowStyle Hidden
}
You can grab the function along with the updated version of my test app on GitHub
Original Post Starts Here: Ok, if the title didn’t make sense, let me explain.
- Goal 1: Trigger a Restart of a computer, which will use the Configuration Manager Dialogs Boxes and so the CM Client is aware of the Restart and not start any jobs.
- Goal 2: Trigger via PowerShell from the local client without reaching back to the Server (Completely offline)
Basically to replicate this experience, but locally via PowerShell:
Moments after I choose “Restart” on PC 06, I see:
I want to be able to trigger the CM Native Restart Dialog following the Restart Rules setup in the Client Settings.
Stops along the way:
Community: This got me really close: SCCM Reboot DECODED:: How to make a PC Cancel, Start, Extend or Change mandatory reboot to non-mandatory on the fly. The problem was that it required a restart of the CM Service, which you can’t really do during an Application Install… and I don’t like the idea of restarting the CM Service, what if it’s actually doing something when you restart it. So while that post was really helpful to understand how the CM Reboot works, it didn’t get me to the solution.
User Voice Items:
Ideal Solution: CM team adds this functionality: https://configurationmanager.uservoice.com/forums/300492-ideas/suggestions/40159861-ability-to-trigger-reboots-through-the-client-wmi
Another UV that would help with the main reason I need this ability: https://configurationmanager.uservoice.com/forums/300492-ideas/suggestions/38915797-allow-immediate-restart-after-user-initiated-insta
Failed Attempts:
So if you exit an application with Exit Code 3010, it will tell the client a reboot is needed, but on an available deployment will never actually reboot, it just creates the popups. My plan was to create a deadline in the local policy. This actually sorta works. I am able to create a deadline in the past, so as soon as the application is done, it prompts for restart… BUT… the count down doesn’t start until AFTER a Application Policy Evaluation. The Trick her was that you have to make it evaluate the USER deployed applications, not just the Machine. Every thing I did would only trigger machine, unless you ran it from the Control Panel.. See this Twitter Thread
Process:
- Install App, in Script create a Deadline on the App you’re installing (basically flipping it from Available to Required with a deadline in the past)
- $Deadline = “20190528024500.000000+***”
- $AppDeployment.EnforcementDeadline = $deadline
- $AppDeployment.Put()
- If you want to figure out how I got $AppDeployment, see HERE
- Exit App Script with 3010 to tell the system a reboot is needed
- Trigger App Eval
This actually works, if you go to Control Panel, ConfigMgr Actions and trigger the App Eval. But I couldn’t find a way to do that via PowerShell. (yes, there are ways to trigger App Evals, but it only evals MACHINE policies)
Normal App Install, when deployed as Available and exit code 3010:
You can see that you get prompted to restart, but there is no “Deadline” on the restart, you can snooze forever if you want. This is why we created the 2nd UV above
So unless I could figure out a way to trigger an App Eval which also evals the User apps, I couldn’t get this idea to work either.
Presented Solution:
- CM Package “Restart Computer”
- Program “Exit Force Restart”
- General: Command line: cmd.exe /c
- General: Run: Hidden
- General: After running: Configuration Manager restarts computer
- Environment: Program can run: Whether or not a user is logged on
- Environment: Run mode: Run with Admin Rights
- Deployment
- Collection: All Workstations
- Purpose: Required
- Scheduling: Start Time (Available Time): ASAP
- Scheduling: Deadline 10 years in the Future (Assignment Schedule)
- Scheduling: Rerun behavior: Never rerun deployed program
- User Experience: Outside MW: Software install True, System Restart True
- Program “Exit Force Restart”
With this Package / Program, having it deployed to all machines set it up in the policy on the machine, which then allows you to trigger it via PowerShell.
Program Image:
How? Using the trigger schedule method. ([wmiclass]’ROOT\ccm:SMS_Client’).TriggerSchedule($Schedule)
So now that we can programmatically reboot the machine, lets add this into an Application Install
Tying it together
I’ve created an Application for Testing things like this: FakeApp – Available on GitHub
Note, remember you have to have already created the Package and deployed it to the workstations you plan to call the Restart. If you don’t it won’t be able to trigger the restart.
I use this script to test additional items, but basically it sets a registry key to True or False. Everything else in the script is for testing processes.
Running the App on End Point results in triggering the Restart Program and popping up the Dialog.
I’ve also set the Application itself to exit with 3010, which lets the machine know the App itself needs the machine to restart.
When you run the App, in AppEnforce & ExecMgr, you can see the FakeApp Script calling the Exit Force Restart Program. (Function in the FakeApp Installer Script)
The script is available on GitHub, and you’ll see how the App calls the Restart Package:
The Actual Install part of the script is very short, and then calls the Restart function below:
This function finds the policy for the Restart Computer Package, then triggers the “install” of the Package which tells the system to restart.
Now, this is NOT the solution I’d like, but it’s the only thing I could make work. I would really like the ConfigMgr team to do those uservoice options, to allow better control around Application Installs, and give us a way to add a ConfigMgr restart into our own Scripts for our reasons.
Take a look at the full code on GitHub, if you have Qs, hit me up.
Gary Blok – GARYTOWN.COM
Hi,
I’m interested in using this but can you give more information on how you create your CM Package “Restart Computer” because I don’t understand where this General: After running: Configuration Manager restarts computer option is.
Thanks
On the Package, you create a Program. “General” = Tab of the Program, “After Running” = The Option in the program. “CM restarts computer” is the selection for that option.
Hope that helps, I’ve also added an image into the post.
Thanks a lot 🙁
Shame on me, I didn’t look everywhere.
I had success triggering the CM reboot prompt by running the registry script from SCCM Reboot DECODED:: How to make a PC Cancel, Start, Extend or Change mandatory reboot to non-mandatory on the fly site and then running CcmRestart.exe. There wasn’t a need to restart the service.
Thanks for that information.
Maybe you missed the name of the executable: CcmRestart.exe
It actually restarts the service.
can you use this at the end of a task sequence to display the native restart prompt?
Unsure, never tried.
Why not use the built in restart step?
I don’t think you’d want to use this, it would add a long reboot count down during OSD, assuming it worked.
It is not for OSD, I am using this with a script to install Symantec DLP in a task sequence, but want the native software center restart prompt to show with snooze button and timer from client settings. the task sequence checks for previous versions uninstalls them and installs the new app with .bat file. i tried it and it worked, the prompt shows but there is probably a better way. you think if i add exit code 3010 to bat it will prompt? or is there variable i can use to prompt. i have another task sequence with the restart step, using SMSREBOOTMESSAGE and SMSREBOOTIMEOUT but no snooze button, just static restart window
Hi,
Similar to Alan, I have been looking for the ability to do a more traditional CM reboot at the end of a task sequence – something more than the 2hr 45min TS reboot step offers with normal user experience from patching, etc.
I’m simply running the PS script within my app deployment task sequence having pre-deployed the package/program for Exit Force Restart to the collection per Gary’s guidance.
The problem I’m running into is this works about 80% of the time. The other 20% of the time in my testing/piloting, my clients are getting XML errors when running the script and trying to parse the PRG_Requirements piece. Has anyone seen something like this in your usage of this solution? Here is output:
Cannot convert value “System.Object[]” to type “System.Xml.XmlDocument”. Error: “Unexpected XML
declaration. The XML declaration must be the first node in the document, and no white space
characters are allowed to appear before it. Line 30, position 3.”
At XXXXXXX.ps1:6 char:1
+ [XML]$XML = $RestartProgram.PRG_Requirements
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : MetadataError: (:) [], ArgumentTransformationMetadataException
+ FullyQualifiedErrorId : RuntimeException
Cannot convert value
“ROOT\ccm\policy\machine\actualconfig:CCM_SoftwareDistribution.ADV_AdvertisementID=’XXXXXXXX
XXXXXXXX’,PKG_PackageID=’XXXXXXXX XXXXXXXX’,PRG_ProgramID=’Exit Force Restart Exit Force Restart'”
to type “System.Management.ManagementObject”. Error: “Not found ”
At XXXXXXX.ps1:9 char:191
+ … startProgramPackageID)’,PRG_ProgramID=’$($RestartProgramProgramID)'”)
Comparing a working and non-working client, the first piece of the PRG_Requirements in WMI looks the same:
Any insight into this is greatly appreciated. Thank you.