1-- test script for Pinfo and Address functions
2-- use with dhcp.pcap in test/captures directory
3
4local major, minor, micro = get_version():match("(%d+)%.(%d+)%.(%d+)")
5if major then
6    major = tonumber(major)
7    minor = tonumber(minor)
8    micro = tonumber(micro)
9else
10    major = 99
11    minor = 99
12    micro = 99
13end
14
15------------- general test helper funcs ------------
16local FRAME = "frame"
17local OTHER = "other"
18
19local packet_counts = {}
20local function incPktCount(name)
21    if not packet_counts[name] then
22        packet_counts[name] = 1
23    else
24        packet_counts[name] = packet_counts[name] + 1
25    end
26end
27local function getPktCount(name)
28    return packet_counts[name] or 0
29end
30
31local passed = {}
32local function setPassed(name)
33    if not passed[name] then
34        passed[name] = 1
35    else
36        passed[name] = passed[name] + 1
37    end
38end
39
40-- expected number of runs per type
41-- note ip only runs 3 times because it gets removed
42-- and dhcp only runs twice because the filter makes it run
43-- once and then it gets replaced with a different one for the second time
44local taptests = { [FRAME]=4, [OTHER]=0 }
45local function getResults()
46    print("\n-----------------------------\n")
47    for k,v in pairs(taptests) do
48        if v ~= 0 and passed[k] ~= v then
49            print("Something didn't run or ran too much... tests failed!")
50            print("Listener type "..k.." expected: "..v..", but got: "..tostring(passed[k]))
51            return false
52        end
53    end
54    print("All tests passed!\n\n")
55    return true
56end
57
58
59local function testing(type,...)
60    print("---- Testing "..type.." ---- "..tostring(...).." for packet # "..getPktCount(type).." ----")
61end
62
63local function test(type,name, ...)
64    io.stdout:write("test "..type.."-->"..name.."-"..getPktCount(type).."...")
65    if (...) == true then
66        io.stdout:write("passed\n")
67        return true
68    else
69        io.stdout:write("failed!\n")
70        error(name.." test failed!")
71    end
72end
73
74---------
75-- the following are so we can use pcall (which needs a function to call)
76local function setPinfo(pinfo,name,value)
77    pinfo[name] = value
78end
79
80local function getPinfo(pinfo,name)
81    local foo = pinfo[name]
82end
83
84------------- test script ------------
85
86----------------------------------
87-- modify original test function, kinda sorta
88local orig_test = test
89test = function (...)
90    return orig_test(FRAME,...)
91end
92
93
94local tap = Listener.new()
95
96
97function tap.packet(pinfo,tvb)
98    incPktCount(FRAME)
99    testing(FRAME,"Pinfo in Frame")
100
101    test("typeof-1", typeof(pinfo) == "Pinfo")
102
103    test("tostring-1", tostring(pinfo) == "a Pinfo")
104
105    testing(FRAME,"negative tests")
106
107    -- try to set read-only attributes
108--[[
109these tests *should* ALL pass, but currently pinfo read-only members
110silently accept being set (though nothing happens) Blech!!
111    test("Pinfo.number-set-1",not pcall(setPinfo,pinfo,"number",0))
112    test("Pinfo.len-set-1",not pcall(setPinfo,pinfo,"len",0))
113    test("Pinfo.caplen-set-1",not pcall(setPinfo,pinfo,"caplen",0))
114    test("Pinfo.rel_ts-set-1",not pcall(setPinfo,pinfo,"rel_ts",0))
115    test("Pinfo.delta_ts-set-1",not pcall(setPinfo,pinfo,"delta_ts",0))
116    test("Pinfo.delta_dis_ts-set-1",not pcall(setPinfo,pinfo,"delta_dis_ts",0))
117    test("Pinfo.visited-set-1",not pcall(setPinfo,pinfo,"visited",0))
118    test("Pinfo.lo-set-1",not pcall(setPinfo,pinfo,"lo",0))
119    test("Pinfo.hi-set-1",not pcall(setPinfo,pinfo,"hi",0))
120    test("Pinfo.port_type-set-1",not pcall(setPinfo,pinfo,"port_type",0))
121    test("Pinfo.match-set-1",not pcall(setPinfo,pinfo,"match",0))
122    test("Pinfo.curr_proto-set-1",not pcall(setPinfo,pinfo,"curr_proto",0))
123    test("Pinfo.columns-set-1",not pcall(setPinfo,pinfo,"columns",0))
124    test("Pinfo.cols-set-1",not pcall(setPinfo,pinfo,"cols",0))
125    test("Pinfo.private-set-1",not pcall(setPinfo,pinfo,"private",0))
126    test("Pinfo.fragmented-set-1",not pcall(setPinfo,pinfo,"fragmented",0))
127    test("Pinfo.in_error_pkt-set-1",not pcall(setPinfo,pinfo,"in_error_pkt",0))
128    test("Pinfo.match_uint-set-1",not pcall(setPinfo,pinfo,"match_uint",0))
129    test("Pinfo.match_string-set-1",not pcall(setPinfo,pinfo,"match_string",0))
130]]
131
132    -- wrong type being set
133    test("Pinfo.src-set-1",not pcall(setPinfo,pinfo,"src","foobar"))
134    test("Pinfo.dst-set-1",not pcall(setPinfo,pinfo,"dst","foobar"))
135    test("Pinfo.dl_src-set-1",not pcall(setPinfo,pinfo,"dl_src","foobar"))
136    test("Pinfo.dl_dst-set-1",not pcall(setPinfo,pinfo,"dl_dst","foobar"))
137    test("Pinfo.net_src-set-1",not pcall(setPinfo,pinfo,"net_src","foobar"))
138    test("Pinfo.net_dst-set-1",not pcall(setPinfo,pinfo,"net_dst","foobar"))
139    test("Pinfo.src_port-set-1",not pcall(setPinfo,pinfo,"src_port","foobar"))
140    test("Pinfo.dst_port-set-1",not pcall(setPinfo,pinfo,"dst_port","foobar"))
141    if major > 1 or minor > 10 then
142        test("Pinfo.can_desegment-set-1",not pcall(setPinfo,pinfo,"can_desegment","foobar"))
143    end
144    test("Pinfo.desegment_len-set-1",not pcall(setPinfo,pinfo,"desegment_len","foobar"))
145    test("Pinfo.desegment_offset-set-1",not pcall(setPinfo,pinfo,"desegment_offset","foobar"))
146
147    -- invalid attribute names
148--[[
149again, these *should* pass, but Pinfo silently allows it!
150    test("Pinfo.set-1",not pcall(setPinfo,pinfo,"foobar","foobar"))
151    test("Pinfo.get-12",not pcall(getPinfo,pinfo,"foobar"))
152]]
153
154    testing(FRAME,"basic getter tests")
155
156    local pktlen, srcip, dstip, srcport, dstport
157
158    if pinfo.number == 1 or pinfo.number == 3 then
159        pktlen = 314
160        srcip = "0.0.0.0"
161        dstip = "255.255.255.255"
162        srcport = 68
163        dstport = 67
164    else
165        pktlen = 342
166        srcip = "192.168.0.1"
167        dstip = "192.168.0.10"
168        srcport = 67
169        dstport = 68
170    end
171
172    test("Pinfo.number-get-1",pinfo.number == getPktCount(FRAME))
173    test("Pinfo.len-get-1",pinfo.len == pktlen)
174    test("Pinfo.caplen-get-1",pinfo.caplen == pktlen)
175    test("Pinfo.visited-get-1",pinfo.visited == true)
176    test("Pinfo.lo-get-1",tostring(pinfo.lo) == srcip)
177    test("Pinfo.lo-get-2",typeof(pinfo.lo) == "Address")
178    test("Pinfo.hi-get-1",tostring(pinfo.hi) == dstip)
179    test("Pinfo.hi-get-2",typeof(pinfo.hi) == "Address")
180    test("Pinfo.port_type-get-1",pinfo.port_type == 3)
181    test("Pinfo.match-get-1",pinfo.match == 0)
182    test("Pinfo.curr_proto-get-1",tostring(pinfo.curr_proto) == "<Missing Protocol Name>")
183    test("Pinfo.columns-get-1",tostring(pinfo.columns) == "Columns")
184    test("Pinfo.columns-get-2",typeof(pinfo.columns) == "Columns")
185    test("Pinfo.cols-get-1",tostring(pinfo.cols) == "Columns")
186    test("Pinfo.cols-get-2",typeof(pinfo.cols) == "Columns")
187    test("Pinfo.private-get-1",type(pinfo.private) == "userdata")
188    test("Pinfo.fragmented-get-1",pinfo.fragmented == false)
189
190    test("Pinfo.in_error_pkt-get-1",pinfo.in_error_pkt == false)
191    test("Pinfo.match_uint-get-1",pinfo.match_uint == 0)
192    test("Pinfo.match_string-get-1",pinfo.match_string == nil)
193
194    test("Pinfo.src-get-1",tostring(pinfo.src) == srcip)
195    test("Pinfo.src-get-2",typeof(pinfo.src) == "Address")
196    test("Pinfo.dst-get-1",tostring(pinfo.dst) == dstip)
197    test("Pinfo.dst-get-2",typeof(pinfo.dst) == "Address")
198
199    test("Pinfo.dl_src-get-1",typeof(pinfo.dl_src) == "Address")
200    test("Pinfo.dl_dst-get-1",typeof(pinfo.dl_dst) == "Address")
201    test("Pinfo.net_src-get-1",tostring(pinfo.net_src) == srcip)
202    test("Pinfo.net_src-get-2",typeof(pinfo.net_src) == "Address")
203    test("Pinfo.net_dst-get-1",tostring(pinfo.net_dst) == dstip)
204    test("Pinfo.net_dst-get-2",typeof(pinfo.net_dst) == "Address")
205    test("Pinfo.src_port-get-1",pinfo.src_port == srcport)
206    test("Pinfo.dst_port-get-1",pinfo.dst_port == dstport)
207    if major > 1 or minor > 10 then
208        test("Pinfo.can_desegment-get-1",pinfo.can_desegment == 0)
209    end
210    test("Pinfo.desegment_len-get-1",pinfo.desegment_len == 0)
211    test("Pinfo.desegment_offset-get-1",pinfo.desegment_offset == 0)
212
213    test("pinfo.p2p_dir", pinfo.p2p_dir == P2P_DIR_UNKNOWN)
214
215    if pinfo.number == 1 then
216        test("Pinfo.rel_ts-get-1",pinfo.rel_ts == 0)
217        test("Pinfo.delta_ts-get-1",pinfo.delta_ts == 0)
218        test("Pinfo.delta_dis_ts-get-1",pinfo.delta_dis_ts == 0)
219    elseif pinfo.number == 2 then
220        test("Pinfo.rel_ts-get-1",pinfo.rel_ts == 0.000295)
221        test("Pinfo.delta_ts-get-1",pinfo.delta_ts == 0.000295)
222        test("Pinfo.delta_dis_ts-get-1",pinfo.delta_dis_ts == 0.000295)
223    elseif pinfo.number == 3 then
224        test("Pinfo.rel_ts-get-1",pinfo.rel_ts == 0.070031)
225        test("Pinfo.delta_ts-get-1",pinfo.delta_ts == 0.069736)
226        test("Pinfo.delta_dis_ts-get-1",pinfo.delta_dis_ts == 0.069736)
227    elseif pinfo.number == 4 then
228        test("Pinfo.rel_ts-get-1",pinfo.rel_ts == 0.070345)
229        test("Pinfo.delta_ts-get-1",pinfo.delta_ts == 0.000314)
230        test("Pinfo.delta_dis_ts-get-1",pinfo.delta_dis_ts == 0.000314)
231    end
232
233
234    testing(FRAME,"basic setter tests")
235
236    local tmp = pinfo.src
237    pinfo.src = pinfo.dst
238    pinfo.dst = tmp
239    test("Pinfo.src-set-1",tostring(pinfo.src) == dstip)
240    test("Pinfo.src-set-1",typeof(pinfo.src) == "Address")
241    test("Pinfo.dst-set-1",tostring(pinfo.dst) == srcip)
242    test("Pinfo.dst-set-1",typeof(pinfo.dst) == "Address")
243
244    local dl_dst_val = tostring(pinfo.dl_dst)
245    local dl_src_val = tostring(pinfo.dl_src)
246    tmp = pinfo.dl_src
247    pinfo.dl_src = pinfo.dl_dst
248    pinfo.dl_dst = tmp
249    test("Pinfo.dl_src-set-1",tostring(pinfo.dl_src) == dl_dst_val)
250    test("Pinfo.dl_dst-set-1",tostring(pinfo.dl_dst) == dl_src_val)
251
252    tmp = pinfo.net_src
253    pinfo.net_src = pinfo.net_dst
254    pinfo.net_dst = tmp
255    test("Pinfo.net_src-set-1",tostring(pinfo.net_src) == dstip)
256    test("Pinfo.net_src-set-1",typeof(pinfo.net_src) == "Address")
257    test("Pinfo.net_dst-set-1",tostring(pinfo.net_dst) == srcip)
258    test("Pinfo.net_dst-set-1",typeof(pinfo.net_dst) == "Address")
259
260--[[
261--there's a bug 9792 causing the pinfo.dst_port setter to actually set src_port
262    tmp = pinfo.src_port
263    pinfo.src_port = pinfo.dst_port
264    pinfo.dst_port = tmp
265    test("Pinfo.src_port-set-1",pinfo.src_port == dstport)
266    test("Pinfo.dst_port-set-1",pinfo.dst_port == srcport)
267--]]
268    pinfo.src_port = pinfo.dst_port
269    test("Pinfo.src_port-set-1",pinfo.src_port == dstport)
270
271    if major > 1 or minor > 10 then
272        pinfo.can_desegment = 12
273        test("Pinfo.can_desegment-set-1",pinfo.can_desegment == 12)
274    end
275    pinfo.desegment_len = 34
276    test("Pinfo.desegment_len-set-1",pinfo.desegment_len == 34)
277    pinfo.desegment_offset = 45
278    test("Pinfo.desegment_offset-set-1",pinfo.desegment_offset == 45)
279
280    testing(FRAME,"Address functions")
281    test("Address-eq-1", pinfo.lo == pinfo.dst)
282    test("Address-eq-2", pinfo.lo ~= pinfo.hi)
283    test("Address-lt-1", pinfo.lo < pinfo.hi)
284    test("Address-lt-2", pinfo.hi > pinfo.lo)
285    test("Address-le-1", pinfo.lo <= pinfo.hi)
286    test("Address-le-2", pinfo.lo <= pinfo.dst)
287
288    setPassed(FRAME)
289
290end
291
292function tap.draw()
293    getResults()
294end
295