2 * Routines for X.25 packet disassembly
3 * Olivier Abad <oabad@noos.fr>
7 * Wireshark - Network traffic analyzer
8 * By Gerald Combs <gerald@wireshark.org>
11 * This program is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU General Public License
13 * as published by the Free Software Foundation; either version 2
14 * of the License, or (at your option) any later version.
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 * GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, write to the Free Software
23 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
34 #include <epan/llcsaps.h>
35 #include <epan/packet.h>
36 #include <epan/circuit.h>
37 #include <epan/reassemble.h>
38 #include <epan/prefs.h>
39 #include <epan/emem.h>
40 #include <epan/nlpid.h>
41 #include <epan/x264_prt_id.h>
44 * Direction of packet.
47 X25_FROM_DCE, /* DCE->DTE */
48 X25_FROM_DTE, /* DTE->DCE */
49 X25_UNKNOWN /* direction unknown */
53 * 0 for data packets, 1 for non-data packets.
55 #define X25_NONDATA_BIT 0x01
57 #define X25_CALL_REQUEST 0x0B
58 #define X25_CALL_ACCEPTED 0x0F
59 #define X25_CLEAR_REQUEST 0x13
60 #define X25_CLEAR_CONFIRMATION 0x17
61 #define X25_INTERRUPT 0x23
62 #define X25_INTERRUPT_CONFIRMATION 0x27
63 #define X25_RESET_REQUEST 0x1B
64 #define X25_RESET_CONFIRMATION 0x1F
65 #define X25_RESTART_REQUEST 0xFB
66 #define X25_RESTART_CONFIRMATION 0xFF
67 #define X25_REGISTRATION_REQUEST 0xF3
68 #define X25_REGISTRATION_CONFIRMATION 0xF7
69 #define X25_DIAGNOSTIC 0xF1
75 #define PACKET_IS_DATA(type) (!(type & X25_NONDATA_BIT))
76 #define PACKET_TYPE_FC(type) (type & 0x1F)
78 #define X25_MBIT_MOD8 0x10
79 #define X25_MBIT_MOD128 0x01
81 #define X25_ABIT 0x8000
83 #define X25_QBIT 0x8000
84 #define X25_DBIT 0x4000
86 #define X25_FAC_CLASS_MASK 0xC0
88 #define X25_FAC_CLASS_A 0x00
89 #define X25_FAC_CLASS_B 0x40
90 #define X25_FAC_CLASS_C 0x80
91 #define X25_FAC_CLASS_D 0xC0
93 #define X25_FAC_COMP_MARK 0x00
94 #define X25_FAC_REVERSE 0x01
95 #define X25_FAC_THROUGHPUT 0x02
96 #define X25_FAC_CUG 0x03
97 #define X25_FAC_CALLED_MODIF 0x08
98 #define X25_FAC_CUG_OUTGOING_ACC 0x09
99 #define X25_FAC_THROUGHPUT_MIN 0x0A
100 #define X25_FAC_EXPRESS_DATA 0x0B
101 #define X25_FAC_BILATERAL_CUG 0x41
102 #define X25_FAC_PACKET_SIZE 0x42
103 #define X25_FAC_WINDOW_SIZE 0x43
104 #define X25_FAC_RPOA_SELECTION 0x44
105 #define X25_FAC_TRANSIT_DELAY 0x49
106 #define X25_FAC_CALL_TRANSFER 0xC3
107 #define X25_FAC_CALLED_ADDR_EXT 0xC9
108 #define X25_FAC_ETE_TRANSIT_DELAY 0xCA
109 #define X25_FAC_CALLING_ADDR_EXT 0xCB
110 #define X25_FAC_CALL_DEFLECT 0xD1
111 #define X25_FAC_PRIORITY 0xD2
113 static int proto_x25 = -1;
114 static int hf_x25_gfi = -1;
115 static int hf_x25_abit = -1;
116 static int hf_x25_qbit = -1;
117 static int hf_x25_dbit = -1;
118 static int hf_x25_mod = -1;
119 static int hf_x25_lcn = -1;
120 static int hf_x25_type = -1;
121 static int hf_x25_type_fc_mod8 = -1;
122 static int hf_x25_type_data = -1;
123 static int hf_x25_p_r_mod8 = -1;
124 static int hf_x25_p_r_mod128 = -1;
125 static int hf_x25_mbit_mod8 = -1;
126 static int hf_x25_mbit_mod128 = -1;
127 static int hf_x25_p_s_mod8 = -1;
128 static int hf_x25_p_s_mod128 = -1;
130 static gint ett_x25 = -1;
131 static gint ett_x25_gfi = -1;
132 static gint ett_x25_fac = -1;
133 static gint ett_x25_fac_unknown = -1;
134 static gint ett_x25_fac_mark = -1;
135 static gint ett_x25_fac_reverse = -1;
136 static gint ett_x25_fac_throughput = -1;
137 static gint ett_x25_fac_cug = -1;
138 static gint ett_x25_fac_called_modif = -1;
139 static gint ett_x25_fac_cug_outgoing_acc = -1;
140 static gint ett_x25_fac_throughput_min = -1;
141 static gint ett_x25_fac_express_data = -1;
142 static gint ett_x25_fac_bilateral_cug = -1;
143 static gint ett_x25_fac_packet_size = -1;
144 static gint ett_x25_fac_window_size = -1;
145 static gint ett_x25_fac_rpoa_selection = -1;
146 static gint ett_x25_fac_transit_delay = -1;
147 static gint ett_x25_fac_call_transfer = -1;
148 static gint ett_x25_fac_called_addr_ext = -1;
149 static gint ett_x25_fac_ete_transit_delay = -1;
150 static gint ett_x25_fac_calling_addr_ext = -1;
151 static gint ett_x25_fac_call_deflect = -1;
152 static gint ett_x25_fac_priority = -1;
153 static gint ett_x25_user_data = -1;
155 static gint ett_x25_segment = -1;
156 static gint ett_x25_segments = -1;
157 static gint hf_x25_segments = -1;
158 static gint hf_x25_segment = -1;
159 static gint hf_x25_segment_overlap = -1;
160 static gint hf_x25_segment_overlap_conflict = -1;
161 static gint hf_x25_segment_multiple_tails = -1;
162 static gint hf_x25_segment_too_long_segment = -1;
163 static gint hf_x25_segment_error = -1;
165 static const value_string vals_modulo[] = {
171 static const value_string vals_x25_type[] = {
172 { X25_CALL_REQUEST, "Call" },
173 { X25_CALL_ACCEPTED, "Call Accepted" },
174 { X25_CLEAR_REQUEST, "Clear" },
175 { X25_CLEAR_CONFIRMATION, "Clear Confirmation" },
176 { X25_INTERRUPT, "Interrupt" },
177 { X25_INTERRUPT_CONFIRMATION, "Interrupt Confirmation" },
178 { X25_RESET_REQUEST, "Reset" },
179 { X25_RESET_CONFIRMATION, "Reset Confirmation" },
180 { X25_RESTART_REQUEST, "Restart" },
181 { X25_RESTART_CONFIRMATION, "Restart Confirmation" },
182 { X25_REGISTRATION_REQUEST, "Registration" },
183 { X25_REGISTRATION_CONFIRMATION, "Registration Confirmation" },
184 { X25_DIAGNOSTIC, "Diagnostic" },
188 { X25_DATA, "Data" },
192 static struct true_false_string m_bit_tfs = {
197 static const fragment_items x25_frag_items = {
202 &hf_x25_segment_overlap,
203 &hf_x25_segment_overlap_conflict,
204 &hf_x25_segment_multiple_tails,
205 &hf_x25_segment_too_long_segment,
206 &hf_x25_segment_error,
211 static dissector_handle_t ip_handle;
212 static dissector_handle_t clnp_handle;
213 static dissector_handle_t ositp_handle;
214 static dissector_handle_t qllc_handle;
215 static dissector_handle_t data_handle;
218 static gboolean payload_is_qllc_sna = FALSE;
219 static gboolean reassemble_x25 = TRUE;
221 /* Reassembly of X.25 */
223 static GHashTable *x25_segment_table = NULL;
224 static GHashTable *x25_reassembled_table = NULL;
226 static dissector_table_t x25_subdissector_table;
227 static heur_dissector_list_t x25_heur_subdissector_list;
230 x25_hash_add_proto_start(guint16 vc, guint32 frame, dissector_handle_t dissect)
235 * Is there already a circuit with this VC number?
237 circuit = find_circuit(CT_X25, vc, frame);
238 if (circuit != NULL) {
240 * Yes - close it, as we're creating a new one.
242 close_circuit(circuit, frame - 1);
246 * Set up a new circuit.
248 circuit = circuit_new(CT_X25, vc, frame);
253 circuit_set_dissector(circuit, dissect);
257 x25_hash_add_proto_end(guint16 vc, guint32 frame)
262 * Try to find the circuit.
264 circuit = find_circuit(CT_X25, vc, frame);
267 * If we succeeded, close it.
270 close_circuit(circuit, frame);
273 static const char *clear_code(unsigned char code)
277 if (code == 0x00 || (code & 0x80) == 0x80)
278 return "DTE Originated";
280 return "Number Busy";
282 return "Invalid Facility Requested";
284 return "Network Congestion";
286 return "Out Of Order";
288 return "Access Barred";
290 return "Not Obtainable";
292 return "Remote Procedure Error";
294 return "Local Procedure Error";
296 return "RPOA Out Of Order";
298 return "Reverse Charging Acceptance Not Subscribed";
300 return "Incompatible Destination";
302 return "Fast Select Acceptance Not Subscribed";
304 return "Destination Absent";
307 g_snprintf(buffer, 32, "Unknown %02X", code);
312 static const char *clear_diag(unsigned char code)
317 return "No additional information";
319 return "Invalid P(S)";
321 return "Invalid P(R)";
323 return "Packet type invalid";
325 return "Packet type invalid for state r1";
327 return "Packet type invalid for state r2";
329 return "Packet type invalid for state r3";
331 return "Packet type invalid for state p1";
333 return "Packet type invalid for state p2";
335 return "Packet type invalid for state p3";
337 return "Packet type invalid for state p4";
339 return "Packet type invalid for state p5";
341 return "Packet type invalid for state p6";
343 return "Packet type invalid for state p7";
345 return "Packet type invalid for state d1";
347 return "Packet type invalid for state d2";
349 return "Packet type invalid for state d3";
351 return "Packet not allowed";
353 return "Unidentifiable packet";
355 return "Call on one-way logical channel";
357 return "Invalid packet type on a PVC";
359 return "Packet on unassigned LC";
361 return "Reject not subscribed to";
363 return "Packet too short";
365 return "Packet too long";
367 return "Invalid general format identifier";
369 return "Restart/registration packet with nonzero bits";
371 return "Packet type not compatible with facility";
373 return "Unauthorised interrupt confirmation";
375 return "Unauthorised interrupt";
377 return "Unauthorised reject";
379 return "Time expired";
381 return "Time expired for incoming call";
383 return "Time expired for clear indication";
385 return "Time expired for reset indication";
387 return "Time expired for restart indication";
389 return "Time expired for call deflection";
391 return "Call set-up/clearing or registration pb.";
393 return "Facility/registration code not allowed";
395 return "Facility parameter not allowed";
397 return "Invalid called DTE address";
399 return "Invalid calling DTE address";
401 return "Invalid facility/registration length";
403 return "Incoming call barred";
405 return "No logical channel available";
407 return "Call collision";
409 return "Duplicate facility requested";
411 return "Non zero address length";
413 return "Non zero facility length";
415 return "Facility not provided when expected";
417 return "Invalid CCITT-specified DTE facility";
419 return "Max. nb of call redir/defl. exceeded";
421 return "Miscellaneous";
423 return "Improper cause code from DTE";
425 return "Not aligned octet";
427 return "Inconsistent Q bit setting";
429 return "NUI problem";
431 return "International problem";
433 return "Remote network problem";
435 return "International protocol problem";
437 return "International link out of order";
439 return "International link busy";
441 return "Transit network facility problem";
443 return "Remote network facility problem";
445 return "International routing problem";
447 return "Temporary routing problem";
449 return "Unknown called DNIC";
451 return "Maintenance action";
453 return "Timer expired or retransmission count surpassed";
455 return "Timer expired or retransmission count surpassed for INTERRUPT";
457 return "Timer expired or retransmission count surpassed for DATA "
458 "packet transmission";
460 return "Timer expired or retransmission count surpassed for REJECT";
462 return "DTE-specific signals";
464 return "DTE operational";
466 return "DTE not operational";
468 return "DTE resource constraint";
470 return "Fast select not subscribed";
472 return "Invalid partially full DATA packet";
474 return "D-bit procedure not supported";
476 return "Registration/Cancellation confirmed";
478 return "OSI network service problem";
480 return "Disconnection (transient condition)";
482 return "Disconnection (permanent condition)";
484 return "Connection rejection - reason unspecified (transient "
487 return "Connection rejection - reason unspecified (permanent "
490 return "Connection rejection - quality of service not available "
491 "transient condition)";
493 return "Connection rejection - quality of service not available "
494 "permanent condition)";
496 return "Connection rejection - NSAP unreachable (transient condition)";
498 return "Connection rejection - NSAP unreachable (permanent condition)";
500 return "reset - reason unspecified";
502 return "reset - congestion";
504 return "Connection rejection - NSAP address unknown (permanent "
507 return "Higher layer initiated";
509 return "Disconnection - normal";
511 return "Disconnection - abnormal";
513 return "Disconnection - incompatible information in user data";
515 return "Connection rejection - reason unspecified (transient "
518 return "Connection rejection - reason unspecified (permanent "
521 return "Connection rejection - quality of service not available "
522 "(transient condition)";
524 return "Connection rejection - quality of service not available "
525 "(permanent condition)";
527 return "Connection rejection - incompatible information in user data";
529 return "Connection rejection - unrecognizable protocol indentifier "
532 return "Reset - user resynchronization";
535 g_snprintf(buffer, 32, "Unknown %d", code);
540 static const char *reset_code(unsigned char code)
544 if (code == 0x00 || (code & 0x80) == 0x80)
545 return "DTE Originated";
547 return "Out of order";
549 return "Remote Procedure Error";
551 return "Local Procedure Error";
553 return "Network Congestion";
555 return "Remote DTE operational";
557 return "Network operational";
559 return "Incompatible Destination";
561 return "Network out of order";
564 g_snprintf(buffer, 32, "Unknown %02X", code);
569 static const char *restart_code(unsigned char code)
573 if (code == 0x00 || (code & 0x80) == 0x80)
574 return "DTE Originated";
576 return "Local Procedure Error";
578 return "Network Congestion";
580 return "Network Operational";
582 return "Registration/cancellation confirmed";
585 g_snprintf(buffer, 32, "Unknown %02X", code);
590 static const char *registration_code(unsigned char code)
595 return "Invalid facility request";
597 return "Network congestion";
599 return "Local procedure error";
601 return "Registration/cancellation confirmed";
604 g_snprintf(buffer, 32, "Unknown %02X", code);
610 dump_facilities(proto_tree *tree, int *offset, tvbuff_t *tvb)
612 guint8 fac, byte1, byte2, byte3;
613 guint32 len; /* facilities length */
615 proto_tree *fac_tree = 0;
616 proto_tree *fac_subtree;
618 len = tvb_get_guint8(tvb, *offset);
620 ti = proto_tree_add_text(tree, tvb, *offset, len + 1,
622 fac_tree = proto_item_add_subtree(ti, ett_x25_fac);
623 proto_tree_add_text(fac_tree, tvb, *offset, 1,
624 "Facilities length: %d", len);
629 fac = tvb_get_guint8(tvb, *offset);
630 switch(fac & X25_FAC_CLASS_MASK) {
631 case X25_FAC_CLASS_A:
633 case X25_FAC_COMP_MARK:
635 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1,
636 "Code : 00 (Marker)");
637 switch (tvb_get_guint8(tvb, *offset + 1)) {
640 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_mark);
641 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
642 "Parameter : 00 (Network complementary "
643 "services - calling DTE)");
648 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_mark);
649 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
650 "Parameter : FF (Network complementary "
651 "services - called DTE)");
656 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_mark);
657 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
658 "Parameter : 0F (DTE complementary "
664 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_mark);
665 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
666 "Parameter : %02X (Unknown marker)",
667 tvb_get_guint8(tvb, *offset+1));
672 case X25_FAC_REVERSE:
674 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
675 "(Reverse charging / Fast select)", fac);
676 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_reverse);
677 byte1 = tvb_get_guint8(tvb, *offset + 1);
678 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
679 "Parameter : %02X", byte1);
681 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
682 "11.. .... = Fast select with restriction");
683 else if (byte1 & 0x80)
684 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
685 "10.. .... = Fast select - no restriction");
687 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
688 "00.. .... = Fast select not requested");
689 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
690 decode_boolean_bitfield(byte1, 0x01, 1*8,
691 "Reverse charging requested",
692 "Reverse charging not requested"));
695 case X25_FAC_THROUGHPUT:
700 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
701 "(Throughput class negotiation)", fac);
702 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_throughput);
703 byte1 = tvb_get_guint8(tvb, *offset + 1);
715 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (%d bps)",
716 75*(1<<((byte1 >> 4)-3)));
719 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (48000 bps)");
722 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (64000 bps)");
725 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (Reserved)");
727 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
728 decode_numeric_bitfield(byte1, 0xF0, 1*8, tmpbuf));
729 switch (byte1 & 0x0F)
740 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (%d bps)",
741 75*(1<<((byte1 & 0x0F)-3)));
744 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (48000 bps)");
747 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (64000 bps)");
750 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (Reserved)");
752 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
753 decode_numeric_bitfield(byte1, 0x0F, 1*8, tmpbuf));
758 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
759 "(Closed user group selection)", fac);
760 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_cug);
761 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
762 "Closed user group: %02X", tvb_get_guint8(tvb, *offset+1));
765 case X25_FAC_CALLED_MODIF:
767 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
768 "(Called address modified)", fac);
769 fac_subtree = proto_item_add_subtree(ti,
770 ett_x25_fac_called_modif);
771 proto_tree_add_text(fac_tree, tvb, *offset+1, 1,
772 "Parameter %02X", tvb_get_guint8(tvb, *offset+1));
775 case X25_FAC_CUG_OUTGOING_ACC:
777 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
778 "(Closed user group with outgoing access selection)",
780 fac_subtree = proto_item_add_subtree(ti,
781 ett_x25_fac_cug_outgoing_acc);
782 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
783 "Closed user group: %02X", tvb_get_guint8(tvb, *offset+1));
786 case X25_FAC_THROUGHPUT_MIN:
788 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
789 "(Minimum throughput class)", fac);
790 fac_subtree = proto_item_add_subtree(ti,
791 ett_x25_fac_throughput_min);
792 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
793 "Parameter %02X", tvb_get_guint8(tvb, *offset+1));
796 case X25_FAC_EXPRESS_DATA:
798 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
799 "(Negotiation of express data)", fac);
800 fac_subtree = proto_item_add_subtree(ti,
801 ett_x25_fac_express_data);
802 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
803 "Parameter %02X", tvb_get_guint8(tvb, *offset+1));
808 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1,
809 "Code : %02X (Unknown class A)", fac);
810 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_unknown);
811 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
812 "Parameter %02X", tvb_get_guint8(tvb, *offset+1));
819 case X25_FAC_CLASS_B:
821 case X25_FAC_BILATERAL_CUG:
823 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
824 "(Bilateral closed user group selection)", fac);
825 fac_subtree = proto_item_add_subtree(ti,
826 ett_x25_fac_bilateral_cug);
827 proto_tree_add_text(fac_subtree, tvb, *offset+1, 2,
828 "Bilateral CUG: %04X",
829 tvb_get_ntohs(tvb, *offset+1));
832 case X25_FAC_PACKET_SIZE:
838 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
839 "(Packet size)", fac);
840 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_packet_size);
841 byte1 = tvb_get_guint8(tvb, *offset + 1);
845 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (16)");
848 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (32)");
851 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (64)");
854 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (128)");
857 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (256)");
860 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (512)");
863 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (1024)");
866 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (2048)");
869 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (4096)");
872 g_snprintf(tmpbuf, 80, "From the called DTE : %%u (Unknown)");
875 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
876 decode_numeric_bitfield(byte1, 0x0F, 1*8, tmpbuf));
878 byte2 = tvb_get_guint8(tvb, *offset + 1);
882 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (16)");
885 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (32)");
888 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (64)");
891 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (128)");
894 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (256)");
897 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (512)");
900 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (1024)");
903 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (2048)");
906 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (4096)");
909 g_snprintf(tmpbuf, 80, "From the calling DTE : %%u (Unknown)");
912 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
913 decode_numeric_bitfield(byte2, 0x0F, 1*8, tmpbuf));
916 case X25_FAC_WINDOW_SIZE:
918 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
919 "(Window size)", fac);
920 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_window_size);
921 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
922 decode_numeric_bitfield(tvb_get_guint8(tvb, *offset+1),
923 0x7F, 1*8, "From the called DTE: %u"));
924 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
925 decode_numeric_bitfield(tvb_get_guint8(tvb, *offset+2),
926 0x7F, 1*8, "From the calling DTE: %u"));
929 case X25_FAC_RPOA_SELECTION:
931 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
932 "(RPOA selection)", fac);
933 fac_subtree = proto_item_add_subtree(ti,
934 ett_x25_fac_rpoa_selection);
935 proto_tree_add_text(fac_subtree, tvb, *offset+1, 2,
936 "Data network identification code : %04X",
937 tvb_get_ntohs(tvb, *offset+1));
940 case X25_FAC_TRANSIT_DELAY:
942 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
943 "(Transit delay selection and indication)", fac);
944 fac_subtree = proto_item_add_subtree(ti,
945 ett_x25_fac_transit_delay);
946 proto_tree_add_text(fac_subtree, tvb, *offset+1, 2,
947 "Transit delay: %d ms",
948 tvb_get_ntohs(tvb, *offset+1));
953 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1,
954 "Code : %02X (Unknown class B)", fac);
955 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_unknown);
956 proto_tree_add_text(fac_subtree, tvb, *offset+1, 2,
957 "Parameter %04X", tvb_get_ntohs(tvb, *offset+1));
964 case X25_FAC_CLASS_C:
966 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1,
967 "Code : %02X (Unknown class C)", fac);
968 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_unknown);
969 proto_tree_add_text(fac_subtree, tvb, *offset+1, 3,
971 tvb_get_ntoh24(tvb, *offset+1));
976 case X25_FAC_CLASS_D:
978 case X25_FAC_CALL_TRANSFER:
983 tmpbuf=ep_alloc(258);
984 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
985 "(Call redirection or deflection notification)", fac);
986 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_call_transfer);
987 byte1 = tvb_get_guint8(tvb, *offset+1);
989 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
990 "Bogus length : %d", byte1);
993 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
994 "Length : %u", byte1);
996 byte2 = tvb_get_guint8(tvb, *offset+2);
997 if ((byte2 & 0xC0) == 0xC0) {
998 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
999 "Reason : call deflection by the originally "
1000 "called DTE address");
1005 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1006 "Reason : originally called DTE busy");
1009 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1010 "Reason : call dist. within a hunt group");
1013 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1014 "Reason : originally called DTE out of order");
1017 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1018 "Reason : systematic call redirection");
1021 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1022 "Reason : unknown");
1026 byte3 = tvb_get_guint8(tvb, *offset+3);
1027 proto_tree_add_text(fac_subtree, tvb, *offset+3, 1,
1028 "Number of semi-octets in DTE address : %u",
1030 for (i = 0; (i<byte3)&&(i<256); i++) {
1032 tmpbuf[i] = ((tvb_get_guint8(tvb, *offset+4+i/2) >> 4)
1034 /* if > 9, convert to the right hexadecimal letter */
1035 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1037 tmpbuf[i] = (tvb_get_guint8(tvb, *offset+4+i/2)
1039 /* if > 9, convert to the right hexadecimal letter */
1040 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1044 proto_tree_add_text(fac_subtree, tvb, *offset+4, byte1 - 2,
1045 "DTE address : %s", tmpbuf);
1048 case X25_FAC_CALLING_ADDR_EXT:
1053 tmpbuf=ep_alloc(258);
1054 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
1055 "(Calling address extension)", fac);
1056 fac_subtree = proto_item_add_subtree(ti,
1057 ett_x25_fac_calling_addr_ext);
1058 byte1 = tvb_get_guint8(tvb, *offset+1);
1060 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1061 "Bogus length : %d", byte1);
1064 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1065 "Length : %u", byte1);
1067 byte2 = tvb_get_guint8(tvb, *offset+2) & 0x3F;
1068 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1069 "Number of semi-octets in DTE address : %u", byte2);
1070 for (i = 0; (i<byte2)&&(i<256) ; i++) {
1072 tmpbuf[i] = ((tvb_get_guint8(tvb, *offset+3+i/2) >> 4)
1074 /* if > 9, convert to the right hexadecimal letter */
1075 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1077 tmpbuf[i] = (tvb_get_guint8(tvb, *offset+3+i/2)
1079 /* if > 9, convert to the right hexadecimal letter */
1080 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1084 proto_tree_add_text(fac_subtree, tvb, *offset+3, byte1 - 1,
1085 "DTE address : %s", tmpbuf);
1088 case X25_FAC_CALLED_ADDR_EXT:
1093 tmpbuf=ep_alloc(258);
1094 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
1095 "(Called address extension)", fac);
1096 fac_subtree = proto_item_add_subtree(ti,
1097 ett_x25_fac_called_addr_ext);
1098 byte1 = tvb_get_guint8(tvb, *offset+1);
1100 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1101 "Bogus length : %d", byte1);
1104 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1105 "Length : %u", byte1);
1107 byte2 = tvb_get_guint8(tvb, *offset+2) & 0x3F;
1108 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1109 "Number of semi-octets in DTE address : %u", byte2);
1110 for (i = 0; (i<byte2)&&(i<256) ; i++) {
1112 tmpbuf[i] = ((tvb_get_guint8(tvb, *offset+3+i/2) >> 4)
1114 /* if > 9, convert to the right hexadecimal letter */
1115 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1117 tmpbuf[i] = (tvb_get_guint8(tvb, *offset+3+i/2)
1119 /* if > 9, convert to the right hexadecimal letter */
1120 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1124 proto_tree_add_text(fac_subtree, tvb, *offset+3, byte1 - 1,
1125 "DTE address : %s", tmpbuf);
1128 case X25_FAC_ETE_TRANSIT_DELAY:
1130 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
1131 "(End to end transit delay)", fac);
1132 fac_subtree = proto_item_add_subtree(ti,
1133 ett_x25_fac_ete_transit_delay);
1134 byte1 = tvb_get_guint8(tvb, *offset+1);
1135 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1136 "Length : %u", byte1);
1137 proto_tree_add_text(fac_subtree, tvb, *offset+2, byte1, "Value");
1140 case X25_FAC_CALL_DEFLECT:
1145 tmpbuf=ep_alloc(258);
1146 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1, "Code : %02X "
1147 "(Call deflection selection)", fac);
1148 fac_subtree = proto_item_add_subtree(ti,
1149 ett_x25_fac_call_deflect);
1150 byte1 = tvb_get_guint8(tvb, *offset+1);
1152 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1153 "Bogus length : %d", byte1);
1156 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1157 "Length : %u", byte1);
1159 byte2 = tvb_get_guint8(tvb, *offset+2);
1160 if ((byte2 & 0xC0) == 0xC0)
1161 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1162 "Reason : call DTE originated");
1164 proto_tree_add_text(fac_subtree, tvb, *offset+2, 1,
1165 "Reason : unknown");
1166 byte3 = tvb_get_guint8(tvb, *offset+3);
1167 proto_tree_add_text(fac_subtree, tvb, *offset+3, 1,
1168 "Number of semi-octets in the alternative DTE address : %u",
1170 for (i = 0; (i<byte3)&&(i<256) ; i++) {
1172 tmpbuf[i] = ((tvb_get_guint8(tvb, *offset+4+i/2) >> 4)
1174 /* if > 9, convert to the right hexadecimal letter */
1175 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1177 tmpbuf[i] = (tvb_get_guint8(tvb, *offset+4+i/2)
1179 /* if > 9, convert to the right hexadecimal letter */
1180 if (tmpbuf[i] > '9') tmpbuf[i] += ('A' - '0' - 10);
1184 proto_tree_add_text(fac_subtree, tvb, *offset+4, byte1 - 2,
1185 "Alternative DTE address : %s", tmpbuf);
1188 case X25_FAC_PRIORITY:
1190 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1,
1191 "Code : %02X (Priority)", fac);
1192 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_priority);
1193 byte1 = tvb_get_guint8(tvb, *offset+1);
1194 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1195 "Length : %u", byte1);
1196 proto_tree_add_text(fac_subtree, tvb, *offset+2, byte1, "Value");
1201 ti = proto_tree_add_text(fac_tree, tvb, *offset, 1,
1202 "Code : %02X (Unknown class D)", fac);
1203 fac_subtree = proto_item_add_subtree(ti, ett_x25_fac_unknown);
1204 byte1 = tvb_get_guint8(tvb, *offset+1);
1205 proto_tree_add_text(fac_subtree, tvb, *offset+1, 1,
1206 "Length : %u", byte1);
1207 proto_tree_add_text(fac_subtree, tvb, *offset+2, byte1, "Value");
1210 byte1 = tvb_get_guint8(tvb, *offset+1);
1211 (*offset) += byte1+2;
1219 x25_ntoa(proto_tree *tree, int *offset, tvbuff_t *tvb,
1220 packet_info *pinfo, gboolean is_registration)
1224 char *addr1, *addr2;
1225 char *first, *second;
1232 byte = tvb_get_guint8(tvb, *offset);
1233 len1 = (byte >> 0) & 0x0F;
1234 len2 = (byte >> 4) & 0x0F;
1237 proto_tree_add_text(tree, tvb, *offset, 1,
1238 decode_numeric_bitfield(byte, 0xF0, 1*8,
1240 "DTE address length : %u" :
1241 "Calling address length : %u"));
1242 proto_tree_add_text(tree, tvb, *offset, 1,
1243 decode_numeric_bitfield(byte, 0x0F, 1*8,
1245 "DCE address length : %u" :
1246 "Called address length : %u"));
1250 localoffset = *offset;
1251 byte = tvb_get_guint8(tvb, localoffset);
1255 for (i = 0; i < (len1 + len2); i++) {
1258 *first++ = ((byte >> 0) & 0x0F) + '0';
1260 byte = tvb_get_guint8(tvb, localoffset);
1262 *first++ = ((byte >> 4) & 0x0F) + '0';
1266 *second++ = ((byte >> 0) & 0x0F) + '0';
1268 byte = tvb_get_guint8(tvb, localoffset);
1270 *second++ = ((byte >> 4) & 0x0F) + '0';
1279 if (check_col(pinfo->cinfo, COL_RES_DL_DST))
1280 col_add_str(pinfo->cinfo, COL_RES_DL_DST, addr1);
1282 proto_tree_add_text(tree, tvb, *offset,
1285 "DCE address : %s" :
1286 "Called address : %s",
1290 if (check_col(pinfo->cinfo, COL_RES_DL_SRC))
1291 col_add_str(pinfo->cinfo, COL_RES_DL_SRC, addr2);
1293 proto_tree_add_text(tree, tvb, *offset + len1/2,
1294 (len2+1)/2+(len1%2+(len2+1)%2)/2,
1296 "DTE address : %s" :
1297 "Calling address : %s",
1300 (*offset) += ((len1 + len2 + 1) / 2);
1304 x25_toa(proto_tree *tree, int *offset, tvbuff_t *tvb,
1309 char *addr1, *addr2;
1310 char *first, *second;
1314 addr1=ep_alloc(256);
1315 addr2=ep_alloc(256);
1317 len1 = tvb_get_guint8(tvb, *offset);
1319 proto_tree_add_text(tree, tvb, *offset, 1,
1320 "Called address length : %u",
1325 len2 = tvb_get_guint8(tvb, *offset);
1327 proto_tree_add_text(tree, tvb, *offset, 1,
1328 "Calling address length : %u",
1333 localoffset = *offset;
1334 byte = tvb_get_guint8(tvb, localoffset);
1337 * XXX - the first two half-octets of the address are the TOA and
1338 * NPI; process them as such and, if the TOA says an address is
1339 * an alternative address, process it correctly (i.e., not as a
1340 * sequence of half-octets containing digit values).
1344 for (i = 0; i < (len1 + len2); i++) {
1347 *first++ = ((byte >> 0) & 0x0F) + '0';
1349 byte = tvb_get_guint8(tvb, localoffset);
1351 *first++ = ((byte >> 4) & 0x0F) + '0';
1355 *second++ = ((byte >> 0) & 0x0F) + '0';
1357 byte = tvb_get_guint8(tvb, localoffset);
1359 *second++ = ((byte >> 4) & 0x0F) + '0';
1368 if (check_col(pinfo->cinfo, COL_RES_DL_DST))
1369 col_add_str(pinfo->cinfo, COL_RES_DL_DST, addr1);
1371 proto_tree_add_text(tree, tvb, *offset,
1373 "Called address : %s",
1377 if (check_col(pinfo->cinfo, COL_RES_DL_SRC))
1378 col_add_str(pinfo->cinfo, COL_RES_DL_SRC, addr2);
1380 proto_tree_add_text(tree, tvb, *offset + len1/2,
1381 (len2+1)/2+(len1%2+(len2+1)%2)/2,
1382 "Calling address : %s",
1385 (*offset) += ((len1 + len2 + 1) / 2);
1389 get_x25_pkt_len(tvbuff_t *tvb)
1391 guint length, called_len, calling_len, dte_len, dce_len;
1392 guint8 byte2, bytex;
1394 byte2 = tvb_get_guint8(tvb, 2);
1397 case X25_CALL_REQUEST:
1398 bytex = tvb_get_guint8(tvb, 3);
1399 called_len = (bytex >> 0) & 0x0F;
1400 calling_len = (bytex >> 4) & 0x0F;
1401 length = 4 + (called_len + calling_len + 1) / 2; /* addr */
1402 if (length < tvb_reported_length(tvb))
1403 length += (1 + tvb_get_guint8(tvb, length)); /* facilities */
1405 return MIN(tvb_reported_length(tvb),length);
1407 case X25_CALL_ACCEPTED:
1408 /* The calling/called address length byte (following the packet type)
1409 * is not mandatory, so we must check the packet length before trying
1411 if (tvb_reported_length(tvb) == 3)
1413 bytex = tvb_get_guint8(tvb, 3);
1414 called_len = (bytex >> 0) & 0x0F;
1415 calling_len = (bytex >> 4) & 0x0F;
1416 length = 4 + (called_len + calling_len + 1) / 2; /* addr */
1417 if (length < tvb_reported_length(tvb))
1418 length += (1 + tvb_get_guint8(tvb, length)); /* facilities */
1420 return MIN(tvb_reported_length(tvb),length);
1422 case X25_CLEAR_REQUEST:
1423 case X25_RESET_REQUEST:
1424 case X25_RESTART_REQUEST:
1425 return MIN(tvb_reported_length(tvb),5);
1427 case X25_DIAGNOSTIC:
1428 return MIN(tvb_reported_length(tvb),4);
1430 case X25_CLEAR_CONFIRMATION:
1432 case X25_INTERRUPT_CONFIRMATION:
1433 case X25_RESET_CONFIRMATION:
1434 case X25_RESTART_CONFIRMATION:
1435 return MIN(tvb_reported_length(tvb),3);
1437 case X25_REGISTRATION_REQUEST:
1438 bytex = tvb_get_guint8(tvb, 3);
1439 dce_len = (bytex >> 0) & 0x0F;
1440 dte_len = (bytex >> 4) & 0x0F;
1441 length = 4 + (dte_len + dce_len + 1) / 2; /* addr */
1442 if (length < tvb_reported_length(tvb))
1443 length += (1 + tvb_get_guint8(tvb, length)); /* registration */
1445 return MIN(tvb_reported_length(tvb),length);
1447 case X25_REGISTRATION_CONFIRMATION:
1448 bytex = tvb_get_guint8(tvb, 5);
1449 dce_len = (bytex >> 0) & 0x0F;
1450 dte_len = (bytex >> 4) & 0x0F;
1451 length = 6 + (dte_len + dce_len + 1) / 2; /* addr */
1452 if (length < tvb_reported_length(tvb))
1453 length += (1 + tvb_get_guint8(tvb, length)); /* registration */
1455 return MIN(tvb_reported_length(tvb),length);
1458 if (PACKET_IS_DATA(byte2))
1459 return MIN(tvb_reported_length(tvb),3);
1461 switch (PACKET_TYPE_FC(byte2))
1464 return MIN(tvb_reported_length(tvb),3);
1467 return MIN(tvb_reported_length(tvb),3);
1470 return MIN(tvb_reported_length(tvb),3);
1476 static const value_string prt_id_vals[] = {
1477 {PRT_ID_ISO_8073, "ISO 8073 COTP"},
1478 {PRT_ID_ISO_8602, "ISO 8602 CLTP"},
1479 {PRT_ID_ISO_10736_ISO_8073, "ISO 10736 in conjunction with ISO 8073 COTP"},
1480 {PRT_ID_ISO_10736_ISO_8602, "ISO 10736 in conjunction with ISO 8602 CLTP"},
1484 static const value_string sharing_strategy_vals[] = {
1485 {0x00, "No sharing"},
1490 dissect_x25_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1491 x25_dir_t dir, gboolean side)
1493 proto_tree *x25_tree=0, *gfi_tree=0, *userdata_tree=0;
1495 guint localoffset=0;
1499 dissector_handle_t dissect = NULL;
1500 gboolean toa; /* TOA/NPI address format */
1503 const char *short_name = NULL, *long_name = NULL;
1504 tvbuff_t *next_tvb = NULL;
1505 gboolean q_bit_set = FALSE;
1509 void *saved_private_data;
1510 fragment_data *fd_head;
1516 if (check_col(pinfo->cinfo, COL_PROTOCOL))
1517 col_set_str(pinfo->cinfo, COL_PROTOCOL, "X.25");
1519 bytes0_1 = tvb_get_ntohs(tvb, 0);
1521 modulo = ((bytes0_1 & 0x2000) ? 128 : 8);
1522 vc = (int)(bytes0_1 & 0x0FFF);
1524 pinfo->ctype = CT_X25;
1525 pinfo->circuit_id = vc;
1527 if (bytes0_1 & X25_ABIT) toa = TRUE;
1530 x25_pkt_len = get_x25_pkt_len(tvb);
1531 if (x25_pkt_len < 3) /* packet too short */
1533 if (check_col(pinfo->cinfo, COL_INFO))
1534 col_set_str(pinfo->cinfo, COL_INFO, "Invalid/short X.25 packet");
1536 proto_tree_add_protocol_format(tree, proto_x25, tvb, 0, -1,
1537 "Invalid/short X.25 packet");
1541 pkt_type = tvb_get_guint8(tvb, 2);
1542 if (PACKET_IS_DATA(pkt_type)) {
1543 if (bytes0_1 & X25_QBIT)
1548 ti = proto_tree_add_item(tree, proto_x25, tvb, 0, x25_pkt_len, FALSE);
1549 x25_tree = proto_item_add_subtree(ti, ett_x25);
1550 ti = proto_tree_add_item(x25_tree, hf_x25_gfi, tvb, 0, 2, FALSE);
1551 gfi_tree = proto_item_add_subtree(ti, ett_x25_gfi);
1553 if (PACKET_IS_DATA(pkt_type)) {
1554 proto_tree_add_boolean(gfi_tree, hf_x25_qbit, tvb, 0, 2,
1557 else if (pkt_type == X25_CALL_REQUEST ||
1558 pkt_type == X25_CALL_ACCEPTED ||
1559 pkt_type == X25_CLEAR_REQUEST ||
1560 pkt_type == X25_CLEAR_CONFIRMATION) {
1561 proto_tree_add_boolean(gfi_tree, hf_x25_abit, tvb, 0, 2,
1565 if (pkt_type == X25_CALL_REQUEST || pkt_type == X25_CALL_ACCEPTED ||
1566 PACKET_IS_DATA(pkt_type)) {
1567 proto_tree_add_boolean(gfi_tree, hf_x25_dbit, tvb, 0, 2,
1570 proto_tree_add_uint(gfi_tree, hf_x25_mod, tvb, 0, 2, bytes0_1);
1574 case X25_CALL_REQUEST:
1578 short_name = "Inc. call";
1579 long_name = "Incoming call";
1583 short_name = "Call req.";
1584 long_name = "Call request";
1588 short_name = "Inc. call/Call req.";
1589 long_name = "Incoming call/Call request";
1592 if (check_col(pinfo->cinfo, COL_INFO))
1593 col_add_fstr(pinfo->cinfo, COL_INFO, "%s VC:%d", short_name, vc);
1595 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb,
1597 proto_tree_add_uint_format(x25_tree, hf_x25_type, tvb, 2, 1,
1598 X25_CALL_REQUEST, "Packet Type: %s", long_name);
1601 if (localoffset < x25_pkt_len) { /* calling/called addresses */
1603 x25_toa(x25_tree, (gint*)&localoffset, tvb, pinfo);
1605 x25_ntoa(x25_tree, (gint*)&localoffset, tvb, pinfo, FALSE);
1608 if (localoffset < x25_pkt_len) /* facilities */
1609 dump_facilities(x25_tree, (gint*)&localoffset, tvb);
1611 if (localoffset < tvb_reported_length(tvb)) /* user data */
1615 ti = proto_tree_add_text(x25_tree, tvb, localoffset, -1,
1617 userdata_tree = proto_item_add_subtree(ti, ett_x25_user_data);
1620 /* X.263/ISO 9577 says that:
1622 When CLNP or ESIS are run over X.25, the SPI
1623 is 0x81 or 0x82, respectively; those are the
1624 NLPIDs for those protocol.
1626 When X.224/ISO 8073 COTP is run over X.25, and
1627 when ISO 11570 explicit identification is being
1628 used, the first octet of the user data field is
1629 a TPDU length field, and the rest is "as defined
1630 in ITU-T Rec. X.225 | ISO/IEC 8073, Annex B,
1631 or ITU-T Rec. X.264 and ISO/IEC 11570".
1633 When X.264/ISO 11570 default identification is
1634 being used, there is no user data field in the
1635 CALL REQUEST packet. This is for X.225/ISO 8073
1638 It also says that SPI values from 0x03 through 0x3f are
1639 reserved and are in use by X.224/ISO 8073 Annex B and
1640 X.264/ISO 11570. The note says that those values are
1641 not NLPIDs, they're "used by the respective higher layer
1642 protocol" and "not used for higher layer protocol
1643 identification". I infer from this and from what
1644 X.264/ISO 11570 says that this means that values in those
1645 range are valid values for the first octet of an
1646 X.224/ISO 8073 packet or for X.264/ISO 11570.
1648 Annex B of X.225/ISO 8073 mentions some additional TPDU
1649 types that can be put in what I presume is the user
1650 data of connect requests. It says that:
1652 The sending transport entity shall:
1654 a) either not transmit any TPDU in the NS-user data
1655 parameter of the N-CONNECT request primitive; or
1657 b) transmit the UN-TPDU (see ITU-T Rec. X.264 and
1658 ISO/IEC 11570) followed by the NCM-TPDU in the
1659 NS-user data parameter of the N-CONNECT request
1662 I don't know if this means that the user data field
1663 will contain a UN TPDU followed by an NCM TPDU or not.
1665 X.264/ISO 11570 says that:
1667 When default identification is being used,
1668 X.225/ISO 8073 COTP is identified. No user data
1669 is sent in the network-layer connection request.
1671 When explicit identification is being used,
1672 the user data is a UN TPDU ("Use of network
1673 connection TPDU"), which specifies the transport
1674 protocol to use over this network connection.
1675 It also says that the length of a UN TPDU shall
1676 not exceed 32 octets, i.e. shall not exceed 0x20;
1677 it says this is "due to the desire not to conflict
1678 with the protocol identifier field carried by X.25
1679 CALL REQUEST/INCOMING CALL packets", and says that
1680 field has values specified in X.244. X.244 has been
1681 superseded by X.263/ISO 9577, so that presumably
1682 means the goal is to allow a UN TPDU's length
1683 field to be distinguished from an NLPID, allowing
1684 you to tell whether X.264/ISO 11570 explicit
1685 identification is being used or an NLPID is
1686 being used as the SPI.
1688 I read this as meaning that, if the ISO mechanisms are
1689 used to identify the protocol being carried over X.25:
1691 if there's no user data in the CALL REQUEST/
1692 INCOMING CALL packet, it's COTP;
1694 if there is user data, then:
1696 if the first octet is less than or equal to
1697 32, it might be a UN TPDU, and that identifies
1698 the transport protocol being used, and
1699 it may be followed by more data, such
1700 as a COTP NCM TPDU if it's COTP;
1702 if the first octet is greater than 32, it's
1703 an NLPID, *not* a TPDU length, and the
1704 stuff following it is *not* a TPDU.
1706 Figure A.2 of X.263/ISO 9577 seems to say that the
1707 first octet of the user data is a TPDU length field,
1708 in the range 0x03 through 0x82, and says they are
1709 for X.225/ISO 8073 Annex B or X.264/ISO 11570.
1711 However, X.264/ISO 11570 seems to imply that the length
1712 field would be that of a UN TPDU, which must be less
1713 than or equal to 0x20, and X.225/ISO 8073 Annex B seems
1714 to indicate that the user data must begin with
1715 an X.264/ISO 11570 UN TPDU, so I'd say that A.2 should
1716 have said "in the range 0x03 through 0x20", instead
1717 (the length value doesn't include the length field,
1718 and the minimum UN TPDU has length, type, PRT-ID,
1719 and SHARE, so that's 3 bytes without the length). */
1720 spi = tvb_get_guint8(tvb, localoffset);
1721 if (spi > 32 || spi < 3) {
1722 /* First octet is > 32, or < 3, so the user data isn't an
1723 X.264/ISO 11570 UN TPDU */
1726 /* First octet is >= 3 and <= 32, so the user data *might*
1727 be an X.264/ISO 11570 UN TPDU. Check whether we have
1728 enough data to see if it is. */
1729 if (tvb_bytes_exist(tvb, localoffset+1, 1)) {
1730 /* We do; check whether the second octet is 1. */
1731 if (tvb_get_guint8(tvb, localoffset+1) == 0x01) {
1732 /* Yes, the second byte is 1, so it looks like
1736 /* No, the second byte is not 1, so it's not a
1741 /* We can't see the second byte of the putative UN
1742 TPDU, so we don't know if that's what it is. */
1746 if (is_x_264 == -1) {
1748 * We don't know what it is; just skip it.
1750 localoffset = tvb_length(tvb);
1751 } else if (is_x_264) {
1752 /* It looks like an X.264 UN TPDU, so show it as such. */
1753 if (userdata_tree) {
1754 proto_tree_add_text(userdata_tree, tvb, localoffset, 1,
1755 "X.264 length indicator: %u",
1757 proto_tree_add_text(userdata_tree, tvb, localoffset+1, 1,
1758 "X.264 UN TPDU identifier: 0x%02X",
1759 tvb_get_guint8(tvb, localoffset+1));
1761 prt_id = tvb_get_guint8(tvb, localoffset+2);
1762 if (userdata_tree) {
1763 proto_tree_add_text(userdata_tree, tvb, localoffset+2, 1,
1764 "X.264 protocol identifier: %s",
1765 val_to_str(prt_id, prt_id_vals,
1766 "Unknown (0x%02X)"));
1767 proto_tree_add_text(userdata_tree, tvb, localoffset+3, 1,
1768 "X.264 sharing strategy: %s",
1769 val_to_str(tvb_get_guint8(tvb, localoffset+3),
1770 sharing_strategy_vals, "Unknown (0x%02X)"));
1773 /* XXX - dissect the variable part? */
1775 /* The length doesn't include the length octet itself. */
1776 localoffset += spi + 1;
1780 case PRT_ID_ISO_8073:
1782 if (!pinfo->fd->flags.visited)
1783 x25_hash_add_proto_start(vc, pinfo->fd->num, ositp_handle);
1784 /* XXX - dissect the rest of the user data as COTP?
1785 That needs support for NCM TPDUs, etc. */
1788 case PRT_ID_ISO_8602:
1790 if (!pinfo->fd->flags.visited)
1791 x25_hash_add_proto_start(vc, pinfo->fd->num, ositp_handle);
1794 } else if (is_x_264 == 0) {
1795 /* It doesn't look like a UN TPDU, so compare the first
1796 octet of the CALL REQUEST packet with various X.263/
1797 ISO 9577 NLPIDs, as per Annex A of X.263/ISO 9577. */
1799 if (userdata_tree) {
1800 proto_tree_add_text(userdata_tree, tvb, localoffset, 1,
1801 "X.263 secondary protocol ID: %s",
1802 val_to_str(spi, nlpid_vals, "Unknown (0x%02x)"));
1805 if (!pinfo->fd->flags.visited) {
1807 * Is there a dissector handle for this SPI?
1808 * If so, assign it to this virtual circuit.
1810 dissect = dissector_get_port_handle(x25_subdissector_table, spi);
1811 if (dissect != NULL)
1812 x25_hash_add_proto_start(vc, pinfo->fd->num, dissect);
1816 * If there's only one octet of user data, it's just
1817 * an NLPID; don't try to dissect it.
1819 if (localoffset + 1 == tvb_reported_length(tvb))
1823 * There's more than one octet of user data, so we'll
1824 * dissect it; for some protocols, the NLPID is considered
1825 * to be part of the PDU, so, for those cases, we don't
1826 * skip past it. For other protocols, we skip the NLPID.
1830 case NLPID_ISO8473_CLNP:
1831 case NLPID_ISO9542_ESIS:
1832 case NLPID_ISO10589_ISIS:
1833 case NLPID_ISO10747_IDRP:
1836 * The NLPID is part of the PDU. Don't skip it.
1837 * But if it's all there is to the PDU, don't
1838 * bother dissecting it.
1842 case NLPID_SPI_X_29:
1844 * The first 4 bytes of the call user data are
1845 * the SPI plus 3 reserved bytes; they are not
1846 * part of the data to be dissected as X.29 data.
1853 * The NLPID isn't part of the PDU - skip it.
1854 * If that means there's nothing to dissect
1860 /* if there's no user data in the CALL REQUEST/
1861 INCOMING CALL packet, it's COTP; */
1863 x25_hash_add_proto_start(vc, pinfo->fd->num, ositp_handle);
1867 case X25_CALL_ACCEPTED:
1871 short_name = "Call conn.";
1872 long_name = "Call connected";
1876 short_name = "Call acc.";
1877 long_name = "Call accepted";
1881 short_name = "Call conn./Call acc.";
1882 long_name = "Call connected/Call accepted";
1885 if(check_col(pinfo->cinfo, COL_INFO))
1886 col_add_fstr(pinfo->cinfo, COL_INFO, "%s VC:%d", short_name, vc);
1888 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
1889 proto_tree_add_uint_format(x25_tree, hf_x25_type, tvb, 2, 1,
1890 X25_CALL_ACCEPTED, "Packet Type: %s", long_name);
1893 if (localoffset < x25_pkt_len) { /* calling/called addresses */
1895 x25_toa(x25_tree, (gint*)&localoffset, tvb, pinfo);
1897 x25_ntoa(x25_tree, (gint*)&localoffset, tvb, pinfo, FALSE);
1900 if (localoffset < x25_pkt_len) /* facilities */
1901 dump_facilities(x25_tree, (gint*)&localoffset, tvb);
1903 case X25_CLEAR_REQUEST:
1907 short_name = "Clear ind.";
1908 long_name = "Clear indication";
1912 short_name = "Clear req.";
1913 long_name = "Clear request";
1917 short_name = "Clear ind./Clear req.";
1918 long_name = "Clear indication/Clear request";
1921 if(check_col(pinfo->cinfo, COL_INFO)) {
1922 col_add_fstr(pinfo->cinfo, COL_INFO, "%s VC:%d %s - %s", short_name,
1923 vc, clear_code(tvb_get_guint8(tvb, 3)),
1924 clear_diag(tvb_get_guint8(tvb, 4)));
1926 x25_hash_add_proto_end(vc, pinfo->fd->num);
1928 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
1929 proto_tree_add_uint_format(x25_tree, hf_x25_type, tvb,
1930 localoffset+2, 1, X25_CLEAR_REQUEST, "Packet Type: %s",
1932 proto_tree_add_text(x25_tree, tvb, 3, 1,
1933 "Cause : %s", clear_code(tvb_get_guint8(tvb, 3)));
1934 proto_tree_add_text(x25_tree, tvb, 4, 1,
1935 "Diagnostic : %s", clear_diag(tvb_get_guint8(tvb, 4)));
1937 localoffset = x25_pkt_len;
1939 case X25_CLEAR_CONFIRMATION:
1940 if(check_col(pinfo->cinfo, COL_INFO))
1941 col_add_fstr(pinfo->cinfo, COL_INFO, "Clear Conf. VC:%d", vc);
1943 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
1944 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
1945 X25_CLEAR_CONFIRMATION);
1947 localoffset = x25_pkt_len;
1949 if (localoffset < tvb_reported_length(tvb)) { /* extended clear conf format */
1951 x25_toa(x25_tree, (gint*)&localoffset, tvb, pinfo);
1953 x25_ntoa(x25_tree,(gint*)&localoffset, tvb, pinfo, FALSE);
1956 if (localoffset < tvb_reported_length(tvb)) /* facilities */
1957 dump_facilities(x25_tree, (gint*)&localoffset, tvb);
1959 case X25_DIAGNOSTIC:
1960 if(check_col(pinfo->cinfo, COL_INFO)) {
1961 col_add_fstr(pinfo->cinfo, COL_INFO, "Diag. %d",
1962 (int)tvb_get_guint8(tvb, 3));
1965 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
1967 proto_tree_add_text(x25_tree, tvb, 3, 1,
1968 "Diagnostic : %d", (int)tvb_get_guint8(tvb, 3));
1970 localoffset = x25_pkt_len;
1973 if(check_col(pinfo->cinfo, COL_INFO))
1974 col_add_fstr(pinfo->cinfo, COL_INFO, "Interrupt VC:%d", vc);
1976 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
1977 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
1980 localoffset = x25_pkt_len;
1982 case X25_INTERRUPT_CONFIRMATION:
1983 if(check_col(pinfo->cinfo, COL_INFO))
1984 col_add_fstr(pinfo->cinfo, COL_INFO, "Interrupt Conf. VC:%d", vc);
1986 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
1987 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
1988 X25_INTERRUPT_CONFIRMATION);
1990 localoffset = x25_pkt_len;
1992 case X25_RESET_REQUEST:
1996 short_name = "Reset ind.";
1997 long_name = "Reset indication";
2001 short_name = "Reset req.";
2002 long_name = "Reset request";
2006 short_name = "Reset ind./Reset req.";
2007 long_name = "Reset indication/Reset request";
2010 if(check_col(pinfo->cinfo, COL_INFO)) {
2011 col_add_fstr(pinfo->cinfo, COL_INFO, "%s VC:%d %s - Diag.:%d",
2012 short_name, vc, reset_code(tvb_get_guint8(tvb, 3)),
2013 (int)tvb_get_guint8(tvb, 4));
2015 x25_hash_add_proto_end(vc, pinfo->fd->num);
2017 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
2018 proto_tree_add_uint_format(x25_tree, hf_x25_type, tvb, 2, 1,
2019 X25_RESET_REQUEST, "Packet Type: %s", long_name);
2020 proto_tree_add_text(x25_tree, tvb, 3, 1,
2021 "Cause : %s", reset_code(tvb_get_guint8(tvb, 3)));
2022 proto_tree_add_text(x25_tree, tvb, 4, 1,
2023 "Diagnostic : %d", (int)tvb_get_guint8(tvb, 4));
2025 localoffset = x25_pkt_len;
2027 case X25_RESET_CONFIRMATION:
2028 if(check_col(pinfo->cinfo, COL_INFO))
2029 col_add_fstr(pinfo->cinfo, COL_INFO, "Reset conf. VC:%d", vc);
2031 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, 0, 2, bytes0_1);
2032 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
2033 X25_RESET_CONFIRMATION);
2035 localoffset = x25_pkt_len;
2037 case X25_RESTART_REQUEST:
2041 short_name = "Restart ind.";
2042 long_name = "Restart indication";
2046 short_name = "Restart req.";
2047 long_name = "Restart request";
2051 short_name = "Restart ind./Restart req.";
2052 long_name = "Restart indication/Restart request";
2055 if(check_col(pinfo->cinfo, COL_INFO)) {
2056 col_add_fstr(pinfo->cinfo, COL_INFO, "%s %s - Diag.:%d",
2058 restart_code(tvb_get_guint8(tvb, 3)),
2059 (int)tvb_get_guint8(tvb, 4));
2062 proto_tree_add_uint_format(x25_tree, hf_x25_type, tvb, 2, 1,
2063 X25_RESTART_REQUEST, "Packet Type: %s", long_name);
2064 proto_tree_add_text(x25_tree, tvb, 3, 1,
2065 "Cause : %s", restart_code(tvb_get_guint8(tvb, 3)));
2066 proto_tree_add_text(x25_tree, tvb, 4, 1,
2067 "Diagnostic : %d", (int)tvb_get_guint8(tvb, 4));
2069 localoffset = x25_pkt_len;
2071 case X25_RESTART_CONFIRMATION:
2072 if(check_col(pinfo->cinfo, COL_INFO))
2073 col_set_str(pinfo->cinfo, COL_INFO, "Restart conf.");
2075 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
2076 X25_RESTART_CONFIRMATION);
2077 localoffset = x25_pkt_len;
2079 case X25_REGISTRATION_REQUEST:
2080 if(check_col(pinfo->cinfo, COL_INFO))
2081 col_set_str(pinfo->cinfo, COL_INFO, "Registration req.");
2083 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
2084 X25_REGISTRATION_REQUEST);
2086 if (localoffset < x25_pkt_len)
2087 x25_ntoa(x25_tree, (gint*)&localoffset, tvb, pinfo, TRUE);
2090 if (localoffset < x25_pkt_len)
2091 proto_tree_add_text(x25_tree, tvb, localoffset, 1,
2092 "Registration length: %d",
2093 tvb_get_guint8(tvb, localoffset) & 0x7F);
2094 if (localoffset+1 < x25_pkt_len)
2095 proto_tree_add_text(x25_tree, tvb, localoffset+1,
2096 tvb_get_guint8(tvb, localoffset) & 0x7F,
2099 localoffset = tvb_reported_length(tvb);
2101 case X25_REGISTRATION_CONFIRMATION:
2102 if(check_col(pinfo->cinfo, COL_INFO))
2103 col_set_str(pinfo->cinfo, COL_INFO, "Registration conf.");
2105 proto_tree_add_uint(x25_tree, hf_x25_type, tvb, 2, 1,
2106 X25_REGISTRATION_CONFIRMATION);
2107 proto_tree_add_text(x25_tree, tvb, 3, 1,
2108 "Cause: %s", registration_code(tvb_get_guint8(tvb, 3)));
2109 proto_tree_add_text(x25_tree, tvb, 4, 1,
2110 "Diagnostic: %s", registration_code(tvb_get_guint8(tvb, 4)));
2113 if (localoffset < x25_pkt_len)
2114 x25_ntoa(x25_tree, (gint*)&localoffset, tvb, pinfo, TRUE);
2117 if (localoffset < x25_pkt_len)
2118 proto_tree_add_text(x25_tree, tvb, localoffset, 1,
2119 "Registration length: %d",
2120 tvb_get_guint8(tvb, localoffset) & 0x7F);
2121 if (localoffset+1 < x25_pkt_len)
2122 proto_tree_add_text(x25_tree, tvb, localoffset+1,
2123 tvb_get_guint8(tvb, localoffset) & 0x7F,
2126 localoffset = tvb_reported_length(tvb);
2130 if (PACKET_IS_DATA(pkt_type))
2132 if(check_col(pinfo->cinfo, COL_INFO)) {
2134 col_add_fstr(pinfo->cinfo, COL_INFO,
2135 "Data VC:%d P(S):%d P(R):%d %s", vc,
2136 (pkt_type >> 1) & 0x07,
2137 (pkt_type >> 5) & 0x07,
2138 (pkt_type & X25_MBIT_MOD8) ? " M" : "");
2140 col_add_fstr(pinfo->cinfo, COL_INFO,
2141 "Data VC:%d P(S):%d P(R):%d %s", vc,
2142 tvb_get_guint8(tvb, localoffset+1) >> 1,
2144 (tvb_get_guint8(tvb, localoffset+1) & X25_MBIT_MOD128) ? " M" : "");
2147 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, localoffset-2,
2150 proto_tree_add_uint(x25_tree, hf_x25_p_r_mod8, tvb,
2151 localoffset, 1, pkt_type);
2152 proto_tree_add_boolean(x25_tree, hf_x25_mbit_mod8, tvb,
2153 localoffset, 1, pkt_type);
2154 proto_tree_add_uint(x25_tree, hf_x25_p_s_mod8, tvb,
2155 localoffset, 1, pkt_type);
2156 proto_tree_add_uint(x25_tree, hf_x25_type_data, tvb,
2157 localoffset, 1, pkt_type);
2160 proto_tree_add_uint(x25_tree, hf_x25_p_r_mod128, tvb,
2161 localoffset, 1, pkt_type);
2162 proto_tree_add_uint(x25_tree, hf_x25_type_data, tvb,
2163 localoffset, 1, pkt_type);
2164 proto_tree_add_uint(x25_tree, hf_x25_p_s_mod128, tvb,
2166 tvb_get_guint8(tvb, localoffset+1));
2167 proto_tree_add_boolean(x25_tree, hf_x25_mbit_mod128, tvb,
2169 tvb_get_guint8(tvb, localoffset+1));
2173 m_bit_set = pkt_type & X25_MBIT_MOD8;
2176 m_bit_set = tvb_get_guint8(tvb, localoffset+1) & X25_MBIT_MOD128;
2179 payload_len = tvb_reported_length_remaining(tvb, localoffset);
2180 if (reassemble_x25) {
2182 * Reassemble received and sent traffic separately.
2183 * We don't reassemble traffic with an unknown direction
2189 * OR in an extra bit to distinguish from traffic
2190 * in the other direction.
2192 frag_key |= 0x10000;
2194 fd_head = fragment_add_seq_next(tvb, localoffset,
2197 x25_reassembled_table,
2198 payload_len, m_bit_set);
2199 pinfo->fragmented = m_bit_set;
2202 if (fd_head->next) {
2203 proto_item *frag_tree_item;
2205 /* This is the last packet */
2206 next_tvb = tvb_new_real_data(fd_head->data,
2209 tvb_set_child_real_data_tvbuff(tvb, next_tvb);
2210 add_new_data_source(pinfo, next_tvb, "Reassembled X.25");
2211 show_fragment_seq_tree(fd_head,
2214 pinfo, next_tvb, &frag_tree_item);
2218 if (m_bit_set && next_tvb == NULL) {
2220 * This isn't the last packet, so just
2221 * show it as X.25 user data.
2223 proto_tree_add_text(x25_tree, tvb, localoffset, -1,
2224 "User data (%u byte%s)", payload_len,
2225 plurality(payload_len, "", "s"));
2233 * Non-data packets (RR, RNR, REJ).
2235 switch (PACKET_TYPE_FC(pkt_type))
2238 if(check_col(pinfo->cinfo, COL_INFO)) {
2240 col_add_fstr(pinfo->cinfo, COL_INFO, "RR VC:%d P(R):%d",
2241 vc, (pkt_type >> 5) & 0x07);
2243 col_add_fstr(pinfo->cinfo, COL_INFO, "RR VC:%d P(R):%d",
2244 vc, tvb_get_guint8(tvb, localoffset+1) >> 1);
2247 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, localoffset-2,
2250 proto_tree_add_uint(x25_tree, hf_x25_p_r_mod8, tvb,
2251 localoffset, 1, pkt_type);
2252 proto_tree_add_uint(x25_tree, hf_x25_type_fc_mod8, tvb,
2253 localoffset, 1, X25_RR);
2256 proto_tree_add_uint(x25_tree, hf_x25_type, tvb,
2257 localoffset, 1, X25_RR);
2258 proto_tree_add_item(x25_tree, hf_x25_p_r_mod128, tvb,
2259 localoffset+1, 1, FALSE);
2265 if(check_col(pinfo->cinfo, COL_INFO)) {
2267 col_add_fstr(pinfo->cinfo, COL_INFO, "RNR VC:%d P(R):%d",
2268 vc, (pkt_type >> 5) & 0x07);
2270 col_add_fstr(pinfo->cinfo, COL_INFO, "RNR VC:%d P(R):%d",
2271 vc, tvb_get_guint8(tvb, localoffset+1) >> 1);
2274 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, localoffset-2,
2277 proto_tree_add_uint(x25_tree, hf_x25_p_r_mod8, tvb,
2278 localoffset, 1, pkt_type);
2279 proto_tree_add_uint(x25_tree, hf_x25_type_fc_mod8, tvb,
2280 localoffset, 1, X25_RNR);
2283 proto_tree_add_uint(x25_tree, hf_x25_type, tvb,
2284 localoffset, 1, X25_RNR);
2285 proto_tree_add_item(x25_tree, hf_x25_p_r_mod128, tvb,
2286 localoffset+1, 1, FALSE);
2292 if(check_col(pinfo->cinfo, COL_INFO)) {
2294 col_add_fstr(pinfo->cinfo, COL_INFO, "REJ VC:%d P(R):%d",
2295 vc, (pkt_type >> 5) & 0x07);
2297 col_add_fstr(pinfo->cinfo, COL_INFO, "REJ VC:%d P(R):%d",
2298 vc, tvb_get_guint8(tvb, localoffset+1) >> 1);
2301 proto_tree_add_uint(x25_tree, hf_x25_lcn, tvb, localoffset-2,
2304 proto_tree_add_uint(x25_tree, hf_x25_p_r_mod8, tvb,
2305 localoffset, 1, pkt_type);
2306 proto_tree_add_uint(x25_tree, hf_x25_type_fc_mod8, tvb,
2307 localoffset, 1, X25_REJ);
2310 proto_tree_add_uint(x25_tree, hf_x25_type, tvb,
2311 localoffset, 1, X25_REJ);
2312 proto_tree_add_item(x25_tree, hf_x25_p_r_mod128, tvb,
2313 localoffset+1, 1, FALSE);
2317 localoffset += (modulo == 8) ? 1 : 2;
2320 if (localoffset >= tvb_reported_length(tvb))
2322 if (pinfo->fragmented)
2326 next_tvb = tvb_new_subset(tvb, localoffset, -1, -1);
2328 saved_private_data = pinfo->private_data;
2329 pinfo->private_data = &q_bit_set;
2331 /* See if there's already a dissector for this circuit. */
2332 if (try_circuit_dissector(CT_X25, vc, pinfo->fd->num, next_tvb, pinfo,
2334 pinfo->private_data = saved_private_data;
2335 return; /* found it and dissected it */
2338 /* Did the user suggest QLLC/SNA? */
2339 if (payload_is_qllc_sna) {
2340 /* Yes - dissect it as QLLC/SNA. */
2341 if (!pinfo->fd->flags.visited)
2342 x25_hash_add_proto_start(vc, pinfo->fd->num, qllc_handle);
2343 call_dissector(qllc_handle, next_tvb, pinfo, tree);
2344 pinfo->private_data = saved_private_data;
2348 /* If the Call Req. has not been captured, let's look at the first
2349 two bytes of the payload to see if this looks like COTP. */
2350 if (tvb_get_guint8(tvb, localoffset) == tvb_length(next_tvb)-1) {
2351 /* First byte contains the length of the remaining buffer */
2352 if ((tvb_get_guint8(tvb, localoffset+1) & 0x0F) == 0) {
2353 /* Second byte contains a valid COTP TPDU */
2354 if (!pinfo->fd->flags.visited)
2355 x25_hash_add_proto_start(vc, pinfo->fd->num, ositp_handle);
2356 call_dissector(ositp_handle, next_tvb, pinfo, tree);
2357 pinfo->private_data = saved_private_data;
2362 /* Then let's look at the first byte of the payload to see if this
2363 looks like IP or CLNP. */
2364 switch (tvb_get_guint8(tvb, localoffset)) {
2367 /* Looks like an IP header */
2368 if (!pinfo->fd->flags.visited)
2369 x25_hash_add_proto_start(vc, pinfo->fd->num, ip_handle);
2370 call_dissector(ip_handle, next_tvb, pinfo, tree);
2371 pinfo->private_data = saved_private_data;
2374 case NLPID_ISO8473_CLNP:
2375 if (!pinfo->fd->flags.visited)
2376 x25_hash_add_proto_start(vc, pinfo->fd->num, clnp_handle);
2377 call_dissector(clnp_handle, next_tvb, pinfo, tree);
2378 pinfo->private_data = saved_private_data;
2382 /* Try the heuristic dissectors. */
2383 if (dissector_try_heuristic(x25_heur_subdissector_list, next_tvb, pinfo,
2385 pinfo->private_data = saved_private_data;
2389 /* All else failed; dissect it as raw data */
2390 call_dissector(data_handle, next_tvb, pinfo, tree);
2391 pinfo->private_data = saved_private_data;
2395 * X.25 dissector for use when "pinfo->pseudo_header" points to a
2396 * "struct x25_phdr".
2399 dissect_x25_dir(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2401 dissect_x25_common(tvb, pinfo, tree,
2402 (pinfo->pseudo_header->x25.flags & FROM_DCE) ? X25_FROM_DCE :
2404 pinfo->pseudo_header->x25.flags & FROM_DCE);
2408 * X.25 dissector for use when "pinfo->pseudo_header" doesn't point to a
2409 * "struct x25_phdr".
2412 dissect_x25(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
2417 * We don't know if this packet is DTE->DCE or DCE->DCE.
2418 * However, we can, at least, distinguish between the two
2419 * sides of the conversation, based on the addresses and
2422 direction = CMP_ADDRESS(&pinfo->src, &pinfo->dst);
2424 direction = (pinfo->srcport > pinfo->destport)*2 - 1;
2425 dissect_x25_common(tvb, pinfo, tree, X25_UNKNOWN, direction > 0);
2429 x25_reassemble_init(void)
2431 fragment_table_init(&x25_segment_table);
2432 reassembled_table_init(&x25_reassembled_table);
2436 proto_register_x25(void)
2438 static hf_register_info hf[] = {
2440 { "GFI", "x.25.gfi", FT_UINT16, BASE_DEC, NULL, 0xF000,
2441 "General format identifier", HFILL }},
2443 { "A Bit", "x.25.a", FT_BOOLEAN, 16, NULL, X25_ABIT,
2444 "Address Bit", HFILL }},
2446 { "Q Bit", "x.25.q", FT_BOOLEAN, 16, NULL, X25_QBIT,
2447 "Qualifier Bit", HFILL }},
2449 { "D Bit", "x.25.d", FT_BOOLEAN, 16, NULL, X25_DBIT,
2450 "Delivery Confirmation Bit", HFILL }},
2452 { "Modulo", "x.25.mod", FT_UINT16, BASE_DEC, VALS(vals_modulo), 0x3000,
2453 "Specifies whether the frame is modulo 8 or 128", HFILL }},
2455 { "Logical Channel", "x.25.lcn", FT_UINT16, BASE_DEC, NULL, 0x0FFF,
2456 "Logical Channel Number", HFILL }},
2458 { "Packet Type", "x.25.type", FT_UINT8, BASE_HEX, VALS(vals_x25_type), 0x0,
2459 "Packet Type", HFILL }},
2460 { &hf_x25_type_fc_mod8,
2461 { "Packet Type", "x.25.type", FT_UINT8, BASE_HEX, VALS(vals_x25_type), 0x1F,
2462 "Packet Type", HFILL }},
2463 { &hf_x25_type_data,
2464 { "Packet Type", "x.25.type", FT_UINT8, BASE_HEX, VALS(vals_x25_type), 0x01,
2465 "Packet Type", HFILL }},
2467 { "P(R)", "x.25.p_r", FT_UINT8, BASE_DEC, NULL, 0xE0,
2468 "Packet Receive Sequence Number", HFILL }},
2469 { &hf_x25_p_r_mod128,
2470 { "P(R)", "x.25.p_r", FT_UINT8, BASE_DEC, NULL, 0xFE,
2471 "Packet Receive Sequence Number", HFILL }},
2472 { &hf_x25_mbit_mod8,
2473 { "M Bit", "x.25.m", FT_BOOLEAN, 8, TFS(&m_bit_tfs), X25_MBIT_MOD8,
2474 "More Bit", HFILL }},
2475 { &hf_x25_mbit_mod128,
2476 { "M Bit", "x.25.m", FT_BOOLEAN, 8, TFS(&m_bit_tfs), X25_MBIT_MOD128,
2477 "More Bit", HFILL }},
2479 { "P(S)", "x.25.p_s", FT_UINT8, BASE_DEC, NULL, 0x0E,
2480 "Packet Send Sequence Number", HFILL }},
2481 { &hf_x25_p_s_mod128,
2482 { "P(S)", "x.25.p_s", FT_UINT8, BASE_DEC, NULL, 0xFE,
2483 "Packet Send Sequence Number", HFILL }},
2484 { &hf_x25_segment_overlap,
2485 { "Fragment overlap", "x25.fragment.overlap", FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2486 "Fragment overlaps with other fragments", HFILL }},
2488 { &hf_x25_segment_overlap_conflict,
2489 { "Conflicting data in fragment overlap", "x25.fragment.overlap.conflict", FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2490 "Overlapping fragments contained conflicting data", HFILL }},
2492 { &hf_x25_segment_multiple_tails,
2493 { "Multiple tail fragments found", "x25.fragment.multipletails", FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2494 "Several tails were found when defragmenting the packet", HFILL }},
2496 { &hf_x25_segment_too_long_segment,
2497 { "Fragment too long", "x25.fragment.toolongfragment", FT_BOOLEAN, BASE_NONE, NULL, 0x0,
2498 "Fragment contained data past end of packet", HFILL }},
2500 { &hf_x25_segment_error,
2501 { "Defragmentation error", "x25.fragment.error", FT_FRAMENUM, BASE_NONE, NULL, 0x0,
2502 "Defragmentation error due to illegal fragments", HFILL }},
2505 { "X.25 Fragment", "x25.fragment", FT_FRAMENUM, BASE_NONE, NULL, 0x0,
2506 "X25 Fragment", HFILL }},
2509 { "X.25 Fragments", "x25.fragments", FT_NONE, BASE_NONE, NULL, 0x0,
2510 "X.25 Fragments", HFILL }},
2512 static gint *ett[] = {
2516 &ett_x25_fac_unknown,
2518 &ett_x25_fac_reverse,
2519 &ett_x25_fac_throughput,
2521 &ett_x25_fac_called_modif,
2522 &ett_x25_fac_cug_outgoing_acc,
2523 &ett_x25_fac_throughput_min,
2524 &ett_x25_fac_express_data,
2525 &ett_x25_fac_bilateral_cug,
2526 &ett_x25_fac_packet_size,
2527 &ett_x25_fac_window_size,
2528 &ett_x25_fac_rpoa_selection,
2529 &ett_x25_fac_transit_delay,
2530 &ett_x25_fac_call_transfer,
2531 &ett_x25_fac_called_addr_ext,
2532 &ett_x25_fac_ete_transit_delay,
2533 &ett_x25_fac_calling_addr_ext,
2534 &ett_x25_fac_call_deflect,
2535 &ett_x25_fac_priority,
2540 module_t *x25_module;
2542 proto_x25 = proto_register_protocol ("X.25", "X.25", "x.25");
2543 proto_register_field_array (proto_x25, hf, array_length(hf));
2544 proto_register_subtree_array(ett, array_length(ett));
2546 x25_subdissector_table = register_dissector_table("x.25.spi",
2547 "X.25 secondary protocol identifier", FT_UINT8, BASE_HEX);
2548 register_heur_dissector_list("x.25", &x25_heur_subdissector_list);
2550 register_dissector("x.25_dir", dissect_x25_dir, proto_x25);
2551 register_dissector("x.25", dissect_x25, proto_x25);
2554 x25_module = prefs_register_protocol(proto_x25, NULL);
2555 prefs_register_obsolete_preference(x25_module, "non_q_bit_is_sna");
2556 prefs_register_bool_preference(x25_module, "payload_is_qllc_sna",
2557 "Default to QLLC/SNA",
2558 "If CALL REQUEST not seen or didn't specify protocol, dissect as QLLC/SNA",
2559 &payload_is_qllc_sna);
2560 prefs_register_bool_preference(x25_module, "reassemble",
2561 "Reassemble fragmented X.25 packets",
2562 "Reassemble fragmented X.25 packets",
2564 register_init_routine(&x25_reassemble_init);
2568 proto_reg_handoff_x25(void)
2570 dissector_handle_t x25_handle;
2573 * Get handles for various dissectors.
2575 ip_handle = find_dissector("ip");
2576 clnp_handle = find_dissector("clnp");
2577 ositp_handle = find_dissector("ositp");
2578 qllc_handle = find_dissector("qllc");
2579 data_handle = find_dissector("data");
2581 x25_handle = find_dissector("x.25");
2582 dissector_add("llc.dsap", SAP_X25, x25_handle);