Outcome after Windows 11 24H2 install:
fsutil 8dot3name scan /s C:
Total affected registry keys: 40
files & directories scanned: 163804
found: 0
To get this result requires an install.wim without 8dot3 names, and timely use of
fsutil.exe behavior set disable8dot3 1
fsutil.exe 8dot3name set C: 1
Note: Some of the wide, unbroken pre-formatted lines below do not display well in this web page. To see them better, hightlight all, copy, and paste into text editor, e.g., Notepad++.
Preparation and Windows Install Steps:
Step 0: Obtain ISO and install.wim
Obtain Windows Install ISO from trusted source, e.g., Microsoft. Extract sources/install.wim from ISO with unzip program, e.g., 7Zip. From this original install.wim, extract parts if wanted, e.g., only Pro, only Pro N, Home and Pro.
Example to extract just Pro N:
dism /Get-WimInfo /WimFile:"Z:\wims\oem\install.wim" dism /Export-Image /SourceImageFile:"Z:\wims\oem\install.wim" /SourceIndex:7 /DestinationImageFile:"C:\temp\pro_n\install.wim"
Step 1: Prepare wim file:
Note 0: This is the only step where stripping 8dot3name is performed.
Note 1: Removing the 8dot3 names from the wim file is necessary, else the installed files will not be free of 8dot3 names, despite other steps later.
Note 2: This example includes sideloading Windows Updates. Edit Updates_List.txt as wanted, e.g., empty for no updates.
For more info on sideloading Windows Updates, RTFM the DISM docs, and do not follow incomplete instructions from web searches.
https://learn.microsoft.com/en-us/windows-hardware/manufacture/desktop/dism-operating-system-package-servicing-command-line-options?view=windows-11 https://learn.microsoft.com/en-us/windows-hardware/manufacture/desktop/add-or-remove-packages-offline-using-dism?view=windows-11Note 3: Contents of my Updates_List.txt:
cumulative\windows11.0-kb5053598-x64_6cb3ffc5c4d652793dc71705248426eecdacdfd0.msu cumulative_.net\windows11.0-kb5049622-x64-ndp481_afb8c71d1958d98de4082ff732762242e9460fad.msuNote: Dependency in folder Updates\cumulative\ but not listed in Updates_List.txt:
windows11.0-kb5043080-x64_953449672073f8fb99badb4cc6d5d7849b9c83e8.msu
Updates downloaded from Windows Catalog:
24H2 x64 -Preview https://catalog.update.microsoft.com/Search.aspx?q=24h2+x64+-preview&scol=DateComputed&sdir=desc Cumulative Windows 11 x64 -Preview https://catalog.update.microsoft.com/Search.aspx?q=cumulative+windows+11+x64+-preview&scol=DateComputed&sdir=desc Cumulative .NET Windows 11 x64 -Preview https://catalog.update.microsoft.com/Search.aspx?q=cumulative+.net+windows+11+x64+-preview&scol=DateComputed&sdir=desc https://learn.microsoft.com/en-us/windows/release-health/windows11-release-informationThe following scripts are modifications of works by https://schneegans.de and https://github.com/memstechtips.
Wim-Add-Updates-and-Strip-8dot3names.ps1:
# Note: Requires elevated privileges to run.
# Note: Before first use, maybe need to call PsExec.exe/PsExec64.exe manually to accept eula.
#
# https://answers.microsoft.com/en-us/windows/forum/all/remove-multiple-indexes-with-dism/b57d2169-47a2-41f6-b667-af2c8ef44b06
#
# https://www.xda-developers.com/integrate-updates-windows-11-iso/
# https://woshub.com/add-updates-into-windows-image/
# https://woshub.com/integrate-drivers-to-windows-install-media/
#
# https://learn.microsoft.com/en-us/windows/deployment/customize-boot-image?tabs=powershell#step-12-export-boot-image-to-reduce-size
#
# https://schneegans.de/windows/no-8.3/
# https://learn.microsoft.com/de-de/archive/blogs/josebda/windows-server-2012-file-server-tip-disable-8-3-naming-and-strip-those-short-names-too
#
function Wim-Add-Updates-and-Strip-8dot3names {
[CmdletBinding()]
param(
[Parameter( Mandatory )]
[string]
$WimFile,
[Parameter( Mandatory )]
[string]
$UpdatesList,
[Parameter( Mandatory )]
[string]
$UpdatesDir,
[Parameter( Mandatory )]
[string]
$TempMountDirectory,
[ValidateSet( 'Errors', 'Warnings', 'WarningsInfo' )]
[string]
$LogLevel = 'Errors',
[Parameter( Mandatory )]
[string]
$PsExecPath,
[string]
$Dism = "$env:windir\system32\Dism.exe",
[string]
$fsutil = "$env:windir\system32\fsutil.exe",
[Parameter( Mandatory )]
[string]
$TempWimDirectory
);
$ErrorActionPreference = "Stop";
$RequiredInput = @($WimFile, $PsExecPath, $Dism, $fsutil, $UpdatesList);
$RequiredInput.ForEach( {
if( -not [System.IO.File]::Exists( $_ ) ) {
throw "'$_' not found.";
}
} );
$params = @{
LogLevel = $LogLevel;
};
Write-Output $(Get-Date -Format u);
dir -Path $WimFile;
& $PsExecPath -accepteula -nobanner -s $Dism /Get-WimInfo /WimFile:$WimFile;
& $PsExecPath -accepteula -nobanner -s $Dism /Get-WimInfo /WimFile:$WimFile /Index:1;
if( $LASTEXITCODE ) {
throw "exited with error code $LASTEXITCODE.";
};
$TempDirs = @($TempMountDirectory, $TempWimDirectory);
$TempDirs.ForEach( {
if (Test-Path -Path "$_") {
throw "$_ should not already exist.";
};
New-Item -Path "$_" -Type Directory;
} );
Get-WindowsImage -ImagePath $WimFile @params | ForEach-Object -Process {
Write-Output $(Get-Date -Format u);
Write-Output ("Processing edition '{0}'. Mounting to '{1}'." -f $_.ImageName, $TempMountDirectory);
Mount-WindowsImage -Path $TempMountDirectory -ImagePath $WimFile -Name $_.ImageName @params;
Write-Output $(Get-Date -Format u);
Write-Output "Adding updates...";
& $PsExecPath -accepteula -nobanner -s $Dism /Image:$TempMountDirectory /Get-Packages /Format:Table;
$UpdateFiles = Get-Content -Path $UpdatesList;
$UpdateFiles.ForEach( {
Write-Output $(Get-Date -Format u);
$UpdateFile = "$UpdatesDir\$_";
Write-Output ("Processing Update: '{0}'" -f $UpdateFile);
& $PsExecPath -accepteula -nobanner -s $Dism /Image:$TempMountDirectory /Add-Package /PackagePath:$UpdateFile;
if( $LASTEXITCODE ) {
throw "exited with error code $LASTEXITCODE.";
};
Write-Output $(Get-Date -Format u);
& $PsExecPath -accepteula -nobanner -s $Dism /Image:$TempMountDirectory /Get-Packages /Format:Table;
} );
Write-Output ("Stripping 8dot3names in '{0}'..." -f $TempMountDirectory);
& $PsExecPath -accepteula -nobanner -s $fsutil 8dot3name strip /f /s "$TempMountDirectory";
if( $LASTEXITCODE ) {
throw "exited with error code $LASTEXITCODE.";
};
& $PsExecPath -accepteula -nobanner -s $fsutil 8dot3name scan /s "$TempMountDirectory";
Write-Output $(Get-Date -Format u);
Dismount-WindowsImage -Path $TempMountDirectory -Save @params;
Write-Output $(Get-Date -Format u);
};
Remove-Item -LiteralPath "$TempMountDirectory" -Force;
& $PsExecPath -accepteula -nobanner -s $Dism /Get-WimInfo /WimFile:$WimFile;
& $PsExecPath -accepteula -nobanner -s $Dism /Get-WimInfo /WimFile:$WimFile /Index:1;
if( $LASTEXITCODE ) {
throw "exited with error code $LASTEXITCODE.";
};
Write-Output $(Get-Date -Format u);
$WimFileExported = "$TempWimDirectory\$(Split-Path $WimFile -Leaf)";
Write-Output ("Compressing '{0}' to '{1}'..." -f $WimFile, $WimFileExported);
Export-WindowsImage -SourceImagePath $WimFile -DestinationImagePath $WimFileExported -CompressionType max -Verbose;
Remove-Item -LiteralPath "$WimFile" -Force;
Move-Item -LiteralPath "$WimFileExported" -Destination "$WimFile" -Force;
Remove-Item -LiteralPath "$TempWimDirectory" -Force;
Write-Output $(Get-Date -Format u);
$WimDirectory = Split-Path -Path "$WimFile";
$WimExtension = [System.IO.Path]::GetExtension($WimFile)
Set-Location "$WimDirectory";
$FinalWimFiles = Get-ChildItem -Path "$WimDirectory" -Name "*$WimExtension" -File;
$FinalWimFiles.ForEach( {
Write-Output ("Hashing '{0}'..." -f $_);
dir -Path $_;
$WimFileHash = Get-FileHash -Algorithm SHA256 -Path $_ | % {$_.Hash + " " + (Resolve-Path -Path $_.Path -Relative)};
$WimFileHashStream = [System.IO.StreamWriter]::new("$WimDirectory\$_.SHA256.txt");
$WimFileHashStream.WriteLine($WimFileHash);
$WimFileHashStream.Close();
} );
Write-Output $(Get-Date -Format u);
Write-Output "FINI";
};
$config = @{
WimFile="$(Get-Location)\Win11_24H2_26100.1742_oem_pro\install.wim";
UpdatesList="$(Get-Location)\Updates_List.txt";
UpdatesDir="$(Get-Location)\Updates\";
TempMountDirectory="Z:\mnt";
TempWimDirectory="Z:\TempWim";
PsExecPath="C:\tools\SysinternalsSuite\PsExec64.exe";
};
Wim-Add-Updates-and-Strip-8dot3names @config `
| Tee-Object -FilePath "$(Get-Location)\Wim-Add-Updates-and-Strip-8dot3names--pro.log" -Append
Step 2: Create ISO:
Note: The "sourceroot" contains all contents from original OEM ISO, with sources/install.wim replaced with the one created in previous step.bootOrder.txt contents:
boot\bcd boot\boot.sdi boot\bootfix.bin boot\bootsect.exe boot\etfsboot.com boot\memtest.exe boot\en-us\bootsect.exe.mui boot\fonts\chs_boot.ttf boot\fonts\cht_boot.ttf boot\fonts\jpn_boot.ttf boot\fonts\kor_boot.ttf boot\fonts\wgl4_boot.ttf sources\boot.wimCreate-ISO.ps1:
# Note: Requires elevated privileges to run.
#
# https://learn.microsoft.com/en-us/windows-hardware/manufacture/desktop/oscdimg-command-line-options?view=windows-11
# https://github.com/memstechtips/WIMUtil/blob/main/src/WIMUtil.ps1
function Create-ISO {
[CmdletBinding()]
param(
[Parameter( Mandatory )]
[string]
$PsExecPath,
[Parameter( Mandatory )]
[string]
$oscdimg,
[Parameter( Mandatory )]
[string]
$isoVolumeLabel,
[Parameter( Mandatory )]
[string]
$BootOrderFile,
[Parameter( Mandatory )]
[string]
$sourceroot,
[Parameter( Mandatory )]
[string]
$targetfile
);
$ErrorActionPreference = "Stop";
$RequiredInput = @($PsExecPath, $oscdimg, $BootOrderFile);
$RequiredInput.ForEach( {
if( -not [System.IO.File]::Exists( "$_" ) ) {
throw "'$_' not found.";
}
} );
Write-Output $(Get-Date -Format u);
$targetroot = Split-Path -Path "$targetfile";
if (-not(Test-Path $targetroot -PathType Container)) {
New-Item -path $targetroot -ItemType Directory;
};
# Set-Location "$targetroot";
$etfsboot = "$sourceroot\boot\etfsboot.com";
$efisys = "$sourceroot\efi\microsoft\boot\efisys.bin";
& $PsExecPath -accepteula -nobanner -s "$oscdimg" -m -o -g -h -u2 -udfver102 -l"$isoVolumeLabel" -yo"$BootOrderFile" -bootdata:2#p0,e,b"$etfsboot"#pEF,e,b"$efisys" "$sourceroot" "$targetfile";
dir -Path "$targetfile";
$isoFileHash = Get-FileHash -Algorithm SHA256 -Path "$targetfile" | % {$_.Hash + " " + (Resolve-Path -Path $_.Path -Relative)};
$isoFileHashStream = [System.IO.StreamWriter]::new("$targetfile.SHA256.txt");
$isoFileHashStream.WriteLine($isoFileHash);
$isoFileHashStream.Close();
Write-Output $(Get-Date -Format u);
Write-Output "FINI";
};
$config = @{
sourceroot = "$(Get-Location)\oem_iso";
targetfile = "Z:\temp\created_iso\Win11P_24H2_20250311_en-us_x64.iso";
PsExecPath = "C:\tools\SysinternalsSuite\PsExec64.exe";
oscdimg = "C:\Program Files (x86)\Windows Kits\10\Assessment and Deployment Kit\Deployment Tools\amd64\Oscdimg\oscdimg.exe";
isoVolumeLabel = "W11P_3476";
BootOrderFile = "$(Get-Location)\bootOrder.txt";
};
Create-ISO @config `
| Tee-Object -FilePath "$(Get-Location)\Create-ISO--pro.log" -Append
Note: Keep the length of the isoVolumeLabel to just 11 characters, if preferred.Step 3: Prepare notautounattend.xml
Generate schneegans.de notautounattend.xml with at least these two commands in the section, "Scripts to run in the system context, before user accounts are created":
fsutil.exe 8dot3name set C: 1
fsutil.exe behavior set disable8dot3 1
The first command might not be necessary, but it does not hurt, the second command is necessary.
Note: USB device with notautounattend.xml attached and automatically mounted as C:. After reboot, Windows Setup will re-label volumes.
Step 4: Windows Install:
Note: This does not work in full unattend mode with autounattend.xml. The "Previous Version of Setup" is required.
At Screen: Select setup option: Select "Previous Version of Setup".
At Screen: Windows Setup > Language, Local, Input...
Either of these work, depending on other needs:
X:\sources\setup.exe /Unattend:C:\notautounattend.xml
Or:
X:\sources\setup.exe /NoReboot /Unattend:C:\notautounattend.xml
If using /NoReboot:
Back at Screen: Windows Setup > Language, Local, Input...
X:\Windows\System32\wpeutil.exe reboot
After setup reboot finishes, first boot and first logon scripts run.
Confirmed 8dot3 disabled:
fsutil 8dot3name query C:
fsutil 8dot3name scan /s C:
Total affected registry keys: 40
files & directories scanned: 163804
found: 0