Home » DA » Scripting Win10 Image

My background is more on server technologies and hence inbox tools like PowerShell is more natural than using tools like MDT. For the script to prepare windows 10 image, here are my key objectives

  • It has to be smaller
    • install.esd instead of install.wim
    • ESD file of 64-bit windows 10, with May CU comes to 2.53 GB as compared to 3.18GB of default WIM of TH2.
  • It has to incorporate latest cumulative update
    • Component Clean-up with Base reset to ensure image size is optimal
  • Direct Access (DA) settings to be part of the installation so that if the system is outside corporate network it can still activated through KMS
    • On a DA configured system Windows, WindowsNT and WindowsFirewall hives under HKLM\SOFTWARE\Policies are exported and kept on the image to be applied post OS installation.
    • Root CA of internal PKI infra included as otherwise systems upgraded inside corporate network would not trust DA NLS server certificate and result in “Outside corporate network”. That would prevent them to access corporate resources except the ones part of DA exclusion list
    • SetupComplete.cmd to get these files and certificate installed through script on an un-customized OS image.
  • Prepare the ZIP file of the image apart from ISO file, windows 7 doesn’t have native capability to mount ISO file
# Path to windows 10 64-bit ISO image file
$windows10ISO_64 = "C:\Win10\Soft\SW_DVD5_WIN_ENT_10_1511_64BIT_English_MLF_X20-82288.ISO"
# Path to windows 10 64-bit latest cumulative patch
$windows10patch_64 =  'C:\Win10\cu\Cumulative Update for Windows 10 Version 1511 for x64-based Systems (KB3156421)\AMD64-all-windows10.0-kb3156421-x64_df611d19667c6936ee4a7f77da54801a6b87f275.msu'
# Path to odcimg for ISO creation, part of Win10 ADK
$OCDIMG = "C:\Program Files (x86)\Windows Kits\10\Assessment and Deployment Kit\Deployment Tools\amd64\Oscdimg\oscdimg.exe" 
# Directory containing DA registry files and rootca cert
$DARegfiles = “C:\Win10\DA”
# SetupComplete.cmd script 
$SetupCompletescript = “C:\Win10\Scripts\SetupComplete.cmd”
# Image creation directories
$imagebase = "C:\Win10\Image"
$mountdir = Join-Path $imagebase "mount64"
$ScratchDir = Join-Path $imagebase "ScratchDirectory"
$logfile = Join-Path $imagebase "win10-64bit-dism.log"
$date = get-date -Format ddMMyy
$64imagefoloder = Join-Path $imagebase "64_$date"
$DARegimagedir = Join-Path $mountdir "Windows\PkpnotesDAReg"
$winsetupdir = Join-Path $mountdir "Windows\Setup\Scripts"

if (Test-Path $logfile ) { Remove-Item $logfile }
if (Test-Path $64imagefoloder) {Remove-Item $64imagefoloder -Recurse -Force}

Mount-DiskImage -ImagePath $windows10ISO_64 -Access ReadOnly -StorageType ISO
$ISOmount = Get-DiskImage $windows10ISO_64
if ( $ISOmount.Attached -ne "True" ) { throw "Not able to mount the ISO file" }
$ISOdriveLetter = (Get-Volume -DiskImage $ISOmount).DriveLetter
$ISOdrive = $ISOdriveLetter + ":"
Copy-Item -Path $ISOdrive -Destination $64imagefoloder -Recurse
$BaseOSWIM = join-path $64imagefoloder "\sources\install.wim"
$baseoswimsave = "install64-"+$date+".wim"
$baseossave = join-path $imagebase $baseoswimsave
$BaseOSESD = join-path $64imagefoloder "\sources\install.esd"
Dismount-DiskImage -ImagePath $windows10ISO_64

Set-ItemProperty $BaseOSWIM -Name IsReadOnly -Value $false
$OSImgeInfo = Get-WindowsImage -ImagePath $BaseOSWIM -Index 1
$OSArch = $OSImgeInfo.Architecture
[string]$OSBuild = $OSImgeInfo.Build
if ($OSArch -eq 9 ) {
$ISOfileName = "Win10Ent-"+$OSBuild+"-64bit-DAnApr16CU.ISO"
$ZIPfileName = "Win10Ent-"+$OSBuild+"-64bit-DAnApr16CU.ZIP"
$ISOfile = Join-Path $imagebase $ISOfileName
$ZIPfile = Join-Path $imagebase $ZIPfileName
Else {
Write-Host "Please use 64-bit OS ISO file" -ForegroundColor Red

Mount-WindowsImage -Path $mountdir -ImagePath $BaseOSWIM -Index 1 -ScratchDirectory $ScratchDir -LogPath $logfile 
Add-WindowsPackage -PackagePath $windows10patch_64 -Path $mountdir -ScratchDirectory $ScratchDir -LogPath $logfile
DISM /image:$mountdir /Cleanup-Image /AnalyzeComponentStore
DISM /image:$mountdir /Cleanup-Image /StartComponentCleanup /ResetBase

mkdir $DARegimagedir
Copy-Item -Recurse $DARegfiles $DARegimagedir
mkdir $winsetupdir
Copy-Item $SetupCompletescript $winsetupdir

Write-Host "Saving the 64-bit image in original WIM format" -ForegroundColor Cyan
Dismount-WindowsImage -Path $mountdir -Save -CheckIntegrity -ScratchDirectory $ScratchDir
#Export-WindowsImage -CheckIntegrity -CompressionType recovery -SourceImagePath $BaseOSWIM -SourceIndex 1 -DestinationImagePath $BaseOSESD -LogPath $logfile -ScratchDirectory $ScratchDir
DISM.exe /Export-Image /SourceImageFile:$BaseOSWIM /SourceIndex:1 /DestinationImageFile:$BaseOSESD /Compress:recovery /CheckIntegrity

Set-ItemProperty -Path $BaseOSESD -Name IsReadOnly -Value $true
# Preserve the WIM file as ESD file doesn’t allow mounting for any modification into image.
move-Item $BaseOSWIM $baseossave

if (Test-Path $ISOfile) { Remove-Item $ISOfile }
if (Test-Path $ZIPfile) { Remove-Item $ZIPfile }

$BIOSbootcode = join-path $64imagefoloder "boot\etfsboot.com"
$UEFIbootcode = join-path $64imagefoloder "efi\microsoft\boot\efisys.bin"
$ODCIMFbootcode = "-m -o -u2 -udfver102 -bootdata:2#p0,e,b"+$BIOSbootcode+"#pEF,e,b"+$UEFIbootcode
$ODCIMFArgs = "$ODCIMFbootcode $64imagefoloder $ISOfile"
start -FilePath $OCDIMG -ArgumentList $ODCIMFArgs
Add-Type -assembly "system.io.compression.filesystem"
[io.compression.zipfile]::CreateFromDirectory($64imagefoloder, $ZIPfile, "Optimal", "false")

Content of the SetupComplete.cmd script

Start cmd.exe /c "Regedit /s C:\Windows\PkpnotesDAReg\Windows.reg"
Start cmd.exe /c "Regedit /s C:\Windows\PkpnotesDAReg\WindowsNT.reg"
Start cmd.exe /c "Regedit /s C:\Windows\PkpnotesDAReg\windowsfirewall.reg"
certutil -addstore root C:\Windows\PkpnotesDAReg\rootca.cer
sc config IKEEXT start= auto error= ignore
sc config PolicyAgent start= auto error= ignore
sc config iphlpsvc start= auto error= ignore
sc config MpsSvc start= auto error= ignore
sc config NcaSvc start= auto error= ignore


2 Replies to “Scripting Win10 Image”

  1. Jeevan Bisht says:

    This is a great article to read, i was not even aware of this until i read this.

    1. Prasanta Kumar Panda says:

      Glad to hear a comment like this from an expert like you Jeevan, certainly encouraging

Leave a Reply

Your email address will not be published. Required fields are marked *