diff options
author | Guy Harris <guy@alum.mit.edu> | 1999-11-19 09:55:38 +0000 |
---|---|---|
committer | Guy Harris <guy@alum.mit.edu> | 1999-11-19 09:55:38 +0000 |
commit | 8963fabad69eff429d951368a4c2fe4ed09cdef1 (patch) | |
tree | 3205e7772a5a767cbfbaef0b22be52712907bbaa /packet-q2931.c | |
parent | a8dfc56400350815e203666d81316da4f1f2392b (diff) | |
download | wireshark-8963fabad69eff429d951368a4c2fe4ed09cdef1.tar.gz wireshark-8963fabad69eff429d951368a4c2fe4ed09cdef1.tar.bz2 wireshark-8963fabad69eff429d951368a4c2fe4ed09cdef1.zip |
Beginnings of Q.2931 support.
svn path=/trunk/; revision=1068
Diffstat (limited to 'packet-q2931.c')
-rw-r--r-- | packet-q2931.c | 291 |
1 files changed, 291 insertions, 0 deletions
diff --git a/packet-q2931.c b/packet-q2931.c new file mode 100644 index 0000000000..5444e7b9c9 --- /dev/null +++ b/packet-q2931.c @@ -0,0 +1,291 @@ +/* packet-q2931.c + * Routines for Q.2931 frame disassembly + * Guy Harris <guy@alum.mit.edu> + * + * $Id: packet-q2931.c,v 1.1 1999/11/19 09:55:37 guy Exp $ + * + * Ethereal - Network traffic analyzer + * By Gerald Combs <gerald@zing.org> + * Copyright 1998 + * + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + */ + +#ifdef HAVE_CONFIG_H +# include "config.h" +#endif + +#ifdef HAVE_SYS_TYPES_H +# include <sys/types.h> +#endif + +#include <stdio.h> +#include <glib.h> +#include <string.h> +#include "packet.h" + +/* + * See + * + * http://www.protocols.com/pbook/atmsig.htm + * + * for some information on Q.2931, although, alas, not the actual message + * type and information element values - those I got from the FreeBSD 3.2 + * ATM code. + */ + +static int proto_q2931 = -1; +static int hf_q2931_discriminator = -1; +static int hf_q2931_call_ref_len = -1; +static int hf_q2931_call_ref = -1; +static int hf_q2931_message_type = -1; +static int hf_q2931_message_type_ext = -1; +static int hf_q2931_message_len = -1; + +static gint ett_q2931 = -1; +static gint ett_q2931_ie = -1; + +/* + * Q.2931 message types. + */ +#define Q2931_ALERTING 0x01 +#define Q2931_CALL_PROCEEDING 0x02 +#define Q2931_CONNECT 0x07 +#define Q2931_CONNECT_ACK 0x0F +#define Q2931_PROGRESS 0x03 +#define Q2931_SETUP 0x05 +#define Q2931_SETUP_ACK 0x0B +#define Q2931_RELEASE 0x4D +#define Q2931_RELEASE_COMPLETE 0x5A +#define Q2931_RESTART 0x46 +#define Q2931_RESTART_ACK 0x4E +#define Q2931_INFORMATION 0x7B +#define Q2931_NOTIFY 0x6E +#define Q2931_STATUS 0x7D +#define Q2931_STATUS_ENQUIRY 0x75 +#define Q2931_ADD_PARTY 0x80 +#define Q2931_ADD_PARTY_ACK 0x81 +#define Q2931_ADD_PARTY_REJ 0x82 +#define Q2931_DROP_PARTY 0x83 +#define Q2931_DROP_PARTY_ACK 0x84 + +static const value_string q2931_message_type_vals[] = { + { Q2931_ALERTING, "ALERTING" }, + { Q2931_CALL_PROCEEDING, "CALL PROCEEDING" }, + { Q2931_CONNECT, "CONNECT" }, + { Q2931_CONNECT_ACK, "CONNECT ACKNOWLEDGE" }, + { Q2931_PROGRESS, "PROGRESS" }, + { Q2931_SETUP, "SETUP" }, + { Q2931_SETUP_ACK, "SETUP ACKNOWLEDGE" }, + { Q2931_RELEASE, "RELEASE" }, + { Q2931_RELEASE_COMPLETE, "RELEASE COMPLETE" }, + { Q2931_RESTART, "RESTART" }, + { Q2931_RESTART_ACK, "RESTART ACKNOWLEDGE" }, + { Q2931_INFORMATION, "INFORMATION" }, + { Q2931_NOTIFY, "NOTIFY" }, + { Q2931_STATUS, "STATUS" }, + { Q2931_STATUS_ENQUIRY, "STATUS ENQUIRY" }, + { Q2931_ADD_PARTY, "ADD PARTY" }, + { Q2931_ADD_PARTY_ACK, "ADD PARTY ACKNOWLEDGE" }, + { Q2931_ADD_PARTY_REJ, "ADD PARTY REJECT" }, + { Q2931_DROP_PARTY, "DROP PARTY" }, + { Q2931_DROP_PARTY_ACK, "DROP PARTY ACKNOWLEDGE" }, + { 0, NULL } +}; + +/* + * Information elements. + */ + +#define Q2931_IE_CAUSE 0x08 +#define Q2931_IE_CALL_STATE 0x14 +#define Q2931_IE_ENDPOINT_REFERENCE 0x54 +#define Q2931_IE_ENDPOINT_STATE 0x55 +#define Q2931_IE_AAL_PARAMETERS 0x58 +#define Q2931_IE_ATM_USER_CELL_RATE 0x59 +#define Q2931_IE_CONNECTION_IDENTIFIER 0x5A +#define Q2931_IE_QOS_PARAMETER 0x5C /* Quality of Service parameter */ +#define Q2931_IE_BBAND_HI_LAYER_INFO 0x5D /* Broadband high-layer information */ +#define Q2931_IE_BBAND_BRER_CAPACITY 0x5E /* Broadband bearer capacity */ +#define Q2931_IE_BBAND_LOW_LAYER_INFO 0x5F /* Broadband low-layer information */ +#define Q2931_IE_BBAND_LOCKING_SHIFT 0x60 /* Broadband locking shift */ +#define Q2931_IE_BBAND_NLOCKING_SHIFT 0x61 /* Broadband non-locking shift */ +#define Q2931_IE_BBAND_SENDING_COMPL 0x62 /* Broadband sending complete */ +#define Q2931_IE_BBAND_RPT_INDICATOR 0x63 /* Broadband repeat indicator */ +#define Q2931_IE_CALLING_PARTY_NUMBER 0x6C /* Calling Party Number */ +#define Q2931_IE_CALLING_PARTY_SUBADDR 0x6D /* Calling Party Subaddress */ +#define Q2931_IE_CALLED_PARTY_NUMBER 0x70 /* Called Party Number */ +#define Q2931_IE_CALLED_PARTY_SUBADDR 0x71 /* Called Party Subaddress */ +#define Q2931_IE_TRANSIT_NETWORK_SEL 0x78 /* Transit Network Selection */ +#define Q2931_IE_RESTART_INDICATOR 0x79 + +static const value_string q2931_info_element_vals[] = { + { Q2931_IE_CAUSE, "Cause" }, + { Q2931_IE_CALL_STATE, "Call state" }, + { Q2931_IE_ENDPOINT_REFERENCE, "Endpoint reference" }, + { Q2931_IE_ENDPOINT_STATE, "Endpoint state" }, + { Q2931_IE_AAL_PARAMETERS, "AAL parameters" }, + { Q2931_IE_ATM_USER_CELL_RATE, "ATM user cell rate" }, + { Q2931_IE_CONNECTION_IDENTIFIER, "Connection identifier" }, + { Q2931_IE_QOS_PARAMETER, "Quality of service parameter" }, + { Q2931_IE_BBAND_HI_LAYER_INFO, "Broadband high-layer information" }, + { Q2931_IE_BBAND_BRER_CAPACITY, "Broadband bearer capacity" }, + { Q2931_IE_BBAND_LOW_LAYER_INFO, "Broadband low-layer information" }, + { Q2931_IE_BBAND_LOCKING_SHIFT, "Broadband locking shift" }, + { Q2931_IE_BBAND_NLOCKING_SHIFT, "Broadband non-locking shift" }, + { Q2931_IE_BBAND_SENDING_COMPL, "Broadband sending complete" }, + { Q2931_IE_BBAND_RPT_INDICATOR, "Broadband repeat indicator" }, + { Q2931_IE_CALLING_PARTY_NUMBER, "Calling party number" }, + { Q2931_IE_CALLING_PARTY_SUBADDR, "Calling party subaddress" }, + { Q2931_IE_CALLED_PARTY_NUMBER, "Called party number" }, + { Q2931_IE_CALLED_PARTY_SUBADDR, "Called party subaddress" }, + { Q2931_IE_TRANSIT_NETWORK_SEL, "Transit network selection" }, + { Q2931_IE_RESTART_INDICATOR, "Restart indicator" }, + { 0, NULL } +}; + +void +dissect_q2931(const u_char *pd, int offset, frame_data *fd, proto_tree *tree) +{ + proto_tree *q2931_tree = NULL; + proto_item *ti; + proto_tree *ie_tree; + guint8 call_ref_len; + guint8 call_ref[15]; + guint8 message_type; + guint8 message_type_ext; + guint16 message_len; + guint8 info_element; + guint8 info_element_ext; + guint16 info_element_len; + int codeset; + int non_locking_shift; + + if (check_col(fd, COL_PROTOCOL)) + col_add_str(fd, COL_PROTOCOL, "Q.2931"); + + if (tree) { + ti = proto_tree_add_item(tree, proto_q2931, offset, + END_OF_FRAME, NULL); + q2931_tree = proto_item_add_subtree(ti, ett_q2931); + + proto_tree_add_item(q2931_tree, hf_q2931_discriminator, offset, 1, pd[offset]); + } + offset += 1; + call_ref_len = pd[offset] & 0xF; /* XXX - do as a bit field? */ + if (q2931_tree != NULL) + proto_tree_add_item(q2931_tree, hf_q2931_call_ref_len, offset, 1, call_ref_len); + offset += 1; + if (call_ref_len != 0) { + /* XXX - split this into flag and value */ + memcpy(call_ref, &pd[offset], call_ref_len); + if (q2931_tree != NULL) + proto_tree_add_item(q2931_tree, hf_q2931_call_ref, offset, call_ref_len, call_ref); + offset += call_ref_len; + } + message_type = pd[offset]; + if (check_col(fd, COL_INFO)) { + col_add_str(fd, COL_INFO, + val_to_str(message_type, q2931_message_type_vals, + "Unknown message type (0x%02X)")); + } + if (q2931_tree != NULL) + proto_tree_add_item(q2931_tree, hf_q2931_message_type, offset, 1, message_type); + offset += 1; + + message_type_ext = pd[offset]; + if (q2931_tree != NULL) + proto_tree_add_item(q2931_tree, hf_q2931_message_type_ext, offset, 1, message_type_ext); + offset += 1; + + message_len = pntohs(&pd[offset]); + if (q2931_tree != NULL) + proto_tree_add_item(q2931_tree, hf_q2931_message_len, offset, 2, message_len); + offset += 2; + + /* + * And now for the information elements.... + */ + codeset = 0; /* start out in codeset 0 */ + non_locking_shift = TRUE; + while (IS_DATA_IN_FRAME(offset)) { + info_element = pd[offset]; + if (!BYTES_ARE_IN_FRAME(offset + 1, 1)) + break; /* ran past end of frame */ + info_element_ext = pd[offset + 1]; + if (!BYTES_ARE_IN_FRAME(offset + 2, 2)) + break; /* ran past end of frame */ + info_element_len = pntohs(&pd[offset + 2]); + if (!BYTES_ARE_IN_FRAME(offset + 4, info_element_len)) + break; /* ran past end of frame */ + if (q2931_tree != NULL) { + ti = proto_tree_add_text(q2931_tree, offset, + 1+1+2+info_element_len, "%s", + val_to_str(info_element, q2931_info_element_vals, + "Unknown information element (0x%02X)")); + ie_tree = proto_item_add_subtree(ti, ett_q2931_ie); + proto_tree_add_text(ie_tree, offset, 1, + "Information element: %s", + val_to_str(info_element, q2931_info_element_vals, + "Unknown")); + proto_tree_add_text(ie_tree, offset + 1, 1, + "Information element extension: 0x%02x", + info_element_ext); + proto_tree_add_text(ie_tree, offset + 2, 2, + "Length: %u", info_element_len); + } + offset += 1 + 1 + 2 + info_element_len; + } +} + +void +proto_register_q2931(void) +{ + static hf_register_info hf[] = { + { &hf_q2931_discriminator, + { "Protocol discriminator", "q2931.disc", FT_UINT8, BASE_HEX, NULL, 0x0, + "" }}, + + { &hf_q2931_call_ref_len, + { "Call reference value length", "q2931.call_ref_len", FT_UINT8, BASE_DEC, NULL, 0x0, + "" }}, + + { &hf_q2931_call_ref, + { "Call reference value", "q2931.call_ref", FT_BYTES, BASE_HEX, NULL, 0x0, + "" }}, + + { &hf_q2931_message_type, + { "Message type", "q2931.message_type", FT_UINT8, BASE_HEX, VALS(q2931_message_type_vals), 0x0, + "" }}, + + { &hf_q2931_message_type_ext, + { "Message type extension", "q2931.message_type_ext", FT_UINT8, BASE_HEX, NULL, 0x0, + "" }}, + + { &hf_q2931_message_len, + { "Message length", "q2931.message_len", FT_UINT16, BASE_DEC, NULL, 0x0, + "" }}, + + }; + static gint *ett[] = { + &ett_q2931, + &ett_q2931_ie, + }; + + proto_q2931 = proto_register_protocol ("Q.2931", "q2931"); + proto_register_field_array (proto_q2931, hf, array_length(hf)); + proto_register_subtree_array(ett, array_length(ett)); +} |