A few weeks ago Microsoft released a handy tool to help diagnose issues with Windows 10 upgrades called SetupDiag. The tool basically analyzes the Windows Setup logs against known issues and reports it’s findings in a log file. Troubleshooting Windows 10 setup is not the most fun activity, so using this tool certainly makes the process easier. To make it easier still, we can run it using SCCM, either standalone, or as part of a Windows 10 Upgrade task sequence.
Below is a simple PowerShell script wrapper that can be used to run the tool. It checks that the requirement of .Net 4.6 has been met then runs the tool, logging to the location you specify. In this example I am logging the results to the CCM Logs directory for convenience. It creates a file called Setupdiagresults.log and an archive called Logs.zip containing the Windows setup logs used.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Script to run SetupDiag to troubleshoot Windows 10 Setup | |
# Download SetupDiag.exe from https://go.microsoft.com/fwlink/?linkid=870142 and place in same directory as this script | |
# Get the CCM Logs location from registry | |
$LogLocation = Get-ItemProperty –Path "HKLM:\SOFTWARE\Microsoft\CCM\Logging\@Global" –Name LogDirectory | Select –ExpandProperty LogDirectory | |
#$LogLocation = "$env:SystemRoot\CCM\Logs" | |
# Get the location we're running from (or use $PSScriptRoot) | |
$ScriptPath = Split-Path $MyInvocation.MyCommand.Path –Parent | |
# Check that .Net 4.6 minimum is installed | |
If (Get-ChildItem "HKLM:SOFTWARE\Microsoft\NET Framework Setup\NDP\v4\Full\" | Get-ItemPropertyValue –Name Release | ForEach-Object { $_ -ge 393295 }) | |
{ | |
Try | |
{ | |
Start-Process –FilePath "$ScriptPath\SetupDiag.exe" –ArgumentList "/Output:$LogLocation\SetupDiagResults.log" –Wait –ErrorAction Stop | |
} | |
Catch | |
{ | |
"[ERROR] There was an error starting SetupDiag.exe: $_" | Out-file –FilePath "$LogLocation\SetupDiagResults.log" –Force | |
} | |
} | |
Else | |
{ | |
"[ERROR] .Net Framework 4.6 is required to run SetupDiag.exe" | Out-file –FilePath "$LogLocation\SetupDiagResults.log" –Force | |
} |
Download the SetupDiag utility from here, and create a package in SCCM containing both SetupDiag.exe and the PS script in the same directory.
Add a Run PowerShell Script step to your task sequence and reference the package you created.
Here’s an example log file output from a successful upgrade:
Do you run this before or after the upgrade?
After
Is there a way to redirect the log file to a share? I would like to make sure the client is ready for upgrade before i go.
Yes you can set that in the script. Just make sure the context running it has access to the file share.
I am trying to run this from the TS and log was not created. So i am trying to run it manually and gettign an error in the log file:
11:42:16 – SetupDiag: Main() failed with an unhandled exception:
Object reference not set to an instance of an object.
Exception System.NullReferenceException: Object reference not set to an instance of an object.
Any idea what is the issue here? I am trying to scan windows 10 readiness for an upgrade.
Thanks.
The intention here is to troubleshoot W10 upgrade failures. I don’t know that it would work pre-upgrade.
I see. Should i still get a different log file on a 1607?
Thank you.
Hey Trevor,
The script/SetupDiag.exe doesn’t seem to work when the task sequence is deployed with “Access content directly from a distribution point” for some reason. According to the smsts.log the script runs to completion with a 0 exit code but no log is outputted. The script and package work when the deployment is switched off ” access content directly…” . Do you have any ideas why that deployment method could cause any issues?
Thanks
Hey Trevor,
I noticed that when I tried to run the “Run-SetupDiag.ps1” script on a Windows 7 machine attempting the Windows 10 in-place upgrade, it was unable to interpret the “Get-ItemPropertyValue” command.
I changed this line in the script to following, and it’s working correctly on Windows 7 machines now:
If (Get-ChildItem “HKLM:SOFTWARE\Microsoft\NET Framework Setup\NDP\v4\Full\” | Get-ItemProperty -Name Release | Select-Object -ExpandProperty Release | ForEach-Object { $_ -ge 393295 }) {