Powershell - Test-Connection failed due to lack of resources

Windows IP Helper defines IP_REQ_TIMED_OUT error to value 11010 wich is the same as Windows system error WSA_QOS_ADMISSION_FAILURE 11010 'Error due to lack of resources.' so it is likely that what actually received in questioned case was time out error and simply misinterpreted as 'lack of resources'.


In newer versions of PowerShell, the -Quiet parameter on Test-Connection does seem to always return either True or False. It didn't seem to work consistently on older versions, but either I'm doing something differently now or they've improved it:

$Ping = Test-Connection -ComputerName $ComputerName -Count 1 -Quiet

I haven't tested it recently when the network is simply unavailable, however.


Older answer:

Test-Connection doesn't respond well when DNS doesn't respond with an address or when the network is unavailable. That is, if the cmdlet decides it can't send the ping at all, it errors in unpleasant ways that are difficult to trap or ignore. Test-Connection is only useful, then, when you can guarantee that DNS will resolve the name to an address, and that the network will always be present.

I tend to use CIM Pings (Powershell v3+):

$Ping2 = Get-CimInstance -ClassName Win32_PingStatus -Filter "Address='$ComputerName' AND Timeout=1000";

Or WMI pings (Powershell v1 or v2):

$Ping = Get-WmiObject -Class Win32_PingStatus -Filter "Address='$ComputerName' AND Timeout=1000";

Either of which are basically the same, but return slightly different formats for things. Note that Get-WmiObject is not available at all beginning in Powershell v6 because Get-CimInstance was designed to supersede it.

The main disadvantage here is that you have to resolve the status code yourself:

$StatusCodes = @{
    [uint32]0     = 'Success';
    [uint32]11001 = 'Buffer Too Small';
    [uint32]11002 = 'Destination Net Unreachable';
    [uint32]11003 = 'Destination Host Unreachable';
    [uint32]11004 = 'Destination Protocol Unreachable';
    [uint32]11005 = 'Destination Port Unreachable';
    [uint32]11006 = 'No Resources';
    [uint32]11007 = 'Bad Option';
    [uint32]11008 = 'Hardware Error';
    [uint32]11009 = 'Packet Too Big';
    [uint32]11010 = 'Request Timed Out';
    [uint32]11011 = 'Bad Request';
    [uint32]11012 = 'Bad Route';
    [uint32]11013 = 'TimeToLive Expired Transit';
    [uint32]11014 = 'TimeToLive Expired Reassembly';
    [uint32]11015 = 'Parameter Problem';
    [uint32]11016 = 'Source Quench';
    [uint32]11017 = 'Option Too Big';
    [uint32]11018 = 'Bad Destination';
    [uint32]11032 = 'Negotiating IPSEC';
    [uint32]11050 = 'General Failure'
    };
$StatusCodes[$Ping.StatusCode];
$StatusCodes[$Ping2.StatusCode];

Alternately, I've used .Net Pings like @BenH described, too, which does a lot of that work for you. There was a reason I stopped using them in favor of WMI and CIM, but I can no longer remember what that reason was.


I am partial to using the .Net Ping class rather than Test-Connection

$Timeout = 100
$Ping = New-Object System.Net.NetworkInformation.Ping
$Response = $Ping.Send($Name,$Timeout)
$Response.Status

Note that the Send method can take additional parameters if you need to set TTL/Fragmentation. Also timeout is in milliseconds, with just $name the timeout I think is 5 seconds, which is usually too long.