Scenario
You've found that your VM / computer has some file corruption issues, and when you're trying to run a windows update or a DISM /RestoreHealth, it reports
C:\Windows\system32>dism.exe /online /cleanup-image /restorehealth Deployment Image Servicing and Management tool Version: 10.0.14393.4169 Image Version: 10.0.14393.4169 [==========================100.0%==========================] Error: 0x800f081f The source files could not be found. Use the "Source" option to specify the location of the files that are required to restore the feature. For more information on specifying a source location, see http://go.microsoft.com/fwlink/?LinkId=243077. The DISM log file can be found at C:\Windows\Logs\DISM\dism.log
You may even try certain combinations of /Source:...install.wim:1 to no avail.
The issue is that the component that needs to be fixed, is not on the source file you have specified. Who knows why it can't get it from Windows Update, but the result is the same - it can't find the right version of the file it needs.
If you do go and check dism.log, you'll get some typically unhelpful log messages:
2023-02-01 02:25:08, Info DISM DISM Package Manager: PID=6968 TID=6156 Error in operation: (null) (CBS HRESULT=0x80070002) - CCbsConUIHandler::Error 2023-02-01 02:25:08, Error DISM DISM Package Manager: PID=6968 TID=1888 Failed finalizing changes. - CDISMPackageManager::Internal_Finalize(hr:0x80070002) 2023-02-01 02:25:08, Error DISM DISM Package Manager: PID=6968 TID=1888 Failed processing package changes with session option CbsSessionOptionAnalyzeStore - CDISMPackageManager::AnalyzeComponentStore(hr:0x80070002) 2023-02-01 02:25:08, Error DISM DISM Package Manager: PID=6968 TID=1888 Failed to analyze component store. - CPackageManagerCLIHandler::ProcessCmdLine_CleanupImage(hr:0x80070002) 2023-02-01 02:25:08, Error DISM DISM Package Manager: PID=6968 TID=1888 Failed while processing command cleanup-image. - CPackageManagerCLIHandler::ExecuteCmdLine(hr:0x80070002) 2023-02-01 02:25:08, Info DISM DISM Package Manager: PID=6968 TID=1888 Further logs for online package and feature related operations can be found at %WINDIR%\logs\CBS\cbs.log - CPackageManagerCLIHandler::ExecuteCmdLine 2023-02-01 02:25:08, Error DISM DISM.EXE: DISM Package Manager processed the command line but failed. HRESULT=80070002
This is, obviously, completely useless to us. Something Happened!. But! The useful information actually lives in C:\Windows\Logs\CBS\cbs.log
2023-02-01 02:25:07, Info CBS Skipping package [OpenSSH-Client-Package~31bf3856ad364e35~amd64~~10.0.17763.1] since it has a release-type [OnDemand Pack] that makes it not superseded 2023-02-01 02:25:07, Info CBS Skipping package [OpenSSH-Server-Package~31bf3856ad364e35~amd64~~10.0.17763.1] since it has a release-type [OnDemand Pack] that makes it not superseded 2023-02-01 02:25:08, Info CBS Failed to load package: Package_for_DotNetRollup~31bf3856ad364e35~amd64~~10.0.3946.2 [HRESULT = 0x80070002 - ERROR_FILE_NOT_FOUND] 2023-02-01 02:25:08, Info CBS Failed to read manifest content. [HRESULT = 0x80070002 - ERROR_FILE_NOT_FOUND] 2023-02-01 02:25:08, Info CBS Failed checking if package is deeply superseded: [Package_for_DotNetRollup~31bf3856ad364e35~amd64~~10.0.3946.2] [HRESULT = 0x80070002 - ERROR_FILE_NOT_FOUND] 2023-02-01 02:25:08, Info CBS Analyze: Failed to collect packages from package store [HRESULT = 0x80070002 - ERROR_FILE_NOT_FOUND] 2023-02-01 02:25:08, Info CBS Analyze: Failed getting superseded package count [HRESULT = 0x80070002 - ERROR_FILE_NOT_FOUND] 2023-02-01 02:25:08, Info CBS Reboot mark cleared
Aha! We finally find something telling us what is causing DISM so much trouble.
The Investigation
The fix boils down to "Supply DISM the components it needs to fix the issue" or "Re-install that update / component / package".
First thing that needs to happen either way is to find the .msu or .cab etc. for that package.
Alternatively, you might get lucky and the name of the component contains the KB ID of the update that contains the component it needs:
2023-02-02 13:36:43, Error CSI 00000001 (F) STATUS_OBJECT_NAME_NOT_FOUND #227620# from Windows::Rtl::SystemImplementation::DirectFileSystemProvider::SysCreateFile(flags = 0, handle = {provider=NULL, handle=0, name= ("null")}, da = (FILE_GENERIC_READ|DELETE), oa = @0xa0a91fcca0->OBJECT_ATTRIBUTES {s:48; rd:NULL; on:[98]'\??\C:\Windows\Servicing\Packages\Package_4944_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.cat'; a:(OBJ_CASE_INSENSITIVE)}, iosb = @0xa0a91fcc40, as = (null), fa = (FILE_ATTRIBUTE_NORMAL), sa = (FILE_SHARE_READ|FILE_S[gle=0xd0000034] 2023-02-02 13:36:43, Error CSI HARE_WRITE|FILE_SHARE_DELETE), cd = FILE_OPEN, co = (FILE_NON_DIRECTORY_FILE|FILE_SYNCHRONOUS_IO_NONALERT), eab = NULL, eal = 0, disp = Invalid)
2023-02-02 13:39:59, Info CBS Repr: Add missing package manifest/cat for package:Package_4944_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15
2023-02-02 15:11:53, Info CBS Exec: Not able to find Package_5009_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.mum from directory local source
In these extra examples, we see Package_xxxx_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.cat which means we need to download the .MSU of KB5014692.
In the first case, I needed to find a file that contained components for Package_for_DotNetRollup~31bf3856ad364e35~amd64~~ at version 10.0.3946.2, or perhaps later.
After some googling around, I knew that this was going to be a 20xx-xx Cumulative Update for .NET Framework 3.5 and 4.7.2 for Windows Server 2019 for x64, but I didn't really know which month would work.
If you have an update downloaded that you think might be a candidate, you can download it from https://www.catalog.update.microsoft.com/ and then view the contents of the .msu or .cab with 7-Zip or file-roller (linux). Inside the archive, there is a XML file that describes the components that reside within:
Bingo!
In this case, it turns out that 2022-05 Cumulative Update for .NET Framework 3.5 and 4.7.2 for Windows Server 2019 for x64 (KB5013641) was exactly the update I needed. I was able to find this after a bit of back-tracking through the update catalog until the numbers lined up.
The Install
Now that we had the update that should Fix It All (TM), we now had to install it.
If the world was a better place, perhaps you could just re-install the update with wusa <<updatefile>>.msu, but alas, because it was "already installed" this did not work.
Using an Update File as the source
Originally I had no luck specifying the exact source to allow DISM to perform the repair online, but luckily (?) I had another machine with more corruption (where the KB5014692 examples come from above), and I was able to find an online method of repair.
Conveniently, while messing around and attempting to repair using the /Source: argument, I was able to trigger the following:
2023-02-02 15:11:53, Info CBS Identity mismatch between package: \\?\C:\Windows\CbsTemp\31012565_543117373\update.mum and identity: Package_5008_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15 [HRESULT = 0x800f0818 - CBS_E_IDENTITY_MISMATCH] 2023-02-02 15:11:53, Info CBS Update.mum found from alternate source, but it is not for package Package_5008_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15 [HRESULT = 0x800f0818 - CBS_E_IDENTITY_MISMATCH] 2023-02-02 15:11:53, Info CBS Repr: Not able to find replacement manifests for package Package_5008_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15 from any local source 2023-02-02 15:11:53, Info CBS Exec: Not able to find Package_5009_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.mum from directory local source 2023-02-02 15:11:53, Info CBS Exec: Not able to find Servicing\Packages\Package_5009_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.mum from directory local source 2023-02-02 15:11:53, Info CBS Exec: Not able to find update.ses from directory local source 2023-02-02 15:11:53, Info CBS Exec: Not able to find Servicing\Packages\update.ses from directory local source
This looks an awful lot like CBS is checking a search path here, and seems to be looking for a few different files:
- \\?\C:\Windows\CbsTemp\31012565_543117373\update.mum
- Update.mum found from alternate source
- Package_5009_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.mum
- Servicing\Packages\Package_5009_for_KB5014692~31bf3856ad364e35~amd64~~10.0.2.15.mum
- update.ses
- Servicing\Packages\update.ses
We'll need to keep an eye out for these file names (particularly update.mum and update.ses) while we're poking around the update files.
If you use 7-Zip (or Windows Explorer) to open the KB5014692 update file, you'll find the following files:
The SSU-...cab is a Servicing Stack Update file, and in this case I didn't think we needed it, so I went straight to opening the Windows10.0-KB5014692-x64.cab file, containing the update specific files.
Opening that, we see
An update.cat and update.mum! I extracted and copied all of these files, but DISM didn't appear to read the files correctly. Since there was another CAB file there, I extracted that one...
Now this looks like a real update. We have another update.cat and update.mum, and three more CABs. Just to be thorough, I peeked inside one of these CABs:
That looks a lot like the Windows WinSxS folder! I also found something even more promising further down:
Perfect! I extracted all three of these CAB files, and didn't even bother copying them to the problematic server. I told DISM to use the source straight off the C$ share of the server I'd been using to poke around, along with the /LimitAccess argument to stop DISM from trying to download the files from Windows Update.
DISM /Online /Cleanup-Image /RestoreHealth /Source:\\server.domain\C$\folder\Windows10.0-KB5014692-v2-x64\Cab_1_for_KB5014692_PSFX /LimitAccess
Note: This command will still work for an offline repair, but you'll obviously need to substitute /Online for the appropriate flags.
(In this case, the destination of the /Source: argument contains the contents of the Cab_x_for... CABs, extracted out and combined into one folder.)
Finally, we can see that it's managed to repair all of the issues in the logs:
Offline Package Install
If you have no luck with the source extract method, or just want to try this way, read on.
Since I was running Windows Server 2019, I could not use DISM to apply the update directly to the running OS, but I could do it offline. https://learn.microsoft.com/en-us/windows-hardware/manufacture/desktop/add-or-remove-packages-offline-using-dism?view=windows-11
First I copied the file to the system - I found it easiest to download it using the running system using powershell.
$ProgressPreference = "SilentlyContinue" Invoke-WebRequest -UseBasicParsing https://catalog.s.download.windowsupdate.com/c/msdownload/update/software/secu/2022/04/windows10.0-kb5013641-x64_5cf245f52876a8a50a7155fada0245c6d0533bfb.msu -OutFile windows10.0-kb5013641-x64_5cf245f52876a8a50a7155fada0245c6d0533bfb.msu
I booted into the Windows RE environment (by triggering a hard-reset of the VM the moment the spinning dots showed up on the bootscreen, three times), loaded the SCSI driver, and installed the package:
Dism /Image:E: /Add-Package /PackagePath:C:\Users\NRoach44.DA\windows10.0-kb5013641-x64_5cf245f52876a8a50a7155fada0245c6d0533bfb.msu
It finished successfully after a few moments, and I rebooted the machine. It booted up OK, so I ran another /RestoreHealth...
... and it worked fine!
By far the hardest part of this was identifying the right update to download - I'm not sure if there's a better way (surely there is!) but hopefully a good method shows up at some point.
Addendum: From some initial poking around, it looks like the WSUSSCN2.CAB file, once fully extracted out, has some hits for the Package_for_DotNetRollup string, so if you get stuck, try looking in there for your Component ID.
Conclusion
I've come across DISM source issues a handful of times in my career, and it always bugged me that the tool was clearly stating what the problem was, but the documentation from Microsoft was so lacking that I couldn't give the tool the nudge it needed to fix everything. It was very satisfying to finally be able to fix DISM's component store properly, and restore this machine to fully functioning status!
As a side note, this VM lived on a host with very slow storage. Before doing any of this work, I copied it to my laptop with NVME storage - making all of this nice and quick. It would not surprise me to find out that the slow storage caused this 2022-05 update to fail to install, and then it's just been sitting there failing any updates since then.
Links
- https://www.catalog.update.microsoft.com/ - Windows Update Catalog - All (?) updates are downloadable from here
- https://learn.microsoft.com/en-us/windows-hardware/manufacture/desktop/add-or-remove-packages-offline-using-dism?view=windows-11 - How to use DISM offline to add "packages" to a Windows Image
- https://old.reddit.com/r/sysadmin/comments/fx8te9/i_had_to_pinch_myself_to_make_sure_i_wasnt/fmtdu9z/ - A comment I saved years ago for when I would need it - Walks through creating a Windows image with the updates, and then using it as a source.
- https://wvdvegt.wordpress.com/2020/09/03/dism-repairs-for-old-updates-still-requiring-reboot/ - Walks through extracting an update to use as a source