CPing
v1.53 A C++ class to encapsulate "Ping" on Windows
Included is a C++ class to support the PING/ICMP protocol. ICMP for those not
familiar with all the internet protocols is the protocol used to retrieve information
about how IP packets are routed.
Features
- Simple and clean C++ interface.
- The interface provided is synchronous which provides an easier programming
model than using asynchronous sockets.
- A configurable timeout for the connection can be set through the class API.
- The classes are fully Unicode compliant and include Unicode built options
in the workspace file.
The enclosed zip file contains the CPing source
code and a simple test program to exercise all of the functions the classes provide.
Copyright
- You are allowed to include the source code in any product (commercial, shareware,
freeware or otherwise) when your product is released in binary form.
- You are allowed to modify the source code in any way you want except you
cannot modify the copyright details at the top of each module.
- If you want to distribute source code with your application, then you are
only allowed to distribute versions released by the author. This is to maintain
a single distribution point for the source code.
Updates
v1.53 (18 March 2022)
- Updated copyright details.
- Updated the code to use C++ uniform initialization for all variable
declarations.
v1.52 (10 December 2021)
- Made a number of methods nodiscard.
- Replaced ATL::CHeapPtr<BYTE> with std::vector<BYTE>.
v1.51 (30 March 2021)
- Updated copyright details.
- Updated the PingUsingICMPv4 and PingUsingICMPv6 methods to preserve the
last error value across calls to IcmpCloseHandle. Thanks to Geoff Shapiro
for reporting this issue.
v1.50 (28 March 2020)
- Updated copyright details.
- Fixed more Clang-Tidy static code analysis warnings in the code.
v1.49 (29 December 2019)
- Fixed various Clang-Tidy static code analysis warnings in the code.
v1.48 (10 November 2019)
- Updated initialization of various structs to use C++ 11 list
initialization
- Replaced BOOL with bool in a number of places throughout the codebase
v1.47 (3 May 2019)
- Updated copyright details.
- Updated the code to clean compile on VC 2019
v1.46 (3 November 2018)
- Updated copyright details.
- Fixed a number of C++ core guidelines compiler warnings. These changes
mean that the code will now only compile on VC 2017 or later.
- Removed all code which used GetProcAddress in the sample app.
v1.45 (26 December 2017)
- Updated copyright details.
- Replaced CString::operator LPC*STR() calls throughout the codebase with
CString::GetString calls
- Replaced NULL throughout the codebase with nullptr. This means that the
minimum requirement for the code is now VC 2010.
- Removed all the code which uses GetProcAddress to access the functions
in Iphlpapi.dll. Instead now the code implicitly links to Iphlpapi.dll.
v1.44 (8 May 2016)
- Minor update to the header file inclusions in ping.cpp, ping.h and
stdafx.h
v1.43 (6 May 2016)
- Split CPingReply class into two separate CPingReplyv4 and CPingReplyv6 classes.
v1.42 (2 May 2016)
- Updated copyright details.
- Updated the sample project settings to more modern default values.
- Updated the code to compile cleanly on VC 2010 - 2015.
- Replaced all calls to TRACE with ATLTRACE
- Code no longer uses LoadLibrary without an absolute path when loading Iphlpapi
/ ICMP dlls. This avoids DLL planting security issues.
- Removed code from CPing::DecodeResponse which checks i_type & i_id header
values.
- Made class MFC independent. Now the code only depends on ATL.
- Removed code from CPing::PingUsingICMP which parses the response.
- Added support for IPv6 in addition to IPv4. This means that the minimum
supported version of VC which supports CPing is now VC 2008. The sample now
ships with a VC 2008 solution.
- Code now supports IcmpSendEcho2Ex which supports IPv4 source address binding
- Removed the PingUsingWinsock method from the class as all the ping functionality
can now be achieved via the Icmp* Windows API calls. This means that the CPING_NO_ICMP
and CPING_NO_WINSOCK2 preprocessor values are defunct and have been removed.
- Added SAL annotations to all the code.
- Added support for the IP_FLAG_REVERSE IP_OPTION_INFORMATION flag.
- Addition of GetICMP_ECHO_REPLY and GetICMPV6_ECHO_REPLY methods to the CPingReply
class which allow access to the raw ICMP echo reply structure.
v1.41 (7 June 2008)
- Updated copyright details
- Updated the sample app to clean compile on VC 2008
- Code now compiles cleanly using Code Analysis (/analyze)
- The code has now been updated to support VC 2005 or later only
- Replaced all calls to ZeroMemory with memset
- Code now uses ATL::CHeapPtr for managed raw buffers
- The "Bind", "FillIcmpData", "DecodeResponse"
and "GenerateIPChecksum" methods have been made virtual. This for
example allows client code to decide what data gets put into ICMP request packets.
Thanks to Dinci Glas for prompting this update.
v1.40 (10 July 2006)
- Updated copyright details
- The code now requires the Platform SDK if compiled using VC 6.
- Integrated the functionality of _CPING_ICMP class into CPing
- Optimized CPingReply constructor code
- Code now uses newer C++ style casts instead of C style casts.
- Addition of CPING_EXT_CLASS macro to allow the code to be easily added to
an extension dll.
- Code now uses newer C++ style casts instead of C style casts.
- Updated the code to clean compile on VC 2005.
- Updated documentation to use the same style as the web site.
v1.39 (31 July 2005)
- Now the PingUsingICMP method using the versions provided in the IP Helper
dll namely "Iphlpapi.dll" before falling back to "ICMP.dll".
- Tidied up the various ICMP defines by making them part of the _CPING_ICMP
class
v1.38 (31 July 2005)
- When sending a ping, the allowable size of the data in the packet can now
be anywhere from 0 to 65500. Previosuly sending a ping using Winsock was limited
to a data size of 1024 and when using ICMP.dll, the size was limited to 255.
Thanks to Leon Luu for reporting this issue.
v1.37 (11 June 2005)
- Reviewed all TRACE statements for correctness. Thanks to "Grenal" for reporting
this issue.
- Checked all premature return points in the codebase to ensure the last error
value is preserved.
- Fixed an unreferrenced variable in DecodeResponse function when code is
compiled with Visual Studio .NET 2003
v1.36 (12 April 2004)
- Fixed a bug in the declaration of h_len and version in the IP_HEADER structure.
Also made the source and destination IP addresses longs instead of ints to avoid
any porting problems. Thanks to Yuh-Rong Leu for reporting this problem.
- Fixed a bug in PingUsingWinsock when a timeout occurs and it returns TRUE.
Thanks to Yuh-Rong Leu for reporting this problem.
- Updated the documentation to refer to using the value from GetCurrentThreadId()
for the nSequenceNumber parameter when calling the PingUsingWinsock function.
Again thanks to Yuh-Rong Leu for reporting this issue.
- Fixed an issue in DecodeResponse where if bTryAgain was set to TRUE, the
return value was incorrectly also being set to TRUE. Thanks to Yuh-Rong Leu
for reporting this issue.
v1.35 (23 November 2003)
- Fixed a level 4 warning in VC 6 in the function CPing::PingUsingWinsock.
27 June 2003
- Updated the documentation including description of PingUsingWinsock function
plus a general review
v1.34 (13 March 2003)
- Fixed a bug in CPing::IsSocketReadible in the setup of the timval structure.
Thanks to "InBloom Support" for reporting this.
v1.33 (10 March 2003)
- Fixed a bug where using PingUsingWinsock and setting the data size greater
than 1004 appears to cause Winsock error 10040 - The datagram is too large to
fit into the buffer and is truncated. Thanks to Paul Golightly for reported
this and provided the fix.
v1.32 (22 November 2002)
- Fixed an issue in the calculation of the packet size when sending using
raw sockets.
- Default sample now uses a default TTL of 30
- Changes the nPacketSize parameter to the Ping method to be nDataSize which
is what it really is.
- Reviewed all the TRACE messages for correctness
- Made all the helper functions used by the code member functions of the class
- General tidy up of the various defines
- Winsock 2 version of ping now allows you to specify the sequence number
of the packet. This allows the ping to exclude packets from the same process
id which are being generated by for example another thread.
- Fixed a bug in the call to recvfrom. The receive buffer size was not being
specified correctly.
- ICMP response packets from other processes are now ignored when waiting
for an ICMP response
- ICMP response packets from the same process but which have an incorrect
sequence number are now ignored when waiting for an ICMP response.
- Fix a resource leak of a socket when unexpected failures occur in the CPing::PingUsingWinsock
function
v1.31 (5 May 2002)
- Now includes a EchoReplyStatus in CPingReply structure if CPING_NO_ICMP
is not defined.
23 March 2002
- Fixed an issue in the sample app which could result in a crash if the app
was requested to resolve host names but the lookup fails. The CPing code has
not been updated just the sample app code.
v1.3 (25 February 2002)
- Winsock 2 code path now allows you to bind the socket to a specific NIC.
This can prove useful when you want to run a targeted ping request on a mulithoned
machine.
- Tidied up the code in the sample application
- Provide a complete set of command line options for the sample app. It now
provides almost a 1 - 1 implementation of the built in Ping options.
- Completly reworked and recoded all the CPing code.
- Client code is now responsible for initializing Winsock instead of having
it embedded in the CPing code.
v1.24 (12 January 2002)
- Updated copyright information.
- Now initializes Winsock 2.0 instead of Winsock 2.1. Thanks to Lev Elbert
for spotting this problem.
v1.23 (15 July 2001)
- Updated copyright information
- Code now automatically pulls in the Winsock 2 libraries as and when needed
v1.22 (1 March 2000)
- Fixed a problem where I was incorrectly overwritting memory in the function
FillIcmpData.
- tidied up the console info issued by CPing.
- Minor changes to the way the demo program is initialized (main Vs tmain
etc.)
v1.21 (9 November 1998)
- Now ships with a VC 5 workspace file instead of VC 6. This is mainly because
a lot of people have not migrated to it yet.
- Workspace file now includes configurations to allow both the Winsock 2 and
ICMP based code to be exercised.
- Fixed a level 4 warning which was occurring.
- Removed a number of compiler errors which was occurring when code was compiled
to use the ICMP or Winsock 2.
- Fixed a bug whereby a ping to a non-existent host using the Winsock 2 method
blocked indefinitely.
- Fixed a socket handle leak which was occurring if the Winsock 2 method of
pinging was used.
- Fixed error in API documentation when compared with the actual header file.
- Fixed error in API documentation regarding default timeouts value.
v1.2 (30 July 1998)
- Can now use both Winsock 2 calls and ICMP style calls at the same time with
the use of 2 preprocessor directives.
- sample program now use generic entry point _tmain.
- Got rid of a 2 level 4 compiler warnings.
- Fixed a problem with the cleanup of ICMP dll usage.
- Tidied up and optimized the usage of static variables.
- VC++ 6.0 project file is now used for the sample so beware.
v1.1 (23 June 1998)
- The class now supports using Winsock 2 calls instead of using the ICMP dll.
To use Winsock 2 calls in CPing instead of the ICMP dll, just define the preprocessor
constant "CPING_USE_WINSOCK2" and don't forget to link to "ws2_32.lib".
v1.0 (11 June 1998)