Skip to content

PacketAssert

Ondrej Lichtner edited this page Nov 4, 2016 · 4 revisions

1. Basic description

This test checks whether or not specific packets are being transferred through the specified interface correctly. For this functionality tcpdump is used. Packets that should be counted are specified using multiple regular expressions that are used to parse the output from tcpdump. For a packet to be counted it needs to pass through every specified filter.

This test can be used to look for specific types of communication, or to detect unwanted amounts of certain kinds of traffic.

2. Options

This test module accepts these options:

interface selects the interface on which will the module capture packets. It represents the argument -i of the tcpdump command. This option is mandatory.
filter is a pcap-filter expression that will be used to by tcpdump to filter captured packets.
promiscuous adds the -p argument to the tcpdump command, enabling promiscuous mode
grep_for is an option that can be used multiple times to specify more values. The values are additional regular expressions that will be used to further filter the captured packets.
min is an integer value used for the final evaluation of the tests result. For the test to be successful at least min packets must have been captured. The default value is 1.
max is an integer value used for the final evaluation of the tests result. For the test to be successful at most max packets must have been captured.

3. Usage Example

This test can only be run as a background command. This is because the tcpdump that is used is not restricted to any duration. Executing it as a normal command would therefore stop the rest of the command sequence. You can see an example usage of this module in the following recipe snippet:

<run module="PacketAssert" host="testmachine2" bg_id="test">
    <options>
        <option name="interface" value="{devname(testmachine2, testifc2)}"/>
        <option name="filter" value="icmp"/>
        <option name="max" value="100"/>
        <option name="grep_for" value="echo request"/>
    </options>
</run>
<run module="IcmpPing" host="testmachine1">
    <options>
        <option name="addr" value="{ip(testmachine2, testifc2)}"/>
        <option name="count" value="20"/>
        <option name="interval" value="1"/>
    </options>
</run>
<intr host="testmachine2" bg_id="test"/>

For this demonstration I decided to use an additional ping command that will create some traffic for us. The option filter of the PacketAssert command is set to filter only icmp packets and additionally we are interested in echo requests so we added this to the option grep_for.

4. Results

Given the commands from the previous section we can expect that 20 of packets will be captured due to the options supplied to the IcmpPing test module. This can be seen in the following test results:

25/01 10:38:29|       (127.0.0.1) INFO: Executing command: [type (test), machine_id (testmachine2), value (PacketAssert), bg_id (test)]
25/01 10:38:27|  (192.168.122.30) DEBUG: Running in background with id "test", pid "2485"
25/01 10:38:29|       (127.0.0.1) DEBUG: Result: {'passed': True}
25/01 10:38:29|       (127.0.0.1) INFO: Executing command: [type (test), machine_id (testmachine1), value (IcmpPing)]
25/01 10:38:26| (192.168.122.109) DEBUG: Executing: "ping 192.168.100.2 -c 20 -i 1"
25/01 10:38:46| (192.168.122.109) DEBUG: 
    Stdout:
    ----------------------------
    PING 192.168.100.2 (192.168.100.2) 56(84) bytes of data.
    64 bytes from 192.168.100.2: icmp_seq=1 ttl=64 time=1.39 ms
    64 bytes from 192.168.100.2: icmp_seq=2 ttl=64 time=0.674 ms
    64 bytes from 192.168.100.2: icmp_seq=3 ttl=64 time=1.14 ms
    64 bytes from 192.168.100.2: icmp_seq=4 ttl=64 time=1.28 ms
    64 bytes from 192.168.100.2: icmp_seq=5 ttl=64 time=1.11 ms
    64 bytes from 192.168.100.2: icmp_seq=6 ttl=64 time=1.19 ms
    64 bytes from 192.168.100.2: icmp_seq=7 ttl=64 time=1.01 ms
    64 bytes from 192.168.100.2: icmp_seq=8 ttl=64 time=1.24 ms
    64 bytes from 192.168.100.2: icmp_seq=9 ttl=64 time=0.711 ms
    64 bytes from 192.168.100.2: icmp_seq=10 ttl=64 time=0.570 ms
    64 bytes from 192.168.100.2: icmp_seq=11 ttl=64 time=0.558 ms
    64 bytes from 192.168.100.2: icmp_seq=12 ttl=64 time=0.561 ms
    64 bytes from 192.168.100.2: icmp_seq=13 ttl=64 time=1.03 ms
    64 bytes from 192.168.100.2: icmp_seq=14 ttl=64 time=1.23 ms
    64 bytes from 192.168.100.2: icmp_seq=15 ttl=64 time=1.18 ms
    64 bytes from 192.168.100.2: icmp_seq=16 ttl=64 time=1.12 ms
    64 bytes from 192.168.100.2: icmp_seq=17 ttl=64 time=1.17 ms
    64 bytes from 192.168.100.2: icmp_seq=18 ttl=64 time=1.17 ms
    64 bytes from 192.168.100.2: icmp_seq=19 ttl=64 time=1.18 ms
    64 bytes from 192.168.100.2: icmp_seq=20 ttl=64 time=1.25 ms
    
    --- 192.168.100.2 ping statistics ---
    20 packets transmitted, 20 received, 0% packet loss, time 19025ms
    rtt min/avg/max/mdev = 0.558/1.041/1.398/0.263 ms
    ----------------------------
25/01 10:38:46| (192.168.122.109) DEBUG: Transmitted "20", received "20", rate "100%", limit_rate "80%"
25/01 10:38:46| (192.168.122.109) DEBUG: rtt min "0.558", avg "1.041", max "1.398", mdev "0.263"
25/01 10:38:46| (192.168.122.109) DEBUG: PASSED
25/01 10:38:48|       (127.0.0.1) DEBUG: Result: {'res_data': {'rate': 100}, 'passed': True}
25/01 10:38:48|       (127.0.0.1) INFO: Result data: {'rate': 100}
25/01 10:38:48|       (127.0.0.1) INFO: Executing command: [type (intr), machine_id (testmachine2), value (test)]
25/01 10:38:46|  (192.168.122.30) DEBUG: Interrupting background command with id "test", pid "2485"
25/01 10:38:27|  (192.168.122.30) INFO: Capturing started
25/01 10:38:46|  (192.168.122.30) INFO: Capturing finished. Received 20 packets
25/01 10:38:46|  (192.168.122.30) DEBUG: PASSED
25/01 10:38:48|       (127.0.0.1) DEBUG: Result: {'res_data': {'received': 20, 'max': 100, 'min': 1}, 'passed': True}
25/01 10:38:48|       (127.0.0.1) INFO: Result data: {'max': 100, 'min': 1, 'received': 20}