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

Discussion in 'Scripting' started by freddie-o, Mar 21, 2019.

  1. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,358
    2,267
    60
    Updated
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @title Windows Installation Disk v1.7 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
    }
    $Env:ScriptPath=""; $Env:ScriptPath=""  # delete environment variables
    #
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    # $newsize = $pswindow.buffersize   # set the buffer size
    # $newsize.height = 3000            # 3000 lines
    # $newsize.width = 150                # 150 characters
    # $pswindow.buffersize = $newsize    # set the BufferSize properties
    # $newsize = $pswindow.buffersize   # assign the BufferSize properties to a variable named $newsize
    # $pswindow.buffersize = $newsize    # assign the values to the actual console window
    # $newsize = $pswindow.windowsize    # set the window size
    # $newsize.height = [Math]::Min(50, $host.ui.rawui.MaxWindowSize.height)
    # $newsize.width = [Math]::Min(150, $host.ui.rawui.MaxWindowSize.Width)
    # $pswindow.windowsize = $newsize
    $pswindow.windowtitle = "Windows Installation Disk v1.7 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    [console]::ForegroundColor = "yellow"
    [console]::BackgroundColor = "blue"
    #
    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
       title="Select ISO image"
    #   ShowHelp = $True
        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
    #
    # .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);
    '
    # Hide = 0,
    # ShowNormal = 1,
    # ShowMinimized = 2,
    # ShowMaximized = 3,
    # Maximize = 3,
    # ShowNormalNoActivate = 4,
    # Show = 5,
    # Minimize = 6,
    # ShowMinNoActivate = 7,
    # ShowNoActivate = 8,
    # Restore = 9,
    # ShowDefault = 10,
    # ForceMinimized = 11
    #
    function Show-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 1)
    }
    function Hide-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 0)
    }
    Function Cancel
    {
        [Environment]::Exit(1)
    }
    clear-host
    #
    $Global:ImagePath=""
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the size of the window:
    # $Form.FormBorderStyle = "none"
    $Form.ControlBox = $True
    $Form.Text="Windows Installation Disk v1.7"
    $Form.Width=450 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    $Form.AutoSize=$true # AutoSize property to make the form automatically stretch, if the elements on the form are out of bounds
    $Form.KeyPreview = $True
    $Form.Add_KeyDown({if ($_.KeyCode -eq "Enter"){$OKButton.PerformClick()}})         # Enter = click OK button
    $Form.Add_KeyDown({if ($_.KeyCode -eq "Escape"){$CancelButton.PerformClick()}})    # Escape = click on Cancel button
    $Form.BackColor = "#232323"
    
    $OKButton=New-Object System.Windows.Forms.Button # Put the OK button on the form
    $OKButton.Location=New-Object System.Drawing.Point(315,170)
    $OKButton.Text="OK"
    $OKButton.Font='Courier New,9'
    $OKButton.Size=New-Object System.Drawing.Size(100,25)
    # $OKButton.Size=New-Object System.Drawing.Size(125,20)
    $OKButton.ForeColor = [System.Drawing.Color]::White
    $OKButton.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    $Form.Controls.Add($OKButton)
    $OKButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
    
    $SelectUSBDisk=New-Object System.Windows.Forms.Label # Put the SelectUSBDisk label on the form
    $SelectUSBDisk.Location=New-Object System.Drawing.Point(20,25)
    $SelectUSBDisk.Font='Courier New,9'
    $SelectUSBDisk.Size=New-Object System.Drawing.Size(350,20)
    $SelectUSBDisk.ForeColor = [System.Drawing.Color]::White                       
    $Form.Controls.Add($SelectUSBDisk)
    
    $SelectISO=New-Object System.Windows.Forms.Label # Put the SelectISO label on the form
    $SelectISO.Location=New-Object System.Drawing.Point(20,90)
    $SelectISO.Font='Courier New,9'
    $SelectISO.Size=New-Object System.Drawing.Size(350,20)
    $SelectISO.text="Select ISO image:"
    $SelectISO.ForeColor = [System.Drawing.Color]::White                                                                 
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the SelectISO button on the form
    $SelectISOButton.Location=New-Object System.Drawing.Point(375,110)
    $SelectISOButton.Text="..."
    $SelectISOButton.Font='Courier New,9'
    $SelectISOButton.Size=New-Object System.Drawing.Size(40,22)
    # $SelectISOButton.Size=New-Object System.Drawing.Size(40,22)
    $SelectISOButton.ForeColor = [System.Drawing.Color]::White                                                 
    $SelectISOButton.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    
    $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='Courier New,9'
    $ISOFile.Size=New-Object System.Drawing.Size(350,22)
    $ISOFile.Backcolor = [System.Drawing.Color]::White
    $ISOFile.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat   
    
    $Warning=New-Object System.Windows.Forms.Label # Put the Warning label on the form
    $Warning.Location=New-Object System.Drawing.Point(20,30)
    $Warning.Font='Courier New,9'
    $Warning.Size=New-Object System.Drawing.Size(380,80)
    $Warning.text="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?"
    $Warning.ForeColor = [System.Drawing.Color]::White
    #
    #    Select the USB disk
    # Create a drop-down list and fill it
    $USBDiskList=New-Object System.Windows.Forms.ComboBox
    $USBDiskList.DropDownStyle=[System.Windows.Forms.ComboBoxStyle]::DropDownList;
    $USBDiskList.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    $USBDiskList.Location=New-Object System.Drawing.Point(20,45)
    $USBDiskList.Size=New-Object System.Drawing.Size(395,20)
    $USBDiskList.Font='Courier New,9'
    $Form.Controls.Add($SelectUSBDiskList)
    $USBDisks=@() # array with USB disk number
    $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    Hide-Console # Hide console display
    
    $Complete=New-Object System.Windows.Forms.Label # Put the Complete label on the form
    $Complete.Location=New-Object System.Drawing.Point(20,30)
    $Complete.Font='Courier New,9'
    $Complete.Size=New-Object System.Drawing.Size(400,40)
    $Complete.text="The Windows Installation Disk completed successfully."
    $Complete.ForeColor = [System.Drawing.Color]::White
    #                                                                                   
    While (!$Disks) {
        $SelectUSBDisk.Text="Please plug in your USB disk."
        if ($form.ShowDialog() -eq "Cancel"){cancel}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    
    $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='Courier New,9'
    $CancelButton.Size=New-Object System.Drawing.Size(100,25)
    # $CancelButton.Size=New-Object System.Drawing.Size(120,20)
    $CancelButton.ForeColor = [System.Drawing.Color]::White
    $CancelButton.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    $Form.Controls.Add($CancelButton)
    # $CancelButton.Add_Click({$Form.Close();cancel})
    $CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel
    
    $Form.Controls.Add($SelectISO)
    $Form.Controls.Add($ISOFile)
    $Form.Controls.Remove($OKButton)
    $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)+"..."}
         $OKButton.Text="Create disk"
         $Form.Controls.Add($OKButton)})
     
    Foreach ($USBDisk in $Disks) {
        $FriendlyName=($USBDisk.FriendlyName).PadRight(40," ").substring(0,40)
        $USBDisks+=$USBDisk.DiskNumber
        $USBDiskList.Items.Add(("{0,-44}{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,-38}[{3:n2} GB]" -f " ", ($Partition.DriveLetter), $Volume.FileSystemLabel.PadRight(30," ").substring(0,30), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    
    $SelectUSBDisk.Text="Select USB disk:"
    #
    $Form.Controls.Add($SelectISOButton)
    #
    if ($form.ShowDialog() -eq "Cancel") {Cancel}
    #
    # 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
    #
    if (ImagePath -eq ""){Cancel} # this can't happen, but keep the test
    #  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}
    #
    # Ready to create the USB disk. Ask for confirmation
    #
    $Form.Controls.Remove($USBDiskList)
    $Form.Controls.Remove($SelectUSBDisk)
    $Form.Controls.Remove($SelectISOButton)
    $Form.Controls.Remove($ISOFile)
    $Form.Controls.Remove($SelectISO)
    $OKButton.Text="Yes"
    $CancelButton.Text="No"
    $Form.Controls.Add($OKButton)
    $Form.Controls.Add($Warning)
    if ($form.ShowDialog() -eq "Cancel") {DisMount-DiskImage -ImagePath $ImagePath |out-null;Cancel}
    Clear-Host
    $pswindow.windowtitle = "Windows Installation Disk v1.7 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    Show-Console | Out-Null # Restore console display
    #    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
    #
    $Form.Controls.Remove($USBDiskList)
    $Form.Controls.Remove($SelectUSBDisk)
    $Form.Controls.Remove($SelectISOButton)
    $Form.Controls.Remove($OKButton)
    $Form.Controls.Remove($ISOFile)
    $Form.Controls.Remove($SelectISO)
    $Form.Controls.Remove($Warning)
    $CancelButton.Text="Close"
    $Form.Controls.Add($CancelButton)
    $Form.Controls.Add($Complete)
    if ($form.ShowDialog() -eq "Cancel") {Cancel}
    
    
     
  2. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    60
    Still garbage at the end of the script.
     
  3. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,358
    2,267
    60
    I think we'll go with this
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @title Windows Installation Disk v1.7 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
    }
    $Env:ScriptPath=""; $Env:ScriptPath=""  # delete environment variables
    #
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    # $newsize = $pswindow.buffersize   # set the buffer size
    # $newsize.height = 3000            # 3000 lines
    # $newsize.width = 150                # 150 characters
    # $pswindow.buffersize = $newsize    # set the BufferSize properties
    # $newsize = $pswindow.buffersize   # assign the BufferSize properties to a variable named $newsize
    # $pswindow.buffersize = $newsize    # assign the values to the actual console window
    # $newsize = $pswindow.windowsize    # set the window size
    # $newsize.height = [Math]::Min(50, $host.ui.rawui.MaxWindowSize.height)
    # $newsize.width = [Math]::Min(150, $host.ui.rawui.MaxWindowSize.Width)
    # $pswindow.windowsize = $newsize
    $pswindow.windowtitle = "Windows Installation Disk v1.7 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    [console]::ForegroundColor = "yellow"
    [console]::BackgroundColor = "blue"
    #
    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
       title="Select ISO image"
    #   ShowHelp = $True
        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
    #
    # .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);
    '
    # Hide = 0,
    # ShowNormal = 1,
    # ShowMinimized = 2,
    # ShowMaximized = 3,
    # Maximize = 3,
    # ShowNormalNoActivate = 4,
    # Show = 5,
    # Minimize = 6,
    # ShowMinNoActivate = 7,
    # ShowNoActivate = 8,
    # Restore = 9,
    # ShowDefault = 10,
    # ForceMinimized = 11
    #
    function Show-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 1)
    }
    function Hide-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 0)
    }
    Function Cancel
    {
        [Environment]::Exit(1)
    }
    clear-host
    #
    $Global:ImagePath=""
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the size of the window:
    # $Form.FormBorderStyle = "none"
    $Form.ControlBox = $True
    $Form.Text="Windows Installation Disk v1.7"
    $Form.Width=450 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    $Form.AutoSize=$true # AutoSize property to make the form automatically stretch, if the elements on the form are out of bounds
    $Form.KeyPreview = $True
    $Form.Add_KeyDown({if ($_.KeyCode -eq "Enter"){$OKButton.PerformClick()}})         # Enter = click OK button
    $Form.Add_KeyDown({if ($_.KeyCode -eq "Escape"){$CancelButton.PerformClick()}})    # Escape = click on Cancel button
    $Form.BackColor = "#CCCCCC"
    
    $OKButton=New-Object System.Windows.Forms.Button # Put the OK button on the form
    $OKButton.Location=New-Object System.Drawing.Point(315,170)
    $OKButton.Text="OK"
    $OKButton.Font='Courier New,9'
    $OKButton.Size=New-Object System.Drawing.Size(100,25)
    # $OKButton.Size=New-Object System.Drawing.Size(125,20)
    $OKButton.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    $Form.Controls.Add($OKButton)
    $OKButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
    
    $SelectUSBDisk=New-Object System.Windows.Forms.Label # Put the SelectUSBDisk label on the form
    $SelectUSBDisk.Location=New-Object System.Drawing.Point(20,25)
    $SelectUSBDisk.Font='Courier New,9'
    $SelectUSBDisk.Size=New-Object System.Drawing.Size(350,20)
    $Form.Controls.Add($SelectUSBDisk)
    
    $SelectISO=New-Object System.Windows.Forms.Label # Put the SelectISO label on the form
    $SelectISO.Location=New-Object System.Drawing.Point(20,90)
    $SelectISO.Font='Courier New,9'
    $SelectISO.Size=New-Object System.Drawing.Size(350,20)
    $SelectISO.text="Select ISO image:"
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the SelectISO button on the form
    $SelectISOButton.Location=New-Object System.Drawing.Point(375,110)
    $SelectISOButton.Text="..."
    $SelectISOButton.Font='Courier New,9'
    $SelectISOButton.Size=New-Object System.Drawing.Size(40,22)
    # $SelectISOButton.Size=New-Object System.Drawing.Size(40,22)
    $SelectISOButton.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    
    $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='Courier New,9'
    $ISOFile.Size=New-Object System.Drawing.Size(350,22)
    $ISOFile.Backcolor = [System.Drawing.Color]::White
    $ISOFile.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat   
    
    $Warning=New-Object System.Windows.Forms.Label # Put the Warning label on the form
    $Warning.Location=New-Object System.Drawing.Point(20,30)
    $Warning.Font='Courier New,9'
    $Warning.Size=New-Object System.Drawing.Size(380,80)
    $Warning.text="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?"
    
    #
    #    Select the USB disk
    # Create a drop-down list and fill it
    $USBDiskList=New-Object System.Windows.Forms.ComboBox
    $USBDiskList.DropDownStyle=[System.Windows.Forms.ComboBoxStyle]::DropDownList;
    $USBDiskList.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    $USBDiskList.Location=New-Object System.Drawing.Point(20,45)
    $USBDiskList.Size=New-Object System.Drawing.Size(395,20)
    $USBDiskList.Font='Courier New,9'
    $Form.Controls.Add($SelectUSBDiskList)
    $USBDisks=@() # array with USB disk number
    $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    Hide-Console # Hide console display
    
    $Complete=New-Object System.Windows.Forms.Label # Put the Complete label on the form
    $Complete.Location=New-Object System.Drawing.Point(20,30)
    $Complete.Font='Courier New,9'
    $Complete.Size=New-Object System.Drawing.Size(400,40)
    $Complete.text="The Windows Installation Disk completed successfully."
    #                                                                                   
    While (!$Disks) {
        $SelectUSBDisk.Text="Please plug in your USB disk."
        if ($form.ShowDialog() -eq "Cancel"){cancel}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    
    $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='Courier New,9'
    $CancelButton.Size=New-Object System.Drawing.Size(100,25)
    # $CancelButton.Size=New-Object System.Drawing.Size(120,20)
    $CancelButton.Flatstyle = [System.Windows.Forms.Flatstyle]::Flat
    $Form.Controls.Add($CancelButton)
    # $CancelButton.Add_Click({$Form.Close();cancel})
    $CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel
    
    $Form.Controls.Add($SelectISO)
    $Form.Controls.Add($ISOFile)
    $Form.Controls.Remove($OKButton)
    $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)+"..."}
         $OKButton.Text="Create disk"
         $Form.Controls.Add($OKButton)})
     
    Foreach ($USBDisk in $Disks) {
        $FriendlyName=($USBDisk.FriendlyName).PadRight(40," ").substring(0,40)
        $USBDisks+=$USBDisk.DiskNumber
        $USBDiskList.Items.Add(("{0,-44}{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,-38}[{3:n2} GB]" -f " ", ($Partition.DriveLetter), $Volume.FileSystemLabel.PadRight(30," ").substring(0,30), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    
    $SelectUSBDisk.Text="Select USB disk:"
    #
    $Form.Controls.Add($SelectISOButton)
    #
    if ($form.ShowDialog() -eq "Cancel") {Cancel}
    #
    # 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
    #
    if (ImagePath -eq ""){Cancel} # this can't happen, but keep the test
    #  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}
    #
    # Ready to create the USB disk. Ask for confirmation
    #
    $Form.Controls.Remove($USBDiskList)
    $Form.Controls.Remove($SelectUSBDisk)
    $Form.Controls.Remove($SelectISOButton)
    $Form.Controls.Remove($ISOFile)
    $Form.Controls.Remove($SelectISO)
    $OKButton.Text="Yes"
    $CancelButton.Text="No"
    $Form.Controls.Add($OKButton)
    $Form.Controls.Add($Warning)
    if ($form.ShowDialog() -eq "Cancel") {DisMount-DiskImage -ImagePath $ImagePath |out-null;Cancel}
    Clear-Host
    $pswindow.windowtitle = "Windows Installation Disk v1.7 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    Show-Console | Out-Null # Restore console display
    #    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
    #
    $Form.Controls.Remove($USBDiskList)
    $Form.Controls.Remove($SelectUSBDisk)
    $Form.Controls.Remove($SelectISOButton)
    $Form.Controls.Remove($ISOFile)
    $Form.Controls.Remove($SelectISO)
    $Form.Controls.Remove($Warning)
    $Form.Controls.Remove($OKButton)
    $CancelButton.Text="Close"
    $Form.Controls.Add($Complete)
    if ($form.ShowDialog() -eq "Cancel") {Cancel}
    
    
     
  4. Hasefroch

    Hasefroch MDL Senior Member

    Dec 24, 2018
    270
    160
    10
    this works on Windows 7? or only in Windows 10?
     
  5. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    60
    Not sure. Partition a USB flash drive was only available on Windows 10 but i don't remember the first release of Windows 10 supporting this (and the script uses this feature). If you have a recent release of windows 10, no problem.
     
  6. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    60
    #189 rpo, Aug 31, 2019
    Last edited: Sep 6, 2019
    I tested only uac escalation on w7.
    For "older" systems, the script is not needed because the install.wim should not exceed 4 GBytes. You have only to mount the iso image and copy the content on a fat32
    usb flash drive.

    Following is the systhesis of the "official" script (set "rpo=" and my variations (set "rpo=1")
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    [USER=239034]@SeT[/USER] "title=Windows Installation Disk v1.7 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    [USER=571939]@Color[/USER] 1E&title %title%
    [USER=239034]@SeT[/USER] "rpo=1"&@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
    }
    $rpo=$env:rpo # [USER=239034]@SeT[/USER] rpo=1&@set "__AR...
    #
    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
        title="Select ISO image"
        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
    #
    # .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);
    '
    # Hide = 0,
    # ShowNormal = 1,
    # ShowMinimized = 2,
    # ShowMaximized = 3,
    # Maximize = 3,
    # ShowNormalNoActivate = 4,
    # Show = 5,
    # Minimize = 6,
    # ShowMinNoActivate = 7,
    # ShowNoActivate = 8,
    # Restore = 9,
    # ShowDefault = 10,
    # ForceMinimized = 11
    #
    function Show-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 1)
    }
    function Hide-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 0)
    }
    Function Cancel
    {
        [Environment]::Exit(1)
    }
    clear-host
    #
    $Global:ImagePath=""
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the size of the window:
    # $Form.FormBorderStyle = "none"
    IF ($rpo){$Form.ControlBox = $false}
    $Form.Text=($env:title).split("by")[0]
    $Form.Width=450 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    $Form.KeyPreview = $True
    $Form.Add_KeyDown({if ($_.KeyCode -eq "Enter"){$OKButton.PerformClick()}})         # Enter = click OK button
    $Form.Add_KeyDown({if ($_.KeyCode -eq "Escape"){$CancelButton.PerformClick()}})    # Escape = click on Cancel button
    $Form.BackColor = "#CCCCCC"
    
    $OKButton=New-Object System.Windows.Forms.Button # Put the OK button on the form
    $OKButton.Location=New-Object System.Drawing.Point(315,170)
    $OKButton.Text="OK"
    $OKButton.Font='Consolas,10'
    $OKButton.Size=New-Object System.Drawing.Size(100,25)
    $OKButton.Flatstyle = "Flat"
    if ($rpo){$OKButton.FlatAppearance.BorderSize = 1}
    $OKButton.TabIndex=0
    $Form.Controls.Add($OKButton)
    $OKButton.DialogResult = "OK"
    
    $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='Consolas,10'
    $CancelButton.Size=New-Object System.Drawing.Size(100,25)
    $CancelButton.Flatstyle = "Flat"
    if ($rpo){$CancelButton.FlatAppearance.BorderSize = 1}
    $CancelButton.TabIndex=99
    $CancelButton.DialogResult = "Cancel"
    
    $SelectUSBDisk=New-Object System.Windows.Forms.Label # Put the SelectUSBDisk label on the form
    $SelectUSBDisk.Location=New-Object System.Drawing.Point(20,25)
    $SelectUSBDisk.Font='Consolas,10'
    $SelectUSBDisk.Size=New-Object System.Drawing.Size(350,20)
    $Form.Controls.Add($SelectUSBDisk)
    
    $SelectISO=New-Object System.Windows.Forms.Label # Put the SelectISO label on the form
    $SelectISO.Location=New-Object System.Drawing.Point(20,90)
    $SelectISO.Font='Consolas,10'
    $SelectISO.Size=New-Object System.Drawing.Size(350,20)
    $SelectISO.text="Select ISO image:"
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the SelectISO button on the form
    $SelectISOButton.Flatstyle = "Flat"
    if ($rpo){
    $SelectISOButton.Location=New-Object System.Drawing.Point(20,90)
    $SelectISOButton.Text="Select ISO image"
    $SelectISOButton.Font='Consolas,10'
    $SelectISOButton.FlatAppearance.BorderSize = 2
    $SelectISOButton.TabIndex=5
    $SelectISOButton.Size=New-Object System.Drawing.Size(140,25)
    } else {
    $SelectISOButton.Location=New-Object System.Drawing.Point(375,110)
    $SelectISOButton.Text="..."
    $SelectISOButton.Font='Consolas,10'
    $SelectISOButton.Size=New-Object System.Drawing.Size(40,22)
    }
    $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(350,22)
    if ($rpo) {$ISOFile.Size=New-Object System.Drawing.Size(395,20)
               $ISOFile.Location=New-Object System.Drawing.Point(20,120)}
    $ISOFile.Backcolor = "White"
    $ISOFile.Flatstyle = "Flat"  
    
    $Warning=New-Object System.Windows.Forms.Label # Put the Warning label on the form
    $Warning.Location=New-Object System.Drawing.Point(20,30)
    $Warning.Font='Consolas,10'
    $Warning.Size=New-Object System.Drawing.Size(380,80)
    $Warning.text="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?"
    
    #
    #    Select the USB disk
    # Create a drop-down list and fill it
    $USBDiskList=New-Object System.Windows.Forms.ComboBox
    $USBDiskList.DropDownStyle=[System.Windows.Forms.ComboBoxStyle]::DropDownList;
    $USBDiskList.Flatstyle = "Flat"
    $USBDiskList.Location=New-Object System.Drawing.Point(20,45)
    $USBDiskList.Size=New-Object System.Drawing.Size(395,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")}
    Hide-Console # Hide console display
    
    $Complete=New-Object System.Windows.Forms.Label # Put the Complete label on the form
    $Complete.Location=New-Object System.Drawing.Point(20,30)
    $Complete.Font='Consolas,10'
    $Complete.Size=New-Object System.Drawing.Size(410,40)
    $Complete.text="The Windows Installation Disk completed successfully."
    #                                                                                  
    While (!$Disks) {
        if ($rpo){$Form.Controls.Add($CancelButton)}
        $SelectUSBDisk.Text="Please plug in your USB disk."
        if ($form.ShowDialog() -eq "Cancel"){cancel}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    
    $Form.Controls.Add($CancelButton)
    
    if (!$rpo) {$Form.Controls.Remove($CancelButton)
                $Form.Controls.Add($SelectISO)
                $CancelButton.FlatAppearance.BorderSize = 1
                $Form.Controls.Add($CancelButton)}
    $Form.Controls.Add($ISOFile)
    $Form.Controls.Remove($OKButton)
    $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 ($rpo) {$l=49} else {$l=43}
        if (($ISOFile.Text).length -gt $l) {$ISOFile.Text = $ImagePath.PadRight(100," ").substring(0,($l-1))+"..."}
        if ($rpo) {$Form.Controls.Remove($SelectISOButton)
                    $Form.Controls.Remove($CancelButton)
                    $OKButton.FlatAppearance.BorderSize = 2
                    $SelectISOButton.FlatAppearance.BorderSize = 1
                    $CancelButton.FlatAppearance.BorderSize = 1
                    $Form.Controls.Add($CancelButton)
                    $Form.Controls.Add($SelectISOButton)}
         $OKButton.Text="Create disk"
         $Form.Controls.Add($OKButton)})
    
    Foreach ($USBDisk in $Disks) {
        $FriendlyName=($USBDisk.FriendlyName).PadRight(40," ").substring(0,40)
        $USBDisks+=$USBDisk.DiskNumber
        $USBDiskList.Items.Add(("{0,-46}{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,-40}[{3:n2} GB]" -f " ", ($Partition.DriveLetter), $Volume.FileSystemLabel.PadRight(30," ").substring(0,30), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    
    $SelectUSBDisk.Text="Select USB disk:"
    #
    $Form.Controls.Add($SelectISOButton)
    #
    if ($form.ShowDialog() -eq "Cancel") {Cancel}
    #
    # 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
    #
    if ($ImagePath -eq ""){Cancel} # this can't happen, but keep the test
    #  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}
    #
    # Ready to create the USB disk. Ask for confirmation
    #
    $Form.Controls.Remove($USBDiskList)
    $Form.Controls.Remove($SelectUSBDisk)
    $Form.Controls.Remove($SelectISOButton)
    $Form.Controls.Remove($ISOFile)
    if (!$rpo){$Form.Controls.Remove($SelectISO)}
    $OKButton.Text="Yes"
    $CancelButton.Text="No"
    $Form.Controls.Add($OKButton)
    $Form.Controls.Add($Warning)
    if ($form.ShowDialog() -eq "Cancel") {DisMount-DiskImage -ImagePath $ImagePath |out-null;Cancel}
    Clear-Host
    $host.ui.rawui.windowtitle = "Windows Installation Disk v1.7 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    Show-Console | Out-Null # Restore console display
    #    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
    #
    if($rpo){
        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}
    else {  
        robocopy $iso $usbntfs /e
        robocopy $iso"\" $usbfat32"\" bootmgr bootmgr.efi
        robocopy $iso"\boot" $usbfat32"\boot" /e
        robocopy $iso"\efi" $usbfat32"\efi" /e
        robocopy $iso"\sources" $usbfat32"\sources" boot.wim}
    
    # Eject the mounted iso image
    DisMount-DiskImage -ImagePath $ImagePath |out-null
    #
    if ($rpo){Read-Host "`r`n`r`nThe Windows Installation Disk completed successfully. Press ""Enter key"" to exit"|Out-Null;exit}
    $Form.Controls.Remove($USBDiskList)
    $Form.Controls.Remove($SelectUSBDisk)
    $Form.Controls.Remove($SelectISOButton)
    $Form.Controls.Remove($ISOFile)
    $Form.Controls.Remove($SelectISO)
    $Form.Controls.Remove($Warning)
    $Form.Controls.Remove($OKButton)
    $CancelButton.Text="Close"
    $Form.Controls.Add($Complete)
    if ($form.ShowDialog() -eq "Cancel") {Exit}
    #
    
     
  7. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,358
    2,267
    60
    #190 freddie-o, Sep 5, 2019
    Last edited: Sep 6, 2019
    (OP)
    Reverted :)
    4th edit:
    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @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
    }
    $Env:ScriptPath=""; $Env:ScriptPath=""  # delete environment variables
    
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    $pswindow.windowtitle = "Windows Installation Disk v1.8 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    #
    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
    #
    # .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);
    '
    # Hide = 0,
    # ShowNormal = 1,
    # ShowMinimized = 2,
    # ShowMaximized = 3,
    # Maximize = 3,
    # ShowNormalNoActivate = 4,
    # Show = 5,
    # Minimize = 6,
    # ShowMinNoActivate = 7,
    # ShowNoActivate = 8,
    # Restore = 9,
    # ShowDefault = 10,
    # ForceMinimized = 11
    #
    function Show-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 1)
    }
    function Hide-Console
    {
        $consolePtr = [Console.Window]::GetConsoleWindow()
        [Console.Window]::ShowWindow($consolePtr, 0)
    }
    Function Cancel
    {
        [Environment]::Exit(1)
    }
    clear-host
    #
    $Global:ImagePath=""
    $USB=$Null
    $Form=New-Object System.Windows.Forms.Form # Create the screen form (window)
    $Form.TopMost = $True
    # Set the size of the window:
    # $Form.FormBorderStyle = "none"
    $Form.ControlBox = $True
    $Form.Text="Windows Installation Disk v1.8"
    $Form.Width=420 ; $Form.Height=250
    $Form.StartPosition = "CenterScreen"
    $Form.KeyPreview = $True
    
    $CreateDiskButton=New-Object System.Windows.Forms.Button # Put the CreateDisk button on the form
    $CreateDiskButton.Location=New-Object System.Drawing.Point(265,170)
    $CreateDiskButton.Text="Create Disk"
    $CreateDiskButton.Font='Consolas,10'
    $CreateDiskButton.Size=New-Object System.Drawing.Size(120,25)
    # $CreateDiskButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($CreateDiskButton)
    $CreateDiskButton.DialogResult = [System.Windows.Forms.DialogResult]::OK
    
    $BootDisk=New-Object System.Windows.Forms.Label # Put the Boot Disk label on the form
    $BootDisk.Location=New-Object System.Drawing.Point(20,25)
    $BootDisk.Font='Consolas,10'
    $BootDisk.Size=New-Object System.Drawing.Size(400,20)
    $Form.Controls.Add($BootDisk)
    
    $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"
    
    $SelectISOButton=New-Object System.Windows.Forms.Button # Put the SelectISO button on the form
    $SelectISOButton.Location=New-Object System.Drawing.Point(265,170)
    $SelectISOButton.Text="Select ISO"
    $SelectISOButton.Font='Consolas,10'
    $SelectISOButton.Size=New-Object System.Drawing.Size(120,25)
    # $SelectISOButton.Size=New-Object System.Drawing.Size(120,25)
    
    $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
    #
    #    Select the USB disk
    # 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")}
    Hide-Console # Hide console display
    #                                                                                   
    While (!$Disks) {
        $Result=$wshell.Popup("Please plug in your USB disk.",0,"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")}
    }
    
    $CancelButton=New-Object System.Windows.Forms.Button # Put the Cancel button on the form
    $CancelButton.Location=New-Object System.Drawing.Point(135,170)
    $CancelButton.Text="Cancel"
    $CancelButton.Font='Consolas,10'
    $CancelButton.Size=New-Object System.Drawing.Size(120,25)
    # $CancelButton.Size=New-Object System.Drawing.Size(120,25)
    $Form.Controls.Add($CancelButton)
    # $CancelButton.Add_Click({$Form.Close();cancel})
    $CancelButton.DialogResult = [System.Windows.Forms.DialogResult]::Cancel
    
    $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(30," ").substring(0,30), ($Partition.Size/1GB)))|out-null
                }
            }
        }
    }
    $form.Controls.Add($USBDiskList)
    $USBDiskList.SelectedIndex=0
    
    $BootDisk.Text="Boot Disk"
    #
    $Form.Controls.Add($SelectISOButton)
    #
    if ($form.ShowDialog() -eq "Cancel") {Cancel}
    #
    # 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
    #
    if (ImagePath -eq ""){Cancel} # this can't happen, but keep the test
    #  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}
    #
    $Result=$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,"Create the Windows Installation Disk",4+48)
    if ($result -eq 7) {DisMount-DiskImage -ImagePath $ImagePath |Out-Null;exit}
    Clear-Host
    Show-Console | Out-Null # Restore console display
    $pswindow.windowtitle = "Windows Installation Disk v1.8 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    #    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,"Complete",0+64) | Out-Null;exit
    
    
     
  8. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    60
    You can delete the instruction at line 17 (my bad, i introduced it)
    You can simplify lines 135-136 by
    Code:
    if($wshell.Popup("Please plug in your USB disk.",0,"Plug in the USB disk",1+64) -eq 2){exit}    
    and 200-201 by
    Code:
    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,"Create the Windows Installation Disk",4+48) -eq 7){DisMount-DiskImage -ImagePath $ImagePath;exit}
    It's only to have a cleaner code.
     
  9. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,358
    2,267
    60
    #193 freddie-o, Sep 7, 2019
    Last edited: Sep 7, 2019
    (OP)
    Reverted so the console is not hidden anymore and some more minor changes to the UI.

    Code:
    <# : standard way of doing hybrid batch + powershell scripts
    @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
    }
    $Env:ScriptPath=""; $Env:ScriptPath=""  # delete environment variables
    #
    $pswindow = $host.ui.rawui          # create a reference to the console’s UI.RawUI child object
    $pswindow.windowtitle = "Windows Installation Disk v1.8.1 by: rpo/freddie-o/abbodi1406/BAU [forums.mydigitallife.net]"
    #
    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="Windows Installation Disk v1.8.1"
    $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 first then click ""OK"" to continue.",0,"Plug in the USB disk",1+64) -eq 2){exit}
        $Disks=Get-Disk | Where-Object {($_.BusType -eq "USB") -and ($_.OperationalStatus -eq "Online")}
    }
    $BootDisk=New-Object System.Windows.Forms.Label # Put the Boot Disk label on the form
    $BootDisk.Location=New-Object System.Drawing.Point(20,25)
    $BootDisk.Text="USB Disk"
    $BootDisk.Font='Consolas,10'
    $BootDisk.Size=New-Object System.Drawing.Size(400,20)
    $Form.Controls.Add($BootDisk)
    
    $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 SelectISO 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 CreateDisk 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,"Cancel script",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,"Warning",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,"Complete",0+64) | Out-Null;exit
    
    
     
  10. MMIKEE

    MMIKEE MDL Senior Member

    Oct 6, 2012
    380
    361
    10
    @freddie-o and @rpo
    Per my previous post #146 I still cannot get any releases to work properly on my Laptop w/ LTSB 2016-x64...

    Build/Update Revision : 14393 {rs1_release} / 3144
    Release Identifier : 1607
    Build Information : 14393.3143
    Detected .Net Versions : v1.1.4322, v2.0.50727, v3.5, v4.0.30319, v4.8 or later {Rev: 528049}
    Powershell Version{s} : 1.0, 2.0, 3.0, 4.0, 5.0, 5.1

    This Laptop has a User Name with a SPACE between 2 words IF that matters...

    However, yesterday I tried using v1.8 on a VMware LTSC-2019 on this same Laptop with a 32GB Flash Drive and it works as advertised...

    I would appreciate some thoughts / suggestions to determine the cause of this...
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  11. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    60
    Refer to post 187. I suppose that your windows release doesn't support usb flash drive partitioning. The full support is available with windows 1703.
     
  12. MMIKEE

    MMIKEE MDL Senior Member

    Oct 6, 2012
    380
    361
    10
    #196 MMIKEE, Sep 7, 2019
    Last edited: Sep 7, 2019
    I suppose this is the problem. I can use Rufus to effectively create a bootable USB with any OS installation so far but it only creates a single partition...
    Is there any modification that can be made to the script that will remedy this shortcomming of older W10 OS's like LTSB-2016 ???

    Udpate:
    I can confirm that this is the problem... I used a Partition Manager program to attempt to partition this USB Flash Drive and it reported that this OS .14393 aka 1607 (LTSB 2016) does not allow USB Flash Drive partitioning...

    I 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...
     
    Stop hovering to collapse... Click to collapse... Hover to expand... Click to expand...
  13. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    60
    If you create a usb flash disk with Rufus for uefi/gpte systems and ntfs, you will remark that 2 partitions are created on the usb drive : one ntfs and one fat32, and you can't boot on a mbr system.
    No modification can be made to the script. Other options have been mentioned on mdl.
    AFAIK you can partition usb flash drives with 3rd party programs (minitool partition wizard and others), but the problems appear when trying to access these partitions with Windows.
     
  14. 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...
  15. rpo

    rpo MDL Expert

    Jan 3, 2010
    1,440
    1,420
    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.
     
  16. freddie-o

    freddie-o MDL Expert

    Jul 29, 2009
    1,358
    2,267
    60
    #200 freddie-o, Sep 7, 2019
    Last edited: Sep 8, 2019
    (OP)
    Added "Supported Windows versions" to the OP.