示例#1
0
void fec_info_column(struct _fec *fec, packet_info *pinfo)
{
	if (fec->sbn_present)
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "SBN: %u", fec->sbn);

	if (fec->esi_present)
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "ESI: 0x%X", fec->esi);
}
示例#2
0
/* Decode and display the PDU Burst */
static void pdu_burst_decoder(proto_tree *tree, tvbuff_t *tvb, gint offset, gint length, packet_info *pinfo, gint burst_number, gint frag_type, gint frag_number)
{
	fragment_head *pdu_frag;
	tvbuff_t *pdu_tvb = NULL;

	/* update the info column */
	switch (frag_type)
	{
		case TLV_FIRST_FRAG:
			col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "First TLV Fragment (%d)", frag_number);
		break;
		case TLV_LAST_FRAG:
			col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Last TLV Fragment (%d)", frag_number);
		break;
		case TLV_MIDDLE_FRAG:
			col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Middle TLV Fragment %d", frag_number);
		break;
	}
	if(frag_type == TLV_NO_FRAG)
	{	/* not fragmented PDU */
		pdu_tvb =  tvb_new_subset_length(tvb, offset, length);
	}
	else	/* fragmented PDU */
	{	/* add the fragment */
		pdu_frag = fragment_add_seq(&pdu_reassembly_table, tvb, offset, pinfo, burst_number, NULL, frag_number - 1, length, ((frag_type==TLV_LAST_FRAG)?0:1), 0);
		if(pdu_frag && frag_type == TLV_LAST_FRAG)
		{
			/* create the new tvb for defragmented frame */
			pdu_tvb = tvb_new_chain(tvb, pdu_frag->tvb_data);
			/* add the defragmented data to the data source list */
			add_new_data_source(pinfo, pdu_tvb, "Reassembled WiMax PDU Frame");
		}
		else
		{
			pdu_tvb = NULL;
			if(frag_type == TLV_LAST_FRAG)
			{	/* update the info column */
				col_append_sep_str(pinfo->cinfo, COL_INFO, ", ", "Incomplete PDU frame");
			}
		}
	}
	/* process the defragmented PDU burst */
	if(pdu_tvb)
	{
		if(wimax_pdu_burst_handle)
		{/* decode and display PDU Burst */
			call_dissector(wimax_pdu_burst_handle, pdu_tvb, pinfo, tree);
		}
		else	/* display PDU Burst info */
		{	/* update the info column */
			col_append_str(pinfo->cinfo, COL_INFO, "PDU Burst");
		}
	}
}
示例#3
0
static void
decode_iei_reset_flag(nsip_ie_t *ie, build_info_t *bi, int ie_start_offset) {
  guint8 flag;
  proto_item *tf;
  proto_tree *field_tree;

  flag = tvb_get_guint8(bi->tvb, bi->offset);
  if (bi->nsip_tree) {

     tf = proto_tree_add_text(bi->nsip_tree, bi->tvb, ie_start_offset,
                 ie->total_length,
                 "Reset Flag: %#02x", flag);

     field_tree = proto_item_add_subtree(tf, ett_nsip_reset_flag);
     proto_tree_add_boolean(field_tree, hf_nsip_reset_flag, bi->tvb,
                           bi->offset, 1,
                           flag & NSIP_MASK_RESET_FLAG);
     if (flag & NSIP_MASK_RESET_FLAG) {
         col_append_sep_fstr(bi->pinfo->cinfo, COL_INFO, NSIP_SEP,
                   "Reset");
         proto_item_append_text(bi->ti, ", Reset");
     }
     proto_tree_add_uint(field_tree, hf_nsip_reset_flag_spare,
                           bi->tvb, bi->offset, 1,
                           flag & NSIP_MASK_RESET_FLAG_SPARE);
  }
  bi->offset += 1;
}
static int
dissect_form_urlencoded(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
{
	proto_tree	*url_tree;
	proto_tree	*sub;
	proto_item	*ti;
	gint		offset = 0, next_offset;
	const char	*data_name;

	data_name = pinfo->match_string;
	if (! (data_name && data_name[0])) {
		/*
		 * No information from "match_string"
		 */
		data_name = (char *)data;
		if (! (data_name && data_name[0])) {
			/*
			 * No information from dissector data
			 */
			data_name = NULL;
		}
	}

	if (data_name)
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s)", data_name);

	ti = proto_tree_add_item(tree, hfi_urlencoded, tvb, 0, -1, ENC_NA);
	if (data_name)
		proto_item_append_text(ti, ": %s", data_name);
	url_tree = proto_item_add_subtree(ti, ett_form_urlencoded);

	while (tvb_reported_length_remaining(tvb, offset) > 0) {
		const int start_offset = offset;
		char *key, *value;

		ti = proto_tree_add_item(url_tree, &hfi_form_keyvalue, tvb, offset, 0, ENC_NA);

		sub = proto_item_add_subtree(ti, ett_form_keyvalue);

		next_offset = get_form_key_value(tvb, &key, offset, '=');
		if (next_offset == -1)
			break;
		proto_tree_add_string(sub, &hfi_form_key, tvb, offset, next_offset - offset, key);
		proto_item_append_text(sub, ": \"%s\"", key);

		offset = next_offset+1;

		next_offset = get_form_key_value(tvb, &value, offset, '&');
		if (next_offset == -1)
			break;
		proto_tree_add_string(sub, &hfi_form_value, tvb, offset, next_offset - offset, value);
		proto_item_append_text(sub, " = \"%s\"", value);

		offset = next_offset+1;

		proto_item_set_len(ti, offset - start_offset);
	}

	return tvb_captured_length(tvb);
}
示例#5
0
static void
decode_iei_transaction_id(nsip_ie_t *ie, build_info_t *bi, int ie_start_offset) {
  guint8 id;
  id = tvb_get_guint8(bi->tvb, bi->offset);
  proto_tree_add_uint(bi->nsip_tree, hf_nsip_transaction_id,
                      bi->tvb, ie_start_offset, ie->total_length, id);
  col_append_sep_fstr(bi->pinfo->cinfo, COL_INFO, NSIP_SEP,
            "Transaction Id: %d", id);
  bi->offset += 1;
}
示例#6
0
static void
decode_iei_bvci(nsip_ie_t *ie, build_info_t *bi, int ie_start_offset) {
  guint16 bvci = tvb_get_ntohs(bi->tvb, bi->offset);

  proto_tree_add_uint(bi->nsip_tree, hf_nsip_bvci, bi->tvb,
                      ie_start_offset, ie->total_length, bvci);
  bi->offset += ie->value_length;

  col_append_sep_fstr(bi->pinfo->cinfo, COL_INFO, NSIP_SEP,
                        "BVCI %u", bvci);
  proto_item_append_text(bi->ti, ", BVCI %u", bvci);
}
示例#7
0
static void
decode_iei_nsei(nsip_ie_t *ie, build_info_t *bi, int ie_start_offset) {
  guint16 nsei = tvb_get_ntohs(bi->tvb, bi->offset);

  if (bi->nsip_tree) {
    proto_tree_add_uint(bi->nsip_tree, hf_nsip_nsei, bi->tvb,
                        ie_start_offset, ie->total_length, nsei);
  }
  bi->offset += ie->value_length;

  if (check_col(bi->pinfo->cinfo, COL_INFO)) {
    col_append_sep_fstr(bi->pinfo->cinfo, COL_INFO, NSIP_SEP,
                        "NSEI %u", nsei);
  }
  proto_item_append_text(bi->ti, ", NSEI %u", nsei);
}
示例#8
0
static void
decode_iei_ns_vci(nsip_ie_t *ie, build_info_t *bi, int ie_start_offset) {
  guint16 ns_vci;

  if (bi->nsip_tree) {
    ns_vci = tvb_get_ntohs(bi->tvb, bi->offset);

    proto_tree_add_uint_format(bi->nsip_tree, hf_nsip_ns_vci,
                               bi->tvb, ie_start_offset, ie->total_length,
                               ns_vci,
                               "NS VCI: %#04x", ns_vci);
    col_append_sep_fstr(bi->pinfo->cinfo, COL_INFO, NSIP_SEP,
        "NS VCI: %#04x", ns_vci);
    proto_item_append_text(bi->ti, ", NS VCI: %#04x", ns_vci);
  }
  bi->offset += ie->value_length;
}
示例#9
0
/**
 * dissect_messageid is a utility function which
 * calculates the ID of the message.
 *
 * @see dissect_packetid()
 * @see dissect_reliable_message_index_base()
 * @see dissect_content_length()
 * @see dissect_reliable_message_number()
 * @see dissect_payload()
 * @param buffer the buffer to the data
 * @param offset the offset where to start reading the data
 * @param tree the parent tree where the dissected data is going to be inserted
 * @return int returns the messageid
 *
 */
static int
dissect_messageid(tvbuff_t *buffer, int *offset, proto_tree *tree, packet_info *pinfo, gboolean separator)
{
    gint   messageid_length;
    guint8 messageid;
    gboolean col_write;

    messageid = tvb_get_guint8(buffer, (*offset));

    switch(messageid)
    {
        case DISCONNECT:
        case DISCONNECTACK:
        case CONNECTSYN:
        case CONNECTSYNACK:
        case CONNECTACK:
            messageid_length = 4;
        break;
        default:
            messageid_length = 1;
        break;
    }

    proto_tree_add_uint_format_value(tree, hf_knet_messageid, buffer, *offset, messageid_length, messageid,
            "%s (%d)", val_to_str_const(messageid, packettypenames, "AppData or Malformed Message ID"), messageid);

    /* XXX - TCP reassembly disables writing columns which prevents populating COL_INFO if multiple KNET messages
       appear in a single packet that needed to be reassembled.
       Force making columns writable.
    */
    if (separator)
    {
        col_write = col_get_writable(pinfo->cinfo);
        col_set_writable(pinfo->cinfo, TRUE);
        col_append_sep_fstr(pinfo->cinfo, COL_INFO, ", ", "%s (%d)", val_to_str_const(messageid, packettypenames, "AppData"), messageid);
        col_set_writable(pinfo->cinfo, col_write);
    }
    else
    {
        col_append_fstr(pinfo->cinfo, COL_INFO, "%s (%d)", val_to_str_const(messageid, packettypenames, "AppData"), messageid);
    }

    *offset += messageid_length;

    return messageid;
}
示例#10
0
static void
decode_iei_cause(nsip_ie_t *ie, build_info_t *bi, int ie_start_offset) {
  guint8 cause;

  cause = tvb_get_guint8(bi->tvb, bi->offset);
  proto_tree_add_uint(bi->nsip_tree, hf_nsip_cause,
      bi->tvb, ie_start_offset, ie->total_length,
      cause);
  col_append_sep_fstr(bi->pinfo->cinfo, COL_INFO, NSIP_SEP,
      "Cause: %s",
      val_to_str(cause, tab_nsip_cause_values, "Unknown (0x%02x)"));

  proto_item_append_text(bi->ti, ", Cause: %s",
            val_to_str(cause, tab_nsip_cause_values, "Unknown (0x%02x)"));

  bi->offset += ie->value_length;
}
示例#11
0
/* Display the raw WiMax TLV */
void proto_tree_add_tlv(tlv_info_t *self, tvbuff_t *tvb, guint offset, packet_info *pinfo, proto_tree *tree, gint hf, guint encoding)
{
	guint tlv_offset;
	gint tlv_type, tlv_len;

	/* make sure the TLV information is valid */
	if(!self->valid)
	{	/* invalid TLV info */
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Invalid TLV");
		return;
	}
	tlv_offset = offset;
	/* display TLV type */
	proto_tree_add_item(tree, hf_m2m_type, tvb, tlv_offset, 1, ENC_BIG_ENDIAN);
	tlv_offset++;
	/* check the TLV length type */
	if( self->length_type )
	{	/* multiple bytes TLV length */
		/* display the length of the TLV length with MSB */
		proto_tree_add_item(tree, hf_m2m_len_size, tvb, tlv_offset, 1, ENC_BIG_ENDIAN);
		tlv_offset++;
		if(self->size_of_length)
			/* display the multiple byte TLV length */
			proto_tree_add_item(tree, hf_m2m_len, tvb, tlv_offset, self->size_of_length, ENC_BIG_ENDIAN);
		else
			return;
	}
	else	/* display the single byte TLV length */
		proto_tree_add_item(tree, hf_m2m_len, tvb, tlv_offset, 1, ENC_BIG_ENDIAN);

	tlv_type = get_tlv_type(self);
	/* Display Frame Number as special case for filter */
	if ( tlv_type == TLV_FRAME_NUM )
	{
		return;
	}

	/* get the TLV length */
	tlv_len = get_tlv_length(self);
	proto_tree_add_item(tree, hf, tvb, (offset + self->value_offset), tlv_len, encoding);
}
示例#12
0
/* The dissector itself */
static void dissect_at(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    proto_item *item;
    proto_tree *at_tree;
    gint len;

    len = tvb_reported_length(tvb);
    col_append_str(pinfo->cinfo, COL_PROTOCOL, "/AT");
    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "AT Command: %s",
                        tvb_format_text_wsp(tvb, 0, len));

    if (tree) {
        /* Start with a top-level item to add everything else to */
        item = proto_tree_add_item(tree, proto_at, tvb, 0, -1, ENC_NA);
        at_tree = proto_item_add_subtree(item, ett_at);

        /* Command */
        proto_tree_add_item(at_tree, hf_at_command, tvb, 0, len, ENC_ASCII|ENC_NA);
        proto_item_append_text(item, ": %s", tvb_format_text_wsp(tvb, 0, len));
    }
}
示例#13
0
static void
dissect_nsip(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) {
  guint8 pdu_type;
  build_info_t bi = { NULL, 0, NULL, NULL, NULL, NULL };
  proto_tree *nsip_tree;

  bi.tvb = tvb;
  bi.pinfo = pinfo;
  bi.parent_tree = tree;

  pinfo->current_proto = "GPRS-NS";

  if (!nsip_is_recursive) {
    col_set_str(pinfo->cinfo, COL_PROTOCOL, "GPRS-NS");
    col_clear(pinfo->cinfo, COL_INFO);
  }

  pdu_type = tvb_get_guint8(tvb, 0);
  bi.offset++;

  if (tree) {
    bi.ti = proto_tree_add_item(tree, proto_nsip, tvb, 0, -1,
                             ENC_NA);
    nsip_tree = proto_item_add_subtree(bi.ti, ett_nsip);
    proto_tree_add_item(nsip_tree, hf_nsip_pdu_type, tvb, 0, 1, ENC_NA);
    proto_item_append_text(bi.ti, ", PDU type: %s",
                               val_to_str_const(pdu_type, tab_nsip_pdu_types, "Unknown"));
    bi.nsip_tree = nsip_tree;
  }

  if (!nsip_is_recursive) {
    col_set_str(pinfo->cinfo, COL_INFO,
                val_to_str_const(pdu_type, tab_nsip_pdu_types, "Unknown PDU type"));
  } else {
    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NSIP_SEP, "%s",
                val_to_str_const(pdu_type, tab_nsip_pdu_types, "Unknown PDU type"));
  }
  decode_pdu(pdu_type, &bi);
}
示例#14
0
static int
ssh_dissect_encrypted_packet(tvbuff_t *tvb, packet_info *pinfo,
		struct ssh_peer_data *peer_data,
		int offset, proto_tree *tree)
{
	gint len;
	guint plen;

	len = tvb_reported_length_remaining(tvb, offset);
	col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Encrypted packet (len=%d)", len);

	if (tree) {
		gint encrypted_len = len;

		if (len > 4 && peer_data->length_is_plaintext) {
			plen = tvb_get_ntohl(tvb, offset) ;
			proto_tree_add_uint(tree, hf_ssh_packet_length, tvb, offset, 4, plen);
			encrypted_len -= 4;
		}
		else if (len > 4) {
			proto_tree_add_item(tree, hf_ssh_packet_length_encrypted, tvb, offset, 4, ENC_NA);
			encrypted_len -= 4;
		}

		if (peer_data->mac_length>0)
			encrypted_len -= peer_data->mac_length;

		proto_tree_add_item(tree, hf_ssh_encrypted_packet,
					tvb, offset+4, encrypted_len, ENC_NA);

		if (peer_data->mac_length>0)
			proto_tree_add_item(tree, hf_ssh_mac_string,
				tvb, offset+4+encrypted_len,
				peer_data->mac_length, ENC_NA);
	}
	offset+=len;
	return offset;
}
示例#15
0
void
dissect_nvme_data_response(tvbuff_t *nvme_tvb, packet_info *pinfo, proto_tree *root_tree,
                 struct nvme_q_ctx *q_ctx, struct nvme_cmd_ctx *cmd_ctx, guint len)
{
    proto_tree *cmd_tree;
    proto_item *ti;
    const guint8 *str_opcode;

    col_set_str(pinfo->cinfo, COL_PROTOCOL, "NVMe");
    ti = proto_tree_add_item(root_tree, proto_nvme, nvme_tvb, 0,
                             len, ENC_NA);
    cmd_tree = proto_item_add_subtree(ti, ett_data);
    if (q_ctx->qid) { //IOQ
        str_opcode = val_to_str(cmd_ctx->opcode, ioq_opc_tbl,
                                "Unknown IOQ Opcode");
        switch (cmd_ctx->opcode) {
        case NVME_IOQ_OPC_READ:
        case NVME_IOQ_OPC_WRITE:
        default:
            proto_tree_add_bytes_format_value(cmd_tree, hf_nvme_gen_data,
                                              nvme_tvb, 0, len, NULL,
                                              "%s", str_opcode);
            break;
        }
    } else { //AQ
        str_opcode = val_to_str(cmd_ctx->opcode, aq_opc_tbl,
                                "Unknown AQ Opcode");
        switch (cmd_ctx->opcode) {
        default:
            proto_tree_add_bytes_format_value(cmd_tree, hf_nvme_gen_data,
                                              nvme_tvb, 0, len, NULL,
                                              "%s", str_opcode);
            break;
        }
    }
    col_append_sep_fstr(pinfo->cinfo, COL_INFO, " | ", "NVMe %s: Data", str_opcode);
}
示例#16
0
/* The dissector itself */
static void dissect_chdr(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    // Here are all the variables
    proto_item *item;
    proto_item *stream_item;
    proto_tree *chdr_tree;
    proto_item *header_item;
    proto_tree *header_tree;
    proto_tree *stream_tree;
    proto_item *response_item;
    proto_tree *response_tree;
    proto_item *cmd_item;
    proto_tree *cmd_tree;
    gint len;

    gint flag_offset;
    guint8 *bytes;
    guint8 hdr_bits = 0;
    guint8 pkt_type = 0;
    gboolean flag_has_time = 0;
    gboolean flag_is_data = 0;
    gboolean flag_is_fc = 0;
    gboolean flag_is_cmd = 0;
    gboolean flag_is_resp = 0;
    gboolean flag_is_eob = 0;
    gboolean flag_is_error = 0;
    unsigned long long timestamp;
    gboolean is_network;
    gint endianness;
    gint id_pos_usb[4] = {7, 6, 5, 4};
    gint id_pos_net[4] = {4, 5, 6, 7};
    gint id_pos[4] = {7, 6, 5, 4};

    if(pinfo->match_uint == CHDR_PORT){
        is_network = TRUE;
        flag_offset = 0;
        endianness = ENC_BIG_ENDIAN;
        memcpy(id_pos, id_pos_net, 4 * sizeof(gint));
    }
    else{   // Parsing a USB capture
        is_network = FALSE;
        flag_offset = 3;
        endianness = ENC_LITTLE_ENDIAN;
        memcpy(id_pos, id_pos_usb, 4 * sizeof(gint));
    }

    len = tvb_reported_length(tvb);

    col_append_str(pinfo->cinfo, COL_PROTOCOL, "/CHDR");
    /* This throws a warning: */
    /*col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "CHDR", tvb_format_text_wsp(tvb, 0, len));*/
    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "CHDR");

    if (tree){
        int chdr_size = -1;

        if (len >= 4){
            chdr_size = 8;
            bytes = tvb_get_string(wmem_packet_scope(), tvb, 0, 4);
	    hdr_bits = (bytes[flag_offset] & 0xF0) >> 4;
	    pkt_type = hdr_bits >> 2;
	    flag_is_data = (pkt_type == 0);
	    flag_is_fc = (pkt_type == 1);
	    flag_is_cmd = (pkt_type == 2);
	    flag_is_resp = (pkt_type == 3);
	    flag_is_eob = flag_is_data && (hdr_bits & 0x1);
	    flag_is_error = flag_is_resp && (hdr_bits & 0x1);
            flag_has_time = hdr_bits & 0x2;
            if (flag_has_time)
                chdr_size += 8; // 64-bit timestamp
        }

        /* Start with a top-level item to add everything else to */
        item = proto_tree_add_item(tree, proto_chdr, tvb, 0, min(len, chdr_size), ENC_NA);

        if (len >= 4) {
            chdr_tree = proto_item_add_subtree(item, ett_chdr);

            /* Header info. First, a top-level header tree item: */
            header_item = proto_tree_add_item(chdr_tree, hf_chdr_hdr, tvb, flag_offset, 1, endianness);
            header_tree = proto_item_add_subtree(header_item, ett_chdr_header);
            proto_item_append_text(header_item, ", Packet type: %s",
                val_to_str(hdr_bits & 0xD, CHDR_PACKET_TYPES, "Unknown (0x%x)")
            );
            /* Let us query hdr.type */
            proto_tree_add_string(
                header_tree, hf_chdr_type, tvb, flag_offset, 1,
                val_to_str(hdr_bits & 0xD, CHDR_PACKET_TYPES_SHORT, "invalid")
            );
            /* And other flags */
            proto_tree_add_boolean(header_tree, hf_chdr_has_time, tvb, flag_offset, 1, flag_has_time);
            if (flag_is_data) {
                proto_tree_add_boolean(header_tree, hf_chdr_eob, tvb, flag_offset, 1, flag_is_eob);
            }
            if (flag_is_resp) {
                proto_tree_add_boolean(header_tree, hf_chdr_error, tvb, flag_offset, 1, flag_is_error);
            }

            /* These lines add sequence, packet_size and stream ID */
            proto_tree_add_item(chdr_tree, hf_chdr_sequence, tvb, (is_network ? 0:2), 2, endianness);
            proto_tree_add_item(chdr_tree, hf_chdr_packet_size, tvb, (is_network ? 2:0), 2, endianness);

            if (len >= 8){
                /* stream id can be broken down to 4 sections. these are collapsed in a subtree */
                stream_item = proto_tree_add_item(chdr_tree, hf_chdr_stream_id, tvb, 4, 4, endianness);
                stream_tree = proto_item_add_subtree(stream_item, ett_chdr_id);
                proto_tree_add_item(stream_tree, hf_chdr_src_dev, tvb, id_pos[0], 1, ENC_NA);
                proto_tree_add_item(stream_tree, hf_chdr_src_ep,  tvb, id_pos[1], 1, ENC_NA);
                proto_tree_add_item(stream_tree, hf_chdr_dst_dev, tvb, id_pos[2], 1, ENC_NA);
                proto_tree_add_item(stream_tree, hf_chdr_dst_ep,  tvb, id_pos[3], 1, ENC_NA);

                /* Block ports (only add them if address points to a device) */
                bytes = tvb_get_string(wmem_packet_scope(), tvb, 0, 8);
		if (bytes[id_pos[0]] != 0) {
                    proto_tree_add_item(stream_tree, hf_chdr_src_blockport, tvb, id_pos[1], 1, ENC_NA);
		}
		if (bytes[id_pos[2]] != 0) {
                    proto_tree_add_item(stream_tree, hf_chdr_dst_blockport, tvb, id_pos[3], 1, ENC_NA);
		}

		/* Append SID in sid_t hex format */
                proto_item_append_text(stream_item, " (%02X:%02X>%02X:%02X)",
                    bytes[id_pos[0]],
                    bytes[id_pos[1]],
                    bytes[id_pos[2]],
                    bytes[id_pos[3]]
                );

                /* if has_time flag is present interpret timestamp */
                if ((flag_has_time) && (len >= 16)){
                    if (is_network)
                        item = proto_tree_add_item(chdr_tree, hf_chdr_timestamp, tvb, 8, 8, endianness);
                    else{
                        bytes = (guint8*) tvb_get_string(wmem_packet_scope(), tvb, 8, sizeof(unsigned long long));
                        timestamp = get_timestamp(bytes, sizeof(unsigned long long));
                        proto_tree_add_uint64(chdr_tree, hf_chdr_timestamp, tvb, 8, 8, timestamp);
                    }
                }

                int remaining_bytes = (len - chdr_size);
                int show_raw_payload = (remaining_bytes > 0);

                if (flag_is_cmd && remaining_bytes == 8) {
                    cmd_item = proto_tree_add_item(chdr_tree, hf_chdr_cmd, tvb, chdr_size, 8, endianness);
                    cmd_tree = proto_item_add_subtree(cmd_item, ett_chdr_cmd);
                    proto_tree_add_item(cmd_tree, hf_chdr_cmd_address, tvb, chdr_size,     4, endianness);
                    proto_tree_add_item(cmd_tree, hf_chdr_cmd_value,   tvb, chdr_size + 4, 4, endianness);
                } else if (flag_is_resp) {
                    response_item = proto_tree_add_item(chdr_tree, hf_chdr_ext_response, tvb, chdr_size, 8, endianness);
                    response_tree = proto_item_add_subtree(response_item, ett_chdr_response);

                    proto_tree_add_item(response_tree, hf_chdr_ext_status_code, tvb, chdr_size, 4, endianness);
                    /* This will show the 12-bits of sequence ID in the last 2 bytes */
                    proto_tree_add_item(response_tree, hf_chdr_ext_seq_num, tvb, (chdr_size + 4 + (is_network ? 2 : 0)), 2, endianness);
                } else if (show_raw_payload) {
                    proto_tree_add_item(chdr_tree, hf_chdr_payload, tvb, chdr_size, -1, ENC_NA);
                }
            }
        }
    }
示例#17
0
static int
dissect_json(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
{
	proto_tree *json_tree = NULL;
	proto_item *ti = NULL;

	json_parser_data_t parser_data;
	tvbparse_t *tt;

	const char *data_name;
	int offset;

	/* JSON dissector can be called in a JSON native file or when transported
	 * by another protocol. We set the column values only if they've not been
	 * already set by someone else.
	 */
	wmem_list_frame_t *proto = wmem_list_frame_prev(wmem_list_tail(pinfo->layers));
	if (proto) {
		const char *name = proto_get_protocol_filter_name(GPOINTER_TO_INT(wmem_list_frame_data(proto)));

		if (!strcmp(name, "frame")) {
			col_set_str(pinfo->cinfo, COL_PROTOCOL, "JSON");
			col_set_str(pinfo->cinfo, COL_INFO, "JavaScript Object Notation");
		}
	}

	data_name = pinfo->match_string;
	if (! (data_name && data_name[0])) {
		/*
		 * No information from "match_string"
		 */
		data_name = (char *)data;
		if (! (data_name && data_name[0])) {
			/*
			 * No information from dissector data
			 */
			data_name = NULL;
		}
	}

	if (tree) {
		ti = proto_tree_add_item(tree, hfi_json, tvb, 0, -1, ENC_NA);
		json_tree = proto_item_add_subtree(ti, ett_json);

		if (data_name)
			proto_item_append_text(ti, ": %s", data_name);
	}

	offset = 0;

	parser_data.stack = wmem_stack_new(wmem_packet_scope());
	wmem_stack_push(parser_data.stack, json_tree);

	tt = tvbparse_init(tvb, offset, -1, &parser_data, want_ignore);

	/* XXX, only one json in packet? */
	while ((tvbparse_get(tt, want)))
		;

	offset = tvbparse_curr_offset(tt);

	proto_item_set_len(ti, offset);

	/* if we have some unparsed data, pass to data-text-lines dissector (?) */
	if (tvb_reported_length_remaining(tvb, offset) > 0) {
		tvbuff_t *next_tvb;

		next_tvb = tvb_new_subset_remaining(tvb, offset);

		call_dissector_with_data(text_lines_handle, next_tvb, pinfo, tree, data);
	} else if (data_name) {
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s)", data_name);
	}

	return tvb_captured_length(tvb);
}
示例#18
0
/* Dissect a FEC header:
 * fec - ptr to the logical FEC packet representation to fill
 * hf - ptr to header fields array
 * ett - ptr to ett array
 * prefs - ptr to FEC prefs array
 * tvb - buffer
 * pinfo - packet info
 * tree - tree where to add FEC header subtree
 * offset - ptr to offset to use and update
 */
static int
dissect_fec(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data)
{
    proto_item          *ti;
    proto_tree          *fec_tree;
    guint                offset      = 0;
    fec_data_exchange_t *fec         = (fec_data_exchange_t*)data;
    guint8               encoding_id = 0;
    fec_packet_data_t   *packet_data = (fec_packet_data_t*)p_get_proto_data(wmem_file_scope(), pinfo, proto_rmt_fec, 0);

    if (fec != NULL)
    {
        encoding_id = fec->encoding_id;
    }

    /* Create the FEC subtree */
    ti = proto_tree_add_item(tree, proto_rmt_fec, tvb, offset, -1, ENC_NA);
    fec_tree = proto_item_add_subtree(ti, ett_main);

    proto_tree_add_uint(fec_tree, hf_encoding_id, tvb, offset, 0, encoding_id);

    if (encoding_id >= 128 && (packet_data != NULL))
        proto_tree_add_uint(fec_tree, hf_instance_id, tvb, offset, 0, packet_data->instance_id);

    switch (encoding_id)
    {
    case 0:
    case 1:
    case 130:
        proto_tree_add_item(fec_tree, hf_sbn, tvb, offset,   2, ENC_BIG_ENDIAN);
        proto_tree_add_item(fec_tree, hf_esi, tvb, offset+2, 2, ENC_BIG_ENDIAN);

        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "SBN: %u", tvb_get_ntohs(tvb, offset));
        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "ESI: 0x%X", tvb_get_ntohs(tvb, offset+2));

        offset += 4;
        break;

    case 2:
    case 128:
    case 132:
        proto_tree_add_item(fec_tree, hf_sbn, tvb, offset,   4, ENC_BIG_ENDIAN);
        proto_tree_add_item(fec_tree, hf_esi, tvb, offset+4, 4, ENC_BIG_ENDIAN);

        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "SBN: %u", tvb_get_ntohl(tvb, offset));
        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "ESI: 0x%X", tvb_get_ntohl(tvb, offset+4));

        offset += 8;
        break;

    case 3:
    case 4:
        proto_tree_add_item(fec_tree, hf_sbn_with_mask, tvb, offset, 4, ENC_BIG_ENDIAN);
        proto_tree_add_item(fec_tree, hf_esi_with_mask, tvb, offset, 4, ENC_BIG_ENDIAN);

        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "SBN: %u", tvb_get_ntohl(tvb, offset) >> 20);
        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "ESI: 0x%X", tvb_get_ntohl(tvb, offset) & 0xfffff);

        offset += 4;
        break;

    case 6:
        proto_tree_add_item(fec_tree, hf_sbn, tvb, offset,   1, ENC_BIG_ENDIAN);
        proto_tree_add_item(fec_tree, hf_esi, tvb, offset+1, 3, ENC_BIG_ENDIAN);

        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "SBN: %u", tvb_get_guint8(tvb, offset));
        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "ESI: 0x%X", tvb_get_ntoh24(tvb, offset+1));

        offset += 4;
        break;

    case 129:
        proto_tree_add_item(fec_tree, hf_sbn, tvb, offset,   4, ENC_BIG_ENDIAN);
        proto_tree_add_item(fec_tree, hf_sbl, tvb, offset+4, 2, ENC_BIG_ENDIAN);
        proto_tree_add_item(fec_tree, hf_esi, tvb, offset+6, 2, ENC_BIG_ENDIAN);

        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "SBN: %u", tvb_get_ntohl(tvb, offset));
        col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "ESI: 0x%X", tvb_get_ntohs(tvb, offset+6));

        offset += 8;
        break;
    }

    return offset;
}
示例#19
0
static void
dissect_rtmpt(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
	proto_tree	*rtmpt_tree = NULL;
	proto_tree	*rtmptroot_tree = NULL;
	proto_item	*ti = NULL;
	gint        offset = 0;

	struct tcpinfo* tcpinfo = pinfo->private_data;

	guint8  iCommand = -1;
	guint32 iLength = 1;
	guint16 iHeaderType = 4;
	guint16 iHeaderLength;
	guint8  iID;
	guint   rtmp_index;

	conversation_t * current_conversation;
	rtmpt_conversation_data_t * conversation_data;
	rtmpt_packet_data_t * packet_data;

	rtmpt_chunk_data_t *current_chunk_data = NULL;
	rtmpt_chunk_data_t *initial_chunk_data = NULL;

	tvbuff_t*   amf_tvb;

	current_conversation = find_conversation(pinfo->fd->num, &pinfo->src, &pinfo->dst, pinfo->ptype, pinfo->srcport, pinfo->destport, 0);

	if (NULL != current_conversation)
	{
		conversation_data = (rtmpt_conversation_data_t*)conversation_get_proto_data(current_conversation, proto_rtmpt);
		if (NULL == conversation_data)
		{
			conversation_data = se_alloc(sizeof(rtmpt_conversation_data_t));
			memset((void*)conversation_data, 0, sizeof(rtmpt_conversation_data_t));
			conversation_add_proto_data(current_conversation, proto_rtmpt, conversation_data);
			conversation_data->current_chunks = g_hash_table_new(g_direct_hash, g_direct_equal);
			conversation_data->previous_frame_number = -1;
			conversation_data->current_chunk_size = RTMPT_DEFAULT_CHUNK_SIZE;
			conversation_data->is_rtmpe = 0;
		}

		packet_data = p_get_proto_data(pinfo->fd, proto_rtmpt);
		if (NULL == packet_data)
		{
			packet_data = se_alloc(sizeof(rtmpt_packet_data_t));
			memset((void*)packet_data, 0, sizeof(rtmpt_packet_data_t));
			p_add_proto_data(pinfo->fd, proto_rtmpt, packet_data);
			packet_data->initial_chunks = g_hash_table_new(g_direct_hash, g_direct_equal);
			packet_data->initial_chunk_size = conversation_data->current_chunk_size;
		}


		if (conversation_data->is_rtmpe == 1)
		{
			col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTMPE");
			return;
		}
		else
		{
			col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTMP");
		}

		if (conversation_data->previous_frame_number != (guint) pinfo->fd->num)
		{
			conversation_data->current_chunk_size = packet_data->initial_chunk_size;
		}

		col_set_writable(pinfo->cinfo, TRUE);
		col_clear(pinfo->cinfo, COL_INFO);

		conversation_data->previous_frame_number = pinfo->fd->num;
		if (tvb_length_remaining(tvb, offset) >= 1)
		{
			if (tcpinfo->lastackseq == RTMPT_HANDSHAKE_OFFSET_1 && tcpinfo->seq == RTMPT_HANDSHAKE_OFFSET_1)
			{
				iCommand =  RTMPT_TYPE_HANDSHAKE_1;
			}
			else if (tcpinfo->lastackseq == RTMPT_HANDSHAKE_OFFSET_2 && tcpinfo->seq == RTMPT_HANDSHAKE_OFFSET_1) iCommand =  RTMPT_TYPE_HANDSHAKE_2;
			else if (tcpinfo->seq == RTMPT_HANDSHAKE_OFFSET_2
			         && tvb_length(tvb) == RTMPT_HANDSHAKE_LENGTH_3) iCommand = RTMPT_TYPE_HANDSHAKE_3;
			else
			{
				iID = tvb_get_guint8(tvb, offset + 0);
				iHeaderType = iID >> 6;
				rtmp_index = iID & 0x3F;

				current_chunk_data = g_hash_table_lookup(conversation_data->current_chunks, GUINT_TO_POINTER(rtmp_index));
				initial_chunk_data = g_hash_table_lookup(packet_data->initial_chunks, GUINT_TO_POINTER(rtmp_index));

				if (iHeaderType <= 2) iLength = tvb_get_ntoh24(tvb, offset + 4);
				if (iHeaderType <= 1)
				{
					iCommand = tvb_get_guint8(tvb, offset + 7);
					if (NULL == current_chunk_data)
					{
						current_chunk_data = se_alloc(sizeof(rtmpt_chunk_data_t));
						memset((void*)current_chunk_data, 0, sizeof(rtmpt_chunk_data_t));
						g_hash_table_insert(conversation_data->current_chunks, GUINT_TO_POINTER(rtmp_index), current_chunk_data);
					}

					current_chunk_data->data_type = iCommand;
					current_chunk_data->last_length = iLength;
					current_chunk_data->frame_modified = pinfo->fd->num;
				}
				else
				{
					/* must get the command type from the previous entries in the hash table */
					/* try to use the current_chunk_data unless it is from a different frame */
					if (NULL != current_chunk_data && NULL != initial_chunk_data)
					{
						/* we have precedent data (we should)*/
						if (current_chunk_data->frame_modified != pinfo->fd->num)
						{
							iCommand = initial_chunk_data->data_type;
							iLength = initial_chunk_data->length_remaining;
							current_chunk_data->frame_modified = pinfo->fd->num;
							current_chunk_data->data_type = iCommand;
							current_chunk_data->last_length = iLength;
							current_chunk_data->dechunk_buffer = initial_chunk_data->dechunk_buffer;
						}
						else
						{
							iCommand = current_chunk_data->data_type;
							iLength = current_chunk_data->length_remaining;
						}

						if (iLength > conversation_data->current_chunk_size)
						{
							iLength = conversation_data->current_chunk_size;
						}
					}
				}
			}

			iHeaderLength = rtmpt_header_length_from_type(iHeaderType);


			if (check_col(pinfo->cinfo, COL_INFO))
			{
				col_append_sep_fstr(pinfo->cinfo, COL_INFO, " | ", "%s", val_to_str(iCommand, rtmpt_opcode_vals, "Unknown (0x%01x)"));
				col_set_fence(pinfo->cinfo, COL_INFO);
			}

			if (tree)
			{
				ti = proto_tree_add_item(tree, proto_rtmpt, tvb, offset, -1, FALSE);
				proto_item_append_text(ti, " (%s)", val_to_str(iCommand, rtmpt_opcode_vals, "Unknown (0x%01x)"));
				rtmptroot_tree = proto_item_add_subtree(ti, ett_rtmpt);

				ti = proto_tree_add_text(rtmptroot_tree, tvb, offset, iHeaderLength, RTMPT_TEXT_RTMP_HEADER);
				proto_item_append_text(ti, " (%s)", val_to_str(iCommand, rtmpt_opcode_vals, "Unknown (0x%01x)"));
				rtmpt_tree = proto_item_add_subtree(ti, ett_rtmpt_header);

				if (iHeaderType <= 3) proto_tree_add_item(rtmpt_tree, hf_rtmpt_header_objid, tvb, offset + 0, 1, FALSE);
				if (iHeaderType <= 2) proto_tree_add_item(rtmpt_tree, hf_rtmpt_header_timestamp, tvb, offset + 1, 3, FALSE);
				if (iHeaderType <= 1) proto_tree_add_item(rtmpt_tree, hf_rtmpt_header_body_size, tvb, offset + 4, 3, FALSE);
				if (iHeaderType <= 1) proto_tree_add_item(rtmpt_tree, hf_rtmpt_header_function, tvb, offset + 7, 1, FALSE);
				if (iHeaderType <= 0) proto_tree_add_item(rtmpt_tree, hf_rtmpt_header_source, tvb, offset + 8, 4, TRUE);

				if (iCommand == RTMPT_TYPE_HANDSHAKE_1)
				{
					proto_tree_add_item(rtmpt_tree, hf_rtmpt_handshake_data, tvb, 1, 1536, FALSE);
				}
				else if (iCommand == RTMPT_TYPE_HANDSHAKE_2)
				{
					proto_tree_add_item(rtmpt_tree, hf_rtmpt_handshake_data, tvb, 1, 1536, FALSE);
					proto_tree_add_item(rtmpt_tree, hf_rtmpt_handshake_data, tvb, 1537, 1536, FALSE);
				}
				else if (iCommand == RTMPT_TYPE_HANDSHAKE_3)
				{
					proto_tree_add_item(rtmpt_tree, hf_rtmpt_handshake_data, tvb, 0, -1, FALSE);
				}
				else if (iCommand == RTMPT_TYPE_CHUNK_SIZE)
				{
					conversation_data->current_chunk_size = tvb_get_ntohl (tvb, offset + iHeaderLength);
				}

				offset = iHeaderLength;
				if (tvb_length_remaining(tvb, offset))
				{
					ti = proto_tree_add_text(rtmptroot_tree, tvb, offset, -1, RTMPT_TEXT_RTMP_BODY);
				}


				if (iCommand == RTMPT_TYPE_INVOKE || iCommand == RTMPT_TYPE_NOTIFY)
				{
					guint iChunkSize = tvb_length_remaining(tvb, iHeaderLength);
					/* we have data which will be AMF */
					/* we should add it to a new tvb */
					if (NULL != current_chunk_data)
					{
						if (NULL == current_chunk_data->dechunk_buffer)
						{
							/* we have to create a new tvbuffer */
							current_chunk_data->dechunk_buffer = tvb_new_composite();
						}
						if (!(current_chunk_data->dechunk_buffer->initialized))
						{
							/* add the existing data to the new buffer */
							tvb_composite_append(current_chunk_data->dechunk_buffer,
							                     tvb_new_real_data(tvb_memdup(tvb, iHeaderLength, iChunkSize), iChunkSize, iChunkSize));

							if (current_chunk_data->length_remaining <= 0)
							{
								guint amf_length;
								guint8* amf_data;

								tvb_composite_finalize(current_chunk_data->dechunk_buffer);

								amf_length = tvb_length(current_chunk_data->dechunk_buffer);

								if (amf_length == 0)
								{
									return;
								}


								amf_data = tvb_memdup(current_chunk_data->dechunk_buffer, 0, amf_length);

								amf_tvb = tvb_new_real_data(amf_data, tvb_length_remaining(current_chunk_data->dechunk_buffer, 0), tvb_length_remaining(current_chunk_data->dechunk_buffer, 0));

								add_new_data_source(pinfo, amf_tvb, "Dechunked AMF data");
								ti = proto_tree_add_item(tree, proto_rtmpt, amf_tvb, 0, -1, FALSE);
								rtmpt_tree = proto_item_add_subtree(ti, ett_rtmpt_body);
								proto_tree_set_appendix(rtmpt_tree, amf_tvb, 0, tvb_length_remaining(amf_tvb, 0));
								proto_item_append_text(rtmpt_tree, " (%s)", "AMF Data");
								dissect_rtmpt_amf(amf_tvb, rtmpt_tree);
								current_chunk_data->dechunk_buffer = NULL;
							}
						}
					}
				}
			}
		}
	}
示例#20
0
static int
dissect_text_lines(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
{
	proto_tree	*subtree;
	proto_item	*ti;
	gint		offset = 0, next_offset;
	gint		len;
	http_message_info_t *message_info;
	const char	*data_name;
	int length = tvb_captured_length(tvb);

	/* Check if this is actually xml
	 * If there is less than 38 characters this is not XML
	 * <?xml version="1.0" encoding="UTF-8"?>
	 */
	if(length > 38){
		if (tvb_strncaseeql(tvb, 0, "<?xml", 5) == 0){
			call_dissector(xml_handle, tvb, pinfo, tree);
			return length;
		}
	}

	data_name = pinfo->match_string;
	if (! (data_name && data_name[0])) {
		/*
		 * No information from "match_string"
		 */
		message_info = (http_message_info_t *)data;
		if (message_info == NULL) {
			/*
			 * No information from dissector data
			 */
			data_name = NULL;
		} else {
			data_name = message_info->media_str;
			if (! (data_name && data_name[0])) {
				/*
				 * No information from dissector data
				 */
				data_name = NULL;
			}
		}
	}

	if (data_name)
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s)",
				data_name);

	if (tree) {
		guint lines_read = 0;
		ti = proto_tree_add_item(tree, proto_text_lines,
				tvb, 0, -1, ENC_NA);
		if (data_name)
			proto_item_append_text(ti, ": %s", data_name);
		subtree = proto_item_add_subtree(ti, ett_text_lines);
		/* Read the media line by line */
		while (tvb_offset_exists(tvb, offset)) {
			/*
			 * XXX - we need to be passed the parameters
			 * of the content type via data parameter,
			 * so that we know the character set.  We'd
			 * have to handle that character set, which
			 * might be a multibyte character set such
			 * as "iso-10646-ucs-2", or might require other
			 * special processing.
			 */
			len = tvb_find_line_end(tvb, offset, -1, &next_offset, FALSE);
			if (len == -1)
				break;

			/* We use next_offset - offset instead of len in the
			 * call to proto_tree_add_format_text() so it will include the
			 * line terminator(s) (\r and/or \n) in the display.
			 */
			proto_tree_add_format_text(subtree, tvb, offset, next_offset - offset);
			lines_read++;
			offset = next_offset;
		}
		proto_item_append_text(subtree, " (%u lines)", lines_read);
	}

	return length;
}
示例#21
0
static int
dissect_iso7816_atr(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    gint        offset=0;
    guint       i=0;  /* loop index for TA(i)...TD(i) */
    proto_item *td_it;
    proto_tree *td_tree=NULL;
    guint8      ta, tb, tc, td, k=0;
    gint        tck_len;
    proto_item *err_it;

    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "ATR sequence");

    /* ISO 7816-4, section 4 indicates that concatenations are big endian */
    proto_tree_add_item(tree, hf_iso7816_atr_init_char,
            tvb, offset, 1, ENC_BIG_ENDIAN);
    offset++;

    do {
        /* for i==0, this is the T0 byte, otherwise it's the TD(i) byte
           in each loop, we dissect T0/TD(i) and TA(i+1), TB(i+1), TC(i+1) */
        td = tvb_get_guint8(tvb, offset);
        if (i==0) {
            td_it = proto_tree_add_item(tree, hf_iso7816_atr_t0,
                    tvb, offset, 1, ENC_BIG_ENDIAN);
        }
        else {
            td_it = proto_tree_add_uint_format(tree, hf_iso7816_atr_td,
                    tvb, offset, 1, td,
                    "Interface character TD(%d): 0x%02x", i, td);
        }
        td_tree = proto_item_add_subtree(td_it, ett_iso7816_atr_td);

        proto_tree_add_boolean_format(td_tree, hf_iso7816_atr_next_ta_present,
                tvb, offset, 1, td&0x10,
                "TA(%d) present: %s", i+1, td&0x10 ? "True" : "False");
        proto_tree_add_boolean_format(td_tree, hf_iso7816_atr_next_tb_present,
                tvb, offset, 1, td&0x20,
                "TB(%d) present: %s", i+1, td&0x20 ? "True" : "False");
        proto_tree_add_boolean_format(td_tree, hf_iso7816_atr_next_tc_present,
                tvb, offset, 1, td&0x40,
                "TC(%d) present: %s", i+1, td&0x40 ? "True" : "False");
        proto_tree_add_boolean_format(td_tree, hf_iso7816_atr_next_td_present,
                tvb, offset, 1, td&0x80,
                "TD(%d) present: %s", i+1, td&0x80 ? "True" : "False");

        if (i==0) {
            k = td&0x0F;   /* number of historical bytes */
            proto_tree_add_item(td_tree, hf_iso7816_atr_k,
                    tvb, offset, 1, ENC_BIG_ENDIAN);
        }
        else {
            proto_tree_add_item(td_tree, hf_iso7816_atr_t,
                    tvb, offset, 1, ENC_BIG_ENDIAN);
        }
        offset++;

        if (td&0x10) {
            ta = tvb_get_guint8(tvb, offset);
            /* we read TA(i+1), see comment above */
            proto_tree_add_uint_format(tree, hf_iso7816_atr_ta, tvb, offset, 1,
                    ta, "Interface character TA(%d): 0x%02x", i+1, ta);
            offset++;
        }
        if (td&0x20) {
            tb = tvb_get_guint8(tvb, offset);
            proto_tree_add_uint_format(tree, hf_iso7816_atr_tb, tvb, offset, 1,
                    tb, "Interface character TB(%d): 0x%02x", i+1, tb);
            offset++;
        }
        if (td&0x40) {
            tc = tvb_get_guint8(tvb, offset);
            proto_tree_add_uint_format(tree, hf_iso7816_atr_tc, tvb, offset, 1,
                    tc, "Interface character TC(%d): 0x%02x", i+1, tc);
            offset++;
        }

        i++;
    } while (td&0x80);

    if (k>0) {
        proto_tree_add_item(tree, hf_iso7816_atr_hist_bytes,
                tvb, offset, k, ENC_NA);
        offset += k;
    }

    tck_len = tvb_reported_length_remaining(tvb, offset);
    /* tck is either absent or exactly one byte */
    if (tck_len==1) {
        proto_tree_add_item(tree, hf_iso7816_atr_tck,
                tvb, offset, 1, ENC_BIG_ENDIAN);
        offset++;
    }
    else if (tck_len>1) {
        err_it = proto_tree_add_text(tree, tvb, offset, tck_len,
                "Invalid TCK byte");
        expert_add_info_format(pinfo, err_it, PI_PROTOCOL, PI_WARN,
                "TCK byte must either be absent or exactly one byte");
    }

    return offset;
}
示例#22
0
static int
dissect_text_lines(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data)
{
	proto_tree	*subtree;
	proto_item	*ti;
	gint		offset = 0, next_offset;
	gint		len;
	const char	*data_name;
	guint8		word[6];
	int length = tvb_length(tvb);

	/* Check if this is actually xml
	 * If there is less than 38 characters this is not XML
	 * <?xml version="1.0" encoding="UTF-8"?>
	 */
	if(length > 38){
		tvb_get_nstringz0(tvb, 0, sizeof(word),word);
		if (g_ascii_strncasecmp(word, "<?xml", 5) == 0){
			call_dissector(xml_handle, tvb, pinfo, tree);
			return tvb_length(tvb);
		}
	}

	data_name = pinfo->match_string;
	if (! (data_name && data_name[0])) {
		/*
		 * No information from "match_string"
		 */
		data_name = (char *)data;
		if (! (data_name && data_name[0])) {
			/*
			 * No information from dissector data
			 */
			data_name = (char *)(pinfo->private_data);
			if (! (data_name && data_name[0])) {
				/*
				 * No information from "private_data"
				 */
				data_name = NULL;
			}
		}
	}

	if (data_name)
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s)",
				data_name);

	if (tree) {
		ti = proto_tree_add_item(tree, proto_text_lines,
				tvb, 0, -1, ENC_NA);
		if (data_name)
			proto_item_append_text(ti, ": %s", data_name);
		subtree = proto_item_add_subtree(ti, ett_text_lines);
		/* Read the media line by line */
		while (tvb_reported_length_remaining(tvb, offset) != 0) {
			/*
			 * XXX - we need to be passed the parameters
			 * of the content type via "pinfo->private_data",
			 * so that we know the character set.  We'd
			 * have to handle that character set, which
			 * might be a multibyte character set such
			 * as "iso-10646-ucs-2", or might require other
			 * special processing.
			 */
			len = tvb_find_line_end(tvb, offset,
					tvb_ensure_length_remaining(tvb, offset),
					&next_offset, FALSE);
			if (len == -1)
				break;

			/* We use next_offset - offset instead of len in the
			 * call to tvb_format_text() so it will include the
			 * line terminator(s) (\r and/or \n) in the display.
			 */
			proto_tree_add_text(subtree, tvb, offset, next_offset - offset,
					    "%s", tvb_format_text(tvb, offset,
								  next_offset - offset));
			offset = next_offset;
		}
	}

	return tvb_length(tvb);
}
示例#23
0
static int
ssh_dissect_ssh1(tvbuff_t *tvb, packet_info *pinfo,
		struct ssh_flow_data *global_data,
		int offset, proto_tree *tree, int is_response,
		gboolean *need_desegmentation)
{
	guint 	plen, padding_length, len;
	guint8 	msg_code;
	guint	remain_length;

	proto_item *ssh1_tree;

	struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];

	ssh1_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_ssh1, NULL, "SSH Version 1");

	/*
	 * We use "tvb_ensure_length_remaining()" to make sure there
	 * actually *is* data remaining.
	 *
	 * This means we're guaranteed that "remain_length" is positive.
	 */
	remain_length = tvb_ensure_length_remaining(tvb, offset);
	/*
	 * Can we do reassembly?
	 */
	if (ssh_desegment && pinfo->can_desegment) {
		/*
		 * Yes - would an SSH header starting at this offset be split
		 * across segment boundaries?
		 */
		if (remain_length < 4) {
			/*
			 * Yes.  Tell the TCP dissector where the data for
			 * this message starts in the data it handed us and
			 * that we need "some more data."  Don't tell it
			 * exactly how many bytes we need because if/when we
			 * ask for even more (after the header) that will
			 * break reassembly.
			 */
			pinfo->desegment_offset = offset;
			pinfo->desegment_len = DESEGMENT_ONE_MORE_SEGMENT;
			*need_desegmentation = TRUE;
			return offset;
		}
	}
	plen = tvb_get_ntohl(tvb, offset) ;
	padding_length  = 8 - plen%8;


	if (ssh_desegment && pinfo->can_desegment) {
		if (plen+4+padding_length >  remain_length) {
			pinfo->desegment_offset = offset;
			pinfo->desegment_len = plen+padding_length - remain_length;
			*need_desegmentation = TRUE;
			return offset;
		}
	}

	if (plen >= 0xffff) {
		if (ssh1_tree && plen > 0) {
			  proto_tree_add_uint_format(ssh1_tree, hf_ssh_packet_length, tvb,
			    offset, 4, plen, "Overly large length %x", plen);
		}
		plen = remain_length-4-padding_length;
	} else {
		if (ssh1_tree && plen > 0) {
			  proto_tree_add_uint(ssh1_tree, hf_ssh_packet_length, tvb,
			    offset, 4, plen);
		}
	}
	offset+=4;
/* padding length */

	if (tree) {
		  proto_tree_add_uint(ssh1_tree, hf_ssh_padding_length, tvb,
		    offset, padding_length, padding_length);
	}
	offset += padding_length;

	/* msg_code */
	if ((peer_data->frame_key_start == 0) ||
		((peer_data->frame_key_start >= pinfo->fd->num) && (pinfo->fd->num <= peer_data->frame_key_end))) {
		msg_code = tvb_get_guint8(tvb, offset);

		proto_tree_add_item(ssh1_tree, hf_ssh_msg_code, tvb, offset, 1, ENC_NA);
		col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
			val_to_str(msg_code, ssh1_msg_vals, "Unknown (%u)"));
		offset += 1;
		len = plen -1;
		if (!pinfo->fd->flags.visited) {
			if (peer_data->frame_key_start == 0)
				peer_data->frame_key_start = pinfo->fd->num;
			peer_data->frame_key_end = pinfo->fd->num;
		}
	} else {
		len = plen;
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Encrypted packet (len=%d)", len);
	}
	/* payload */
	if (ssh1_tree) {
		proto_tree_add_item(ssh1_tree, hf_ssh_payload,
		    tvb, offset, len, ENC_NA);
	}
	offset+=len;

	return offset;
}
示例#24
0
static int
ssh_dissect_protocol(tvbuff_t *tvb, packet_info *pinfo,
		struct ssh_flow_data *global_data,
		int offset, proto_tree *tree, int is_response, guint * version,
		gboolean *need_desegmentation)
{
	guint	remain_length;
	gint	linelen, protolen;

	/*
	 *  If the first packet do not contain the banner,
	 *  it is dump in the middle of a flow or not a ssh at all
	 */
	if (tvb_strncaseeql(tvb, offset, "SSH-", 4) != 0) {
		offset = ssh_dissect_encrypted_packet(tvb, pinfo,
			&global_data->peer_data[is_response], offset, tree);
		return offset;
	}

	if (!is_response) {
		if (tvb_strncaseeql(tvb, offset, "SSH-2.", 6) == 0) {
			*(version) = SSH_VERSION_2;
		} else if (tvb_strncaseeql(tvb, offset, "SSH-1.99-", 9) == 0) {
			*(version) = SSH_VERSION_2;
		} else if (tvb_strncaseeql(tvb, offset, "SSH-1.", 6) == 0) {
			*(version) = SSH_VERSION_1;
		}
	}

	/*
	 * We use "tvb_ensure_length_remaining()" to make sure there
	 * actually *is* data remaining.
	 *
	 * This means we're guaranteed that "remain_length" is positive.
	 */
	remain_length = tvb_ensure_length_remaining(tvb, offset);
	/*linelen = tvb_find_line_end(tvb, offset, -1, &next_offset, FALSE);
	 */
	linelen = tvb_find_guint8(tvb, offset, -1, '\n');

	if (ssh_desegment && pinfo->can_desegment) {
		if (linelen == -1 || remain_length < (guint)linelen-offset) {
			pinfo->desegment_offset = offset;
			pinfo->desegment_len = linelen-remain_length;
			*need_desegmentation = TRUE;
			return offset;
		}
	}
	if (linelen == -1) {
		/* XXX - reassemble across segment boundaries? */
		linelen = remain_length;
		protolen = linelen;
	} else {
		linelen = linelen - offset + 1;

		if (linelen > 1 && tvb_get_guint8(tvb, offset + linelen - 2) == '\r')
			protolen = linelen - 2;
		else
			protolen = linelen - 1;
	}

	col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Protocol (%s)",
			tvb_format_text(tvb, offset, protolen));

	proto_tree_add_item(tree, hf_ssh_protocol,
					tvb, offset, linelen, ENC_ASCII|ENC_NA);
	offset+=linelen;
	return offset;
}
示例#25
0
static void
dissect_fefd(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    proto_item *ti;
    proto_tree *fefd_tree = NULL;
    int offset = 0;
    guint16 type;
    guint16 length;
    proto_item *tlvi;
    proto_tree *tlv_tree;
    int real_length;

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

    if (tree) {
	proto_item *flags_ti;
	proto_tree *flags_tree;

	ti = proto_tree_add_item(tree, proto_fefd, tvb, offset, -1, FALSE);
	fefd_tree = proto_item_add_subtree(ti, ett_fefd);

	/* FEFD header */
	proto_tree_add_item(fefd_tree, hf_fefd_version, tvb, offset, 1, FALSE);
	proto_tree_add_item(fefd_tree, hf_fefd_opcode, tvb, offset, 1, FALSE);
	offset += 1;
	flags_ti = proto_tree_add_item(fefd_tree, hf_fefd_flags, tvb, offset, 1, FALSE);
	flags_tree = proto_item_add_subtree(ti, ett_fefd_flags);
	proto_tree_add_item(flags_tree, hf_fefd_flags_rt, tvb, offset, 1, FALSE);
	proto_tree_add_item(flags_tree, hf_fefd_flags_rsy, tvb, offset, 1, FALSE);
	offset += 1;
	proto_tree_add_item(fefd_tree, hf_fefd_checksum, tvb, offset, 2, FALSE);
	offset += 2;
    } else {
	offset += 4; /* The version/opcode/flags/checksum fields from above */
    }

	while (tvb_reported_length_remaining(tvb, offset) != 0) {
	    type = tvb_get_ntohs(tvb, offset + TLV_TYPE);
	    length = tvb_get_ntohs(tvb, offset + TLV_LENGTH);
	    if (length < 4) {
		if (tree) {
		    tlvi = proto_tree_add_text(fefd_tree, tvb, offset, 4,
			"TLV with invalid length %u (< 4)",
			length);
		    tlv_tree = proto_item_add_subtree(tlvi, ett_fefd_tlv);
		    proto_tree_add_uint(tlv_tree, hf_fefd_tlvtype, tvb,
				offset + TLV_TYPE, 2, type);
		    proto_tree_add_uint(tlv_tree, hf_fefd_tlvlength, tvb,
				offset + TLV_LENGTH, 2, length);
		}
		offset += 4;
		break;
	    }

	    switch (type) {

	    case TYPE_DEVICE_ID:
		/* Device ID */

		if (check_col(pinfo->cinfo, COL_INFO))
		    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL,
				    "Device ID: %s",
				    tvb_format_stringzpad(tvb, offset + 4,
							  length - 4));

		if (tree) {
		    tlvi = proto_tree_add_text(fefd_tree, tvb, offset,
				length, "Device ID: %s",
				tvb_format_stringzpad(tvb, offset + 4, length - 4));
		    tlv_tree = proto_item_add_subtree(tlvi, ett_fefd_tlv);
		    proto_tree_add_uint(tlv_tree, hf_fefd_tlvtype, tvb,
				offset + TLV_TYPE, 2, type);
		    proto_tree_add_uint(tlv_tree, hf_fefd_tlvlength, tvb,
				offset + TLV_LENGTH, 2, length);
		    proto_tree_add_text(tlv_tree, tvb, offset + 4,
				length - 4, "Device ID: %s",
				tvb_format_stringzpad(tvb, offset + 4, length - 4));
		}
		offset += length;
		break;

	    case TYPE_PORT_ID:
		real_length = length;
		if (tvb_get_guint8(tvb, offset + real_length) != 0x00) {
		    /* The length in the TLV doesn't appear to be the
		       length of the TLV, as the byte just past it
		       isn't the first byte of a 2-byte big-endian
		       small integer; make the length of the TLV the length
		       in the TLV, plus 4 bytes for the TLV type and length,
		       minus 1 because that's what makes one capture work. */
		    real_length = length + 3;
		}

		if (check_col(pinfo->cinfo, COL_INFO))
		    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL,
				    "Port ID: %s",
				    tvb_format_stringzpad(tvb, offset + 4, real_length - 4));

		if (tree) {
		    tlvi = proto_tree_add_text(fefd_tree, tvb, offset,
			    real_length, "Port ID: %s",
			    tvb_format_text(tvb, offset + 4, real_length - 4));
		    tlv_tree = proto_item_add_subtree(tlvi, ett_fefd_tlv);
		    proto_tree_add_uint(tlv_tree, hf_fefd_tlvtype, tvb,
			    offset + TLV_TYPE, 2, type);
		    proto_tree_add_uint(tlv_tree, hf_fefd_tlvlength, tvb,
			    offset + TLV_LENGTH, 2, length);
		    proto_tree_add_text(tlv_tree, tvb, offset + 4,
			    real_length - 4,
			    "Sent through Interface: %s",
			    tvb_format_text(tvb, offset + 4, real_length - 4));
		}
		offset += real_length;
		break;

	    case TYPE_ECHO:
	    case TYPE_MESSAGE_INTERVAL:
	    case TYPE_TIMEOUT_INTERVAL:
	    case TYPE_DEVICE_NAME:
	    case TYPE_SEQUENCE_NUMBER:
	    default:
		tlvi = proto_tree_add_text(fefd_tree, tvb, offset,
			length, "Type: %s, length: %u",
			val_to_str(type, type_vals, "Unknown (0x%04x)"),
			length);
		tlv_tree = proto_item_add_subtree(tlvi, ett_fefd_tlv);
		proto_tree_add_uint(tlv_tree, hf_fefd_tlvtype, tvb,
			offset + TLV_TYPE, 2, type);
		proto_tree_add_uint(tlv_tree, hf_fefd_tlvlength, tvb,
			offset + TLV_LENGTH, 2, length);
		if (length > 4) {
			proto_tree_add_text(tlv_tree, tvb, offset + 4,
				length - 4, "Data");
		} else {
			return;
		}
		offset += length;
	    }
	}

    call_dissector(data_handle, tvb_new_subset_remaining(tvb, offset), pinfo, fefd_tree);
}
示例#26
0
static void
dissect_text_lines(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
	proto_tree	*subtree;
	proto_item	*ti;
	gint		offset = 0, next_offset;
	gint		len;
	const char	*data_name;

	data_name = pinfo->match_string;
	if (! (data_name && data_name[0])) {
		/*
		 * No information from "match_string"
		 */
		data_name = (char *)(pinfo->private_data);
		if (! (data_name && data_name[0])) {
			/*
			 * No information from "private_data"
			 */
			data_name = NULL;
		}
	}

	if (data_name && check_col(pinfo->cinfo, COL_INFO))
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s)",
				data_name);

	if (tree) {
		ti = proto_tree_add_item(tree, proto_text_lines,
				tvb, 0, -1, FALSE);
		if (data_name)
			proto_item_append_text(ti, ": %s", data_name);
		subtree = proto_item_add_subtree(ti, ett_text_lines);
		/* Read the media line by line */
		while (tvb_reported_length_remaining(tvb, offset) != 0) {
			/*
			 * XXX - we need to be passed the parameters
			 * of the content type via "pinfo->private_data",
			 * so that we know the character set.  We'd
			 * have to handle that character set, which
			 * might be a multibyte character set such
			 * as "iso-10646-ucs-2", or might require other
			 * special processing.
			 */
			len = tvb_find_line_end(tvb, offset,
					tvb_ensure_length_remaining(tvb, offset),
					&next_offset, FALSE);
			if (len == -1)
				break;

			/* We use next_offset - offset instead of len in the
			 * call to tvb_format_text() so it will include the
			 * line terminator(s) (\r and/or \n) in the display.
			 */
			proto_tree_add_text(subtree, tvb, offset, next_offset - offset,
					    "%s", tvb_format_text(tvb, offset,
								  next_offset - offset));
			offset = next_offset;
		}
	}
}
示例#27
0
static void
dissect_http2_frame_pdu(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree )
{
        proto_item *ti;
        proto_tree *http2_tree;
        guint32 offset = 0;
    
        http2_frame_header frame;

        /* tvb_memeql makes certain there are enough bytes in the buffer.
         * returns -1 if there are not enough bytes or if there is not a
         * match.  Returns 0 on a match */
        if ( tvb_memeql( tvb, offset, kMagicHello, MAGIC_FRAME_LENGTH ) == 0 )
        {
                col_append_sep_str( pinfo->cinfo, COL_INFO, ", ", "Magic" );
                
                ti = proto_tree_add_item(tree, proto_http2, tvb, offset, MAGIC_FRAME_LENGTH, ENC_NA);
                proto_item_append_text( ti, ", Magic" );
                
                http2_tree = proto_item_add_subtree(ti, ett_http2);
                
                proto_tree_add_item(http2_tree, hf_http2_magic, tvb,
                                    offset, MAGIC_FRAME_LENGTH, ENC_BIG_ENDIAN);
                return;
        }


        frame.length   = tvb_get_ntohs( tvb, offset + 0 );
        frame.type     = tvb_get_guint8( tvb, offset + 2 );
        frame.flags    = tvb_get_guint8( tvb, offset + 3 );
        frame.streamid = tvb_get_ntohl( tvb, offset + 4 );

        col_append_sep_fstr( pinfo->cinfo, COL_INFO, ", ", "%s",
                             val_to_str( frame.type, frametypenames, "Unknown (0x%02X)" ) );

    
        /* create display subtree for the protocol */
        ti = proto_tree_add_item(tree, proto_http2, tvb, offset, FRAME_HEADER_LENGTH + frame.length, ENC_NA);

        proto_item_append_text( ti, ", %s", val_to_str( frame.type, frametypenames, "Unknown (0x%02X)" ) );
        proto_item_append_text( ti, ", Length: %d, Flags: %d, streamid: %d",
                                frame.length, frame.flags, frame.streamid );
    
        http2_tree = proto_item_add_subtree(ti, ett_http2);

        /* Add an item to the subtree, see section 1.6 of README.developer for more
         * information. */
        proto_tree_add_item(http2_tree, hf_http2_length, tvb,
                            offset + 0, 2, ENC_BIG_ENDIAN);
        proto_tree_add_item(http2_tree, hf_http2_type, tvb,
                            offset + 2, 1, ENC_BIG_ENDIAN);
        proto_tree_add_item(http2_tree, hf_http2_flags, tvb,
                            offset + 3, 1, ENC_BIG_ENDIAN);
        proto_tree_add_item(http2_tree, hf_http2_streamid, tvb,
                            offset + 4, 4, ENC_BIG_ENDIAN);
        proto_tree_add_item(http2_tree, hf_http2_payload, tvb,
                            offset + 8, frame.length, ENC_BIG_ENDIAN);

        offset += frame.length + FRAME_HEADER_LENGTH;

        return;
}
static int
dissect_dlm_controld(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree,
		     const gchar* col_str)
{
  guint length;
  int offset;

  proto_tree *dlm_controld_tree, *tree, *version_tree;
  proto_item *item, *version_item;
  guint32 type;

  length = tvb_length(tvb);
  if ( length < ( 2 * 3 ) + 2 + 4 + 4 + 4 + 4 + 4 + 4 + 8)
    return 0;

  type = tvb_get_letohs(tvb, ( 2 * 3 ));
  if (check_col(pinfo->cinfo, COL_INFO))
    col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s :%s)", 
			  col_str, val_to_str(type, vals_header_type, "UNKNOWN-TYPE"));

  if (!parent_tree)
    goto out;

  offset = 0;
  item = proto_tree_add_item(parent_tree, proto_dlm_controld, tvb, 
			     offset, -1, TRUE);
  dlm_controld_tree = proto_item_add_subtree(item, ett_dlm_controld);

  offset += 0;
  item = proto_tree_add_item(dlm_controld_tree, hf_dlm_controld_header, tvb, 
			     offset, -1, TRUE);
  tree = proto_item_add_subtree(item, ett_dlm_controld_header);

  offset += 0;
  version_item = proto_tree_add_item(tree, 
				     hf_dlm_controld_header_version, 
				     tvb, offset, -1, TRUE);
  version_tree = proto_item_add_subtree(version_item, 
					ett_dlm_controld_header_version);

  offset += 0;
  proto_tree_add_item(version_tree, hf_dlm_controld_header_version_major, 
		      tvb, offset, 2, TRUE);

  offset += 2;
  proto_tree_add_item(version_tree, hf_dlm_controld_header_version_minor, 
		      tvb, offset, 2, TRUE);

  offset += 2;
  proto_tree_add_item(version_tree, hf_dlm_controld_header_version_patch, 
		      tvb, offset, 2, TRUE);

  offset += 2;
  type = tvb_get_letohs(tvb, offset);
  proto_tree_add_item(tree, hf_dlm_controld_header_type, 
		      tvb, offset, 2, TRUE);

  offset += 2;
  proto_tree_add_item(tree, hf_dlm_controld_header_nodeid, 
		      tvb, offset, 4, TRUE);

  offset += 4;
  proto_tree_add_item(tree, hf_dlm_controld_header_to_nodeid, 
		      tvb, offset, 4, TRUE);

  offset += 4;
  proto_tree_add_item(tree, hf_dlm_controld_header_global_id, 
		      tvb, offset, 4, TRUE);

  offset += 4;
  proto_tree_add_bitmask(tree, tvb, offset, hf_dlm_controld_header_flags, 
			 ett_dlm_controld_header_flags, header_flags_fields,
			 TRUE);

  offset += 4;
  switch (type)
    {
    default:
      proto_tree_add_item(tree, hf_dlm_controld_header_msgdata, 
			  tvb, offset, 4, TRUE);
      break;
    }

  offset += 4;
  proto_tree_add_item(tree, hf_dlm_controld_header_pad1, 
		      tvb, offset, 4, TRUE);

  offset += 4;
  proto_tree_add_item(tree, hf_dlm_controld_header_pad2, 
		      tvb, offset, 8, TRUE);

  offset += 8;
  switch (type)
    {
    case DLM_MSG_PROTOCOL:
      offset += dissect_dlm_controld_protocol(tvb, pinfo, dlm_controld_tree, offset, length);
      break;
    case DLM_MSG_START:
    case DLM_MSG_PLOCKS_STORED:
      offset += dissect_dlm_controld_start_or_plocks_stored(tvb, pinfo, dlm_controld_tree, offset, length);
      break;
    default:
      break;
    }
 out:
  return offset;
}
示例#29
0
/* The dissector itself */
static void dissect_chdr(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
    // Here are all the variables
    proto_item *item;
    proto_item *stream_item;
    proto_tree *chdr_tree;
    proto_tree *stream_tree;
    gint len;

    gint flag_offset;
    guint8 *bytes;
    gboolean flag_has_time;
    guint64 timestamp;
    gboolean is_network;
    gint endianness;
    gint id_pos_usb[4] = {7, 6, 5, 4};
    gint id_pos_net[4] = {4, 5, 6, 7};
    gint id_pos[4] = {7, 6, 5, 4};

    if(pinfo->match_uint == CHDR_PORT) {
        is_network = TRUE;
        flag_offset = 0;
        endianness = ENC_BIG_ENDIAN;
        memcpy(id_pos, id_pos_net, 4 * sizeof(gint));
    }
    else {
        is_network = FALSE;
        flag_offset = 3;
        endianness = ENC_LITTLE_ENDIAN;
        memcpy(id_pos, id_pos_usb, 4 * sizeof(gint));
    }

    len = tvb_reported_length(tvb);

    col_append_str(pinfo->cinfo, COL_PROTOCOL, "/CHDR");
    col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "CHDR",
                        tvb_format_text_wsp(tvb, 0, len));

    if (tree) {
        /* Start with a top-level item to add everything else to */
        item = proto_tree_add_item(tree, proto_chdr, tvb, 0, 16, ENC_NA);
        chdr_tree = proto_item_add_subtree(item, ett_chdr);

        bytes = tvb_get_string(tvb, 0, 4);
        flag_has_time = bytes[flag_offset] & 0x20;

        /* These lines add flag info to tree */
        proto_tree_add_item(chdr_tree, hf_chdr_is_extension, tvb, flag_offset, 1, ENC_NA);
        proto_tree_add_item(chdr_tree, hf_chdr_reserved, tvb, flag_offset, 1, ENC_NA);
        proto_tree_add_item(chdr_tree, hf_chdr_has_time, tvb, flag_offset, 1, ENC_NA);
        proto_tree_add_item(chdr_tree, hf_chdr_eob, tvb, flag_offset, 1, ENC_NA);

        /* These lines add sequence, packet_size and stream ID */
        proto_tree_add_item(chdr_tree, hf_chdr_sequence, tvb, is_network ? 0:2, 2, endianness);
        proto_tree_add_item(chdr_tree, hf_chdr_packet_size, tvb, is_network ? 2:0, 2, endianness);

        /* stream id can be broken down to 4 sections. these are collapsed in a subtree */
        stream_item = proto_tree_add_item(chdr_tree, hf_chdr_stream_id, tvb, 4, 4, endianness);
        stream_tree = proto_item_add_subtree(stream_item, ett_chdr_id);
        proto_tree_add_item(stream_tree, hf_chdr_src_dev, tvb, id_pos[0], 1, ENC_NA);
        proto_tree_add_item(stream_tree, hf_chdr_src_ep, tvb, id_pos[1], 1, ENC_NA);
        proto_tree_add_item(stream_tree, hf_chdr_dst_dev, tvb, id_pos[2], 1, ENC_NA);
        proto_tree_add_item(stream_tree, hf_chdr_dst_ep, tvb, id_pos[3], 1, ENC_NA);

        /* if has_time flag is present interpret timestamp */
        if(flag_has_time) {
            item = proto_tree_add_item(chdr_tree, hf_chdr_timestamp, tvb, 8, 8, endianness);

            if(!is_network) {
                bytes = (guint8*) tvb_get_string(tvb, 8, 8);
                timestamp = get_timestamp(bytes, 8);
            }
        }
    }
}
示例#30
0
static void
dissect_json(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
	proto_tree *json_tree = NULL;
	proto_item *ti = NULL;

	json_parser_data_t parser_data;
	tvbparse_t *tt;

	const char *data_name;
	int offset;

	data_name = pinfo->match_string;
	if (!(data_name && data_name[0])) {
		/*
		 * No information from "match_string"
		 */
		data_name = (char *)(pinfo->private_data);
		if (!(data_name && data_name[0])) {
			/*
			 * No information from "private_data"
			 */
			data_name = NULL;
		}
	}

	if (tree) {
		ti = proto_tree_add_item(tree, proto_json, tvb, 0, -1, ENC_NA);
		json_tree = proto_item_add_subtree(ti, ett_json);

		if (data_name)
			proto_item_append_text(ti, ": %s", data_name);
	}

	offset = 0;
	
	parser_data.stack = ep_stack_new();
	ep_stack_push(parser_data.stack, json_tree);

	tt = tvbparse_init(tvb, offset, -1, &parser_data, want_ignore);

	/* XXX, only one json in packet? */
	while ((tvbparse_get(tt, want)))
		;

	offset = tvbparse_curr_offset(tt);

	proto_item_set_len(ti, offset);

	/* if we have some unparsed data, pass to data-text-lines dissector (?) */
	if (tvb_length_remaining(tvb, offset) > 0) {
		int datalen, reported_datalen;
		tvbuff_t *next_tvb;
		
		datalen = tvb_length_remaining(tvb, offset);
		reported_datalen = tvb_reported_length_remaining(tvb, offset);

		next_tvb = tvb_new_subset(tvb, offset, datalen, reported_datalen);

		call_dissector(text_lines_handle, next_tvb, pinfo, tree);
	} else if (data_name) {
		col_append_sep_fstr(pinfo->cinfo, COL_INFO, " ", "(%s)", data_name);
	}
}