Public/AzStackHci.PageFileSettings.ps1

# ///////////////////////////////////////////////////////////////////
# Get-AzStackHciPageFileSettings Function
# Used to get information about the current page file settings
# on the system.
# ///////////////////////////////////////////////////////////////////
Function Get-AzStackHciPageFileSettings {
    <#
    .SYNOPSIS
 
    Gets current page file settings
 
    .DESCRIPTION
 
    Queries the system for current page file settings
 
    #>


    [CmdletBinding()]
    [OutputType([void])]
    param (
        [switch]$NoOutput
    )

    begin {
        # Requires administrator permissions to get page file settings and write to log file to disk
        if (-not (Test-Elevation)) { throw "This script must be run as an Administrator." }

        $DateFormatted = Get-Date -f "yyyyMMdd"
        if(-not(Test-Path "C:\ProgramData\AzStackHci.DiagnosticSettings\"))
        {
            try {
                New-Item "C:\ProgramData\AzStackHci.DiagnosticSettings\" -ItemType Directory -ErrorAction Stop | Out-Null
            } catch {
                Throw "Failed to create output directory 'C:\ProgramData\AzStackHci.DiagnosticSettings\': $($_.Exception.Message)"
            }
        }
    }

    process {
        # Handle -NoOutput: suppress all console output
        if ($NoOutput.IsPresent) {
            $script:SilentMode = $true
            $VerbosePreference = 'SilentlyContinue'
            $DebugPreference = 'SilentlyContinue'
        }

        try {
            # Get current page file settings
            [bool]$script:PageFileAutoManaged = (Get-CimInstance Win32_ComputerSystem).AutomaticManagedPagefile
        } catch {
            Write-Verbose "Failed to get current page file settings. Error: $($_.Exception.Message)" -Verbose
            Throw "Failed to get current page file settings. Error: $($_.Exception.Message)"
        }
        
        "$(Get-Date -Format "yyyy-MM-dd HH:mm:ss")"  | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -ErrorAction Stop

        "Saving Page File configuration for node $($env:computername)" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop

        if($script:PageFileAutoManaged -eq $False){
            # Page File manual settings
            Write-Verbose "Current Settings: Page File automatic management is Disabled" -Verbose
            "Current Settings: Page File automatic management is Disabled`n" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
            Write-Verbose "Current Page File Configuration:" -Verbose
            "Current Page File Configuration:" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
            # Note: if Page File Automatic Manager = True, the PageFileSettings is Null
            try {
                $script:PageFileConfiguration = Get-CimInstance -ClassName Win32_PageFileSetting
            } catch {
                Write-Verbose "Failed to get current page file settings. Error: $($_.Exception.Message)" -Verbose
                Throw "Failed to get current page file settings. Error: $($_.Exception.Message)"
            }
            $PageFileSettings = ("Caption", "Description", "InitialSize", "MaximumSize" , "Name", "SettingID")
            foreach($PageFileSetting in $PageFileSettings){
                Write-Verbose "`t$PageFileSetting = $($PageFileConfiguration.$PageFileSetting)" -Verbose
                "`t$PageFileSetting = $($PageFileConfiguration.$PageFileSetting)" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
            }
            Write-Verbose "`n" -Verbose
            
        } elseif($script:PageFileAutoManaged -eq $True){
            Write-Verbose "Current Settings: Page File automatic management is Enabled" -Verbose
            "Current Settings: Page File automatic management is Enabled" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
        
        } else {
            Write-Error "Current Settings: Page File automatic management is Unknown" -Verbose
            "Current Settings: Page File automatic management is Unknown" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
        }
            
        # Page File usage: (info only, not always accurate)
        try {
            $script:PageFileUsage = Get-CimInstance Win32_PageFileUsage
        } catch {
            Write-Verbose "Failed to get page file usage. Error: $($_.Exception.Message)" -Verbose
            Throw "Failed to get page file usage. Error: $($_.Exception.Message)"
        }
        $PageFileUsageAttributes = ("AllocatedBaseSize", "Caption", "CurrentUsage", "Description" , "InstallDate", "Name", "PeakUsage", "Status", "TempPageFile")
        Write-Verbose "Page File usage:" -Verbose
        "Page File usage:" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
        foreach($PageFileUsageAttribute in $PageFileUsageAttributes){
            Write-Verbose "`t$PageFileUsageAttribute = $($PageFileUsage.$PageFileUsageAttribute)" -Verbose
            "`t$PageFileUsageAttribute = $($PageFileUsage.$PageFileUsageAttribute)" | Out-File $("C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt") -Append -ErrorAction Stop
        }
        $script:PageFileAllocatedBaseSize = $PageFileUsage.AllocatedBaseSize
        $script:PageFileCurrentUsage = $PageFileUsage.CurrentUsage
        $script:PageFilePeakUsage = $PageFileUsage.PeakUsage

        Write-Verbose "Current Page File settings exported to 'C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_$DateFormatted.txt'" -Verbose

        Write-HostAzS `n

    } # End of process block

    end {
        if ($NoOutput.IsPresent) { $script:SilentMode = $false }
        Write-Debug "Completed Get-AzStackHciPageFileSettings function"
    }
} # End of Get-AzStackHciPageFileSettings


# ///////////////////////////////////////////////////////////////////
# Set-AzStackHciPageFileMinimumSettings Function
# Used to set a static 4GB page file on the system, target drive is
# the only parameter.
# ///////////////////////////////////////////////////////////////////
Function Set-AzStackHciPageFileMinimumSettings {
    <#
    .SYNOPSIS
 
    Sets page file settings to minimum 4GB fixed size
 
    .DESCRIPTION
 
    Queries the system for current page file settings
 
    #>


    [CmdletBinding(SupportsShouldProcess, ConfirmImpact = 'High')]
    [OutputType([void])]
    param (
        # Path to drive letter for PageFile
        [Parameter(Mandatory=$true,Position=1)]
        [ValidateScript({Test-Path $_})]
        [String]
        [ValidatePattern('^[C-Zc-z]:\\?$')]$PageFileFileDriveLetter, # Drive letter for the page file, must be a valid drive letter (C: through Z:)

        [Parameter(Mandatory=$false, HelpMessage="Optional switch to prevent console output from the function.")]
        [switch]$NoOutput
    )

    begin {
        # Requires administrator permissions to set page file settings
        if (-not (Test-Elevation)) { throw "This script must be run as an Administrator." }

        # Call function to get current Page File settings and save to backup log file
        Get-AzStackHciPageFileSettings
    }

    process {
        # Handle -NoOutput: suppress all console output
        if ($NoOutput.IsPresent) {
            $script:SilentMode = $true
            $VerbosePreference = 'SilentlyContinue'
            $DebugPreference = 'SilentlyContinue'
        }

        # if the drive letter is only 2 characters (C:), add a backslash to the end (C:\)
        if($PageFileFileDriveLetter.Length -eq 2){
            $PageFileFileDriveLetter = $($PageFileFileDriveLetter + "\")
        }

        # ShouldProcess gate: prompt user before modifying page file settings
        if (-not $PSCmdlet.ShouldProcess("Page file on $PageFileFileDriveLetter", "Set fixed 4GB page file")) {
            return
        }

        try {
            # Get current page file settings
            [bool]$script:PageFileAutoManaged = (Get-CimInstance Win32_ComputerSystem).AutomaticManagedPagefile
        } catch {
            Write-Verbose "Failed to get current page file settings. Error: $($_.Exception.Message)" -Verbose
            Throw "Failed to get current page file settings. Error: $($_.Exception.Message)"
        }
        
        # If page file is NOT automatically managed
        if($script:PageFileAutoManaged -eq $False){
            # Page File manual settings
            Write-HostAzS "Automatic management of page file already disabled"
            Write-HostAzS "Configuring a fixed page file of 4GB size using file: $($PageFileFileDriveLetter)pagefile.sys`n"
            try {
                $script:PageFileConfiguration = Get-CimInstance -ClassName Win32_PageFileSetting
            } catch {
                Write-Verbose "Failed to get existing page file settings. Error: $($_.Exception.Message)" -Verbose
                Throw "Error: Failed to get existing page file settings. Error: $($_.Exception.Message)"
            }
            # Remove existing manual page file settings
            if($PageFileConfiguration){
                if(($PageFileConfiguration | Measure-Object).Count -eq 1){
                    try {
                        # Delete existing page file settings
                        $PageFileConfiguration | Remove-CimInstance
                    } catch {
                        Write-Verbose "Failed to delete existing page file settings. Error: $($_.Exception.Message)" -Verbose
                        Throw "Error: Failed to delete existing page file settings. Error: $($_.Exception.Message)"
                    }
                    Write-Verbose "Existing page file settings removed." -Verbose
                } else {
                    Write-Verbose "Unexpected configuration, more than one page file is currently configured! Expected 1, but found $(($PageFileConfiguration | Measure-Object).Count) x page files." -Verbose
                    Throw "Error: Unexpected configuration, more than one page file currently configured! Expected 1, but found $(($PageFileConfiguration | Measure-Object).Count) x page files."
                }
            } else {
                Write-Verbose "Existing page file settings not found." -Verbose
            }
            # Set a New page file, and set the size to 4GB fixed
            try 
            {
                # Use New-CimInstance to create a new page file setting, due to "Set-WmiInstance : Generic failure" error, if no existing page file settings are configured (as deleted).
                $PageFile = New-CimInstance -ClassName Win32_PageFileSetting -Property @{ Name= "$($PageFileFileDriveLetter)pagefile.sys" }
                $PageFile | Set-CimInstance -Property @{ InitialSize = 4096; MaximumSize = 4096 }
            } catch {
                Write-Verbose "Failed to set minimum page file settings. Error: $($_.Exception.Message)" -Verbose
                Throw "Failed to set minimum page file settings. Error: $($_.Exception.Message)"
            }
            if($PageFile){
                Write-Verbose "Page File settings updated successfully to a fixed size of 4GB" -Verbose
                Write-Verbose "Page File: = '$($pagefile.Description)'" -Verbose
            } else {
                Write-Verbose "Failed to configure minimum page file settings." -Verbose
                Throw "Error: Failed to configure minimum page file settings."
            }

        } elseif($script:PageFileAutoManaged -eq $True){
            # If the page file is currently automatically managed
            Write-HostAzS "Disabling automatic management of page file"
            # Remove System Managed:
            try {
                $ComputerSystem = Get-CimInstance -ClassName Win32_ComputerSystem
            }
            catch {
                Write-Verbose "Failed to get existing automatic management settings. Error: $($_.Exception.Message)" -Verbose
                Throw "Error: Failed to get existing automatic management settings. Error: $($_.Exception.Message)"
            }
            try {
                $ComputerSystem | Set-CimInstance -Property @{ AutomaticManagedPagefile = $false }
            }
            catch {
                Write-Verbose "Failed to disable automatic management of page file. Error: $($_.Exception.Message)" -Verbose
                Throw "Error: Failed to disable automatic management of page file. Error: $($_.Exception.Message)"
            }
            Write-Verbose "Automatic management of page file disabled" -Verbose

            try {
                $script:PageFileConfiguration = Get-CimInstance -ClassName Win32_PageFileSetting
            } catch {
                Write-Verbose "Failed to get existing page file settings. Error: $($_.Exception.Message)" -Verbose
                Throw "Error: Failed to get existing page file settings. Error: $($_.Exception.Message)"
            }

            Write-HostAzS "Configuring a fixed page file of 4GB size using file: $($PageFileFileDriveLetter)pagefile.sys`n"
            # Remove existing page file setting and set a new page file, and set the size to 4GB fixed
            if($PageFileConfiguration){
                if(($PageFileConfiguration | Measure-Object).Count -eq 1){
                    try {
                        # Delete existing page file settings
                        $PageFileConfiguration | Remove-CimInstance
                    } catch {
                        Write-Verbose "Failed to delete existing page file settings. Error: $($_.Exception.Message)" -Verbose
                        Throw "Error: Failed to delete existing page file settings. Error: $($_.Exception.Message)"
                    }
                    Write-Verbose "Existing page file settings removed." -Verbose
                } else {
                    Write-Verbose "Unexpected configuration, more than one page file is currently configured! Expected 1, but found $(($PageFileConfiguration | Measure-Object).Count) x page files." -Verbose
                    Throw "Error: Unexpected configuration, more than one page file currently configured! Expected 1, but found $(($PageFileConfiguration | Measure-Object).Count) x page files."
                }

                # Set a New page file, and set the size to 4GB fixed
                try 
                {
                    # Use New-CimInstance to create a new page file setting, due to "Set-WmiInstance : Generic failure" error, if no existing page file settings are configured (as deleted).
                    $PageFile = New-CimInstance -ClassName Win32_PageFileSetting -Property @{ Name= "$($PageFileFileDriveLetter)pagefile.sys" }
                    $PageFile | Set-CimInstance -Property @{ InitialSize = 4096; MaximumSize = 4096 }
                } catch {
                    Write-Verbose "Failed to set new page file settings. Error: $($_.Exception.Message)" -Verbose
                    Throw "Failed to set new page file settings. Error: $($_.Exception.Message)"
                }
                if($PageFile){
                    Write-Verbose "Page File settings updated successfully to a fixed size of 4GB" -Verbose
                    Write-Verbose "Page File: = '$($pagefile.Description)'" -Verbose
                } else {
                    Write-Verbose "Failed to configure minimum page file settings." -Verbose
                    Throw "Error: Failed to configure minimum page file settings."
                }
                Write-Verbose "Page File settings updated to minimum recommended configuration, (static size of 4GB)." -Verbose

            } # End of If PageFileConfiguration
            
            Write-Verbose "A system restart is required for Page File changes to take effect.`n`n" -Verbose

        } else {
            Write-Error "Current Settings: Page File automatic management is Unknown (not enabled or disabled)." -Verbose
            Throw "Error: Current Settings: Page File automatic management is Unknown (not enabled or disabled)."
        } # End of If PageFileAutoManaged

    } # End of process block

    end {
        if ($NoOutput.IsPresent) { $script:SilentMode = $false }
        Write-Debug "Completed Set-AzStackHciPageFileMinimumSettings function"
    }

} # End of Set-AzStackHciPageFileMinimumSettings


# ///////////////////////////////////////////////////////////////////
# Restore-AzStackHciPageFileSettings function
# Used to restore or roll back page file settings
# ///////////////////////////////////////////////////////////////////
Function Restore-AzStackHciPageFileSettings
{
    <#
    .SYNOPSIS
 
    Restores page file settings from a backup file
 
    .DESCRIPTION
 
    Restores the page file settings from a backup file, using the 'PageFile_Settings_YYYYMMDD.txt' file.
    Requires administrator permissions to restore page file settings
     
    #>


    [CmdletBinding()]
    [OutputType([void])]
    param (
        # File path to backup file
        [Parameter(Mandatory=$true,Position=0)]
        [ValidateScript({Test-Path $_})]
        [String]$PageFileSettingsFilePath, # File used to restore settings from, must be a valid path

        [Parameter(Mandatory=$false, HelpMessage="Optional switch to prevent console output from the function.")]
        [switch]$NoOutput
    )

    begin {
        # Requires administrator permissions to set page file settings
        if (-not (Test-Elevation)) { throw "This script must be run as an Administrator." }
    }

    process {
        # Handle -NoOutput: suppress all console output
        if ($NoOutput.IsPresent) {
            $script:SilentMode = $true
            $VerbosePreference = 'SilentlyContinue'
            $DebugPreference = 'SilentlyContinue'
        }

        # Read the memory dump settings from the backup file into an array
        if($PageFileSettingsFilePath -like "C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_*"){
            Write-Verbose "Reading Page File settings from backup file: $PageFileSettingsFilePath" -Verbose
        } else {
            Write-Verbose "Page File settings backup file path must start with 'C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_'" -Verbose
            throw "Error: Page File settings backup file path must start with 'C:\ProgramData\AzStackHci.DiagnosticSettings\PageFile_Settings_'"
        }
        # Read the page file settings from the backup file into an array
        [string[]]$RestorePageFileSettings = Get-Content $PageFileSettingsFilePath -ErrorAction Stop

        try {
            # Get current page file settings
            [bool]$script:PageFileAutoManaged = (Get-CimInstance Win32_ComputerSystem).AutomaticManagedPagefile
        } catch {
            Write-Verbose "Failed to get current page file settings. Error: $($_.Exception.Message)" -Verbose
            Throw "Failed to get current page file settings. Error: $($_.Exception.Message)"
        }

        # Date time thePage File settings were saved should be the first line in the file
        try {
            [datetime]$DateTimePageFileSettings = $RestorePageFileSettings[0]    
        }
        catch {
            throw "Failed to get the date and time the Page File settings were saved. Error: $($_.Exception.Message)"
        }
        
        # Confirm with user before restoring the page file settings
        Write-Verbose "Restoring Page File settings from $PageFileSettingsFilePath, saved on $DateTimePageFileSettings" -Verbose
        if ($script:SilentMode) {
            $RestoreConfirmation = "Y"
        } else {
            $RestoreConfirmation = Read-Host "Do you want to restore the page file settings from $PageFileSettingsFilePath? (Y/N)" -ErrorAction Stop
        }
        if($RestoreConfirmation -ne "Y"){
            Write-Verbose "Page File settings restore cancelled by user." -Verbose
            return
        }
        
        [int]$RestoreVariableCounter = 0
        # Restore the page file settings, the first two lines (0-1) are the date and time and machine name. The required information starts at line three.
        # i = 2 is the third line in the file, which is the first setting (Enabled or Disabled for automatic page file management)
        # Loop through the settings, and restore the page file settings
        for($i=2; $i -lt ($RestorePageFileSettings.Count -3); $i++)
        {
            # Get the setting from the backup file array on each iteration
            $Setting = $RestorePageFileSettings[$i]

            if(($i -eq 2) -and ($Setting -eq "Current Settings: Page File automatic management is Disabled")){
                # Page File settings are manually configured
                [bool]$RestorePageFileAutoManaged = $False
                Continue
            } elseif(($i -eq 2) -and ($Setting -eq "Current Settings: Page File automatic management is Enabled")){
                # Page File settings are automatically managed
                [bool]$RestorePageFileAutoManaged = $True
                Continue
            } else {
                if($i -eq 2){
                    Write-Verbose "Error: Expected setting 'Current Settings: Page File automatic management is Disabled' or 'Current Settings: Page File automatic management is Enabled', but got '$Setting'." -Verbose
                    throw "Error: Expected setting 'Current Settings: Page File automatic management is Disabled' or 'Current Settings: Page File automatic management is Enabled', but got '$Setting'."
                }
            }
            
            if(($i -eq 3) -and ($RestorePageFileAutoManaged)){
                if($Setting -eq "Page File usage:"){
                    # Skip the line that says "Page File usage:"
                    Continue
                }
            } elseif(($i -eq 3) -and (-not($RestorePageFileAutoManaged))){
                if($Setting -eq "Current Page File Configuration:"){
                    # Skip the line that says "Current Page File Configuration:"
                    Continue
                }
            }

            if([string]::IsNullOrWhiteSpace($Setting)){
                # Skip blank lines, such as line 4
                Continue
            }
            # Debugging output, when running with -Debug
            Write-Debug "Backup file input: $Setting"
            # Split the setting into the name and value
            $SettingName = $Setting.Split("=",[System.StringSplitOptions]::RemoveEmptyEntries)[0].Trim()
            if(-not($SettingName -in ("Page File usage:","Current Page File Configuration:"))){
                # Check if the setting value is a comment, as won't have a value in the backup file
                $SettingValue = $Setting.Split("=",[System.StringSplitOptions]::RemoveEmptyEntries)[1].Trim()
            }

            # If the page file was automatically managed in the backup file
            if($RestorePageFileAutoManaged){
                # We us the "Name" setting to restore the page file settings, as this is the path to the Page file.
                if($SettingName -eq "Name"){
                    # Revert Page File to System Managed:
                    # Check if the page file is already automatically managed, if not, revert to automatically managed
                    if($PageFileAutoManaged){
                        # Page File is already automatically managed
                        Write-Verbose "Restore Page File settings: Unexpected configuration - Page File is already automatically managed, no action required." -Verbose
                        throw "Restore Page File settings: Unexpected configuration - Page File is already configured to be automatically managed, no action required."
                    
                    } else { # Page File is manually configured (expected with 4GB fixed size), so revert to automatically managed
                        
                        Write-Verbose "Restore Page File: Reverting Page File to automatically managed." -Verbose
                        # Remove manual page file, using the current settings
                        try {
                            $script:PageFileConfiguration = Get-CimInstance -ClassName Win32_PageFileSetting
                        } catch {
                            Write-Verbose "Failed to get existing page file settings. Error: $($_.Exception.Message)" -Verbose
                            Throw "Failed to get existing page file settings. Error: $($_.Exception.Message)"
                        }
                        # Check there is only one page file configured
                        if(($script:PageFileConfiguration | Measure-Object).Count -eq 1) {
                            # Remove existing manual page file settings
                            try {
                                # Remove existing manual page file settings
                                $PageFileConfiguration | Remove-CimInstance
                            } catch {
                                Write-Verbose "Failed to delete existing page file settings. Error: $($_.Exception.Message)" -Verbose
                                Throw "Failed to delete existing page file settings. Error: $($_.Exception.Message)"
                            }
                            Write-Verbose "Existing manual page file settings removed." -Verbose
                        } else {
                            Write-Verbose "Error: Unexpected configuration - Expected only 1 page file to be configured, but found $(($script:PageFileConfiguration | Measure-Object).Count)" -Verbose
                            throw "Error: Unexpected configuration - Expected only 1 page file to be configured, but found $(($script:PageFileConfiguration | Measure-Object).Count)"
                        }
                        
                        # New Page File, using the file path from the backup file:
                        try {
                            Write-Verbose "Setting new page file settings to automatically managed." -Verbose
                            $RestorePageFile = New-CimInstance -ClassName Win32_PageFileSetting -Property @{ Name= $SettingValue }
                            $RestorePageFile | Set-CimInstance -Property @{ InitialSize = 0; MaximumSize = 0 }
                        } catch {
                            Write-Verbose "Error: Failed to restore system managed page file settings. Error: $($_.Exception.Message)" -Verbose
                            Throw "Error: Failed to restore system managed page file settings. Error: $($_.Exception.Message)"
                        }
                        if($RestorePageFile){
                            Write-Verbose "System managed page file configured successfully: '$($RestorePageFile.Description)'" -Verbose
                        } else {
                            Write-Verbose "Failed to restore system managed page file settings." -Verbose
                            Throw "Error: Failed to restore system managed page file settings."
                        }

                        # Enable Automatic Management on all drives:
                        try {
                            $ComputerSystem = Get-CimInstance -ClassName Win32_ComputerSystem
                        }
                        catch {
                            Write-Verbose "Failed to get existing automatic management settings. Error: $($_.Exception.Message)" -Verbose
                            Throw "Error: Failed to get existing automatic management settings. Error: $($_.Exception.Message)"
                        }
                        try {
                            $ComputerSystem | Set-CimInstance -Property @{ AutomaticManagedPagefile = $true }
                            Write-Verbose "Automatic management of page file enabled" -Verbose
                        }
                        catch {
                            Write-Verbose "Failed to enable automatic management of page file. Error: $($_.Exception.Message)" -Verbose
                            Throw "Error: Failed to enable automatic management of page file. Error: $($_.Exception.Message)"
                        }

                        Write-Verbose "Page File settings reverted to automatically managed." -Verbose
                        Write-Verbose "A system restart is required for the Page File changes to take effect." -Verbose
                        Return $True
                    }
                }

            # If the page file was manually configured in the backup file
            } elseif(-not($RestorePageFileAutoManaged)){
                
                # Get the six manual Page File settings from input backup file...
                if($SettingName -in ("Caption", "Description", "InitialSize", "MaximumSize" , "Name", "SettingID")){
                    # Increment the counter for the number of settings restored
                    $RestoreVariableCounter++
                    if($RestoreVariableCounter -le 6){ # Only create variables for first six settings that match above.
                        # Set the Page File settings from the backup file
                        New-Variable -Name RestorePageFile$SettingName -Value $SettingValue
                    } else {
                        Write-Verbose "Error: Unexpected configuration - Restoring multiple manual page files." -Verbose
                        throw "Unexpected configuration - Restoring multiple manual page files"
                    }
                }
                
                # Restore the Page File settings from the backup file
                if($SettingName -eq "Page File usage:"){
                    # Ready to restore the manual page file settings, as we don't use the "Page File usage:" line or anything after it.
                    # Get the current page file settings to check if the page file is the same as the backup file
                    try {
                        $script:PageFileConfiguration = Get-CimInstance -ClassName Win32_PageFileSetting
                    } catch {
                        Write-Verbose "Failed to get existing page file settings. Error: $($_.Exception.Message)" -Verbose
                        Throw "Failed to get existing page file settings. Error: $($_.Exception.Message)"
                    }
                    # Ensure there is only one page file currently configured (expected with 4GB fixed size)
                    if(($script:PageFileConfiguration | Measure-Object).Count -eq 1) {
                        # Check if the page file is the same as the backup file
                        if($PageFileConfiguration.Caption -eq $RestorePageFileCaption){
                            # Remove existing manual page file settings
                            try {
                                # Remove existing manual page file settings
                                $PageFileConfiguration | Remove-CimInstance
                            } catch {
                                Write-Verbose "Failed to delete existing page file settings. Error: $($_.Exception.Message)" -Verbose
                                Throw "Failed to delete existing page file settings. Error: $($_.Exception.Message)"
                            }
                            Write-Verbose "Existing manual page file settings removed." -Verbose
                        }
                    } else {
                        Write-Verbose "Error: Unexpected configuration - Expected only 1 page file to be configured, but found $(($script:PageFileConfiguration | Measure-Object).Count)" -Verbose
                        throw "Error: Unexpected configuration - Expected only 1 page file to be configured, but found $(($script:PageFileConfiguration | Measure-Object).Count)"
                    }

                    # Restore page file, creating a new page file configuration, setting the size values from the backup file
                    try {
                        Write-Verbose "Restoring page file settings from backup file." -Verbose
                        Write-Debug "{Name = $RestorePageFileName; InitialSize = $RestorePageFileInitialSize; MaximumSize = $RestorePageFileMaximumSize"
                        $RestorePageFile = New-CimInstance -ClassName Win32_PageFileSetting -Property @{ Name= $RestorePageFileName }
                        $RestorePageFile | Set-CimInstance -Property @{ InitialSize = $RestorePageFileInitialSize; MaximumSize = $RestorePageFileMaximumSize }
                    } catch {
                        Write-Verbose "Failed to restore static page file settings. Error: $($_.Exception.Message)" -Verbose
                        Throw "Error: Failed to restore static page file settings. Error: $($_.Exception.Message)"
                    }
                    if($RestorePageFile){
                        Write-Verbose "Static page file configuration restored successfully: '$($RestorePageFile.Description)'" -Verbose
                    } else {
                        Write-Verbose "Failed to restore static page file settings." -Verbose
                        Throw "Error: Failed to restore static page file settings."
                    }
                    Write-Verbose "Page File configured with InitialSize = $RestorePageFileInitialSize and MaximumSize = $RestorePageFileMaximumSize" -Verbose

                    Write-Verbose "Page File settings have been successfully restored from backup file." -Verbose
                    Write-Verbose "A system restart is required for the Page File changes to take effect." -Verbose
                    Return $True
                }
            
            } else {
                Write-Verbose "Error: Unexpected configuration - Page File settings were not automatically managed or manually configured." -Verbose
                throw "Unexpected configuration - Page File settings are not automatically managed or manually configured."
            }

        } # End of for loop

    } # End of process block

    end {
        if ($NoOutput.IsPresent) { $script:SilentMode = $false }
        Write-Debug "Completed Restore-AzStackHciPageFileSettings function"
    }

} # End of Restore-AzStackHciPageFileSettings function