From 9d8faf2b01ab01ce46010f67e8eed330190b4033 Mon Sep 17 00:00:00 2001 From: Guilherme Maciel Ferreira Date: Thu, 3 Mar 2011 16:15:10 +0100 Subject: [PATCH] Moved ICMP abstraction classes to the icmp directory, leaving the ping directory only for ping classes --- src/CMakeLists.txt | 7 ++- src/icmp/checksumcalculator.h | 70 ++++++++++++++++++++++++ src/icmp/icmpchecksumcalculator.h | 13 +++++ src/icmp/icmpdata.h | 12 ++++ src/icmp/icmpheader.cpp | 109 +++++++++++++++++++++++++++++++++++++ src/icmp/icmpheader.h | 87 +++++++++++++++++++++++++++++ src/icmp/icmppacket.cpp | 74 +++++++++++++++++++++++++ src/icmp/icmppacket.h | 89 ++++++++++++++++++++++++++++++ src/icmp/ipv4header.cpp | 106 ++++++++++++++++++++++++++++++++++++ src/icmp/ipv4header.h | 78 ++++++++++++++++++++++++++ src/ping/checksumcalculator.h | 70 ------------------------ src/ping/icmpchecksumcalculator.h | 13 ----- src/ping/icmpdata.h | 12 ---- src/ping/icmpheader.cpp | 109 ------------------------------------- src/ping/icmpheader.h | 87 ----------------------------- src/ping/icmppacket.cpp | 74 ------------------------- src/ping/icmppacket.h | 89 ------------------------------ src/ping/ipv4header.cpp | 106 ------------------------------------ src/ping/ipv4header.h | 78 -------------------------- 19 files changed, 642 insertions(+), 641 deletions(-) create mode 100644 src/icmp/checksumcalculator.h create mode 100644 src/icmp/icmpchecksumcalculator.h create mode 100644 src/icmp/icmpdata.h create mode 100644 src/icmp/icmpheader.cpp create mode 100644 src/icmp/icmpheader.h create mode 100644 src/icmp/icmppacket.cpp create mode 100644 src/icmp/icmppacket.h create mode 100644 src/icmp/ipv4header.cpp create mode 100644 src/icmp/ipv4header.h delete mode 100644 src/ping/checksumcalculator.h delete mode 100644 src/ping/icmpchecksumcalculator.h delete mode 100644 src/ping/icmpdata.h delete mode 100644 src/ping/icmpheader.cpp delete mode 100644 src/ping/icmpheader.h delete mode 100644 src/ping/icmppacket.cpp delete mode 100644 src/ping/icmppacket.h delete mode 100644 src/ping/ipv4header.cpp delete mode 100644 src/ping/ipv4header.h diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 8d8f4e3..2c5bf24 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,6 +1,7 @@ # include directories where the source code is located include_directories( config + icmp ping ${Boost_INCLUDE_DIRS} ) @@ -9,11 +10,11 @@ include_directories( set( SOURCES config/configuration.cpp config/configurationreader.cpp + icmp/icmpheader.cpp + icmp/icmppacket.cpp + icmp/ipv4header.cpp ping/boostpinger.cpp ping/host.cpp - ping/icmpheader.cpp - ping/icmppacket.cpp - ping/ipv4header.cpp ping/pingcheck.cpp ping/pinger.cpp main.cpp diff --git a/src/icmp/checksumcalculator.h b/src/icmp/checksumcalculator.h new file mode 100644 index 0000000..9b5b657 --- /dev/null +++ b/src/icmp/checksumcalculator.h @@ -0,0 +1,70 @@ +#ifndef CHECKSUMCALCULATOR_H +#define CHECKSUMCALCULATOR_H + +#include + +//----------------------------------------------------------------------------- +// ChecksumCalculator +//----------------------------------------------------------------------------- + +template +class ChecksumCalculator +{ +public: + ChecksumCalculator( + Iterator body_begin, + Iterator body_end + ); + + uint16_t compute( + uint8_t type, + uint8_t code, + uint16_t identifier, + uint16_t sequence_number + ); + +private: + Iterator body_begin; + Iterator body_end; + +}; + +template + ChecksumCalculator::ChecksumCalculator( + Iterator body_begin, + Iterator body_end + ) : + body_begin(), + body_end() + { + this->body_begin = body_begin; + this->body_end = body_end; + } + +template + uint16_t ChecksumCalculator::compute( + uint8_t type, + uint8_t code, + uint16_t identifier, + uint16_t sequence_number + ) + { + uint32_t sum = (type << 8) + code + identifier + sequence_number; + + Iterator body_iter = body_begin; + while ( body_iter != body_end ) + { + sum += (static_cast ( *body_iter++ ) << 8); + if ( body_iter != body_end ) + sum += static_cast ( *body_iter++ ); + } + + sum = (sum >> 16) + (sum & 0xFFFF); + sum += (sum >> 16); + + uint16_t checksum = static_cast ( ~sum ); + + return checksum; + } + +#endif /* CHECKSUMCALCULATOR_H */ diff --git a/src/icmp/icmpchecksumcalculator.h b/src/icmp/icmpchecksumcalculator.h new file mode 100644 index 0000000..fe08d3e --- /dev/null +++ b/src/icmp/icmpchecksumcalculator.h @@ -0,0 +1,13 @@ +#ifndef ICMPCHECKSUMCALCULATOR_H +#define ICMPCHECKSUMCALCULATOR_H + +#include "checksumcalculator.h" +#include "icmpdata.h" + +//----------------------------------------------------------------------------- +// IcmpChecksumCalculator +//----------------------------------------------------------------------------- + +typedef ChecksumCalculator IcmpChecksumCalculator; + +#endif /* ICMPCHECKSUMCALCULATOR_H */ diff --git a/src/icmp/icmpdata.h b/src/icmp/icmpdata.h new file mode 100644 index 0000000..d17c199 --- /dev/null +++ b/src/icmp/icmpdata.h @@ -0,0 +1,12 @@ +#ifndef ICMPDATA_H +#define ICMPDATA_H + +#include + +//----------------------------------------------------------------------------- +// IcmpData +//----------------------------------------------------------------------------- + +typedef std::string IcmpData; + +#endif /* ICMPDATA_H */ diff --git a/src/icmp/icmpheader.cpp b/src/icmp/icmpheader.cpp new file mode 100644 index 0000000..9ca552c --- /dev/null +++ b/src/icmp/icmpheader.cpp @@ -0,0 +1,109 @@ +#include "icmpheader.h" + +//----------------------------------------------------------------------------- +// IcmpHeader +//----------------------------------------------------------------------------- + +IcmpHeader::IcmpHeader() +{ + std::fill( Rep, Rep + sizeof(Rep), 0 ); +} + +IcmpHeader::IcmpHeader( + IcmpHeader::IcmpType type, + uint8_t code, + uint16_t checksum, + uint16_t identifier, + uint16_t sequence_number +) +{ + std::fill( Rep, Rep + sizeof(Rep), 0 ); + + set_type( type ); + set_code( code ); + set_checksum( checksum ); + set_identifier( identifier ); + set_sequence_number( sequence_number ); +} + +IcmpHeader::IcmpType IcmpHeader::get_type() const +{ + uint8_t n = Rep[ 0 ]; + IcmpHeader::IcmpType type = static_cast ( n ); + + return type; +} + +void IcmpHeader::set_type( IcmpHeader::IcmpType type ) +{ + uint8_t n = type; + + Rep[ 0 ] = n; +} + +uint8_t IcmpHeader::get_code() const +{ + return Rep[ 1 ]; +} + +void IcmpHeader::set_code( uint8_t code ) +{ + Rep[ 1 ] = code; +} + +uint16_t IcmpHeader::get_checksum() const +{ + return decode( 2, 3 ); +} + +void IcmpHeader::set_checksum( uint16_t checksum ) +{ + encode( 2, 3, checksum ); +} + +uint16_t IcmpHeader::get_identifier() const +{ + return decode( 4, 5 ); +} + +void IcmpHeader::set_identifier( uint16_t identifier ) +{ + encode( 4, 5, identifier ); +} + +uint16_t IcmpHeader::get_sequence_number() const +{ + return decode( 6, 7 ); +} + +void IcmpHeader::set_sequence_number( uint16_t sequence_number ) +{ + encode( 6, 7, sequence_number ); +} + +std::istream& operator>>( + std::istream &is, + IcmpHeader &header +) +{ + return is.read( reinterpret_cast ( header.Rep ), 8 ); +} + +std::ostream& operator<<( + std::ostream &os, + const IcmpHeader &header +) +{ + return os.write( reinterpret_cast ( header.Rep ), 8 ); +} + +uint16_t IcmpHeader::decode( int a, int b ) const +{ + return ( Rep[ a ] << 8 ) + Rep[ b ]; +} + +void IcmpHeader::encode( int a, int b, uint16_t n ) +{ + Rep[ a ] = static_cast ( n >> 8 ); + Rep[ b ] = static_cast ( n & 0xFF ); +} diff --git a/src/icmp/icmpheader.h b/src/icmp/icmpheader.h new file mode 100644 index 0000000..ae354d3 --- /dev/null +++ b/src/icmp/icmpheader.h @@ -0,0 +1,87 @@ +#ifndef ICMP_HEADER_HPP +#define ICMP_HEADER_HPP + +#include +#include +#include + +//----------------------------------------------------------------------------- +// IcmpHeader +//----------------------------------------------------------------------------- +// ICMP header format +// +// 0 8 16 31 +// +---------------+---------------+------------------------------+ --- +// | | | | ^ +// | type | code | checksum | | +// | | | | | +// +---------------+---------------+------------------------------+ 8 bytes +// | | | | +// | identifier | sequence number | | +// | | | v +// +-------------------------------+------------------------------+ --- +// +//----------------------------------------------------------------------------- + +class IcmpHeader +{ +public: + enum IcmpType + { + EchoReply = 0, + DestinationUnreachable = 3, + SourceQuench = 4, + Redirect = 5, + EchoRequest = 8, + TimeExceeded = 11, + ParameterProblem = 12, + TimestampRequest = 13, + TimestampReply = 14, + InfoRequest = 15, + InfoReply = 16, + AddressRequest = 17, + AddressReply = 18 + }; + + IcmpHeader(); + IcmpHeader( + IcmpType type, + uint8_t code, + uint16_t checksum, + uint16_t identifier, + uint16_t sequence_number + ); + + IcmpType get_type() const; + void set_type( const IcmpType type ); + + uint8_t get_code() const; + void set_code( const uint8_t code ); + + uint16_t get_checksum() const; + void set_checksum( const uint16_t checksum ); + + uint16_t get_identifier() const; + void set_identifier( const uint16_t identifier ); + + uint16_t get_sequence_number() const; + void set_sequence_number( const uint16_t sequence_number ); + + friend std::istream& operator>>( + std::istream &is, + IcmpHeader &header + ); + friend std::ostream& operator<<( + std::ostream &os, + const IcmpHeader &header + ); + +private: + uint16_t decode( int a, int b ) const; + void encode( int a, int b, uint16_t n ); + + uint8_t Rep[ 8 ]; + +}; + +#endif // ICMP_HEADER_H diff --git a/src/icmp/icmppacket.cpp b/src/icmp/icmppacket.cpp new file mode 100644 index 0000000..a8ab37d --- /dev/null +++ b/src/icmp/icmppacket.cpp @@ -0,0 +1,74 @@ +#include "icmppacket.h" + +//----------------------------------------------------------------------------- +// IcmpPacket +//----------------------------------------------------------------------------- + +IcmpPacket::IcmpPacket() : + IpHeader(), + IcmpPayloadHeader(), + IcmpPayloadData() +{ +} + +IcmpPacket::IcmpPacket( + const IcmpHeader &icmp_header, + const IcmpData &icmp_data +) : + IpHeader(), + IcmpPayloadHeader( icmp_header ), + IcmpPayloadData( icmp_data ) +{ +} + +IcmpPacket::~IcmpPacket() +{ +} + +Ipv4Header IcmpPacket::get_ip_header() const +{ + return IpHeader; +} + +IcmpHeader IcmpPacket::get_icmp_header() const +{ + return IcmpPayloadHeader; +} + +IcmpData IcmpPacket::get_icmp_data() const +{ + return IcmpPayloadData; +} + +bool IcmpPacket::match( + IcmpHeader::IcmpType type, + uint16_t identifier, + uint16_t sequence_number +) +{ + bool type_match = IcmpPayloadHeader.get_type() == type; + bool identifier_match = IcmpPayloadHeader.get_identifier() == identifier; + bool seq_num_match = IcmpPayloadHeader.get_sequence_number() == sequence_number; + + return ( type_match && identifier_match && seq_num_match ); +} + +std::istream& operator>>( + std::istream &is, + IcmpPacket &packet +) +{ + is >> packet.IpHeader >> packet.IcmpPayloadHeader >> packet.IcmpPayloadData; + + return is; +} + +std::ostream& operator<<( + std::ostream& os, + const IcmpPacket& packet +) +{ + os << packet.IcmpPayloadHeader << packet.IcmpPayloadData; + + return os; +} diff --git a/src/icmp/icmppacket.h b/src/icmp/icmppacket.h new file mode 100644 index 0000000..4ef7803 --- /dev/null +++ b/src/icmp/icmppacket.h @@ -0,0 +1,89 @@ +#ifndef ICMPPACKET_H +#define ICMPPACKET_H + +#include +#include +#include + +#include "ipv4header.h" +#include "icmpheader.h" +#include "icmpdata.h" + +//----------------------------------------------------------------------------- +// IcmpPacket +//----------------------------------------------------------------------------- +// ICMP packet/message format: +// +// 0 8 16 31 +// +-------+-------+---------------+------------------------------+ --- +// | | | | | ^ +// |version|header | type of | total length in bytes | | +// | (4) | length| service | | | +// +-------+-------+---------------+-+-+-+------------------------+ | +// | | | | | | | +// | identification |0|D|M| fragment offset | | +// | | |F|F| | | +// +---------------+---------------+-+-+-+------------------------+ | +// | | | | | +// | time to live | protocol | header checksum | IPv4 Header +// | | | | 20 bytes +// +---------------+---------------+------------------------------+ | +// | | | +// | source IPv4 address | | +// | | | +// +--------------------------------------------------------------+ | +// | | | +// | destination IPv4 address | | +// | | v +// +---------------+---------------+------------------------------+ --- +// | | | | ^ +// | type | code | checksum | | +// | | | | | +// +---------------+---------------+------------------------------+ | +// | | | ICMP Payload +// | identifier | sequence number | (header + +// | | | data) +// +-------------------------------+------------------------------+ 8+ bytes +// | | | +// | data (optional) | | +// | | v +// +-------------------------------+------------------------------+ --- +// +//----------------------------------------------------------------------------- + +class IcmpPacket +{ +public: + IcmpPacket(); + IcmpPacket( + const IcmpHeader &icmp_header, + const IcmpData &icmp_data + ); + virtual ~IcmpPacket(); + + Ipv4Header get_ip_header() const; + IcmpHeader get_icmp_header() const; + IcmpData get_icmp_data() const; + + bool match( + IcmpHeader::IcmpType type, + uint16_t identifier, + uint16_t sequence_number + ); + + friend std::istream& operator>>( + std::istream &is, + IcmpPacket &packet + ); + friend std::ostream& operator<<( + std::ostream &os, + const IcmpPacket &packet + ); + +private: + Ipv4Header IpHeader; + IcmpHeader IcmpPayloadHeader; + IcmpData IcmpPayloadData; +}; + +#endif /* ICMPPACKET_H */ diff --git a/src/icmp/ipv4header.cpp b/src/icmp/ipv4header.cpp new file mode 100644 index 0000000..b7df6f8 --- /dev/null +++ b/src/icmp/ipv4header.cpp @@ -0,0 +1,106 @@ +#include "ipv4header.h" + +//----------------------------------------------------------------------------- +// Ipv4Header +//----------------------------------------------------------------------------- + +Ipv4Header::Ipv4Header() +{ + std::fill( Rep, Rep + sizeof(Rep), 0 ); +} + +uint8_t Ipv4Header::get_version() const +{ + return (Rep[ 0 ] >> 4) & 0xF; +} + +uint16_t Ipv4Header::get_header_length() const +{ + return (Rep[ 0 ] & 0xF) * 4; +} + +uint8_t Ipv4Header::get_type_of_service() const +{ + return Rep[ 1 ]; +} + +uint16_t Ipv4Header::get_total_length() const +{ + return decode( 2, 3 ); +} + +uint16_t Ipv4Header::get_identification() const +{ + return decode( 4, 5 ); +} + +bool Ipv4Header::dont_fragment() const +{ + return ( ( Rep[ 6 ] & 0x40 ) != 0 ); +} + +bool Ipv4Header::more_fragments() const +{ + return ( ( Rep[ 6 ] & 0x20 ) != 0 ); +} + +uint16_t Ipv4Header::get_fragment_offset() const +{ + return decode( 6, 7 ) & 0x1FFF; +} + +uint8_t Ipv4Header::get_time_to_live() const +{ + return Rep[ 8 ]; +} + +uint8_t Ipv4Header::get_protocol() const +{ + return Rep[ 9 ]; +} + +uint16_t Ipv4Header::get_header_checksum() const +{ + return decode( 10, 11 ); +} + +boost::asio::ip::address_v4 Ipv4Header::get_source_address() const +{ + boost::asio::ip::address_v4::bytes_type bytes = { { + Rep[ 12 ], + Rep[ 13 ], + Rep[ 14 ], + Rep[ 15 ] } }; + return boost::asio::ip::address_v4( bytes ); +} + +boost::asio::ip::address_v4 Ipv4Header::get_destination_address() const +{ + boost::asio::ip::address_v4::bytes_type bytes = { { + Rep[ 16 ], + Rep[ 17 ], + Rep[ 18 ], + Rep[ 19 ] } }; + return boost::asio::ip::address_v4( bytes ); +} + +std::istream& operator>>( + std::istream &is, + Ipv4Header &header +) +{ + is.read( reinterpret_cast ( header.Rep ), 20 ); + if ( header.get_version() != 4 ) + is.setstate( std::ios::failbit ); + std::streamsize options_length = header.get_header_length() - 20; + if ( options_length < 0 || options_length > 40 ) + is.setstate( std::ios::failbit ); + else + is.read( reinterpret_cast ( header.Rep ) + 20, options_length ); + return is; +} + +uint16_t Ipv4Header::decode( int a, int b ) const +{ + return ((Rep[ a ] << 8) + Rep[ b ]); +} diff --git a/src/icmp/ipv4header.h b/src/icmp/ipv4header.h new file mode 100644 index 0000000..8132b6b --- /dev/null +++ b/src/icmp/ipv4header.h @@ -0,0 +1,78 @@ +#ifndef IPV4_HEADER_HPP +#define IPV4_HEADER_HPP + +#include +#include +#include + +//----------------------------------------------------------------------------- +// Ipv4Header +//----------------------------------------------------------------------------- +// IPv4 header format: +// +// 0 8 16 31 +// +-------+-------+---------------+------------------------------+ --- +// | | | | | ^ +// |version|header | type of | total length in bytes | | +// | (4) | length| service | | | +// +-------+-------+---------------+-+-+-+------------------------+ | +// | | | | | | | +// | identification |0|D|M| fragment offset | | +// | | |F|F| | | +// +---------------+---------------+-+-+-+------------------------+ | +// | | | | | +// | time to live | protocol | header checksum | 20 bytes +// | | | | | +// +---------------+---------------+------------------------------+ | +// | | | +// | source IPv4 address | | +// | | | +// +--------------------------------------------------------------+ | +// | | | +// | destination IPv4 address | | +// | | v +// +--------------------------------------------------------------+ --- +// | | ^ +// | | | +// / options (if any) / 0 - 40 +// / / bytes +// | | | +// | | v +// +--------------------------------------------------------------+ --- +// +//----------------------------------------------------------------------------- + +class Ipv4Header +{ +public: + Ipv4Header(); + + uint8_t get_version() const; + uint16_t get_header_length() const; + uint8_t get_type_of_service() const; + uint16_t get_total_length() const; + + uint16_t get_identification() const; + bool dont_fragment() const; + bool more_fragments() const; + uint16_t get_fragment_offset() const; + + uint8_t get_time_to_live() const; + uint8_t get_protocol() const; + uint16_t get_header_checksum() const; + + boost::asio::ip::address_v4 get_source_address() const; + boost::asio::ip::address_v4 get_destination_address() const; + + friend std::istream& operator>>( + std::istream &is, + Ipv4Header &header + ); + +private: + uint16_t decode( int a, int b ) const; + + uint8_t Rep[ 60 ]; +}; + +#endif // IPV4_HEADER_H diff --git a/src/ping/checksumcalculator.h b/src/ping/checksumcalculator.h deleted file mode 100644 index 9b5b657..0000000 --- a/src/ping/checksumcalculator.h +++ /dev/null @@ -1,70 +0,0 @@ -#ifndef CHECKSUMCALCULATOR_H -#define CHECKSUMCALCULATOR_H - -#include - -//----------------------------------------------------------------------------- -// ChecksumCalculator -//----------------------------------------------------------------------------- - -template -class ChecksumCalculator -{ -public: - ChecksumCalculator( - Iterator body_begin, - Iterator body_end - ); - - uint16_t compute( - uint8_t type, - uint8_t code, - uint16_t identifier, - uint16_t sequence_number - ); - -private: - Iterator body_begin; - Iterator body_end; - -}; - -template - ChecksumCalculator::ChecksumCalculator( - Iterator body_begin, - Iterator body_end - ) : - body_begin(), - body_end() - { - this->body_begin = body_begin; - this->body_end = body_end; - } - -template - uint16_t ChecksumCalculator::compute( - uint8_t type, - uint8_t code, - uint16_t identifier, - uint16_t sequence_number - ) - { - uint32_t sum = (type << 8) + code + identifier + sequence_number; - - Iterator body_iter = body_begin; - while ( body_iter != body_end ) - { - sum += (static_cast ( *body_iter++ ) << 8); - if ( body_iter != body_end ) - sum += static_cast ( *body_iter++ ); - } - - sum = (sum >> 16) + (sum & 0xFFFF); - sum += (sum >> 16); - - uint16_t checksum = static_cast ( ~sum ); - - return checksum; - } - -#endif /* CHECKSUMCALCULATOR_H */ diff --git a/src/ping/icmpchecksumcalculator.h b/src/ping/icmpchecksumcalculator.h deleted file mode 100644 index fe08d3e..0000000 --- a/src/ping/icmpchecksumcalculator.h +++ /dev/null @@ -1,13 +0,0 @@ -#ifndef ICMPCHECKSUMCALCULATOR_H -#define ICMPCHECKSUMCALCULATOR_H - -#include "checksumcalculator.h" -#include "icmpdata.h" - -//----------------------------------------------------------------------------- -// IcmpChecksumCalculator -//----------------------------------------------------------------------------- - -typedef ChecksumCalculator IcmpChecksumCalculator; - -#endif /* ICMPCHECKSUMCALCULATOR_H */ diff --git a/src/ping/icmpdata.h b/src/ping/icmpdata.h deleted file mode 100644 index d17c199..0000000 --- a/src/ping/icmpdata.h +++ /dev/null @@ -1,12 +0,0 @@ -#ifndef ICMPDATA_H -#define ICMPDATA_H - -#include - -//----------------------------------------------------------------------------- -// IcmpData -//----------------------------------------------------------------------------- - -typedef std::string IcmpData; - -#endif /* ICMPDATA_H */ diff --git a/src/ping/icmpheader.cpp b/src/ping/icmpheader.cpp deleted file mode 100644 index 9ca552c..0000000 --- a/src/ping/icmpheader.cpp +++ /dev/null @@ -1,109 +0,0 @@ -#include "icmpheader.h" - -//----------------------------------------------------------------------------- -// IcmpHeader -//----------------------------------------------------------------------------- - -IcmpHeader::IcmpHeader() -{ - std::fill( Rep, Rep + sizeof(Rep), 0 ); -} - -IcmpHeader::IcmpHeader( - IcmpHeader::IcmpType type, - uint8_t code, - uint16_t checksum, - uint16_t identifier, - uint16_t sequence_number -) -{ - std::fill( Rep, Rep + sizeof(Rep), 0 ); - - set_type( type ); - set_code( code ); - set_checksum( checksum ); - set_identifier( identifier ); - set_sequence_number( sequence_number ); -} - -IcmpHeader::IcmpType IcmpHeader::get_type() const -{ - uint8_t n = Rep[ 0 ]; - IcmpHeader::IcmpType type = static_cast ( n ); - - return type; -} - -void IcmpHeader::set_type( IcmpHeader::IcmpType type ) -{ - uint8_t n = type; - - Rep[ 0 ] = n; -} - -uint8_t IcmpHeader::get_code() const -{ - return Rep[ 1 ]; -} - -void IcmpHeader::set_code( uint8_t code ) -{ - Rep[ 1 ] = code; -} - -uint16_t IcmpHeader::get_checksum() const -{ - return decode( 2, 3 ); -} - -void IcmpHeader::set_checksum( uint16_t checksum ) -{ - encode( 2, 3, checksum ); -} - -uint16_t IcmpHeader::get_identifier() const -{ - return decode( 4, 5 ); -} - -void IcmpHeader::set_identifier( uint16_t identifier ) -{ - encode( 4, 5, identifier ); -} - -uint16_t IcmpHeader::get_sequence_number() const -{ - return decode( 6, 7 ); -} - -void IcmpHeader::set_sequence_number( uint16_t sequence_number ) -{ - encode( 6, 7, sequence_number ); -} - -std::istream& operator>>( - std::istream &is, - IcmpHeader &header -) -{ - return is.read( reinterpret_cast ( header.Rep ), 8 ); -} - -std::ostream& operator<<( - std::ostream &os, - const IcmpHeader &header -) -{ - return os.write( reinterpret_cast ( header.Rep ), 8 ); -} - -uint16_t IcmpHeader::decode( int a, int b ) const -{ - return ( Rep[ a ] << 8 ) + Rep[ b ]; -} - -void IcmpHeader::encode( int a, int b, uint16_t n ) -{ - Rep[ a ] = static_cast ( n >> 8 ); - Rep[ b ] = static_cast ( n & 0xFF ); -} diff --git a/src/ping/icmpheader.h b/src/ping/icmpheader.h deleted file mode 100644 index ae354d3..0000000 --- a/src/ping/icmpheader.h +++ /dev/null @@ -1,87 +0,0 @@ -#ifndef ICMP_HEADER_HPP -#define ICMP_HEADER_HPP - -#include -#include -#include - -//----------------------------------------------------------------------------- -// IcmpHeader -//----------------------------------------------------------------------------- -// ICMP header format -// -// 0 8 16 31 -// +---------------+---------------+------------------------------+ --- -// | | | | ^ -// | type | code | checksum | | -// | | | | | -// +---------------+---------------+------------------------------+ 8 bytes -// | | | | -// | identifier | sequence number | | -// | | | v -// +-------------------------------+------------------------------+ --- -// -//----------------------------------------------------------------------------- - -class IcmpHeader -{ -public: - enum IcmpType - { - EchoReply = 0, - DestinationUnreachable = 3, - SourceQuench = 4, - Redirect = 5, - EchoRequest = 8, - TimeExceeded = 11, - ParameterProblem = 12, - TimestampRequest = 13, - TimestampReply = 14, - InfoRequest = 15, - InfoReply = 16, - AddressRequest = 17, - AddressReply = 18 - }; - - IcmpHeader(); - IcmpHeader( - IcmpType type, - uint8_t code, - uint16_t checksum, - uint16_t identifier, - uint16_t sequence_number - ); - - IcmpType get_type() const; - void set_type( const IcmpType type ); - - uint8_t get_code() const; - void set_code( const uint8_t code ); - - uint16_t get_checksum() const; - void set_checksum( const uint16_t checksum ); - - uint16_t get_identifier() const; - void set_identifier( const uint16_t identifier ); - - uint16_t get_sequence_number() const; - void set_sequence_number( const uint16_t sequence_number ); - - friend std::istream& operator>>( - std::istream &is, - IcmpHeader &header - ); - friend std::ostream& operator<<( - std::ostream &os, - const IcmpHeader &header - ); - -private: - uint16_t decode( int a, int b ) const; - void encode( int a, int b, uint16_t n ); - - uint8_t Rep[ 8 ]; - -}; - -#endif // ICMP_HEADER_H diff --git a/src/ping/icmppacket.cpp b/src/ping/icmppacket.cpp deleted file mode 100644 index a8ab37d..0000000 --- a/src/ping/icmppacket.cpp +++ /dev/null @@ -1,74 +0,0 @@ -#include "icmppacket.h" - -//----------------------------------------------------------------------------- -// IcmpPacket -//----------------------------------------------------------------------------- - -IcmpPacket::IcmpPacket() : - IpHeader(), - IcmpPayloadHeader(), - IcmpPayloadData() -{ -} - -IcmpPacket::IcmpPacket( - const IcmpHeader &icmp_header, - const IcmpData &icmp_data -) : - IpHeader(), - IcmpPayloadHeader( icmp_header ), - IcmpPayloadData( icmp_data ) -{ -} - -IcmpPacket::~IcmpPacket() -{ -} - -Ipv4Header IcmpPacket::get_ip_header() const -{ - return IpHeader; -} - -IcmpHeader IcmpPacket::get_icmp_header() const -{ - return IcmpPayloadHeader; -} - -IcmpData IcmpPacket::get_icmp_data() const -{ - return IcmpPayloadData; -} - -bool IcmpPacket::match( - IcmpHeader::IcmpType type, - uint16_t identifier, - uint16_t sequence_number -) -{ - bool type_match = IcmpPayloadHeader.get_type() == type; - bool identifier_match = IcmpPayloadHeader.get_identifier() == identifier; - bool seq_num_match = IcmpPayloadHeader.get_sequence_number() == sequence_number; - - return ( type_match && identifier_match && seq_num_match ); -} - -std::istream& operator>>( - std::istream &is, - IcmpPacket &packet -) -{ - is >> packet.IpHeader >> packet.IcmpPayloadHeader >> packet.IcmpPayloadData; - - return is; -} - -std::ostream& operator<<( - std::ostream& os, - const IcmpPacket& packet -) -{ - os << packet.IcmpPayloadHeader << packet.IcmpPayloadData; - - return os; -} diff --git a/src/ping/icmppacket.h b/src/ping/icmppacket.h deleted file mode 100644 index 4ef7803..0000000 --- a/src/ping/icmppacket.h +++ /dev/null @@ -1,89 +0,0 @@ -#ifndef ICMPPACKET_H -#define ICMPPACKET_H - -#include -#include -#include - -#include "ipv4header.h" -#include "icmpheader.h" -#include "icmpdata.h" - -//----------------------------------------------------------------------------- -// IcmpPacket -//----------------------------------------------------------------------------- -// ICMP packet/message format: -// -// 0 8 16 31 -// +-------+-------+---------------+------------------------------+ --- -// | | | | | ^ -// |version|header | type of | total length in bytes | | -// | (4) | length| service | | | -// +-------+-------+---------------+-+-+-+------------------------+ | -// | | | | | | | -// | identification |0|D|M| fragment offset | | -// | | |F|F| | | -// +---------------+---------------+-+-+-+------------------------+ | -// | | | | | -// | time to live | protocol | header checksum | IPv4 Header -// | | | | 20 bytes -// +---------------+---------------+------------------------------+ | -// | | | -// | source IPv4 address | | -// | | | -// +--------------------------------------------------------------+ | -// | | | -// | destination IPv4 address | | -// | | v -// +---------------+---------------+------------------------------+ --- -// | | | | ^ -// | type | code | checksum | | -// | | | | | -// +---------------+---------------+------------------------------+ | -// | | | ICMP Payload -// | identifier | sequence number | (header + -// | | | data) -// +-------------------------------+------------------------------+ 8+ bytes -// | | | -// | data (optional) | | -// | | v -// +-------------------------------+------------------------------+ --- -// -//----------------------------------------------------------------------------- - -class IcmpPacket -{ -public: - IcmpPacket(); - IcmpPacket( - const IcmpHeader &icmp_header, - const IcmpData &icmp_data - ); - virtual ~IcmpPacket(); - - Ipv4Header get_ip_header() const; - IcmpHeader get_icmp_header() const; - IcmpData get_icmp_data() const; - - bool match( - IcmpHeader::IcmpType type, - uint16_t identifier, - uint16_t sequence_number - ); - - friend std::istream& operator>>( - std::istream &is, - IcmpPacket &packet - ); - friend std::ostream& operator<<( - std::ostream &os, - const IcmpPacket &packet - ); - -private: - Ipv4Header IpHeader; - IcmpHeader IcmpPayloadHeader; - IcmpData IcmpPayloadData; -}; - -#endif /* ICMPPACKET_H */ diff --git a/src/ping/ipv4header.cpp b/src/ping/ipv4header.cpp deleted file mode 100644 index b7df6f8..0000000 --- a/src/ping/ipv4header.cpp +++ /dev/null @@ -1,106 +0,0 @@ -#include "ipv4header.h" - -//----------------------------------------------------------------------------- -// Ipv4Header -//----------------------------------------------------------------------------- - -Ipv4Header::Ipv4Header() -{ - std::fill( Rep, Rep + sizeof(Rep), 0 ); -} - -uint8_t Ipv4Header::get_version() const -{ - return (Rep[ 0 ] >> 4) & 0xF; -} - -uint16_t Ipv4Header::get_header_length() const -{ - return (Rep[ 0 ] & 0xF) * 4; -} - -uint8_t Ipv4Header::get_type_of_service() const -{ - return Rep[ 1 ]; -} - -uint16_t Ipv4Header::get_total_length() const -{ - return decode( 2, 3 ); -} - -uint16_t Ipv4Header::get_identification() const -{ - return decode( 4, 5 ); -} - -bool Ipv4Header::dont_fragment() const -{ - return ( ( Rep[ 6 ] & 0x40 ) != 0 ); -} - -bool Ipv4Header::more_fragments() const -{ - return ( ( Rep[ 6 ] & 0x20 ) != 0 ); -} - -uint16_t Ipv4Header::get_fragment_offset() const -{ - return decode( 6, 7 ) & 0x1FFF; -} - -uint8_t Ipv4Header::get_time_to_live() const -{ - return Rep[ 8 ]; -} - -uint8_t Ipv4Header::get_protocol() const -{ - return Rep[ 9 ]; -} - -uint16_t Ipv4Header::get_header_checksum() const -{ - return decode( 10, 11 ); -} - -boost::asio::ip::address_v4 Ipv4Header::get_source_address() const -{ - boost::asio::ip::address_v4::bytes_type bytes = { { - Rep[ 12 ], - Rep[ 13 ], - Rep[ 14 ], - Rep[ 15 ] } }; - return boost::asio::ip::address_v4( bytes ); -} - -boost::asio::ip::address_v4 Ipv4Header::get_destination_address() const -{ - boost::asio::ip::address_v4::bytes_type bytes = { { - Rep[ 16 ], - Rep[ 17 ], - Rep[ 18 ], - Rep[ 19 ] } }; - return boost::asio::ip::address_v4( bytes ); -} - -std::istream& operator>>( - std::istream &is, - Ipv4Header &header -) -{ - is.read( reinterpret_cast ( header.Rep ), 20 ); - if ( header.get_version() != 4 ) - is.setstate( std::ios::failbit ); - std::streamsize options_length = header.get_header_length() - 20; - if ( options_length < 0 || options_length > 40 ) - is.setstate( std::ios::failbit ); - else - is.read( reinterpret_cast ( header.Rep ) + 20, options_length ); - return is; -} - -uint16_t Ipv4Header::decode( int a, int b ) const -{ - return ((Rep[ a ] << 8) + Rep[ b ]); -} diff --git a/src/ping/ipv4header.h b/src/ping/ipv4header.h deleted file mode 100644 index 8132b6b..0000000 --- a/src/ping/ipv4header.h +++ /dev/null @@ -1,78 +0,0 @@ -#ifndef IPV4_HEADER_HPP -#define IPV4_HEADER_HPP - -#include -#include -#include - -//----------------------------------------------------------------------------- -// Ipv4Header -//----------------------------------------------------------------------------- -// IPv4 header format: -// -// 0 8 16 31 -// +-------+-------+---------------+------------------------------+ --- -// | | | | | ^ -// |version|header | type of | total length in bytes | | -// | (4) | length| service | | | -// +-------+-------+---------------+-+-+-+------------------------+ | -// | | | | | | | -// | identification |0|D|M| fragment offset | | -// | | |F|F| | | -// +---------------+---------------+-+-+-+------------------------+ | -// | | | | | -// | time to live | protocol | header checksum | 20 bytes -// | | | | | -// +---------------+---------------+------------------------------+ | -// | | | -// | source IPv4 address | | -// | | | -// +--------------------------------------------------------------+ | -// | | | -// | destination IPv4 address | | -// | | v -// +--------------------------------------------------------------+ --- -// | | ^ -// | | | -// / options (if any) / 0 - 40 -// / / bytes -// | | | -// | | v -// +--------------------------------------------------------------+ --- -// -//----------------------------------------------------------------------------- - -class Ipv4Header -{ -public: - Ipv4Header(); - - uint8_t get_version() const; - uint16_t get_header_length() const; - uint8_t get_type_of_service() const; - uint16_t get_total_length() const; - - uint16_t get_identification() const; - bool dont_fragment() const; - bool more_fragments() const; - uint16_t get_fragment_offset() const; - - uint8_t get_time_to_live() const; - uint8_t get_protocol() const; - uint16_t get_header_checksum() const; - - boost::asio::ip::address_v4 get_source_address() const; - boost::asio::ip::address_v4 get_destination_address() const; - - friend std::istream& operator>>( - std::istream &is, - Ipv4Header &header - ); - -private: - uint16_t decode( int a, int b ) const; - - uint8_t Rep[ 60 ]; -}; - -#endif // IPV4_HEADER_H -- 1.7.1