Monday, May 6, 2013

Using powershell to get a detailed report of your hyper-v Server and VM's running on it

This is now officially a free part of microsofts Codeplex project at Yeah!
This has now been added to a free GUI powershell hyper-v manager.

Just released a new hyper-v manager that is free for non commercial use and pay for use if commercial.

I endorse this product as I helped in it's design and features and the GUI is much better than my product.

Probus-IT Hyper-V Manager (HVM) will help you to manage Hyper-V Servers and virtual machines. It is especially useful on core installations where you cannot run Microsoft Hyper-V manager locally. No RSAT or DOT-Net install needed. No fiddling with cmdkey and HVRemote-scripts. Installs on 32 and 64-Bit windows. Use it on Servers, desktops and Core installations both 32 and 64-Bit.
Thanks Håkan Lindén


Single Powershell script to get a detailed report of your Vhosts and its VM's , works in Core and Datacenter 2012 versions running powershell 3.0. You can kick it off with a batch file see below or simply right-click on it and choose run with powershell if you have a GUI desktop.

Create directory structure C:\software\reports
save the below 2 lines as getreport.bat and save to C:\software then sent to desktop as link.

call powershell C:\software\getvmlist.ps1

Save the below as getvmreport.ps1 to C:\software\
if you want to download them go to

Contents of getvmlist.ps1

ECHO "RUNNING THE REPORT NOW...takes approximately 2 minutes"

# Variables
$DateStamp = get-date -uformat "%m-%d-%Y"
# path and filename for report file
$file = "C:\software\reports\Report_$DATEStamp.txt"
$VMS = get-vm
$computers = $Env:COMPUTERNAME

# put todays date and time in the file
echo "Date report was ran" | out-file $file
get-date | out-file $file -append

# get the vhost uptime
Get-CimInstance Win32_OperatingSystem -comp $computers | Select @{Name="VHostName";Expression={$_."csname"}},@{Name="Uptime=D.H:M:S.Millseconds";Expression={(Get-Date) - $_.LastBootUpTime}},LastBootUpTime | format-table -autosize | out-file $file -append

# get the vhost name, total virtual CPU count, total RAM, virtualharddiskpath and virtualmachinepath
Get-VMHost | Select @{Name="VHostName";Expression={$_."Name"}},@{N="Total RAM(GB)";E={""+ [math]::round($_.Memorycapacity/1GB)}},logicalprocessorcount,virtualharddiskpath,virtualmachinepath | format-table -autosize | out-file $file -append

echo "VHOST Server IP Addresses and NIC's" | out-file $file -append
Get-WMIObject win32_NetworkAdapterConfiguration |   Where-Object { $_.IPEnabled -eq $true } | Select IPAddress,Description | format-table -autosize | out-file $file -append

echo "VHOST Server drive C: Disk Space" | out-file $file -append
# to get D: drive add ,D after C  - E: drive ,E etc.
Get-psdrive C | Select Root,@{N="Total(GB)";E={""+ [math]::round(($$_.used)/1GB)}},@{N="Used(GB)";E={""+ [math]::round($_.used/1GB)}},@{N="Free(GB)";E={""+ [math]::round($}} |format-table -autosize | out-file $file -append

echo "VHosts virtual switch(s) information" | out-file $file -append
get-vmswitch * | out-file $file -append

echo "Total number of VM's on server" | out-file $file -append
echo "------------------------------" | out-file $file -append
$VMS.Count | out-file $file -append
echo " " | out-file $file -append

echo "NOTE: Nothing listed under DVD Media Path = Nothing mounted in DVD" | out-file $file -append
$outputArray = @()
foreach($VM in $VMS)
      $VMsRAM = [math]::round($VM.Memoryassigned/1GB)
      $VMsCPU = $VM.processorCount
      $VMsState = $VM.State
      $VMsStatus = $VM.Status
      $VMsUptime = $VM.Uptime
      $VMsAutomaticstartaction = $VM.Automaticstartaction
      $VMsIntegrationServicesVersion = $VM.IntegrationServicesVersion
      $VMsReplicationState = $VM.ReplicationState
      $VHDs = Get-VHD -VMId $VM.VMiD
      $VHDsGB = [math]::round($VHDs.FileSize/1GB)
      $VMDVD = Get-vmdvddrive -VMname $VM.VMname
      $output = new-object psobject
      $output | add-member noteproperty "VM Name" $VM.Name
      $output | add-member noteproperty "RAM(GB)" $VMsRAM
      $output | add-member noteproperty "vCPU" $VMsCPU
      $output | add-member noteproperty "State" $VMsState
      $output | add-member noteproperty "Status" $VMsStatus
      $output | add-member noteproperty "Uptime" $VMsUptime
      $output | add-member noteproperty "Start Action" $VMsAutomaticstartaction
      $output | add-member noteproperty "Integration Tools" $VMsIntegrationServicesVersion
      $output | add-member noteproperty "Replication State" $VMsReplicationState
      $output | add-member noteproperty "VHD Path" $VHDs.Path
      $output | add-member noteproperty "Size GB" $VHDsGB
      $output | add-member noteproperty "VHD Type" $VHDs.vhdtype
      $output | add-member noteproperty "VHD Format" $VHDs.vhdformat
      $output | add-member noteproperty "DVD Media Type" $VMDVD.dvdmediatype
      $output | add-member noteproperty "DVD Media Path" $VMDVD.path
      $outputArray += $output
write-output $outputarray | sort "VM Name" | format-table * -autosize | out-string -width 600 | out-file $file -append

Echo "VM's BIOS setting" | out-file $file -append
get-vmbios *  | sort "VMName" | Format-Table -autosize | out-file $file -append

echo "VM's Virtual Switch name and IP address" | out-file $file -append
get-vmnetworkadapter * | Select vmname,switchname,ipaddresses | sort "VMName" | format-table -autosize | out-file $file -append

echo "VM's Snapshot and location" | out-file $file -append
echo "If nothing is Listed below, then there are no Snapshots" | sort "VMName" | format-table -autosize | out-file $file -append
get-vmsnapshot -vmname * | out-file $file -append

#load the report in notepad
notepad.exe "C:\software\reports\Report_$DATEStamp.txt"

Output of the report.bat to C:\softeware\reports\report_%date%.txt

Date report was ran
Thursday, May 23, 2013 2:27:52 PM

VHostName Uptime=D.H:M:S.Millseconds LastBootUpTime    
--------- -------------------------- --------------    
VHOST1    21.02:41:19.8376964        5/2/2013 11:46:32 AM

VHostName Total RAM(GB) LogicalProcessorCount VirtualHardDiskPath VirtualMachinePath
--------- ------------- --------------------- ------------------- ------------------
VHOST1    192                              32        C:\VirtualServers   C:\VirtualServers

VHOST Server IP Addresses and NIC's
IPAddress                                   Description                                            
---------                                   -----------                                            
{, fe80::5c8b:7bd6:cb53:2ccd}    Hyper-V Virtual Ethernet Adapter #2                    

VHOST Server drive C: Disk Space
Root Total(GB) Used(GB) Free(GB)
---- --------- -------- --------
C:\  1675      918      757  

VHosts virtual switch(s) information
Name         SwitchType NetAdapterInterfaceDescription                        
----         ---------- ------------------------------                        
PROD Network External   Broadcom BCM5709C NetXtreme II GigE (NDIS VBD Client) #36

Total number of VM's on server

NOTE: Nothing listed under DVD Media Path = Nothing mounted in DVD
VM Name                       RAM(GB) vCPU   State Status             Uptime        Start Action Integration Tools Replication State VHD Path                                                                          Size GB VHD Type VHD Format DVD Media Type DVD Media Path
-------                       ------- ----   ----- ------             ------        ------------ ----------------- ----------------- --------                                                                          ------- -------- ---------- -------------- --------------
TEST1                               2    1 Running Operating normally 8.11:18:28  StartIfRunning 6.2.9200.16384             Disabled C:\VirtualServers\Test1\test1-2008r2.vhdx                                              70    Fixed       VHDX           None            

VM's BIOS setting
VMName                        StartupOrder                            NumLockEnabled
------                        ------------                            --------------
TEST1                         {CD, IDE, LegacyNetworkAdapter, Floppy} True      

VM's Virtual Switch name and IP address
VMName                        SwitchName   IPAddresses                                        
------                        ----------   -----------                                        
TEST1                         PROD Network {, fe80::8929:b7c0:6427:1b29}            

VM's Snapshot and location
If nothing is Listed below, then there are no Snapshots

You now have a detailed report file that tells you the :
The Reports data and time
The Vhost's Name and Uptime
The Vhost's amount of RAM,Virtual CPUs,the virtual hard disk path and virtual machine path.
The Vhosts IP addresses, MACs and NIC Description
The Vhost disk space available on drive C: (you can add as many drives as you need in the script)
The Vhosts Virtual switches and their names
The Total # of VM's on the VHost and their: Name, RAM(GB), vCPU Count, State, Status, Uptime, AutomaticStartAction, IntegrationServicesVersion
The VM's BIOS setting (startorder and num-lock state)
*The VM's Virtual Switch it is attached to and IP address/MAC
The VM's DVD information and if anything is mounted
The VM's Hard drive file location, type, format and size
The VM's snapshots and location

* If you know for a fact your VM's have a NIC and IP address but the report shows none, you need to install the latest Microsoft Integration tools in order for the powershell scrip to see your VM's IP.

You can use the task scheduler i talked about in the backups blog post to autorun this during the day and them use a dos command line emailer to send you the file in email via smtp.


  1. I ran it and I got no VMs. what latest Microsoft Integration tools do I need to install

  2. Some lines need to be replaced in order to work with multiple VHDs:

    $VHDs = Get-VHD -VMId $VM.VMiD
    #$VHDsGB = [math]::round($VHDs.FileSize/1GB)
    foreach ($VHD in $VHDs) {
    $VHDsGB += [math]::round($VHD.FileSize/1GB)

  3. hi, this is a good script but can you please help to customize it? actually i need this for all the hosts in my environment and how can we execute it remotely.

    1. You could script it to connect using:
      Connect-PSSession -ComputerName BAVM1
      have the .ps1 file in a shared drive and call it from each machine.
      The result name could include the machines name:
      $file = "\\Server1\data\Report_$Env:COMPUTERNAME_$DATEStamp.txt"
      Didn't check it out myself.

  4. This comment has been removed by the author.

  5. Great script !
    I have added the following VHDs health check to it:

    Echo "Active VM's VHD health check" | out-file $file -append
    $VHDsInUse = $VMS.VMID | Get-VHD | Select-Object Path
    $VHDsInUse | select Path,@{n="Test";Expression={ Test-VHD $_.Path}} | sort Test | out-file $file -append

    Echo "VHD health check for Orphan/Parent VHDs" | out-file $file -append
    $VHDFiles = dir (Get-VMHost).VirtualHardDiskPath | Select FullName
    $OrphanVHD = @()
    foreach($VHD in $VHDFiles) {
    if(($VHDsInUse.Path -notcontains $VHD.FullName) -and ($VHD.FullName -like "*.vhd*")){
    $OrphanVHD += $VHD}}
    $OrphanVHD | Select FullName,@{n="Test";Expression={ Test-VHD $_.fullname}} | sort Test | out-file $file -append