Win10+ Setup Disk (Works with UEFI Secure Boot / BIOS / Install.wim over 4 GB)

Discussion in 'MDL Projects and Applications' started by rpo, Mar 18, 2019.

  1. MMIKEE

    MMIKEE MDL Senior Member

    Oct 6, 2012
    380
    361
    10
    You are correct and what I should have stated...

    Rufus has always worked well for me in creating MBR & GPT partitions on USB Flash Drives for subsequent OS Installations but I was mostly CURIOUS how this script worked and believe it's a viable option for interested users using NEWer W10 OS's = 1703+...

    I still suggest: Adding this LIMITATION to the OP so users with older OS's will not waste their time trying to utilize this script on those OS's...
    I wasted a lot of time TESTing all the versions / releases attempting to get it to work properly with LTSB-2016...
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  2. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,504
    1,514
    60
    @freddie-o
    script 1.8.1
    When you update the title, you have to update lines 21 and 43. Just replace line 43 by
    Code:
    $Form.Text=($pswindow.windowtitle -split " by:")[0]
    , so you change only line 21 for subsequent modifications.
    And delete line 18.
     
  3. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    #203 freddie-o, Sep 7, 2019
    Last edited: Sep 8, 2019
    Added "Supported Windows versions" to the OP.
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  4. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    #204 freddie-o, Sep 7, 2019
    Last edited: Sep 8, 2019
    Updated to v1.8.1
    Cleaned up the script and made some minor changes to the script and UI.

    Also added "Supported Windows versions" of the script to the OP.
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  5. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,504
    1,514
    60
    Suggestions introducing very lite changes.
    The title is moved to the cmd part of the script, it is easier to find for modification.
    The variable $ShortTitle contains the first part of the title. It is used for the gui display and for the popup messages.
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @title Windows Installation Disk v1.8.1 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]&color 1E
    @set "__ARGS__=%*" &powershell -noprofile -c "$ScriptPath='%~f0';iex(Get-Content($ScriptPath) -raw)" &exit/b
    #>
    #
    #   This script must be executed with admin privilege
    #
    #   Test Administrator privileges
    If (-NOT ([Security.Principal.WindowsPrincipal] [Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole] "Administrator"))
    {
        $uac_error="Elevating UAC for Administrator Privileges failed"
        #   The following test is to avoid infinite looping if elevating UAC for Administrator Privileges failed
        if ($env:__ARGS__ -eq $uac_error) {
        "$uac_error`r`nRight click on the script and select ""Run as administrator""`r`nPress Enter to exit..."|write-host;pause >$null;exit/b}
    #   Restart the script to get Administrator privileges and exit
                                                                                              
        Start-Process "$ScriptPath" $uac_error -Verb runAs; exit
    }
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    $pswindow.windowtitle = ([string]($pswindow.windowtitle -split "^.*  ")).trim() ; $ShortTitle=($pswindow.windowtitle -split " by: .*")[0]
    #
    Add-Type -AssemblyName System.Windows.Forms # Load the class System.Windows.Forms
    #
    Function Get-FileName
    {
    # Filebrowser dialog
    $FileBrowser = New-Object System.Windows.Forms.OpenFileDialog -Property @{
       Multiselect = $false # One file can be chosen
        Filter = 'ISO images (*.iso)|*.iso' # Select only iso files
    }
    IF ($FileBrowser.ShowDialog() -eq "Cancel"){Cancel}
    $FileBrowser.filename    # return the file name
    }
    $wshell=New-Object -ComObject Wscript.Shell
    #
    clear-host
    #
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the title and size of the window:
    $Form.Text=$ShortTitle
    $Form.Width=420 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    
    # Create a drop-down list and fill it
    $USBDiskList=New-Object System.Windows.Forms.ComboBox
    $USBDiskList.DropDownStyle=[System.Windows.Forms.ComboBoxStyle]::DropDownList;
    $USBDiskList.Location=New-Object System.Drawing.Point(20,45)
    $USBDiskList.Size=New-Object System.Drawing.Size(365,20)
    $USBDiskList.Font='Consolas,10'
    $Form.Controls.Add($SelectUSBDiskList)
    $USBDisks=@() # array with USB disk number
    $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    
    While (!$Disks) {
        if($wshell.Popup("Please plug in your USB disk then click ""OK"" to continue.",0,$ShortTitle,1+64) -eq 2){exit}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    $USBDisk=New-Object System.Windows.Forms.Label # Put the USB Disk label on the form
    $USBDisk.Location=New-Object System.Drawing.Point(20,25)
    $USBDisk.Text="USB Disk"
    $USBDisk.Font='Consolas,10'
    $USBDisk.Size=New-Object System.Drawing.Size(400,20)
    $Form.Controls.Add($USBDisk)
    
    $ISOImage=New-Object System.Windows.Forms.Label # Put the ISO Image label on the form
    $ISOImage.Location=New-Object System.Drawing.Point(20,90)
    $ISOImage.Font='Consolas,10'
    $ISOImage.Size=New-Object System.Drawing.Size(350,20)
    $ISOImage.text="ISO Image"
    $Form.Controls.Add($ISOImage)
    
    $ISOFile=New-Object System.Windows.Forms.Label # Put the ISO file name on the form
    $ISOFile.Location=New-Object System.Drawing.Point(20,110)
    $ISOFile.Text=" "
    $ISOFile.Font='Consolas,10'
    $ISOFile.Size=New-Object System.Drawing.Size(365,22)
    $ISOFile.Backcolor = [System.Drawing.Color]::White
    $ISOFile.BorderStyle = [System.Windows.Forms.BorderStyle]::Fixed3D
    $Form.Controls.Add($ISOFile)
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the Select ISO button on the form
    $SelectISOButton.Location=New-Object System.Drawing.Point(135,170)
    $SelectISOButton.Text="Select ISO"
    $SelectISOButton.Font='Consolas,10'
    $SelectISOButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($SelectISOButton)
    
    $CancelButton=New-Object System.Windows.Forms.Button # Put the Cancel button on the form
    $CancelButton.Location=New-Object System.Drawing.Point(265,170)
    $CancelButton.Text="Cancel"
    $CancelButton.Font='Consolas,10'
    $CancelButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($CancelButton)
    $CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel
    
    $CreateDiskButton=New-Object System.Windows.Forms.Button # Put the Create Disk button on the form
    $CreateDiskButton.Location=New-Object System.Drawing.Point(135,170)
    $CreateDiskButton.Text="Create Disk"
    $CreateDiskButton.Font='Consolas,10'
    $CreateDiskButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($CreateDiskButton)
    $CreateDiskButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
    
    $Form.Controls.Add($ISOImage)
    $Form.Controls.Add($ISOFile)
    $Form.Controls.Remove($CreateDiskButton)
    $SelectISOButton.Add_Click(
        {$Global:ImagePath = Get-FileName # get the iso image path with file browser dialog
         $ImagePath= Split-Path -Path $Global:ImagePath -leaf # extract filename and extension (iso)
         $ISOFile.Text = $ImagePath
         if (($ISOFile.Text).length -gt 44) {$ISOFile.Text = $ImagePath.PadRight(100," ").substring(0,43)+"..."}
         $Form.Controls.Remove($SelectISOButton)
         $Form.Controls.Add($CreateDiskButton)})
    Foreach ($USBDisk in $Disks) {
        $FriendlyName=($USBDisk.FriendlyName).PadRight(40," ").substring(0,39)
        $USBDisks+=$USBDisk.DiskNumber
        $USBDiskList.Items.Add(("{0,-39}{1:n2} GB" -f $FriendlyName,($USBDisk.Size/1GB)))|out-null
        $Partitions = Get-Partition | Where-Object { $_.DiskNumber -eq $USBDisk.DiskNumber}
        If ($Partitions) {
            Foreach ($Partition in $Partitions) {
            $Volumes=get-volume | Where-Object {$Partition.AccessPaths -contains  $_.path }
                Foreach ($Volume in $Volumes) {
                    $USBDisks+=$USBDisk.DiskNumber
                    $USBDiskList.Items.Add(("{0,-1}({1,1}:){2,-32}[{3:n2} GB]" -f " ", ($Partition.DriveLetter), $Volume.FileSystemLabel.PadRight(25," ").substring(0,25), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    #
    if ($form.ShowDialog() -eq "Cancel"){$wshell.Popup("The script was cancelled.",1,$ShortTitle,0+64) | Out-Null;exit}
    #
    # At this point the mounted USB disk and the iso image file path are defined
    #
    $USB=$USBDisks[$USBDiskList.SelectedIndex]
    #
    # Mount the image file if not already mounted and get the drive letter
    #
    #  Check if iso already mounted
        $ISO = (Get-DiskImage -ImagePath $ImagePath | Get-Volume).DriveLetter
    #    Mount iso
        IF (!$ISO) {Mount-DiskImage -ImagePath $ImagePath -StorageType ISO |out-null
        $ISO = (Get-DiskImage -ImagePath $ImagePath | Get-Volume).DriveLetter}
        $ISO=$ISO+":"
    if ($ISO -eq ":") {Cancel}
    #
    if($wshell.Popup("Warning! Your USB disk will be converted to MBR scheme, repartitioned and reformatted. All the data will be lost. `r`n`r`nAre you sure you want to continue?",0,$ShortTitle,4+48) -eq 7){DisMount-DiskImage -ImagePath $ImagePath;exit}
    Clear-Host
    #    Clear the USB stick
    Clear-Disk $usb -RemoveData -RemoveOEM -Confirm:$false
    set-disk $usb -partitionstyle mbr
    Stop-Service ShellHWDetection -erroraction silentlycontinue|out-null
    #    Create the fat32 boot partition
    $usbfat32=(New-Partition -DiskNumber $usb -Size  1GB -AssignDriveLetter | Format-Volume -FileSystem FAT32 -NewFileSystemLabel "BOOT").DriveLetter + ":"
    #    Create the ntfs intall partition
    $usbntfs=(New-Partition -DiskNumber $usb -UseMaximumSize -AssignDriveLetter -IsActive | Format-Volume -FileSystem NTFS -NewFileSystemLabel "INSTALL").DriveLetter + ":"
    Start-Service ShellHWDetection -erroraction silentlycontinue|out-null
    #
    robocopy $iso $usbntfs /e /xf $iso\boot\bcd $iso\efi\microsoft\boot\bcd
    robocopy $iso"\" $usbfat32"\" bootmgr bootmgr.efi
    robocopy $iso"\boot" $usbfat32"\boot" /e /xf $iso\boot\bcd
    robocopy $iso"\efi" $usbfat32"\efi" /e /xf $iso\efi\microsoft\boot\bcd
    robocopy $iso"\sources" $usbfat32"\sources" boot.wim
    
    Copy-Item $ISO"\boot\bcd" $env:temp -Force
    & bcdedit /store ($env:temp + "\bcd") /set '{default}' bootmenupolicy Legacy
    Set-ItemProperty -Path ($env:temp + "\bcd") -Name IsReadOnly -Value $true
    Copy-Item ($env:temp + "\bcd") $usbfat32"\boot\bcd" -Force
    Copy-Item ($env:temp + "\bcd") $usbntfs"\boot\bcd" -Force
    Copy-Item $ISO"\EFI\Microsoft\boot\bcd" $env:temp -Force
    & bcdedit /store ($env:temp + "\bcd") /set '{default}' bootmenupolicy Legacy
    Set-ItemProperty -Path ($env:temp + "\bcd") -Name IsReadOnly -Value $true
    Copy-Item ($env:temp + "\bcd") $usbfat32"\EFI\Microsoft\boot\bcd" -Force
    Copy-Item ($env:temp + "\bcd") $usbntfs"\EFI\Microsoft\boot\bcd" -Force
    remove-item ($env:temp + "\bcd") -force
    remove-item ($env:temp + "\bcd.*") -force
    # Eject the mounted iso image
    DisMount-DiskImage -ImagePath $ImagePath |out-null
    $wshell.Popup("The Windows Installation Disk completed successfully.",0,$ShortTitle,0+64) | Out-Null;exit
    
     
  6. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    Enabled visual styles but it only affects the "Form" not the "pop-ups"?

    Code:
    [System.Windows.Forms.Application]::EnableVisualStyles();
    
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  7. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,504
    1,514
    60
    I guess popup is not based upon .net framework.
     
  8. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    Figured it out
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @title Windows Installation Disk v1.8.2 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]
    @set "__ARGS__=%*" &powershell -noprofile -c "$ScriptPath='%~f0';iex(Get-Content($ScriptPath) -raw)" &exit/b
    #>
    #
    #   This script must be executed with admin privilege
    #
    #   Test Administrator privileges
    If (-NOT ([Security.Principal.WindowsPrincipal] [Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole] "Administrator"))
    {
        $uac_error="Elevating UAC for Administrator Privileges failed"
        #   The following test is to avoid infinite looping if elevating UAC for Administrator Privileges failed
        if ($env:__ARGS__ -eq $uac_error) {
        "$uac_error`r`nRight click on the script and select ""Run as administrator""`r`nPress Enter to exit..."|write-host;pause >$null;exit/b}
    #   Restart the script to get Administrator privileges and exit
                                                                                              
        Start-Process "$ScriptPath" $uac_error -Verb runAs; exit
    }
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    $pswindow.windowtitle = ([string]($pswindow.windowtitle -split "^.*  ")).trim() ; $ShortTitle=($pswindow.windowtitle -split " by: .*")[0]
    #
    Add-Type -AssemblyName System.Windows.Forms # Load the class System.Windows.Forms
    #
    Function Get-FileName
    {
    # Filebrowser dialog
    $FileBrowser = New-Object System.Windows.Forms.OpenFileDialog -Property @{
       Multiselect = $false # One file can be chosen
        Filter = 'ISO images (*.iso)|*.iso' # Select only iso files
    }
    IF ($FileBrowser.ShowDialog() -eq "Cancel"){Cancel}
    $FileBrowser.filename    # return the file name
    }
    $wshell=New-Object -ComObject Wscript.Shell
    #
    clear-host
    #
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the title and size of the window:
    $Form.Text=$ShortTitle
    $Form.Width=420 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    
    [System.Windows.Forms.Application]::EnableVisualStyles();
    
    # Create a drop-down list and fill it
    $USBDiskList=New-Object System.Windows.Forms.ComboBox
    $USBDiskList.DropDownStyle=[System.Windows.Forms.ComboBoxStyle]::DropDownList;
    $USBDiskList.Location=New-Object System.Drawing.Point(20,45)
    $USBDiskList.Size=New-Object System.Drawing.Size(365,20)
    $USBDiskList.Font='Consolas,10'
    $Form.Controls.Add($SelectUSBDiskList)
    $USBDisks=@() # array with USB disk number
    $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    
    While (!$Disks) {
        $Result=[System.Windows.Forms.MessageBox]::Show("Please plug in your USB disk first. `r`n`r`nClick OK to continue.","Plug in the USB disk","1","64")
            if ($result -eq 2) {Out-Null;exit}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    $USBDisk=New-Object System.Windows.Forms.Label # Put the USB Disk label on the form
    $USBDisk.Location=New-Object System.Drawing.Point(20,25)
    $USBDisk.Text="USB Disk"
    $USBDisk.Font='Consolas,10'
    $USBDisk.Size=New-Object System.Drawing.Size(400,20)
    $Form.Controls.Add($USBDisk)
    
    $ISOImage=New-Object System.Windows.Forms.Label # Put the ISO Image label on the form
    $ISOImage.Location=New-Object System.Drawing.Point(20,90)
    $ISOImage.Font='Consolas,10'
    $ISOImage.Size=New-Object System.Drawing.Size(350,20)
    $ISOImage.text="ISO Image"
    $Form.Controls.Add($ISOImage)
    
    $ISOFile=New-Object System.Windows.Forms.Label # Put the ISO file name on the form
    $ISOFile.Location=New-Object System.Drawing.Point(20,110)
    $ISOFile.Text=" "
    $ISOFile.Font='Consolas,10'
    $ISOFile.Size=New-Object System.Drawing.Size(365,22)
    $ISOFile.Backcolor = [System.Drawing.Color]::White
    $ISOFile.BorderStyle = [System.Windows.Forms.BorderStyle]::FixedSingle
    $Form.Controls.Add($ISOFile)
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the Select ISO button on the form
    $SelectISOButton.Location=New-Object System.Drawing.Point(135,170)
    $SelectISOButton.Text="Select ISO"
    $SelectISOButton.Font='Consolas,10'
    $SelectISOButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($SelectISOButton)
    
    $CancelButton=New-Object System.Windows.Forms.Button # Put the Cancel button on the form
    $CancelButton.Location=New-Object System.Drawing.Point(265,170)
    $CancelButton.Text="Cancel"
    $CancelButton.Font='Consolas,10'
    $CancelButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($CancelButton)
    $CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel
    
    $CreateDiskButton=New-Object System.Windows.Forms.Button # Put the Create Disk button on the form
    $CreateDiskButton.Location=New-Object System.Drawing.Point(135,170)
    $CreateDiskButton.Text="Create Disk"
    $CreateDiskButton.Font='Consolas,10'
    $CreateDiskButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($CreateDiskButton)
    $CreateDiskButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
    
    $Form.Controls.Add($ISOImage)
    $Form.Controls.Add($ISOFile)
    $Form.Controls.Remove($CreateDiskButton)
    $SelectISOButton.Add_Click(
        {$Global:ImagePath = Get-FileName # get the iso image path with file browser dialog
         $ImagePath= Split-Path -Path $Global:ImagePath -leaf # extract filename and extension (iso)
         $ISOFile.Text = $ImagePath
         if (($ISOFile.Text).length -gt 44) {$ISOFile.Text = $ImagePath.PadRight(100," ").substring(0,43)+"..."}
         $Form.Controls.Remove($SelectISOButton)
         $Form.Controls.Add($CreateDiskButton)})
    Foreach ($USBDisk in $Disks) {
        $FriendlyName=($USBDisk.FriendlyName).PadRight(40," ").substring(0,39)
        $USBDisks+=$USBDisk.DiskNumber
        $USBDiskList.Items.Add(("{0,-39}{1:n2} GB" -f $FriendlyName,($USBDisk.Size/1GB)))|out-null
        $Partitions = Get-Partition | Where-Object { $_.DiskNumber -eq $USBDisk.DiskNumber}
        If ($Partitions) {
            Foreach ($Partition in $Partitions) {
            $Volumes=get-volume | Where-Object {$Partition.AccessPaths -contains  $_.path }
                Foreach ($Volume in $Volumes) {
                    $USBDisks+=$USBDisk.DiskNumber
                    $USBDiskList.Items.Add(("{0,-1}({1,1}:){2,-32}[{3:n2} GB]" -f " ", ($Partition.DriveLetter), $Volume.FileSystemLabel.PadRight(25," ").substring(0,25), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    #
    if ($form.ShowDialog() -eq "Cancel"){exit}
    #
    # At this point the mounted USB disk and the iso image file path are defined
    #
    $USB=$USBDisks[$USBDiskList.SelectedIndex]
    #
    # Mount the image file if not already mounted and get the drive letter
    #
    #  Check if iso already mounted
        $ISO = (Get-DiskImage -ImagePath $ImagePath | Get-Volume).DriveLetter
    #    Mount iso
        IF (!$ISO) {Mount-DiskImage -ImagePath $ImagePath -StorageType ISO |out-null
        $ISO = (Get-DiskImage -ImagePath $ImagePath | Get-Volume).DriveLetter}
        $ISO=$ISO+":"
    if ($ISO -eq ":") {exit}
    #
    $Result=[System.Windows.Forms.MessageBox]::Show("WARNING! Your USB disk will be converted to MBR scheme, repartitioned and reformatted. `r`n`r`nAll partitions and data stored in the disk will be erased. `r`n`r`nAre you sure you want to continue?","Warning","4","48")
            if ($result -eq 7){DisMount-DiskImage -ImagePath $ImagePath;exit}
    Clear-Host
    #    Clear the USB stick
    Clear-Disk $usb -RemoveData -RemoveOEM -Confirm:$false
    set-disk $usb -partitionstyle mbr
    Stop-Service ShellHWDetection -erroraction silentlycontinue|out-null
    #    Create the fat32 boot partition
    $usbfat32=(New-Partition -DiskNumber $usb -Size  1GB -AssignDriveLetter | Format-Volume -FileSystem FAT32 -NewFileSystemLabel "BOOT").DriveLetter + ":"
    #    Create the ntfs intall partition
    $usbntfs=(New-Partition -DiskNumber $usb -UseMaximumSize -AssignDriveLetter -IsActive | Format-Volume -FileSystem NTFS -NewFileSystemLabel "INSTALL").DriveLetter + ":"
    Start-Service ShellHWDetection -erroraction silentlycontinue|out-null
    #
    robocopy $iso $usbntfs /e /xf $iso\boot\bcd $iso\efi\microsoft\boot\bcd
    robocopy $iso"\" $usbfat32"\" bootmgr bootmgr.efi
    robocopy $iso"\boot" $usbfat32"\boot" /e /xf $iso\boot\bcd
    robocopy $iso"\efi" $usbfat32"\efi" /e /xf $iso\efi\microsoft\boot\bcd
    robocopy $iso"\sources" $usbfat32"\sources" boot.wim
    
    Copy-Item $ISO"\boot\bcd" $env:temp -Force
    & bcdedit /store ($env:temp + "\bcd") /set '{default}' bootmenupolicy Legacy
    Set-ItemProperty -Path ($env:temp + "\bcd") -Name IsReadOnly -Value $true
    Copy-Item ($env:temp + "\bcd") $usbfat32"\boot\bcd" -Force
    Copy-Item ($env:temp + "\bcd") $usbntfs"\boot\bcd" -Force
    Copy-Item $ISO"\EFI\Microsoft\boot\bcd" $env:temp -Force
    & bcdedit /store ($env:temp + "\bcd") /set '{default}' bootmenupolicy Legacy
    Set-ItemProperty -Path ($env:temp + "\bcd") -Name IsReadOnly -Value $true
    Copy-Item ($env:temp + "\bcd") $usbfat32"\EFI\Microsoft\boot\bcd" -Force
    Copy-Item ($env:temp + "\bcd") $usbntfs"\EFI\Microsoft\boot\bcd" -Force
    remove-item ($env:temp + "\bcd") -force
    remove-item ($env:temp + "\bcd.*") -force
    # Eject the mounted iso image
    DisMount-DiskImage -ImagePath $ImagePath |out-null
    [System.Windows.Forms.MessageBox]::Show("The Windows Installation Disk completed successfully.","Complete")
    
    
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  9. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    This would be great if the Form had a progress bar.

    Code:
    # .Net methods for hiding/showing the console in the background
    Add-Type -Name Window -Namespace Console -MemberDefinition '
    [DllImport("Kernel32.dll")]
    public static extern IntPtr GetConsoleWindow();
    
    [DllImport("user32.dll")]
    public static extern bool ShowWindow(IntPtr hWnd, Int32 nCmdShow);
    '
    function Hide-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        #0 hide
        [Console.Window]::ShowWindow($consolePtr, 0)
    }
    Hide-Console
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  10. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    Updated to v1.8.2
    Enabled Visual Styles
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  11. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    #211 freddie-o, Sep 9, 2019
    Last edited: Sep 9, 2019
    EDIT: Made a few corrections and changes to v1.8.2 and replaced the script in the OP (again)
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  12. vigipirate

    vigipirate MDL Senior Member

    Feb 24, 2011
    402
    100
    10
    Hello
    thank you all for your work really great j uses the script not too much problem
    simply when i want to mount the boot.wim image impossible if you could edit the script because in dism it does not want to mount my boot image .wim
    The specified image does not exist in Windows Image Manager.
    First look in the Windows Image Manager for existing images.
    The DISM log file is located ... the location C: \ Windows \ Logs \ DISM \ dism.log
    Thanks for your help
     
  13. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,504
    1,514
    60
    My remarks concerning 1.8.2
    replace line 31 (because the Cancel function has been removed) by :
    IF ($FileBrowser.ShowDialog() -eq "Cancel"){[Environment]::Exit(0)}
    delete line 34
    replace lines 59-60 by :
    if([System.Windows.Forms.MessageBox]::Show("Please plug in your USB disk first.`n`nClick OK to continue.",$ShortTitle,"OKCancel","Information") -eq "Cancel") {exit}
    delete line 106
    delete lines 109-111
    lines 137-140 ???? what is that ???
    if($form.ShowDialog() -eq "Cancel") {[System.Windows.Forms.MessageBox]::Show("The script was cancelled.",$ShortTitle,"OK","Error")|out-Null;exit}
    replace lines 156-157 by :
    If([System.Windows.Forms.MessageBox]::Show("WARNING! Your USB disk will be converted to MBR scheme, repartitioned and reformatted.`n`nAll partitions and data stored in the disk will be erased.`r`n`r`nAre you sure you want to continue?",$ShortTitle,"YESNO","Warning") -eq "NO"){DisMount-DiskImage -ImagePath $ImagePath|Out-Null;exit}
    Replace lines 189-190 by :
    [System.Windows.Forms.MessageBox]::Show("The Windows Installation Disk completed successfully.",$ShortTitle,"OK","Information")|Out-Null;exit
    I don't understand your problem. The boot.wim is taken from the iso image you supply and copied without any modification in the two sources directories. Does your usb disk boot?
     
  14. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    Updated to v1.9
    Changed the name of script to "Win10 Installation Disk"
    Made corrections and modifications to the script.
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  15. Flipp3r

    Flipp3r MDL Guru

    Feb 11, 2009
    2,023
    977
    90
    Hi I just tried the v1.9 script.
    When I first ran it by clicking on the script through explorer, it prompted for admin, defaulted to the inserted usb key, let me choose the iso but quit without error when I continued.
    I then opened an admin cmd prompt & ran the script, no errors - all good.

    On the 1st page you have:
    I boot my usb key in uefi mode and got the progress bar so I guess your also setting "EFI\Microsoft\boot\bcd" to "bootmenupolicy Legacy" as well.
    Doesn't really matter though...
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  16. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    It's supposed to run as Admin without having to open a command prompt (Admin).
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  17. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,504
    1,514
    60
    Yes, you are right.
     
  18. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    Updated to v1.9.1
    Separated the "Select ISO" and "Create Disk" buttons so you still have opportunity to change your choice of ISO before creating the installation disk.
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  19. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,504
    1,514
    60
    This is exactly what i achieved in one of my previous scripts.
    In the meantime i worked on 1.9 :
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @title Win10 Installation Disk 1.9 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]
    @set "__ARGS__=%*" &powershell -noprofile -c "$ScriptPath='%~f0';iex((Get-Content($ScriptPath))  -join [char[]]10)" &exit/b
    #>
    #
    #   This script must be executed with admin privilege
    #
    #   Test Administrator privileges
    If (-NOT ([Security.Principal.WindowsPrincipal] [Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole] "Administrator"))
    {
        $uac_error="Elevating UAC for Administrator Privileges failed"
        #   The following test is to avoid infinite looping if elevating UAC for Administrator Privileges failed
        if ($env:__ARGS__ -eq $uac_error) {
        "$uac_error`r`nRight click on the script and select ""Run as administrator""`r`nPress Enter to exit..."|write-host;pause >$null;exit/b}
    #   Restart the script to get Administrator privileges and exit
                                                                                             
        Start-Process "$ScriptPath" $uac_error -Verb runAs; exit
    }
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    $pswindow.windowtitle = ([string]($pswindow.windowtitle -split "^.*  ")).trim() ; $ShortTitle=($pswindow.windowtitle -split " by: .*")[0]
    #
    Add-Type -AssemblyName System.Windows.Forms # Load the class System.Windows.Forms
    #
    Function Get-FileName
    {
    # Filebrowser dialog
    $FileBrowser = New-Object System.Windows.Forms.OpenFileDialog -Property @{
       Multiselect = $false # One file can be chosen
        Filter = 'ISO images (*.iso)|*.iso' # Select only iso files
    }
    IF ($FileBrowser.ShowDialog() -eq "Cancel"){[Environment]::Exit(0)}
    $FileBrowser.filename    # return the file name
    }
    #
    Function MsgBox {[System.Windows.Forms.MessageBox]::Show($Args[0],$ShortTitle,$Args[1],$Args[2])}
    #
    clear-host
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the title and size of the window:
    $Form.Text=$ShortTitle
    $Form.Width=420 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    $Form.ControlBox = $false
    $Form.SizeGripStyle = "Hide"
    [System.Windows.Forms.Application]::EnableVisualStyles();
    
    # Create a drop-down list and fill it
    $USBDiskList=New-Object System.Windows.Forms.ComboBox
    $USBDiskList.DropDownStyle=[System.Windows.Forms.ComboBoxStyle]::DropDownList;
    $USBDiskList.Location=New-Object System.Drawing.Point(20,45)
    $USBDiskList.Size=New-Object System.Drawing.Size(365,20)
    $USBDiskList.Font='Consolas,10'
    $Form.Controls.Add($SelectUSBDiskList)
    $USBDisks=@() # array with USB disk number
    $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    
    While (!$Disks) {
    if((MsgBox "Please plug in your USB disk first then click OK to continue." "OKCancel" "Information") -eq "Cancel") {exit}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    $USBDisk=New-Object System.Windows.Forms.Label # Put the USB Disk label on the form
    $USBDisk.Location=New-Object System.Drawing.Point(20,25)
    $USBDisk.Text="USB Disk"
    $USBDisk.Font='Default Font,9'
    $USBDisk.Size=New-Object System.Drawing.Size(400,20)
    $Form.Controls.Add($USBDisk)
    
    $ISOImage=New-Object System.Windows.Forms.Label # Put the ISO Image label on the form
    $ISOImage.Location=New-Object System.Drawing.Point(20,90)
    $ISOImage.Font='Default Font,9'
    $ISOImage.Size=New-Object System.Drawing.Size(350,20)
    $ISOImage.text="ISO Image"
    $Form.Controls.Add($ISOImage)
    
    $ISOFile=New-Object System.Windows.Forms.Label # Put the ISO file name on the form
    $ISOFile.Location=New-Object System.Drawing.Point(20,110)
    $ISOFile.Text=" "
    $ISOFile.Font='Consolas,10'
    $ISOFile.Size=New-Object System.Drawing.Size(365,20)
    $ISOFile.Backcolor = [System.Drawing.Color]::White
    $ISOFile.BorderStyle = [System.Windows.Forms.BorderStyle]::FixedSingle
    $Form.Controls.Add($ISOFile)
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the Select ISO button on the form
    $SelectISOButton.Location=New-Object System.Drawing.Point(150,170)
    $SelectISOButton.Text="Select ISO"
    $SelectISOButton.Font='Default Font,9'
    $SelectISOButton.Size=New-Object System.Drawing.Size(100,26)
    $Form.Controls.Add($SelectISOButton)
    
    $CancelButton=New-Object System.Windows.Forms.Button # Put the Cancel button on the form
    $CancelButton.Location=New-Object System.Drawing.Point(20,170)
    $CancelButton.Text="Cancel"
    $CancelButton.Font='Default Font,9'
    $CancelButton.Size=New-Object System.Drawing.Size(100,26)
    $Form.Controls.Add($CancelButton)
    $CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel
    
    $CreateDiskButton=New-Object System.Windows.Forms.Button # Put the Create Disk button on the form
    $CreateDiskButton.Location=New-Object System.Drawing.Point(285,170)
    $CreateDiskButton.Text="Create Disk"
    $CreateDiskButton.Font='Default Font,9'
    $CreateDiskButton.Size=New-Object System.Drawing.Size(100,26)
    $CreateDiskButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
    
    $SelectISOButton.Add_Click({
        $Global:ImagePath = Get-FileName # get the iso image path with file browser dialog
        $ImagePath= Split-Path -Path $Global:ImagePath -leaf # extract filename and extension (iso)
        $ISOFile.Text = $ImagePath
        if (($ISOFile.Text).length -gt 44) {$ISOFile.Text = $ImagePath.PadRight(100," ").substring(0,43)+"..."}
        $CreateDiskButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
        $Form.Controls.Add($CreateDiskButton)
        $CreateDiskButton.Focus()})
       
    Foreach ($USBDisk in $Disks) {
        $FriendlyName=($USBDisk.FriendlyName).PadRight(40," ").substring(0,39)
        $USBDisks+=$USBDisk.DiskNumber
        $USBDiskList.Items.Add(("{0,-39}{1:n2} GB" -f $FriendlyName,($USBDisk.Size/1GB)))|out-null
        $Partitions = Get-Partition | Where-Object { $_.DiskNumber -eq $USBDisk.DiskNumber}
        If ($Partitions) {
            Foreach ($Partition in $Partitions) {
            $Volumes=get-volume | Where-Object {$Partition.AccessPaths -contains  $_.path }
                Foreach ($Volume in $Volumes) {
                    $USBDisks+=$USBDisk.DiskNumber
                    $USBDiskList.Items.Add(("{0,-2}({1,1}:){2,-32}[{3:n2} GB]" -f " ", ($Partition.DriveLetter), $Volume.FileSystemLabel.PadRight(25," ").substring(0,25), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    #
    if($form.ShowDialog() -eq "Cancel") {MsgBox "The script was cancelled." "OK" "Error"|out-Null;exit}
    #
    # At this point the mounted USB disk and the iso image file path are defined
    #
    $USB=$USBDisks[$USBDiskList.SelectedIndex]
    #
    # Mount the image file if not already mounted and get the drive letter
    #
    #  Check if iso already mounted
        $ISO = (Get-DiskImage -ImagePath $ImagePath | Get-Volume).DriveLetter
    #    Mount iso
        If (!$ISO) {Mount-DiskImage -ImagePath $ImagePath -StorageType ISO |out-null
        $ISO = (Get-DiskImage -ImagePath $ImagePath | Get-Volume).DriveLetter}
        $ISO=$ISO+":"
    If ($ISO -eq ":") {exit}
    #
    If((MsgBox "WARNING! Your USB disk will be converted to MBR scheme, repartitioned and reformatted.`n`nAll partitions and data stored in the disk will be erased.`r`n`r`nAre you sure you want to continue?" "YESNO" "Warning") -eq "NO"){DisMount-DiskImage -ImagePath $ImagePath|Out-Null;exit}
    Clear-Host
    #    Clear the USB stick
    Clear-Disk $usb -RemoveData -RemoveOEM -Confirm:$false
    set-disk $usb -partitionstyle mbr
    Stop-Service ShellHWDetection -erroraction silentlycontinue|out-null
    #    Create the fat32 boot partition
    $usbfat32=(New-Partition -DiskNumber $usb -Size  1GB -AssignDriveLetter | Format-Volume -FileSystem FAT32 -NewFileSystemLabel "BOOT").DriveLetter + ":"
    #    Create the ntfs intall partition
    $usbntfs=(New-Partition -DiskNumber $usb -UseMaximumSize -AssignDriveLetter -IsActive | Format-Volume -FileSystem NTFS -NewFileSystemLabel "INSTALL").DriveLetter + ":"
    Start-Service ShellHWDetection -erroraction silentlycontinue|out-null
    #
    robocopy $iso $usbntfs /e /xf $iso\boot\bcd $iso\efi\microsoft\boot\bcd
    robocopy $iso"\" $usbfat32"\" bootmgr bootmgr.efi
    robocopy $iso"\boot" $usbfat32"\boot" /e /xf $iso\boot\bcd
    robocopy $iso"\efi" $usbfat32"\efi" /e /xf $iso\efi\microsoft\boot\bcd
    robocopy $iso"\sources" $usbfat32"\sources" boot.wim
    
    Copy-Item $ISO"\boot\bcd" $env:temp -Force
    & bcdedit /store ($env:temp + "\bcd") /set '{default}' bootmenupolicy Legacy
    Set-ItemProperty -Path ($env:temp + "\bcd") -Name IsReadOnly -Value $true
    Copy-Item ($env:temp + "\bcd") $usbfat32"\boot\bcd" -Force
    Copy-Item ($env:temp + "\bcd") $usbntfs"\boot\bcd" -Force
    Copy-Item $ISO"\EFI\Microsoft\boot\bcd" $env:temp -Force
    & bcdedit /store ($env:temp + "\bcd") /set '{default}' bootmenupolicy Legacy
    Set-ItemProperty -Path ($env:temp + "\bcd") -Name IsReadOnly -Value $true
    Copy-Item ($env:temp + "\bcd") $usbfat32"\EFI\Microsoft\boot\bcd" -Force
    Copy-Item ($env:temp + "\bcd") $usbntfs"\EFI\Microsoft\boot\bcd" -Force
    remove-item ($env:temp + "\bcd") -force
    remove-item ($env:temp + "\bcd.*") -force
    # Eject the mounted iso image
    DisMount-DiskImage -ImagePath $ImagePath |out-null
    MsgBox "The installation disk completed successfully." "OK" "Information" |Out-Null;exit

    The main modifications :
    Created a MsgBox function and changed the script accordlingly.
    Put the Cancel button to the left down corner
    Put focus on the create disk button
     
  20. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,605
    2,676
    60
    The Cancel button used to be in the left corner but I moved it to the right corner because generally all UIs have it in the right corner. I'll update the script in the OP.
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...