Use val_to_str_const() where appropriate;
[metze/wireshark/wip.git] / epan / dissectors / packet-iax2.c
1 /*
2  * packet-iax2.c
3  *
4  * Routines for IAX2 packet disassembly
5  * By Alastair Maw <asterisk@almaw.com>
6  * Copyright 2003 Alastair Maw
7  *
8  * IAX2 is a VoIP protocol for the open source PBX Asterisk. Please see
9  * http://www.asterisk.org for more information; see RFC 5456 for the
10  * protocol.
11  *
12  * $Id$
13  *
14  * Wireshark - Network traffic analyzer
15  * By Gerald Combs <gerald@wireshark.org>
16  * Copyright 1998 Gerald Combs
17  *
18  * This program is free software; you can redistribute it and/or
19  * modify it under the terms of the GNU General Public License
20  * as published by the Free Software Foundation; either version 2
21  * of the License, or (at your option) any later version.
22  *
23  * This program is distributed in the hope that it will be useful,
24  * but WITHOUT ANY WARRANTY; without even the implied warranty of
25  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
26  * GNU General Public License for more details.
27  *
28  * You should have received a copy of the GNU General Public License
29  * along with this program; if not, write to the Free Software
30  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
31  */
32
33 #ifdef HAVE_CONFIG_H
34 # include "config.h"
35 #endif
36
37 #include <string.h>
38
39 #include <glib.h>
40
41 #include <epan/circuit.h>
42 #include <epan/packet.h>
43 #include <epan/to_str.h>
44 #include <epan/emem.h>
45 #include <epan/reassemble.h>
46 #include <epan/aftypes.h>
47 #include <epan/tap.h>
48 #include <epan/tap-voip.h>
49
50 #include "packet-iax2.h"
51 #include <epan/iax2_codec_type.h>
52
53 #define IAX2_PORT               4569
54 #define PROTO_TAG_IAX2          "IAX2"
55
56 /* enough to hold any address in an address_t */
57 #define MAX_ADDRESS 16
58
59 /* the maximum number of transfers (of each end) we can deal with per call,
60  * plus one */
61 #define IAX_MAX_TRANSFERS 2
62
63 /* #define DEBUG_HASHING */
64 /* #define DEBUG_DESEGMENT */
65
66 /* Wireshark ID of the IAX2 protocol */
67 static int proto_iax2 = -1;
68
69 /* tap register id */
70 static int iax2_tap = -1;
71
72 /* protocol tap info */
73 static iax2_info_t ii_arr[1];
74 static iax2_info_t *iax2_info = ii_arr;
75
76 /* The following hf_* variables are used to hold the wireshark IDs of
77  * our header fields; they are filled out when we call
78  * proto_register_field_array() in proto_register_iax2()
79  */
80 static int hf_iax2_packet_type = -1;
81 static int hf_iax2_retransmission = -1;
82 static int hf_iax2_callno = -1;
83 static int hf_iax2_scallno = -1;
84 static int hf_iax2_dcallno = -1;
85 static int hf_iax2_ts = -1;
86 static int hf_iax2_minits = -1;
87 static int hf_iax2_minividts = -1;
88 static int hf_iax2_absts = -1;
89 static int hf_iax2_lateness = -1;
90 static int hf_iax2_minividmarker = -1;
91 static int hf_iax2_oseqno = -1;
92 static int hf_iax2_iseqno = -1;
93 static int hf_iax2_type = -1;
94 static int hf_iax2_csub = -1;
95 static int hf_iax2_dtmf_csub = -1;
96 static int hf_iax2_cmd_csub = -1;
97 static int hf_iax2_iax_csub = -1;
98 static int hf_iax2_voice_csub = -1;
99 static int hf_iax2_voice_codec = -1;
100 static int hf_iax2_video_csub = -1;
101 static int hf_iax2_video_codec = -1;
102 static int hf_iax2_marker = -1;
103 static int hf_iax2_modem_csub = -1;
104 static int hf_iax2_trunk_metacmd = -1;
105 static int hf_iax2_trunk_cmddata = -1;
106 static int hf_iax2_trunk_cmddata_ts = -1;
107 static int hf_iax2_trunk_ts = -1;
108 static int hf_iax2_trunk_ncalls = -1;
109 static int hf_iax2_trunk_call_len = -1;
110 static int hf_iax2_trunk_call_scallno = -1;
111 static int hf_iax2_trunk_call_ts = -1;
112 static int hf_iax2_trunk_call_data = -1;
113
114 static int hf_iax2_cap_g723_1 = -1;
115 static int hf_iax2_cap_gsm = -1;
116 static int hf_iax2_cap_ulaw = -1;
117 static int hf_iax2_cap_alaw = -1;
118 static int hf_iax2_cap_g726_aal2 = -1;
119 static int hf_iax2_cap_adpcm = -1;
120 static int hf_iax2_cap_slinear = -1;
121 static int hf_iax2_cap_lpc10 = -1;
122 static int hf_iax2_cap_g729a = -1;
123 static int hf_iax2_cap_speex = -1;
124 static int hf_iax2_cap_ilbc = -1;
125 static int hf_iax2_cap_g726 = -1;
126 static int hf_iax2_cap_g722 = -1;
127 static int hf_iax2_cap_siren7 = -1;
128 static int hf_iax2_cap_siren14 = -1;
129 static int hf_iax2_cap_slinear16 = -1;
130 static int hf_iax2_cap_jpeg = -1;
131 static int hf_iax2_cap_png = -1;
132 static int hf_iax2_cap_h261 = -1;
133 static int hf_iax2_cap_h263 = -1;
134 static int hf_iax2_cap_h263_plus = -1;
135 static int hf_iax2_cap_h264 = -1;
136 static int hf_iax2_cap_mpeg4 = -1;
137
138 static int hf_iax2_fragments = -1;
139 static int hf_iax2_fragment = -1;
140 static int hf_iax2_fragment_overlap = -1;
141 static int hf_iax2_fragment_overlap_conflict = -1;
142 static int hf_iax2_fragment_multiple_tails = -1;
143 static int hf_iax2_fragment_too_long_fragment = -1;
144 static int hf_iax2_fragment_error = -1;
145 static int hf_iax2_fragment_count = -1;
146 static int hf_iax2_reassembled_in = -1;
147 static int hf_iax2_reassembled_length = -1;
148
149
150 /* hf_iax2_ies is an array of header fields, one per potential Information
151  * Element. It's done this way (rather than having separate variables for each
152  * IE) to make the dissection of information elements clearer and more
153  * orthogonal.
154  *
155  * To add the ability to dissect a new information element, just add an
156  * appropriate entry to hf[] in proto_register_iax2(); dissect_ies() will then
157  * pick it up automatically.
158  */
159 #define NUM_HF_IAX2_IES 256
160 static int hf_iax2_ies[NUM_HF_IAX2_IES];
161 static int hf_iax2_ie_datetime = -1;
162 static int hf_IAX_IE_APPARENTADDR_SINFAMILY = -1;
163 static int hf_IAX_IE_APPARENTADDR_SINPORT = -1;
164 static int hf_IAX_IE_APPARENTADDR_SINADDR = -1;
165 static int hf_IAX_IE_UNKNOWN_BYTE = -1;
166 static int hf_IAX_IE_UNKNOWN_I16 = -1;
167 static int hf_IAX_IE_UNKNOWN_I32 = -1;
168 static int hf_IAX_IE_UNKNOWN_BYTES = -1;
169
170 /* These are the ids of the subtrees that we may be creating */
171 static gint ett_iax2 = -1;
172 static gint ett_iax2_full_mini_subtree = -1;
173 static gint ett_iax2_type = -1;         /* Frame-type specific subtree */
174 static gint ett_iax2_ie = -1;           /* single IE */
175 static gint ett_iax2_codecs = -1;       /* capabilities IE */
176 static gint ett_iax2_ies_apparent_addr = -1; /* apparent address IE */
177 static gint ett_iax2_fragment = -1;
178 static gint ett_iax2_fragments = -1;
179 static gint ett_iax2_trunk_cmddata = -1;
180 static gint ett_iax2_trunk_call = -1;
181
182 static const fragment_items iax2_fragment_items = {
183   &ett_iax2_fragment,
184   &ett_iax2_fragments,
185   &hf_iax2_fragments,
186   &hf_iax2_fragment,
187   &hf_iax2_fragment_overlap,
188   &hf_iax2_fragment_overlap_conflict,
189   &hf_iax2_fragment_multiple_tails,
190   &hf_iax2_fragment_too_long_fragment,
191   &hf_iax2_fragment_error,
192   &hf_iax2_fragment_count,
193   &hf_iax2_reassembled_in,
194   &hf_iax2_reassembled_length,
195   "iax2 fragments"
196 };
197
198 static dissector_handle_t data_handle;
199
200 /* data-call subdissectors, AST_DATAFORMAT_* */
201 static dissector_table_t iax2_dataformat_dissector_table;
202 /* voice/video call subdissectors, AST_FORMAT_* */
203 static dissector_table_t iax2_codec_dissector_table;
204
205
206 /* IAX2 Meta trunk packet Command data flags */
207 #define IAX2_TRUNK_TS 1
208
209 /* IAX2 Full-frame types */
210 static const value_string iax_frame_types[] = {
211   {0, "(0?)"},
212   {AST_FRAME_DTMF_END, "DTMF End"},
213   {AST_FRAME_VOICE, "Voice"},
214   {AST_FRAME_VIDEO, "Video"},
215   {AST_FRAME_CONTROL, "Control"},
216   {AST_FRAME_NULL, "NULL"},
217   {AST_FRAME_IAX, "IAX"},
218   {AST_FRAME_TEXT, "Text"},
219   {AST_FRAME_IMAGE, "Image"},
220   {AST_FRAME_HTML, "HTML"},
221   {AST_FRAME_CNG, "Comfort Noise"},
222   {AST_FRAME_MODEM, "Modem"},
223   {AST_FRAME_DTMF_BEGIN, "DTMF Begin"},
224   {0,NULL}
225 };
226
227 /* Subclasses for IAX packets */
228 static const value_string iax_iax_subclasses[] = {
229   {0, "(0?)"},
230   {1, "NEW"},
231   {2, "PING"},
232   {3, "PONG"},
233   {4, "ACK"},
234   {5, "HANGUP"},
235   {6, "REJECT"},
236   {7, "ACCEPT"},
237   {8, "AUTHREQ"},
238   {9, "AUTHREP"},
239   {10, "INVAL"},
240   {11, "LAGRQ"},
241   {12, "LAGRP"},
242   {13, "REGREQ"},
243   {14, "REGAUTH"},
244   {15, "REGACK"},
245   {16, "REGREJ"},
246   {17, "REGREL"},
247   {18, "VNAK"},
248   {19, "DPREQ"},
249   {20, "DPREP"},
250   {21, "DIAL"},
251   {22, "TXREQ"},
252   {23, "TXCNT"},
253   {24, "TXACC"},
254   {25, "TXREADY"},
255   {26, "TXREL"},
256   {27, "TXREJ"},
257   {28, "QUELCH"},
258   {29, "UNQULCH"},
259   {30, "POKE"},
260   {31, "PAGE"},
261   {32, "MWI"},
262   {33, "UNSUPPORTED"},
263   {34, "TRANSFER"},
264   {35, "PROVISION"},
265   {36, "FWDOWNL"},
266   {37, "FWDATA"},
267   {38, "TXMEDIA"},
268   {39, "RTKEY"},
269   {40, "CALLTOKEN"},
270   {0,NULL}
271 };
272
273 /* Subclasses for Control packets */
274 static const value_string iax_cmd_subclasses[] = {
275   {0, "(0?)"},
276   {1, "HANGUP"},
277   {2, "RING"},
278   {3, "RINGING"},
279   {4, "ANSWER"},
280   {5, "BUSY"},
281   {6, "TKOFFHK"},
282   {7, "OFFHOOK"},
283   {0xFF, "stop sounds"}, /* sent by app_dial, and not much else */
284   {0,NULL}
285 };
286
287 /* IAX2 to tap-voip call state mapping */
288 static const voip_call_state tap_cmd_voip_state[] = {
289   VOIP_NO_STATE,
290   VOIP_COMPLETED, /*HANGUP*/
291   VOIP_RINGING,   /*RING*/
292   VOIP_RINGING,   /*RINGING*/
293   VOIP_IN_CALL,   /*ANSWER*/
294   VOIP_REJECTED,  /*BUSY*/
295   VOIP_UNKNOWN,   /*TKOFFHK*/
296   VOIP_UNKNOWN    /*OFFHOOK*/
297 };
298 #define NUM_TAP_CMD_VOIP_STATES array_length(tap_cmd_voip_state)
299
300 /* Subclasses for Modem packets */
301 static const value_string iax_modem_subclasses[] = {
302   {0, "(0?)"},
303   {1, "T.38"},
304   {2, "V.150"},
305   {0,NULL}
306 };
307
308 /* Information elements */
309 static const value_string iax_ies_type[] = {
310   {IAX_IE_CALLED_NUMBER,    "Number/extension being called"},
311   {IAX_IE_CALLING_NUMBER,   "Calling number"},
312   {IAX_IE_CALLING_ANI,      "Calling number ANI for billing"},
313   {IAX_IE_CALLING_NAME,     "Name of caller"},
314   {IAX_IE_CALLED_CONTEXT,   "Context for number"},
315   {IAX_IE_USERNAME,         "Username (peer or user) for authentication"},
316   {IAX_IE_PASSWORD,         "Password for authentication"},
317   {IAX_IE_CAPABILITY,       "Actual codec capability"},
318   {IAX_IE_FORMAT,           "Desired codec format"},
319   {IAX_IE_LANGUAGE,         "Desired language"},
320   {IAX_IE_VERSION,          "Protocol version"},
321   {IAX_IE_ADSICPE,          "CPE ADSI capability"},
322   {IAX_IE_DNID,             "Originally dialed DNID"},
323   {IAX_IE_AUTHMETHODS,      "Authentication method(s)"},
324   {IAX_IE_CHALLENGE,        "Challenge data for MD5/RSA"},
325   {IAX_IE_MD5_RESULT,       "MD5 challenge result"},
326   {IAX_IE_RSA_RESULT,       "RSA challenge result"},
327   {IAX_IE_APPARENT_ADDR,    "Apparent address of peer"},
328   {IAX_IE_REFRESH,          "When to refresh registration"},
329   {IAX_IE_DPSTATUS,         "Dialplan status"},
330   {IAX_IE_CALLNO,           "Call number of peer"},
331   {IAX_IE_CAUSE,            "Cause"},
332   {IAX_IE_IAX_UNKNOWN,      "Unknown IAX command"},
333   {IAX_IE_MSGCOUNT,         "How many messages waiting"},
334   {IAX_IE_AUTOANSWER,       "Request auto-answering"},
335   {IAX_IE_MUSICONHOLD,      "Request musiconhold with QUELCH"},
336   {IAX_IE_TRANSFERID,       "Transfer Request Identifier"},
337   {IAX_IE_RDNIS,            "Referring DNIS"},
338   {IAX_IE_PROVISIONING,     "Provisioning info"},
339   {IAX_IE_AESPROVISIONING,  "AES Provisioning info"},
340   {IAX_IE_DATETIME,         "Date/Time"},
341   {IAX_IE_DEVICETYPE,       "Device type"},
342   {IAX_IE_SERVICEIDENT,     "Service Identifier"},
343   {IAX_IE_FIRMWAREVER,      "Firmware revision"},
344   {IAX_IE_FWBLOCKDESC,      "Firmware block description"},
345   {IAX_IE_FWBLOCKDATA,      "Firmware block of data"},
346   {IAX_IE_PROVVER,          "Provisioning version"},
347   {IAX_IE_CALLINGPRES,      "Calling presentation"},
348   {IAX_IE_CALLINGTON,       "Calling type of number"},
349   {IAX_IE_CALLINGTNS,       "Calling transit network select"},
350   {IAX_IE_SAMPLINGRATE,     "Supported sampling rates"},
351   {IAX_IE_CAUSECODE,        "Hangup cause"},
352   {IAX_IE_ENCRYPTION,       "Encryption format"},
353   {IAX_IE_ENCKEY,           "Raw encryption key"},
354   {IAX_IE_CODEC_PREFS,      "Codec preferences"},
355   {IAX_IE_RR_JITTER,        "Received jitter"},
356   {IAX_IE_RR_LOSS,          "Received loss"},
357   {IAX_IE_RR_PKTS,          "Received frames"},
358   {IAX_IE_RR_DELAY,         "Max playout delay in ms for received frames"},
359   {IAX_IE_RR_DROPPED,       "Dropped frames"},
360   {IAX_IE_RR_OOO,           "Frames received out of order"},
361   {IAX_IE_DATAFORMAT,       "Data call format"},
362   {IAX_IE_VARIABLE,         "IAX2 variable"},
363   {IAX_IE_OSPTOKEN,         "OSP Token"},
364   {IAX_IE_CALLTOKEN,        "Call Token"},
365   {IAX_IE_CAPABILITY2,      "64-bit codec capability"},
366   {IAX_IE_FORMAT2,          "64-bit codec format"},
367   {0,NULL}
368 };
369
370 static const value_string codec_types[] = {
371   {AST_FORMAT_G723_1,   "G.723.1 compression"},
372   {AST_FORMAT_GSM,      "GSM compression"},
373   {AST_FORMAT_ULAW,     "Raw mu-law data (G.711)"},
374   {AST_FORMAT_ALAW,     "Raw A-law data (G.711)"},
375   {AST_FORMAT_G726_AAL2,"ADPCM (G.726, 32kbps)"},
376   {AST_FORMAT_ADPCM,    "ADPCM (IMA)"},
377   {AST_FORMAT_SLINEAR,  "Raw 16-bit Signed Linear (8000 Hz) PCM"},
378   {AST_FORMAT_LPC10,    "LPC10, 180 samples/frame"},
379   {AST_FORMAT_G729A,    "G.729a Audio"},
380   {AST_FORMAT_SPEEX,    "SpeeX Free Compression"},
381   {AST_FORMAT_ILBC,     "iLBC Free Compression"},
382   {AST_FORMAT_G726,     "G.726 compression"},
383   {AST_FORMAT_G722,     "G.722 wideband"},
384   {AST_FORMAT_SIREN7,   "G.722.1 32k wideband (aka Siren7)"},
385   {AST_FORMAT_SIREN14,  "G.722.1 Annex C 48k wideband (aka Siren14)"},
386   {AST_FORMAT_SLINEAR16,"Raw 16kHz signed linear audio"},
387   {AST_FORMAT_JPEG,     "JPEG Images"},
388   {AST_FORMAT_PNG,      "PNG Images"},
389   {AST_FORMAT_H261,     "H.261 Video"},
390   {AST_FORMAT_H263,     "H.263 Video"},
391   {AST_FORMAT_H263_PLUS,"H.263+ Video"},
392   {AST_FORMAT_H264,     "H.264 Video"},
393   {AST_FORMAT_MP4_VIDEO,"MPEG4 Video"},
394   {0,NULL}
395 };
396
397 static const value_string iax_dataformats[] = {
398   {AST_DATAFORMAT_NULL,     "N/A (analogue call?)"},
399   {AST_DATAFORMAT_V110,     "ITU-T V.110 rate adaption"},
400   {AST_DATAFORMAT_H223_H245,"ITU-T H.223/H.245"},
401   {0,NULL}
402 };
403
404
405 static const value_string iax_packet_types[] = {
406   {IAX2_FULL_PACKET,       "Full packet"},
407   {IAX2_MINI_VOICE_PACKET, "Mini voice packet"},
408   {IAX2_MINI_VIDEO_PACKET, "Mini video packet"},
409   {IAX2_TRUNK_PACKET,      "Trunk packet"},
410   {0,NULL}
411 };
412
413 static const value_string iax_causecodes[] = {
414   {AST_CAUSE_UNALLOCATED,                 "Unallocated"},
415   {AST_CAUSE_NO_ROUTE_TRANSIT_NET,        "No route transit net"},
416   {AST_CAUSE_NO_ROUTE_DESTINATION,        "No route to destination"},
417   {AST_CAUSE_MISDIALLED_TRUNK_PREFIX,     "Misdialled trunk prefix"},
418   {AST_CAUSE_CHANNEL_UNACCEPTABLE,        "Channel unacceptable"},
419   {AST_CAUSE_CALL_AWARDED_DELIVERED,      "Call awarded delivered"},
420   {AST_CAUSE_PRE_EMPTED,                  "Preempted"},
421   {AST_CAUSE_NUMBER_PORTED_NOT_HERE,      "Number ported not here"},
422   {AST_CAUSE_NORMAL_CLEARING,             "Normal clearing"},
423   {AST_CAUSE_USER_BUSY,                   "User busy"},
424   {AST_CAUSE_NO_USER_RESPONSE,            "No user response"},
425   {AST_CAUSE_NO_ANSWER,                   "No answer"},
426   {AST_CAUSE_SUBSCRIBER_ABSENT,           "Subscriber absent"},
427   {AST_CAUSE_CALL_REJECTED,               "Call rejected"},
428   {AST_CAUSE_NUMBER_CHANGED,              "Number changed"},
429   {AST_CAUSE_REDIRECTED_TO_NEW_DESTINATION,"Redirected to new destination"},
430   {AST_CAUSE_ANSWERED_ELSEWHERE,          "Answered elsewhere"},
431   {AST_CAUSE_DESTINATION_OUT_OF_ORDER,    "Destination out of order"},
432   {AST_CAUSE_INVALID_NUMBER_FORMAT,       "Invalid number format"},
433   {AST_CAUSE_FACILITY_REJECTED,           "Facility rejected"},
434   {AST_CAUSE_RESPONSE_TO_STATUS_ENQUIRY,  "Response to status inquiry"},
435   {AST_CAUSE_NORMAL_UNSPECIFIED,          "Normal unspecified"},
436   {AST_CAUSE_NORMAL_CIRCUIT_CONGESTION,   "Normal circuit congestion"},
437   {AST_CAUSE_NETWORK_OUT_OF_ORDER,        "Network out of order"},
438   {AST_CAUSE_NORMAL_TEMPORARY_FAILURE,    "Normal temporary failure"},
439   {AST_CAUSE_SWITCH_CONGESTION,           "Switch congestion"},
440   {AST_CAUSE_ACCESS_INFO_DISCARDED,       "Access info discarded"},
441   {AST_CAUSE_REQUESTED_CHAN_UNAVAIL,      "Requested channel unavailable"},
442   {AST_CAUSE_FACILITY_NOT_SUBSCRIBED,     "Facility not subscribed"},
443   {AST_CAUSE_OUTGOING_CALL_BARRED,        "Outgoing call barred"},
444   {AST_CAUSE_INCOMING_CALL_BARRED,        "Incoming call barred"},
445   {AST_CAUSE_BEARERCAPABILITY_NOTAUTH,    "Bearer capability not authorized"},
446   {AST_CAUSE_BEARERCAPABILITY_NOTAVAIL,   "Bearer capability not available"},
447   {AST_CAUSE_BEARERCAPABILITY_NOTIMPL,    "Bearer capability not implemented"},
448   {AST_CAUSE_CHAN_NOT_IMPLEMENTED,        "Channel not implemented"},
449   {AST_CAUSE_FACILITY_NOT_IMPLEMENTED,    "Facility not implemented"},
450   {AST_CAUSE_INVALID_CALL_REFERENCE,      "Invalid call reference"},
451   {AST_CAUSE_INCOMPATIBLE_DESTINATION,    "Incompatible destination"},
452   {AST_CAUSE_INVALID_MSG_UNSPECIFIED,     "Invalid message unspecified"},
453   {AST_CAUSE_MANDATORY_IE_MISSING,        "Mandatory IE missing"},
454   {AST_CAUSE_MESSAGE_TYPE_NONEXIST,       "Message type nonexistent"},
455   {AST_CAUSE_WRONG_MESSAGE,               "Wrong message"},
456   {AST_CAUSE_IE_NONEXIST,                 "IE nonexistent"},
457   {AST_CAUSE_INVALID_IE_CONTENTS,         "Invalid IE contents"},
458   {AST_CAUSE_WRONG_CALL_STATE,            "Wrong call state"},
459   {AST_CAUSE_RECOVERY_ON_TIMER_EXPIRE,    "Recovery on timer expire"},
460   {AST_CAUSE_MANDATORY_IE_LENGTH_ERROR,   "Mandatory IE length error"},
461   {AST_CAUSE_PROTOCOL_ERROR,              "Protocol error"},
462   {AST_CAUSE_INTERWORKING,                "Interworking"},
463   {0, NULL}
464 };
465
466
467 /* ************************************************************************* */
468
469 /* In order to track IAX calls, we have a hash table which maps
470  * {addr,port type,port,call} to a unique circuit id.
471  *
472  * Each call has two such circuits associated with it (a forward and a
473  * reverse circuit, where 'forward' is defined as the direction the NEW
474  * packet went in), and we maintain an iax_call_data structure for each
475  * call, attached to both circuits with circuit_add_proto_data.
476  *
477  * Because {addr,port type,port,call} quadruplets can be reused
478  * (Asterisk reuses call numbers), circuit ids aren't unique to
479  * individual calls and we treat NEW packets somewhat specially. When we
480  * get such a packet, we see if there are any calls with a matching
481  * circuit id, and make sure that its circuits are marked as ended
482  * before that packet.
483  *
484  * A second complication is that we only know one quadruplet at the time
485  * the NEW packet is processed: there is therefore cunningness in
486  * iax_lookup_circuit_details() to look for replies to NEW packets and
487  * create the reverse circuit.
488  */
489
490
491 /* start with a hash of {addr,port type,port,call}->{id} */
492
493 typedef struct {
494   address addr;
495   port_type ptype;
496   guint32 port;
497   guint32 callno;
498
499   /* this is where addr->data points to. it's put in here for easy freeing */
500   guint8 address_data[MAX_ADDRESS];
501 } iax_circuit_key;
502
503 /* tables */
504 static GHashTable *iax_circuit_hashtab = NULL;
505 static guint circuitcount = 0;
506
507 /* the number of keys and values to reserve space for in each memory chunk.
508    We assume we won't be tracking many calls at once so this is quite low.
509 */
510 #define IAX_INIT_PACKET_COUNT 10
511
512 #ifdef DEBUG_HASHING
513 static gchar *key_to_str( const iax_circuit_key *key )
514 {
515   static int i=0;
516   static gchar *strp, str[3][80];
517
518   i++;
519   if(i>=3){
520     i=0;
521   }
522   strp=str[i];
523
524   /* why doesn't ep_address_to_str take a const pointer?
525      cast the warnings into oblivion. */
526
527   /* XXX - is this a case for ep_alloc? */
528   g_snprintf(strp, 80, "{%s:%i,%i}",
529              ep_address_to_str((address *)&key->addr),
530              key->port,
531              key->callno);
532   return strp;
533 }
534 #endif
535
536 /* Hash Functions */
537 static gint iax_circuit_equal(gconstpointer v, gconstpointer w)
538 {
539   const iax_circuit_key *v1 = (const iax_circuit_key *)v;
540   const iax_circuit_key *v2 = (const iax_circuit_key *)w;
541   gint result;
542
543   result = ( ADDRESSES_EQUAL(&(v1->addr), &(v2->addr)) &&
544              v1->ptype == v2->ptype &&
545              v1->port  == v2->port &&
546              v1->callno== v2->callno);
547 #ifdef DEBUG_HASHING
548   g_debug( "+++ Comparing for equality: %s, %s: %u",key_to_str(v1), key_to_str(v2), result);
549 #endif
550
551   return result;
552 }
553
554 static guint iax_circuit_hash (gconstpointer v)
555 {
556   const iax_circuit_key *key = (const iax_circuit_key *)v;
557   guint hash_val;
558
559   hash_val = 0;
560   ADD_ADDRESS_TO_HASH(hash_val, &key->addr);
561   hash_val += (guint)(key->ptype);
562   hash_val += (guint)(key->port);
563   hash_val += (guint)(key->callno);
564
565 #ifdef DEBUG_HASHING
566   g_debug( "+++ Hashing key: %s, result %#x", key_to_str(key), hash_val );
567 #endif
568
569   return (guint) hash_val;
570 }
571
572 /* Find, or create, a circuit for the given
573    {address,porttype,port,call} quadruplet
574 */
575 static guint iax_circuit_lookup(const address *address_p,
576                                 port_type ptype,
577                                 guint32 port,
578                                 guint32 callno)
579 {
580   iax_circuit_key key;
581   guint32 *circuit_id_p;
582
583   key.addr = *address_p;
584   key.ptype = ptype;
585   key.port = port;
586   key.callno = callno;
587
588   circuit_id_p = g_hash_table_lookup( iax_circuit_hashtab, &key);
589   if( ! circuit_id_p ) {
590     iax_circuit_key *new_key;
591
592     new_key = se_alloc(sizeof(iax_circuit_key));
593     new_key->addr.type = address_p->type;
594     new_key->addr.len = MIN(address_p->len,MAX_ADDRESS);
595     new_key->addr.data = new_key->address_data;
596     memcpy(new_key->address_data,address_p->data,new_key->addr.len);
597     new_key->ptype = ptype;
598     new_key->port = port;
599     new_key->callno = callno;
600
601     circuit_id_p = se_alloc(sizeof(iax_circuit_key));
602     *circuit_id_p = ++circuitcount;
603
604     g_hash_table_insert(iax_circuit_hashtab, new_key, circuit_id_p);
605
606 #ifdef DEBUG_HASHING
607     g_debug("Created new circuit id %u for node %s", *circuit_id_p, key_to_str(new_key));
608 #endif
609   }
610
611   return *circuit_id_p;
612 }
613
614
615 /* ************************************************************************* */
616
617 typedef struct {
618   guint32     current_frag_id; /* invalid unless current_frag_bytes > 0 */
619   guint32     current_frag_bytes;
620   guint32     current_frag_minlen;
621 } iax_call_dirdata;
622
623 /* This is our per-call data structure, which is attached to both the
624  * forward and reverse circuits.
625  */
626 typedef struct iax_call_data {
627   /* For this data, src and dst are relative to the original direction under
628      which this call is stored. Obviously if the reversed flag is set true by
629      iax_find_call, src and dst are reversed relative to the direction the
630      actual source and destination of the data.
631
632      if the codec changes mid-call, we update it here; because we store a codec
633      number with each packet too, we handle going back to earlier packets
634      without problem.
635   */
636
637   iax_dataformat_t dataformat;
638   guint32 src_codec, dst_codec;
639   guint32 src_vformat, dst_vformat;
640
641   /* when a transfer takes place, we'll get a new circuit id; we assume that we
642      don't try to transfer more than IAX_MAX_TRANSFERS times in a call */
643   guint forward_circuit_ids[IAX_MAX_TRANSFERS];
644   guint reverse_circuit_ids[IAX_MAX_TRANSFERS];
645   guint n_forward_circuit_ids;
646   guint n_reverse_circuit_ids;
647
648   /* this is the subdissector for the call */
649   dissector_handle_t subdissector;
650
651   /* the absolute start time of the call */
652   nstime_t start_time;
653
654   GHashTable *fid_table;
655   GHashTable *fragment_table;
656   iax_call_dirdata dirdata[2];
657 } iax_call_data;
658
659 static void iax_init_hash( void )
660 {
661   if (iax_circuit_hashtab)
662     g_hash_table_destroy(iax_circuit_hashtab);
663
664   iax_circuit_hashtab = g_hash_table_new(iax_circuit_hash, iax_circuit_equal);
665
666   circuitcount = 0;
667 }
668
669
670
671 /* creates a new CT_IAX2 circuit with a specified circuit id for a call
672  *
673  * typically a call has up to three associated circuits: an original source, an
674  * original destination, and the result of a transfer.
675  *
676  * For each endpoint, a CT_IAX2 circuit is created and added to the call_data
677  * by this function
678  *
679  * 'reversed' should be true if this end is the one which would have _received_
680  * the NEW packet, or it is an endpoint to which the 'destination' is being
681  * transferred.
682  *
683  */
684 static circuit_t *iax2_new_circuit_for_call(guint circuit_id, guint framenum, iax_call_data *iax_call,
685                                             gboolean reversed)
686 {
687   circuit_t *res;
688
689   if(( reversed && iax_call->n_reverse_circuit_ids >= IAX_MAX_TRANSFERS) ||
690      ( !reversed && iax_call->n_forward_circuit_ids >= IAX_MAX_TRANSFERS)) {
691     g_warning("Too many transfers for iax_call");
692     return NULL;
693   }
694
695   res = circuit_new(CT_IAX2,
696                     circuit_id,
697                     framenum );
698
699   circuit_add_proto_data(res, proto_iax2, iax_call);
700
701   if( reversed )
702     iax_call -> reverse_circuit_ids[iax_call->n_reverse_circuit_ids++] = circuit_id;
703   else
704     iax_call -> forward_circuit_ids[iax_call->n_forward_circuit_ids++] = circuit_id;
705
706   return res;
707 }
708
709
710 /* returns true if this circuit id is a "forward" circuit for this call: ie, it
711  * is the point which _sent_ the original 'NEW' packet, or a point to which that
712  * end was subsequently transferred */
713 static gboolean is_forward_circuit(guint circuit_id,
714                                    const iax_call_data *iax_call)
715 {
716   guint i;
717   for(i=0;i<iax_call->n_forward_circuit_ids;i++){
718     if(circuit_id == iax_call->forward_circuit_ids[i])
719       return TRUE;
720   }
721   return FALSE;
722 }
723
724 /* returns true if this circuit id is a "reverse" circuit for this call: ie, it
725  * is the point which _received_ the original 'NEW' packet, or a point to which that
726  * end was subsequently transferred */
727 static gboolean is_reverse_circuit(guint circuit_id,
728                                    const iax_call_data *iax_call)
729 {
730   guint i;
731   for(i=0;i<iax_call->n_reverse_circuit_ids;i++){
732     if(circuit_id == iax_call->reverse_circuit_ids[i])
733       return TRUE;
734   }
735   return FALSE;
736 }
737
738
739 static iax_call_data *iax_lookup_call_from_dest( guint src_circuit_id,
740                                                  guint dst_circuit_id,
741                                                  guint framenum,
742                                                  gboolean *reversed_p)
743 {
744   circuit_t *dst_circuit;
745   iax_call_data * iax_call;
746   gboolean reversed = FALSE;
747
748   dst_circuit = find_circuit( CT_IAX2,
749                               dst_circuit_id,
750                               framenum );
751
752   if( !dst_circuit ) {
753 #ifdef DEBUG_HASHING
754     g_debug( "++ destination circuit not found, must have missed NEW packet" );
755 #endif
756     if( reversed_p )
757       *reversed_p = FALSE;
758     return NULL;
759   }
760
761 #ifdef DEBUG_HASHING
762   g_debug( "++ found destination circuit" );
763 #endif
764
765   iax_call = (iax_call_data *)circuit_get_proto_data(dst_circuit,proto_iax2);
766
767   /* there's no way we can create a CT_IAX2 circuit without adding
768      iax call data to it; assert this */
769   DISSECTOR_ASSERT(iax_call);
770
771   if( is_forward_circuit(dst_circuit_id, iax_call )) {
772 #ifdef DEBUG_HASHING
773     g_debug( "++ destination circuit matches forward_circuit_id of call, "
774              "therefore packet is reversed" );
775 #endif
776
777     reversed = TRUE;
778
779     if( iax_call -> n_reverse_circuit_ids == 0 ) {
780       /* we are going in the reverse direction, and this call
781          doesn't have a reverse circuit associated with it.
782          create one now. */
783 #ifdef DEBUG_HASHING
784       g_debug( "++ reverse_circuit_id of call is zero, need to create a "
785                "new reverse circuit for this call" );
786 #endif
787
788       iax2_new_circuit_for_call( src_circuit_id, framenum, iax_call, TRUE );
789 #ifdef DEBUG_HASHING
790       g_debug( "++ done" );
791 #endif
792     } else if( !is_reverse_circuit(src_circuit_id, iax_call )) {
793       g_warning( "IAX Packet %u from circuit ids %u->%u "
794                  "conflicts with earlier call with circuit ids %u->%u",
795                  framenum,
796                  src_circuit_id,dst_circuit_id,
797                  iax_call->forward_circuit_ids[0],
798                  iax_call->reverse_circuit_ids[0]);
799       return NULL;
800     }
801   } else if ( is_reverse_circuit(dst_circuit_id, iax_call)) {
802 #ifdef DEBUG_HASHING
803     g_debug( "++ destination circuit matches reverse_circuit_id of call, "
804              "therefore packet is forward" );
805 #endif
806
807     reversed = FALSE;
808     if( !is_forward_circuit(src_circuit_id, iax_call)) {
809       g_warning( "IAX Packet %u from circuit ids %u->%u "
810                  "conflicts with earlier call with circuit ids %u->%u",
811                  framenum,
812                  src_circuit_id,dst_circuit_id,
813                  iax_call->forward_circuit_ids[0],
814                  iax_call->reverse_circuit_ids[0]);
815       if( reversed_p )
816         *reversed_p = FALSE;
817       return NULL;
818     }
819   } else {
820     DISSECTOR_ASSERT_NOT_REACHED();
821   }
822
823   if( reversed_p )
824     *reversed_p = reversed;
825
826   return iax_call;
827 }
828
829
830 /* looks up an iax_call for this packet */
831 static iax_call_data *iax_lookup_call( packet_info *pinfo,
832                                        guint32 scallno,
833                                        guint32 dcallno,
834                                        gboolean *reversed_p)
835 {
836   gboolean reversed = FALSE;
837   iax_call_data *iax_call = NULL;
838   guint src_circuit_id;
839
840 #ifdef DEBUG_HASHING
841   g_debug( "++ iax_lookup_circuit_details: Looking up circuit for frame %u, "
842              "from {%s:%u:%u} to {%s:%u:%u}", pinfo->fd->num,
843              ep_address_to_str(&pinfo->src),pinfo->srcport,scallno,
844              ep_address_to_str(&pinfo->dst),pinfo->destport,dcallno);
845 #endif
846
847
848   src_circuit_id = iax_circuit_lookup(&pinfo->src,pinfo->ptype,
849                                       pinfo->srcport,scallno);
850
851
852   /* the most reliable indicator of call is the destination callno, if
853      we have one */
854   if( dcallno != 0 ) {
855     guint dst_circuit_id;
856 #ifdef DEBUG_HASHING
857     g_debug( "++ dcallno non-zero, looking up destination circuit" );
858 #endif
859
860     dst_circuit_id = iax_circuit_lookup(&pinfo->dst,pinfo->ptype,
861                                         pinfo->destport,dcallno);
862
863     iax_call = iax_lookup_call_from_dest(src_circuit_id, dst_circuit_id,
864                                          pinfo->fd->num, &reversed);
865   } else {
866     circuit_t *src_circuit;
867
868     /* in all other circumstances, the source circuit should already
869      * exist: its absence indicates that we missed the all-important NEW
870      * packet.
871      */
872
873     src_circuit = find_circuit( CT_IAX2,
874                             src_circuit_id,
875                             pinfo->fd->num );
876
877     if( src_circuit ) {
878       iax_call = (iax_call_data *)circuit_get_proto_data(src_circuit,proto_iax2);
879
880       /* there's no way we can create a CT_IAX2 circuit without adding
881          iax call data to it; assert this */
882       DISSECTOR_ASSERT(iax_call);
883
884       if( is_forward_circuit(src_circuit_id,iax_call))
885         reversed = FALSE;
886       else if(is_reverse_circuit(src_circuit_id,iax_call))
887         reversed = TRUE;
888       else {
889         /* there's also no way we can attach an iax_call_data to a circuit
890            without the circuit being either the forward or reverse circuit
891            for that call; assert this too.
892         */
893         DISSECTOR_ASSERT_NOT_REACHED();
894       }
895     }
896   }
897
898   if(reversed_p)
899     *reversed_p = reversed;
900
901 #ifdef DEBUG_HASHING
902   if( iax_call ) {
903     g_debug( "++ Found call for packet: id %u, reversed=%c", iax_call->forward_circuit_ids[0], reversed?'1':'0' );
904   } else {
905     g_debug( "++ Call not found. Must have missed the NEW packet?" );
906   }
907 #endif
908
909   return iax_call;
910 }
911
912 /* initialize the per-direction parts of an iax_call_data structure */
913 static void init_dir_data(iax_call_dirdata *dirdata)
914 {
915   dirdata -> current_frag_bytes=0;
916   dirdata -> current_frag_minlen=0;
917 }
918
919
920 /* handles a NEW packet by creating a new iax call and forward circuit.
921    the reverse circuit is not created until the ACK is received and
922    is created by iax_lookup_circuit_details. */
923 static iax_call_data *iax_new_call( packet_info *pinfo,
924                                     guint32 scallno)
925 {
926   iax_call_data *call;
927   guint circuit_id;
928   static const nstime_t millisecond = {0, 1000000};
929
930 #ifdef DEBUG_HASHING
931   g_debug( "+ new_circuit: Handling NEW packet, frame %u", pinfo->fd->num );
932 #endif
933
934   circuit_id = iax_circuit_lookup(&pinfo->src,pinfo->ptype,
935                                   pinfo->srcport,scallno);
936
937   call = se_alloc(sizeof(iax_call_data));
938   call -> dataformat = 0;
939   call -> src_codec = 0;
940   call -> dst_codec = 0;
941   call -> n_forward_circuit_ids = 0;
942   call -> n_reverse_circuit_ids = 0;
943   call -> subdissector = NULL;
944   call -> start_time = pinfo->fd->abs_ts;
945   nstime_delta(&call -> start_time, &call -> start_time, &millisecond);
946   call -> fid_table = g_hash_table_new(g_direct_hash, g_direct_equal);
947   init_dir_data(&call->dirdata[0]);
948   init_dir_data(&call->dirdata[1]);
949   call->fragment_table = NULL;
950   fragment_table_init(&(call->fragment_table));
951
952   iax2_new_circuit_for_call(circuit_id,pinfo->fd->num,call,FALSE);
953
954   return call;
955 }
956
957
958 /* ************************************************************************* */
959
960 /* per-packet data */
961 typedef struct iax_packet_data {
962   gboolean first_time; /* we're dissecting this packet for the first time; so
963                           things like codec and transfer requests should be
964                           propagated into the call data */
965   iax_call_data *call_data;
966   guint32 codec;
967   gboolean reversed;
968   nstime_t abstime;    /* the absolute time of this packet, based on its
969                         * timestamp and the NEW packet's time (-1 if unknown) */
970 } iax_packet_data;
971
972 static iax_packet_data *iax_new_packet_data(iax_call_data *call, gboolean reversed)
973 {
974   iax_packet_data *p = se_alloc(sizeof(iax_packet_data));
975   p->first_time=TRUE;
976   p->call_data=call;
977   p->codec=0;
978   p->reversed=reversed;
979   p->abstime.secs=-1;
980   p->abstime.nsecs=-1;
981   return p;
982 }
983
984 static void  iax2_populate_pinfo_from_packet_data(packet_info *pinfo, const iax_packet_data * p)
985 {
986   /* info for subdissectors. We always pass on the original forward circuit,
987    * and steal the p2p_dir flag to indicate the direction */
988   if( p->call_data == NULL ) {
989      /* if we missed the NEW packet for this call, call_data will be null. it's
990       * tbd what the best thing to do here is. */
991     pinfo -> ctype = CT_NONE;
992   } else {
993     pinfo -> ctype = CT_IAX2;
994     pinfo -> circuit_id = (guint32)p->call_data->forward_circuit_ids[0];
995     pinfo -> p2p_dir = p->reversed?P2P_DIR_RECV:P2P_DIR_SENT;
996
997     if (check_col (pinfo->cinfo, COL_IF_DIR))
998       col_set_str (pinfo->cinfo, COL_IF_DIR, p->reversed ? "rev" : "fwd" );
999   }
1000 }
1001
1002
1003 /* ************************************************************************* */
1004
1005 /* this is passed up from the IE dissector to the main dissector */
1006 typedef struct
1007 {
1008   address peer_address;
1009   port_type peer_ptype;
1010   guint32 peer_port;
1011   guint32 peer_callno;
1012   guint32 dataformat;
1013 } iax2_ie_data;
1014
1015
1016 static guint32 dissect_fullpacket (tvbuff_t * tvb, guint32 offset,
1017                                    guint16 scallno,
1018                                    packet_info * pinfo,
1019                                    proto_tree * iax2_tree,
1020                                    proto_tree * main_tree);
1021
1022
1023 static guint32 dissect_minipacket (tvbuff_t * tvb, guint32 offset,
1024                                    guint16 scallno,
1025                                    packet_info * pinfo,
1026                                    proto_tree * iax2_tree,
1027                                    proto_tree * main_tree);
1028
1029 static guint32 dissect_minivideopacket (tvbuff_t * tvb, guint32 offset,
1030                                         guint16 scallno,
1031                                         packet_info * pinfo,
1032                                         proto_tree * iax2_tree,
1033                                         proto_tree * main_tree);
1034
1035 static guint32 dissect_trunkpacket (tvbuff_t * tvb, guint32 offset,
1036                                         guint16 scallno,
1037                                         packet_info * pinfo,
1038                                         proto_tree * iax2_tree,
1039                                         proto_tree * main_tree);
1040
1041 static void dissect_payload(tvbuff_t *tvb, guint32 offset,
1042                             packet_info *pinfo, proto_tree *iax2_tree,
1043                             proto_tree *tree, guint32 ts, gboolean video,
1044                             iax_packet_data *iax_packet);
1045
1046
1047
1048 static void
1049 dissect_iax2 (tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree)
1050 {
1051   proto_item *iax2_item = NULL;
1052   proto_tree *iax2_tree = NULL;
1053   proto_tree *full_mini_subtree = NULL;
1054   guint32 offset = 0, len;
1055   guint16 scallno = 0;
1056   guint16 stmp;
1057   packet_type type;
1058
1059   /* set up the protocol and info fields in the summary pane */
1060   col_set_str (pinfo->cinfo, COL_PROTOCOL, PROTO_TAG_IAX2);
1061   col_clear(pinfo->cinfo, COL_INFO);
1062
1063   /* add the 'iax2' tree to the main tree */
1064   if (tree)
1065     {
1066       iax2_item = proto_tree_add_item (tree, proto_iax2, tvb, offset, -1, ENC_NA);
1067       iax2_tree = proto_item_add_subtree (iax2_item, ett_iax2);
1068     }
1069
1070   stmp = tvb_get_ntohs(tvb, offset);
1071   if( stmp == 0 ) {
1072     /* starting with 0x0000 indicates meta packet which can be either a mini
1073      * video packet or a trunk packet */
1074     offset+=2;
1075     stmp = tvb_get_ntohs(tvb, offset);
1076     if( stmp & 0x8000 ) {
1077       /* mini video packet */
1078       type = IAX2_MINI_VIDEO_PACKET;
1079       scallno = stmp & 0x7FFF;
1080       offset += 2;
1081     }
1082     else {
1083       type = IAX2_TRUNK_PACKET;
1084     }
1085   } else {
1086     /* The source call/fullpacket flag is common to both mini and full packets */
1087     scallno = tvb_get_ntohs(tvb, offset);
1088     offset += 2;
1089     if( scallno & 0x8000 )
1090       type = IAX2_FULL_PACKET;
1091     else {
1092       type = IAX2_MINI_VOICE_PACKET;
1093     }
1094     scallno &= 0x7FFF;
1095   }
1096
1097   if( tree ) {
1098     proto_item *full_mini_base;
1099
1100     full_mini_base = proto_tree_add_uint(iax2_tree, hf_iax2_packet_type, tvb, 0, offset, type);
1101     full_mini_subtree = proto_item_add_subtree(full_mini_base, ett_iax2_full_mini_subtree);
1102
1103     if( scallno != 0 )
1104       proto_tree_add_item (full_mini_subtree, hf_iax2_scallno, tvb, offset-2, 2, ENC_BIG_ENDIAN);
1105   }
1106
1107   iax2_info->ptype = type;
1108   iax2_info->scallno = 0;
1109   iax2_info->dcallno = 0;
1110   iax2_info->ftype = 0;
1111   iax2_info->csub = 0;
1112   iax2_info->payload_len = 0;
1113   iax2_info->timestamp = 0;
1114   iax2_info->callState = VOIP_NO_STATE;
1115   iax2_info->messageName = NULL;
1116   iax2_info->callingParty = NULL;
1117   iax2_info->calledParty = NULL;
1118   iax2_info->payload_data = NULL;
1119
1120   switch( type ) {
1121     case IAX2_FULL_PACKET:
1122       len = dissect_fullpacket( tvb, offset, scallno, pinfo, full_mini_subtree, tree );
1123       break;
1124     case IAX2_MINI_VOICE_PACKET:
1125       iax2_info->messageName = "MINI_VOICE_PACKET";
1126       len = dissect_minipacket( tvb, offset, scallno, pinfo, full_mini_subtree, tree );
1127       break;
1128     case IAX2_MINI_VIDEO_PACKET:
1129       iax2_info->messageName = "MINI_VIDEO_PACKET";
1130       len = dissect_minivideopacket( tvb, offset, scallno, pinfo, full_mini_subtree, tree );
1131       break;
1132     case IAX2_TRUNK_PACKET:
1133       iax2_info->messageName = "TRUNK_PACKET";
1134       len = dissect_trunkpacket( tvb, offset, scallno, pinfo, full_mini_subtree, tree );
1135       break;
1136     default:
1137       len = 0;
1138   }
1139
1140   /* update the 'length' of the main IAX2 header field so that it covers just the headers,
1141      not the audio data. */
1142   proto_item_set_len(iax2_item, len);
1143   tap_queue_packet(iax2_tap, pinfo, iax2_info);
1144 }
1145
1146 static proto_item *dissect_datetime_ie(tvbuff_t *tvb, guint32 offset, proto_tree *ies_tree)
1147 {
1148   struct tm tm;
1149   guint32 ie_val;
1150   nstime_t datetime;
1151
1152   proto_tree_add_item (ies_tree, hf_iax2_ies[IAX_IE_DATETIME], tvb, offset + 2, 4, ENC_BIG_ENDIAN);
1153   ie_val = tvb_get_ntohl(tvb, offset+2);
1154
1155   /* who's crazy idea for a time encoding was this? */
1156   tm.tm_sec  = (ie_val & 0x1f) << 1;
1157   tm.tm_min  = (ie_val>>5) & 0x3f;
1158   tm.tm_hour = (ie_val>>11) & 0x1f;
1159   tm.tm_mday = (ie_val>>16) & 0x1f;
1160   tm.tm_mon  = ((ie_val>>21) & 0xf) - 1;
1161   tm.tm_year = ((ie_val>>25) & 0x7f) + 100;
1162   tm.tm_isdst= -1; /* there's no info on whether DST was in force; assume it's
1163                     * the same as currently */
1164
1165   datetime.secs = mktime(&tm);
1166   datetime.nsecs = 0;
1167   return proto_tree_add_time (ies_tree, hf_iax2_ie_datetime, tvb, offset+2, 4, &datetime);
1168 }
1169
1170
1171 /* dissect the information elements in an IAX frame. Returns the updated offset */
1172 static guint32 dissect_ies (tvbuff_t * tvb, guint32 offset,
1173                             proto_tree * iax_tree,
1174                             iax2_ie_data *ie_data)
1175 {
1176   DISSECTOR_ASSERT(ie_data);
1177
1178   while (offset < tvb_reported_length (tvb)) {
1179
1180     int ies_type = tvb_get_guint8(tvb, offset);
1181     int ies_len = tvb_get_guint8(tvb, offset + 1);
1182     guint16 apparent_addr_family;
1183
1184     /* do non-tree-dependent stuff first */
1185     switch(ies_type) {
1186       case IAX_IE_DATAFORMAT:
1187         if (ies_len != 4) THROW(ReportedBoundsError);
1188         ie_data -> dataformat = tvb_get_ntohl(tvb, offset+2);
1189         break;
1190
1191       case IAX_IE_CALLED_NUMBER:
1192         iax2_info->calledParty = g_strdup(tvb_format_text(tvb, offset+2, ies_len));
1193         break;
1194       case IAX_IE_CALLING_NUMBER:
1195         iax2_info->callingParty = g_strdup(tvb_format_text(tvb, offset+2, ies_len));
1196         break;
1197
1198       case IAX_IE_APPARENT_ADDR:
1199         /* The IAX2 I-D says that the "apparent address" structure
1200            "is the same as the linux struct sockaddr_in", without
1201            bothering to note that the address family field is in
1202            *host* byte order in that structure (the I-D seems to be
1203            assuming that "everything is a Vax^Wx86 or x86-64" with
1204            the address family field being little-endian).
1205
1206            This means the address family values are the Linux
1207            address family values. */
1208         apparent_addr_family = tvb_get_letohs(tvb, offset+2);
1209         switch( apparent_addr_family ) {
1210           case LINUX_AF_INET:
1211             /* IAX is always over UDP */
1212             ie_data->peer_ptype = PT_UDP;
1213             ie_data->peer_port = tvb_get_ntohs(tvb, offset+4);
1214
1215             /* the ip address is big-endian, but then so is peer_address.data */
1216             SET_ADDRESS(&ie_data->peer_address,AT_IPv4,4,tvb_get_ptr(tvb,offset+6,4));
1217             break;
1218
1219           default:
1220             g_warning("Not supported in IAX dissector: peer address family of %u", apparent_addr_family);
1221             break;
1222         }
1223         break;
1224     }
1225
1226
1227     /* the rest of this stuff only needs doing if we have an iax_tree */
1228
1229     if( iax_tree && ies_type < NUM_HF_IAX2_IES ) {
1230       proto_item *ti, *ie_item = NULL;
1231       proto_tree *ies_tree;
1232       int ie_hf = hf_iax2_ies[ies_type];
1233
1234       ti = proto_tree_add_text(iax_tree, tvb, offset, ies_len+2, " " );
1235
1236       ies_tree = proto_item_add_subtree(ti, ett_iax2_ie);
1237
1238       proto_tree_add_text(ies_tree, tvb, offset, 1, "IE id: %s (0x%02X)",
1239                           val_to_str_const(ies_type, iax_ies_type, "Unknown"),
1240                           ies_type);
1241
1242       proto_tree_add_text(ies_tree, tvb, offset+1, 1, "Length: %u",ies_len);
1243
1244
1245       /* hf_iax2_ies[] is an array, indexed by IE number, of header-fields, one
1246          per IE. Apart from a couple of special cases which require more
1247          complex decoding, we can just look up an entry from the array, and add
1248          the relevant item, although the encoding value used depends on the
1249          type of the item.
1250       */
1251
1252       switch (ies_type) {
1253         case IAX_IE_DATETIME:
1254           ie_item = dissect_datetime_ie(tvb,offset,ies_tree);
1255           break;
1256
1257
1258         case IAX_IE_CAPABILITY:
1259         {
1260           proto_tree *codec_tree;
1261
1262           if (ies_len != 4) THROW(ReportedBoundsError);
1263
1264           ie_item =
1265             proto_tree_add_item (ies_tree, ie_hf,
1266                                  tvb, offset + 2, ies_len, ENC_BIG_ENDIAN);
1267           codec_tree =
1268             proto_item_add_subtree (ie_item, ett_iax2_codecs);
1269
1270           proto_tree_add_item(codec_tree, hf_iax2_cap_g723_1, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1271           proto_tree_add_item(codec_tree, hf_iax2_cap_gsm, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1272           proto_tree_add_item(codec_tree, hf_iax2_cap_ulaw, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1273           proto_tree_add_item(codec_tree, hf_iax2_cap_alaw, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1274           proto_tree_add_item(codec_tree, hf_iax2_cap_g726_aal2, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1275           proto_tree_add_item(codec_tree, hf_iax2_cap_adpcm, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1276           proto_tree_add_item(codec_tree, hf_iax2_cap_slinear, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1277           proto_tree_add_item(codec_tree, hf_iax2_cap_lpc10, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1278           proto_tree_add_item(codec_tree, hf_iax2_cap_g729a, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1279           proto_tree_add_item(codec_tree, hf_iax2_cap_speex, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1280           proto_tree_add_item(codec_tree, hf_iax2_cap_ilbc, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1281           proto_tree_add_item(codec_tree, hf_iax2_cap_g726, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1282           proto_tree_add_item(codec_tree, hf_iax2_cap_g722, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1283           proto_tree_add_item(codec_tree, hf_iax2_cap_siren7, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1284           proto_tree_add_item(codec_tree, hf_iax2_cap_siren14, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1285           proto_tree_add_item(codec_tree, hf_iax2_cap_slinear16, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1286           proto_tree_add_item(codec_tree, hf_iax2_cap_jpeg, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1287           proto_tree_add_item(codec_tree, hf_iax2_cap_png, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1288           proto_tree_add_item(codec_tree, hf_iax2_cap_h261, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1289           proto_tree_add_item(codec_tree, hf_iax2_cap_h263, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1290           proto_tree_add_item(codec_tree, hf_iax2_cap_h263_plus, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1291           proto_tree_add_item(codec_tree, hf_iax2_cap_h264, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1292           proto_tree_add_item(codec_tree, hf_iax2_cap_mpeg4, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN );
1293           break;
1294         }
1295
1296         case IAX_IE_APPARENT_ADDR:
1297         {
1298           proto_tree *sockaddr_tree = NULL;
1299
1300           ie_item = proto_tree_add_text(ies_tree, tvb, offset + 2, 16, "Apparent Address");
1301           sockaddr_tree = proto_item_add_subtree(ie_item, ett_iax2_ies_apparent_addr);
1302
1303           /* The IAX2 I-D says that the "apparent address" structure
1304              "is the same as the linux struct sockaddr_in", without
1305              bothering to note that the address family field is in
1306              *host* byte order in that structure (the I-D seems to be
1307              assuming that "everything is a Vax^Wx86 or x86-64" with
1308              the address family field being little-endian).
1309
1310              This means the address family values are the Linux
1311              address family values. */
1312           apparent_addr_family = tvb_get_letohs(tvb, offset+2);
1313           proto_tree_add_uint(sockaddr_tree, hf_IAX_IE_APPARENTADDR_SINFAMILY, tvb, offset + 2, 2, apparent_addr_family);
1314
1315           switch(  apparent_addr_family ) {
1316             case LINUX_AF_INET:
1317             {
1318               guint32 addr;
1319               proto_tree_add_uint(sockaddr_tree, hf_IAX_IE_APPARENTADDR_SINPORT, tvb, offset + 4, 2, ie_data->peer_port);
1320               memcpy(&addr, ie_data->peer_address.data, 4);
1321               proto_tree_add_ipv4(sockaddr_tree, hf_IAX_IE_APPARENTADDR_SINADDR, tvb, offset + 6, 4, addr);
1322               break;
1323             }
1324           }
1325           break;
1326         }
1327
1328         default:
1329           if( ie_hf != -1 ) {
1330             /* throw an error if the IE isn't the expected length */
1331             enum ftenum type = proto_registrar_get_nth(ie_hf)->type;
1332             gint explen = ftype_length(type);
1333             if(explen != 0 && ies_len != explen)
1334               THROW(ReportedBoundsError);
1335             switch (type) {
1336             case FT_UINT8:
1337             case FT_UINT16:
1338             case FT_UINT24:
1339             case FT_UINT32:
1340             case FT_UINT64:
1341             case FT_INT8:
1342             case FT_INT16:
1343             case FT_INT24:
1344             case FT_INT32:
1345             case FT_INT64:
1346             case FT_BOOLEAN:
1347             case FT_IPv4:
1348                 ie_item = proto_tree_add_item(ies_tree, ie_hf, tvb, offset + 2, ies_len, ENC_BIG_ENDIAN);
1349                 break;
1350
1351             case FT_BYTES:
1352             case FT_NONE:
1353                 ie_item = proto_tree_add_item(ies_tree, ie_hf, tvb, offset + 2, ies_len, ENC_NA);
1354                 break;
1355
1356             case FT_STRING:
1357             case FT_STRINGZ:
1358                 ie_item = proto_tree_add_item(ies_tree, ie_hf, tvb, offset + 2, ies_len, ENC_UTF_8|ENC_NA);
1359                 break;
1360
1361             default:
1362                 DISSECTOR_ASSERT_NOT_REACHED();
1363                 break;
1364             }
1365           } else {
1366             /* we don't understand this ie: add a generic one */
1367             guint32 value;
1368             const guint8 *ptr;
1369             const gchar *ie_name = val_to_str_const(ies_type, iax_ies_type, "Unknown");
1370
1371             switch(ies_len) {
1372               case 1:
1373                 value = tvb_get_guint8(tvb, offset + 2);
1374                 ie_item =
1375                   proto_tree_add_uint_format(ies_tree, hf_IAX_IE_UNKNOWN_BYTE,
1376                                              tvb, offset+2, 1, value,
1377                                              "%s: %#02x", ie_name, value );
1378                 break;
1379
1380               case 2:
1381                 value = tvb_get_ntohs(tvb, offset + 2);
1382                 ie_item =
1383                   proto_tree_add_uint_format(ies_tree, hf_IAX_IE_UNKNOWN_I16,
1384                                              tvb, offset+2, 2, value,
1385                                              "%s: %#04x", ie_name, value );
1386                 break;
1387
1388               case 4:
1389                 value = tvb_get_ntohl(tvb, offset + 2);
1390                 ie_item =
1391                   proto_tree_add_uint_format(ies_tree, hf_IAX_IE_UNKNOWN_I32,
1392                                              tvb, offset+2, 4, value,
1393                                              "%s: %#08x", ie_name, value );
1394                 break;
1395
1396               default:
1397                 ptr = tvb_get_ephemeral_string(tvb, offset + 2, ies_len);
1398                 ie_item =
1399                   proto_tree_add_string_format(ies_tree, hf_IAX_IE_UNKNOWN_BYTES,
1400                                                tvb, offset+2, ies_len, ptr,
1401                                                "%s: %s", ie_name, ptr );
1402                 break;
1403             }
1404           }
1405           break;
1406       }
1407
1408       /* by now, we *really* ought to have added an item */
1409       DISSECTOR_ASSERT(ie_item != NULL);
1410
1411       /* Retrieve the text from the item we added, and append it to the main IE
1412        * item */
1413       if(!PROTO_ITEM_IS_HIDDEN(ti)) {
1414         field_info *ie_finfo = PITEM_FINFO(ie_item);
1415
1416         /* if the representation of the item has already been set, use that;
1417            else we have to allocate a block to put the text into */
1418         if( ie_finfo && ie_finfo->rep != NULL )
1419           proto_item_set_text(ti, "Information Element: %s",
1420                               ie_finfo->rep->representation);
1421         else {
1422           guint8 *ie_val = NULL;
1423           ie_val = ep_alloc(ITEM_LABEL_LENGTH);
1424           proto_item_fill_label(ie_finfo, ie_val);
1425           proto_item_set_text(ti, "Information Element: %s",
1426                               ie_val);
1427         }
1428       }
1429     }
1430
1431     offset += ies_len + 2;
1432   }
1433   return offset;
1434 }
1435
1436 static guint32 uncompress_subclass(guint8 csub)
1437 {
1438   /* If the SC_LOG flag is set, return 2^csub otherwise csub */
1439   if (csub & 0x80) {
1440     /* special case for 'compressed' -1 */
1441     if (csub == 0xff)
1442       return (guint32)-1;
1443     else
1444       return 1 << (csub & 0x1F);
1445   }
1446   else
1447     return (guint32)csub;
1448 }
1449
1450 /* returns the new offset */
1451 static guint32 dissect_iax2_command(tvbuff_t * tvb, guint32 offset,
1452                                     packet_info * pinfo, proto_tree *tree,
1453                                     iax_packet_data *iax_packet)
1454 {
1455   guint8 csub = tvb_get_guint8(tvb, offset);
1456   guint8 address_data[MAX_ADDRESS];
1457   iax2_ie_data ie_data;
1458   iax_call_data *iax_call;
1459
1460   ie_data.peer_address.type = AT_NONE;
1461   ie_data.peer_address.len = 0;
1462   ie_data.peer_address.data = address_data;
1463   ie_data.peer_ptype = 0;
1464   ie_data.peer_port = 0;
1465   ie_data.peer_callno = 0;
1466   ie_data.dataformat = (guint32)-1;
1467   iax_call = iax_packet -> call_data;
1468
1469   /* add the subclass */
1470   proto_tree_add_uint (tree, hf_iax2_iax_csub, tvb, offset, 1, csub);
1471   offset++;
1472
1473   if (check_col (pinfo->cinfo, COL_INFO))
1474     col_append_fstr (pinfo->cinfo, COL_INFO, " %s",
1475                      val_to_str (csub, iax_iax_subclasses, "unknown (0x%02x)"));
1476
1477   if (offset >= tvb_reported_length (tvb))
1478     return offset;
1479
1480   offset = dissect_ies(tvb, offset, tree, &ie_data);
1481
1482   /* if this is a data call, set up a subdissector for the circuit */
1483   if(iax_call && ie_data.dataformat != (guint32)-1 && iax_call -> subdissector == NULL) {
1484     iax_call -> subdissector = dissector_get_uint_handle(iax2_dataformat_dissector_table, ie_data.dataformat );
1485     iax_call -> dataformat = ie_data.dataformat;
1486   }
1487
1488   /* if this is a transfer request, record it in the call data */
1489   if( csub == IAX_COMMAND_TXREQ && iax_packet -> first_time ) {
1490     if( ie_data.peer_address.type != AT_NONE && ie_data.peer_callno != 0 ) {
1491       guint tx_circuit = iax_circuit_lookup(&ie_data.peer_address,
1492                                             ie_data.peer_ptype,
1493                                             ie_data.peer_port,
1494                                             ie_data.peer_callno);
1495
1496 #if 0
1497       g_debug("found transfer request for call %u->%u, to new id %u",
1498                 iax_call->forward_circuit_ids[0],
1499                 iax_call->reverse_circuit_ids[0],
1500                 tx_circuit);
1501 #endif
1502
1503       iax2_new_circuit_for_call(tx_circuit,pinfo->fd->num,iax_call,iax_packet->reversed);
1504     }
1505   }
1506
1507   return offset;
1508 }
1509
1510 static void iax2_add_ts_fields(packet_info * pinfo, proto_tree * iax2_tree, iax_packet_data *iax_packet, guint16 shortts)
1511 {
1512   guint32 longts = shortts;
1513   nstime_t ts;
1514   proto_item *item;
1515
1516   if(iax_packet->call_data == NULL) {
1517     /* no call info for this frame; perhaps we missed the NEW packet */
1518     return;
1519   }
1520
1521   if(iax_packet->abstime.secs == -1) {
1522     time_t start_secs = iax_packet->call_data->start_time.secs;
1523     gint32 abs_secs = (gint32) (start_secs + longts/1000);
1524
1525     /* deal with short timestamps by assuming that packets are never more than
1526      * 16 seconds late */
1527     while(abs_secs < pinfo->fd->abs_ts.secs - 16) {
1528       longts += 32768;
1529       abs_secs = (gint32) (start_secs + longts/1000);
1530     }
1531
1532     iax_packet->abstime.secs=abs_secs;
1533     iax_packet->abstime.nsecs=iax_packet->call_data->start_time.nsecs + (longts % 1000) * 1000000;
1534     if(iax_packet->abstime.nsecs >= 1000000000) {
1535       iax_packet->abstime.nsecs -= 1000000000;
1536       iax_packet->abstime.secs ++;
1537     }
1538   }
1539   iax2_info->timestamp = longts;
1540
1541   if (iax2_tree) {
1542     item = proto_tree_add_time(iax2_tree, hf_iax2_absts, NULL, 0, 0, &iax_packet->abstime);
1543     PROTO_ITEM_SET_GENERATED(item);
1544
1545     ts  = pinfo->fd->abs_ts;
1546     nstime_delta(&ts, &ts, &iax_packet->abstime);
1547
1548     item = proto_tree_add_time(iax2_tree, hf_iax2_lateness, NULL, 0, 0, &ts);
1549     PROTO_ITEM_SET_GENERATED(item);
1550   }
1551 }
1552
1553 /* returns the new offset */
1554 static guint32
1555 dissect_fullpacket (tvbuff_t * tvb, guint32 offset,
1556                     guint16 scallno,
1557                     packet_info * pinfo, proto_tree * iax2_tree,
1558                     proto_tree * main_tree)
1559 {
1560   guint16 dcallno;
1561   guint32 ts;
1562   guint8 type;
1563   guint8 csub;
1564   guint32 codec;
1565
1566   proto_tree *packet_type_tree = NULL;
1567   iax_call_data *iax_call;
1568   iax_packet_data *iax_packet;
1569   gboolean reversed;
1570   gboolean rtp_marker;
1571
1572   /*
1573    * remove the top bit for retransmission detection
1574    */
1575   dcallno = tvb_get_ntohs(tvb, offset) & 0x7FFF;
1576   ts = tvb_get_ntohl(tvb, offset+2);
1577   type = tvb_get_guint8(tvb, offset + 8);
1578   csub = tvb_get_guint8(tvb, offset + 9);
1579   iax2_info->ftype = type;
1580   iax2_info->csub = csub;
1581   iax2_info->scallno = scallno;
1582   iax2_info->dcallno = dcallno;
1583
1584   /* see if we've seen this packet before */
1585   iax_packet = (iax_packet_data *)p_get_proto_data(pinfo->fd,proto_iax2);
1586   if( !iax_packet ) {
1587     /* if not, find or create an iax_call info structure for this IAX session. */
1588
1589     if( type == AST_FRAME_IAX && csub == IAX_COMMAND_NEW ) {
1590       /* NEW packets start a new call */
1591       iax_call = iax_new_call(pinfo,scallno);
1592       reversed = FALSE;
1593     } else {
1594       iax_call = iax_lookup_call(pinfo, scallno, dcallno,
1595                                  &reversed);
1596     }
1597
1598     iax_packet = iax_new_packet_data(iax_call, reversed);
1599     p_add_proto_data(pinfo->fd,proto_iax2,iax_packet);
1600   } else {
1601     iax_call = iax_packet->call_data;
1602     reversed = iax_packet->reversed;
1603   }
1604
1605   iax2_populate_pinfo_from_packet_data(pinfo, iax_packet);
1606
1607   if( iax2_tree ) {
1608       proto_item *packet_type_base;
1609
1610       proto_tree_add_item (iax2_tree, hf_iax2_dcallno, tvb, offset, 2, ENC_BIG_ENDIAN );
1611
1612       proto_tree_add_item(iax2_tree, hf_iax2_retransmission, tvb, offset, 2, ENC_BIG_ENDIAN );
1613
1614       if( iax_call ) {
1615         proto_item *item =
1616           proto_tree_add_uint (iax2_tree, hf_iax2_callno, tvb, 0, 4,
1617                              iax_call->forward_circuit_ids[0] );
1618         PROTO_ITEM_SET_GENERATED(item);
1619       }
1620
1621       proto_tree_add_uint (iax2_tree, hf_iax2_ts, tvb, offset+2, 4, ts);
1622       iax2_add_ts_fields(pinfo, iax2_tree, iax_packet, (guint16)ts);
1623
1624       proto_tree_add_item (iax2_tree, hf_iax2_oseqno, tvb, offset+6, 1,
1625                            ENC_BIG_ENDIAN);
1626
1627       proto_tree_add_item (iax2_tree, hf_iax2_iseqno, tvb, offset+7, 1,
1628                            ENC_BIG_ENDIAN);
1629       packet_type_base = proto_tree_add_uint (iax2_tree, hf_iax2_type, tvb,
1630                                               offset+8, 1, type);
1631
1632       /* add the type-specific subtree */
1633       packet_type_tree = proto_item_add_subtree (packet_type_base, ett_iax2_type);
1634   } else {
1635     iax2_add_ts_fields(pinfo, iax2_tree, iax_packet, (guint16)ts);
1636   }
1637
1638
1639   /* add frame type to info line */
1640   if (check_col (pinfo->cinfo, COL_INFO)) {
1641     col_add_fstr (pinfo->cinfo, COL_INFO, "%s, source call# %d, timestamp %ums",
1642                   val_to_str (type, iax_frame_types, "Unknown (0x%02x)"),
1643                   scallno, ts);
1644   }
1645   iax2_info->messageName = val_to_str (type, iax_frame_types, "Unknown (0x%02x)");
1646
1647   switch( type ) {
1648   case AST_FRAME_IAX:
1649     offset=dissect_iax2_command(tvb,offset+9,pinfo,packet_type_tree,iax_packet);
1650     iax2_info->messageName = val_to_str (csub, iax_iax_subclasses, "unknown (0x%02x)");
1651     iax2_info->callState = csub;
1652     break;
1653
1654   case AST_FRAME_DTMF_BEGIN:
1655   case AST_FRAME_DTMF_END:
1656     proto_tree_add_item (packet_type_tree, hf_iax2_dtmf_csub, tvb, offset+9, 1, ENC_ASCII|ENC_NA);
1657     offset += 10;
1658
1659     if (check_col (pinfo->cinfo, COL_INFO))
1660       col_append_fstr (pinfo->cinfo, COL_INFO, " digit %c", csub );
1661     break;
1662
1663   case AST_FRAME_CONTROL:
1664     /* add the subclass */
1665     proto_tree_add_uint (packet_type_tree, hf_iax2_cmd_csub, tvb,
1666                          offset+9, 1, csub);
1667     offset += 10;
1668
1669     if (check_col (pinfo->cinfo, COL_INFO))
1670       col_append_fstr (pinfo->cinfo, COL_INFO, " %s",
1671                        val_to_str (csub, iax_cmd_subclasses, "unknown (0x%02x)"));
1672     iax2_info->messageName = val_to_str (csub, iax_cmd_subclasses, "unknown (0x%02x)");
1673     if (csub < NUM_TAP_CMD_VOIP_STATES) iax2_info->callState = tap_cmd_voip_state[csub];
1674     break;
1675
1676   case AST_FRAME_VOICE:
1677     /* add the codec */
1678     iax_packet -> codec = codec = uncompress_subclass(csub);
1679
1680     if( packet_type_tree ) {
1681       proto_item *item;
1682       proto_tree_add_item (packet_type_tree, hf_iax2_voice_csub, tvb, offset+9, 1, ENC_BIG_ENDIAN);
1683       item = proto_tree_add_uint (packet_type_tree, hf_iax2_voice_codec, tvb, offset+9, 1, codec);
1684       PROTO_ITEM_SET_GENERATED(item);
1685     }
1686
1687     offset += 10;
1688
1689     if( iax_call ) {
1690       if( reversed ) {
1691         iax_call->dst_codec = codec;
1692       } else {
1693         iax_call->src_codec = codec;
1694       }
1695     }
1696
1697     dissect_payload(tvb, offset, pinfo, iax2_tree, main_tree, ts, FALSE,iax_packet);
1698     break;
1699
1700   case AST_FRAME_VIDEO:
1701     /* bit 6 of the csub is used to represent the rtp 'marker' bit */
1702     rtp_marker = csub & 0x40 ? TRUE:FALSE;
1703     iax_packet -> codec = codec = uncompress_subclass((guint8) (csub & ~40));
1704
1705     if( packet_type_tree ) {
1706       proto_item *item;
1707       proto_tree_add_item (packet_type_tree, hf_iax2_video_csub, tvb, offset+9, 1, ENC_BIG_ENDIAN);
1708       proto_tree_add_item (packet_type_tree, hf_iax2_marker, tvb, offset+9, 1, ENC_BIG_ENDIAN);
1709       item = proto_tree_add_uint (packet_type_tree, hf_iax2_video_codec, tvb, offset+9, 1, codec);
1710       PROTO_ITEM_SET_GENERATED(item);
1711     }
1712
1713     offset += 10;
1714
1715     if( iax_call && iax_packet -> first_time ) {
1716       if( reversed ) {
1717         iax_call->dst_vformat = codec;
1718       } else {
1719         iax_call->src_vformat = codec;
1720       }
1721     }
1722
1723     if( rtp_marker )
1724       col_append_str (pinfo->cinfo, COL_INFO, ", Mark" );
1725
1726
1727     dissect_payload(tvb, offset, pinfo, iax2_tree, main_tree, ts, TRUE, iax_packet);
1728     break;
1729
1730   case AST_FRAME_MODEM:
1731     proto_tree_add_item (packet_type_tree, hf_iax2_modem_csub, tvb, offset+9, 1, ENC_BIG_ENDIAN);
1732     offset += 10;
1733
1734     if (check_col (pinfo->cinfo, COL_INFO))
1735       col_append_fstr (pinfo->cinfo, COL_INFO, " %s",
1736                        val_to_str (csub, iax_modem_subclasses, "unknown (0x%02x)"));
1737     break;
1738
1739   case AST_FRAME_HTML:
1740   case AST_FRAME_CNG:
1741   default:
1742     proto_tree_add_uint (packet_type_tree, hf_iax2_csub, tvb, offset+9,
1743                          1, csub);
1744     offset += 10;
1745
1746     if (check_col (pinfo->cinfo, COL_INFO))
1747       col_append_fstr (pinfo->cinfo, COL_INFO, " subclass %d", csub );
1748     break;
1749   }
1750
1751   /* next time we come to parse this packet, don't propagate the codec into the
1752    * call_data */
1753   iax_packet->first_time = FALSE;
1754
1755   return offset;
1756 }
1757
1758 static iax_packet_data *iax2_get_packet_data_for_minipacket(packet_info * pinfo,
1759                                                             guint16 scallno,
1760                                                             gboolean video)
1761 {
1762   /* see if we've seen this packet before */
1763   iax_packet_data *p = (iax_packet_data *)p_get_proto_data(pinfo->fd,proto_iax2);
1764
1765   if( !p ) {
1766     /* if not, find or create an iax_call info structure for this IAX session. */
1767     gboolean reversed;
1768     iax_call_data *iax_call;
1769
1770     iax_call = iax_lookup_call(pinfo, scallno, 0, &reversed);
1771
1772     p = iax_new_packet_data(iax_call,reversed);
1773     p_add_proto_data(pinfo->fd,proto_iax2,p);
1774
1775     /* set the codec for this frame to be whatever the last full frame used */
1776     if( iax_call ) {
1777      if( video )
1778         p->codec = reversed ? iax_call -> dst_vformat : iax_call -> src_vformat;
1779       else
1780         p->codec = reversed ? iax_call -> dst_codec : iax_call -> src_codec;
1781     }
1782   }
1783
1784   iax2_populate_pinfo_from_packet_data(pinfo, p);
1785   return p;
1786 }
1787
1788
1789 static guint32 dissect_minivideopacket (tvbuff_t * tvb, guint32 offset,
1790                                         guint16 scallno, packet_info * pinfo,
1791                                         proto_tree * iax2_tree, proto_tree *main_tree)
1792 {
1793   guint32 ts;
1794   iax_packet_data *iax_packet;
1795   gboolean rtp_marker;
1796   proto_item *item;
1797
1798   ts = tvb_get_ntohs(tvb, offset);
1799
1800   /* bit 15 of the ts is used to represent the rtp 'marker' bit */
1801   rtp_marker = ts & 0x8000 ? TRUE:FALSE;
1802   ts &= ~0x8000;
1803
1804   iax_packet = iax2_get_packet_data_for_minipacket(pinfo, scallno, TRUE);
1805
1806   if( iax2_tree ) {
1807     if( iax_packet->call_data ) {
1808       item =
1809         proto_tree_add_uint (iax2_tree, hf_iax2_callno, tvb, 0, 4,
1810                                     iax_packet->call_data->forward_circuit_ids[0] );
1811       PROTO_ITEM_SET_GENERATED(item);
1812     }
1813
1814     proto_tree_add_item (iax2_tree, hf_iax2_minividts, tvb, offset, 2, ENC_BIG_ENDIAN);
1815     iax2_add_ts_fields(pinfo, iax2_tree, iax_packet, (guint16)ts);
1816     proto_tree_add_item (iax2_tree, hf_iax2_minividmarker, tvb, offset, 2, ENC_BIG_ENDIAN);
1817   } else {
1818     iax2_add_ts_fields(pinfo, iax2_tree, iax_packet, (guint16)ts);
1819   }
1820
1821   offset += 2;
1822
1823   if (check_col (pinfo->cinfo, COL_INFO))
1824       col_add_fstr (pinfo->cinfo, COL_INFO,
1825                     "Mini video packet, source call# %d, timestamp %ums%s",
1826                     scallno, ts, rtp_marker?", Mark":"");
1827
1828
1829   dissect_payload(tvb, offset, pinfo, iax2_tree, main_tree, ts, TRUE, iax_packet);
1830
1831   /* next time we come to parse this packet, don't propagate the codec into the
1832    * call_data */
1833   iax_packet->first_time = FALSE;
1834
1835   return offset;
1836 }
1837
1838 static guint32
1839 dissect_minipacket (tvbuff_t * tvb, guint32 offset, guint16 scallno, packet_info * pinfo, proto_tree * iax2_tree,
1840                     proto_tree *main_tree)
1841 {
1842   guint32 ts;
1843   iax_packet_data *iax_packet;
1844   proto_item *item;
1845
1846   ts = tvb_get_ntohs(tvb, offset);
1847
1848   iax_packet = iax2_get_packet_data_for_minipacket(pinfo, scallno, FALSE);
1849
1850   if( iax2_tree ) {
1851     if( iax_packet->call_data ) {
1852       item = proto_tree_add_uint (iax2_tree, hf_iax2_callno, tvb, 0, 4,
1853                                   iax_packet->call_data->forward_circuit_ids[0] );
1854       PROTO_ITEM_SET_GENERATED(item);
1855     }
1856
1857     proto_tree_add_uint (iax2_tree, hf_iax2_minits, tvb, offset, 2, ts);
1858     iax2_add_ts_fields(pinfo, iax2_tree, iax_packet,(guint16)ts);
1859   } else {
1860     iax2_add_ts_fields(pinfo, iax2_tree, iax_packet, (guint16)ts);
1861   }
1862
1863
1864   offset += 2;
1865
1866   if (check_col (pinfo->cinfo, COL_INFO))
1867       col_add_fstr (pinfo->cinfo, COL_INFO,
1868                     "Mini packet, source call# %d, timestamp %ums",
1869                     scallno, ts);
1870
1871
1872   /* XXX fix the timestamp logic */
1873   dissect_payload(tvb, offset, pinfo, iax2_tree, main_tree, ts, FALSE, iax_packet);
1874
1875
1876   /* next time we come to parse this packet, don't propagate the codec into the
1877    * call_data */
1878   iax_packet->first_time = FALSE;
1879
1880   return offset;
1881 }
1882
1883
1884 static guint32 dissect_trunkcall_ts (tvbuff_t * tvb, guint32 offset, proto_tree * iax2_tree, guint16 * scallno)
1885 {
1886   proto_item *call_item;
1887   proto_tree *call_tree;
1888   guint16 datalen, rlen, ts;
1889   /*
1890    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1891    |     Data Length (in octets)   |R|     Source Call Number      |
1892    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1893    |           time-stamp          |                               |
1894    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+                               |
1895    |                                       Data                    |
1896    :                                                               :
1897    |                                                               |
1898    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1899    */
1900   datalen = tvb_get_ntohs(tvb, offset);
1901   *scallno = tvb_get_ntohs(tvb, offset + 2);
1902   ts = tvb_get_ntohs(tvb, offset + 4);
1903
1904   rlen = MIN(tvb_length(tvb) - offset - 6, datalen);
1905
1906   if( iax2_tree ) {
1907     call_item = proto_tree_add_text(iax2_tree, tvb, offset, rlen + 6, "Trunk call from %u, ts: %u", *scallno, ts);
1908     call_tree = proto_item_add_subtree(call_item, ett_iax2_trunk_call);
1909
1910     proto_tree_add_item(call_tree, hf_iax2_trunk_call_len, tvb, offset, 2, ENC_BIG_ENDIAN);
1911     proto_tree_add_item(call_tree, hf_iax2_trunk_call_scallno, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
1912     proto_tree_add_item(call_tree, hf_iax2_trunk_call_ts, tvb, offset + 4, 2, ENC_BIG_ENDIAN);
1913     proto_tree_add_item(call_tree, hf_iax2_trunk_call_data, tvb, offset + 6, rlen, ENC_NA);
1914   }
1915   offset += 6 + rlen;
1916
1917   return offset;
1918 }
1919
1920 static guint32 dissect_trunkcall_nots (tvbuff_t * tvb, guint32 offset, proto_tree * iax2_tree, guint16 * scallno)
1921 {
1922   proto_item *call_item;
1923   proto_tree *call_tree;
1924   guint16 datalen, rlen;
1925   /*
1926    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1927    |R|      Source Call Number     |     Data Length (in octets)   |
1928    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1929    |                                                               |
1930    :                             Data                              :
1931    |                                                               |
1932    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1933    */
1934   *scallno = tvb_get_ntohs(tvb, offset);
1935   datalen = tvb_get_ntohs(tvb, offset + 2);
1936
1937   rlen = MIN(tvb_length(tvb) - offset - 4, datalen);
1938
1939   if( iax2_tree ) {
1940     call_item = proto_tree_add_text(iax2_tree, tvb, offset, rlen + 6, "Trunk call from %u", *scallno);
1941     call_tree = proto_item_add_subtree(call_item, ett_iax2_trunk_call);
1942
1943     proto_tree_add_item(call_tree, hf_iax2_trunk_call_scallno, tvb, offset, 2, ENC_BIG_ENDIAN);
1944     proto_tree_add_item(call_tree, hf_iax2_trunk_call_len, tvb, offset + 2, 2, ENC_BIG_ENDIAN);
1945     proto_tree_add_item(call_tree, hf_iax2_trunk_call_data, tvb, offset + 4, rlen, ENC_NA);
1946   }
1947   offset += 4 + rlen;
1948
1949   return offset;
1950 }
1951
1952 typedef struct _call_list {
1953   guint16 scallno;
1954   struct _call_list *next;
1955 } call_list;
1956
1957 static call_list *call_list_append(call_list *list, guint16 scallno)
1958 {
1959   call_list *node = ep_alloc0(sizeof(call_list));
1960
1961   node->scallno = scallno;
1962
1963   if (list) {
1964     call_list *cur = list;
1965     while (cur->next) {
1966       cur = cur->next;
1967     }
1968     cur->next = node;
1969     return list;
1970   } else {
1971     return node;
1972   }
1973 }
1974
1975 static gboolean call_list_find(call_list *list, guint16 scallno)
1976 {
1977   for (; list; list = list->next) {
1978     if (list->scallno == scallno) {
1979       return TRUE;
1980     }
1981   }
1982   return FALSE;
1983 }
1984
1985 static guint call_list_length(call_list *list)
1986 {
1987   guint count = 0;
1988   for (; list; list = list->next) {
1989     count++;
1990   }
1991   return count;
1992 }
1993
1994 static guint32 dissect_trunkpacket (tvbuff_t * tvb, guint32 offset,
1995                                         guint16 scallno _U_, packet_info * pinfo,
1996                                         proto_tree * iax2_tree, proto_tree *main_tree _U_)
1997 {
1998   guint8 cmddata, trunkts;
1999   guint nframes = 0, ncalls = 0;
2000   /*iax_packet_data *iax_packet;*/
2001   proto_item *cd, *nc = NULL;
2002   proto_tree *field_tree = NULL;
2003   call_list *calls = NULL;
2004
2005   cmddata = tvb_get_guint8(tvb, offset + 1);
2006   trunkts = cmddata & IAX2_TRUNK_TS;
2007
2008   /* 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1   */
2009   /* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ */
2010   /* |F|         Meta Indicator      |V|Meta Command | Cmd Data (0)  | */
2011   /* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ */
2012   /* |                            time-stamp                         | */
2013   /* +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ */
2014
2015   if( iax2_tree ) {
2016     /* Meta Command */
2017     proto_tree_add_item(iax2_tree, hf_iax2_trunk_metacmd, tvb, offset, 1, ENC_BIG_ENDIAN);
2018
2019     /* Command data */
2020     cd = proto_tree_add_uint(iax2_tree, hf_iax2_trunk_cmddata, tvb, offset + 1, 1, cmddata);
2021     field_tree = proto_item_add_subtree(cd, ett_iax2_trunk_cmddata);
2022     if (trunkts)
2023       proto_item_append_text(cd, " (trunk timestamps)");
2024
2025     /* CD -> Trunk timestamp */
2026     proto_tree_add_boolean(field_tree, hf_iax2_trunk_cmddata_ts, tvb, offset + 1, 1, cmddata);
2027
2028     /* Timestamp */
2029     proto_tree_add_item(iax2_tree, hf_iax2_trunk_ts, tvb, offset + 2, 4, ENC_BIG_ENDIAN);
2030   }
2031
2032   offset += 6;
2033
2034   if( trunkts ) {
2035     /* Trunk calls with timestamp */
2036     while(tvb_length_remaining(tvb, offset) >= 6) {
2037       guint16 scallno;
2038       offset = dissect_trunkcall_ts (tvb, offset, iax2_tree, &scallno);
2039       if (!call_list_find (calls, scallno)) {
2040         calls = call_list_append (calls, scallno);
2041       }
2042       nframes++;
2043         }
2044   }
2045   else {
2046     /* Trunk calls without timestamp */
2047     while(tvb_length_remaining(tvb, offset) >= 4) {
2048       guint16 scallno;
2049       offset = dissect_trunkcall_nots (tvb, offset, iax2_tree, &scallno);
2050       if (!call_list_find (calls, scallno)) {
2051         calls = call_list_append (calls, scallno);
2052       }
2053       nframes++;
2054     }
2055   }
2056
2057   ncalls = call_list_length (calls);
2058
2059   if( iax2_tree ) {
2060     /* number of items */
2061     nc = proto_tree_add_uint(iax2_tree, hf_iax2_trunk_ncalls, NULL, 0, 0, ncalls);
2062     PROTO_ITEM_SET_GENERATED(nc);
2063   }
2064
2065   col_add_fstr (pinfo->cinfo, COL_INFO, "Trunk packet with %d media frame%s for %d call%s",
2066                 nframes, plurality(nframes, "", "s"),
2067                 ncalls, plurality(ncalls, "", "s"));
2068
2069   return offset;
2070 }
2071
2072
2073 static void process_iax_pdu( tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
2074                               gboolean video, iax_packet_data *iax_packet )
2075 {
2076   guint32 codec = iax_packet -> codec;
2077   iax_call_data *iax_call = iax_packet -> call_data;
2078
2079 #ifdef DEBUG_DESEGMENT
2080   g_debug("calling process_iax_pdu; len = %u", tvb_reported_length(tvb));
2081 #endif
2082
2083   if( !video && iax_call && iax_call->subdissector ) {
2084     call_dissector(iax_call->subdissector, tvb, pinfo, tree);
2085   }else if( codec != 0 && dissector_try_uint(iax2_codec_dissector_table, codec, tvb, pinfo, tree )) {
2086     /* codec dissector handled our data */
2087   }else {
2088     /* we don't know how to dissect our data: dissect it as data */
2089     call_dissector(data_handle,tvb, pinfo, tree);
2090   }
2091
2092 #ifdef DEBUG_DESEGMENT
2093   g_debug("called process_iax_pdu; pinfo->desegment_len=%u; pinfo->desegment_offset=%u",
2094             pinfo->desegment_len, pinfo->desegment_offset);
2095 #endif
2096 }
2097
2098 static void desegment_iax(tvbuff_t *tvb, packet_info *pinfo, proto_tree *iax2_tree,
2099                           proto_tree *tree, gboolean video, iax_packet_data *iax_packet )
2100 {
2101
2102   iax_call_data *iax_call = iax_packet -> call_data;
2103   iax_call_dirdata *dirdata;
2104   gpointer value=NULL;
2105   guint32 frag_offset=0;
2106   fragment_data *fd_head;
2107   gboolean must_desegment = FALSE;
2108
2109   DISSECTOR_ASSERT(iax_call);
2110
2111   pinfo->can_desegment = 2;
2112   pinfo->desegment_offset = 0;
2113   pinfo->desegment_len = 0;
2114
2115 #ifdef DEBUG_DESEGMENT
2116   g_debug("dissecting packet %u", pinfo->fd->num);
2117 #endif
2118
2119   dirdata = &(iax_call->dirdata[!!(iax_packet->reversed)]);
2120
2121   if((!pinfo->fd->flags.visited && dirdata->current_frag_bytes > 0) ||
2122      (value = g_hash_table_lookup(iax_call->fid_table,
2123                                   GUINT_TO_POINTER(pinfo->fd->num))) != NULL ) {
2124     /* then we are continuing an already-started pdu */
2125     guint32 fid;
2126     guint32 frag_len = tvb_reported_length( tvb );
2127     gboolean complete;
2128
2129 #ifdef DEBUG_DESEGMENT
2130     g_debug("visited: %i; c_f_b: %u; hash: %u->%u", pinfo->fd->flags.visited?1:0,
2131             dirdata->current_frag_bytes, pinfo->fd->num, fid);
2132 #endif
2133
2134     if(!pinfo->fd->flags.visited) {
2135       guint32 tot_len;
2136       fid = dirdata->current_frag_id;
2137       tot_len                      = dirdata->current_frag_minlen;
2138       g_hash_table_insert( iax_call->fid_table, GUINT_TO_POINTER(pinfo->fd->num), GUINT_TO_POINTER(fid) );
2139       frag_offset                  = dirdata->current_frag_bytes;
2140       dirdata->current_frag_bytes += frag_len;
2141       complete                     = dirdata->current_frag_bytes > tot_len;
2142 #ifdef DEBUG_DESEGMENT
2143       g_debug("hash: %u->%u; frag_offset: %u; c_f_b: %u; totlen: %u",
2144               pinfo->fd->num, fid, frag_offset, dirdata->current_frag_bytes, tot_len );
2145 #endif
2146     } else {
2147       fid = GPOINTER_TO_UINT(value);
2148       /* these values are unused by fragment_add if pinfo->fd->flags.visited */
2149       dirdata->current_frag_bytes = 0;
2150       complete = FALSE;
2151     }
2152
2153     /* fragment_add checks for already-added */
2154     fd_head = fragment_add( tvb, 0, pinfo, fid,
2155                             iax_call->fragment_table,
2156                             frag_offset,
2157                             frag_len, !complete );
2158
2159     if(fd_head && (pinfo->fd->num == fd_head->reassembled_in)) {
2160       gint32 old_len;
2161       tvbuff_t *next_tvb = tvb_new_child_real_data(tvb, fd_head->data, fd_head->datalen, fd_head->datalen);
2162       add_new_data_source(pinfo, next_tvb, "Reassembled IAX2");
2163
2164       process_iax_pdu(next_tvb,pinfo,tree,video,iax_packet);
2165
2166       /* calculate the amount of data which was available to the higher-level
2167          dissector before we added this segment; if the returned offset is
2168          within that section, the higher-level dissector was unable to find any
2169          pdus; if it's after that, it found one or more complete PDUs.
2170       */
2171       old_len = (gint32)(tvb_reported_length(next_tvb) - frag_len);
2172       if( pinfo->desegment_len &&
2173           pinfo->desegment_offset < old_len ) {
2174         /* oops, it wasn't actually complete */
2175         fragment_set_partial_reassembly(pinfo, fid, iax_call->fragment_table);
2176         if(pinfo->desegment_len == DESEGMENT_ONE_MORE_SEGMENT) {
2177           /* only one more byte should be enough for a retry */
2178           dirdata->current_frag_minlen = fd_head->datalen + 1;
2179         } else {
2180           dirdata->current_frag_minlen = fd_head->datalen + pinfo->desegment_len;
2181         }
2182       } else {
2183         /* we successfully dissected some data; create the proto tree items for
2184          * the fragments, and flag any remaining data for desegmentation */
2185
2186         proto_item *iax_tree_item, *frag_tree_item;
2187         /* this nargery is to insert the fragment tree into the main tree
2188          * between the IAX protocol entry and the subdissector entry */
2189         show_fragment_tree(fd_head, &iax2_fragment_items, tree, pinfo, next_tvb, &frag_tree_item);
2190         iax_tree_item = proto_tree_get_parent( iax2_tree );
2191         if( frag_tree_item && iax_tree_item )
2192           proto_tree_move_item( tree, iax_tree_item, frag_tree_item );
2193
2194         dirdata->current_frag_minlen = dirdata->current_frag_id = dirdata->current_frag_bytes = 0;
2195
2196         if( pinfo->desegment_len ) {
2197           /* there's a bit of data left to desegment */
2198           must_desegment = TRUE;
2199           /* make desegment_offset relative to our tvb */
2200           pinfo->desegment_offset -= old_len;
2201         }
2202
2203         /* don't add a 'reassembled in' item for this pdu */
2204         fd_head = NULL;
2205       }
2206     }
2207   } else {
2208     /* This segment was not found in our table, so it doesn't
2209        contain a continuation of a higher-level PDU.
2210        Call the normal subdissector.
2211     */
2212
2213     process_iax_pdu(tvb,pinfo,tree,video,iax_packet);
2214
2215     if(pinfo->desegment_len) {
2216       /* the higher-level dissector has asked for some more data - ie,
2217          the end of this segment does not coincide with the end of a
2218          higher-level PDU. */
2219       must_desegment = TRUE;
2220     }
2221
2222     fd_head = NULL;
2223   }
2224
2225   /* must_desegment is set if the end of this segment (or the whole of it)
2226    * contained the start of a higher-level PDU; we must add whatever is left of
2227    * this segment (after pinfo->desegment_offset) to a fragment table for disassembly. */
2228   if(must_desegment) {
2229     guint32 fid = pinfo->fd->num; /* a new fragment id */
2230     guint32 deseg_offset = pinfo->desegment_offset;
2231     guint32 frag_len = tvb_reported_length_remaining(tvb,deseg_offset);
2232     dirdata->current_frag_id = fid;
2233     dirdata->current_frag_bytes = frag_len;
2234
2235     if(pinfo->desegment_len == DESEGMENT_ONE_MORE_SEGMENT) {
2236       /* only one more byte should be enough for a retry */
2237       dirdata->current_frag_minlen = frag_len + 1;
2238     } else {
2239       dirdata->current_frag_minlen = frag_len + pinfo->desegment_len;
2240     }
2241
2242     fd_head = fragment_add(tvb, deseg_offset, pinfo, fid,
2243                            iax_call->fragment_table,
2244                            0, frag_len, TRUE );
2245 #ifdef DEBUG_DESEGMENT
2246     g_debug("Start offset of undissected bytes: %u; "
2247             "Bytes remaining in this segment: %u; min required bytes: %u\n",
2248             deseg_offset, frag_len, frag_len + pinfo->desegment_len);
2249 #endif
2250   }
2251
2252   /* add a 'reassembled in' item if necessary */
2253   if( fd_head != NULL ) {
2254     guint32 deseg_offset = pinfo->desegment_offset;
2255     if( fd_head->reassembled_in != 0 &&
2256         !(fd_head->flags & FD_PARTIAL_REASSEMBLY) ) {
2257       proto_item *iax_tree_item;
2258       iax_tree_item = proto_tree_add_uint( tree, hf_iax2_reassembled_in,
2259                                            tvb, deseg_offset, tvb_reported_length_remaining(tvb,deseg_offset),
2260                                            fd_head->reassembled_in);
2261       PROTO_ITEM_SET_GENERATED(iax_tree_item);
2262     } else {
2263       /* this fragment is never reassembled */
2264       proto_tree_add_text( tree, tvb, deseg_offset, -1,
2265                            "IAX2 fragment, unfinished");
2266     }
2267
2268     if( pinfo->desegment_offset == 0 ) {
2269       col_set_str(pinfo->cinfo, COL_PROTOCOL, "IAX2");
2270       col_set_str(pinfo->cinfo, COL_INFO, "[IAX2 segment of a reassembled PDU]");
2271     }
2272   }
2273
2274   pinfo->can_desegment = 0;
2275   pinfo->desegment_offset = 0;
2276   pinfo->desegment_len = 0;
2277 }
2278
2279 static void dissect_payload(tvbuff_t *tvb, guint32 offset,
2280                             packet_info *pinfo, proto_tree *iax2_tree,
2281                             proto_tree *tree, guint32 ts _U_, gboolean video,
2282                             iax_packet_data *iax_packet)
2283 {
2284 #if 0
2285   gboolean out_of_order = FALSE;
2286 #endif
2287   tvbuff_t *sub_tvb;
2288   guint32 codec = iax_packet -> codec;
2289   guint32 nbytes;
2290   iax_call_data *iax_call = iax_packet -> call_data;
2291
2292   if( offset >= tvb_reported_length (tvb)) {
2293     col_append_str (pinfo->cinfo, COL_INFO, ", empty frame" );
2294     return;
2295   }
2296
2297   sub_tvb = tvb_new_subset_remaining(tvb, offset);
2298
2299   /* XXX shouldn't pass through out-of-order packets. */
2300
2301   if (check_col (pinfo->cinfo, COL_INFO)) {
2302     if( !video && iax_call && iax_call -> dataformat != 0 ) {
2303       col_append_fstr (pinfo->cinfo, COL_INFO, ", data, format %s",
2304                        val_to_str (iax_call -> dataformat,
2305                                    iax_dataformats, "unknown (0x%02x)"));
2306 #if 0
2307       if( out_of_order )
2308         col_append_str (pinfo->cinfo, COL_INFO, " (out-of-order packet)");
2309 #endif
2310     } else {
2311       col_append_fstr (pinfo->cinfo, COL_INFO, ", %s",
2312                        val_to_str (codec, codec_types, "unknown (0x%02x)"));
2313     }
2314   }
2315
2316   nbytes = tvb_reported_length(sub_tvb);
2317   proto_tree_add_text( iax2_tree, sub_tvb, 0, -1,
2318                        "IAX2 payload (%u byte%s)", nbytes,
2319                        plurality( nbytes, "", "s" ));
2320
2321   iax2_info->payload_len = nbytes;
2322   iax2_info->payload_data = tvb_get_ptr(sub_tvb, 0, -1);
2323
2324   /* pass the rest of the block to a subdissector */
2325   if(iax_packet->call_data)
2326     desegment_iax( sub_tvb, pinfo, iax2_tree, tree, video, iax_packet );
2327   else
2328     process_iax_pdu(sub_tvb,pinfo,tree,video,iax_packet);
2329 }
2330
2331 /*
2332  * Init routines
2333  */
2334
2335 /* called at the start of a capture. We should clear out our static, per-capture
2336  * data.
2337  */
2338
2339 static void
2340 iax_init_protocol(void)
2341 {
2342   iax_init_hash();
2343
2344 }
2345
2346
2347 void
2348 proto_register_iax2 (void)
2349 {
2350   /* A header field is something you can search/filter on.
2351    *
2352    * We create a structure to register our fields. It consists of an
2353    * array of hf_register_info structures, each of which are of the format
2354    * {&(field id), {name, abbrev, type, display, strings, bitmask, blurb, HFILL}}.
2355    */
2356
2357   static hf_register_info hf[] = {
2358
2359     {&hf_iax2_packet_type,
2360      {"Packet type", "iax2.packet_type", FT_UINT8, BASE_DEC, VALS(iax_packet_types), 0,
2361       "Full/minivoice/minivideo/trunk packet",
2362       HFILL}},
2363
2364     {&hf_iax2_callno,
2365      {"Call identifier", "iax2.call", FT_UINT32, BASE_DEC, NULL, 0,
2366       "This is the identifier Wireshark assigns to identify this call. It does not correspond to any real field in the protocol", HFILL }},
2367
2368     {&hf_iax2_scallno,
2369      {"Source call", "iax2.src_call", FT_UINT16, BASE_DEC, NULL, 0x7FFF,
2370       "src_call holds the number of this call at the packet source pbx",
2371       HFILL}},
2372
2373     /* FIXME could this be turned into a FRAMENUM field? */
2374     {&hf_iax2_dcallno,
2375      {"Destination call", "iax2.dst_call", FT_UINT16, BASE_DEC, NULL, 0x7FFF,
2376       "dst_call holds the number of this call at the packet destination",
2377       HFILL}},
2378
2379     {&hf_iax2_retransmission,
2380      {"Retransmission", "iax2.retransmission", FT_BOOLEAN, 16,
2381       NULL, 0x8000,
2382       "retransmission is set if this packet is a retransmission of an earlier failed packet", HFILL}},
2383
2384     {&hf_iax2_ts,
2385      {"Timestamp", "iax2.timestamp", FT_UINT32, BASE_DEC, NULL, 0x0,
2386       "timestamp is the time, in ms after the start of this call, at which this packet was transmitted",
2387       HFILL}},
2388
2389     {&hf_iax2_minits,
2390      {"Timestamp", "iax2.timestamp", FT_UINT16, BASE_DEC, NULL, 0x0,
2391       "timestamp is the time, in ms after the start of this call, at which this packet was transmitted",
2392       HFILL}},
2393
2394     {&hf_iax2_minividts,
2395      {"Timestamp", "iax2.timestamp", FT_UINT16, BASE_DEC, NULL, 0x7FFF,
2396       "timestamp is the time, in ms after the start of this call, at which this packet was transmitted",
2397       HFILL}},
2398
2399     {&hf_iax2_absts,
2400      {"Absolute Time", "iax2.abstime", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL, NULL, 0x0,
2401       "The absolute time of this packet (calculated by adding the IAX timestamp to  the start time of this call)",
2402       HFILL}},
2403
2404     {&hf_iax2_lateness,
2405      {"Lateness", "iax2.lateness", FT_RELATIVE_TIME, BASE_NONE, NULL, 0x0,
2406       "The lateness of this packet compared to its timestamp",
2407       HFILL}},
2408
2409     {&hf_iax2_minividmarker,
2410      {"Marker", "iax2.video.marker", FT_UINT16, BASE_DEC, NULL, 0x8000,
2411       "RTP end-of-frame marker",
2412       HFILL}},
2413
2414     {&hf_iax2_oseqno,
2415      {"Outbound seq.no.", "iax2.oseqno", FT_UINT16, BASE_DEC, NULL,
2416       0x0,
2417       "oseqno is the sequence no of this packet. The first packet has oseqno==0, and subsequent packets increment the oseqno by 1",
2418       HFILL}},
2419
2420     {&hf_iax2_iseqno,
2421      {"Inbound seq.no.", "iax2.iseqno", FT_UINT16, BASE_DEC, NULL, 0x0,
2422       "iseqno is the sequence no of the last successfully received packet",
2423       HFILL}},
2424
2425     {&hf_iax2_type,
2426      {"Type", "iax2.type", FT_UINT8, BASE_DEC, VALS (iax_frame_types),
2427       0x0,
2428       "For full IAX2 frames, type is the type of frame",
2429       HFILL}},
2430
2431     {&hf_iax2_csub,
2432      {"Unknown subclass", "iax2.subclass", FT_UINT8, BASE_DEC, NULL, 0x0,
2433       "Subclass of unknown type of full IAX2 frame",
2434       HFILL}},
2435
2436     {&hf_iax2_dtmf_csub,
2437      {"DTMF subclass (digit)", "iax2.dtmf.subclass", FT_STRINGZ, BASE_NONE, NULL, 0x0,
2438       "DTMF subclass gives the DTMF digit",
2439       HFILL}},
2440
2441     {&hf_iax2_cmd_csub,
2442      {"Control subclass", "iax2.control.subclass", FT_UINT8, BASE_DEC,
2443       VALS (iax_cmd_subclasses), 0x0,
2444       "This gives the command number for a Control packet.", HFILL}},
2445
2446     {&hf_iax2_iax_csub,
2447      {"IAX subclass", "iax2.iax.subclass", FT_UINT8, BASE_DEC,
2448       VALS (iax_iax_subclasses),
2449       0x0,
2450       "IAX subclass gives the command number for IAX signaling packets", HFILL}},
2451
2452     {&hf_iax2_voice_csub,
2453      {"Voice Subclass (compressed codec no)", "iax2.voice.subclass", FT_UINT8, BASE_DEC, NULL, 0x0,
2454       NULL,
2455       HFILL}},
2456
2457     {&hf_iax2_voice_codec,
2458      {"CODEC", "iax2.voice.codec", FT_UINT32, BASE_HEX, VALS (codec_types),
2459       0x0,
2460       "CODEC gives the codec used to encode audio data", HFILL}},
2461
2462     {&hf_iax2_video_csub,
2463      {"Video Subclass (compressed codec no)", "iax2.video.subclass", FT_UINT8, BASE_DEC, NULL, 0xBF,
2464       NULL,
2465       HFILL}},
2466
2467     {&hf_iax2_marker,
2468      {"Marker", "iax2.video.marker", FT_BOOLEAN, 8, NULL, 0x40,
2469       "RTP end-of-frame marker",
2470       HFILL}},
2471
2472     {&hf_iax2_video_codec,
2473      {"CODEC", "iax2.video.codec", FT_UINT32, BASE_HEX, VALS (codec_types), 0,
2474       "The codec used to encode video data", HFILL}},
2475
2476     {&hf_iax2_modem_csub,
2477      {"Modem subclass", "iax2.modem.subclass", FT_UINT8, BASE_DEC,
2478       VALS (iax_modem_subclasses),
2479       0x0,
2480       "Modem subclass gives the type of modem", HFILL}},
2481
2482     {&hf_iax2_trunk_ts,
2483      {"Timestamp", "iax2.timestamp", FT_UINT32, BASE_DEC, NULL, 0x0,
2484       "timestamp is the time, in ms after the start of Command data this call, at which this trunk packet was transmitted",
2485       HFILL}},
2486
2487     {&hf_iax2_trunk_metacmd,
2488      {"Meta command", "iax2.trunk.metacmd", FT_UINT8, BASE_DEC, NULL, 0x7F,
2489       "Meta command indicates whether or not the Meta Frame is a trunk.", HFILL}},
2490
2491     {&hf_iax2_trunk_cmddata,
2492      {"Command data", "iax2.trunk.cmddata", FT_UINT8, BASE_HEX, NULL, 0x0,
2493       "Flags for options that apply to a trunked call", HFILL}},
2494
2495     {&hf_iax2_trunk_cmddata_ts,
2496      {"Trunk timestamps", "iax2.trunk.cmddata.ts", FT_BOOLEAN, 8, NULL, IAX2_TRUNK_TS,
2497       "True: calls do each include their own timestamp", HFILL}},
2498
2499     {&hf_iax2_trunk_call_len,
2500      {"Data length", "iax2.trunk.call.len", FT_UINT16, BASE_DEC, NULL, 0x0,
2501       "Trunk call data length in octets", HFILL}},
2502
2503     {&hf_iax2_trunk_call_scallno,
2504      {"Source call number", "iax2.trunk.call.scallno", FT_UINT16, BASE_DEC, NULL, 0x7FFF,
2505       "Trunk call source call number", HFILL}},
2506
2507     {&hf_iax2_trunk_call_ts,
2508      {"Timestamp", "iax2.trunk.call.ts", FT_UINT16, BASE_DEC, NULL, 0x0,
2509       "timestamp is the time, in ms after the start of this call, at which this packet was transmitted",
2510       HFILL}},
2511
2512     {&hf_iax2_trunk_call_data,
2513      {"Data", "iax2.trunk.call.payload", FT_BYTES, BASE_NONE, NULL, 0x0,
2514       "Payload carried by this trunked packet.",
2515       HFILL}},
2516
2517     {&hf_iax2_trunk_ncalls,
2518      {"Number of calls", "iax2.trunk.ncalls", FT_UINT16, BASE_DEC, NULL, 0x0,
2519       "Number of calls in this trunk packet",
2520       HFILL}},
2521
2522     /*
2523      * Decoding for the ies
2524      */
2525
2526     {&hf_IAX_IE_APPARENTADDR_SINFAMILY,
2527      {"Family", "iax2.iax.app_addr.sinfamily", FT_UINT16, BASE_DEC, NULL, 0, NULL, HFILL }},
2528     {&hf_IAX_IE_APPARENTADDR_SINPORT,
2529      {"Port", "iax2.iax.app_addr.sinport", FT_UINT16, BASE_DEC, NULL, 0, NULL, HFILL }},
2530     {&hf_IAX_IE_APPARENTADDR_SINADDR,
2531      {"Address", "iax2.iax.app_addr.sinaddr", FT_IPv4, BASE_NONE, NULL, 0, NULL, HFILL }},
2532
2533     {&hf_iax2_ies[IAX_IE_CALLED_NUMBER],
2534      {"Number/extension being called", "iax2.iax.called_number",
2535       FT_STRING,
2536       BASE_NONE, NULL, 0x0, NULL, HFILL}},
2537
2538     {&hf_iax2_ies[IAX_IE_CALLING_NUMBER],
2539      {"Calling number", "iax2.iax.calling_number", FT_STRING,
2540       BASE_NONE, NULL,
2541       0x0, NULL, HFILL}},
2542
2543     {&hf_iax2_ies[IAX_IE_CALLING_ANI],
2544      {"Calling number ANI for billing", "iax2.iax.calling_ani",
2545       FT_STRING,
2546       BASE_NONE, NULL, 0x0, NULL, HFILL}},
2547
2548     {&hf_iax2_ies[IAX_IE_CALLING_NAME],
2549      {"Name of caller", "iax2.iax.calling_name", FT_STRING, BASE_NONE,
2550       NULL,
2551       0x0, NULL, HFILL}},
2552
2553     {&hf_iax2_ies[IAX_IE_CALLED_CONTEXT],
2554      {"Context for number", "iax2.iax.called_context", FT_STRING,
2555       BASE_NONE,
2556       NULL, 0x0, NULL, HFILL}},
2557
2558     {&hf_iax2_ies[IAX_IE_USERNAME],
2559      {"Username (peer or user) for authentication",
2560       "iax2.iax.username",
2561       FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL}},
2562
2563     {&hf_iax2_ies[IAX_IE_PASSWORD],
2564      {"Password for authentication", "iax2.iax.password", FT_STRING,
2565       BASE_NONE, NULL, 0x0, NULL, HFILL}},
2566
2567     {&hf_iax2_ies[IAX_IE_CAPABILITY],
2568      {"Actual codec capability", "iax2.iax.capability", FT_UINT32,
2569       BASE_HEX,
2570       NULL, 0x0, NULL, HFILL}},
2571
2572     {&hf_iax2_ies[IAX_IE_FORMAT],
2573      {"Desired codec format", "iax2.iax.format", FT_UINT32, BASE_HEX,
2574       VALS (codec_types), 0x0, NULL, HFILL}},
2575
2576     {&hf_iax2_ies[IAX_IE_LANGUAGE],
2577      {"Desired language", "iax2.iax.language", FT_STRING, BASE_NONE,
2578       NULL,
2579       0x0, NULL, HFILL}},
2580
2581     {&hf_iax2_ies[IAX_IE_VERSION],
2582      {"Protocol version", "iax2.iax.version", FT_UINT16, BASE_HEX, NULL,
2583       0x0,
2584       NULL, HFILL}},
2585
2586     {&hf_iax2_ies[IAX_IE_ADSICPE],
2587      {"CPE ADSI capability", "iax2.iax.cpe_adsi", FT_UINT16, BASE_HEX,
2588       NULL,
2589       0x0, NULL, HFILL}},
2590
2591     {&hf_iax2_ies[IAX_IE_DNID],
2592      {"Originally dialed DNID", "iax2.iax.dnid", FT_STRING, BASE_NONE,
2593       NULL,
2594       0x0, NULL, HFILL}},
2595
2596     {&hf_iax2_ies[IAX_IE_AUTHMETHODS],
2597      {"Authentication method(s)", "iax2.iax.auth.methods", FT_UINT16,
2598       BASE_HEX,
2599       NULL, 0x0, NULL, HFILL}},
2600
2601     {&hf_iax2_ies[IAX_IE_CHALLENGE],
2602      {"Challenge data for MD5/RSA", "iax2.iax.auth.challenge",
2603       FT_STRING,
2604       BASE_NONE, NULL, 0x0, NULL, HFILL}},
2605
2606     {&hf_iax2_ies[IAX_IE_MD5_RESULT],
2607      {"MD5 challenge result", "iax2.iax.auth.md5", FT_STRING,
2608       BASE_NONE, NULL,
2609       0x0, NULL, HFILL}},
2610
2611     {&hf_iax2_ies[IAX_IE_RSA_RESULT],
2612      {"RSA challenge result", "iax2.iax.auth.rsa", FT_STRING,
2613       BASE_NONE, NULL,
2614       0x0, NULL, HFILL}},
2615
2616     {&hf_iax2_ies[IAX_IE_REFRESH],
2617      {"When to refresh registration", "iax2.iax.refresh", FT_INT16,
2618       BASE_DEC,
2619       NULL, 0x0, NULL, HFILL}},
2620
2621     {&hf_iax2_ies[IAX_IE_DPSTATUS],
2622      {"Dialplan status", "iax2.iax.dialplan_status", FT_UINT16,
2623       BASE_HEX, NULL,
2624       0x0, NULL, HFILL}},
2625
2626     {&hf_iax2_ies[IAX_IE_CALLNO],
2627      {"Call number of peer", "iax2.iax.call_no", FT_UINT16, BASE_DEC,
2628       NULL,
2629       0x0, NULL, HFILL}},
2630
2631     {&hf_iax2_ies[IAX_IE_CAUSE],
2632      {"Cause", "iax2.iax.cause", FT_STRING, BASE_NONE, NULL, 0x0, NULL,
2633       HFILL}},
2634
2635     {&hf_iax2_ies[IAX_IE_IAX_UNKNOWN],
2636      {"Unknown IAX command", "iax2.iax.iax_unknown", FT_BYTES,
2637       BASE_NONE, NULL,
2638       0x0, NULL, HFILL}},
2639
2640     {&hf_iax2_ies[IAX_IE_MSGCOUNT],
2641      {"How many messages waiting", "iax2.iax.msg_count", FT_INT16,
2642       BASE_DEC,
2643       NULL, 0x0, NULL, HFILL}},
2644
2645     {&hf_iax2_ies[IAX_IE_AUTOANSWER],
2646      {"Request auto-answering", "iax2.iax.autoanswer", FT_NONE,
2647       BASE_NONE,
2648       NULL, 0x0, NULL, HFILL}},
2649
2650     {&hf_iax2_ies[IAX_IE_MUSICONHOLD],
2651      {"Request musiconhold with QUELCH", "iax2.iax.moh", FT_NONE,
2652       BASE_NONE,
2653       NULL, 0x0, NULL, HFILL}},
2654
2655     {&hf_iax2_ies[IAX_IE_TRANSFERID],
2656      {"Transfer Request Identifier", "iax2.iax.transferid", FT_UINT32,
2657       BASE_HEX, NULL, 0x0, NULL, HFILL}},
2658
2659     {&hf_iax2_ies[IAX_IE_RDNIS],
2660      {"Referring DNIS", "iax2.iax.rdnis", FT_STRING, BASE_NONE, NULL,
2661       0x0, NULL,
2662       HFILL}},
2663
2664     {&hf_iax2_ies[IAX_IE_PROVISIONING],
2665      {"Provisioning info","iax2.iax.provisioning", FT_STRING, BASE_NONE,
2666        NULL, 0x0, NULL, HFILL}},
2667
2668     {&hf_iax2_ies[IAX_IE_AESPROVISIONING],
2669      {"AES Provisioning info","iax2.iax.aesprovisioning", FT_STRING, BASE_NONE,
2670        NULL, 0x0, NULL, HFILL}},
2671
2672     {&hf_iax2_ies[IAX_IE_DATETIME],
2673      {"Date/Time", "iax2.iax.datetime.raw", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL}},
2674
2675     {&hf_iax2_ie_datetime,
2676      {"Date/Time", "iax2.iax.datetime", FT_ABSOLUTE_TIME, ABSOLUTE_TIME_LOCAL, NULL, 0x0, NULL, HFILL }},
2677
2678     {&hf_iax2_ies[IAX_IE_DEVICETYPE],
2679      {"Device type", "iax2.iax.devicetype", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL}},
2680
2681     {&hf_iax2_ies[IAX_IE_SERVICEIDENT],
2682      {"Service identifier", "iax2.iax.serviceident", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL}},
2683
2684     {&hf_iax2_ies[IAX_IE_FIRMWAREVER],
2685      {"Firmware version", "iax2.iax.firmwarever", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2686
2687     {&hf_iax2_ies[IAX_IE_FWBLOCKDESC],
2688      {"Firmware block description", "iax2.iax.fwblockdesc", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2689
2690     {&hf_iax2_ies[IAX_IE_FWBLOCKDATA],
2691      {"Firmware block of data", "iax2.iax.fwblockdata", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL}},
2692
2693     {&hf_iax2_ies[IAX_IE_PROVVER],
2694      {"Provisioning version", "iax2.iax.provver", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2695
2696     {&hf_iax2_ies[IAX_IE_CALLINGPRES],
2697      {"Calling presentation", "iax2.iax.callingpres", FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2698
2699     {&hf_iax2_ies[IAX_IE_CALLINGTON],
2700      {"Calling type of number", "iax2.iax.callington", FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2701
2702     {&hf_iax2_ies[IAX_IE_CALLINGTNS],
2703      {"Calling transit network select", "iax2.iax.callingtns", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2704
2705     {&hf_iax2_ies[IAX_IE_SAMPLINGRATE],
2706      {"Supported sampling rates", "iax2.iax.samplingrate", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2707
2708     {&hf_iax2_ies[IAX_IE_CAUSECODE],
2709      {"Hangup cause", "iax2.iax.causecode", FT_UINT8, BASE_HEX, VALS(iax_causecodes),
2710        0x0, NULL, HFILL}},
2711
2712     {&hf_iax2_ies[IAX_IE_ENCRYPTION],
2713      {"Encryption format", "iax2.iax.encryption", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2714
2715     {&hf_iax2_ies[IAX_IE_ENCKEY],
2716      {"Encryption key", "iax2.iax.enckey", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL}},
2717
2718     {&hf_iax2_ies[IAX_IE_CODEC_PREFS],
2719      {"Codec negotiation", "iax2.iax.codecprefs", FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL}},
2720
2721     {&hf_iax2_ies[IAX_IE_RR_JITTER],
2722      {"Received jitter (as in RFC1889)", "iax2.iax.rrjitter", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2723
2724     {&hf_iax2_ies[IAX_IE_RR_LOSS],
2725      {"Received loss (high byte loss pct, low 24 bits loss count, as in rfc1889)", "iax2.iax.rrloss",
2726        FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2727
2728     {&hf_iax2_ies[IAX_IE_RR_PKTS],
2729      {"Total frames received", "iax2.iax.rrpkts", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2730
2731     {&hf_iax2_ies[IAX_IE_RR_DELAY],
2732      {"Max playout delay in ms for received frames", "iax2.iax.rrdelay", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2733
2734     {&hf_iax2_ies[IAX_IE_RR_DROPPED],
2735      {"Dropped frames (presumably by jitterbuffer)", "iax2.iax.rrdropped", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2736
2737     {&hf_iax2_ies[IAX_IE_RR_OOO],
2738      {"Frame received out of order", "iax2.iax.rrooo", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL}},
2739
2740     {&hf_iax2_ies[IAX_IE_DATAFORMAT],
2741      {"Data call format", "iax2.iax.dataformat", FT_UINT32, BASE_HEX,
2742       VALS(iax_dataformats), 0x0, NULL, HFILL}},
2743
2744     {&hf_IAX_IE_UNKNOWN_BYTE,
2745      {"Unknown", "iax2.iax.unknownbyte", FT_UINT8, BASE_HEX, NULL,
2746       0x0, "Raw data for unknown IEs",
2747       HFILL}},
2748     {&hf_IAX_IE_UNKNOWN_I16,
2749      {"Unknown", "iax2.iax.unknownshort", FT_UINT16, BASE_HEX, NULL,
2750       0x0, "Raw data for unknown IEs",
2751       HFILL}},
2752     {&hf_IAX_IE_UNKNOWN_I32,
2753      {"Unknown", "iax2.iax.unknownlong", FT_UINT32, BASE_HEX, NULL,
2754       0x0, "Raw data for unknown IEs",
2755       HFILL}},
2756     {&hf_IAX_IE_UNKNOWN_BYTES,
2757      {"Unknown", "iax2.iax.unknownstring", FT_STRING, BASE_NONE, NULL,
2758       0x0, "Raw data for unknown IEs",
2759       HFILL}},
2760
2761     /* capabilities */
2762     {&hf_iax2_cap_g723_1,
2763      {"G.723.1 compression", "iax2.cap.g723_1", FT_BOOLEAN, 32,
2764       TFS(&tfs_supported_not_supported), AST_FORMAT_G723_1,
2765       NULL, HFILL }},
2766
2767     {&hf_iax2_cap_gsm,
2768      {"GSM compression", "iax2.cap.gsm", FT_BOOLEAN, 32,
2769        TFS(&tfs_supported_not_supported), AST_FORMAT_GSM,
2770       NULL, HFILL }},
2771
2772     {&hf_iax2_cap_ulaw,
2773      {"Raw mu-law data (G.711)", "iax2.cap.ulaw",FT_BOOLEAN, 32,
2774       TFS(&tfs_supported_not_supported), AST_FORMAT_ULAW,
2775       NULL, HFILL }},
2776
2777      {&hf_iax2_cap_alaw,
2778       {"Raw A-law data (G.711)", "iax2.cap.alaw",FT_BOOLEAN, 32,
2779        TFS(&tfs_supported_not_supported), AST_FORMAT_ALAW,
2780        NULL, HFILL }},
2781
2782     {&hf_iax2_cap_g726_aal2,
2783      {"G.726 compression (AAL2 packing)", "iax2.cap.g726_aal2",FT_BOOLEAN, 32,
2784       TFS(&tfs_supported_not_supported), AST_FORMAT_G726_AAL2,
2785       NULL, HFILL }},
2786
2787     {&hf_iax2_cap_adpcm,
2788      {"ADPCM", "iax2.cap.adpcm", FT_BOOLEAN, 32,
2789       TFS(&tfs_supported_not_supported), AST_FORMAT_ADPCM,
2790       NULL, HFILL }},
2791
2792     {&hf_iax2_cap_slinear,
2793      {"Raw 16-bit Signed Linear (8000 Hz) PCM", "iax2.cap.slinear",
2794       FT_BOOLEAN, 32, TFS(&tfs_supported_not_supported), AST_FORMAT_SLINEAR,
2795       NULL, HFILL }},
2796
2797     {&hf_iax2_cap_lpc10,
2798      {"LPC10, 180 samples/frame", "iax2.cap.lpc10", FT_BOOLEAN, 32,
2799       TFS(&tfs_supported_not_supported), AST_FORMAT_LPC10,
2800       NULL, HFILL }},
2801
2802     {&hf_iax2_cap_g729a,
2803      {"G.729a Audio", "iax2.cap.g729a", FT_BOOLEAN, 32,
2804       TFS(&tfs_supported_not_supported), AST_FORMAT_G729A,
2805       NULL, HFILL }},
2806
2807     {&hf_iax2_cap_speex,
2808      {"SPEEX Audio", "iax2.cap.speex", FT_BOOLEAN, 32,
2809       TFS(&tfs_supported_not_supported), AST_FORMAT_SPEEX,
2810       NULL, HFILL }},
2811
2812     {&hf_iax2_cap_ilbc,
2813      {"iLBC Free compressed Audio", "iax2.cap.ilbc", FT_BOOLEAN, 32,
2814       TFS(&tfs_supported_not_supported), AST_FORMAT_ILBC,
2815       NULL, HFILL }},
2816
2817     {&hf_iax2_cap_g726,
2818      {"ADPCM (G.726, 32kbps, RFC3551 codeword packing)", "iax2.cap.g726", FT_BOOLEAN, 32,
2819       TFS(&tfs_supported_not_supported), AST_FORMAT_G726,
2820       NULL, HFILL }},
2821
2822     {&hf_iax2_cap_g722,
2823      {"G.722 wideband audio", "iax2.cap.g722", FT_BOOLEAN, 32,
2824       TFS(&tfs_supported_not_supported), AST_FORMAT_G722,
2825       NULL, HFILL }},
2826
2827     {&hf_iax2_cap_siren7,
2828      {"G.722.1 (also known as Siren7, 32kbps assumed)", "iax2.cap.siren7", FT_BOOLEAN, 32,
2829       TFS(&tfs_supported_not_supported), AST_FORMAT_SIREN7,
2830       NULL, HFILL }},
2831
2832     {&hf_iax2_cap_siren14,
2833      {"G.722.1 Annex C (also known as Siren14, 48kbps assumed)", "iax2.cap.siren14", FT_BOOLEAN, 32,
2834       TFS(&tfs_supported_not_supported), AST_FORMAT_SIREN14,
2835       NULL, HFILL }},
2836
2837     {&hf_iax2_cap_slinear16,
2838      {"Raw 16-bit Signed Linear (16000 Hz) PCM", "iax2.cap.slinear16", FT_BOOLEAN, 32,
2839       TFS(&tfs_supported_not_supported), AST_FORMAT_SLINEAR16,
2840       NULL, HFILL }},
2841
2842     {&hf_iax2_cap_jpeg,
2843      {"JPEG images", "iax2.cap.jpeg", FT_BOOLEAN, 32,
2844       TFS(&tfs_supported_not_supported), AST_FORMAT_JPEG,
2845       NULL, HFILL }},
2846
2847     {&hf_iax2_cap_png,
2848      {"PNG images", "iax2.cap.png", FT_BOOLEAN, 32,
2849       TFS(&tfs_supported_not_supported), AST_FORMAT_PNG,
2850       NULL, HFILL }},
2851
2852     {&hf_iax2_cap_h261,
2853      {"H.261 video", "iax2.cap.h261", FT_BOOLEAN, 32,
2854       TFS(&tfs_supported_not_supported), AST_FORMAT_H261,
2855       NULL, HFILL }},
2856
2857     {&hf_iax2_cap_h263,
2858      {"H.263 video", "iax2.cap.h263", FT_BOOLEAN, 32,
2859       TFS(&tfs_supported_not_supported), AST_FORMAT_H263,
2860       NULL, HFILL }},
2861
2862     {&hf_iax2_cap_h263_plus,
2863      {"H.263+ video", "iax2.cap.h263_plus", FT_BOOLEAN, 32,
2864       TFS(&tfs_supported_not_supported), AST_FORMAT_H263_PLUS,
2865       NULL, HFILL }},
2866
2867     {&hf_iax2_cap_h264,
2868      {"H.264 video", "iax2.cap.h264", FT_BOOLEAN, 32,
2869       TFS(&tfs_supported_not_supported), AST_FORMAT_H264,
2870       NULL, HFILL }},
2871
2872     {&hf_iax2_cap_mpeg4,
2873      {"MPEG4 video", "iax2.cap.mpeg4", FT_BOOLEAN, 32,
2874       TFS(&tfs_supported_not_supported), AST_FORMAT_MP4_VIDEO,
2875       NULL, HFILL }},
2876
2877     /* reassembly stuff */
2878     {&hf_iax2_fragments,
2879      {"IAX2 Fragments", "iax2.fragments", FT_NONE, BASE_NONE, NULL, 0x0,
2880       NULL, HFILL }},
2881
2882     {&hf_iax2_fragment,
2883      {"IAX2 Fragment data", "iax2.fragment", FT_FRAMENUM, BASE_NONE, NULL, 0x0,
2884       NULL, HFILL }},
2885
2886     {&hf_iax2_fragment_overlap,
2887      {"Fragment overlap", "iax2.fragment.overlap", FT_BOOLEAN, BASE_NONE,
2888       NULL, 0x0, "Fragment overlaps with other fragments", HFILL }},
2889
2890     {&hf_iax2_fragment_overlap_conflict,
2891      {"Conflicting data in fragment overlap", "iax2.fragment.overlap.conflict",
2892       FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2893       "Overlapping fragments contained conflicting data", HFILL }},
2894
2895     {&hf_iax2_fragment_multiple_tails,
2896      {"Multiple tail fragments found", "iax2.fragment.multipletails",
2897       FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2898       "Several tails were found when defragmenting the packet", HFILL }},
2899
2900     {&hf_iax2_fragment_too_long_fragment,
2901      {"Fragment too long", "iax2.fragment.toolongfragment",
2902       FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2903       "Fragment contained data past end of packet", HFILL }},
2904
2905     {&hf_iax2_fragment_error,
2906      {"Defragmentation error", "iax2.fragment.error",
2907       FT_FRAMENUM, BASE_NONE, NULL, 0x0,
2908       "Defragmentation error due to illegal fragments", HFILL }},
2909
2910     {&hf_iax2_fragment_count,
2911      {"Fragment count", "iax2.fragment.count",
2912       FT_UINT32, BASE_DEC, NULL, 0x0,
2913       NULL, HFILL }},
2914
2915     {&hf_iax2_reassembled_in,
2916      {"IAX2 fragment, reassembled in frame", "iax2.reassembled_in",
2917       FT_FRAMENUM, BASE_NONE, NULL, 0x0,
2918       "This IAX2 packet is reassembled in this frame", HFILL }},
2919
2920     {&hf_iax2_reassembled_length,
2921      {"Reassembled IAX2 length", "iax2.reassembled.length",
2922       FT_UINT32, BASE_DEC, NULL, 0x0,
2923       "The total length of the reassembled payload", HFILL }}
2924   };
2925
2926   static gint *ett[] = {
2927     &ett_iax2,
2928     &ett_iax2_full_mini_subtree,
2929     &ett_iax2_type,
2930     &ett_iax2_ie,
2931     &ett_iax2_codecs,
2932     &ett_iax2_ies_apparent_addr,
2933     &ett_iax2_fragment,
2934     &ett_iax2_fragments,
2935     &ett_iax2_trunk_cmddata,
2936     &ett_iax2_trunk_call
2937   };
2938
2939   /* initialize the hf_iax2_ies[] array to -1 */
2940   memset(hf_iax2_ies,0xff,sizeof(hf_iax2_ies));
2941
2942   proto_iax2 =
2943     proto_register_protocol ("Inter-Asterisk eXchange v2", "IAX2", "iax2");
2944   proto_register_field_array (proto_iax2, hf, array_length (hf));
2945   proto_register_subtree_array (ett, array_length (ett));
2946
2947   register_dissector("iax2", dissect_iax2, proto_iax2);
2948
2949   iax2_codec_dissector_table = register_dissector_table(
2950     "iax2.codec","IAX codec number", FT_UINT32, BASE_HEX);
2951   iax2_dataformat_dissector_table = register_dissector_table(
2952     "iax2.dataformat","IAX dataformat number", FT_UINT32, BASE_HEX);
2953
2954   /* register our init routine to be called at the start of a capture,
2955      to clear out our hash tables etc */
2956   register_init_routine(&iax_init_protocol);
2957   iax2_tap = register_tap("IAX2");
2958 }
2959
2960 void
2961 proto_reg_handoff_iax2 (void)
2962 {
2963   dissector_handle_t v110_handle = NULL;
2964
2965   dissector_add_uint("udp.port", IAX2_PORT, find_dissector("iax2"));
2966   v110_handle =  find_dissector("v110");
2967   if(v110_handle)
2968     dissector_add_uint("iax2.dataformat", AST_DATAFORMAT_V110, v110_handle);
2969   data_handle = find_dissector("data");
2970 }
2971
2972 /*
2973  * Editor modelines
2974  *
2975  * Local Variables:
2976  * c-basic-offset: 2
2977  * tab-width: 8
2978  * indent-tabs-mode: nil
2979  * End:
2980  *
2981  * ex: set shiftwidth=2 tabstop=8 expandtab:
2982  * :indentSize=2:tabSize=8:noTabs=true:
2983  */