Exemplo n.º 1
0
/* ================================================================= */
static void
dissect_serialization(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
	proto_tree	*ser_tree = NULL;
	proto_item	*ti;

	col_set_str(pinfo->cinfo, COL_PROTOCOL, "NW_SERIAL");
	col_clear(pinfo->cinfo, COL_INFO);

	if (tree) {
		ti = proto_tree_add_item(tree, proto_serialization, tvb, 0, -1,
		    ENC_NA);
		ser_tree = proto_item_add_subtree(ti, ett_serialization);
	}

	if (check_col(pinfo->cinfo, COL_INFO)) {
		col_add_fstr(pinfo->cinfo, COL_INFO, "Serial number %s",
		    tvb_bytes_to_str(tvb, 0, 6));
	}

	if (tree) {
		proto_tree_add_text(ser_tree, tvb, 0, 6,
		      "Serial number: %s", tvb_bytes_to_str(tvb, 0, 6));
	}
}
Exemplo n.º 2
0
static int
dissect_bencoded_string(tvbuff_t *tvb, packet_info _U_*pinfo, proto_tree *tree, guint offset, char **result, gboolean tohex, char *label )
{
  guint string_len_start;
  guint string_len;

  string_len_start = offset;

  while( tvb_get_guint8(tvb,offset) != ':' )
    offset += 1;

  string_len = atoi( tvb_get_ephemeral_string(tvb,string_len_start,offset-string_len_start) );
  /* skip the ':' */
  offset += 1;

  /* fill the return data */
  if( tohex )
    *result = tvb_bytes_to_str(tvb, offset, string_len );
  else
    *result = tvb_get_ephemeral_string( tvb, offset, string_len );

  proto_tree_add_string_format( tree, hf_bencoded_string, tvb, offset, string_len, *result, "%s: %s", label, *result );
  offset += string_len;
  return offset;
}
Exemplo n.º 3
0
static void
add_octetstring_value(const gchar *tag_desc, proto_tree *tree, tvbuff_t *tvb,
                      int offset, int name_length, int value_length)
{
    offset = add_value_head(tag_desc, tree, tvb, offset, name_length,
                            value_length, NULL);
    proto_tree_add_text(tree, tvb, offset, value_length,
                        "Value: %s", tvb_bytes_to_str(tvb, offset, value_length));
}
Exemplo n.º 4
0
static gchar *
tvb_aarpproaddr_to_str(tvbuff_t *tvb, gint offset, int ad_len, guint16 type)
{
  if (AARP_PRO_IS_ATALK(type, ad_len)) {
    /* Appletalk address.  */
    return tvb_atalkid_to_str(tvb, offset);
  }
  return tvb_bytes_to_str(tvb, offset, ad_len);
}
Exemplo n.º 5
0
static gint
dissect_om2k_attr_unkn(tvbuff_t *tvb, gint offset, gint len, gint iei, proto_tree *tree)
{
	proto_tree_add_bytes_format(tree, hf_om2k_unknown_val, tvb,
				    offset, len, NULL,
				    "%s: %s",
				    val_to_str_ext(iei, &om2k_attr_vals_ext, "0x%02x"),
				    tvb_bytes_to_str(wmem_packet_scope(), tvb, offset, len));
	return len;
}
Exemplo n.º 6
0
static const gchar *
tvb_aarphrdaddr_to_str(tvbuff_t *tvb, gint offset, int ad_len, guint16 type)
{
  if (AARP_HW_IS_ETHER(type, ad_len)) {
    /* Ethernet address (or Token Ring address, which is the same type
       of address). */
    return tvb_ether_to_str(tvb, offset);
  }
  return tvb_bytes_to_str(tvb, offset, ad_len);
}
Exemplo n.º 7
0
static int
dissect_bt_dht_nodes(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, guint offset, char **result, char *label )
{
  proto_item *ti;
  proto_tree *sub_tree;
  proto_item *node_ti;
  proto_tree *node_tree;

  guint       node_index;
  guint       string_len_start;
  guint       string_len;
  address     addr;
  guint16     port;
  guint8     *id;

  ti = proto_tree_add_item( tree, hf_bt_dht_nodes, tvb, offset, 0, ENC_NA );
  sub_tree = proto_item_add_subtree( ti, ett_bt_dht_nodes);
  node_index = 0;

  string_len_start = offset;
  while( tvb_get_guint8(tvb,offset) != ':' )
    offset += 1;

  string_len = atoi( tvb_get_ephemeral_string(tvb,string_len_start,offset-string_len_start) );
  /* skip the ':' */
  offset += 1;

  /* 20 bytes id, 4 bytes ip, 2 bytes port */
  for( ; string_len>=26; string_len-=26, offset+=26 )
  {
    node_index += 1;

    id = tvb_bytes_to_str(tvb, offset, 20 );
    SET_ADDRESS( &addr, AT_IPv4, 4, tvb_get_ptr( tvb, offset, 4) );
    port = tvb_get_letohl( tvb, offset+24 );

    node_ti = proto_tree_add_none_format( sub_tree, hf_bt_dht_node, tvb, offset, 26,
        "%d\t%s %s:%u", node_index, id, ep_address_to_str( &addr ), port );
    node_tree = proto_item_add_subtree( node_ti, ett_bt_dht_peers);

    proto_tree_add_item( node_tree, hf_bt_dht_id, tvb, offset, 20, ENC_NA);
    proto_tree_add_item( node_tree, hf_ip, tvb, offset+20, 4, ENC_BIG_ENDIAN);
    proto_tree_add_item( node_tree, hf_port, tvb, offset+24, 2, ENC_BIG_ENDIAN);
  }
  if( string_len>0 )
  {
    proto_tree_add_item( tree, hf_truncated_data, tvb, offset, string_len, ENC_NA );
    offset += string_len;
  }
  proto_item_set_text( ti, "%s: %d nodes", label, node_index );
  col_append_fstr( pinfo->cinfo, COL_INFO, "reply=%d nodes  ", node_index );
  *result = ep_strdup_printf("%d", node_index);

  return offset;
}
Exemplo n.º 8
0
/* Add a default subtree to a tree item */
void rmt_ext_decode_default_subtree(struct _ext *e, tvbuff_t *tvb, proto_item *ti, gint ett)
{
	proto_tree *ext_tree;

	ext_tree = proto_item_add_subtree(ti, ett);
	rmt_ext_decode_default_header(e, tvb, ext_tree);

	if (ext_tree)
		proto_tree_add_text(ext_tree, tvb, e->hec_offset, e->hec_size,
			"Header Extension Content (HEC): %s", tvb_bytes_to_str(tvb, e->hec_offset, e->hec_size));
}
Exemplo n.º 9
0
const gchar *
tvb_arphrdaddr_to_str(tvbuff_t *tvb, gint offset, int ad_len, guint16 type)
{
  if (ad_len == 0)
    return "<No address>";
  if (ARP_HW_IS_ETHER(type, ad_len)) {
    /* Ethernet address (or IEEE 802.x address, which is the same type of
       address). */
    return tvb_ether_to_str(tvb, offset);
  }
  return tvb_bytes_to_str(tvb, offset, ad_len);
}
Exemplo n.º 10
0
static proto_tree *
add_octetstring_tree(proto_tree *tree, tvbuff_t *tvb, int offset,
                     int name_length, int value_length)
{
    proto_item *ti;

    ti = proto_tree_add_text(tree, tvb, offset,
                             1 + 2 + name_length + 2 + value_length,
                             "%s: %s",
                             tvb_format_text(tvb, offset + 1 + 2, name_length),
                             tvb_bytes_to_str(tvb, offset + 1 + 2 + name_length + 2, value_length));
    return proto_item_add_subtree(ti, ett_ipp_attr);
}
Exemplo n.º 11
0
WSLUA_METAMETHOD Tvb__tostring(lua_State* L) {
    /* Convert the bytes of a `Tvb` into a string, to be used for debugging purposes, as '...'
       will be appended if the string is too long. */
    Tvb tvb = checkTvb(L,1);
    int len = tvb_captured_length(tvb->ws_tvb);
    char* str = tvb_bytes_to_str(NULL,tvb->ws_tvb,0,len);

    lua_pushfstring(L, "TVB(%d) : %s", len, str);

    wmem_free(NULL, str);

    WSLUA_RETURN(1); /* The string. */
}
Exemplo n.º 12
0
WSLUA_METAMETHOD TvbRange__tostring(lua_State* L) {
	/* Converts the TvbRange into a string. As the string gets truncated
	   you should use this only for debugging purposes
	   or if what you want is to have a truncated string in the format 67:89:AB:... */
    TvbRange tvbr = checkTvbRange(L,1);

    if (!(tvbr && tvbr->tvb)) return 0;
    if (tvbr->tvb->expired) {
        luaL_error(L,"expired tvb");
        return 0;
    }

    lua_pushstring(L,tvb_bytes_to_str(tvbr->tvb->ws_tvb,tvbr->offset,tvbr->len));
    return 1;
}
Exemplo n.º 13
0
static int
dissect_bencoded_string(tvbuff_t *tvb, packet_info _U_*pinfo, proto_tree *tree, guint offset, char **result, gboolean tohex, const char *label )
{
  guint string_len;
  string_len = bencoded_string_length(tvb, &offset);

  /* fill the return data */
  if( tohex )
    *result = tvb_bytes_to_str(tvb, offset, string_len );
  else
    *result = tvb_get_string( wmem_packet_scope(), tvb, offset, string_len );

  proto_tree_add_string_format( tree, hf_bencoded_string, tvb, offset, string_len, *result, "%s: %s", label, *result );
  offset += string_len;
  return offset;
}
Exemplo n.º 14
0
WSLUA_METAMETHOD Tvb__tostring(lua_State* L) {
	/* Convert the bytes of a Tvb into a string, to be used for debugging purposes as '...' will be appended in case the string is too long. */
    Tvb tvb = checkTvb(L,1);
    int len;
    gchar* str;

    if (!tvb) return 0;
    if (tvb->expired) {
        luaL_error(L,"expired tvb");
        return 0;
    }

    len = tvb_length(tvb->ws_tvb);
    str = ep_strdup_printf("TVB(%i) : %s",len,tvb_bytes_to_str(tvb->ws_tvb,0,len));
    lua_pushstring(L,str);
    WSLUA_RETURN(1); /* The string. */
}
Exemplo n.º 15
0
static int
dissect_bt_dht_nodes(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, guint offset, char **result, const char *label )
{
  proto_item *ti;
  proto_tree *sub_tree;
  proto_item *node_ti;
  proto_tree *node_tree;

  guint       node_index;
  guint       string_len;

  string_len = bencoded_string_length(tvb, &offset);

  ti = proto_tree_add_item( tree, hf_bt_dht_nodes, tvb, offset, string_len, ENC_NA );
  sub_tree = proto_item_add_subtree( ti, ett_bt_dht_nodes);
  node_index = 0;

  /* 20 bytes id, 4 bytes ip, 2 bytes port */
  for( ; string_len>=26; string_len-=26, offset+=26 )
  {
    node_index += 1;


    node_ti = proto_tree_add_item( sub_tree, hf_bt_dht_node, tvb, offset, 26, ENC_NA);
    proto_item_append_text(node_ti, " %d", node_index);
    node_tree = proto_item_add_subtree( node_ti, ett_bt_dht_peers);

    proto_tree_add_item( node_tree, hf_bt_dht_id, tvb, offset, 20, ENC_NA);
    proto_item_append_text(node_ti, " (id: %s", tvb_bytes_to_str(tvb, offset, 20));
    proto_tree_add_item( node_tree, hf_ip, tvb, offset+20, 4, ENC_BIG_ENDIAN);
    proto_item_append_text(node_ti, ", IP/Port: %s", tvb_ip_to_str(tvb, offset+20));
    proto_tree_add_item( node_tree, hf_port, tvb, offset+24, 2, ENC_BIG_ENDIAN);
    proto_item_append_text(node_ti, ":%u)", tvb_get_ntohs( tvb, offset+24 ));
  }
  if( string_len>0 )
  {
    proto_tree_add_item( tree, hf_truncated_data, tvb, offset, string_len, ENC_NA );
    offset += string_len;
  }
  proto_item_set_text( ti, "%s: %d nodes", label, node_index );
  col_append_fstr( pinfo->cinfo, COL_INFO, "reply=%d nodes ", node_index );
  *result = wmem_strdup_printf(wmem_packet_scope(), "%d", node_index);

  return offset;
}
Exemplo n.º 16
0
WSLUA_METAMETHOD TvbRange__tostring(lua_State* L) {
    /* Converts the `TvbRange` into a string. Since the string gets truncated,
       you should use this only for debugging purposes
       or if what you want is to have a truncated string in the format 67:89:AB:... */
    TvbRange tvbr = checkTvbRange(L,1);
    char* str = NULL;

    if (!(tvbr && tvbr->tvb)) return 0;
    if (tvbr->tvb->expired) {
        luaL_error(L,"expired tvb");
        return 0;
    }

    str = tvb_bytes_to_str(NULL,tvbr->tvb->ws_tvb,tvbr->offset,tvbr->len);

    lua_pushstring(L,str);
    wmem_free(NULL, str);

    WSLUA_RETURN(1); /* A Lua hex string of the first 24 binary bytes in the `TvbRange`. */
}
Exemplo n.º 17
0
static int
add_session_id(proto_tree *tree, int hf, int hf_str, tvbuff_t *tvb, int offset)
{
	guint count;
	guint i;
	guint64 session_id;
	header_field_info *hfinfo;

	count = tvb_get_guint8(tvb, offset);
	if (count == 0)
		proto_tree_add_string (tree, hf_str, tvb, offset, count+1, "NULL");
	else if (count <= 8) {
		session_id = 0;
		for (i = 0; i < count; i++)
			session_id = (session_id << 8) | tvb_get_guint8(tvb, offset + i);
		proto_tree_add_uint64 (tree, hf, tvb, offset, count+1, session_id);
	} else {
		hfinfo = proto_registrar_get_nth(hf);
		proto_tree_add_text (tree, tvb, offset, count+1, "%s: %s",
		    hfinfo->name, tvb_bytes_to_str(tvb, offset+1, count));
	}
	return offset+1+count;
}
Exemplo n.º 18
0
/*
 * dissect_pgm - The dissector for Pragmatic General Multicast
 */
static void
dissect_pgm(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
	guint16 pgmhdr_sport;
	guint16 pgmhdr_dport;
	guint8 pgmhdr_type;
	guint8 pgmhdr_opts;
	guint16 pgmhdr_cksum;
	guint16 pgmhdr_tsdulen;
	guint32 sqn;
	guint16 afi;

	guint plen = 0;
	proto_item *ti;
	const char *pktname;
	const char *pollstname;
	char *gsi;
	gboolean isdata = FALSE;
	guint pgmlen, reportedlen;

	col_set_str(pinfo->cinfo, COL_PROTOCOL, "PGM");

	if (check_col(pinfo->cinfo, COL_INFO)) {
		col_clear(pinfo->cinfo, COL_INFO);
		if (tvb_reported_length_remaining(tvb, 0) < 18) {
			col_set_str(pinfo->cinfo, COL_INFO,
				"Packet too small");
			return;
		}
	}

	pinfo->srcport = pgmhdr_sport = tvb_get_ntohs(tvb, 0);
	pinfo->destport = pgmhdr_dport = tvb_get_ntohs(tvb, 2);

	pgmhdr_type = tvb_get_guint8(tvb, 4);
	pktname = val_to_str(pgmhdr_type, type_vals, "Unknown (0x%02x)");

	pgmhdr_opts = tvb_get_guint8(tvb, 5);
	pgmhdr_cksum = tvb_get_ntohs(tvb, 6);
	gsi = tvb_bytes_to_str(tvb, 8, 6);
	pgmhdr_tsdulen = tvb_get_ntohs(tvb, 14);
	sqn = tvb_get_ntohl(tvb, 16);

	switch(pgmhdr_type) {
	case PGM_SPM_PCKT:
	case PGM_NAK_PCKT:
	case PGM_NNAK_PCKT:
	case PGM_NCF_PCKT:
	case PGM_POLR_PCKT:
	case PGM_ACK_PCKT:
		if (check_col(pinfo->cinfo, COL_INFO)) {
			col_add_fstr(pinfo->cinfo, COL_INFO,
				"%-5s sqn 0x%x gsi %s", pktname, sqn, gsi);
		}
		break;
	case PGM_RDATA_PCKT:
	case PGM_ODATA_PCKT:
		if (check_col(pinfo->cinfo, COL_INFO)) {
			col_add_fstr(pinfo->cinfo, COL_INFO,
			    "%-5s sqn 0x%x gsi %s tsdulen %d", pktname, sqn, gsi,
			    pgmhdr_tsdulen);
		}
		isdata = TRUE;
		break;
	case PGM_POLL_PCKT: {
		guint16 poll_stype = tvb_get_ntohs(tvb, 22);
		pollstname = val_to_str(poll_stype, poll_subtype_vals, "Unknown (0x%02x)");

		if (check_col(pinfo->cinfo, COL_INFO)) {
			col_add_fstr(pinfo->cinfo, COL_INFO,
				"%-5s sqn 0x%x gsi %s subtype %s",
					pktname, sqn, gsi, pollstname);
		}
		}
		break;
	default:
		return;
	}

	{
		proto_tree *pgm_tree = NULL;
		proto_tree *opt_tree = NULL;
		proto_tree *type_tree = NULL;
		proto_item *tf, *hidden_item;
		ptvcursor_t* cursor;

		ti = proto_tree_add_protocol_format(tree, proto_pgm,
			tvb, 0, -1,
			"Pragmatic General Multicast: Type %s"
			    " Src Port %u, Dst Port %u, GSI %s", pktname,
			pgmhdr_sport, pgmhdr_dport, gsi);

		pgm_tree = proto_item_add_subtree(ti, ett_pgm);

		cursor = ptvcursor_new(pgm_tree, tvb, 0);

		hidden_item = proto_tree_add_item(pgm_tree, hf_pgm_port, tvb, 0, 2, ENC_BIG_ENDIAN);
		PROTO_ITEM_SET_HIDDEN(hidden_item);
		hidden_item = proto_tree_add_item(pgm_tree, hf_pgm_port, tvb, 2, 2, ENC_BIG_ENDIAN);
		PROTO_ITEM_SET_HIDDEN(hidden_item);
		ptvcursor_add(cursor, hf_pgm_main_sport, 2, ENC_BIG_ENDIAN);
		ptvcursor_add(cursor, hf_pgm_main_dport, 2, ENC_BIG_ENDIAN);
		ptvcursor_add(cursor, hf_pgm_main_type, 1, ENC_BIG_ENDIAN);

		tf = proto_tree_add_uint_format(pgm_tree, hf_pgm_main_opts, tvb,
			ptvcursor_current_offset(cursor), 1, pgmhdr_opts, "Options: %s (0x%x)",
			optsstr(pgmhdr_opts), pgmhdr_opts);
		opt_tree = proto_item_add_subtree(tf, ett_pgm_optbits);
		ptvcursor_set_tree(cursor, opt_tree);

		ptvcursor_add_no_advance(cursor, hf_pgm_main_opts_opt, 1, ENC_BIG_ENDIAN);
		ptvcursor_add_no_advance(cursor, hf_pgm_main_opts_netsig, 1, ENC_BIG_ENDIAN);
		ptvcursor_add_no_advance(cursor, hf_pgm_main_opts_varlen, 1, ENC_BIG_ENDIAN);
		ptvcursor_add(cursor, hf_pgm_main_opts_parity, 1, ENC_BIG_ENDIAN);
		ptvcursor_set_tree(cursor, pgm_tree);

		/* Checksum may be 0 (not available), but not for DATA packets */
		if ((pgmhdr_type != PGM_RDATA_PCKT) && (pgmhdr_type != PGM_ODATA_PCKT) &&
		    (pgmhdr_cksum == 0))
		{
			proto_tree_add_uint_format(pgm_tree, hf_pgm_main_cksum, tvb,
				ptvcursor_current_offset(cursor), 2, pgmhdr_cksum, "Checksum: not available");
		} else {
			reportedlen = tvb_reported_length(tvb);
			pgmlen = tvb_length(tvb);
			if (pgm_check_checksum && pgmlen >= reportedlen) {
				vec_t cksum_vec[1];
				guint16 computed_cksum;

				cksum_vec[0].ptr = tvb_get_ptr(tvb, 0, pgmlen);
				cksum_vec[0].len = pgmlen;
				computed_cksum = in_cksum(&cksum_vec[0], 1);
				if (computed_cksum == 0) {
					proto_tree_add_uint_format(pgm_tree, hf_pgm_main_cksum, tvb,
						ptvcursor_current_offset(cursor), 2, pgmhdr_cksum, "Checksum: 0x%04x [correct]", pgmhdr_cksum);
				} else {
					hidden_item = proto_tree_add_boolean(pgm_tree, hf_pgm_main_cksum_bad, tvb,
					    ptvcursor_current_offset(cursor), 2, TRUE);
					PROTO_ITEM_SET_HIDDEN(hidden_item);
					proto_tree_add_uint_format(pgm_tree, hf_pgm_main_cksum, tvb,
					    ptvcursor_current_offset(cursor), 2, pgmhdr_cksum, "Checksum: 0x%04x [incorrect, should be 0x%04x]",
						pgmhdr_cksum, in_cksum_shouldbe(pgmhdr_cksum, computed_cksum));
				}
			} else {
				ptvcursor_add_no_advance(cursor, hf_pgm_main_cksum, 2, ENC_BIG_ENDIAN);
			}
		}
		ptvcursor_advance(cursor, 2);

		ptvcursor_add(cursor, hf_pgm_main_gsi, 6, ENC_NA);
		ptvcursor_add(cursor, hf_pgm_main_tsdulen, 2, ENC_BIG_ENDIAN);

		tf = proto_tree_add_text(pgm_tree, tvb, ptvcursor_current_offset(cursor), plen, "%s Packet", pktname);
		switch(pgmhdr_type) {
		case PGM_SPM_PCKT:
			type_tree = proto_item_add_subtree(tf, ett_pgm_spm);
			ptvcursor_set_tree(cursor, type_tree);

			ptvcursor_add(cursor, hf_pgm_spm_sqn, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_spm_trail, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_spm_lead, 4, ENC_BIG_ENDIAN);
			afi = tvb_get_ntohs(tvb, ptvcursor_current_offset(cursor));
			ptvcursor_add(cursor, hf_pgm_spm_pathafi, 2, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_spm_res, 2, ENC_BIG_ENDIAN);

			switch (afi) {
			case AFNUM_INET:
				ptvcursor_add(cursor, hf_pgm_spm_path, 4, ENC_BIG_ENDIAN);
				break;

			case AFNUM_INET6:
				ptvcursor_add(cursor, hf_pgm_spm_path6, 16, ENC_NA);
				break;

			default:
				proto_tree_add_text(type_tree, tvb, ptvcursor_current_offset(cursor), -1,
				    "Can't handle this address format");
				return;
			}
			break;
		case PGM_RDATA_PCKT:
		case PGM_ODATA_PCKT:
			type_tree = proto_item_add_subtree(tf, ett_pgm_data);
			ptvcursor_set_tree(cursor, type_tree);

			ptvcursor_add(cursor, hf_pgm_spm_sqn, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_spm_trail, 4, ENC_BIG_ENDIAN);
			break;
		case PGM_NAK_PCKT:
		case PGM_NNAK_PCKT:
		case PGM_NCF_PCKT:
			type_tree = proto_item_add_subtree(tf, ett_pgm_nak);
			ptvcursor_set_tree(cursor, type_tree);

			ptvcursor_add(cursor, hf_pgm_nak_sqn, 4, ENC_BIG_ENDIAN);
			afi = tvb_get_ntohs(tvb, ptvcursor_current_offset(cursor));
			ptvcursor_add(cursor, hf_pgm_nak_srcafi, 2, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_nak_srcres, 2, ENC_BIG_ENDIAN);

			switch (afi) {
			case AFNUM_INET:
				ptvcursor_add(cursor, hf_pgm_nak_src, 4, ENC_BIG_ENDIAN);
				break;

			case AFNUM_INET6:
				ptvcursor_add(cursor, hf_pgm_nak_src6, 16, ENC_NA);
				break;

			default:
				proto_tree_add_text(type_tree, tvb, ptvcursor_current_offset(cursor), -1,
				    "Can't handle this address format");
				break;
			}

			afi = tvb_get_ntohs(tvb, ptvcursor_current_offset(cursor));
			ptvcursor_add(cursor, hf_pgm_nak_grpafi, 2, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_nak_grpres, 2, ENC_BIG_ENDIAN);

			switch (afi) {
			case AFNUM_INET:
				ptvcursor_add(cursor, hf_pgm_nak_grp, 4, ENC_BIG_ENDIAN);
				break;

			case AFNUM_INET6:
				ptvcursor_add(cursor, hf_pgm_nak_grp6, 16, ENC_NA);
				break;

			default:
				proto_tree_add_text(type_tree, tvb, ptvcursor_current_offset(cursor), -1,
				    "Can't handle this address format");
				return;
			}
			break;
		case PGM_POLL_PCKT:
			type_tree = proto_item_add_subtree(tf, ett_pgm_poll);
			ptvcursor_set_tree(cursor, type_tree);

			ptvcursor_add(cursor, hf_pgm_poll_sqn, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_poll_round, 2, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_poll_subtype, 2, ENC_BIG_ENDIAN);
			afi = tvb_get_ntohs(tvb, ptvcursor_current_offset(cursor));
			ptvcursor_add(cursor, hf_pgm_poll_pathafi, 2, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_poll_res, 2, ENC_BIG_ENDIAN);

			switch (afi) {
			case AFNUM_INET:
				ptvcursor_add(cursor, hf_pgm_poll_path, 4, ENC_BIG_ENDIAN);
				break;

			case AFNUM_INET6:
				ptvcursor_add(cursor, hf_pgm_poll_path6, 16, ENC_NA);
				break;

			default:
				proto_tree_add_text(type_tree, tvb, ptvcursor_current_offset(cursor), -1,
				    "Can't handle this address format");
				break;
			}

			ptvcursor_add(cursor, hf_pgm_poll_backoff_ivl, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_poll_rand_str, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_poll_matching_bmask, 4, ENC_BIG_ENDIAN);
			break;
		case PGM_POLR_PCKT:
			type_tree = proto_item_add_subtree(tf, ett_pgm_polr);
			ptvcursor_set_tree(cursor, type_tree);

			ptvcursor_add(cursor, hf_pgm_polr_sqn, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_polr_round, 2, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_polr_res, 2, ENC_BIG_ENDIAN);
			break;
		case PGM_ACK_PCKT:
			type_tree = proto_item_add_subtree(tf, ett_pgm_ack);
			ptvcursor_set_tree(cursor, type_tree);

			ptvcursor_add(cursor, hf_pgm_ack_sqn, 4, ENC_BIG_ENDIAN);
			ptvcursor_add(cursor, hf_pgm_ack_bitmap, 4, ENC_BIG_ENDIAN);
			break;
		}

		if (pgmhdr_opts & PGM_OPT)
			dissect_pgmopts(cursor, pktname);

		if (isdata)
			decode_pgm_ports(tvb, ptvcursor_current_offset(cursor), pinfo, tree, pgmhdr_sport, pgmhdr_dport);
	}
}
Exemplo n.º 19
0
void dissect_nhrp_hdr(tvbuff_t *tvb,
					  packet_info *pinfo,
					  proto_tree *tree,
					  gint *pOffset,
					  gint *pMandLen,
					  gint *pExtLen,
					  oui_info_t **pOuiInfo,
					  e_nhrp_hdr *hdr)
{
	gint	offset = *pOffset;
	const gchar *pro_type_str;
	guint   total_len = tvb_reported_length(tvb);
	guint16	ipcsum, rx_chksum;

	proto_item *nhrp_tree_item = NULL;
	proto_tree *nhrp_tree = NULL;
	proto_item *shtl_tree_item = NULL;
	proto_tree *shtl_tree = NULL;
	proto_item *sstl_tree_item = NULL;
	proto_tree *sstl_tree = NULL;
	proto_item *ti;

	nhrp_tree_item = proto_tree_add_text(tree, tvb, offset, 20, "NHRP Fixed Header");
	nhrp_tree = proto_item_add_subtree(nhrp_tree_item, ett_nhrp_hdr);

	hdr->ar_pktsz = tvb_get_ntohs(tvb, 10);
	if (total_len > hdr->ar_pktsz) {
		total_len = hdr->ar_pktsz;
	}

	hdr->ar_afn = tvb_get_ntohs(tvb, offset);
	proto_tree_add_item(nhrp_tree, hf_nhrp_hdr_afn, tvb, offset, 2, FALSE);
	offset += 2;

	hdr->ar_pro_type = tvb_get_ntohs(tvb, offset);
	if (hdr->ar_pro_type <= 0xFF) {
		/* It's an NLPID */
		pro_type_str = val_to_str(hdr->ar_pro_type, nlpid_vals,
		    "Unknown NLPID");
	} else if (hdr->ar_pro_type <= 0x3FF) {
		/* Reserved for future use by the IETF */
		pro_type_str = "Reserved for future use by the IETF";
	} else if (hdr->ar_pro_type <= 0x04FF) {
		/* Allocated for use by the ATM Forum */
		pro_type_str = "Allocated for use by the ATM Forum";
	} else if (hdr->ar_pro_type <= 0x05FF) {
		/* Experimental/Local use */
		pro_type_str = "Experimental/Local use";
	} else {
		pro_type_str = val_to_str(hdr->ar_pro_type, etype_vals,
		    "Unknown Ethertype");
	}
	proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_pro_type, tvb, offset, 2,
	    hdr->ar_pro_type, "Protocol Type (short form): %s (0x%04x)",
	    pro_type_str, hdr->ar_pro_type);
	offset += 2;

	if (hdr->ar_pro_type == NLPID_SNAP) {
		/*
		 * The long form protocol type is a SNAP OUI and PID.
		 */
		hdr->ar_pro_type_oui = tvb_get_ntoh24(tvb, offset);
		proto_tree_add_uint(nhrp_tree, hf_nhrp_hdr_pro_snap_oui,
		    tvb, offset, 3, hdr->ar_pro_type_oui);
		offset += 3;

		hdr->ar_pro_type_pid = tvb_get_ntohs(tvb, offset);
		*pOuiInfo = get_snap_oui_info(hdr->ar_pro_type_oui);
		if (*pOuiInfo != NULL) {
			proto_tree_add_uint(nhrp_tree,
			    *(*pOuiInfo)->field_info->p_id,
			    tvb, offset, 2, hdr->ar_pro_type_pid);
		} else {
			proto_tree_add_uint(nhrp_tree, hf_nhrp_hdr_pro_snap_pid,
			    tvb, offset, 2, hdr->ar_pro_type_pid);
		}
	} else {
		/*
		 * XXX - we should check that this is zero, as RFC 2332
		 * says it should be zero.
		 */
		proto_tree_add_text(nhrp_tree, tvb, offset, 5,
						"Protocol Type (long form): %s",
						tvb_bytes_to_str(tvb, offset, 5));
		offset += 5;
	}

	proto_tree_add_item(nhrp_tree, hf_nhrp_hdr_hopcnt, tvb, offset, 1, FALSE);
	offset += 1;

	proto_tree_add_item(nhrp_tree, hf_nhrp_hdr_pktsz, tvb, offset, 2, FALSE);
	offset += 2;

	rx_chksum = tvb_get_ntohs(tvb, offset);
	if (tvb_bytes_exist(tvb, 0, total_len)) {
		ipcsum = nhrp_checksum(tvb_get_ptr(tvb, 0, total_len),
		    total_len);
		if (ipcsum == 0) {
			proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_chksum, tvb, offset, 2, rx_chksum,
			    "NHRP Packet checksum: 0x%04x [correct]", rx_chksum);
		} else {
			proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_chksum, tvb, offset, 2, rx_chksum,
			    "NHRP Packet checksum: 0x%04x [incorrect, should be 0x%04x]", rx_chksum,
			    in_cksum_shouldbe(rx_chksum, ipcsum));
		}
	} else {
		proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_chksum, tvb, offset, 2, rx_chksum,
		    "NHRP Packet checksum: 0x%04x [not all data available]", rx_chksum);
	}
	offset += 2;

	hdr->ar_extoff = tvb_get_ntohs(tvb, offset);
	ti = proto_tree_add_item(nhrp_tree, hf_nhrp_hdr_extoff, tvb, offset, 2, FALSE);
	if (hdr->ar_extoff != 0 && hdr->ar_extoff < 20) {
		expert_add_info_format(pinfo, ti, PI_MALFORMED, PI_ERROR,
		    "Extension offset is less than the fixed header length");
	}
	offset += 2;

	hdr->ar_op_version = tvb_get_guint8(tvb, offset);
	proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_version, tvb, offset, 1,
		hdr->ar_op_version, "Version : %u (%s)", hdr->ar_op_version,
		(hdr->ar_op_version == 1) ? "NHRP - rfc2332" : "Unknown");
	offset += 1;
	proto_tree_add_item(nhrp_tree, hf_nhrp_hdr_op_type, tvb, offset, 1, FALSE);
	offset += 1;

	hdr->ar_shtl = tvb_get_guint8(tvb, offset);
	shtl_tree_item = proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_shtl,
		tvb, offset, 1, hdr->ar_shtl, "Source Address Type/Len: %s/%u",
		val_to_str(NHRP_SHTL_TYPE(hdr->ar_shtl), nhrp_shtl_type_vals, "Unknown Type"),
		NHRP_SHTL_LEN(hdr->ar_shtl));
	shtl_tree = proto_item_add_subtree(shtl_tree_item, ett_nhrp_hdr_shtl);
	proto_tree_add_item(shtl_tree, hf_nhrp_hdr_shtl_type, tvb, offset, 1, FALSE);
	proto_tree_add_item(shtl_tree, hf_nhrp_hdr_shtl_len, tvb, offset, 1, FALSE);
	offset += 1;

	hdr->ar_sstl = tvb_get_guint8(tvb, offset);
	sstl_tree_item = proto_tree_add_uint_format(nhrp_tree, hf_nhrp_hdr_sstl,
		tvb, offset, 1, hdr->ar_sstl, "Source SubAddress Type/Len: %s/%u",
		val_to_str(NHRP_SHTL_TYPE(hdr->ar_sstl), nhrp_shtl_type_vals, "Unknown Type"),
		NHRP_SHTL_LEN(hdr->ar_sstl));
	sstl_tree = proto_item_add_subtree(sstl_tree_item, ett_nhrp_hdr_sstl);
	proto_tree_add_item(sstl_tree, hf_nhrp_hdr_sstl_type, tvb, offset, 1, FALSE);
	proto_tree_add_item(sstl_tree, hf_nhrp_hdr_sstl_len, tvb, offset, 1, FALSE);
	offset += 1;

	*pOffset = offset;
	if (hdr->ar_extoff != 0) {
		if (hdr->ar_extoff >= 20) {
			*pMandLen = hdr->ar_extoff - 20;
			*pExtLen = total_len - hdr->ar_extoff;
		} else {
			/* Error */
			*pMandLen = 0;
			*pExtLen = 0;
		}
	}
	else {
		if (total_len >= 20)
			*pMandLen = total_len - 20;
		else {
			/* "Can't happen" - we would have thrown an exception */
			*pMandLen = 0;
		}
		*pExtLen = 0;
	}
}
Exemplo n.º 20
0
/*
 * XXX - shouldn't there be a centralized routine for dissecting NSAPs?
 * See also "dissect_nsap()" in epan/dissectors/packet-isup.c and
 * "print_nsap_net_buf()" and "print_nsap_net()" in epan/osi=utils.c.
 */
void
dissect_atm_nsap(tvbuff_t *tvb, int offset, int len, proto_tree *tree)
{
  guint8 afi;

  afi = tvb_get_guint8(tvb, offset);
  switch (afi) {

    case 0x39:	/* DCC ATM format */
    case 0xBD:	/* DCC ATM group format */
      proto_tree_add_text(tree, tvb, offset + 0, 3,
                          "Data Country Code%s: 0x%04X",
                          (afi == 0xBD) ? " (group)" : "",
                          tvb_get_ntohs(tvb, offset + 1));
      proto_tree_add_text(tree, tvb, offset + 3, 10,
                          "High Order DSP: %s",
                          tvb_bytes_to_str(tvb, offset + 3, 10));
      proto_tree_add_text(tree, tvb, offset + 13, 6,
                          "End System Identifier: %s",
                          tvb_bytes_to_str(tvb, offset + 13, 6));
      proto_tree_add_text(tree, tvb, offset + 19, 1,
                          "Selector: 0x%02X", tvb_get_guint8(tvb, offset + 19));
      break;

    case 0x47:	/* ICD ATM format */
    case 0xC5:	/* ICD ATM group format */
      proto_tree_add_text(tree, tvb, offset + 0, 3,
                          "International Code Designator%s: 0x%04X",
                          (afi == 0xC5) ? " (group)" : "",
                          tvb_get_ntohs(tvb, offset + 1));
      proto_tree_add_text(tree, tvb, offset + 3, 10,
                          "High Order DSP: %s",
                          tvb_bytes_to_str(tvb, offset + 3, 10));
      proto_tree_add_text(tree, tvb, offset + 13, 6,
                          "End System Identifier: %s",
                          tvb_bytes_to_str(tvb, offset + 13, 6));
      proto_tree_add_text(tree, tvb, offset + 19, 1,
                          "Selector: 0x%02X", tvb_get_guint8(tvb, offset + 19));
      break;

    case 0x45:	/* E.164 ATM format */
    case 0xC3:	/* E.164 ATM group format */
      proto_tree_add_text(tree, tvb, offset + 0, 9,
                          "E.164 ISDN%s: %s",
                          (afi == 0xC3) ? " (group)" : "",
                          tvb_bytes_to_str(tvb, offset + 1, 8));
      proto_tree_add_text(tree, tvb, offset + 9, 4,
                          "High Order DSP: %s",
                          tvb_bytes_to_str(tvb, offset + 3, 10));
      proto_tree_add_text(tree, tvb, offset + 13, 6,
                          "End System Identifier: %s",
                          tvb_bytes_to_str(tvb, offset + 13, 6));
      proto_tree_add_text(tree, tvb, offset + 19, 1,
                          "Selector: 0x%02X", tvb_get_guint8(tvb, offset + 19));
      break;

    default:
      proto_tree_add_text(tree, tvb, offset, 1,
                          "Unknown AFI: 0x%02X", afi);
      proto_tree_add_text(tree, tvb, offset + 1, len - 1,
                          "Rest of address: %s",
                          tvb_bytes_to_str(tvb, offset + 1, len - 1));
      break;
  }
}
Exemplo n.º 21
0
void dissect_cie_list(tvbuff_t *tvb,
					  packet_info *pinfo,
					  proto_tree *tree,
					  gint offset,
					  gint cieEnd,
					  e_nhrp_hdr *hdr,
					  gint isReq,
					  gboolean codeinfo)
{
	proto_item *cli_addr_tree_item = NULL;
	proto_tree *cli_addr_tree = NULL;
	proto_item *cli_saddr_tree_item = NULL;
	proto_tree *cli_saddr_tree = NULL;
	guint8 val;

	while ((offset + 12) <= cieEnd) {
		guint cli_addr_len = tvb_get_guint8(tvb, offset + 8);
		guint cli_saddr_len = tvb_get_guint8(tvb, offset + 9);
		guint cli_prot_len = tvb_get_guint8(tvb, offset + 10);
		guint cie_len = 12 + cli_addr_len + cli_saddr_len + cli_prot_len;
		proto_item *cie_tree_item = proto_tree_add_text(tree, tvb, offset, cie_len, "Client Information Entry");
		proto_tree *cie_tree = proto_item_add_subtree(cie_tree_item, ett_nhrp_cie);

		if (isReq) {
			proto_tree_add_item(cie_tree, hf_nhrp_code, tvb, offset, 1, FALSE);
		}
		else {
			guint8 code = tvb_get_guint8(tvb, offset);
			if ( codeinfo ) {
				col_append_fstr(pinfo->cinfo, COL_INFO, ", Code=%s",
					val_to_str(code, nhrp_cie_code_vals, "Unknown (%u)"));
			}
			proto_tree_add_text(cie_tree, tvb, offset, 1, "Code: %s",
								val_to_str(code, nhrp_cie_code_vals, "Unknown (%u)"));
		}
		offset += 1;

		proto_tree_add_item(cie_tree, hf_nhrp_prefix_len, tvb, offset, 1, FALSE);
		offset += 1;

		proto_tree_add_item(cie_tree, hf_nhrp_unused, tvb, offset, 2, FALSE);
		offset += 2;

		proto_tree_add_item(cie_tree, hf_nhrp_mtu, tvb, offset, 2, FALSE);
		offset += 2;

		proto_tree_add_item(cie_tree, hf_nhrp_holding_time, tvb, offset, 2, FALSE);
		offset += 2;

		val = tvb_get_guint8(tvb, offset);
		cli_addr_tree_item = proto_tree_add_uint_format(cie_tree,
			hf_nhrp_cli_addr_tl, tvb, offset, 1, val,
			"Client Address Type/Len: %s/%u",
			val_to_str(NHRP_SHTL_TYPE(val), nhrp_shtl_type_vals, "Unknown Type"),
			NHRP_SHTL_LEN(val));
		cli_addr_tree = proto_item_add_subtree(cli_addr_tree_item, ett_nhrp_cie_cli_addr_tl);
		proto_tree_add_item(cli_addr_tree, hf_nhrp_cli_addr_tl_type, tvb, offset, 1, FALSE);
		proto_tree_add_item(cli_addr_tree, hf_nhrp_cli_addr_tl_len, tvb, offset, 1, FALSE);
		offset += 1;

		val = tvb_get_guint8(tvb, offset);
		cli_saddr_tree_item = proto_tree_add_uint_format(cie_tree,
			hf_nhrp_cli_saddr_tl, tvb, offset, 1, val,
			"Client Sub Address Type/Len: %s/%u",
			val_to_str(NHRP_SHTL_TYPE(val), nhrp_shtl_type_vals, "Unknown Type"),
			NHRP_SHTL_LEN(val));
		cli_saddr_tree = proto_item_add_subtree(cli_saddr_tree_item, ett_nhrp_cie_cli_saddr_tl);
		proto_tree_add_item(cli_saddr_tree, hf_nhrp_cli_saddr_tl_type, tvb, offset, 1, FALSE);
		proto_tree_add_item(cli_saddr_tree, hf_nhrp_cli_saddr_tl_len, tvb, offset, 1, FALSE);
		offset += 1;

		proto_tree_add_item(cie_tree, hf_nhrp_cli_prot_len, tvb, offset, 1, FALSE);
		offset += 1;

		proto_tree_add_item(cie_tree, hf_nhrp_pref, tvb, offset, 1, FALSE);
		offset += 1;

		if (cli_addr_len) {
			switch (hdr->ar_afn) {

			case AFNUM_INET:
				if (cli_addr_len == 4)
					proto_tree_add_item(cie_tree, hf_nhrp_client_nbma_addr, tvb, offset, 4, FALSE);
				else {
					proto_tree_add_text(cie_tree, tvb, offset, cli_addr_len,
					    "Client NBMA Address: %s",
					    tvb_bytes_to_str(tvb, offset, cli_addr_len));
				}
				break;

			default:
				proto_tree_add_text(cie_tree, tvb, offset, cli_addr_len,
				    "Client NBMA Address: %s",
				    tvb_bytes_to_str(tvb, offset, cli_addr_len));
				break;
			}
			offset += cli_addr_len;
		}

		if (cli_saddr_len) {
			proto_tree_add_text(cie_tree, tvb, offset, cli_saddr_len,
								"Client NBMA Sub Address: %s",
								tvb_bytes_to_str(tvb, offset, cli_saddr_len));
		}

		if (cli_prot_len) {
			if (cli_prot_len == 4)
				proto_tree_add_ipv4(cie_tree, hf_nhrp_client_prot_addr, tvb, offset, 4, FALSE);
			else {
				proto_tree_add_text(cie_tree, tvb, offset, cli_prot_len,
									"Client Protocol Address: %s",
									tvb_bytes_to_str(tvb, offset, cli_prot_len));
			}
			offset += cli_prot_len;
		}
	}
}
Exemplo n.º 22
0
void dissect_nhrp_mand(tvbuff_t *tvb,
					   packet_info *pinfo,
					   proto_tree *tree,
					   gint *pOffset,
					   gint mandLen,
					   oui_info_t *oui_info,
					   e_nhrp_hdr *hdr,
					   guint *srcLen,
					   gboolean codeinfo)
{
	gint	offset = *pOffset;
	gint	mandEnd = offset + mandLen;
	guint8	ssl, shl;
	guint16	flags;
	guint	dstLen;
	gboolean isReq = 0;
	gboolean isErr = 0;
	gboolean isInd = 0;

	proto_item *nhrp_tree_item = NULL;
	proto_item *flag_item = NULL;
	proto_tree *nhrp_tree = NULL;
	proto_tree *flag_tree = NULL;

	tvb_ensure_bytes_exist(tvb, offset, mandLen);

	switch (hdr->ar_op_type)
	{
	case NHRP_RESOLUTION_REPLY:
	case NHRP_REGISTRATION_REPLY:
	case NHRP_PURGE_REPLY:
		break;
	case NHRP_RESOLUTION_REQ:
	case NHRP_REGISTRATION_REQ:
	case NHRP_PURGE_REQ:
		isReq = 1;
		break;
	case NHRP_ERROR_INDICATION:	/* This needs special treatment */
		isErr = 1;
		isInd = 1;
		break;
	case NHRP_TRAFFIC_INDICATION:
		isInd = 1;
		break;
	}
	nhrp_tree_item = proto_tree_add_text(tree, tvb, offset, mandLen, "NHRP Mandatory Part");
	nhrp_tree = proto_item_add_subtree(nhrp_tree_item, ett_nhrp_mand);

	*srcLen = tvb_get_guint8(tvb, offset);
	proto_tree_add_item(nhrp_tree, hf_nhrp_src_proto_len, tvb, offset, 1, FALSE);
	offset += 1;

	dstLen = tvb_get_guint8(tvb, offset);
	proto_tree_add_item(nhrp_tree, hf_nhrp_dst_proto_len, tvb, offset, 1, FALSE);
	offset += 1;

	if (!isInd) {
		flags = tvb_get_ntohs(tvb, offset);
		flag_item = proto_tree_add_uint(nhrp_tree, hf_nhrp_flags, tvb, offset, 2, flags);
		flag_tree = proto_item_add_subtree(flag_item, ett_nhrp_mand_flag);

		switch (hdr->ar_op_type)
		{
		case NHRP_RESOLUTION_REQ:
		case NHRP_RESOLUTION_REPLY:
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_Q, tvb, offset, 2, flags);
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_A, tvb, offset, 2, flags);
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_D, tvb, offset, 2, flags);
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_U1, tvb, offset, 2, flags);
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_S, tvb, offset, 2, flags);
			break;
		case NHRP_REGISTRATION_REQ:
		case NHRP_REGISTRATION_REPLY:
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_U2, tvb, offset, 2, flags);
			break;

		case NHRP_PURGE_REQ:
		case NHRP_PURGE_REPLY:
			proto_tree_add_boolean(flag_tree, hf_nhrp_flag_N, tvb, offset, 2, flags);
			break;
		}
		proto_tree_add_boolean(flag_tree, hf_nhrp_flag_NAT, tvb, offset, 2, flags);

		offset += 2;

		col_append_fstr(pinfo->cinfo, COL_INFO, ", ID=%u", tvb_get_ntohl(tvb, offset));
		proto_tree_add_item(nhrp_tree, hf_nhrp_request_id, tvb, offset, 4, FALSE);
		offset += 4;
	}
	else if (isErr) {
		offset += 2;

		col_append_fstr(pinfo->cinfo, COL_INFO, ", %s",
			val_to_str(tvb_get_ntohs(tvb, offset), nhrp_error_code_vals, "Unknown Error (%u)"));
		proto_tree_add_item(nhrp_tree, hf_nhrp_error_code, tvb, offset, 2, FALSE);
		offset += 2;

		proto_tree_add_item(nhrp_tree, hf_nhrp_error_offset, tvb, offset, 2, FALSE);
		offset += 2;
	}
	else {
		offset += 6;
	}

	shl = NHRP_SHTL_LEN(hdr->ar_shtl);
	if (shl) {
		switch (hdr->ar_afn) {

		case AFNUM_INET:
			if (shl == 4)
				proto_tree_add_item(nhrp_tree, hf_nhrp_src_nbma_addr, tvb, offset, 4, FALSE);
			else {
				proto_tree_add_text(nhrp_tree, tvb, offset, shl,
				    "Source NBMA Address: %s",
				    tvb_bytes_to_str(tvb, offset, shl));
			}
			break;

		default:
			proto_tree_add_text(nhrp_tree, tvb, offset, shl,
			    "Source NBMA Address: %s",
			    tvb_bytes_to_str(tvb, offset, shl));
			break;
		}
		offset += shl;
	}

	ssl = NHRP_SHTL_LEN(hdr->ar_sstl);
	if (ssl) {
		proto_tree_add_text(nhrp_tree, tvb, offset, ssl,
							"Source NBMA Sub Address: %s",
							tvb_bytes_to_str(tvb, offset, ssl));
		offset += ssl;
	}

	if (*srcLen == 4) {
		proto_tree_add_item(nhrp_tree, hf_nhrp_src_prot_addr, tvb, offset, 4, FALSE);
		offset += 4;
	}
	else if (*srcLen) {
		proto_tree_add_text(nhrp_tree, tvb, offset, *srcLen,
							"Source Protocol Address: %s",
							tvb_bytes_to_str(tvb, offset, *srcLen));
		offset += *srcLen;
	}

	if (dstLen == 4) {
		proto_tree_add_item(nhrp_tree, hf_nhrp_dst_prot_addr, tvb, offset, 4, FALSE);
		offset += 4;
	}
	else if (dstLen) {
		proto_tree_add_text(nhrp_tree, tvb, offset, dstLen,
							"Destination Protocol Address: %s",
							tvb_bytes_to_str(tvb, offset, dstLen));
		offset += dstLen;
	}

	if (isInd) {
		gboolean save_in_error_pkt;
		gint pkt_len = mandEnd - offset;
		proto_item *ind_tree_item = proto_tree_add_text(tree, tvb, offset, pkt_len, "Packet Causing Indication");
		proto_tree *ind_tree = proto_item_add_subtree(ind_tree_item, ett_nhrp_indication);
		gboolean dissected;
		tvbuff_t *sub_tvb;

		save_in_error_pkt = pinfo->in_error_pkt;
		pinfo->in_error_pkt = TRUE;
		sub_tvb = tvb_new_subset_remaining(tvb, offset);
		if (isErr) {
			_dissect_nhrp(sub_tvb, pinfo, ind_tree, TRUE, FALSE);
		}
		else {
			if (hdr->ar_pro_type <= 0xFF) {
				/* It's an NLPID */
				if (hdr->ar_pro_type == NLPID_SNAP) {
					/*
					 * Dissect based on the SNAP OUI
					 * and PID.
					 */
					if (hdr->ar_pro_type_oui == 0x000000) {
						/*
						 * "Should not happen", as
						 * the protocol type should
						 * be the Ethertype, but....
						 */
						dissected = dissector_try_port(
						    ethertype_subdissector_table,
						    hdr->ar_pro_type_pid,
						    sub_tvb, pinfo, ind_tree);
					} else {
						/*
						 * If we have a dissector
						 * table, use it, otherwise
						 * just dissect as data.
						 */
						if (oui_info != NULL) {
							dissected = dissector_try_port(
							    oui_info->table,
							    hdr->ar_pro_type_pid,
							    sub_tvb, pinfo,
							    ind_tree);
						} else
							dissected = FALSE;
					}
				} else {
					/*
					 * Dissect based on the NLPID.
					 */
					dissected = dissector_try_port(
					    osinl_subdissector_table,
					    hdr->ar_pro_type, sub_tvb, pinfo,
					    ind_tree) ||
					            dissector_try_port(
					    osinl_excl_subdissector_table,
					    hdr->ar_pro_type, sub_tvb, pinfo,
					    ind_tree);
				}
			} else if (hdr->ar_pro_type <= 0x3FF) {
				/* Reserved for future use by the IETF */
				dissected = FALSE;
			} else if (hdr->ar_pro_type <= 0x04FF) {
				/* Allocated for use by the ATM Forum */
				dissected = FALSE;
			} else if (hdr->ar_pro_type <= 0x05FF) {
				/* Experimental/Local use */
				dissected = FALSE;
			} else {
				dissected = dissector_try_port(
				    ethertype_subdissector_table,
				    hdr->ar_pro_type, sub_tvb, pinfo, ind_tree);
			}
			if (!dissected) {
				call_dissector(data_handle, sub_tvb, pinfo,
				    ind_tree);
			}
		}
		pinfo->in_error_pkt = save_in_error_pkt;
		offset = mandEnd;
	}

	/* According to RFC 2332, section 5.2.7, there shouldn't be any extensions
	 * in the Error Indication packet. */
	if (isErr && tvb_reported_length_remaining(tvb, offset)) {
		expert_add_info_format(pinfo, tree, PI_MALFORMED, PI_ERROR,
			"Extensions not allowed per RFC2332 section 5.2.7");
	}

	dissect_cie_list(tvb, pinfo, nhrp_tree, offset, mandEnd, hdr, isReq, codeinfo);

	*pOffset = mandEnd;
}
Exemplo n.º 23
0
static void
dissect_bacnet(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
	proto_item *ti;
	proto_item *ct;
	proto_tree *bacnet_tree;
	proto_tree *control_tree;

	gint offset;
	guint8 bacnet_version;
	guint8 bacnet_control;
	guint8 bacnet_dlen;
	guint8 bacnet_slen;
	guint8 bacnet_mesgtyp;
	guint8 bacnet_rejectreason;
	guint8 bacnet_rportnum;
	guint8 bacnet_pinfolen;
	guint8 i;
	tvbuff_t *next_tvb;
	guint32 vendor_id;

	col_set_str(pinfo->cinfo, COL_PROTOCOL, "BACnet-NPDU");

	col_set_str(pinfo->cinfo, COL_INFO, "Building Automation and Control Network NPDU");

	offset = 0;
	bacnet_version = tvb_get_guint8(tvb, offset);
	bacnet_control = tvb_get_guint8(tvb, offset+1);

	/* I don't know the length of the NPDU yet; Setting the length after dissection */
	ti = proto_tree_add_item(tree, proto_bacnet, tvb, 0, -1, ENC_NA);

	bacnet_tree = proto_item_add_subtree(ti, ett_bacnet);

	proto_tree_add_uint_format_value(bacnet_tree, hf_bacnet_version, tvb,
					 offset, 1,
					 bacnet_version,"0x%02x (%s)",bacnet_version,
					 (bacnet_version == 0x01)?"ASHRAE 135-1995":"unknown");
	offset ++;
	ct = proto_tree_add_uint(bacnet_tree, hf_bacnet_control,
		tvb, offset, 1, bacnet_control);
	control_tree = proto_item_add_subtree(ct, ett_bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_net,
		tvb, offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_res1, tvb,
		offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_dest, tvb,
		offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_res2, tvb,
		offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_src, tvb,
		offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_expect, tvb,
		offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_prio_high,
		tvb, offset, 1, bacnet_control);
	proto_tree_add_boolean(control_tree, hf_bacnet_control_prio_low,
		tvb, offset, 1, bacnet_control);
	offset ++;
	if (bacnet_control & BAC_CONTROL_DEST) { /* DNET, DLEN, DADR */
		proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
			tvb, offset, 2, ENC_BIG_ENDIAN);
		offset += 2;
		bacnet_dlen = tvb_get_guint8(tvb, offset);
		/* DLEN = 0 is broadcast on dest.network */
		if( bacnet_dlen == 0) {
			/* append to hf_bacnet_dlen: broadcast */
			proto_tree_add_uint_format_value(bacnet_tree,
			    hf_bacnet_dlen, tvb, offset, 1, bacnet_dlen,
			    "%d indicates Broadcast on Destination Network",
			    bacnet_dlen);
			offset ++;
			/* going to SNET */
		} else if (bacnet_dlen==6) {
			proto_tree_add_uint(bacnet_tree, hf_bacnet_dlen,
				tvb, offset, 1, bacnet_dlen);
			offset ++;
			/* Ethernet MAC */
			proto_tree_add_item(bacnet_tree,
				hf_bacnet_dadr_eth, tvb, offset,
				bacnet_dlen, ENC_NA);
			offset += bacnet_dlen;
		} else if (bacnet_dlen==1) {
			proto_tree_add_uint(bacnet_tree, hf_bacnet_dlen,
				tvb, offset, 1, bacnet_dlen);
			offset ++;
			/* MS/TP or ARCNET MAC */
			proto_tree_add_item(bacnet_tree,
				hf_bacnet_dadr_mstp, tvb, offset,
				bacnet_dlen, ENC_BIG_ENDIAN);
			offset += bacnet_dlen;
		} else if (bacnet_dlen<7) {
			proto_tree_add_uint(bacnet_tree, hf_bacnet_dlen,
				tvb, offset, 1, bacnet_dlen);
			offset ++;
			/* Other MAC formats should be included here */
			proto_tree_add_item(bacnet_tree,
				hf_bacnet_dadr_tmp, tvb, offset,
				bacnet_dlen, ENC_NA);
			offset += bacnet_dlen;
		} else {
			proto_tree_add_uint_format_value(bacnet_tree,
			    hf_bacnet_dlen, tvb, offset, 1, bacnet_dlen,
			    "%d invalid!",
			    bacnet_dlen);
		}
	}
	if (bacnet_control & BAC_CONTROL_SRC) { /* SNET, SLEN, SADR */
		/* SNET */
		proto_tree_add_uint(bacnet_tree, hf_bacnet_snet,
			tvb, offset, 2, tvb_get_ntohs(tvb, offset));
		offset += 2;
		bacnet_slen = tvb_get_guint8(tvb, offset);
		if( bacnet_slen == 0) { /* SLEN = 0 invalid */
			proto_tree_add_uint_format_value(bacnet_tree,
			    hf_bacnet_slen, tvb, offset, 1, bacnet_slen,
			    "%d invalid!",
			    bacnet_slen);
			offset ++;
		} else if (bacnet_slen==6) {
			/* SLEN */
			 proto_tree_add_uint(bacnet_tree, hf_bacnet_slen,
				tvb, offset, 1, bacnet_slen);
			offset ++;
			/* Ethernet MAC */
			proto_tree_add_item(bacnet_tree,
				hf_bacnet_sadr_eth, tvb, offset,
				bacnet_slen, ENC_NA);
			offset += bacnet_slen;
		} else if (bacnet_slen==1) {
			/* SLEN */
			 proto_tree_add_uint(bacnet_tree, hf_bacnet_slen,
				tvb, offset, 1, bacnet_slen);
			offset ++;
			/* MS/TP or ARCNET MAC */
			proto_tree_add_item(bacnet_tree,
				hf_bacnet_sadr_mstp, tvb, offset,
				bacnet_slen, ENC_BIG_ENDIAN);
			offset += bacnet_slen;
		} else if (bacnet_slen<6) { /* LON MAC */
			/* SLEN */
			 proto_tree_add_uint(bacnet_tree, hf_bacnet_slen,
				tvb, offset, 1, bacnet_slen);
			offset ++;
			/* Other MAC formats should be included here */
			proto_tree_add_item(bacnet_tree,
				hf_bacnet_sadr_tmp, tvb, offset,
				bacnet_slen, ENC_NA);
			offset += bacnet_slen;
		} else {
			proto_tree_add_uint_format_value(bacnet_tree,
			hf_bacnet_slen, tvb, offset, 1, bacnet_slen,
			    "%d invalid!",
			    bacnet_slen);
			offset ++;
		}
	}
	if (bacnet_control & BAC_CONTROL_DEST) { /* Hopcount */
		proto_tree_add_item(bacnet_tree, hf_bacnet_hopc,
			tvb, offset, 1, ENC_BIG_ENDIAN);
		offset ++;
	}
	/* Network Layer Message Type */
	if (bacnet_control & BAC_CONTROL_NET) {
		bacnet_mesgtyp =  tvb_get_guint8(tvb, offset);
		proto_tree_add_uint_format_value(bacnet_tree,
		hf_bacnet_mesgtyp, tvb, offset, 1, bacnet_mesgtyp,
			"%02x (%s)", bacnet_mesgtyp,
			bacnet_mesgtyp_name(bacnet_mesgtyp));
		/* Put the NPDU Type in the info column */
		col_add_str(pinfo->cinfo, COL_INFO,
			    bacnet_mesgtyp_name(bacnet_mesgtyp));
		offset ++;
		/* Vendor ID
		* The standard says: "If Bit 7 of the control octet is 1 and
		* the Message Type field contains a value in the range
		* X'80' - X'FF', then a Vendor ID field shall be present (...)."
		* We should not go any further in dissecting the packet if it's
		* not present, but we don't know about that: No length field...
		*/
		if (bacnet_mesgtyp > 0x7f) {
			/* Note: our next_tvb includes message type and vendor id! */
			next_tvb = tvb_new_subset_remaining(tvb, offset-1);
			vendor_id = tvb_get_ntohs(tvb, offset);
			proto_tree_add_uint(bacnet_tree, hf_bacnet_vendor, tvb,
					offset, 2, vendor_id);
			offset += 2;	/* vendor_id */
			if (dissector_try_uint(bacnet_dissector_table,
					vendor_id, next_tvb, pinfo, bacnet_tree)) {
					/* we parsed it so skip over length and we are done */
					/* Note: offset has now been bumped for message type and vendor id so we take that out of our next_tvb size */
					offset += tvb_length(next_tvb) -3;
			}
		}
		/* Performance Index (in I-Could-Be-Router-To-Network) */
		if (bacnet_mesgtyp == BAC_NET_ICB_R) {
			proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
				tvb, offset, 2, ENC_BIG_ENDIAN);
			offset += 2;
			proto_tree_add_item(bacnet_tree, hf_bacnet_perf,
				tvb, offset, 1, ENC_BIG_ENDIAN);
			offset ++;
		}
		/* Reason, DNET (in Reject-Message-To-Network) */
		if (bacnet_mesgtyp == BAC_NET_REJ) {
			bacnet_rejectreason = tvb_get_guint8(tvb, offset);
			proto_tree_add_uint_format_value(bacnet_tree,
				hf_bacnet_rejectreason,
				tvb, offset, 1,
				bacnet_rejectreason, "%d (%s)",
				bacnet_rejectreason,
				bacnet_rejectreason_name(bacnet_rejectreason));
			offset ++;
			proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
				tvb, offset, 2, ENC_BIG_ENDIAN);
			offset += 2;
		}
		/* N*DNET (in Router-Busy-To-Network,Router-Available-To-Network) */
		if ((bacnet_mesgtyp == BAC_NET_R_BUSY) ||
			(bacnet_mesgtyp == BAC_NET_WHO_R) ||
			(bacnet_mesgtyp == BAC_NET_R_AVA) ||
			(bacnet_mesgtyp == BAC_NET_IAM_R) ) {
			while(tvb_reported_length_remaining(tvb, offset) > 1 ) {
				proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
					tvb, offset, 2, ENC_BIG_ENDIAN);
				offset += 2;
			}
		}
		/* Initialize-Routing-Table */
		if ( (bacnet_mesgtyp == BAC_NET_INIT_RTAB) ||
			(bacnet_mesgtyp == BAC_NET_INIT_RTAB_ACK) ) {
			bacnet_rportnum = tvb_get_guint8(tvb, offset);
			/* number of ports */
			proto_tree_add_uint(bacnet_tree, hf_bacnet_rportnum,
				tvb, offset, 1, bacnet_rportnum);
			offset ++;
			for(i=0; i<bacnet_rportnum; i++) {
					/* Connected DNET */
					proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
					tvb, offset, 2, ENC_BIG_ENDIAN);
					offset += 2;
					/* Port ID */
					proto_tree_add_item(bacnet_tree, hf_bacnet_portid,
					tvb, offset, 1, ENC_BIG_ENDIAN);
					offset ++;
					/* Port Info Length */
					bacnet_pinfolen = tvb_get_guint8(tvb, offset);
					proto_tree_add_uint(bacnet_tree, hf_bacnet_pinfolen,
					tvb, offset, 1, bacnet_pinfolen);
					offset ++;
					proto_tree_add_text(bacnet_tree, tvb, offset,
					bacnet_pinfolen, "Port Info: %s",
					tvb_bytes_to_str(tvb, offset, bacnet_pinfolen));
					offset += bacnet_pinfolen;
			}
		}
		/* Establish-Connection-To-Network */
		if (bacnet_mesgtyp == BAC_NET_EST_CON) {
			proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
				tvb, offset, 2, ENC_BIG_ENDIAN);
			offset += 2;
			proto_tree_add_item(bacnet_tree, hf_bacnet_term_time_value,
				tvb, offset, 1, ENC_BIG_ENDIAN);
			offset ++;
		}
		/* Disconnect-Connection-To-Network */
		if (bacnet_mesgtyp == BAC_NET_DISC_CON) {
			proto_tree_add_item(bacnet_tree, hf_bacnet_dnet,
				tvb, offset, 2, ENC_BIG_ENDIAN);
			offset += 2;
		}
	}
	/* Now set NPDU length */
	proto_item_set_len(ti, offset);

	/* dissect BACnet APDU */
	next_tvb = tvb_new_subset_remaining(tvb,offset);
	if (bacnet_control & BAC_CONTROL_NET) {
		/* Unknown function - dissect the payload as data */
		call_dissector(data_handle, next_tvb, pinfo, tree);
	} else {
		/* APDU - call the APDU dissector */
		call_dissector(bacapp_handle, next_tvb, pinfo, tree);
	}
}
Exemplo n.º 24
0
void dissect_nhrp_ext(tvbuff_t *tvb,
					  packet_info *pinfo,
					  proto_tree *tree,
					  gint *pOffset,
					  gint extLen,
					  e_nhrp_hdr *hdr,
					  guint srcLen,
					  gboolean nested)
{
	gint	offset = *pOffset;
	gint	extEnd = offset + extLen;

	proto_item *nhrp_tree_item = NULL;
	proto_tree *nhrp_tree = NULL;
	proto_item *ti = NULL;

	tvb_ensure_bytes_exist(tvb, offset, extLen);

	while ((offset + 4) <= extEnd)
	{
		gint extTypeC = tvb_get_ntohs(tvb, offset);
		gint extType = extTypeC & 0x3FFF;
		guint len  = tvb_get_ntohs(tvb, offset+2);

		if ((extType == NHRP_EXT_NAT_ADDRESS) && (len == 8)) {
			/* Assume it's not really a Cisco NAT extension, but a device
			 * capabilities extension instead (see RFC 2735). */
			nhrp_tree_item =  proto_tree_add_text(tree, tvb, offset,
				len + 4, "Device Capabilities Extension");
		}
		else {
			nhrp_tree_item =  proto_tree_add_text(tree, tvb, offset,
				len + 4, "%s",
				val_to_str(extType, ext_type_vals, "Unknown (%u)"));
		}
		nhrp_tree = proto_item_add_subtree(nhrp_tree_item, ett_nhrp_ext);
		proto_tree_add_boolean(nhrp_tree, hf_nhrp_ext_C, tvb, offset, 2, extTypeC);
		proto_tree_add_item(nhrp_tree, hf_nhrp_ext_type, tvb, offset, 2, FALSE);
		offset += 2;

		proto_tree_add_item(nhrp_tree, hf_nhrp_ext_len, tvb, offset, 2, FALSE);
		offset += 2;

		if (len && (extType != NHRP_EXT_NULL)) {
			tvb_ensure_bytes_exist(tvb, offset, len);
			if ((extType == NHRP_EXT_NAT_ADDRESS) && (len == 8)) {
				/* Assume it's not really a Cisco NAT extension, but a device
				 * capabilities extension instead (see RFC 2735). */
				proto_item *devcap_item;
				proto_tree *devcap_tree;
				proto_item *cap_item;
				proto_tree *cap_tree;

				devcap_item = proto_tree_add_text(nhrp_tree, tvb, offset, len,
					"Extension Data: Src is %sVPN-aware; Dst is %sVPN-aware",
					tvb_get_ntohl(tvb, offset) & 1 ? "" : "non-",
					tvb_get_ntohl(tvb, offset + 4) & 1 ? "" : "non-");
				devcap_tree = proto_item_add_subtree(devcap_item, ett_nhrp_devcap_ext);
				cap_item = proto_tree_add_item(devcap_tree, hf_nhrp_devcap_ext_srccap, tvb, offset, 4, FALSE);
				cap_tree = proto_item_add_subtree(cap_item, ett_nhrp_devcap_ext_srccap);
				proto_tree_add_item(cap_tree, hf_nhrp_devcap_ext_srccap_V, tvb, offset, 4, FALSE);

				cap_item = proto_tree_add_item(devcap_tree, hf_nhrp_devcap_ext_dstcap, tvb, offset + 4, 4, FALSE);
				cap_tree = proto_item_add_subtree(cap_item, ett_nhrp_devcap_ext_dstcap);
				proto_tree_add_item(cap_tree, hf_nhrp_devcap_ext_dstcap_V, tvb, offset + 4, 4, FALSE);
				goto skip_switch;
			}

			switch (extType) {
			case NHRP_EXT_RESP_ADDR:
			case NHRP_EXT_FWD_RECORD:
			case NHRP_EXT_REV_RECORD:
			case NHRP_EXT_NAT_ADDRESS:
				dissect_cie_list(tvb, pinfo, nhrp_tree,
				    offset, offset + len, hdr, 0, FALSE);
				break;

			case NHRP_EXT_AUTH:
			case NHRP_EXT_MOBILE_AUTH:
				if (len < (4 + srcLen)) {
					ti = proto_tree_add_text(nhrp_tree, tvb, offset, len,
						"Malformed Extension: %s",
						tvb_bytes_to_str(tvb, offset, len));
					expert_add_info_format(pinfo, ti, PI_MALFORMED, PI_ERROR,
						"Incomplete Authentication Extension");
				}
				else {
					proto_item *auth_item;
					proto_tree *auth_tree;

					auth_item = proto_tree_add_text(nhrp_tree, tvb, offset, len,
						"Extension Data: SPI=%u: Data=%s", tvb_get_ntohs(tvb, offset + 2),
						tvb_bytes_to_str(tvb, offset + 4, len - 4));
					auth_tree = proto_item_add_subtree(auth_item, ett_nhrp_auth_ext);
					proto_tree_add_item(auth_tree, hf_nhrp_auth_ext_reserved, tvb, offset, 2, FALSE);
					proto_tree_add_item(auth_tree, hf_nhrp_auth_ext_spi, tvb, offset + 2, 2, FALSE);
					if (srcLen == 4)
						proto_tree_add_item(auth_tree, hf_nhrp_auth_ext_src_addr, tvb, offset + 4, 4, FALSE);
					else if (srcLen) {
						proto_tree_add_text(auth_tree, tvb, offset + 4, srcLen,
							"Source Address: %s",
							tvb_bytes_to_str(tvb, offset + 4, srcLen));
					}
					if (len > (4 + srcLen)) {
						proto_tree_add_text(auth_tree, tvb, offset + 4 + srcLen, len - (4 + srcLen),
							"Data: %s", tvb_bytes_to_str(tvb, offset + 4 + srcLen, len - (4 + srcLen)));
					}
				}
				break;

			case NHRP_EXT_VENDOR_PRIV:
				if (len < 3) {
					ti = proto_tree_add_text(nhrp_tree, tvb, offset, len,
						"Malformed Extension: %s",
						tvb_bytes_to_str(tvb, offset, len));
					expert_add_info_format(pinfo, ti, PI_MALFORMED, PI_ERROR,
						"Incomplete Vendor-Private Extension");
				}
				else {
					proto_item *vendor_item;
					proto_tree *vendor_tree;
					gchar manuf[3];

					tvb_memcpy(tvb, manuf, offset, 3);
					vendor_item = proto_tree_add_text(nhrp_tree, tvb, offset, len,
						"Extension Data: Vendor ID=%s, Data=%s", get_manuf_name(manuf),
						tvb_bytes_to_str(tvb, offset + 3, len - 3));
					vendor_tree = proto_item_add_subtree(vendor_item, ett_nhrp_vendor_ext);
					proto_tree_add_bytes_format(vendor_tree, hf_nhrp_vendor_ext_id, tvb,
						offset, 3, manuf, "Vendor ID: %s", get_manuf_name(manuf));
					if (len > 3) {
						proto_tree_add_text(vendor_tree, tvb, offset + 3, len - 3,
							"Data: %s", tvb_bytes_to_str(tvb, offset + 3, len - 3));
					}
				}
				break;

			default:
				proto_tree_add_text(nhrp_tree, tvb, offset, len,
					"Extension Value: %s",
					tvb_bytes_to_str(tvb, offset, len));
				break;
			}
skip_switch:
			offset += len;
		}

		if (!nested) {
			len = tvb_reported_length_remaining(tvb, offset);
			if ((extType == NHRP_EXT_NULL) && len) {
				ti = proto_tree_add_text(tree, tvb, offset, len,
					"Unknown Data (%d bytes)", len);
				expert_add_info_format(pinfo, ti, PI_MALFORMED, PI_ERROR,
					"Superfluous data follows End Extension");
				break;
			}
		}
	}

	*pOffset = extEnd;
}
Exemplo n.º 25
0
static void
dissect_dlsw_capex(tvbuff_t *tvb, proto_tree *tree, proto_tree *ti2)
{
  int mlen,vlen,vtype,offset=4,gdsid,sap,i=0;
  proto_tree *ti,*dlsw_vector_tree;
  mlen=tvb_get_ntohs(tvb,0);
  gdsid=tvb_get_ntohs(tvb,2);
  proto_tree_add_text (tree,tvb,0,2,"Capabilities Length =  %d",mlen) ;
  proto_tree_add_text (tree,tvb,2,2,"%s",val_to_str_const( gdsid, dlsw_gds_vals, "Invalid GDS ID"));
  proto_item_append_text(ti2," - %s",val_to_str_const( gdsid, dlsw_gds_vals, "Invalid GDS ID"));
  switch (gdsid) {
    case DLSW_GDSID_ACK:
      break;
    case DLSW_GDSID_REF:
      proto_tree_add_text (tree,tvb,4,2,"Error pointer =  %d",tvb_get_ntohs(tvb,4));
      proto_tree_add_text (tree,tvb,6,2,"Error cause = %s",
                           val_to_str_const(tvb_get_ntohs(tvb,6), dlsw_refuse_vals, "Unknown refuse cause"));
      break;
    case DLSW_GDSID_SEND:
      while (offset < mlen){
        vlen=tvb_get_guint8(tvb,offset);
        if (vlen < 3) THROW(ReportedBoundsError);
        vtype=tvb_get_guint8(tvb,offset+1);
        ti=proto_tree_add_text (tree,tvb,offset,vlen,"%s",
                                val_to_str_const(vtype,dlsw_vector_vals,"Unknown vector type"));
        dlsw_vector_tree = proto_item_add_subtree(ti, ett_dlsw_vector);
        proto_tree_add_text (dlsw_vector_tree,tvb,offset,1,  "Vector Length = %d",vlen);
        proto_tree_add_text (dlsw_vector_tree,tvb,offset+1,1,"Vector Type   = %s (0x%02x)",
                             val_to_str_const(vtype,dlsw_vector_vals,"Unknown vector type"), vtype);
        switch (vtype){
          case 0x81:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "OUI = 0x%06x",tvb_get_ntoh24(tvb,offset+2));
            break;
          case 0x82:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "DLSw Version = %d.%d",tvb_get_guint8(tvb,offset+2),tvb_get_guint8(tvb,offset+3));
            break;
          case 0x83:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "Initial Pacing Window = %d",tvb_get_ntohs(tvb,offset+2));
            break;
          case 0x84:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "Version String = %s",tvb_format_text(tvb,offset+2,vlen-2));
            break;
          case 0x85:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "MAC Address Exclusivity = %s",tvb_get_guint8(tvb,offset+2)==1?"On":"Off");
            break;
          case 0x86:
            while (i<vlen-2)
            {
              sap=tvb_get_guint8(tvb,offset+2+i);
              proto_tree_add_text (dlsw_vector_tree,tvb,offset+2+i,1,
                                   "SAP List Support = 0x%x0=%s 0x%x2=%s 0x%x4=%s 0x%x6=%s 0x%x8=%s 0x%xa=%s 0x%xc=%s 0x%xe=%s",
                                   i,sap&0x80?"on ":"off",i,sap&0x40?"on ":"off",i,sap&0x20?"on ":"off",i,sap&0x10?"on ":"off",
                                   i,sap&0x08?"on ":"off",i,sap&0x04?"on ":"off",i,sap&0x02?"on ":"off",i,sap&0x01?"on ":"off");
              i++;
            }
            break;
          case 0x87:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "TCP connections  = %d",tvb_get_guint8(tvb,offset+2));
            break;
          case 0x88:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "NetBIOS Name Exclusivity = %s",tvb_get_guint8(tvb,offset+2)==1?"On":"Off");
            break;
          case 0x89:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "MAC Address List = %s / %s",tvb_bytes_to_str(tvb,offset+2,6)
                                 ,tvb_bytes_to_str(tvb,offset+8,6));
            break;
          case 0x8a:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 /* %s */           "NetBIOS name = %s",/* tvb_get_guint8(tvb,offset+2)==0?"Individual":"Group",*/
                                 tvb_format_text(tvb,offset+2,vlen-2));
            break;
          case 0x8b:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "Vendor OUI = 0x%06x",tvb_get_ntoh24(tvb,offset+2));
            break;
          case 0x8c:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,
                                 "Multicast Version Number = %d",tvb_get_guint8(tvb,offset+2));
            break;
          default:
            proto_tree_add_text (dlsw_vector_tree,tvb,offset+2,vlen-2,"Vector Data = ???");
        }
        offset+=vlen;
      };
      break;
    default:
      proto_tree_add_text (tree,tvb,4,mlen - 4,"Unknown data");
  }

}
Exemplo n.º 26
0
static void
dissect_dlsw_pdu(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
  guint version,hlen = 0,mlen = 0,mtype,dlchlen = 0,direction,flags;
  proto_tree      *dlsw_tree = NULL, *ti,*ti2, *dlsw_header_tree = NULL;
  proto_tree      *dlsw_flags_tree,*dlsw_data_tree;

  col_set_str(pinfo->cinfo, COL_PROTOCOL, "DLSw");

  version=tvb_get_guint8(tvb,0);

  col_add_fstr(pinfo->cinfo, COL_INFO, "DLSw %s",val_to_str_const(version , dlsw_version_vals, "Unknown Version"));

  if (tree)
  {
    ti = proto_tree_add_item(tree, proto_dlsw, tvb, 0, -1, ENC_NA);
    dlsw_tree = proto_item_add_subtree(ti, ett_dlsw);

    hlen=tvb_get_guint8(tvb,1);

    ti2 = proto_tree_add_text (dlsw_tree, tvb, 0, hlen,"DLSw header, %s",
                               val_to_str_const(version , dlsw_version_vals, "Unknown Version"));

    dlsw_header_tree = proto_item_add_subtree(ti2, ett_dlsw_header);
    proto_tree_add_text (dlsw_header_tree,tvb,0 ,1,"Version        = %s",
                         val_to_str_const(version , dlsw_version_vals, "Unknown Version, dissection may be inaccurate"));
    proto_tree_add_text (dlsw_header_tree,tvb,1 ,1,"Header Length  = %u",hlen) ;
    mlen=tvb_get_ntohs(tvb,2);
    proto_tree_add_text (dlsw_header_tree,tvb,2 ,2,"Message Length = %u",mlen);
    proto_tree_add_text (dlsw_header_tree,tvb,4 ,4,"Remote DLC     = %u",tvb_get_ntohl(tvb,4)) ;
    proto_tree_add_text (dlsw_header_tree,tvb,8 ,4,"Remote DLC PID = %u",tvb_get_ntohl(tvb,8)) ;
    proto_tree_add_text (dlsw_header_tree,tvb,12,2,"Reserved") ;
  } ;

  mtype=tvb_get_guint8(tvb,14);
  col_append_fstr(pinfo->cinfo, COL_INFO, ", %s",val_to_str_const(mtype , dlsw_type_vals, "Unknown message Type"));
  if (tree)
  {
    proto_tree_add_text (dlsw_header_tree,tvb,14,1,"Message Type   = %s (0x%02x)",
                         val_to_str_const(mtype , dlsw_type_vals, "Unknown Type"),mtype);
    if (mtype==CAP_EXCHANGE)
    {
      proto_tree_add_text (dlsw_header_tree,tvb, 15,1,"Not used for CapEx") ;
    }
    else
    {
      flags = tvb_get_guint8(tvb,15);
      ti2 = proto_tree_add_text (dlsw_header_tree, tvb, 15,1,"Flow ctrl byte = 0x%02x",flags);
      dlsw_flags_tree = proto_item_add_subtree(ti2, ett_dlsw_fc);
      proto_tree_add_item(dlsw_flags_tree, hf_dlsw_flow_control_indication, tvb, 15, 1, ENC_BIG_ENDIAN);
      if (flags & 0x80)
      {
        proto_tree_add_item(dlsw_flags_tree, hf_dlsw_flow_control_ack, tvb, 15, 1, ENC_BIG_ENDIAN);
        proto_tree_add_item(dlsw_flags_tree, hf_dlsw_flow_control_operator, tvb, 15, 1, ENC_BIG_ENDIAN);
      }
    }
    if (hlen != DLSW_INFO_HEADER)
    {
      if (mtype==CAP_EXCHANGE)
      {
        proto_tree_add_text (dlsw_header_tree,tvb, 16,1,"Protocol ID    = 0x%02x",tvb_get_guint8(tvb,16)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 17,1,"Header Number  = 0x%02x",tvb_get_guint8(tvb,17)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 18,5,"Not used for CapEx") ;
        proto_tree_add_text (dlsw_header_tree,tvb, 23,1,"Old message type = %s (0x%02x)",
                             val_to_str_const(tvb_get_guint8(tvb,23) , dlsw_type_vals, "Unknown Type"),
                             tvb_get_guint8(tvb,23));
        direction=tvb_get_guint8(tvb,38);
        proto_tree_add_text (dlsw_header_tree,tvb, 24,14,"Not used for CapEx") ;
        proto_tree_add_text (dlsw_header_tree,tvb, 38,1,"Frame direction   =  %s (0x%02x)",
                             val_to_str_const(direction , dlsw_capex_type_vals, "Unknown Direction"),
                             direction);
        proto_tree_add_text (dlsw_header_tree,tvb, 39,33,"Not used for CapEx") ;
      }
      else
      {
        proto_tree_add_text (dlsw_header_tree,tvb, 16,1,"Protocol ID    = 0x%02x",tvb_get_guint8(tvb,16)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 17,1,"Header Number  = 0x%02x",tvb_get_guint8(tvb,17)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 18,2,"Reserved") ;
        proto_tree_add_text (dlsw_header_tree,tvb, 20,1,"Largest Frame size  = %u",tvb_get_guint8(tvb,20)) ;
        flags = tvb_get_guint8(tvb,21);
        ti2 = proto_tree_add_text (dlsw_header_tree,tvb, 21,1,"SSP Flags      = 0x%02x",flags) ;
        dlsw_flags_tree = proto_item_add_subtree(ti2, ett_dlsw_sspflags);
        proto_tree_add_item (dlsw_flags_tree, hf_dlsw_flags_explorer_msg, tvb, 21, 1, ENC_BIG_ENDIAN);
        proto_tree_add_text (dlsw_header_tree,tvb, 22,1,"Circuit priority = %s",
                             val_to_str((tvb_get_guint8(tvb,22)&7),dlsw_pri_vals, "Unknown (%d)")) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 23,1,"Old message type = %s (0x%02x)",
                             val_to_str_const(tvb_get_guint8(tvb,23) , dlsw_type_vals, "Unknown Type"),
                             tvb_get_guint8(tvb,23));
        proto_tree_add_text (dlsw_header_tree,tvb, 24,6,"Target MAC Address  = %s",tvb_bytes_to_str(tvb,24,6)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 30,6,"Origin MAC Address  = %s",tvb_bytes_to_str(tvb,30,6)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 36,1,"Origin Link SAP     = 0x%02x",tvb_get_guint8(tvb,36)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 37,1,"Target Link SAP     = 0x%02x",tvb_get_guint8(tvb,37)) ;
        direction=tvb_get_guint8(tvb,38);
        proto_tree_add_text (dlsw_header_tree,tvb, 38,1,"Frame direction   =  %s (0x%02x)",
                             val_to_str_const(direction , dlsw_frame_direction_vals, "Unknown Direction"),
                             direction);
        proto_tree_add_text (dlsw_header_tree,tvb, 39,3,"Reserved") ;
        dlchlen=tvb_get_ntohs(tvb,42);
        if ( dlchlen > mlen )
        {
          proto_tree_add_text (dlsw_header_tree,tvb, 42,2,"DLC Header Length = %u (bogus, must be <= message length %u)",dlchlen, mlen) ;
          return;
        }
        proto_tree_add_text (dlsw_header_tree,tvb, 42,2,"DLC Header Length = %u",dlchlen) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 44,4,"Origin DLC Port ID     = %u",tvb_get_ntohl(tvb,44)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 48,4,"Origin DLC             = %u",tvb_get_ntohl(tvb,48)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 52,4,"Origin Transport ID    = %u",tvb_get_ntohl(tvb,52)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 56,4,"Target DLC Port ID     = %u",tvb_get_ntohl(tvb,56)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 60,4,"Target DLC             = %u",tvb_get_ntohl(tvb,60)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 64,4,"Target Transport ID    = %u",tvb_get_ntohl(tvb,64)) ;
        proto_tree_add_text (dlsw_header_tree,tvb, 68,4,"Reserved") ;
      }
    }

/* end of header dissector */

    ti2 = proto_tree_add_text (dlsw_tree, tvb, hlen, mlen,"DLSw data");
    dlsw_data_tree = proto_item_add_subtree(ti2, ett_dlsw_data);

    switch (mtype)
    {
      case CAP_EXCHANGE:
        dissect_dlsw_capex(tvb_new_subset(tvb, hlen, mlen, -1), dlsw_data_tree,ti2);
        break;
      case IFCM:
      case INFOFRAME:
      case KEEPALIVE:
        proto_tree_add_text (dlsw_data_tree,tvb,hlen,mlen,"Data") ;
        break;

      default:
        if (dlchlen!=0)
        {
          proto_tree_add_text (dlsw_data_tree,tvb,hlen,1,"DLC Header - AC byte : 0x%02x",tvb_get_guint8(tvb,hlen)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+1,1,"DLC Header - FC byte : 0x%02x",tvb_get_guint8(tvb,hlen+1)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+2,6,"DLC Header - DA : %s",tvb_bytes_to_str(tvb,hlen+2,6)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+8,6,"DLC Header - SA : %s",tvb_bytes_to_str(tvb,hlen+8,6)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+14,18,"DLC Header - RIF : %s",tvb_bytes_to_str(tvb,hlen+14,18)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+32,1,"DLC Header - DSAP : 0x%02x",tvb_get_guint8(tvb,hlen+32)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+33,1,"DLC Header - SSAP : 0x%02x",tvb_get_guint8(tvb,hlen+33)) ;
          proto_tree_add_text (dlsw_data_tree,tvb,hlen+34,1,"DLC Header - Ctrl : 0x%02x",tvb_get_guint8(tvb,hlen+34)) ;
        }
        proto_tree_add_text (dlsw_data_tree,tvb,hlen+dlchlen,mlen-dlchlen,"Data") ;
    }

  }
}