diff options
author | Guy Harris <guy@alum.mit.edu> | 2004-01-03 03:51:27 +0000 |
---|---|---|
committer | Guy Harris <guy@alum.mit.edu> | 2004-01-03 03:51:27 +0000 |
commit | 30ce42b1e9a4d5efd8041c7351106cceba9926c3 (patch) | |
tree | 5d4cf986a8de4dcb06414d369c1626c92863b839 | |
parent | 044e7f9875eb7e3ac2cc07f1280ecf27ff4cdd24 (diff) |
Have "dissect_xdlc_control()" take a pointer to a structure containing
pointers to hf_ values, so the subfields of the control field are put
into the protocol tree as filterable items. Change the protocols that
use it appropriately.
Export "dissect_xdlc_control()" to plugins.
svn path=/trunk/; revision=9531
-rw-r--r-- | packet-fr.c | 81 | ||||
-rw-r--r-- | packet-lapb.c | 61 | ||||
-rw-r--r-- | packet-lapd.c | 91 | ||||
-rw-r--r-- | packet-llc.c | 89 | ||||
-rw-r--r-- | packet-sdlc.c | 61 | ||||
-rw-r--r-- | packet-v120.c | 79 | ||||
-rw-r--r-- | plugins/Xass-list | 2 | ||||
-rw-r--r-- | plugins/Xplugin_api.c | 1 | ||||
-rw-r--r-- | plugins/Xplugin_api.h | 1 | ||||
-rw-r--r-- | plugins/Xplugin_api_decls.h | 1 | ||||
-rw-r--r-- | plugins/Xplugin_table.h | 1 | ||||
-rw-r--r-- | plugins/plugin_api_list.c | 8 | ||||
-rw-r--r-- | xdlc.c | 302 | ||||
-rw-r--r-- | xdlc.h | 71 |
14 files changed, 649 insertions, 200 deletions
diff --git a/packet-fr.c b/packet-fr.c index ae599f445e..91f6552fd6 100644 --- a/packet-fr.c +++ b/packet-fr.c @@ -3,7 +3,7 @@ * * Copyright 2001, Paul Ionescu <paul@acorp.ro> * - * $Id: packet-fr.c,v 1.45 2003/10/17 23:43:21 guy Exp $ + * $Id: packet-fr.c,v 1.46 2004/01/03 03:49:22 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -91,6 +91,18 @@ static gint hf_fr_lower_dlci = -1; static gint hf_fr_dc = -1; static gint hf_fr_dlci = -1; static gint hf_fr_control = -1; +static gint hf_fr_n_r = -1; +static gint hf_fr_n_s = -1; +static gint hf_fr_p = -1; +static gint hf_fr_p_ext = -1; +static gint hf_fr_f = -1; +static gint hf_fr_f_ext = -1; +static gint hf_fr_s_ftype = -1; +static gint hf_fr_u_modifier_cmd = -1; +static gint hf_fr_u_modifier_resp = -1; +static gint hf_fr_ftype_i = -1; +static gint hf_fr_ftype_s_u = -1; +static gint hf_fr_ftype_s_u_ext = -1; static gint hf_fr_nlpid = -1; static gint hf_fr_oui = -1; static gint hf_fr_pid = -1; @@ -162,6 +174,32 @@ static void dissect_fr_nlpid(tvbuff_t *tvb, int offset, packet_info *pinfo, static void dissect_lapf(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree); static void dissect_fr_xid(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree); +/* Used only for U frames */ +static const xdlc_cf_items fr_cf_items = { + NULL, + NULL, + &hf_fr_p, + &hf_fr_f, + NULL, + &hf_fr_u_modifier_cmd, + &hf_fr_u_modifier_resp, + NULL, + &hf_fr_ftype_s_u +}; + +/* Used only for I and S frames */ +static const xdlc_cf_items fr_cf_items_ext = { + &hf_fr_n_r, + &hf_fr_n_s, + &hf_fr_p_ext, + &hf_fr_f_ext, + &hf_fr_s_ftype, + NULL, + NULL, + &hf_fr_ftype_i, + &hf_fr_ftype_s_u_ext +}; + static void dissect_fr_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, gboolean has_direction) @@ -331,7 +369,8 @@ dissect_fr_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, fr_ctrl = tvb_get_guint8(tvb, offset); if (fr_ctrl == XDLC_U) { dissect_xdlc_control(tvb, offset, pinfo, fr_tree, hf_fr_control, - ett_fr_control, is_response, TRUE, TRUE); + ett_fr_control, &fr_cf_items, &fr_cf_items_ext, + is_response, TRUE, TRUE); offset++; /* @@ -355,6 +394,7 @@ dissect_fr_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, */ dissect_xdlc_control(tvb, offset, pinfo, fr_tree, hf_fr_control, ett_fr_control, + &fr_cf_items, &fr_cf_items_ext, is_response, TRUE, TRUE); dissect_lapf(tvb_new_subset(tvb,offset,-1,-1),pinfo,tree); return; @@ -362,6 +402,7 @@ dissect_fr_common(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, if (fr_ctrl == (XDLC_U|XDLC_XID)) { dissect_xdlc_control(tvb, offset, pinfo, fr_tree, hf_fr_control, ett_fr_control, + &fr_cf_items, &fr_cf_items_ext, is_response, TRUE, TRUE); dissect_fr_xid(tvb_new_subset(tvb,offset,-1,-1),pinfo,tree); return; @@ -593,6 +634,42 @@ void proto_register_fr(void) { &hf_fr_control, { "Control Field", "fr.control", FT_UINT8, BASE_HEX, NULL, 0x0, "Control field", HFILL }}, + { &hf_fr_n_r, { + "N(R)", "fr.control.n_r", FT_UINT16, BASE_DEC, + NULL, XDLC_N_R_EXT_MASK, "", HFILL }}, + { &hf_fr_n_s, { + "N(S)", "fr.control.n_s", FT_UINT16, BASE_DEC, + NULL, XDLC_N_S_EXT_MASK, "", HFILL }}, + { &hf_fr_p, { + "Poll", "fr.control.p", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + { &hf_fr_p_ext, { + "Poll", "fr.control.p", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + { &hf_fr_f, { + "Final", "fr.control.f", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + { &hf_fr_f_ext, { + "Final", "fr.control.f", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + { &hf_fr_s_ftype, { + "Supervisory frame type", "fr.control.s_ftype", FT_UINT16, BASE_HEX, + VALS(stype_vals), XDLC_S_FTYPE_MASK, "", HFILL }}, + { &hf_fr_u_modifier_cmd, { + "Command", "lapd.control.u_modifier_cmd", FT_UINT8, BASE_HEX, + VALS(modifier_vals_cmd), XDLC_U_MODIFIER_MASK, "", HFILL }}, + { &hf_fr_u_modifier_resp, { + "Response", "lapd.control.u_modifier_resp", FT_UINT8, BASE_HEX, + VALS(modifier_vals_resp), XDLC_U_MODIFIER_MASK, "", HFILL }}, + { &hf_fr_ftype_i, { + "Frame type", "fr.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_I_MASK, "", HFILL }}, + { &hf_fr_ftype_s_u, { + "Frame type", "fr.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, + { &hf_fr_ftype_s_u_ext, { + "Frame type", "fr.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, { &hf_fr_nlpid, { "NLPID", "fr.nlpid", FT_UINT8, BASE_HEX, VALS(fr_nlpid_vals), 0x0, "Frame Relay Encapsulated Protocol NLPID", HFILL }}, diff --git a/packet-lapb.c b/packet-lapb.c index 8b911dae6c..9b1acfa879 100644 --- a/packet-lapb.c +++ b/packet-lapb.c @@ -2,7 +2,7 @@ * Routines for lapb frame disassembly * Olivier Abad <oabad@noos.fr> * - * $Id: packet-lapb.c,v 1.40 2003/09/26 08:19:55 guy Exp $ + * $Id: packet-lapb.c,v 1.41 2004/01/03 03:49:22 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -36,6 +36,15 @@ static int proto_lapb = -1; static int hf_lapb_address = -1; static int hf_lapb_control = -1; +static int hf_lapb_n_r = -1; +static int hf_lapb_n_s = -1; +static int hf_lapb_p = -1; +static int hf_lapb_f = -1; +static int hf_lapb_s_ftype = -1; +static int hf_lapb_u_modifier_cmd = -1; +static int hf_lapb_u_modifier_resp = -1; +static int hf_lapb_ftype_i = -1; +static int hf_lapb_ftype_s_u = -1; static gint ett_lapb = -1; static gint ett_lapb_control = -1; @@ -43,6 +52,18 @@ static gint ett_lapb_control = -1; static dissector_handle_t x25_dir_handle; static dissector_handle_t x25_handle; +static const xdlc_cf_items lapb_cf_items = { + &hf_lapb_n_r, + &hf_lapb_n_s, + &hf_lapb_p, + &hf_lapb_f, + &hf_lapb_s_ftype, + &hf_lapb_u_modifier_cmd, + &hf_lapb_u_modifier_resp, + &hf_lapb_ftype_i, + &hf_lapb_ftype_s_u +}; + static void dissect_lapb(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) { @@ -130,7 +151,7 @@ dissect_lapb(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) lapb_tree = NULL; dissect_xdlc_control(tvb, 1, pinfo, lapb_tree, hf_lapb_control, - ett_lapb_control, is_response, FALSE, FALSE); + ett_lapb_control, &lapb_cf_items, NULL, is_response, FALSE, FALSE); /* not end of frame ==> X.25 */ if (tvb_reported_length(tvb) > 2) { @@ -160,6 +181,42 @@ proto_register_lapb(void) { &hf_lapb_control, { "Control Field", "lapb.control", FT_UINT8, BASE_HEX, NULL, 0x0, "Control field", HFILL }}, + + { &hf_lapb_n_r, + { "N(R)", "lapb.control.n_r", FT_UINT8, BASE_DEC, + NULL, XDLC_N_R_MASK, "", HFILL }}, + + { &hf_lapb_n_s, + { "N(S)", "lapb.control.n_s", FT_UINT8, BASE_DEC, + NULL, XDLC_N_S_MASK, "", HFILL }}, + + { &hf_lapb_p, + { "Poll", "lapb.control.p", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_lapb_f, + { "Final", "lapb.control.f", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_lapb_s_ftype, + { "Supervisory frame type", "lapb.control.s_ftype", FT_UINT8, BASE_HEX, + VALS(stype_vals), XDLC_S_FTYPE_MASK, "", HFILL }}, + + { &hf_lapb_u_modifier_cmd, + { "Command", "lapb.control.u_modifier_cmd", FT_UINT8, BASE_HEX, + VALS(modifier_vals_cmd), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_lapb_u_modifier_resp, + { "Response", "lapb.control.u_modifier_resp", FT_UINT8, BASE_HEX, + VALS(modifier_vals_resp), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_lapb_ftype_i, + { "Frame type", "lapb.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_I_MASK, "", HFILL }}, + + { &hf_lapb_ftype_s_u, + { "Frame type", "lapb.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, }; static gint *ett[] = { &ett_lapb, diff --git a/packet-lapd.c b/packet-lapd.c index f69b5cbce6..03f76efcec 100644 --- a/packet-lapd.c +++ b/packet-lapd.c @@ -2,7 +2,7 @@ * Routines for LAPD frame disassembly * Gilbert Ramirez <gram@alumni.rice.edu> * - * $Id: packet-lapd.c,v 1.35 2003/09/02 19:18:52 guy Exp $ + * $Id: packet-lapd.c,v 1.36 2004/01/03 03:49:22 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -48,6 +48,18 @@ static int hf_lapd_ea1 = -1; static int hf_lapd_tei = -1; static int hf_lapd_ea2 = -1; static int hf_lapd_control = -1; +static int hf_lapd_n_r = -1; +static int hf_lapd_n_s = -1; +static int hf_lapd_p = -1; +static int hf_lapd_p_ext = -1; +static int hf_lapd_f = -1; +static int hf_lapd_f_ext = -1; +static int hf_lapd_s_ftype = -1; +static int hf_lapd_u_modifier_cmd = -1; +static int hf_lapd_u_modifier_resp = -1; +static int hf_lapd_ftype_i = -1; +static int hf_lapd_ftype_s_u = -1; +static int hf_lapd_ftype_s_u_ext = -1; static gint ett_lapd = -1; static gint ett_lapd_address = -1; @@ -79,6 +91,32 @@ static const value_string lapd_sapi_vals[] = { { 0, NULL } }; +/* Used only for U frames */ +static const xdlc_cf_items lapd_cf_items = { + NULL, + NULL, + &hf_lapd_p, + &hf_lapd_f, + NULL, + &hf_lapd_u_modifier_cmd, + &hf_lapd_u_modifier_resp, + NULL, + &hf_lapd_ftype_s_u +}; + +/* Used only for I and S frames */ +static const xdlc_cf_items lapd_cf_items_ext = { + &hf_lapd_n_r, + &hf_lapd_n_s, + &hf_lapd_p_ext, + &hf_lapd_f_ext, + &hf_lapd_s_ftype, + NULL, + NULL, + &hf_lapd_ftype_i, + &hf_lapd_ftype_s_u_ext +}; + static void dissect_lapd(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) { @@ -137,7 +175,8 @@ dissect_lapd(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) } control = dissect_xdlc_control(tvb, 2, pinfo, lapd_tree, hf_lapd_control, - ett_lapd_control, is_response, TRUE, FALSE); + ett_lapd_control, &lapd_cf_items, &lapd_cf_items_ext, is_response, + TRUE, FALSE); lapd_header_len += XDLC_CONTROL_LEN(control, TRUE); if (tree) @@ -195,6 +234,54 @@ proto_register_lapd(void) { &hf_lapd_control, { "Control Field", "lapd.control", FT_UINT16, BASE_HEX, NULL, 0x0, "Control field", HFILL }}, + + { &hf_lapd_n_r, + { "N(R)", "lapd.control.n_r", FT_UINT16, BASE_DEC, + NULL, XDLC_N_R_EXT_MASK, "", HFILL }}, + + { &hf_lapd_n_s, + { "N(S)", "lapd.control.n_s", FT_UINT16, BASE_DEC, + NULL, XDLC_N_S_EXT_MASK, "", HFILL }}, + + { &hf_lapd_p, + { "Poll", "lapd.control.p", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_lapd_p_ext, + { "Poll", "lapd.control.p", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + + { &hf_lapd_f, + { "Final", "lapd.control.f", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_lapd_f_ext, + { "Final", "lapd.control.f", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + + { &hf_lapd_s_ftype, + { "Supervisory frame type", "lapd.control.s_ftype", FT_UINT16, BASE_HEX, + VALS(stype_vals), XDLC_S_FTYPE_MASK, "", HFILL }}, + + { &hf_lapd_u_modifier_cmd, + { "Command", "lapd.control.u_modifier_cmd", FT_UINT8, BASE_HEX, + VALS(modifier_vals_cmd), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_lapd_u_modifier_resp, + { "Response", "lapd.control.u_modifier_resp", FT_UINT8, BASE_HEX, + VALS(modifier_vals_resp), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_lapd_ftype_i, + { "Frame type", "lapd.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_I_MASK, "", HFILL }}, + + { &hf_lapd_ftype_s_u, + { "Frame type", "lapd.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, + + { &hf_lapd_ftype_s_u_ext, + { "Frame type", "lapd.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, }; static gint *ett[] = { &ett_lapd, diff --git a/packet-llc.c b/packet-llc.c index 3bd505e93d..59e5c12470 100644 --- a/packet-llc.c +++ b/packet-llc.c @@ -2,7 +2,7 @@ * Routines for IEEE 802.2 LLC layer * Gilbert Ramirez <gram@alumni.rice.edu> * - * $Id: packet-llc.c,v 1.116 2003/10/01 07:11:44 guy Exp $ + * $Id: packet-llc.c,v 1.117 2004/01/03 03:49:22 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -57,6 +57,18 @@ static int hf_llc_ssap = -1; static int hf_llc_dsap_ig = -1; static int hf_llc_ssap_cr = -1; static int hf_llc_ctrl = -1; +static int hf_llc_n_r = -1; +static int hf_llc_n_s = -1; +static int hf_llc_p = -1; +static int hf_llc_p_ext = -1; +static int hf_llc_f = -1; +static int hf_llc_f_ext = -1; +static int hf_llc_s_ftype = -1; +static int hf_llc_u_modifier_cmd = -1; +static int hf_llc_u_modifier_resp = -1; +static int hf_llc_ftype_i = -1; +static int hf_llc_ftype_s_u = -1; +static int hf_llc_ftype_s_u_ext = -1; static int hf_llc_type = -1; static int hf_llc_oui = -1; static int hf_llc_pid = -1; @@ -298,6 +310,32 @@ capture_llc(const guchar *pd, int offset, int len, packet_counts *ld) { } } +/* Used only for U frames */ +static const xdlc_cf_items llc_cf_items = { + NULL, + NULL, + &hf_llc_p, + &hf_llc_f, + NULL, + &hf_llc_u_modifier_cmd, + &hf_llc_u_modifier_resp, + NULL, + &hf_llc_ftype_s_u +}; + +/* Used only for I and S frames */ +static const xdlc_cf_items llc_cf_items_ext = { + &hf_llc_n_r, + &hf_llc_n_s, + &hf_llc_p_ext, + &hf_llc_f_ext, + &hf_llc_s_ftype, + NULL, + NULL, + &hf_llc_ftype_i, + &hf_llc_ftype_s_u_ext +}; + static void dissect_llc(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) { @@ -347,6 +385,7 @@ dissect_llc(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) */ control = dissect_xdlc_control(tvb, 2, pinfo, llc_tree, hf_llc_ctrl, ett_llc_ctrl, + &llc_cf_items, &llc_cf_items_ext, ssap & SSAP_CR_BIT, TRUE, FALSE); llc_header_len += XDLC_CONTROL_LEN(control, TRUE); if (is_snap) @@ -583,6 +622,54 @@ proto_register_llc(void) { "Control", "llc.control", FT_UINT16, BASE_HEX, NULL, 0x0, "", HFILL }}, + { &hf_llc_n_r, + { "N(R)", "llc.control.n_r", FT_UINT16, BASE_DEC, + NULL, XDLC_N_R_EXT_MASK, "", HFILL }}, + + { &hf_llc_n_s, + { "N(S)", "llc.control.n_s", FT_UINT16, BASE_DEC, + NULL, XDLC_N_S_EXT_MASK, "", HFILL }}, + + { &hf_llc_p, + { "Poll", "llc.control.p", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_llc_p_ext, + { "Poll", "llc.control.p", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + + { &hf_llc_f, + { "Final", "llc.control.f", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_llc_f_ext, + { "Final", "llc.control.f", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + + { &hf_llc_s_ftype, + { "Supervisory frame type", "llc.control.s_ftype", FT_UINT16, BASE_HEX, + VALS(stype_vals), XDLC_S_FTYPE_MASK, "", HFILL }}, + + { &hf_llc_u_modifier_cmd, + { "Command", "llc.control.u_modifier_cmd", FT_UINT8, BASE_HEX, + VALS(modifier_vals_cmd), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_llc_u_modifier_resp, + { "Response", "llc.control.u_modifier_resp", FT_UINT8, BASE_HEX, + VALS(modifier_vals_resp), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_llc_ftype_i, + { "Frame type", "llc.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_I_MASK, "", HFILL }}, + + { &hf_llc_ftype_s_u, + { "Frame type", "llc.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, + + { &hf_llc_ftype_s_u_ext, + { "Frame type", "llc.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, + /* registered here but handled in ethertype.c */ { &hf_llc_type, { "Type", "llc.type", FT_UINT16, BASE_HEX, diff --git a/packet-sdlc.c b/packet-sdlc.c index 8983090ee6..b777178f55 100644 --- a/packet-sdlc.c +++ b/packet-sdlc.c @@ -1,7 +1,7 @@ /* packet-sdlc.c * Routines for SDLC frame disassembly * - * $Id: packet-sdlc.c,v 1.2 2003/09/02 19:18:52 guy Exp $ + * $Id: packet-sdlc.c,v 1.3 2004/01/03 03:49:22 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -41,6 +41,15 @@ static int proto_sdlc = -1; static int hf_sdlc_address = -1; static int hf_sdlc_control = -1; +static int hf_sdlc_n_r = -1; +static int hf_sdlc_n_s = -1; +static int hf_sdlc_p = -1; +static int hf_sdlc_f = -1; +static int hf_sdlc_s_ftype = -1; +static int hf_sdlc_u_modifier_cmd = -1; +static int hf_sdlc_u_modifier_resp = -1; +static int hf_sdlc_ftype_i = -1; +static int hf_sdlc_ftype_s_u = -1; static gint ett_sdlc = -1; static gint ett_sdlc_control = -1; @@ -48,6 +57,18 @@ static gint ett_sdlc_control = -1; static dissector_handle_t sna_handle; static dissector_handle_t data_handle; +static const xdlc_cf_items sdlc_cf_items = { + &hf_sdlc_n_r, + &hf_sdlc_n_s, + &hf_sdlc_p, + &hf_sdlc_f, + &hf_sdlc_s_ftype, + &hf_sdlc_u_modifier_cmd, + &hf_sdlc_u_modifier_resp, + &hf_sdlc_ftype_i, + &hf_sdlc_ftype_s_u +}; + static void dissect_sdlc(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) { @@ -107,7 +128,7 @@ dissect_sdlc(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) * to control what to use. */ control = dissect_xdlc_control(tvb, 1, pinfo, sdlc_tree, hf_sdlc_control, - ett_sdlc_control, is_response, FALSE, FALSE); + ett_sdlc_control, &sdlc_cf_items, NULL, is_response, FALSE, FALSE); sdlc_header_len += XDLC_CONTROL_LEN(control, FALSE); if (tree) @@ -136,6 +157,42 @@ proto_register_sdlc(void) { &hf_sdlc_control, { "Control Field", "sdlc.control", FT_UINT16, BASE_HEX, NULL, 0x0, "Control field", HFILL }}, + + { &hf_sdlc_n_r, + { "N(R)", "sdlc.control.n_r", FT_UINT8, BASE_DEC, + NULL, XDLC_N_R_MASK, "", HFILL }}, + + { &hf_sdlc_n_s, + { "N(S)", "sdlc.control.n_s", FT_UINT8, BASE_DEC, + NULL, XDLC_N_S_MASK, "", HFILL }}, + + { &hf_sdlc_p, + { "Poll", "sdlc.control.p", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_sdlc_f, + { "Final", "sdlc.control.f", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + + { &hf_sdlc_s_ftype, + { "Supervisory frame type", "sdlc.control.s_ftype", FT_UINT8, BASE_HEX, + VALS(stype_vals), XDLC_S_FTYPE_MASK, "", HFILL }}, + + { &hf_sdlc_u_modifier_cmd, + { "Command", "sdlc.control.u_modifier_cmd", FT_UINT8, BASE_HEX, + VALS(modifier_vals_cmd), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_sdlc_u_modifier_resp, + { "Response", "sdlc.control.u_modifier_resp", FT_UINT8, BASE_HEX, + VALS(modifier_vals_resp), XDLC_U_MODIFIER_MASK, "", HFILL }}, + + { &hf_sdlc_ftype_i, + { "Frame type", "sdlc.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_I_MASK, "", HFILL }}, + + { &hf_sdlc_ftype_s_u, + { "Frame type", "sdlc.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, }; static gint *ett[] = { &ett_sdlc, diff --git a/packet-v120.c b/packet-v120.c index 25dc238d4e..610ea7eab0 100644 --- a/packet-v120.c +++ b/packet-v120.c @@ -2,7 +2,7 @@ * Routines for v120 frame disassembly * Bert Driehuis <driehuis@playbeing.org> * - * $Id: packet-v120.c,v 1.31 2003/09/02 19:18:52 guy Exp $ + * $Id: packet-v120.c,v 1.32 2004/01/03 03:49:22 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -36,6 +36,18 @@ static int proto_v120 = -1; static int hf_v120_address = -1; static int hf_v120_control = -1; +static int hf_v120_n_r = -1; +static int hf_v120_n_s = -1; +static int hf_v120_p = -1; +static int hf_v120_p_ext = -1; +static int hf_v120_f = -1; +static int hf_v120_f_ext = -1; +static int hf_v120_s_ftype = -1; +static int hf_v120_u_modifier_cmd = -1; +static int hf_v120_u_modifier_resp = -1; +static int hf_v120_ftype_i = -1; +static int hf_v120_ftype_s_u = -1; +static int hf_v120_ftype_s_u_ext = -1; static int hf_v120_header = -1; static gint ett_v120 = -1; @@ -47,6 +59,32 @@ static dissector_handle_t data_handle; static int dissect_v120_header(tvbuff_t *tvb, int offset, proto_tree *tree); +/* Used only for U frames */ +static const xdlc_cf_items v120_cf_items = { + NULL, + NULL, + &hf_v120_p, + &hf_v120_f, + NULL, + &hf_v120_u_modifier_cmd, + &hf_v120_u_modifier_resp, + NULL, + &hf_v120_ftype_s_u +}; + +/* Used only for I and S frames */ +static const xdlc_cf_items v120_cf_items_ext = { + &hf_v120_n_r, + &hf_v120_n_s, + &hf_v120_p_ext, + &hf_v120_f_ext, + &hf_v120_s_ftype, + NULL, + NULL, + &hf_v120_ftype_i, + &hf_v120_ftype_s_u_ext +}; + static void dissect_v120(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) { @@ -126,7 +164,8 @@ dissect_v120(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) ti = NULL; } control = dissect_xdlc_control(tvb, 2, pinfo, v120_tree, hf_v120_control, - ett_v120_control, is_response, TRUE, FALSE); + ett_v120_control, &v120_cf_items, &v120_cf_items_ext, + is_response, TRUE, FALSE); if (tree) { v120len = 2 + XDLC_CONTROL_LEN(control, TRUE); if (tvb_bytes_exist(tvb, v120len, 1)) @@ -204,6 +243,42 @@ proto_register_v120(void) { &hf_v120_control, { "Control Field", "v120.control", FT_UINT16, BASE_HEX, NULL, 0x0, "", HFILL }}, + { &hf_v120_n_r, + { "N(R)", "v120.control.n_r", FT_UINT16, BASE_DEC, + NULL, XDLC_N_R_EXT_MASK, "", HFILL }}, + { &hf_v120_n_s, + { "N(S)", "v120.control.n_s", FT_UINT16, BASE_DEC, + NULL, XDLC_N_S_EXT_MASK, "", HFILL }}, + { &hf_v120_p, + { "Poll", "v120.control.p", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + { &hf_v120_p_ext, + { "Poll", "v120.control.p", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + { &hf_v120_f, + { "Final", "v120.control.f", FT_BOOLEAN, 8, + TFS(&flags_set_truth), XDLC_P_F, "", HFILL }}, + { &hf_v120_f_ext, + { "Final", "v120.control.f", FT_BOOLEAN, 16, + TFS(&flags_set_truth), XDLC_P_F_EXT, "", HFILL }}, + { &hf_v120_s_ftype, + { "Supervisory frame type", "v120.control.s_ftype", FT_UINT16, BASE_HEX, + VALS(stype_vals), XDLC_S_FTYPE_MASK, "", HFILL }}, + { &hf_v120_u_modifier_cmd, + { "Command", "v120.control.u_modifier_cmd", FT_UINT8, BASE_HEX, + VALS(modifier_vals_cmd), XDLC_U_MODIFIER_MASK, "", HFILL }}, + { &hf_v120_u_modifier_resp, + { "Response", "v120.control.u_modifier_resp", FT_UINT8, BASE_HEX, + VALS(modifier_vals_resp), XDLC_U_MODIFIER_MASK, "", HFILL }}, + { &hf_v120_ftype_i, + { "Frame type", "v120.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_I_MASK, "", HFILL }}, + { &hf_v120_ftype_s_u, + { "Frame type", "v120.control.ftype", FT_UINT8, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, + { &hf_v120_ftype_s_u_ext, + { "Frame type", "v120.control.ftype", FT_UINT16, BASE_HEX, + VALS(ftype_vals), XDLC_S_U_MASK, "", HFILL }}, { &hf_v120_header, { "Header Field", "v120.header", FT_STRING, BASE_NONE, NULL, 0x0, "", HFILL }}, diff --git a/plugins/Xass-list b/plugins/Xass-list index a0052a3661..eb8c51e5eb 100644 --- a/plugins/Xass-list +++ b/plugins/Xass-list @@ -72,4 +72,4 @@ dissector_add_string, dissector_delete_string, dissector_change_string, dissector_reset_string, dissector_try_string, dissector_get_string_handle, get_datafile_path, get_tempfile_path, register_heur_dissector_list, dissector_try_heuristic, asn1_id_decode1, col_get_writable, col_set_writable, -decode_enumerated_bitfield_shifted, +decode_enumerated_bitfield_shifted, dissect_xdlc_control, diff --git a/plugins/Xplugin_api.c b/plugins/Xplugin_api.c index 1d14c7c2f0..71d21da36b 100644 --- a/plugins/Xplugin_api.c +++ b/plugins/Xplugin_api.c @@ -247,3 +247,4 @@ p_asn1_id_decode1 = pat->p_asn1_id_decode1; p_col_get_writable = pat->p_col_get_writable; p_col_set_writable = pat->p_col_set_writable; p_decode_enumerated_bitfield_shifted = pat->p_decode_enumerated_bitfield_shifted; +p_dissect_xdlc_control = pat->p_dissect_xdlc_control; diff --git a/plugins/Xplugin_api.h b/plugins/Xplugin_api.h index 4b86e4911d..f2cf939263 100644 --- a/plugins/Xplugin_api.h +++ b/plugins/Xplugin_api.h @@ -247,3 +247,4 @@ #define col_get_writable (*p_col_get_writable) #define col_set_writable (*p_col_set_writable) #define decode_enumerated_bitfield_shifted (*p_decode_enumerated_bitfield_shifted) +#define dissect_xdlc_control (*p_dissect_xdlc_control) diff --git a/plugins/Xplugin_api_decls.h b/plugins/Xplugin_api_decls.h index 2814307964..c865f917cb 100644 --- a/plugins/Xplugin_api_decls.h +++ b/plugins/Xplugin_api_decls.h @@ -247,3 +247,4 @@ addr_asn1_id_decode1 p_asn1_id_decode1; addr_col_get_writable p_col_get_writable; addr_col_set_writable p_col_set_writable; addr_decode_enumerated_bitfield_shifted p_decode_enumerated_bitfield_shifted; +addr_dissect_xdlc_control p_dissect_xdlc_control; diff --git a/plugins/Xplugin_table.h b/plugins/Xplugin_table.h index 9d0a8da59c..660808b322 100644 --- a/plugins/Xplugin_table.h +++ b/plugins/Xplugin_table.h @@ -247,3 +247,4 @@ typedef int (*addr_asn1_id_decode1) (ASN1_SCK *, guint *); typedef gboolean (*addr_col_get_writable) (column_info *); typedef void (*addr_col_set_writable) (column_info *, gboolean); typedef const char *(*addr_decode_enumerated_bitfield_shifted) (guint32, guint32, int, const value_string *, const char *); +typedef int (*addr_dissect_xdlc_control) (tvbuff_t *, int, packet_info *, proto_tree *, int, gint, const xdlc_cf_items *, const xdlc_cf_items *, int, int, int); diff --git a/plugins/plugin_api_list.c b/plugins/plugin_api_list.c index 07e326ea11..70b666efe5 100644 --- a/plugins/plugin_api_list.c +++ b/plugins/plugin_api_list.c @@ -1,7 +1,7 @@ /* plugin_api_list.c * Used to generate various included files for plugin API * - * $Id: plugin_api_list.c,v 1.19 2003/12/01 23:41:45 guy Exp $ + * $Id: plugin_api_list.c,v 1.20 2004/01/03 03:50:38 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -37,6 +37,7 @@ #include "packet-tcp.h" #include "tap.h" #include "asn1.h" +#include "xdlc.h" #include "epan/except.h" gint check_col(column_info*, gint); @@ -393,3 +394,8 @@ void col_set_writable(column_info *, gboolean); const char *decode_enumerated_bitfield_shifted(guint32, guint32, int, const value_string *, const char *); + +int dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, + proto_tree *xdlc_tree, int hf_xdlc_control, gint ett_xdlc_control, + const xdlc_cf_items *cf_items_nonext, const xdlc_cf_items *cf_items_ext, + int is_response, int extended, int append_info); @@ -2,7 +2,7 @@ * Routines for use by various SDLC-derived protocols, such as HDLC * and its derivatives LAPB, IEEE 802.2 LLC, etc.. * - * $Id: xdlc.c,v 1.21 2003/09/02 19:18:52 guy Exp $ + * $Id: xdlc.c,v 1.22 2004/01/03 03:49:23 guy Exp $ * * Ethereal - Network traffic analyzer * By Gerald Combs <gerald@ethereal.com> @@ -34,39 +34,19 @@ #include <epan/packet.h> #include "xdlc.h" -/* - * N(S) and N(R) fields, in basic and extended operation. - */ -#define XDLC_N_R_MASK 0xE0 /* basic */ -#define XDLC_N_R_SHIFT 5 -#define XDLC_N_R_EXT_MASK 0xFE00 /* extended */ -#define XDLC_N_R_EXT_SHIFT 9 -#define XDLC_N_S_MASK 0x0E /* basic */ -#define XDLC_N_S_SHIFT 1 -#define XDLC_N_S_EXT_MASK 0x00FE /* extended */ -#define XDLC_N_S_EXT_SHIFT 1 - -/* - * Poll/Final bit, in basic and extended operation. - */ -#define XDLC_P_F 0x10 /* basic */ -#define XDLC_P_F_EXT 0x0100 /* extended */ - -/* - * S-format frame types. - */ -#define XDLC_S_FTYPE_MASK 0x0C -#define XDLC_RR 0x00 /* Receiver ready */ -#define XDLC_RNR 0x04 /* Receiver not ready */ -#define XDLC_REJ 0x08 /* Reject */ -#define XDLC_SREJ 0x0C /* Selective reject */ +const value_string ftype_vals[] = { + { XDLC_I, "Information frame" }, + { XDLC_S, "Supervisory frame" }, + { XDLC_U, "Unnumbered frame" }, + { 0, NULL } +}; -static const value_string stype_vals[] = { - { XDLC_RR, "Receiver ready" }, - { XDLC_RNR, "Receiver not ready" }, - { XDLC_REJ, "Reject" }, - { XDLC_SREJ, "Selective reject" }, - { 0, NULL } +const value_string stype_vals[] = { + { XDLC_RR>>2, "Receiver ready" }, + { XDLC_RNR>>2, "Receiver not ready" }, + { XDLC_REJ>>2, "Reject" }, + { XDLC_SREJ>>2, "Selective reject" }, + { 0, NULL } }; static const value_string modifier_short_vals_cmd[] = { @@ -91,25 +71,25 @@ static const value_string modifier_short_vals_cmd[] = { { 0, NULL } }; -static const value_string modifier_vals_cmd[] = { - { XDLC_UI, "Unnumbered Information" }, - { XDLC_UP, "Unnumbered Poll" }, - { XDLC_DISC, "Disconnect" }, - { XDLC_UA, "Unnumbered Acknowledge" }, - { XDLC_SNRM, "Set Normal Response Mode" }, - { XDLC_TEST, "Test" }, - { XDLC_SIM, "Set Initialization Mode" }, - { XDLC_FRMR, "Frame reject" }, - { XDLC_CFGR, "Configure" }, - { XDLC_SARM, "Set Asynchronous Response Mode" }, - { XDLC_SABM, "Set Asynchronous Balanced Mode" }, - { XDLC_SARME, "Set Asynchronous Response Mode Extended" }, - { XDLC_SABME, "Set Asynchronous Balanced Mode Extended" }, - { XDLC_RESET, "Reset" }, - { XDLC_XID, "Exchange identification" }, - { XDLC_SNRME, "Set Normal Response Mode Extended" }, - { XDLC_BCN, "Beacon" }, - { 0, NULL } +const value_string modifier_vals_cmd[] = { + { XDLC_UI>>2, "Unnumbered Information" }, + { XDLC_UP>>2, "Unnumbered Poll" }, + { XDLC_DISC>>2, "Disconnect" }, + { XDLC_UA>>2, "Unnumbered Acknowledge" }, + { XDLC_SNRM>>2, "Set Normal Response Mode" }, + { XDLC_TEST>>2, "Test" }, + { XDLC_SIM>>2, "Set Initialization Mode" }, + { XDLC_FRMR>>2, "Frame reject" }, + { XDLC_CFGR>>2, "Configure" }, + { XDLC_SARM>>2, "Set Asynchronous Response Mode" }, + { XDLC_SABM>>2, "Set Asynchronous Balanced Mode" }, + { XDLC_SARME>>2, "Set Asynchronous Response Mode Extended" }, + { XDLC_SABME>>2, "Set Asynchronous Balanced Mode Extended" }, + { XDLC_RESET>>2, "Reset" }, + { XDLC_XID>>2, "Exchange identification" }, + { XDLC_SNRME>>2, "Set Normal Response Mode Extended" }, + { XDLC_BCN>>2, "Beacon" }, + { 0, NULL } }; static const value_string modifier_short_vals_resp[] = { @@ -133,25 +113,25 @@ static const value_string modifier_short_vals_resp[] = { { 0, NULL } }; -static const value_string modifier_vals_resp[] = { - { XDLC_UI, "Unnumbered Information" }, - { XDLC_UP, "Unnumbered Poll" }, - { XDLC_RD, "Request Disconnect" }, - { XDLC_UA, "Unnumbered Acknowledge" }, - { XDLC_SNRM, "Set Normal Response Mode" }, - { XDLC_TEST, "Test" }, - { XDLC_RIM, "Request Initialization Mode" }, - { XDLC_FRMR, "Frame reject" }, - { XDLC_CFGR, "Configure" }, - { XDLC_DM, "Disconnected mode" }, - { XDLC_SABM, "Set Asynchronous Balanced Mode" }, - { XDLC_SARME, "Set Asynchronous Response Mode Extended" }, - { XDLC_SABME, "Set Asynchronous Balanced Mode Extended" }, - { XDLC_RESET, "Reset" }, - { XDLC_XID, "Exchange identification" }, - { XDLC_SNRME, "Set Normal Response Mode Extended" }, - { XDLC_BCN, "Beacon" }, - { 0, NULL } +const value_string modifier_vals_resp[] = { + { XDLC_UI>>2, "Unnumbered Information" }, + { XDLC_UP>>2, "Unnumbered Poll" }, + { XDLC_RD>>2, "Request Disconnect" }, + { XDLC_UA>>2, "Unnumbered Acknowledge" }, + { XDLC_SNRM>>2, "Set Normal Response Mode" }, + { XDLC_TEST>>2, "Test" }, + { XDLC_RIM>>2, "Request Initialization Mode" }, + { XDLC_FRMR>>2, "Frame reject" }, + { XDLC_CFGR>>2, "Configure" }, + { XDLC_DM>>2, "Disconnected mode" }, + { XDLC_SABM>>2, "Set Asynchronous Balanced Mode" }, + { XDLC_SARME>>2, "Set Asynchronous Response Mode Extended" }, + { XDLC_SABME>>2, "Set Asynchronous Balanced Mode Extended" }, + { XDLC_RESET>>2, "Reset" }, + { XDLC_XID>>2, "Exchange identification" }, + { XDLC_SNRME>>2, "Set Normal Response Mode Extended" }, + { XDLC_BCN>>2, "Beacon" }, + { 0, NULL } }; int @@ -192,9 +172,14 @@ get_xdlc_control(const guchar *pd, int offset, int is_extended) int dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, proto_tree *xdlc_tree, int hf_xdlc_control, gint ett_xdlc_control, + const xdlc_cf_items *cf_items_nonext, const xdlc_cf_items *cf_items_ext, int is_response, int is_extended, int append_info) { guint16 control; + int control_len; + const xdlc_cf_items *cf_items; + char *control_format; + guint16 poll_final; char info[80]; proto_tree *tc, *control_tree; gchar *frame_type = NULL; @@ -203,13 +188,20 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, switch (tvb_get_guint8(tvb, offset) & 0x03) { case XDLC_S: + if (is_extended) { + control = tvb_get_letohs(tvb, offset); + control_len = 2; + cf_items = cf_items_ext; + control_format = "Control field: %s (0x%04X)"; + } else { + control = tvb_get_guint8(tvb, offset); + control_len = 1; + cf_items = cf_items_nonext; + control_format = "Control field: %s (0x%02X)"; + } /* * Supervisory frame. */ - if (is_extended) - control = tvb_get_letohs(tvb, offset); - else - control = tvb_get_guint8(tvb, offset); switch (control & XDLC_S_FTYPE_MASK) { case XDLC_RR: frame_type = "RR"; @@ -228,14 +220,16 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, break; } if (is_extended) { + poll_final = (control & XDLC_P_F_EXT); sprintf(info, "S%s, %sN(R) = %u", frame_type, - ((control & XDLC_P_F_EXT) ? + (poll_final ? (is_response ? "func = F, " : "func = P, ") : ""), (control & XDLC_N_R_EXT_MASK) >> XDLC_N_R_EXT_SHIFT); } else { + poll_final = (control & XDLC_P_F); sprintf(info, "S%s, %sN(R) = %u", frame_type, - ((control & XDLC_P_F) ? + (poll_final ? (is_response ? "func = F, " : "func = P, ") : ""), (control & XDLC_N_R_MASK) >> XDLC_N_R_SHIFT); @@ -248,49 +242,22 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, col_add_str(pinfo->cinfo, COL_INFO, info); } if (xdlc_tree) { - if (is_extended) { - tc = proto_tree_add_uint_format(xdlc_tree, hf_xdlc_control, tvb, - offset, 2, - control, - "Control field: %s (0x%04X)", info, control); - control_tree = proto_item_add_subtree(tc, ett_xdlc_control); - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_numeric_bitfield(control, XDLC_N_R_EXT_MASK, 2*8, - "N(R) = %u")); - if (control & XDLC_P_F_EXT) { - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_boolean_bitfield(control, XDLC_P_F_EXT, 2*8, - (is_response ? "Final" : "Poll"), NULL)); - } - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_enumerated_bitfield(control, XDLC_S_FTYPE_MASK, 2*8, - stype_vals, "Supervisory frame - %s")); - /* This will always say it's a supervisory frame */ - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_boolean_bitfield(control, 0x03, 2*8, - "Supervisory frame", NULL)); - } else { - tc = proto_tree_add_uint_format(xdlc_tree, hf_xdlc_control, tvb, - offset, 1, - control, - "Control field: %s (0x%02X)", info, control); - control_tree = proto_item_add_subtree(tc, ett_xdlc_control); - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_numeric_bitfield(control, XDLC_N_R_MASK, 1*8, - "N(R) = %u")); - if (control & XDLC_P_F) { - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_boolean_bitfield(control, XDLC_P_F, 1*8, - (is_response ? "Final" : "Poll"), NULL)); - } - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_enumerated_bitfield(control, XDLC_S_FTYPE_MASK, 1*8, - stype_vals, "%s")); - /* This will always say it's a supervisory frame */ - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_boolean_bitfield(control, 0x03, 1*8, - "Supervisory frame", NULL)); + tc = proto_tree_add_uint_format(xdlc_tree, hf_xdlc_control, tvb, + offset, control_len, control, control_format, info, control); + control_tree = proto_item_add_subtree(tc, ett_xdlc_control); + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_n_r, + tvb, offset, control_len, control); + if (poll_final) { + proto_tree_add_boolean(control_tree, + (is_response ? *cf_items->hf_xdlc_f : + *cf_items->hf_xdlc_p), + tvb, offset, control_len, control); } + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_s_ftype, + tvb, offset, control_len, control); + /* This will always say it's a supervisory frame */ + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_ftype_s_u, + tvb, offset, control_len, control); } break; @@ -306,6 +273,9 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, * need for it to be 2 bytes in extended operation. */ control = tvb_get_guint8(tvb, offset); + control_len = 1; + cf_items = cf_items_nonext; + control_format = "Control field: %s (0x%02X)"; if (is_response) { modifier = match_strval(control & XDLC_U_MODIFIER_MASK, modifier_short_vals_resp); @@ -315,8 +285,9 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, } if (modifier == NULL) modifier = "Unknown"; + poll_final = (control & XDLC_P_F); sprintf(info, "U%s, func = %s", - ((control & XDLC_P_F) ? + (poll_final ? (is_response ? " F" : " P") : ""), modifier); @@ -328,24 +299,22 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, col_add_str(pinfo->cinfo, COL_INFO, info); } if (xdlc_tree) { - tc = proto_tree_add_uint_format(xdlc_tree, hf_xdlc_control, tvb, - offset, 1, - control, - "Control field: %s (0x%02X)", info, control); + tc = proto_tree_add_uint_format(xdlc_tree, hf_xdlc_control, tvb, + offset, control_len, control, control_format, info, control); control_tree = proto_item_add_subtree(tc, ett_xdlc_control); - if (control & XDLC_P_F) { - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_boolean_bitfield(control, XDLC_P_F, 1*8, - (is_response ? "Final" : "Poll"), NULL)); + if (poll_final) { + proto_tree_add_boolean(control_tree, + (is_response ? *cf_items->hf_xdlc_f: + *cf_items->hf_xdlc_p), + tvb, offset, control_len, control); } - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_enumerated_bitfield(control, XDLC_U_MODIFIER_MASK, 1*8, - (is_response ? modifier_vals_resp : modifier_vals_cmd), - "%s")); + proto_tree_add_uint(control_tree, + (is_response ? *cf_items->hf_xdlc_u_modifier_resp : + *cf_items->hf_xdlc_u_modifier_cmd), + tvb, offset, control_len, control); /* This will always say it's an unnumbered frame */ - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_boolean_bitfield(control, 0x03, 1*8, - "Unnumbered frame", NULL)); + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_ftype_s_u, + tvb, offset, control_len, control); } break; @@ -353,16 +322,22 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, /* * Information frame. */ - if (is_extended) - control = tvb_get_letohs(tvb, offset); - else - control = tvb_get_guint8(tvb, offset); if (is_extended) { + control = tvb_get_letohs(tvb, offset); + control_len = 2; + cf_items = cf_items_ext; + control_format = "Control field: %s (0x%04X)"; + poll_final = (control & XDLC_P_F_EXT); sprintf(info, "I%s, N(R) = %u, N(S) = %u", ((control & XDLC_P_F_EXT) ? " P" : ""), (control & XDLC_N_R_EXT_MASK) >> XDLC_N_R_EXT_SHIFT, (control & XDLC_N_S_EXT_MASK) >> XDLC_N_S_EXT_SHIFT); } else { + control = tvb_get_guint8(tvb, offset); + control_len = 1; + cf_items = cf_items_nonext; + control_format = "Control field: %s (0x%02X)"; + poll_final = (control & XDLC_P_F); sprintf(info, "I%s, N(R) = %u, N(S) = %u", ((control & XDLC_P_F) ? " P" : ""), (control & XDLC_N_R_MASK) >> XDLC_N_R_SHIFT, @@ -377,46 +352,21 @@ dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, } if (xdlc_tree) { tc = proto_tree_add_uint_format(xdlc_tree, hf_xdlc_control, tvb, - offset, (is_extended) ? 2 : 1, - control, - (is_extended) ? "Control field: %s (0x%04X)" - : "Control field: %s (0x%02X)", - info, control); + offset, control_len, control, control_format, info, control); control_tree = proto_item_add_subtree(tc, ett_xdlc_control); - if (is_extended) { - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_numeric_bitfield(control, XDLC_N_R_EXT_MASK, 2*8, - "N(R) = %u")); - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_numeric_bitfield(control, XDLC_N_S_EXT_MASK, 2*8, - "N(S) = %u")); - if (control & XDLC_P_F_EXT) { - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_boolean_bitfield(control, XDLC_P_F_EXT, 2*8, - "Poll", NULL)); - } - /* This will always say it's an information frame */ - proto_tree_add_text(control_tree, tvb, offset, 2, - decode_boolean_bitfield(control, 0x01, 2*8, - NULL, "Information frame")); - } else { - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_numeric_bitfield(control, XDLC_N_R_MASK, 1*8, - "N(R) = %u")); - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_numeric_bitfield(control, XDLC_N_S_MASK, 1*8, - "N(S) = %u")); - if (control & XDLC_P_F) { - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_boolean_bitfield(control, XDLC_P_F, 1*8, - "Poll", NULL)); - } - /* This will always say it's an information frame */ - proto_tree_add_text(control_tree, tvb, offset, 1, - decode_boolean_bitfield(control, 0x01, 1*8, - NULL, "Information frame")); + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_n_r, + tvb, offset, control_len, control); + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_n_s, + tvb, offset, control_len, control); + if (poll_final) { + proto_tree_add_boolean(control_tree, *cf_items->hf_xdlc_p, + tvb, offset, control_len, control); } + /* This will always say it's an information frame */ + proto_tree_add_uint(control_tree, *cf_items->hf_xdlc_ftype_i, + tvb, offset, control_len, control); } + break; } return control; } @@ -2,13 +2,12 @@ * Define *DLC frame types, and routine to dissect the control field of * a *DLC frame. * - * $Id: xdlc.h,v 1.18 2003/09/02 19:18:52 guy Exp $ + * $Id: xdlc.h,v 1.19 2004/01/03 03:49:23 guy Exp $ * * Ethereal - Network traffic analyzer - * By Gerald Combs <gerald@zing.org> + * By Gerald Combs <gerald@ethereal.com> * Copyright 1998 Gerald Combs * - * * 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 @@ -31,9 +30,38 @@ * Low-order bits of first (extended) or only (basic) octet of control * field, specifying the frame type. */ -#define XDLC_I 0x00 /* Information frames */ -#define XDLC_S 0x01 /* Supervisory frames */ -#define XDLC_U 0x03 /* Unnumbered frames */ +#define XDLC_I_MASK 0x01 /* Mask to test for I or not I */ +#define XDLC_I 0x00 /* Information frames */ +#define XDLC_S_U_MASK 0x03 /* Mask to test for S or U */ +#define XDLC_S 0x01 /* Supervisory frames */ +#define XDLC_U 0x03 /* Unnumbered frames */ + +/* + * N(S) and N(R) fields, in basic and extended operation. + */ +#define XDLC_N_R_MASK 0xE0 /* basic */ +#define XDLC_N_R_SHIFT 5 +#define XDLC_N_R_EXT_MASK 0xFE00 /* extended */ +#define XDLC_N_R_EXT_SHIFT 9 +#define XDLC_N_S_MASK 0x0E /* basic */ +#define XDLC_N_S_SHIFT 1 +#define XDLC_N_S_EXT_MASK 0x00FE /* extended */ +#define XDLC_N_S_EXT_SHIFT 1 + +/* + * Poll/Final bit, in basic and extended operation. + */ +#define XDLC_P_F 0x10 /* basic */ +#define XDLC_P_F_EXT 0x0100 /* extended */ + +/* + * S-format frame types. + */ +#define XDLC_S_FTYPE_MASK 0x0C +#define XDLC_RR 0x00 /* Receiver ready */ +#define XDLC_RNR 0x04 /* Receiver not ready */ +#define XDLC_REJ 0x08 /* Reject */ +#define XDLC_SREJ 0x0C /* Selective reject */ /* * U-format modifiers. @@ -68,7 +96,7 @@ * e.g. TEST frames. */ #define XDLC_IS_INFORMATION(control) \ - (((control) & 0x1) == XDLC_I || (control) == (XDLC_UI|XDLC_U)) + (((control) & XDLC_I_MASK) == XDLC_I || (control) == (XDLC_UI|XDLC_U)) /* * This macro takes the control field of an xDLC frame, and a flag saying @@ -77,13 +105,34 @@ * in extended mode, it's 1 byte long, otherwise it's 2 bytes long). */ #define XDLC_CONTROL_LEN(control, is_extended) \ - ((((control) & 0x3) == XDLC_U || !(is_extended)) ? 1 : 2) + ((((control) & XDLC_S_U_MASK) == XDLC_U || !(is_extended)) ? 1 : 2) + +/* + * Structure containing pointers to hf_ values for various subfields of + * the control field. + */ +typedef struct { + int *hf_xdlc_n_r; + int *hf_xdlc_n_s; + int *hf_xdlc_p; + int *hf_xdlc_f; + int *hf_xdlc_s_ftype; + int *hf_xdlc_u_modifier_cmd; + int *hf_xdlc_u_modifier_resp; + int *hf_xdlc_ftype_i; + int *hf_xdlc_ftype_s_u; +} xdlc_cf_items; + +extern const value_string ftype_vals[]; +extern const value_string stype_vals[]; +extern const value_string modifier_vals_cmd[]; +extern const value_string modifier_vals_resp[]; -int get_xdlc_control(const guchar *pd, int offset, - int extended); +extern int get_xdlc_control(const guchar *pd, int offset, int extended); -int dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, +extern int dissect_xdlc_control(tvbuff_t *tvb, int offset, packet_info *pinfo, proto_tree *xdlc_tree, int hf_xdlc_control, gint ett_xdlc_control, + const xdlc_cf_items *cf_items_nonext, const xdlc_cf_items *cf_items_ext, int is_response, int extended, int append_info); #endif |