made nicer static variables of packet dump mode and location
[pingcheck] / test / test_icmppacket.cpp
1 /*
2  The software in this package is distributed under the GNU General
3  Public License version 2 (with a special exception described below).
4
5  A copy of GNU General Public License (GPL) is included in this distribution,
6  in the file COPYING.GPL.
7
8  As a special exception, if other files instantiate templates or use macros
9  or inline functions from this file, or you compile this file and link it
10  with other works to produce a work based on this file, this file
11  does not by itself cause the resulting work to be covered
12  by the GNU General Public License.
13
14  However the source code for this file must still be made available
15  in accordance with section (3) of the GNU General Public License.
16
17  This exception does not invalidate any other reasons why a work based
18  on this file might be covered by the GNU General Public License.
19
20  Christian Herdtweck, Intra2net AG 2015
21  */
22
23 #define BOOST_TEST_MAIN
24 #define BOOST_TEST_DYN_LINK
25
26 #include <fstream>
27 #include <sstream>
28 #include <ios>
29 #include <boost/test/unit_test.hpp>
30 #include <boost/asio.hpp>
31
32 #include "icmp/icmppacketfactory.h"
33 #include "icmp/icmptype.h"
34 #include "tools/pcap.h"
35
36 //------------------------------------------------------------------------------
37 //  helper function
38 //------------------------------------------------------------------------------
39
40 IcmpPacketItem read_packet(const std::string &file_name);
41
42
43 IcmpPacketItem read_packet(const std::string &file_name)
44 {
45     std::stringstream full_name;
46     full_name << DATA_DIR_STRING << "/" << file_name;
47     BOOST_TEST_MESSAGE( "Opening file " << full_name.str() );
48     std::ifstream file_stream(full_name.str().c_str(), std::ios::in |
49                                            std::ios::binary);
50     // could open?
51     BOOST_REQUIRE( file_stream );
52
53     // recognized pcap file?
54     bool is_pcap = consume_single_packet_pcap(file_stream);
55     if ( !is_pcap )
56     {
57         file_stream.close();
58         BOOST_FAIL( "Failed to recognize/consume pcap header!" );
59     }
60
61     IcmpPacketFactory::PacketDumpMode = DUMP_NEVER;
62
63     IcmpPacketItem packet = IcmpPacketFactory::create_icmp_packet(
64                                       boost::asio::ip::icmp::v4(), file_stream);
65     file_stream.close();
66
67     // managed to create packet from rest of file contents?
68     BOOST_REQUIRE( packet );
69     //BOOST_REQUIRE( packet->check_integrity() );   not implemented yet
70     return packet;
71 }
72
73 //------------------------------------------------------------------------------
74 //  TEST SUITE
75 //------------------------------------------------------------------------------
76
77 BOOST_AUTO_TEST_SUITE( TestIcmpPacket )
78
79 BOOST_AUTO_TEST_CASE( EchoRequest )
80 {
81     std::string request_file = "icmp_echorequest.pcap";
82
83     // read request file
84     IcmpPacketItem packet = read_packet(request_file);
85     BOOST_REQUIRE( packet );
86     BOOST_CHECK_EQUAL( packet->get_type_v4(), Icmpv4Type_EchoRequest );
87     BOOST_CHECK_EQUAL( packet->get_source_address().to_string(),
88                        "11.22.33.44");
89     BOOST_CHECK_EQUAL( packet->get_destination_address().to_string(),
90                        "38.100.128.10");
91     BOOST_CHECK_EQUAL( packet->get_icmp_code(), 0 );
92     BOOST_CHECK_EQUAL( packet->get_icmp_size(), 20 );
93 }
94
95
96 BOOST_AUTO_TEST_CASE( EchoReply )
97 {
98     std::string reply_file = "icmp_echoreply.pcap";
99
100     // read reply file
101     IcmpPacketItem packet = read_packet(reply_file);
102     BOOST_REQUIRE( packet );
103     BOOST_CHECK_EQUAL( packet->get_type_v4(), Icmpv4Type_EchoReply );
104     BOOST_CHECK_EQUAL( packet->get_source_address().to_string(),
105                        "38.100.128.10");
106     BOOST_CHECK_EQUAL( packet->get_destination_address().to_string(),
107                        "11.22.33.44");
108     BOOST_CHECK_EQUAL( packet->get_icmp_code(), 0 );
109     BOOST_CHECK_EQUAL( packet->get_icmp_size(), 20 );
110     BOOST_CHECK( packet->match_echo_reply(0xaf36, 1,
111                  boost::asio::ip::address_v4::from_string("38.100.128.10")) );
112 }
113
114 BOOST_AUTO_TEST_CASE( TimeExceeded )
115 {
116     std::string file_name = "icmp_timeexceeded.pcap";
117
118     // read file
119     IcmpPacketItem packet = read_packet(file_name);
120     BOOST_REQUIRE( packet );
121     BOOST_CHECK_EQUAL( packet->get_type_v4(), Icmpv4Type_TimeExceeded );
122     BOOST_CHECK_EQUAL( packet->get_source_address().to_string(),
123                        "193.186.7.1");
124     BOOST_CHECK_EQUAL( packet->get_destination_address().to_string(),
125                        "11.22.33.44");
126     BOOST_CHECK_EQUAL( packet->get_icmp_code(), 0 );
127     BOOST_CHECK_EQUAL( packet->get_icmp_size(), 48 );
128     BOOST_CHECK( packet->match_time_exceeded(0x4ae3, 1,
129                  boost::asio::ip::address_v4::from_string("216.218.186.2")) );
130 }
131
132 BOOST_AUTO_TEST_CASE( DestinationUnreachable )
133 {
134     std::string file_name = "icmp_destinationunreachable.pcap";
135
136     // read file
137     IcmpPacketItem packet = read_packet(file_name);
138     BOOST_REQUIRE( packet );
139     BOOST_CHECK_EQUAL( packet->get_type_v4(), Icmpv4Type_DestinationUnreachable );
140     BOOST_CHECK_EQUAL( packet->get_source_address().to_string(),
141                        "11.22.33.254");
142     BOOST_CHECK_EQUAL( packet->get_destination_address().to_string(),
143                        "11.22.33.44");
144     BOOST_CHECK_EQUAL( packet->get_icmp_code(), 3 );
145     BOOST_CHECK_EQUAL( packet->get_icmp_size(), 92 );
146     BOOST_CHECK( packet->match_destination_unreachable(0x077b, 1,
147                  boost::asio::ip::address_v4::from_string("85.214.66.2")) );
148 }
149
150 BOOST_AUTO_TEST_SUITE_END()
151