How to Create and Manage Hyper-V Virtual Machines on Windows Server 2025

Once the Hyper-V role is installed on Windows Server 2025, the day-to-day work of a virtualisation administrator revolves around creating, configuring, and maintaining virtual machines. Hyper-V provides a rich PowerShell module that makes it straightforward to automate every aspect of VM lifecycle management — from initial provisioning and checkpoint management through to exporting, importing, and migrating VMs between hosts. This tutorial explores the full range of VM management tasks using PowerShell, giving you the commands and knowledge to manage a production Hyper-V environment confidently.

Prerequisites

  • Windows Server 2025 with the Hyper-V role installed (see the previous article for installation steps)
  • Hyper-V PowerShell module loaded — run Import-Module Hyper-V if cmdlets are not available
  • At least one virtual switch already configured (Get-VMSwitch to list existing switches)
  • An installation ISO or pre-built VHDX available on local or network storage
  • Sufficient host resources: recommended minimum 16 GB RAM and 200 GB free disk per test VM
  • Administrator privileges on the Hyper-V host

Step 1: Create a New Virtual Machine with New-VM

The New-VM cmdlet is the primary way to provision virtual machines from PowerShell. It accepts parameters for generation, memory, storage, and networking, letting you build a complete VM definition in a single command.

# Create a Generation 2 VM — recommended for all modern Windows guests
New-VM -Name "WEBSRV01" `
       -Generation 2 `
       -MemoryStartupBytes 4GB `
       -NewVHDPath "D:Hyper-VVMsWEBSRV01WEBSRV01-OS.vhdx" `
       -NewVHDSizeBytes 127GB `
       -SwitchName "External-Switch-01" `
       -Path "D:Hyper-VVMs"

# Create a Generation 1 VM for legacy guest operating systems (e.g., Windows Server 2008)
New-VM -Name "LEGSRV01" `
       -Generation 1 `
       -MemoryStartupBytes 2GB `
       -NewVHDPath "D:Hyper-VVMsLEGSRV01LEGSRV01-OS.vhdx" `
       -NewVHDSizeBytes 80GB `
       -SwitchName "External-Switch-01" `
       -Path "D:Hyper-VVMs"

# Create a VM using an existing VHDX (e.g., a pre-built sysprepped image)
New-VM -Name "APPSRV01" `
       -Generation 2 `
       -MemoryStartupBytes 8GB `
       -VHDPath "D:TemplatesWS2025-Template.vhdx" `
       -SwitchName "External-Switch-01"

Step 2: Configure Dynamic vs Static Memory

Hyper-V offers two memory modes: Static (a fixed allocation that never changes) and Dynamic Memory (the hypervisor adjusts memory between a defined minimum and maximum based on guest demand). Dynamic Memory is ideal when many VMs share a host, as it allows idle VMs to relinquish RAM to VMs under load.

# Configure Dynamic Memory — VM memory fluctuates between 2 GB and 16 GB
Set-VMMemory -VMName "WEBSRV01" `
             -DynamicMemoryEnabled $true `
             -MinimumBytes 2GB `
             -StartupBytes 4GB `
             -MaximumBytes 16GB `
             -Buffer 20 `
             -Priority 80

# Configure Static Memory — VM always holds exactly 8 GB regardless of load
Set-VMMemory -VMName "APPSRV01" `
             -DynamicMemoryEnabled $false `
             -StartupBytes 8GB

# Check current memory configuration for all VMs
Get-VM | Select-Object Name, MemoryStartup, MemoryMinimum, MemoryMaximum, DynamicMemoryEnabled

The -Buffer parameter specifies a percentage of extra memory the VM keeps as a reserve. The -Priority parameter (1–100) controls which VMs receive memory preferentially when the host is under memory pressure.

Step 3: Add a DVD Drive and Attach an Installation ISO

Most new VMs will need to boot from an ISO to complete operating system installation. Hyper-V represents optical drives as DVD drive objects that can be attached and detached at any time.

# Add a DVD drive controller to the VM
Add-VMDvdDrive -VMName "WEBSRV01" -ControllerNumber 0 -ControllerLocation 1

# Attach an ISO image to the DVD drive
Set-VMDvdDrive -VMName "WEBSRV01" `
               -ControllerNumber 0 `
               -ControllerLocation 1 `
               -Path "C:ISOWS2025_SERVER_EVAL_x64FRE_en-us.iso"

# For Generation 2 VMs, set boot order so DVD comes first
$dvdDrive  = Get-VMDvdDrive  -VMName "WEBSRV01"
$vhdDrive  = Get-VMHardDiskDrive -VMName "WEBSRV01"
Set-VMFirmware -VMName "WEBSRV01" -BootOrder $dvdDrive, $vhdDrive

# After OS installation, eject the ISO to prevent re-booting from it
Set-VMDvdDrive -VMName "WEBSRV01" -ControllerNumber 0 -ControllerLocation 1 -Path $null

Step 4: Start VMs and View the VM Inventory

# Start a single VM
Start-VM -Name "WEBSRV01"

# Start all VMs that are currently off
Get-VM | Where-Object { $_.State -eq "Off" } | Start-VM

# Get a summary table of all VMs with key properties
Get-VM | Select-Object Name, State, Generation, `
    @{N="MemoryGB"; E={ [math]::Round($_.MemoryStartup/1GB,1) }}, `
    ProcessorCount, `
    @{N="Uptime"; E={ $_.Uptime }}, `
    @{N="Status"; E={ $_.Status }} | Format-Table -AutoSize

# Get detailed info for a specific VM
Get-VM -Name "WEBSRV01" | Format-List *

Step 5: Work with VM Checkpoints (Snapshots)

Checkpoints capture the complete state of a virtual machine at a point in time — including memory contents, disk state, and device configuration. They are invaluable for testing risky changes (patch deployment, application upgrades) because you can revert the VM instantly if something goes wrong. Windows Server 2025 Hyper-V supports two checkpoint types:

  • Standard Checkpoints: Capture memory state along with disk state. Quick to create but the saved memory state can cause issues for domain-joined VMs or databases upon restore.
  • Production Checkpoints: Use Volume Shadow Copy Service (VSS) inside the guest to create an application-consistent snapshot without capturing live memory. Recommended for production workloads.
# Set checkpoint type for a VM (Production is recommended for servers)
Set-VM -Name "WEBSRV01" -CheckpointType Production

# Create a checkpoint before making changes
Checkpoint-VM -Name "WEBSRV01" -SnapshotName "Pre-Patch-$(Get-Date -Format 'yyyyMMdd-HHmm')"

# List all checkpoints for a VM
Get-VMCheckpoint -VMName "WEBSRV01" | Select-Object Name, CreationTime, CheckpointType | Format-Table

# Restore to the most recent checkpoint
$latestCheckpoint = Get-VMCheckpoint -VMName "WEBSRV01" | Sort-Object CreationTime | Select-Object -Last 1
Restore-VMCheckpoint -VMCheckpoint $latestCheckpoint -Confirm:$false

# Restore to a checkpoint by name
$checkpoint = Get-VMCheckpoint -VMName "WEBSRV01" -Name "Pre-Patch-20250517-1400"
Restore-VMCheckpoint -VMCheckpoint $checkpoint

# Delete a specific checkpoint (the VM's current disk state is unaffected)
Remove-VMCheckpoint -VMName "WEBSRV01" -Name "Pre-Patch-20250517-1400"

# Delete all checkpoints for a VM (merges checkpoint disks back into the primary VHDX)
Get-VMCheckpoint -VMName "WEBSRV01" | Remove-VMCheckpoint

Important: Checkpoints increase disk I/O and consume additional storage. Do not leave long-lived checkpoints on production VMs — always delete them once you have confirmed a change is stable.

Step 6: Export and Import Virtual Machines

Exporting a VM creates a self-contained copy that includes configuration XML, VHDX files, and any snapshots. This is the safest way to back up a VM, create a template, or move a VM to a different host without live migration.

# Export a VM to a folder (VM must be in a running, saved, or off state)
Export-VM -Name "WEBSRV01" -Path "E:VMExports"
# Result: E:VMExportsWEBSRV01 containing Virtual Machines, Virtual Hard Disks, and Snapshots

# Export multiple VMs in parallel using background jobs
Get-VM | ForEach-Object {
    Start-Job -ScriptBlock {
        param($vmName)
        Export-VM -Name $vmName -Path "E:VMExports" -Verbose
    } -ArgumentList $_.Name
}
Get-Job | Wait-Job | Receive-Job

# Import a VM from an export folder — Register (uses files in-place, fastest)
Import-VM -Path "E:VMExportsWEBSRV01Virtual Machines{GUID}.vmcx" `
          -Register

# Import with a copy — copies all files to the default VM path
Import-VM -Path "E:VMExportsWEBSRV01Virtual Machines{GUID}.vmcx" `
          -Copy `
          -VhdDestinationPath "D:Hyper-VVMsWEBSRV01" `
          -VirtualMachinePath "D:Hyper-VVMs"

# Import with a new unique ID — use when importing a duplicate on the same host
Import-VM -Path "E:VMExportsWEBSRV01Virtual Machines{GUID}.vmcx" `
          -Copy `
          -GenerateNewId `
          -VhdDestinationPath "D:Hyper-VVMsWEBSRV01-Copy" `
          -VirtualMachinePath "D:Hyper-VVMs"

Step 7: Move a VM to Another Host or Storage Location

The Move-VM cmdlet migrates a running or stopped VM to another Hyper-V host (live migration) or moves its storage to a different path on the same host (storage migration). For cross-host moves without shared storage, all VM files are transferred over the network while the VM continues running.

# Move VM storage to a different local path (same host, VM can remain running)
Move-VMStorage -VMName "WEBSRV01" `
               -DestinationStoragePath "E:Hyper-VVMsWEBSRV01"

# Live-migrate a running VM to another Hyper-V host (requires Live Migration to be enabled)
Move-VM -Name "WEBSRV01" `
        -DestinationHost "HVHOST02.contoso.local" `
        -IncludeStorage `
        -DestinationStoragePath "D:Hyper-VVMsWEBSRV01"

# Move VM to a host with shared storage (only VM configuration is transferred)
Move-VM -Name "WEBSRV01" `
        -DestinationHost "HVHOST02.contoso.local"

# Check migration status
Get-VM -ComputerName "HVHOST02.contoso.local" -Name "WEBSRV01"

Step 8: Manage VM Hard Disks

# Add a second VHDX to an existing VM (e.g., for application data)
New-VHD -Path "D:Hyper-VVMsWEBSRV01WEBSRV01-Data.vhdx" -SizeBytes 500GB -Dynamic
Add-VMHardDiskDrive -VMName "WEBSRV01" `
                    -ControllerType SCSI `
                    -ControllerNumber 0 `
                    -ControllerLocation 1 `
                    -Path "D:Hyper-VVMsWEBSRV01WEBSRV01-Data.vhdx"

# Expand an existing VHDX online (no downtime required with Windows Server 2025 guest)
Resize-VHD -Path "D:Hyper-VVMsWEBSRV01WEBSRV01-OS.vhdx" -SizeBytes 200GB

# List all hard disk drives attached to a VM
Get-VMHardDiskDrive -VMName "WEBSRV01" | Select-Object VMName, ControllerType, ControllerLocation, Path

Conclusion

Managing Hyper-V virtual machines on Windows Server 2025 through PowerShell gives you the precision and repeatability needed in production environments. In this tutorial you created VMs with both generation types, configured dynamic and static memory, attached ISO images, managed checkpoints using both standard and production types, and handled the full lifecycle of exporting, importing, and moving VMs between hosts and storage locations. With these skills you can build repeatable provisioning scripts, automate routine maintenance, and confidently manage a fleet of virtual machines across one or more Hyper-V hosts. The next step is mastering virtual networking — covered in the following article in this series.