2 * Routines for ppp packet disassembly
4 * $Id: packet-ppp.c,v 1.90 2002/04/14 23:04:03 guy Exp $
6 * Ethereal - Network traffic analyzer
7 * By Gerald Combs <gerald@ethereal.com>
9 * This file created and by Mike Hall <mlh@io.com>
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
31 #ifdef HAVE_SYS_TYPES_H
32 # include <sys/types.h>
38 #include <epan/packet.h>
39 #include "packet-ppp.h"
42 #include <epan/atalk-utils.h>
43 #include "packet-chdlc.h"
44 #include "packet-ip.h"
45 #include "packet-ipx.h"
46 #include "packet-vines.h"
49 #define ppp_min(a, b) ((a<b) ? a : b)
51 static int proto_ppp = -1;
52 static int hf_ppp_address = -1;
53 static int hf_ppp_control = -1;
54 static int hf_ppp_protocol = -1;
56 static gint ett_ppp = -1;
58 static int proto_lcp = -1;
60 static gint ett_lcp = -1;
61 static gint ett_lcp_options = -1;
62 static gint ett_lcp_authprot_opt = -1;
63 static gint ett_lcp_qualprot_opt = -1;
64 static gint ett_lcp_fcs_alternatives_opt = -1;
65 static gint ett_lcp_numbered_mode_opt = -1;
66 static gint ett_lcp_callback_opt = -1;
67 static gint ett_lcp_multilink_ep_disc_opt = -1;
68 static gint ett_lcp_internationalization_opt = -1;
70 static int proto_ipcp = -1;
72 static gint ett_ipcp = -1;
73 static gint ett_ipcp_options = -1;
74 static gint ett_ipcp_ipaddrs_opt = -1;
75 static gint ett_ipcp_compressprot_opt = -1;
77 static int proto_ccp = -1;
79 static gint ett_ccp = -1;
80 static gint ett_ccp_options = -1;
81 static gint ett_ccp_stac_opt = -1;
82 static gint ett_ccp_mppc_opt = -1;
83 static gint ett_ccp_bsdcomp_opt = -1;
84 static gint ett_ccp_lzsdcp_opt = -1;
85 static gint ett_ccp_mvrca_opt = -1;
86 static gint ett_ccp_deflate_opt = -1;
88 static int proto_cbcp = -1;
90 static gint ett_cbcp = -1;
91 static gint ett_cbcp_options = -1;
92 static gint ett_cbcp_callback_opt = -1;
93 static gint ett_cbcp_callback_opt_addr = -1;
95 static int proto_bacp = -1;
97 static gint ett_bacp = -1;
98 static gint ett_bacp_options = -1;
99 static gint ett_bacp_favored_peer_opt = -1;
101 static int proto_bap = -1;
103 static gint ett_bap = -1;
104 static gint ett_bap_options = -1;
105 static gint ett_bap_link_type_opt = -1;
106 static gint ett_bap_phone_delta_opt = -1;
107 static gint ett_bap_phone_delta_subopt = -1;
108 static gint ett_bap_call_status_opt = -1;
110 static int proto_comp_data = -1;
112 static gint ett_comp_data = -1;
114 static int proto_pppmuxcp = -1;
116 static gint ett_pppmuxcp = -1;
117 static gint ett_pppmuxcp_options = -1;
119 static int proto_pppmux = -1;
121 static gint ett_pppmux = -1;
122 static gint ett_pppmux_subframe = -1;
123 static gint ett_pppmux_subframe_hdr = -1;
124 static gint ett_pppmux_subframe_flags = -1;
125 static gint ett_pppmux_subframe_info = -1;
127 static int proto_mp = -1;
128 static int hf_mp_frag_first = -1;
129 static int hf_mp_frag_last = -1;
130 static int hf_mp_sequence_num = -1;
132 static int ett_mp = -1;
133 static int ett_mp_flags = -1;
135 static int proto_pap = -1; /* PAP vars */
136 static gint ett_pap = -1;
137 static gint ett_pap_data = -1;
138 static gint ett_pap_peer_id = -1;
139 static gint ett_pap_password = -1;
140 static gint ett_pap_message = -1;
142 static int proto_chap = -1; /* CHAP vars */
143 static gint ett_chap = -1;
144 static gint ett_chap_data = -1;
145 static gint ett_chap_value = -1;
146 static gint ett_chap_name = -1;
147 static gint ett_chap_message = -1;
149 static dissector_table_t subdissector_table;
150 static dissector_handle_t chdlc_handle;
151 static dissector_handle_t data_handle;
154 static gint ppp_fcs_decode = 0; /* 0 = No FCS, 1 = 16 bit FCS, 2 = 32 bit FCS */
158 gboolean ppp_vj_decomp = TRUE; /* Default to VJ header decompression */
161 * For Default Protocol ID negotiated with PPPMuxCP. We need to
162 * this ID so that if the first subframe doesn't have protocol
166 static guint pppmux_def_prot_id = 0;
168 /* PPP definitions */
170 static const value_string ppp_vals[] = {
173 {PPP_AT, "Appletalk" },
174 {PPP_IPX, "Netware IPX/SPX"},
175 {PPP_VJC_COMP, "VJ compressed TCP"},
176 {PPP_VJC_UNCOMP,"VJ uncompressed TCP"},
177 {PPP_BPDU, "Bridging PDU"},
178 {PPP_VINES, "Vines" },
179 {PPP_MP, "Multilink"},
181 {PPP_MUX, "PPP Multiplexing"},
182 {PPP_COMP, "compressed packet" },
183 {PPP_DEC_LB, "DEC LANBridge100 Spanning Tree"},
184 {PPP_MPLS_UNI, "MPLS Unicast"},
185 {PPP_MPLS_MULTI, "MPLS Multicast"},
186 {PPP_IPCP, "IP Control Protocol" },
187 {PPP_OSICP, "OSI Control Protocol" },
188 {PPP_ATCP, "AppleTalk Control Protocol" },
189 {PPP_IPXCP, "IPX Control Protocol" },
190 {PPP_MUXCP, "PPPMux Control Protocol"},
191 {PPP_CCP, "Compression Control Protocol" },
192 {PPP_LCP, "Link Control Protocol" },
193 {PPP_PAP, "Password Authentication Protocol" },
194 {PPP_LQR, "Link Quality Report protocol" },
195 {PPP_SPAP, "Shiva Password Authentication Protocol" },
196 {PPP_CHAP, "Cryptographic Handshake Auth. Protocol" },
197 {PPP_EAP, "Extensible Authentication Protocol" },
198 {PPP_CBCP, "Callback Control Protocol" },
199 {PPP_BACP, "Bandwidth Allocation Control Protocol" },
200 {PPP_BAP, "Bandwitdh Allocation Protocol" },
204 /* CP (LCP, IPCP, etc.) codes.
207 #define CONFREQ 1 /* Configuration Request */
208 #define CONFACK 2 /* Configuration Ack */
209 #define CONFNAK 3 /* Configuration Nak */
210 #define CONFREJ 4 /* Configuration Reject */
211 #define TERMREQ 5 /* Termination Request */
212 #define TERMACK 6 /* Termination Ack */
213 #define CODEREJ 7 /* Code Reject */
215 static const value_string cp_vals[] = {
216 {CONFREQ, "Configuration Request" },
217 {CONFACK, "Configuration Ack" },
218 {CONFNAK, "Configuration Nak" },
219 {CONFREJ, "Configuration Reject" },
220 {TERMREQ, "Termination Request" },
221 {TERMACK, "Termination Ack" },
222 {CODEREJ, "Code Reject" },
226 * LCP-specific packet types.
228 #define PROTREJ 8 /* Protocol Reject */
229 #define ECHOREQ 9 /* Echo Request */
230 #define ECHOREP 10 /* Echo Reply */
231 #define DISCREQ 11 /* Discard Request */
232 #define IDENT 12 /* Identification */
233 #define TIMEREMAIN 13 /* Time remaining */
236 * CCP-specific packet types.
238 #define RESETREQ 14 /* Reset Request */
239 #define RESETACK 15 /* Reset Ack */
242 * CBCP-specific packet types.
244 #define CBREQ 1 /* Callback Request */
245 #define CBRES 2 /* Callback Response */
246 #define CBACK 3 /* Callback Ack */
248 #define CBCP_OPT 6 /* Use callback control protocol */
251 * BAP-specific packet types.
253 #define BAP_CREQ 1 /* Call Request */
254 #define BAP_CRES 2 /* Call Response */
255 #define BAP_CBREQ 3 /* Callback Request */
256 #define BAP_CBRES 4 /* Callback Response */
257 #define BAP_LDQREQ 5 /* Link Drop Query Request */
258 #define BAP_LDQRES 6 /* Link Drop Query Response */
259 #define BAP_CSI 7 /* Call Status Indication */
260 #define BAP_CSRES 8 /* Call Status Response */
262 static const value_string lcp_vals[] = {
263 {CONFREQ, "Configuration Request" },
264 {CONFACK, "Configuration Ack" },
265 {CONFNAK, "Configuration Nak" },
266 {CONFREJ, "Configuration Reject" },
267 {TERMREQ, "Termination Request" },
268 {TERMACK, "Termination Ack" },
269 {CODEREJ, "Code Reject" },
270 {PROTREJ, "Protocol Reject" },
271 {ECHOREQ, "Echo Request" },
272 {ECHOREP, "Echo Reply" },
273 {DISCREQ, "Discard Request" },
274 {IDENT, "Identification" },
275 {TIMEREMAIN, "Time Remaining" },
279 static const value_string ccp_vals[] = {
280 {CONFREQ, "Configuration Request" },
281 {CONFACK, "Configuration Ack" },
282 {CONFNAK, "Configuration Nak" },
283 {CONFREJ, "Configuration Reject" },
284 {TERMREQ, "Termination Request" },
285 {TERMACK, "Termination Ack" },
286 {CODEREJ, "Code Reject" },
287 {RESETREQ, "Reset Request" },
288 {RESETACK, "Reset Ack" },
292 static const value_string cbcp_vals[] = {
293 {CBREQ, "Callback Request" },
294 {CBRES, "Callback Response" },
295 {CBACK, "Callback Ack" },
299 static const value_string bap_vals[] = {
300 {BAP_CREQ, "Call Request" },
301 {BAP_CRES, "Call Response" },
302 {BAP_CBREQ, "Callback Request" },
303 {BAP_CBRES, "Callback Response" },
304 {BAP_LDQREQ, "Link Drop Query Request" },
305 {BAP_LDQRES, "Link Drop Query Response" },
306 {BAP_CSI, "Call Status Indication" },
307 {BAP_CSRES, "Call Status Response" },
311 #define BAP_RESP_CODE_REQACK 0x00
312 #define BAP_RESP_CODE_REQNAK 0x01
313 #define BAP_RESP_CODE_REQREJ 0x02
314 #define BAP_RESP_CODE_REQFULLNAK 0x03
315 static const value_string bap_resp_code_vals[] = {
316 {BAP_RESP_CODE_REQACK, "Request Ack" },
317 {BAP_RESP_CODE_REQNAK, "Request Nak" },
318 {BAP_RESP_CODE_REQREJ, "Request Rej" },
319 {BAP_RESP_CODE_REQFULLNAK, "Request Full Nak" },
323 #define BAP_LINK_TYPE_ISDN 0 /* ISDN */
324 #define BAP_LINK_TYPE_X25 1 /* X.25 */
325 #define BAP_LINK_TYPE_ANALOG 2 /* Analog */
326 #define BAP_LINK_TYPE_SD 3 /* Switched Digital (non-ISDN) */
327 #define BAP_LINK_TYPE_ISDNOV 4 /* ISDN data over voice */
328 #define BAP_LINK_TYPE_RESV5 5 /* Reserved */
329 #define BAP_LINK_TYPE_RESV6 6 /* Reserved */
330 #define BAP_LINK_TYPE_RESV7 7 /* Reserved */
331 static const value_string bap_link_type_vals[] = {
332 {BAP_LINK_TYPE_ISDN, "ISDN" },
333 {BAP_LINK_TYPE_X25, "X.25" },
334 {BAP_LINK_TYPE_ANALOG, "Analog" },
335 {BAP_LINK_TYPE_SD, "Switched Digital (non-ISDN)" },
336 {BAP_LINK_TYPE_ISDNOV, "ISDN data over voice" },
337 {BAP_LINK_TYPE_RESV5, "Reserved" },
338 {BAP_LINK_TYPE_RESV6, "Reserved" },
339 {BAP_LINK_TYPE_RESV7, "Reserved" },
343 #define BAP_PHONE_DELTA_SUBOPT_UNIQ_DIGIT 1 /* Unique Digit */
344 #define BAP_PHONE_DELTA_SUBOPT_SUBSC_NUM 2 /* Subscriber Number */
345 #define BAP_PHONE_DELTA_SUBOPT_PHONENUM_SUBADDR 3 /* Phone Number Sub Address */
346 static const value_string bap_phone_delta_subopt_vals[] = {
347 {BAP_PHONE_DELTA_SUBOPT_UNIQ_DIGIT, "Unique Digit" },
348 {BAP_PHONE_DELTA_SUBOPT_SUBSC_NUM, "Subscriber Number" },
349 {BAP_PHONE_DELTA_SUBOPT_PHONENUM_SUBADDR, "Phone Number Sub Address" },
354 * Cause codes for Cause.
356 * The following code table is taken from packet-q931.c but is slightly
357 * adapted to BAP protocol.
359 static const value_string q931_cause_code_vals[] = {
360 { 0x00, "Call successful" },
361 { 0x01, "Unallocated (unassigned) number" },
362 { 0x02, "No route to specified transit network" },
363 { 0x03, "No route to destination" },
364 { 0x04, "Send special information tone" },
365 { 0x05, "Misdialled trunk prefix" },
366 { 0x06, "Channel unacceptable" },
367 { 0x07, "Call awarded and being delivered in an established channel" },
368 { 0x08, "Prefix 0 dialed but not allowed" },
369 { 0x09, "Prefix 1 dialed but not allowed" },
370 { 0x0A, "Prefix 1 dialed but not required" },
371 { 0x0B, "More digits received than allowed, call is proceeding" },
372 { 0x10, "Normal call clearing" },
373 { 0x11, "User busy" },
374 { 0x12, "No user responding" },
375 { 0x13, "No answer from user (user alerted)" },
376 { 0x14, "Subscriber absent" },
377 { 0x15, "Call rejected" },
378 { 0x16, "Number changed" },
379 { 0x17, "Reverse charging rejected" },
380 { 0x18, "Call suspended" },
381 { 0x19, "Call resumed" },
382 { 0x1A, "Non-selected user clearing" },
383 { 0x1B, "Destination out of order" },
384 { 0x1C, "Invalid number format (incomplete number)" },
385 { 0x1D, "Facility rejected" },
386 { 0x1E, "Response to STATUS ENQUIRY" },
387 { 0x1F, "Normal unspecified" },
388 { 0x21, "Circuit out of order" },
389 { 0x22, "No circuit/channel available" },
390 { 0x23, "Destination unattainable" },
391 { 0x25, "Degraded service" },
392 { 0x26, "Network out of order" },
393 { 0x27, "Transit delay range cannot be achieved" },
394 { 0x28, "Throughput range cannot be achieved" },
395 { 0x29, "Temporary failure" },
396 { 0x2A, "Switching equipment congestion" },
397 { 0x2B, "Access information discarded" },
398 { 0x2C, "Requested circuit/channel not available" },
399 { 0x2D, "Pre-empted" },
400 { 0x2E, "Precedence call blocked" },
401 { 0x2F, "Resources unavailable, unspecified" },
402 { 0x31, "Quality of service unavailable" },
403 { 0x32, "Requested facility not subscribed" },
404 { 0x33, "Reverse charging not allowed" },
405 { 0x34, "Outgoing calls barred" },
406 { 0x35, "Outgoing calls barred within CUG" },
407 { 0x36, "Incoming calls barred" },
408 { 0x37, "Incoming calls barred within CUG" },
409 { 0x38, "Call waiting not subscribed" },
410 { 0x39, "Bearer capability not authorized" },
411 { 0x3A, "Bearer capability not presently available" },
412 { 0x3E, "Inconsistency in designated outgoing access information and subscriber class" },
413 { 0x3F, "Service or option not available, unspecified" },
414 { 0x41, "Bearer capability not implemented" },
415 { 0x42, "Channel type not implemented" },
416 { 0x43, "Transit network selection not implemented" },
417 { 0x44, "Message not implemented" },
418 { 0x45, "Requested facility not implemented" },
419 { 0x46, "Only restricted digital information bearer capability is available" },
420 { 0x4F, "Service or option not implemented, unspecified" },
421 { 0x51, "Invalid call reference value" },
422 { 0x52, "Identified channel does not exist" },
423 { 0x53, "Call identity does not exist for suspended call" },
424 { 0x54, "Call identity in use" },
425 { 0x55, "No call suspended" },
426 { 0x56, "Call having the requested call identity has been cleared" },
427 { 0x57, "Called user not member of CUG" },
428 { 0x58, "Incompatible destination" },
429 { 0x59, "Non-existent abbreviated address entry" },
430 { 0x5A, "Destination address missing, and direct call not subscribed" },
431 { 0x5B, "Invalid transit network selection (national use)" },
432 { 0x5C, "Invalid facility parameter" },
433 { 0x5D, "Mandatory information element is missing" },
434 { 0x5F, "Invalid message, unspecified" },
435 { 0x60, "Mandatory information element is missing" },
436 { 0x61, "Message type non-existent or not implemented" },
437 { 0x62, "Message not compatible with call state or message type non-existent or not implemented" },
438 { 0x63, "Information element nonexistant or not implemented" },
439 { 0x64, "Invalid information element contents" },
440 { 0x65, "Message not compatible with call state" },
441 { 0x66, "Recovery on timer expiry" },
442 { 0x67, "Parameter non-existent or not implemented - passed on" },
443 { 0x6E, "Message with unrecognized parameter discarded" },
444 { 0x6F, "Protocol error, unspecified" },
445 { 0x7F, "Internetworking, unspecified" },
446 { 0xFF, "Non-specific failure" },
450 static const value_string bap_call_status_opt_action_vals[] = {
456 #define STAC_CM_NONE 0
457 #define STAC_CM_LCB 1
458 #define STAC_CM_CRC 2
460 #define STAC_CM_EXTMODE 4
461 static const value_string stac_checkmode_vals[] = {
462 {STAC_CM_NONE, "None" },
463 {STAC_CM_LCB, "LCB" },
464 {STAC_CM_CRC, "CRC" },
465 {STAC_CM_SN, "Sequence Number" },
466 {STAC_CM_EXTMODE, "Extended Mode" },
470 #define LZSDCP_CM_NONE 0
471 #define LZSDCP_CM_LCB 1
472 #define LZSDCP_CM_SN 2
473 #define LZSDCP_CM_SN_LCB 3
474 static const value_string lzsdcp_checkmode_vals[] = {
475 {LZSDCP_CM_NONE, "None" },
476 {LZSDCP_CM_LCB, "LCB" },
477 {LZSDCP_CM_SN, "Sequence Number" },
478 {LZSDCP_CM_SN_LCB, "Sequence Number + LCB" },
482 #define LZSDCP_PM_NONE 0
483 #define LZSDCP_PM_PROC_UNCOMP 1
484 static const value_string lzsdcp_processmode_vals[] = {
485 {LZSDCP_PM_NONE, "None" },
486 {LZSDCP_PM_PROC_UNCOMP, "Process-Uncompressed" },
493 #define CI_MRU 1 /* Maximum Receive Unit */
494 #define CI_ASYNCMAP 2 /* Async Control Character Map */
495 #define CI_AUTHTYPE 3 /* Authentication Type */
496 #define CI_QUALITY 4 /* Quality Protocol */
497 #define CI_MAGICNUMBER 5 /* Magic Number */
498 #define CI_PCOMPRESSION 7 /* Protocol Field Compression */
499 #define CI_ACCOMPRESSION 8 /* Address/Control Field Compression */
500 #define CI_FCS_ALTERNATIVES 9 /* FCS Alternatives (RFC 1570) */
501 #define CI_SELF_DESCRIBING_PAD 10 /* Self-Describing Pad (RFC 1570) */
502 #define CI_NUMBERED_MODE 11 /* Numbered Mode (RFC 1663) */
503 #define CI_CALLBACK 13 /* Callback (RFC 1570) */
504 #define CI_COMPOUND_FRAMES 15 /* Compound frames (RFC 1570) */
505 #define CI_MULTILINK_MRRU 17 /* Multilink MRRU (RFC 1717) */
506 #define CI_MULTILINK_SSNH 18 /* Multilink Short Sequence Number
508 #define CI_MULTILINK_EP_DISC 19 /* Multilink Endpoint Discriminator
510 #define CI_DCE_IDENTIFIER 21 /* DCE Identifier */
511 #define CI_MULTILINK_PLUS_PROC 22 /* Multilink Plus Procedure */
512 #define CI_LINK_DISC_FOR_BACP 23 /* Link Discriminator for BACP
514 #define CI_LCP_AUTHENTICATION 24 /* LCP Authentication Option */
515 #define CI_COBS 25 /* Consistent Overhead Byte
517 #define CI_PREFIX_ELISION 26 /* Prefix elision */
518 #define CI_MULTILINK_HDR_FMT 27 /* Multilink header format */
519 #define CI_INTERNATIONALIZATION 28 /* Internationalization (RFC 2484) */
520 #define CI_SDL_ON_SONET_SDH 29 /* Simple Data Link on SONET/SDH */
522 static void dissect_lcp_mru_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
523 int offset, guint length, packet_info *pinfo,
525 static void dissect_lcp_async_map_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
526 int offset, guint length, packet_info *pinfo,
528 static void dissect_lcp_protocol_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
529 int offset, guint length, packet_info *pinfo,
531 static void dissect_lcp_authprot_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
532 int offset, guint length, packet_info *pinfo,
534 static void dissect_lcp_magicnumber_opt(const ip_tcp_opt *optp,
535 tvbuff_t *tvb, int offset, guint length,
536 packet_info *pinfo, proto_tree *tree);
537 static void dissect_lcp_fcs_alternatives_opt(const ip_tcp_opt *optp,
538 tvbuff_t *tvb, int offset, guint length,
539 packet_info *pinfo, proto_tree *tree);
540 static void dissect_lcp_numbered_mode_opt(const ip_tcp_opt *optp,
541 tvbuff_t *tvb, int offset, guint length,
542 packet_info *pinfo, proto_tree *tree);
543 static void dissect_lcp_self_describing_pad_opt(const ip_tcp_opt *optp,
544 tvbuff_t *tvb, int offset, guint length,
545 packet_info *pinfo, proto_tree *tree);
546 static void dissect_lcp_callback_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
547 int offset, guint length, packet_info *pinfo,
549 static void dissect_lcp_multilink_mrru_opt(const ip_tcp_opt *optp,
550 tvbuff_t *tvb, int offset, guint length,
551 packet_info *pinfo, proto_tree *tree);
552 static void dissect_lcp_multilink_ep_disc_opt(const ip_tcp_opt *optp,
553 tvbuff_t *tvb, int offset, guint length,
554 packet_info *pinfo, proto_tree *tree);
555 static void dissect_lcp_bap_link_discriminator_opt(const ip_tcp_opt *optp,
556 tvbuff_t *tvb, int offset, guint length,
557 packet_info *pinfo, proto_tree *tree);
558 static void dissect_lcp_internationalization_opt(const ip_tcp_opt *optp,
559 tvbuff_t *tvb, int offset, guint length,
560 packet_info *pinfo, proto_tree *tree);
561 static void dissect_mp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree);
563 static const ip_tcp_opt lcp_opts[] = {
566 "Maximum Receive Unit",
574 "Async Control Character Map",
578 dissect_lcp_async_map_opt
582 "Authentication protocol",
583 &ett_lcp_authprot_opt,
586 dissect_lcp_authprot_opt
591 &ett_lcp_qualprot_opt,
594 dissect_lcp_protocol_opt
602 dissect_lcp_magicnumber_opt
606 "Protocol field compression",
614 "Address/control field compression",
623 &ett_lcp_fcs_alternatives_opt,
626 dissect_lcp_fcs_alternatives_opt
629 CI_SELF_DESCRIBING_PAD,
630 "Maximum octets of self-describing padding",
634 dissect_lcp_self_describing_pad_opt
639 &ett_lcp_numbered_mode_opt,
642 dissect_lcp_numbered_mode_opt
647 &ett_lcp_callback_opt,
650 dissect_lcp_callback_opt,
666 dissect_lcp_multilink_mrru_opt
670 "Use short sequence number headers",
677 CI_MULTILINK_EP_DISC,
678 "Multilink endpoint discriminator",
679 &ett_lcp_multilink_ep_disc_opt,
682 dissect_lcp_multilink_ep_disc_opt,
693 CI_MULTILINK_PLUS_PROC,
694 "Multilink Plus Procedure",
701 CI_LINK_DISC_FOR_BACP,
702 "Link discriminator for BAP",
706 dissect_lcp_bap_link_discriminator_opt
709 CI_LCP_AUTHENTICATION,
710 "LCP authentication",
718 "Consistent Overhead Byte Stuffing",
733 CI_MULTILINK_HDR_FMT,
734 "Multilink header format",
741 CI_INTERNATIONALIZATION,
742 "Internationalization",
743 &ett_lcp_internationalization_opt,
746 dissect_lcp_internationalization_opt
750 "Simple data link on SONET/SDH",
758 #define N_LCP_OPTS (sizeof lcp_opts / sizeof lcp_opts[0])
763 #define CHAP_ALG_MD5 0x05 /* CHAP with MD5 */
764 #define CHAP_ALG_MSV1 0x80 /* MS-CHAPv1 */
765 #define CHAP_ALG_MSV2 0x81 /* MS-CHAPv2 */
767 static const value_string chap_alg_vals[] = {
768 {CHAP_ALG_MD5, "CHAP with MD5" },
769 {CHAP_ALG_MSV1, "MS-CHAP" },
770 {CHAP_ALG_MSV2, "MS-CHAP-2" },
778 #define CI_ADDRS 1 /* IP Addresses (deprecated) (RFC 1172) */
779 #define CI_COMPRESSTYPE 2 /* Compression Type (RFC 1332) */
780 #define CI_ADDR 3 /* IP Address (RFC 1332) */
781 #define CI_MOBILE_IPv4 4 /* Mobile IPv4 (RFC 2290) */
782 #define CI_MS_DNS1 129 /* Primary DNS value (RFC 1877) */
783 #define CI_MS_WINS1 130 /* Primary WINS value (RFC 1877) */
784 #define CI_MS_DNS2 131 /* Secondary DNS value (RFC 1877) */
785 #define CI_MS_WINS2 132 /* Secondary WINS value (RFC 1877) */
787 static void dissect_ipcp_addrs_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
788 int offset, guint length, packet_info *pinfo,
790 static void dissect_ipcp_addr_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
791 int offset, guint length, packet_info *pinfo,
794 static const ip_tcp_opt ipcp_opts[] = {
797 "IP addresses (deprecated)",
798 &ett_ipcp_ipaddrs_opt,
801 dissect_ipcp_addrs_opt
805 "IP compression protocol",
806 &ett_ipcp_compressprot_opt,
809 dissect_lcp_protocol_opt
817 dissect_ipcp_addr_opt
821 "Mobile node's home IP address",
825 dissect_ipcp_addr_opt
829 "Primary DNS server IP address",
833 dissect_ipcp_addr_opt
837 "Primary WINS server IP address",
841 dissect_ipcp_addr_opt
845 "Secondary DNS server IP address",
849 dissect_ipcp_addr_opt
853 "Secondary WINS server IP address",
857 dissect_ipcp_addr_opt
861 #define N_IPCP_OPTS (sizeof ipcp_opts / sizeof ipcp_opts[0])
866 #define CI_CCP_OUI 0 /* OUI (RFC1962) */
867 #define CI_CCP_PREDICT1 1 /* Predictor type 1 (RFC1962) */
868 #define CI_CCP_PREDICT2 2 /* Predictor type 2 (RFC1962) */
869 #define CI_CCP_PUDDLE 3 /* Puddle Jumper (RFC1962) */
870 #define CI_CCP_HPPPC 16 /* Hewlett-Packard PPC (RFC1962) */
871 #define CI_CCP_STAC 17 /* stac Electronics LZS (RFC1974) */
872 #define CI_CCP_MPPC 18 /* Microsoft PPC (RFC2218/3078) */
873 #define CI_CCP_GFZA 19 /* Gandalf FZA (RFC1962) */
874 #define CI_CCP_V42BIS 20 /* V.42bis compression */
875 #define CI_CCP_BSDLZW 21 /* BSD LZW Compress (RFC1977) */
876 #define CI_CCP_LZSDCP 23 /* LZS-DCP (RFC1967) */
877 #define CI_CCP_MVRCA 24 /* MVRCA (Magnalink) (RFC1975) */
878 #define CI_CCP_DEFLATE 26 /* Deflate (RFC1979) */
879 #define CI_CCP_RESERVED 255 /* Reserved (RFC1962) */
882 * Microsoft Point-To-Point Compression (MPPC) and Encryption (MPPE)
885 #define MPPC_SUPPORTED_BITS_C 0x00000001 /* MPPC negotiation */
886 #define MPPE_SUPPORTED_BITS_D 0x00000010 /* Obsolete */
887 #define MPPE_SUPPORTED_BITS_L 0x00000020 /* 40-bit encryption */
888 #define MPPE_SUPPORTED_BITS_S 0x00000040 /* 128-bit encryption */
889 #define MPPE_SUPPORTED_BITS_M 0x00000080 /* 56-bit encryption */
890 #define MPPE_SUPPORTED_BITS_H 0x01000000 /* stateless mode */
892 static void dissect_ccp_stac_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
893 int offset, guint length, packet_info *pinfo,
896 static void dissect_ccp_mppc_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
897 int offset, guint length, packet_info *pinfo,
900 static void dissect_ccp_bsdcomp_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
901 int offset, guint length, packet_info *pinfo,
904 static void dissect_ccp_lzsdcp_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
905 int offset, guint length, packet_info *pinfo,
908 static void dissect_ccp_mvrca_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
909 int offset, guint length, packet_info *pinfo,
912 static void dissect_ccp_deflate_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
913 int offset, guint length, packet_info *pinfo,
916 static const ip_tcp_opt ccp_opts[] = {
919 "Stac Electronics LZS",
923 /* In RFC 1974, this is a fixed-length field of size 5,
924 but in Ascend Proprietary STAC compression this field
925 is 6 octets. Sigh... */
939 &ett_ccp_bsdcomp_opt,
942 dissect_ccp_bsdcomp_opt
950 dissect_ccp_lzsdcp_opt
958 dissect_ccp_mvrca_opt
963 &ett_ccp_deflate_opt,
965 4, /* RFC1979 says the length is 3 but it's actually 4. */
966 dissect_ccp_deflate_opt
970 #define N_CCP_OPTS (sizeof ccp_opts / sizeof ccp_opts[0])
975 #define CI_CBCP_NO_CALLBACK 1 /* No callback */
976 #define CI_CBCP_CB_USER 2 /* Callback to a user-specified number */
977 #define CI_CBCP_CB_PRE 3 /* Callback to a pre-specified or
978 administrator specified number */
979 #define CI_CBCP_CB_ANY 4 /* Callback to any of a list of numbers */
981 static void dissect_cbcp_no_callback_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
982 int offset, guint length, packet_info *pinfo,
985 static void dissect_cbcp_callback_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
986 int offset, guint length, packet_info *pinfo,
989 static const ip_tcp_opt cbcp_opts[] = {
996 dissect_cbcp_no_callback_opt
1000 "Callback to a user-specified number",
1001 &ett_cbcp_callback_opt,
1004 dissect_cbcp_callback_opt
1008 "Callback to a pre-specified or admin-specified number",
1009 &ett_cbcp_callback_opt,
1012 dissect_cbcp_callback_opt
1016 "Callback to any of a list of numbers",
1017 &ett_cbcp_callback_opt,
1020 dissect_cbcp_callback_opt
1025 #define N_CBCP_OPTS (sizeof cbcp_opts / sizeof cbcp_opts[0])
1030 #define CI_BACP_FAVORED_PEER 1 /* Favored-Peer */
1032 static void dissect_bacp_favored_peer_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1033 int offset, guint length, packet_info *pinfo,
1036 static const ip_tcp_opt bacp_opts[] = {
1038 CI_BACP_FAVORED_PEER,
1040 &ett_bacp_favored_peer_opt,
1043 dissect_bacp_favored_peer_opt
1047 #define N_BACP_OPTS (sizeof bacp_opts / sizeof bacp_opts[0])
1052 #define CI_BAP_LINK_TYPE 1 /* Link Type */
1053 #define CI_BAP_PHONE_DELTA 2 /* Phone-Delta */
1054 #define CI_BAP_NO_PHONE_NUM_NEEDED 3 /* No Phone Number Needed */
1055 #define CI_BAP_REASON 4 /* Reason */
1056 #define CI_BAP_LINK_DISC 5 /* Link Discriminator */
1057 #define CI_BAP_CALL_STATUS 6 /* Call Status */
1059 static void dissect_bap_link_type_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1060 int offset, guint length, packet_info *pinfo,
1063 static void dissect_bap_phone_delta_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1064 int offset, guint length, packet_info *pinfo,
1067 static void dissect_bap_link_disc_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1068 int offset, guint length, packet_info *pinfo,
1071 static void dissect_bap_reason_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1072 int offset, guint length, packet_info *pinfo,
1075 static void dissect_bap_call_status_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1076 int offset, guint length, packet_info *pinfo,
1079 static const ip_tcp_opt bap_opts[] = {
1083 &ett_bap_link_type_opt,
1086 dissect_bap_link_type_opt
1091 &ett_bap_phone_delta_opt,
1094 dissect_bap_phone_delta_opt
1097 CI_BAP_NO_PHONE_NUM_NEEDED,
1098 "No Phone Number Needed",
1110 dissect_bap_reason_opt
1114 "Link Discriminator",
1118 dissect_bap_link_disc_opt
1123 &ett_bap_call_status_opt,
1126 dissect_bap_call_status_opt
1130 #define N_BAP_OPTS (sizeof bap_opts / sizeof bap_opts[0])
1132 static void dissect_ppp(tvbuff_t *tvb, packet_info *pinfo,
1135 static const value_string pap_vals[] = {
1136 {CONFREQ, "Authenticate-Request" },
1137 {CONFACK, "Authenticate-Ack" },
1138 {CONFNAK, "Authenticate-Nak" },
1141 static void dissect_pap(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree);
1143 #define CHAP_CHAL 1 /* CHAP Challenge */
1144 #define CHAP_RESP 2 /* CHAP Response */
1145 #define CHAP_SUCC 3 /* CHAP Success */
1146 #define CHAP_FAIL 4 /* CHAP Failure */
1148 static const value_string chap_vals[] = {
1149 {CHAP_CHAL, "Challenge" },
1150 {CHAP_RESP, "Response" },
1151 {CHAP_SUCC, "Success" },
1152 {CHAP_FAIL, "Failure" },
1155 static void dissect_chap(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree);
1157 static const value_string pppmuxcp_vals[] = {
1158 {CONFREQ, "Configuration Request" },
1159 {CONFACK, "Configuration Ack" },
1167 #define CI_DEFAULT_PID 1
1169 static void dissect_pppmuxcp_def_pid_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1170 int offset, guint length, packet_info *pinfo, proto_tree *tree);
1173 static const ip_tcp_opt pppmuxcp_opts[] = {
1176 "Default Protocol ID",
1180 dissect_pppmuxcp_def_pid_opt
1184 #define N_PPPMUXCP_OPTS (sizeof pppmuxcp_opts / sizeof pppmuxcp_opts[0])
1186 static const unsigned int fcstab_32[256] =
1188 0x00000000, 0x77073096, 0xee0e612c, 0x990951ba,
1189 0x076dc419, 0x706af48f, 0xe963a535, 0x9e6495a3,
1190 0x0edb8832, 0x79dcb8a4, 0xe0d5e91e, 0x97d2d988,
1191 0x09b64c2b, 0x7eb17cbd, 0xe7b82d07, 0x90bf1d91,
1192 0x1db71064, 0x6ab020f2, 0xf3b97148, 0x84be41de,
1193 0x1adad47d, 0x6ddde4eb, 0xf4d4b551, 0x83d385c7,
1194 0x136c9856, 0x646ba8c0, 0xfd62f97a, 0x8a65c9ec,
1195 0x14015c4f, 0x63066cd9, 0xfa0f3d63, 0x8d080df5,
1196 0x3b6e20c8, 0x4c69105e, 0xd56041e4, 0xa2677172,
1197 0x3c03e4d1, 0x4b04d447, 0xd20d85fd, 0xa50ab56b,
1198 0x35b5a8fa, 0x42b2986c, 0xdbbbc9d6, 0xacbcf940,
1199 0x32d86ce3, 0x45df5c75, 0xdcd60dcf, 0xabd13d59,
1200 0x26d930ac, 0x51de003a, 0xc8d75180, 0xbfd06116,
1201 0x21b4f4b5, 0x56b3c423, 0xcfba9599, 0xb8bda50f,
1202 0x2802b89e, 0x5f058808, 0xc60cd9b2, 0xb10be924,
1203 0x2f6f7c87, 0x58684c11, 0xc1611dab, 0xb6662d3d,
1204 0x76dc4190, 0x01db7106, 0x98d220bc, 0xefd5102a,
1205 0x71b18589, 0x06b6b51f, 0x9fbfe4a5, 0xe8b8d433,
1206 0x7807c9a2, 0x0f00f934, 0x9609a88e, 0xe10e9818,
1207 0x7f6a0dbb, 0x086d3d2d, 0x91646c97, 0xe6635c01,
1208 0x6b6b51f4, 0x1c6c6162, 0x856530d8, 0xf262004e,
1209 0x6c0695ed, 0x1b01a57b, 0x8208f4c1, 0xf50fc457,
1210 0x65b0d9c6, 0x12b7e950, 0x8bbeb8ea, 0xfcb9887c,
1211 0x62dd1ddf, 0x15da2d49, 0x8cd37cf3, 0xfbd44c65,
1212 0x4db26158, 0x3ab551ce, 0xa3bc0074, 0xd4bb30e2,
1213 0x4adfa541, 0x3dd895d7, 0xa4d1c46d, 0xd3d6f4fb,
1214 0x4369e96a, 0x346ed9fc, 0xad678846, 0xda60b8d0,
1215 0x44042d73, 0x33031de5, 0xaa0a4c5f, 0xdd0d7cc9,
1216 0x5005713c, 0x270241aa, 0xbe0b1010, 0xc90c2086,
1217 0x5768b525, 0x206f85b3, 0xb966d409, 0xce61e49f,
1218 0x5edef90e, 0x29d9c998, 0xb0d09822, 0xc7d7a8b4,
1219 0x59b33d17, 0x2eb40d81, 0xb7bd5c3b, 0xc0ba6cad,
1220 0xedb88320, 0x9abfb3b6, 0x03b6e20c, 0x74b1d29a,
1221 0xead54739, 0x9dd277af, 0x04db2615, 0x73dc1683,
1222 0xe3630b12, 0x94643b84, 0x0d6d6a3e, 0x7a6a5aa8,
1223 0xe40ecf0b, 0x9309ff9d, 0x0a00ae27, 0x7d079eb1,
1224 0xf00f9344, 0x8708a3d2, 0x1e01f268, 0x6906c2fe,
1225 0xf762575d, 0x806567cb, 0x196c3671, 0x6e6b06e7,
1226 0xfed41b76, 0x89d32be0, 0x10da7a5a, 0x67dd4acc,
1227 0xf9b9df6f, 0x8ebeeff9, 0x17b7be43, 0x60b08ed5,
1228 0xd6d6a3e8, 0xa1d1937e, 0x38d8c2c4, 0x4fdff252,
1229 0xd1bb67f1, 0xa6bc5767, 0x3fb506dd, 0x48b2364b,
1230 0xd80d2bda, 0xaf0a1b4c, 0x36034af6, 0x41047a60,
1231 0xdf60efc3, 0xa867df55, 0x316e8eef, 0x4669be79,
1232 0xcb61b38c, 0xbc66831a, 0x256fd2a0, 0x5268e236,
1233 0xcc0c7795, 0xbb0b4703, 0x220216b9, 0x5505262f,
1234 0xc5ba3bbe, 0xb2bd0b28, 0x2bb45a92, 0x5cb36a04,
1235 0xc2d7ffa7, 0xb5d0cf31, 0x2cd99e8b, 0x5bdeae1d,
1236 0x9b64c2b0, 0xec63f226, 0x756aa39c, 0x026d930a,
1237 0x9c0906a9, 0xeb0e363f, 0x72076785, 0x05005713,
1238 0x95bf4a82, 0xe2b87a14, 0x7bb12bae, 0x0cb61b38,
1239 0x92d28e9b, 0xe5d5be0d, 0x7cdcefb7, 0x0bdbdf21,
1240 0x86d3d2d4, 0xf1d4e242, 0x68ddb3f8, 0x1fda836e,
1241 0x81be16cd, 0xf6b9265b, 0x6fb077e1, 0x18b74777,
1242 0x88085ae6, 0xff0f6a70, 0x66063bca, 0x11010b5c,
1243 0x8f659eff, 0xf862ae69, 0x616bffd3, 0x166ccf45,
1244 0xa00ae278, 0xd70dd2ee, 0x4e048354, 0x3903b3c2,
1245 0xa7672661, 0xd06016f7, 0x4969474d, 0x3e6e77db,
1246 0xaed16a4a, 0xd9d65adc, 0x40df0b66, 0x37d83bf0,
1247 0xa9bcae53, 0xdebb9ec5, 0x47b2cf7f, 0x30b5ffe9,
1248 0xbdbdf21c, 0xcabac28a, 0x53b39330, 0x24b4a3a6,
1249 0xbad03605, 0xcdd70693, 0x54de5729, 0x23d967bf,
1250 0xb3667a2e, 0xc4614ab8, 0x5d681b02, 0x2a6f2b94,
1251 0xb40bbe37, 0xc30c8ea1, 0x5a05df1b, 0x2d02ef8d
1254 static const unsigned short fcstab_16[256] = {
1255 0x0000, 0x1189, 0x2312, 0x329b, 0x4624, 0x57ad, 0x6536, 0x74bf,
1256 0x8c48, 0x9dc1, 0xaf5a, 0xbed3, 0xca6c, 0xdbe5, 0xe97e, 0xf8f7,
1257 0x1081, 0x0108, 0x3393, 0x221a, 0x56a5, 0x472c, 0x75b7, 0x643e,
1258 0x9cc9, 0x8d40, 0xbfdb, 0xae52, 0xdaed, 0xcb64, 0xf9ff, 0xe876,
1259 0x2102, 0x308b, 0x0210, 0x1399, 0x6726, 0x76af, 0x4434, 0x55bd,
1260 0xad4a, 0xbcc3, 0x8e58, 0x9fd1, 0xeb6e, 0xfae7, 0xc87c, 0xd9f5,
1261 0x3183, 0x200a, 0x1291, 0x0318, 0x77a7, 0x662e, 0x54b5, 0x453c,
1262 0xbdcb, 0xac42, 0x9ed9, 0x8f50, 0xfbef, 0xea66, 0xd8fd, 0xc974,
1263 0x4204, 0x538d, 0x6116, 0x709f, 0x0420, 0x15a9, 0x2732, 0x36bb,
1264 0xce4c, 0xdfc5, 0xed5e, 0xfcd7, 0x8868, 0x99e1, 0xab7a, 0xbaf3,
1265 0x5285, 0x430c, 0x7197, 0x601e, 0x14a1, 0x0528, 0x37b3, 0x263a,
1266 0xdecd, 0xcf44, 0xfddf, 0xec56, 0x98e9, 0x8960, 0xbbfb, 0xaa72,
1267 0x6306, 0x728f, 0x4014, 0x519d, 0x2522, 0x34ab, 0x0630, 0x17b9,
1268 0xef4e, 0xfec7, 0xcc5c, 0xddd5, 0xa96a, 0xb8e3, 0x8a78, 0x9bf1,
1269 0x7387, 0x620e, 0x5095, 0x411c, 0x35a3, 0x242a, 0x16b1, 0x0738,
1270 0xffcf, 0xee46, 0xdcdd, 0xcd54, 0xb9eb, 0xa862, 0x9af9, 0x8b70,
1271 0x8408, 0x9581, 0xa71a, 0xb693, 0xc22c, 0xd3a5, 0xe13e, 0xf0b7,
1272 0x0840, 0x19c9, 0x2b52, 0x3adb, 0x4e64, 0x5fed, 0x6d76, 0x7cff,
1273 0x9489, 0x8500, 0xb79b, 0xa612, 0xd2ad, 0xc324, 0xf1bf, 0xe036,
1274 0x18c1, 0x0948, 0x3bd3, 0x2a5a, 0x5ee5, 0x4f6c, 0x7df7, 0x6c7e,
1275 0xa50a, 0xb483, 0x8618, 0x9791, 0xe32e, 0xf2a7, 0xc03c, 0xd1b5,
1276 0x2942, 0x38cb, 0x0a50, 0x1bd9, 0x6f66, 0x7eef, 0x4c74, 0x5dfd,
1277 0xb58b, 0xa402, 0x9699, 0x8710, 0xf3af, 0xe226, 0xd0bd, 0xc134,
1278 0x39c3, 0x284a, 0x1ad1, 0x0b58, 0x7fe7, 0x6e6e, 0x5cf5, 0x4d7c,
1279 0xc60c, 0xd785, 0xe51e, 0xf497, 0x8028, 0x91a1, 0xa33a, 0xb2b3,
1280 0x4a44, 0x5bcd, 0x6956, 0x78df, 0x0c60, 0x1de9, 0x2f72, 0x3efb,
1281 0xd68d, 0xc704, 0xf59f, 0xe416, 0x90a9, 0x8120, 0xb3bb, 0xa232,
1282 0x5ac5, 0x4b4c, 0x79d7, 0x685e, 0x1ce1, 0x0d68, 0x3ff3, 0x2e7a,
1283 0xe70e, 0xf687, 0xc41c, 0xd595, 0xa12a, 0xb0a3, 0x8238, 0x93b1,
1284 0x6b46, 0x7acf, 0x4854, 0x59dd, 0x2d62, 0x3ceb, 0x0e70, 0x1ff9,
1285 0xf78f, 0xe606, 0xd49d, 0xc514, 0xb1ab, 0xa022, 0x92b9, 0x8330,
1286 0x7bc7, 0x6a4e, 0x58d5, 0x495c, 0x3de3, 0x2c6a, 0x1ef1, 0x0f78
1290 *******************************************************************************
1291 * DETAILS : Calculate a new FCS-16 given the current FCS-16 and the new data.
1292 *******************************************************************************
1295 fcs16(register guint16 fcs,
1302 /* Check for Invalid Length */
1306 val = tvb_get_guint8(tvbuff, offset++);
1307 fcs = (guint16)((fcs >> 8) & 0x00ff) ^
1308 fcstab_16[((guint16)(fcs ^ (guint16)((val) & 0x00ff)) & 0x00ff)];
1311 return (fcs ^ 0xffff);
1315 *******************************************************************************
1316 * DETAILS : Calculate a new FCS-32 given the current FCS-32 and the new data.
1317 *******************************************************************************
1327 /* Check for invalid Length */
1329 return (0x00000000);
1332 val = tvb_get_guint8(tvbuff, offset++);
1333 fcs = (((fcs) >> 8) ^ fcstab_32[((fcs) ^ (val)) & 0xff]);
1335 return (fcs ^ 0xffffffff);
1339 capture_ppp_hdlc( const u_char *pd, int offset, int len, packet_counts *ld ) {
1340 if (!BYTES_ARE_IN_FRAME(offset, len, 2)) {
1344 if (pd[0] == CHDLC_ADDR_UNICAST || pd[0] == CHDLC_ADDR_MULTICAST) {
1345 capture_chdlc(pd, offset, len, ld);
1348 if (!BYTES_ARE_IN_FRAME(offset, len, 4)) {
1352 switch (pntohs(&pd[offset + 2])) {
1354 capture_ip(pd, offset + 4, len, ld);
1357 capture_ipx(pd, offset + 4, len, ld);
1360 capture_vines(pd, offset + 4, len, ld);
1369 dissect_lcp_mru_opt(const ip_tcp_opt *optp, tvbuff_t *tvb, int offset,
1370 guint length, packet_info *pinfo _U_,
1373 proto_tree_add_text(tree, tvb, offset, length, "%s: %u", optp->name,
1374 tvb_get_ntohs(tvb, offset + 2));
1378 dissect_lcp_async_map_opt(const ip_tcp_opt *optp, tvbuff_t *tvb, int offset,
1379 guint length, packet_info *pinfo _U_,
1384 static const char *ctrlchars[32] = {
1385 "NUL", "SOH", "STX", "ETX", "EOT", "ENQ", "ACK", "BEL",
1386 "BS", "HT", "NL", "VT", "NP (FF)", "CR", "SO", "SI",
1387 "DLE", "DC1 (XON)", "DC2", "DC3 (XOFF)", "DC4", "NAK", "SYN", "ETB",
1388 "CAN", "EM", "SUB", "ESC", "FS", "GS", "RS", "US"
1390 char mapbuf[32*(10+2)+1];
1395 * XXX - walk through the map and show the characters to map?
1396 * Put them in a subtree of this item, and have the top-level item
1397 * either say "None", "All", or give a list of the characters?)
1399 map = tvb_get_ntohl(tvb, offset + 2);
1400 if (map == 0x00000000)
1401 mapstr = "None"; /* don't map any control characters */
1402 else if (map == 0xffffffff)
1403 mapstr = "All"; /* map all control characters */
1406 * Show the names of the control characters being mapped.
1409 for (i = 0; i < 32; i++) {
1410 if (map & (1 << i)) {
1411 if (mapp != &mapbuf[0]) {
1415 strcpy(mapp, ctrlchars[i]);
1416 mapp += strlen(ctrlchars[i]);
1421 proto_tree_add_text(tree, tvb, offset, length, "%s: 0x%08x (%s)", optp->name,
1426 dissect_lcp_protocol_opt(const ip_tcp_opt *optp, tvbuff_t *tvb, int offset,
1427 guint length, packet_info *pinfo _U_,
1432 proto_tree *field_tree = NULL;
1434 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1435 optp->name, length, plurality(length, "", "s"));
1436 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1439 protocol = tvb_get_ntohs(tvb, offset);
1440 proto_tree_add_text(field_tree, tvb, offset, 2, "%s: %s (0x%02x)", optp->name,
1441 val_to_str(protocol, ppp_vals, "Unknown"), protocol);
1445 proto_tree_add_text(field_tree, tvb, offset, length, "Data (%d byte%s)", length,
1446 plurality(length, "", "s"));
1450 dissect_lcp_authprot_opt(const ip_tcp_opt *optp, tvbuff_t *tvb, int offset,
1451 guint length, packet_info *pinfo _U_,
1457 proto_tree *field_tree = NULL;
1459 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1460 optp->name, length, plurality(length, "", "s"));
1461 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1464 protocol = tvb_get_ntohs(tvb, offset);
1465 proto_tree_add_text(field_tree, tvb, offset, 2, "%s: %s (0x%02x)", optp->name,
1466 val_to_str(protocol, ppp_vals, "Unknown"), protocol);
1470 if (protocol == PPP_CHAP) {
1471 algorithm = tvb_get_guint8(tvb, offset);
1472 proto_tree_add_text(field_tree, tvb, offset, length,
1473 "Algorithm: %s (0x%02x)",
1474 val_to_str(algorithm, chap_alg_vals, "Unknown"),
1478 proto_tree_add_text(field_tree, tvb, offset, length, "Data (%d byte%s)", length,
1479 plurality(length, "", "s"));
1485 dissect_lcp_magicnumber_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1486 int offset, guint length, packet_info *pinfo _U_,
1489 proto_tree_add_text(tree, tvb, offset, length, "%s: 0x%08x", optp->name,
1490 tvb_get_ntohl(tvb, offset + 2));
1494 dissect_lcp_fcs_alternatives_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1495 int offset, guint length, packet_info *pinfo _U_,
1499 proto_tree *field_tree = NULL;
1500 guint8 alternatives;
1502 alternatives = tvb_get_guint8(tvb, offset + 2);
1503 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: 0x%02x",
1504 optp->name, alternatives);
1505 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1507 if (alternatives & 0x1)
1508 proto_tree_add_text(field_tree, tvb, offset + 2, 1, "%s",
1509 decode_boolean_bitfield(alternatives, 0x1, 8, "Null FCS", NULL));
1510 if (alternatives & 0x2)
1511 proto_tree_add_text(field_tree, tvb, offset + 2, 1, "%s",
1512 decode_boolean_bitfield(alternatives, 0x2, 8, "CCITT 16-bit FCS", NULL));
1513 if (alternatives & 0x4)
1514 proto_tree_add_text(field_tree, tvb, offset + 2, 1, "%s",
1515 decode_boolean_bitfield(alternatives, 0x4, 8, "CCITT 32-bit FCS", NULL));
1519 dissect_lcp_self_describing_pad_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1520 int offset, guint length, packet_info *pinfo _U_,
1523 proto_tree_add_text(tree, tvb, offset, length, "%s: %u", optp->name,
1524 tvb_get_guint8(tvb, offset + 2));
1528 dissect_lcp_numbered_mode_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1529 int offset, guint length, packet_info *pinfo _U_,
1533 proto_tree *field_tree = NULL;
1535 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1536 optp->name, length, plurality(length, "", "s"));
1537 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1540 proto_tree_add_text(field_tree, tvb, offset, 1, "Window: %u",
1541 tvb_get_guint8(tvb, offset));
1545 proto_tree_add_text(field_tree, tvb, offset, length, "Address (%d byte%s)",
1546 length, plurality(length, "", "s"));
1549 static const value_string callback_op_vals[] = {
1550 {0, "Location is determined by user authentication" },
1551 {1, "Message is dialing string" },
1552 {2, "Message is location identifier" },
1553 {3, "Message is E.164" },
1554 {4, "Message is distinguished name" },
1556 {6, "Location is determined during CBCP negotiation" },
1561 dissect_lcp_callback_opt(const ip_tcp_opt *optp, tvbuff_t *tvb, int offset,
1562 guint length, packet_info *pinfo _U_,
1566 proto_tree *field_tree = NULL;
1569 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1570 optp->name, length, plurality(length, "", "s"));
1571 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1574 operation = tvb_get_guint8(tvb, offset);
1575 proto_tree_add_text(field_tree, tvb, offset, 1, "Operation: %s (0x%02x)",
1576 val_to_str(operation, callback_op_vals, "Unknown"),
1581 proto_tree_add_text(field_tree, tvb, offset, length, "Message (%d byte%s)",
1582 length, plurality(length, "", "s"));
1586 dissect_lcp_multilink_mrru_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1587 int offset, guint length, packet_info *pinfo _U_,
1590 proto_tree_add_text(tree, tvb, offset, length, "%s: %u", optp->name,
1591 tvb_get_ntohs(tvb, offset + 2));
1594 #define CLASS_NULL 0
1595 #define CLASS_LOCAL 1
1597 #define CLASS_IEEE_802_1 3
1598 #define CLASS_PPP_MAGIC_NUMBER 4
1599 #define CLASS_PSDN_DIRECTORY_NUMBER 5
1601 static const value_string multilink_ep_disc_class_vals[] = {
1602 {CLASS_NULL, "Null" },
1603 {CLASS_LOCAL, "Locally assigned address" },
1604 {CLASS_IP, "IP address" },
1605 {CLASS_IEEE_802_1, "IEEE 802.1 globally assigned MAC address" },
1606 {CLASS_PPP_MAGIC_NUMBER, "PPP magic-number block" },
1607 {CLASS_PSDN_DIRECTORY_NUMBER, "Public switched network directory number" },
1612 dissect_lcp_multilink_ep_disc_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1613 int offset, guint length, packet_info *pinfo _U_,
1617 proto_tree *field_tree = NULL;
1618 guint8 ep_disc_class;
1620 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1621 optp->name, length, plurality(length, "", "s"));
1622 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1625 ep_disc_class = tvb_get_guint8(tvb, offset);
1626 proto_tree_add_text(field_tree, tvb, offset, 1, "Class: %s (%u)",
1627 val_to_str(ep_disc_class, multilink_ep_disc_class_vals, "Unknown"),
1632 switch (ep_disc_class) {
1635 proto_tree_add_text(field_tree, tvb, offset, length,
1636 "Address (%d byte%s), should have been empty",
1637 length, plurality(length, "", "s"));
1642 proto_tree_add_text(field_tree, tvb, offset, length,
1643 "Address (%d byte%s), should have been <20",
1644 length, plurality(length, "", "s"));
1646 proto_tree_add_text(field_tree, tvb, offset, length,
1647 "Address (%d byte%s)",
1648 length, plurality(length, "", "s"));
1654 proto_tree_add_text(field_tree, tvb, offset, length,
1655 "Address (%d byte%s), should have been 4",
1656 length, plurality(length, "", "s"));
1658 proto_tree_add_text(field_tree, tvb, offset, length,
1659 "Address: %s", ip_to_str(tvb_get_ptr(tvb, offset, 4)));
1663 case CLASS_IEEE_802_1:
1665 proto_tree_add_text(field_tree, tvb, offset, length,
1666 "Address (%d byte%s), should have been 6",
1667 length, plurality(length, "", "s"));
1669 proto_tree_add_text(field_tree, tvb, offset, length,
1670 "Address: %s", ether_to_str(tvb_get_ptr(tvb, offset, 6)));
1674 case CLASS_PPP_MAGIC_NUMBER:
1675 /* XXX - dissect as 32-bit magic numbers */
1677 proto_tree_add_text(field_tree, tvb, offset, length,
1678 "Address (%d byte%s), should have been <20",
1679 length, plurality(length, "", "s"));
1681 proto_tree_add_text(field_tree, tvb, offset, length,
1682 "Address (%d byte%s)",
1683 length, plurality(length, "", "s"));
1687 case CLASS_PSDN_DIRECTORY_NUMBER:
1689 proto_tree_add_text(field_tree, tvb, offset, length,
1690 "Address (%d byte%s), should have been <20",
1691 length, plurality(length, "", "s"));
1693 proto_tree_add_text(field_tree, tvb, offset, length,
1694 "Address (%d byte%s)",
1695 length, plurality(length, "", "s"));
1700 proto_tree_add_text(field_tree, tvb, offset, length,
1701 "Address (%d byte%s)",
1702 length, plurality(length, "", "s"));
1709 dissect_lcp_bap_link_discriminator_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1710 int offset, guint length, packet_info *pinfo _U_,
1713 proto_tree_add_text(tree, tvb, offset, length,
1714 "%s: 0x%04x", optp->name,
1715 tvb_get_ntohs(tvb, offset + 2));
1718 /* Character set numbers from the IANA charset registry. */
1719 static const value_string charset_num_vals[] = {
1725 dissect_lcp_internationalization_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1726 int offset, guint length, packet_info *pinfo _U_,
1730 proto_tree *field_tree = NULL;
1733 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1734 optp->name, length, plurality(length, "", "s"));
1735 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1738 charset = tvb_get_ntohl(tvb, offset);
1739 proto_tree_add_text(field_tree, tvb, offset, 4, "Character set: %s (0x%04x)",
1740 val_to_str(charset, charset_num_vals, "Unknown"),
1745 /* XXX - should be displayed as an ASCII string */
1746 proto_tree_add_text(field_tree, tvb, offset, length, "Language tag (%d byte%s)",
1747 length, plurality(length, "", "s"));
1752 dissect_ipcp_addrs_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1753 int offset, guint length, packet_info *pinfo _U_,
1757 proto_tree *field_tree = NULL;
1759 tf = proto_tree_add_text(tree, tvb, offset, length, "%s: %u byte%s",
1760 optp->name, length, plurality(length, "", "s"));
1761 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1764 proto_tree_add_text(field_tree, tvb, offset, 4,
1765 "Source IP address: %s",
1766 ip_to_str(tvb_get_ptr(tvb, offset, 4)));
1769 proto_tree_add_text(field_tree, tvb, offset, 4,
1770 "Destination IP address: %s",
1771 ip_to_str(tvb_get_ptr(tvb, offset, 4)));
1774 static void dissect_ipcp_addr_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1775 int offset, guint length, packet_info *pinfo _U_,
1778 proto_tree_add_text(tree, tvb, offset, length, "%s: %s", optp->name,
1779 ip_to_str(tvb_get_ptr(tvb, offset + 2, 4)));
1782 static void dissect_pppmuxcp_def_pid_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1783 int offset, guint length, packet_info *pinfo _U_,
1786 pppmux_def_prot_id = tvb_get_ntohs(tvb, offset + 2);
1787 proto_tree_add_text(tree, tvb, offset + 2, length - 2, "%s: %s (0x%02x)",optp->name,
1788 val_to_str(pppmux_def_prot_id, ppp_vals, "Unknown"), pppmux_def_prot_id);
1793 dissect_ccp_stac_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1794 int offset, guint length, packet_info *pinfo _U_,
1798 proto_tree *field_tree;
1802 proto_tree_add_text(tree, tvb, offset, length,
1803 "%s (Ascend Proprietary version)", optp->name);
1804 /* We don't know how to decode the following 4 octets, since
1805 there's no public document that describe their usage. */
1807 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1808 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1810 proto_tree_add_text(field_tree, tvb, offset + 2, 2,
1811 "History Count: %u", tvb_get_ntohs(tvb, offset + 2));
1812 check_mode = tvb_get_guint8(tvb, offset + 4);
1813 proto_tree_add_text(field_tree, tvb, offset + 4, 1,
1814 "Check Mode: %s (0x%02X)",
1815 val_to_str(check_mode, stac_checkmode_vals, "Unknown"),
1821 dissect_ccp_mppc_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1822 int offset, guint length, packet_info *pinfo _U_,
1826 proto_tree *flags_tree;
1827 guint32 supported_bits;
1829 supported_bits = tvb_get_ntohl(tvb, offset + 2);
1830 tf = proto_tree_add_text(tree, tvb, offset, length,
1831 "%s: Supported Bits: 0x%08X", optp->name, supported_bits);
1832 flags_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1833 proto_tree_add_text(flags_tree, tvb, offset + 2, 4, "%s",
1834 decode_boolean_bitfield(supported_bits, MPPC_SUPPORTED_BITS_C, 8*4,
1835 "Desire to negotiate MPPC", "NO Desire to negotiate MPPC"));
1836 proto_tree_add_text(flags_tree, tvb, offset + 2, 4, "%s",
1837 decode_boolean_bitfield(supported_bits, MPPE_SUPPORTED_BITS_D, 8*4,
1838 "Obsolete (should NOT be 1)", "Obsolete (should ALWAYS be 0)"));
1839 proto_tree_add_text(flags_tree, tvb, offset + 2, 4, "%s",
1840 decode_boolean_bitfield(supported_bits, MPPE_SUPPORTED_BITS_L, 8*4,
1841 "40-bit encryption ON", "40-bit encryption OFF"));
1842 proto_tree_add_text(flags_tree, tvb, offset + 2, 4, "%s",
1843 decode_boolean_bitfield(supported_bits, MPPE_SUPPORTED_BITS_S, 8*4,
1844 "128-bit encryption ON", "128-bit encryption OFF"));
1845 proto_tree_add_text(flags_tree, tvb, offset + 2, 4, "%s",
1846 decode_boolean_bitfield(supported_bits, MPPE_SUPPORTED_BITS_M, 8*4,
1847 "56-bit encryption ON", "56-bit encryption OFF"));
1848 proto_tree_add_text(flags_tree, tvb, offset + 2, 4, "%s",
1849 decode_boolean_bitfield(supported_bits, MPPE_SUPPORTED_BITS_H, 8*4,
1850 "Stateless mode ON", "Stateless mode OFF"));
1854 dissect_ccp_bsdcomp_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1855 int offset, guint length, packet_info *pinfo _U_,
1859 proto_tree *field_tree;
1861 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1862 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1864 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1865 "Version: %u", tvb_get_guint8(tvb, offset + 2) >> 5);
1866 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1868 tvb_get_guint8(tvb, offset + 2) & 0x1f);
1872 dissect_ccp_lzsdcp_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1873 int offset, guint length, packet_info *pinfo _U_,
1877 proto_tree *field_tree;
1879 guint8 process_mode;
1881 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1882 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1884 proto_tree_add_text(field_tree, tvb, offset + 2, 2,
1885 "History Count: %u", tvb_get_ntohs(tvb, offset + 2));
1886 check_mode = tvb_get_guint8(tvb, offset + 4);
1887 proto_tree_add_text(field_tree, tvb, offset + 4, 1,
1888 "Check Mode: %s (0x%02X)",
1889 val_to_str(check_mode, lzsdcp_checkmode_vals, "Unknown"),
1891 process_mode = tvb_get_guint8(tvb, offset + 5);
1892 proto_tree_add_text(field_tree, tvb, offset + 5, 1,
1893 "Process Mode: %s (0x%02X)",
1894 val_to_str(process_mode, lzsdcp_processmode_vals, "Unkown"),
1899 dissect_ccp_mvrca_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1900 int offset, guint length, packet_info *pinfo _U_,
1904 proto_tree *field_tree;
1906 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1907 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1909 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1910 "Features: %u", tvb_get_guint8(tvb, offset + 2) >> 5);
1911 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1912 "Packet by Packet flag: %s",
1913 tvb_get_guint8(tvb, offset + 2) & 0x20 ? "true" : "false");
1914 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1915 "History: %u", tvb_get_guint8(tvb, offset + 2) & 0x20);
1916 proto_tree_add_text(field_tree, tvb, offset + 3, 1,
1917 "Number of contexts: %u", tvb_get_guint8(tvb, offset + 3));
1921 dissect_ccp_deflate_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1922 int offset, guint length, packet_info *pinfo _U_,
1926 proto_tree *field_tree;
1929 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1930 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1932 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1933 "Window: %u", hi_nibble(tvb_get_guint8(tvb, offset + 2)));
1934 method = lo_nibble(tvb_get_guint8(tvb, offset + 2));
1935 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1936 "Method: %s (0x%02x)",
1937 method == 0x08 ? "zlib compression" : "other", method);
1938 proto_tree_add_text(field_tree, tvb, offset + 3, 1,
1939 "Sequence number check method: %u",
1940 tvb_get_guint8(tvb, offset + 2) & 0x03);
1944 dissect_cbcp_no_callback_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1945 int offset, guint length, packet_info *pinfo _U_,
1948 proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1952 dissect_cbcp_callback_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1953 int offset, guint length, packet_info *pinfo _U_,
1957 proto_tree *field_tree;
1959 proto_tree *addr_tree;
1962 guint8 buf[256]; /* Since length field in Callback Conf Option is
1963 8 bits, 256-octet buf is large enough. */
1965 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
1966 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
1968 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
1969 "Callback delay: %u", tvb_get_guint8(tvb, offset + 2));
1973 while (length > 0) {
1974 ta = proto_tree_add_text(field_tree, tvb, offset, length,
1975 "Callback Address");
1976 addr_type = tvb_get_guint8(tvb, offset);
1977 addr_tree = proto_item_add_subtree(tf, ett_cbcp_callback_opt_addr);
1978 proto_tree_add_text(addr_tree, tvb, offset, 1,
1979 "Address Type: %s (%u)",
1980 ((addr_type == 1) ? "PSTN/ISDN" : "Other"), addr_type);
1983 addr_len = tvb_get_nstringz0(tvb, offset, sizeof(buf), buf);
1984 proto_tree_add_text(addr_tree, tvb, offset, addr_len + 1,
1985 "Address: %s", buf);
1986 offset += (addr_len + 1);
1987 length -= (addr_len + 1);
1992 dissect_bacp_favored_peer_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
1993 int offset, guint length, packet_info *pinfo _U_,
1997 proto_tree *field_tree;
1999 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
2000 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
2002 proto_tree_add_text(field_tree, tvb, offset + 2, 4,
2003 "Magic number: 0x%08x", tvb_get_ntohl(tvb, offset + 2));
2007 dissect_bap_link_type_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
2008 int offset, guint length, packet_info *pinfo _U_,
2012 proto_tree *field_tree;
2015 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
2016 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
2018 proto_tree_add_text(field_tree, tvb, offset + 2, 2,
2019 "Link Speed: %u kbps", tvb_get_ntohs(tvb, offset + 2));
2020 link_type = tvb_get_guint8(tvb, offset + 4);
2021 proto_tree_add_text(field_tree, tvb, offset + 4, 1,
2022 "Link Type: %s (%u)", val_to_str(link_type, bap_link_type_vals,
2023 "Unknown"), link_type);
2027 dissect_bap_phone_delta_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
2028 int offset, guint length, packet_info *pinfo _U_,
2032 proto_tree *field_tree;
2034 proto_tree *suboption_tree;
2037 guint8 buf[256]; /* Since Sub-Option length field in BAP Phone-Delta
2038 Option is 8 bits, 256-octets buf is large enough */
2040 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
2041 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
2046 while (length > 0) {
2047 subopt_type = tvb_get_guint8(tvb, offset);
2048 subopt_len = tvb_get_guint8(tvb, offset + 1);
2049 ti = proto_tree_add_text(field_tree, tvb, offset, subopt_len,
2050 "Sub-Option (%d byte%s)",
2051 subopt_len, plurality(subopt_len, "", "s"));
2052 suboption_tree = proto_item_add_subtree(ti, ett_bap_phone_delta_subopt);
2054 proto_tree_add_text(suboption_tree, tvb, offset, 1,
2055 "Sub-Option Type: %s (%u)",
2056 val_to_str(subopt_type, bap_phone_delta_subopt_vals, "Unknown"),
2059 proto_tree_add_text(suboption_tree, tvb, offset + 1, 1,
2060 "Sub-Option Length: %u", subopt_len);
2062 switch (subopt_type) {
2063 case BAP_PHONE_DELTA_SUBOPT_UNIQ_DIGIT:
2064 proto_tree_add_text(suboption_tree, tvb, offset + 2, 1, "Uniq Digit: %u",
2065 tvb_get_guint8(tvb, offset + 2));
2067 case BAP_PHONE_DELTA_SUBOPT_SUBSC_NUM:
2068 tvb_get_nstringz0(tvb, offset + 2, subopt_len - 2, buf);
2069 proto_tree_add_text(suboption_tree, tvb, offset + 2, subopt_len - 2,
2070 "Subscriber Number: %s", buf);
2072 case BAP_PHONE_DELTA_SUBOPT_PHONENUM_SUBADDR:
2073 tvb_get_nstringz0(tvb, offset + 2, subopt_len - 2, buf);
2074 proto_tree_add_text(suboption_tree, tvb, offset + 2, subopt_len - 2,
2075 "Phone Number Sub Address: %s", buf);
2078 proto_tree_add_text(suboption_tree, tvb, offset + 2, subopt_len - 2,
2082 offset += subopt_len;
2083 length -= subopt_len;
2088 dissect_bap_reason_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
2089 int offset, guint length, packet_info *pinfo _U_,
2092 guint8 buf[256]; /* Since length field in BAP Reason Option is
2093 8 bits, 256-octets buf is large enough */
2095 tvb_get_nstringz0(tvb, offset + 2, length - 2, buf);
2096 proto_tree_add_text(tree, tvb, offset, length, "%s: %s",
2101 dissect_bap_link_disc_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
2102 int offset, guint length, packet_info *pinfo _U_,
2105 proto_tree_add_text(tree, tvb, offset, length, "%s: 0x%04x",
2106 optp->name, tvb_get_ntohs(tvb, offset + 2));
2110 dissect_bap_call_status_opt(const ip_tcp_opt *optp, tvbuff_t *tvb,
2111 int offset, guint length, packet_info *pinfo _U_,
2115 proto_tree *field_tree;
2116 guint8 status, action;
2118 tf = proto_tree_add_text(tree, tvb, offset, length, "%s", optp->name);
2119 field_tree = proto_item_add_subtree(tf, *optp->subtree_index);
2121 status = tvb_get_guint8(tvb, offset + 2);
2122 proto_tree_add_text(field_tree, tvb, offset + 2, 1,
2123 "Status: %s (0x%02x)",
2124 val_to_str(status, q931_cause_code_vals, "Unknown"), status);
2126 action = tvb_get_guint8(tvb, offset + 3);
2127 proto_tree_add_text(field_tree, tvb, offset + 3, 1,
2128 "Action: %s (0x%02x)",
2129 val_to_str(action, bap_call_status_opt_action_vals, "Unknown"), action);
2133 dissect_cp( tvbuff_t *tvb, int proto_id, int proto_subtree_index,
2134 const value_string *proto_vals, int options_subtree_index,
2135 const ip_tcp_opt *opts, int nopts, packet_info *pinfo, proto_tree *tree ) {
2137 proto_tree *fh_tree = NULL;
2139 proto_tree *field_tree;
2146 code = tvb_get_guint8(tvb, 0);
2147 id = tvb_get_guint8(tvb, 1);
2148 length = tvb_get_ntohs(tvb, 2);
2150 if(check_col(pinfo->cinfo, COL_PROTOCOL))
2151 col_set_str(pinfo->cinfo, COL_PROTOCOL,
2152 proto_get_protocol_short_name(proto_id));
2154 if(check_col(pinfo->cinfo, COL_INFO))
2155 col_add_fstr(pinfo->cinfo, COL_INFO, "%s %s",
2156 proto_get_protocol_short_name(proto_id),
2157 val_to_str(code, proto_vals, "Unknown"));
2160 ti = proto_tree_add_item(tree, proto_id, tvb, 0, length, FALSE);
2161 fh_tree = proto_item_add_subtree(ti, proto_subtree_index);
2162 proto_tree_add_text(fh_tree, tvb, 0, 1, "Code: %s (0x%02x)",
2163 val_to_str(code, proto_vals, "Unknown"), code);
2164 proto_tree_add_text(fh_tree, tvb, 1, 1, "Identifier: 0x%02x",
2166 proto_tree_add_text(fh_tree, tvb, 2, 2, "Length: %u",
2179 tf = proto_tree_add_text(fh_tree, tvb, offset, length,
2180 "Options: (%d byte%s)", length, plurality(length, "", "s"));
2181 field_tree = proto_item_add_subtree(tf, options_subtree_index);
2182 dissect_ip_tcp_options(tvb, offset, length, opts, nopts, -1,
2193 proto_tree_add_text(fh_tree, tvb, offset, 4, "Magic number: 0x%08x",
2194 tvb_get_ntohl(tvb, offset));
2198 proto_tree_add_text(fh_tree, tvb, offset, length, "Message (%d byte%s)",
2199 length, plurality(length, "", "s"));
2205 proto_tree_add_text(fh_tree, tvb, offset, 4, "Magic number: 0x%08x",
2206 tvb_get_ntohl(tvb, offset));
2209 proto_tree_add_text(fh_tree, tvb, offset, 4, "Seconds remaining: %u",
2210 tvb_get_ntohl(tvb, offset));
2214 proto_tree_add_text(fh_tree, tvb, offset, length, "Message (%d byte%s)",
2215 length, plurality(length, "", "s"));
2221 protocol = tvb_get_ntohs(tvb, offset);
2222 proto_tree_add_text(fh_tree, tvb, offset, 2, "Rejected protocol: %s (0x%04x)",
2223 val_to_str(protocol, ppp_vals, "Unknown"), protocol);
2227 proto_tree_add_text(fh_tree, tvb, offset, length, "Rejected packet (%d byte%s)",
2228 length, plurality(length, "", "s"));
2229 /* XXX - should be dissected as a PPP packet */
2234 /* decode the rejected LCP packet here. */
2236 proto_tree_add_text(fh_tree, tvb, offset, length, "Rejected packet (%d byte%s)",
2237 length, plurality(length, "", "s"));
2243 proto_tree_add_text(fh_tree, tvb, offset, length, "Data (%d byte%s)",
2244 length, plurality(length, "", "s"));
2249 proto_tree_add_text(fh_tree, tvb, offset, length, "Stuff (%d byte%s)",
2250 length, plurality(length, "", "s"));
2255 /* Protocol field compression */
2256 #define PFC_BIT 0x01
2259 dissect_ppp_common( tvbuff_t *tvb, int offset, packet_info *pinfo,
2260 proto_tree *tree, proto_tree *fh_tree,
2266 ppp_prot = tvb_get_guint8(tvb, offset);
2267 if (ppp_prot & PFC_BIT) {
2268 /* Compressed protocol field - just the byte we fetched. */
2271 /* Uncompressed protocol field - fetch all of it. */
2272 ppp_prot = tvb_get_ntohs(tvb, offset);
2276 /* If "ti" is not null, it refers to the top-level "proto_ppp" item
2277 for PPP, and was given a length equal to the length of any
2278 stuff in the header preceding the protocol type, e.g. an HDLC
2279 header, which is just "offset"; add the length of the protocol
2280 type field to it. */
2282 proto_item_set_len(ti, offset + proto_len);
2285 proto_tree_add_uint(fh_tree, hf_ppp_protocol, tvb, offset, proto_len,
2289 next_tvb = tvb_new_subset(tvb, offset + proto_len, -1, -1);
2291 /* do lookup with the subdissector table */
2292 if (!dissector_try_port(subdissector_table, ppp_prot, next_tvb, pinfo, tree)) {
2293 if (check_col(pinfo->cinfo, COL_PROTOCOL))
2294 col_add_fstr(pinfo->cinfo, COL_PROTOCOL, "0x%04x", ppp_prot);
2295 if (check_col(pinfo->cinfo, COL_INFO))
2296 col_add_fstr(pinfo->cinfo, COL_INFO, "PPP %s (0x%04x)",
2297 val_to_str(ppp_prot, ppp_vals, "Unknown"), ppp_prot);
2298 call_dissector(data_handle,next_tvb, pinfo, tree);
2303 dissect_lcp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2305 dissect_cp(tvb, proto_lcp, ett_lcp, lcp_vals, ett_lcp_options,
2306 lcp_opts, N_LCP_OPTS, pinfo, tree);
2310 dissect_ipcp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2312 dissect_cp(tvb, proto_ipcp, ett_ipcp, cp_vals, ett_ipcp_options,
2313 ipcp_opts, N_IPCP_OPTS, pinfo, tree);
2317 dissect_ccp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2319 dissect_cp(tvb, proto_ccp, ett_ccp, ccp_vals, ett_ccp_options,
2320 ccp_opts, N_CCP_OPTS, pinfo, tree);
2324 dissect_cbcp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2326 dissect_cp(tvb, proto_cbcp, ett_cbcp, cbcp_vals, ett_cbcp_options,
2327 cbcp_opts, N_CBCP_OPTS, pinfo, tree);
2331 dissect_bacp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2333 dissect_cp(tvb, proto_bacp, ett_bacp, cp_vals, ett_bacp_options,
2334 bacp_opts, N_BACP_OPTS, pinfo, tree);
2338 dissect_bap(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2342 proto_tree *fh_tree = NULL;
2344 proto_tree *field_tree;
2351 type = tvb_get_guint8(tvb, 0);
2352 id = tvb_get_guint8(tvb, 1);
2353 length = tvb_get_ntohs(tvb, 2);
2355 if(check_col(pinfo->cinfo, COL_PROTOCOL))
2356 col_set_str(pinfo->cinfo, COL_PROTOCOL,
2357 proto_get_protocol_short_name(proto_bap));
2359 if(check_col(pinfo->cinfo, COL_INFO))
2360 col_add_fstr(pinfo->cinfo, COL_INFO, "%s %s",
2361 proto_get_protocol_short_name(proto_bap),
2362 val_to_str(type, bap_vals, "Unknown"));
2365 ti = proto_tree_add_item(tree, proto_bap, tvb, 0, length, FALSE);
2366 fh_tree = proto_item_add_subtree(ti, ett_bap_options);
2367 proto_tree_add_text(fh_tree, tvb, 0, 1, "Type: %s (0x%02x)",
2368 val_to_str(type, bap_vals, "Unknown"), type);
2369 proto_tree_add_text(fh_tree, tvb, 1, 1, "Identifier: 0x%02x",
2371 proto_tree_add_text(fh_tree, tvb, 2, 2, "Length: %u",
2377 if (type == BAP_CRES || type == BAP_CBRES ||
2378 type == BAP_LDQRES || type == BAP_CSRES) {
2379 resp_code = tvb_get_guint8(tvb, offset);
2380 proto_tree_add_text(fh_tree, tvb, offset, 1, "Response Code: %s (0x%02x)",
2381 val_to_str(resp_code, bap_resp_code_vals, "Unknown"), resp_code);
2388 tf = proto_tree_add_text(fh_tree, tvb, offset, length,
2389 "Data (%d byte%s)", length, plurality(length, "", "s"));
2390 field_tree = proto_item_add_subtree(tf, ett_bap_options);
2391 dissect_ip_tcp_options(tvb, offset, length, bap_opts, N_BAP_OPTS, -1,
2398 dissect_comp_data(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2401 proto_tree *comp_data_tree;
2403 if (check_col(pinfo->cinfo, COL_PROTOCOL))
2404 col_set_str(pinfo->cinfo, COL_PROTOCOL,
2405 proto_get_protocol_short_name(proto_comp_data));
2407 if(check_col(pinfo->cinfo, COL_INFO))
2408 col_add_fstr(pinfo->cinfo, COL_INFO, "%s %s",
2409 proto_get_protocol_short_name(proto_comp_data),
2410 val_to_str(PPP_COMP, ppp_vals, "Unknown"));
2413 ti = proto_tree_add_item(tree, proto_comp_data, tvb, 0, -1, FALSE);
2414 comp_data_tree = proto_item_add_subtree(ti, ett_comp_data);
2419 dissect_pppmuxcp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2421 dissect_cp(tvb,proto_pppmuxcp,ett_pppmuxcp,pppmuxcp_vals,
2422 ett_pppmuxcp_options,pppmuxcp_opts,N_PPPMUXCP_OPTS,pinfo,tree);
2425 #define PPPMUX_FLAGS_MASK 0xc0
2426 #define PPPMUX_PFF_BIT_SET 0x80
2427 #define PPPMUX_LXT_BIT_SET 0x40
2430 dissect_pppmux(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2432 proto_tree *mux_tree, *hdr_tree, *sub_tree, *flag_tree;
2433 proto_tree *info_tree;
2434 proto_item *ti = NULL,*sub_ti = NULL;
2439 int offset = 0, length_remaining;
2440 int length_field = 0, pid_field = 0,hdr_length = 0;
2442 if (check_col(pinfo->cinfo, COL_PROTOCOL))
2443 col_set_str(pinfo->cinfo,COL_PROTOCOL, "PPP PPPMux");
2445 if (check_col(pinfo->cinfo, COL_INFO))
2446 col_set_str(pinfo->cinfo, COL_INFO, "PPP Multiplexing");
2448 length_remaining = tvb_reported_length(tvb);
2451 ti = proto_tree_add_item(tree, proto_pppmux, tvb, 0, -1, FALSE);
2452 mux_tree = proto_item_add_subtree(ti,ett_pppmux);
2454 while (length_remaining > 0) {
2456 flags = tvb_get_guint8(tvb,offset) & PPPMUX_FLAGS_MASK;
2458 if (flags && PPPMUX_LXT_BIT_SET ) {
2459 length = tvb_get_ntohs(tvb,offset) & 0x3fff;
2462 length = tvb_get_guint8(tvb,offset) & 0x3f;
2466 if (flags && PPPMUX_PFF_BIT_SET) {
2467 byte = tvb_get_guint8(tvb,offset + length_field);
2468 if (byte && PFC_BIT) { /* Compressed PID field*/
2471 } else { /*PID field is 2 bytes*/
2472 pid = tvb_get_ntohs(tvb,offset + length_field);
2476 if (!pid){ /*No Last PID, hence use the default */
2477 if (pppmux_def_prot_id)
2478 pid = pppmux_def_prot_id;
2482 hdr_length = length_field + pid_field;
2484 ti = proto_tree_add_text(mux_tree, tvb, offset, length + length_field,
2485 "PPPMux Sub-frame");
2486 sub_tree = proto_item_add_subtree(ti,ett_pppmux_subframe);
2487 sub_ti = proto_tree_add_text(sub_tree, tvb, offset,
2488 hdr_length,"Header field");
2490 hdr_tree = proto_item_add_subtree(sub_ti,ett_pppmux_subframe_hdr);
2491 ti = proto_tree_add_text(hdr_tree, tvb, offset, length_field, "PFF/LXT: 0x%02X",
2494 flag_tree = proto_item_add_subtree(ti,ett_pppmux_subframe_flags);
2495 proto_tree_add_text(flag_tree,tvb,offset,length_field,"%s",
2496 decode_boolean_bitfield(flags,0x80,8,"PID Present","PID not present"));
2497 proto_tree_add_text(flag_tree,tvb,offset,length_field,"%s",
2498 decode_boolean_bitfield(flags,0x40,8,"2 bytes ength field ","1 byte length field"));
2500 ti = proto_tree_add_text(hdr_tree,tvb,offset,length_field,"Sub-frame Length = %u",length);
2502 if (flags && PPPMUX_PFF_BIT_SET)
2503 proto_tree_add_text(hdr_tree,tvb,offset + length_field,pid_field,"%s: %s(0x%02x)",
2504 "Protocol ID",val_to_str(pid,ppp_vals,"Unknown"), pid);
2506 offset += hdr_length;
2507 length_remaining -= hdr_length;
2508 length -= pid_field;
2510 sub_ti = proto_tree_add_text(sub_tree,tvb,offset,length,"Information Field");
2511 info_tree = proto_item_add_subtree(sub_ti,ett_pppmux_subframe_info);
2513 next_tvb = tvb_new_subset(tvb,offset,length,-1);
2515 if (!dissector_try_port(subdissector_table, pid, next_tvb, pinfo, info_tree)) {
2516 call_dissector(data_handle, next_tvb, pinfo, info_tree);
2519 length_remaining -= length;
2520 } /* While length_remaining */
2526 #define MP_FRAG_MASK 0xC0
2527 #define MP_FRAG(bits) ((bits) & MP_FRAG_MASK)
2528 #define MP_FRAG_FIRST 0x80
2529 #define MP_FRAG_LAST 0x40
2530 #define MP_FRAG_RESERVED 0x3f
2532 static const true_false_string frag_truth = {
2537 /* According to RFC 1717, the length the MP header isn't indicated anywhere
2538 in the header itself. It starts out at four bytes and can be
2539 negotiated down to two using LCP. We currently assume that all
2540 headers are four bytes. - gcc
2543 dissect_mp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2545 proto_tree *mp_tree, *hdr_tree;
2546 proto_item *ti = NULL;
2551 if (check_col(pinfo->cinfo, COL_PROTOCOL))
2552 col_set_str(pinfo->cinfo, COL_PROTOCOL, "PPP MP");
2554 if (check_col(pinfo->cinfo, COL_INFO))
2555 col_set_str(pinfo->cinfo, COL_INFO, "PPP Multilink");
2557 flags = tvb_get_guint8(tvb, 0);
2567 case MP_FRAG_FIRST|MP_FRAG_LAST:
2568 flag_str = "First, Last";
2571 flag_str = "Unknown";
2574 ti = proto_tree_add_item(tree, proto_mp, tvb, 0, 4, FALSE);
2575 mp_tree = proto_item_add_subtree(ti, ett_mp);
2576 ti = proto_tree_add_text(mp_tree, tvb, 0, 1, "Fragment: 0x%2X (%s)",
2578 hdr_tree = proto_item_add_subtree(ti, ett_mp_flags);
2579 proto_tree_add_boolean(hdr_tree, hf_mp_frag_first, tvb, 0, 1, flags);
2580 proto_tree_add_boolean(hdr_tree, hf_mp_frag_last, tvb, 0, 1, flags),
2581 proto_tree_add_text(hdr_tree, tvb, 0, 1, "%s",
2582 decode_boolean_bitfield(flags, MP_FRAG_RESERVED, sizeof(flags) * 8,
2583 "reserved", "reserved"));
2584 proto_tree_add_item(mp_tree, hf_mp_sequence_num, tvb, 1, 3, FALSE);
2587 if (tvb_reported_length_remaining(tvb, 4) > 0) {
2588 next_tvb = tvb_new_subset(tvb, 4, -1, -1);
2589 dissect_ppp(next_tvb, pinfo, tree);
2594 * Handles PPP without HDLC framing, just a protocol field (RFC 1661).
2597 dissect_ppp( tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree ) {
2598 proto_item *ti = NULL;
2599 proto_tree *fh_tree = NULL;
2602 ti = proto_tree_add_item(tree, proto_ppp, tvb, 0, -1, FALSE);
2603 fh_tree = proto_item_add_subtree(ti, ett_ppp);
2606 dissect_ppp_common(tvb, 0, pinfo, tree, fh_tree, ti);
2610 * Handles link-layer encapsulations where the frame might be
2611 * a PPP in HDLC-like Framing frame (RFC 1662) or a Cisco HDLC frame.
2614 dissect_ppp_hdlc( tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree ) {
2615 proto_item *ti = NULL;
2616 proto_tree *fh_tree = NULL;
2623 byte0 = tvb_get_guint8(tvb, 0);
2624 if (byte0 == CHDLC_ADDR_UNICAST || byte0 == CHDLC_ADDR_MULTICAST) {
2625 /* Cisco HDLC encapsulation */
2626 call_dissector(chdlc_handle, tvb, pinfo, tree);
2630 * XXX - should we have a routine that always dissects PPP, for use
2631 * when we know the packets are PPP, not CHDLC?
2634 /* PPP HDLC encapsulation */
2638 /* address and control are compressed (NULL) */
2642 /* load the top pane info. This should be overwritten by
2643 the next protocol in the stack */
2645 if(check_col(pinfo->cinfo, COL_RES_DL_SRC))
2646 col_set_str(pinfo->cinfo, COL_RES_DL_SRC, "N/A" );
2647 if(check_col(pinfo->cinfo, COL_RES_DL_DST))
2648 col_set_str(pinfo->cinfo, COL_RES_DL_DST, "N/A" );
2649 if(check_col(pinfo->cinfo, COL_PROTOCOL))
2650 col_set_str(pinfo->cinfo, COL_PROTOCOL, "PPP" );
2653 ti = proto_tree_add_item(tree, proto_ppp, tvb, 0, proto_offset, FALSE);
2654 fh_tree = proto_item_add_subtree(ti, ett_ppp);
2655 if (byte0 == 0xff) {
2656 proto_tree_add_item(fh_tree, hf_ppp_address, tvb, 0, 1, FALSE);
2657 proto_tree_add_item(fh_tree, hf_ppp_control, tvb, 1, 1, FALSE);
2661 dissect_ppp_common(tvb, proto_offset, pinfo, tree, fh_tree, ti);
2663 /* Calculate the FCS check */
2664 /* XXX - deal with packets cut off by the snapshot length */
2665 if (ppp_fcs_decode == FCS_16) {
2666 rx_fcs_offset = tvb_length(tvb) - 2;
2667 rx_fcs_exp = fcs16(0xFFFF, tvb, 0, rx_fcs_offset);
2668 rx_fcs_got = tvb_get_letohs(tvb, rx_fcs_offset);
2669 if (rx_fcs_got != rx_fcs_exp) {
2670 proto_tree_add_text(fh_tree, tvb, rx_fcs_offset, 2, "FCS 16: 0x%04x (incorrect, should be %04x)", rx_fcs_got, rx_fcs_exp);
2672 proto_tree_add_text(fh_tree, tvb, rx_fcs_offset, 2, "FCS 16: 0x%04x (correct)", rx_fcs_got);
2674 } else if (ppp_fcs_decode == FCS_32) {
2675 rx_fcs_offset = tvb_length(tvb) - 4;
2676 rx_fcs_exp = fcs32(0xFFFFFFFF, tvb, 0, rx_fcs_offset);
2677 rx_fcs_got = tvb_get_letohl(tvb, rx_fcs_offset);
2678 if (rx_fcs_got != rx_fcs_exp) {
2679 proto_tree_add_text(fh_tree, tvb, rx_fcs_offset, 4, "FCS 32: 0x%08x (incorrect, should be %08x) ", rx_fcs_got, rx_fcs_exp);
2681 proto_tree_add_text(fh_tree, tvb, rx_fcs_offset, 4, "FCS 32: 0x%08x (correct)", rx_fcs_got);
2687 * Handles PAP just as a protocol field
2690 dissect_pap( tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree ) {
2692 proto_tree *fh_tree = NULL;
2694 proto_tree *field_tree;
2696 proto_tree *message_tree;
2698 proto_tree *peer_id_tree;
2700 proto_tree *passwd_tree;
2703 guint8 id, peer_id_length, password_length, msg_length;
2706 code = tvb_get_guint8(tvb, 0);
2707 id = tvb_get_guint8(tvb, 1);
2708 length = tvb_get_ntohs(tvb, 2);
2710 if(check_col(pinfo->cinfo, COL_PROTOCOL))
2711 col_set_str(pinfo->cinfo, COL_PROTOCOL,
2712 proto_get_protocol_short_name(proto_pap));
2714 if(check_col(pinfo->cinfo, COL_INFO))
2715 col_add_fstr(pinfo->cinfo, COL_INFO, "%s %s",
2716 proto_get_protocol_short_name(proto_pap),
2717 val_to_str(code, pap_vals, "Unknown"));
2720 ti = proto_tree_add_item(tree, proto_pap, tvb, 0, length, FALSE);
2721 fh_tree = proto_item_add_subtree(ti, ett_pap);
2722 proto_tree_add_text(fh_tree, tvb, 0, 1, "Code: %s (0x%02x)",
2723 val_to_str(code, pap_vals, "Unknown"), code);
2724 proto_tree_add_text(fh_tree, tvb, 1, 1, "Identifier: 0x%02x",
2726 proto_tree_add_text(fh_tree, tvb, 2, 2, "Length: %u",
2736 tf = proto_tree_add_text(fh_tree, tvb, offset, length,
2737 "Data (%d byte%s)", length, plurality(length, "", "s"));
2738 field_tree = proto_item_add_subtree(tf, ett_pap_data);
2739 peer_id_length = tvb_get_guint8(tvb, offset);
2740 tp = proto_tree_add_text(field_tree, tvb, offset, 1,
2741 "Peer ID length: %d byte%s", peer_id_length, plurality(peer_id_length, "", "s"));
2743 peer_id_tree = proto_item_add_subtree(tp, ett_pap_peer_id);
2744 proto_tree_add_text(peer_id_tree, tvb, ++offset, ppp_min(peer_id_length, length),
2745 "Peer-ID (%d byte%s)", peer_id_length, plurality(peer_id_length, "", "s"));
2746 offset+=peer_id_length;
2747 length-=peer_id_length;
2749 password_length = tvb_get_guint8(tvb, offset);
2751 tpw = proto_tree_add_text(field_tree, tvb, offset, 1,
2752 "Password length: %d byte%s", password_length, plurality(password_length, "", "s"));
2753 passwd_tree = proto_item_add_subtree(tpw, ett_pap_password);
2754 proto_tree_add_text(passwd_tree, tvb, ++offset, ppp_min(password_length, length),
2755 "Password (%d byte%s)", password_length, plurality(password_length, "", "s"));
2767 tf = proto_tree_add_text(fh_tree, tvb, offset, length,
2768 "Data (%d byte%s)", length, plurality(length, "", "s"));
2769 field_tree = proto_item_add_subtree(tf, ett_pap_data);
2770 msg_length = tvb_get_guint8(tvb, offset);
2771 tm = proto_tree_add_text(field_tree, tvb, offset, 1,
2772 "Message length: %d byte%s", msg_length, plurality(msg_length, "", "s"));
2774 message_tree = proto_item_add_subtree(tm, ett_pap_message);
2775 proto_tree_add_text(message_tree, tvb, ++offset, ppp_min(msg_length, length),
2776 "Message (%d byte%s)", msg_length, plurality(msg_length, "", "s"));
2783 proto_tree_add_text(fh_tree, tvb, offset, length, "Stuff (%d byte%s)",
2784 length, plurality(length, "", "s"));
2790 * Handles CHAP just as a protocol field
2793 dissect_chap( tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree ) {
2795 proto_tree *fh_tree = NULL;
2797 proto_tree *field_tree;
2799 proto_tree *value_tree;
2801 guint8 code, id, value_size;
2806 code = tvb_get_guint8(tvb, 0);
2807 id = tvb_get_guint8(tvb, 1);
2808 length = tvb_get_ntohs(tvb, 2);
2810 if(check_col(pinfo->cinfo, COL_PROTOCOL))
2811 col_set_str(pinfo->cinfo, COL_PROTOCOL,
2812 proto_get_protocol_short_name(proto_chap));
2814 if(check_col(pinfo->cinfo, COL_INFO))
2815 col_add_fstr(pinfo->cinfo, COL_INFO, "%s %s",
2816 proto_get_protocol_short_name(proto_chap),
2817 val_to_str(code, chap_vals, "Unknown"));
2820 ti = proto_tree_add_item(tree, proto_chap, tvb, 0, length, FALSE);
2821 fh_tree = proto_item_add_subtree(ti, ett_chap);
2822 proto_tree_add_text(fh_tree, tvb, 0, 1, "Code: %s (0x%02x)",
2823 val_to_str(code, chap_vals, "Unknown"), code);
2824 proto_tree_add_text(fh_tree, tvb, 1, 1, "Identifier: 0x%02x",
2826 proto_tree_add_text(fh_tree, tvb, 2, 2, "Length: %u",
2837 tf = proto_tree_add_text(fh_tree, tvb, offset, length,
2838 "Data (%d byte%s)", length,
2839 plurality(length, "", "s"));
2840 field_tree = proto_item_add_subtree(tf, ett_chap_data);
2841 value_size = tvb_get_guint8(tvb, offset);
2842 name_length = length - value_size - 1;
2843 tv = proto_tree_add_text(field_tree, tvb, offset, 1,
2844 "Value Size: %d byte%s",
2845 value_size, plurality(value_size, "", "s"));
2847 value_tree = proto_item_add_subtree(tv, ett_chap_value);
2848 proto_tree_add_text(value_tree, tvb, ++offset,
2849 ppp_min(value_size, length),
2850 "Value (%d byte%s)",
2851 value_size, plurality(value_size, "", "s"));
2855 proto_tree_add_text(field_tree, tvb, offset,
2856 ppp_min(name_length, length),
2857 "Name (%d byte%s)", name_length,
2858 plurality(name_length, "", "s"));
2869 tf = proto_tree_add_text(fh_tree, tvb, offset, length,
2870 "Data (%d byte%s)", length,
2871 plurality(length, "", "s"));
2872 field_tree = proto_item_add_subtree(tf, ett_chap_data);
2873 tv = proto_tree_add_text(field_tree, tvb, offset, length,
2874 "Message: %d byte%s",
2875 length, plurality(length, "", "s"));
2881 proto_tree_add_text(fh_tree, tvb, offset, length, "Stuff (%d byte%s)",
2882 length, plurality(length, "", "s"));
2889 proto_register_ppp(void)
2891 static hf_register_info hf[] = {
2893 { "Address", "ppp.address", FT_UINT8, BASE_HEX,
2894 NULL, 0x0, "", HFILL }},
2897 { "Control", "ppp.control", FT_UINT8, BASE_HEX,
2898 NULL, 0x0, "", HFILL }},
2901 { "Protocol", "ppp.protocol", FT_UINT16, BASE_HEX,
2902 VALS(ppp_vals), 0x0, "", HFILL }},
2904 static gint *ett[] = {
2908 static enum_val_t ppp_options[] = {
2915 module_t *ppp_module;
2917 proto_ppp = proto_register_protocol("Point-to-Point Protocol", "PPP", "ppp");
2918 proto_register_field_array(proto_ppp, hf, array_length(hf));
2919 proto_register_subtree_array(ett, array_length(ett));
2921 /* subdissector code */
2922 subdissector_table = register_dissector_table("ppp.protocol",
2923 "PPP protocol", FT_UINT16, BASE_HEX);
2925 register_dissector("ppp_hdlc", dissect_ppp_hdlc, proto_ppp);
2926 register_dissector("ppp", dissect_ppp, proto_ppp);
2928 /* Register the preferences for the ppp protocol */
2929 ppp_module = prefs_register_protocol(proto_ppp, NULL);
2931 prefs_register_enum_preference(ppp_module,
2933 "PPP Frame Checksum Type",
2934 "The type of PPP frame checksum (none, 16-bit, 32-bit)",
2936 ppp_options, FALSE);
2937 prefs_register_bool_preference(ppp_module,
2939 "PPP Van Jacobson Compression",
2940 "Whether Van Jacobson-compressed PPP frames should be decompressed",
2943 prefs_register_uint_preference(ppp_module, "default_proto_id",
2944 "PPPMuxCP Default PID",
2945 "Default Protocol ID to be used",
2946 16, &pppmux_def_prot_id);
2950 proto_reg_handoff_ppp(void)
2952 dissector_handle_t ppp_hdlc_handle, ppp_handle;
2955 * Get a handle for the CHDLC dissector.
2957 chdlc_handle = find_dissector("chdlc");
2958 data_handle = find_dissector("data");
2960 ppp_hdlc_handle = find_dissector("ppp_hdlc");
2961 ppp_handle = find_dissector("ppp");
2962 dissector_add("wtap_encap", WTAP_ENCAP_PPP, ppp_hdlc_handle);
2963 dissector_add("wtap_encap", WTAP_ENCAP_PPP_WITH_PHDR, ppp_hdlc_handle);
2964 dissector_add("fr.ietf", NLPID_PPP, ppp_handle);
2965 dissector_add("gre.proto", ETHERTYPE_PPP, ppp_hdlc_handle);
2969 proto_register_mp(void)
2971 static hf_register_info hf[] = {
2972 { &hf_mp_frag_first,
2973 { "First fragment", "mp.first", FT_BOOLEAN, 8,
2974 TFS(&frag_truth), MP_FRAG_FIRST, "", HFILL }},
2977 { "Last fragment", "mp.last", FT_BOOLEAN, 8,
2978 TFS(&frag_truth), MP_FRAG_LAST, "", HFILL }},
2980 { &hf_mp_sequence_num,
2981 { "Sequence number", "mp.seq", FT_UINT24, BASE_DEC, NULL, 0x0,
2984 static gint *ett[] = {
2989 proto_mp = proto_register_protocol("PPP Multilink Protocol", "PPP MP", "mp");
2990 proto_register_field_array(proto_mp, hf, array_length(hf));
2991 proto_register_subtree_array(ett, array_length(ett));
2995 proto_reg_handoff_mp(void)
2997 dissector_handle_t mp_handle;
2999 mp_handle = create_dissector_handle(dissect_mp, proto_mp);
3000 dissector_add("ppp.protocol", PPP_MP, mp_handle);
3004 proto_register_lcp(void)
3006 static gint *ett[] = {
3009 &ett_lcp_authprot_opt,
3010 &ett_lcp_qualprot_opt,
3011 &ett_lcp_fcs_alternatives_opt,
3012 &ett_lcp_numbered_mode_opt,
3013 &ett_lcp_callback_opt,
3014 &ett_lcp_multilink_ep_disc_opt,
3015 &ett_lcp_internationalization_opt,
3018 proto_lcp = proto_register_protocol("PPP Link Control Protocol", "PPP LCP",
3020 proto_register_subtree_array(ett, array_length(ett));
3024 proto_reg_handoff_lcp(void)
3026 dissector_handle_t lcp_handle;
3028 lcp_handle = create_dissector_handle(dissect_lcp, proto_lcp);
3029 dissector_add("ppp.protocol", PPP_LCP, lcp_handle);
3032 * NDISWAN on Windows translates Ethernet frames from higher-level
3033 * protocols into PPP frames to hand to the PPP driver, and translates
3034 * PPP frames from the PPP driver to hand to the higher-level protocols.
3036 * Apparently the PPP driver, on at least some versions of Windows,
3037 * passes frames for internal-to-PPP protocols up through NDISWAN;
3038 * the protocol type field appears to be passed through unchanged
3039 * (unlike what's done with, for example, the protocol type field
3040 * for IP, which is mapped from its PPP value to its Ethernet value).
3042 * This means that we may see, on Ethernet captures, frames for
3043 * protocols internal to PPP, so we register PPP_LCP with the
3044 * "ethertype" dissector table as well as the PPP protocol dissector
3047 dissector_add("ethertype", PPP_LCP, lcp_handle);
3051 proto_register_ipcp(void)
3053 static gint *ett[] = {
3056 &ett_ipcp_ipaddrs_opt,
3057 &ett_ipcp_compressprot_opt,
3060 proto_ipcp = proto_register_protocol("PPP IP Control Protocol", "PPP IPCP",
3062 proto_register_subtree_array(ett, array_length(ett));
3066 proto_reg_handoff_ipcp(void)
3068 dissector_handle_t ipcp_handle;
3070 ipcp_handle = create_dissector_handle(dissect_ipcp, proto_ipcp);
3071 dissector_add("ppp.protocol", PPP_IPCP, ipcp_handle);
3074 * See above comment about NDISWAN for an explanation of why we're
3075 * registering with the "ethertype" dissector table.
3077 dissector_add("ethertype", PPP_IPCP, ipcp_handle);
3081 proto_register_ccp(void)
3083 static gint *ett[] = {
3088 &ett_ccp_bsdcomp_opt,
3089 &ett_ccp_lzsdcp_opt,
3091 &ett_ccp_deflate_opt,
3094 proto_ccp = proto_register_protocol("PPP Compression Control Protocol",
3096 proto_register_subtree_array(ett, array_length(ett));
3100 proto_reg_handoff_ccp(void)
3102 dissector_handle_t ccp_handle;
3104 ccp_handle = create_dissector_handle(dissect_ccp, proto_ccp);
3105 dissector_add("ppp.protocol", PPP_CCP, ccp_handle);
3108 * See above comment about NDISWAN for an explanation of why we're
3109 * registering with the "ethertype" dissector table.
3111 dissector_add("ethertype", PPP_CCP, ccp_handle);
3115 proto_register_cbcp(void)
3117 static gint *ett[] = {
3120 &ett_cbcp_callback_opt,
3121 &ett_cbcp_callback_opt_addr
3124 proto_cbcp = proto_register_protocol("PPP Callback Control Protocoll",
3125 "PPP CBCP", "cbcp");
3126 proto_register_subtree_array(ett, array_length(ett));
3130 proto_reg_handoff_cbcp(void)
3132 dissector_handle_t cbcp_handle;
3134 cbcp_handle = create_dissector_handle(dissect_cbcp, proto_cbcp);
3135 dissector_add("ppp.protocol", PPP_CBCP, cbcp_handle);
3138 * See above comment about NDISWAN for an explanation of why we're
3139 * registering with the "ethertype" dissector table.
3141 dissector_add("ethertype", PPP_CBCP, cbcp_handle);
3145 proto_register_bacp(void)
3147 static gint *ett[] = {
3150 &ett_bacp_favored_peer_opt
3153 proto_bacp = proto_register_protocol("PPP Bandwidth Allocation Control Protocol",
3154 "PPP BACP", "bacp");
3155 proto_register_subtree_array(ett, array_length(ett));
3159 proto_reg_handoff_bacp(void)
3161 dissector_handle_t bacp_handle;
3163 bacp_handle = create_dissector_handle(dissect_bacp, proto_bacp);
3164 dissector_add("ppp.protocol", PPP_BACP, bacp_handle);
3167 * See above comment about NDISWAN for an explanation of why we're
3168 * registering with the "ethertype" dissector table.
3170 dissector_add("ethertype", PPP_BACP, bacp_handle);
3174 proto_register_bap(void)
3176 static gint *ett[] = {
3179 &ett_bap_link_type_opt,
3180 &ett_bap_phone_delta_opt,
3181 &ett_bap_phone_delta_subopt,
3182 &ett_bap_call_status_opt
3185 proto_bap = proto_register_protocol("PPP Bandwidth Allocation Protocol",
3187 proto_register_subtree_array(ett, array_length(ett));
3191 proto_reg_handoff_bap(void)
3193 dissector_handle_t bap_handle;
3195 bap_handle = create_dissector_handle(dissect_bap, proto_bap);
3196 dissector_add("ppp.protocol", PPP_BAP, bap_handle);
3199 * See above comment about NDISWAN for an explanation of why we're
3200 * registering with the "ethertype" dissector table.
3202 dissector_add("ethertype", PPP_BAP, bap_handle);
3206 proto_register_comp_data(void)
3208 static gint *ett[] = {
3212 proto_comp_data = proto_register_protocol("PPP Compressed Datagram",
3213 "PPP Comp", "comp_data");
3214 proto_register_subtree_array(ett, array_length(ett));
3218 proto_reg_handoff_comp_data(void)
3220 dissector_handle_t comp_data_handle;
3222 comp_data_handle = create_dissector_handle(dissect_comp_data,
3224 dissector_add("ppp.protocol", PPP_COMP, comp_data_handle);
3227 * See above comment about NDISWAN for an explanation of why we're
3228 * registering with the "ethertype" dissector table.
3230 dissector_add("ethertype", PPP_COMP, comp_data_handle);
3234 proto_register_pap(void)
3236 static gint *ett[] = {
3244 proto_pap = proto_register_protocol("PPP Password Authentication Protocol", "PPP PAP",
3246 proto_register_subtree_array(ett, array_length(ett));
3250 proto_reg_handoff_pap(void)
3252 dissector_handle_t pap_handle;
3254 pap_handle = create_dissector_handle(dissect_pap, proto_pap);
3255 dissector_add("ppp.protocol", PPP_PAP, pap_handle);
3258 * See above comment about NDISWAN for an explanation of why we're
3259 * registering with the "ethertype" dissector table.
3261 dissector_add("ethertype", PPP_PAP, pap_handle);
3265 proto_register_chap(void)
3267 static gint *ett[] = {
3275 proto_chap = proto_register_protocol("PPP Challenge Handshake Authentication Protocol", "PPP CHAP",
3277 proto_register_subtree_array(ett, array_length(ett));
3281 proto_reg_handoff_chap(void)
3283 dissector_handle_t chap_handle;
3285 chap_handle = create_dissector_handle(dissect_chap, proto_chap);
3286 dissector_add("ppp.protocol", PPP_CHAP, chap_handle);
3289 * See above comment about NDISWAN for an explanation of why we're
3290 * registering with the "ethertype" dissector table.
3292 dissector_add("ethertype", PPP_CHAP, chap_handle);
3296 proto_register_pppmuxcp(void)
3298 static gint *ett[] = {
3300 &ett_pppmuxcp_options,
3303 proto_pppmuxcp = proto_register_protocol("PPPMux Control Protocol",
3306 proto_register_subtree_array(ett, array_length(ett));
3311 proto_reg_handoff_pppmuxcp(void)
3313 dissector_handle_t muxcp_handle;
3315 muxcp_handle = create_dissector_handle(dissect_pppmuxcp, proto_pppmuxcp);
3316 dissector_add("ppp.protocol", PPP_MUXCP, muxcp_handle);
3319 * See above comment about NDISWAN for an explanation of why we're
3320 * registering with the "ethertype" dissector table.
3322 dissector_add("ethertype", PPP_MUXCP, muxcp_handle);
3327 proto_register_pppmux(void)
3329 static gint *ett[] = {
3331 &ett_pppmux_subframe,
3332 &ett_pppmux_subframe_hdr,
3333 &ett_pppmux_subframe_flags,
3334 &ett_pppmux_subframe_info,
3337 proto_pppmux = proto_register_protocol("PPP Multiplexing",
3340 proto_register_subtree_array(ett, array_length(ett));
3344 proto_reg_handoff_pppmux(void)
3346 dissector_handle_t pppmux_handle;
3348 pppmux_handle = create_dissector_handle(dissect_pppmux, proto_pppmux);
3349 dissector_add("ppp.protocol", PPP_MUX, pppmux_handle);
3352 * See above comment about NDISWAN for an explanation of why we're
3353 * registering with the "ethertype" dissector table.
3355 dissector_add("ethertype", PPP_MUX, pppmux_handle);