Exemple #1
0
static void
dissect_irc_tag_data(proto_tree *tree, proto_item *item, tvbuff_t *tvb, int offset, int datalen, packet_info *pinfo, guint8* command)
{
    guchar found_start_needle = 0,
           found_end_needle   = 0;
    gint   tag_start_offset, tag_end_offset;

    tag_start_offset = tvb_pbrk_guint8(tvb, offset, datalen, TAG_DELIMITER, &found_start_needle);
    if (tag_start_offset == -1)
    {
        /* no tag data */
        return;
    }

    tag_end_offset = tvb_pbrk_guint8(tvb, offset, datalen-offset, TAG_DELIMITER, &found_end_needle);
    if (tag_end_offset == -1)
    {
        expert_add_info_format(pinfo, item, PI_MALFORMED, PI_ERROR, "Missing ending tag delimited (0x01)");
        return;
    }

    if ((strcmp(command, "NOTICE") != 0) &&
       (strcmp(command, "PRIVMSG") != 0))
    {
        expert_add_info_format(pinfo, item, PI_PROTOCOL, PI_WARN, "Tag data outside of NOTICE or PRIVMSG command");
    }

    /* Placeholder to call CTCP dissector, strip out delimiter */
    proto_tree_add_item(tree, hf_irc_ctcp, tvb, offset+1, datalen-2, ENC_ASCII|ENC_NA);
}
Exemple #2
0
static void
dissect_irc_tag_data(proto_tree *tree, proto_item *item, tvbuff_t *tvb, int offset, int datalen, packet_info *pinfo, guint8* command)
{
    guchar found_start_needle = 0,
           found_end_needle   = 0;
    gint   tag_start_offset, tag_end_offset;

    tag_start_offset = tvb_pbrk_guint8(tvb, offset, datalen, TAG_DELIMITER, &found_start_needle);
    if (tag_start_offset == -1)
    {
        /* no tag data */
        return;
    }

    tag_end_offset = tvb_pbrk_guint8(tvb, offset, datalen-offset, TAG_DELIMITER, &found_end_needle);
    if (tag_end_offset == -1)
    {
        expert_add_info(pinfo, item, &ei_irc_missing_end_delimiter);
        return;
    }

    if ((strcmp(command, "NOTICE") != 0) &&
       (strcmp(command, "PRIVMSG") != 0))
    {
        expert_add_info(pinfo, item, &ei_irc_tag_data_invalid);
    }

    /* Placeholder to call CTCP dissector, strip out delimiter */
    proto_tree_add_item(tree, hf_irc_ctcp, tvb, offset+1, datalen-2, ENC_ASCII|ENC_NA);
}
static gint
subset_pbrk_guint8(tvbuff_t *tvb, guint abs_offset, guint limit, const guint8 *needles, guchar *found_needle)
{
	struct tvb_subset *subset_tvb = (struct tvb_subset *) tvb;

	return tvb_pbrk_guint8(subset_tvb->subset.tvb, subset_tvb->subset.offset + abs_offset, limit, needles, found_needle);
}
Exemple #4
0
static gint
frame_pbrk_guint8(tvbuff_t *tvb, guint abs_offset, guint limit, const guint8 *needles, guchar *found_needle)
{
	struct tvb_frame *frame_tvb = (struct tvb_frame *) tvb;

	frame_cache(frame_tvb);

	return tvb_pbrk_guint8(tvb, abs_offset, limit, needles, found_needle);
}
static const guint8*
get_unquoted_string(tvbuff_t *tvb, gint offset, gint *next_offset, guint *len)
{
    const guint8* s = NULL;
    guint l = 0;
    gint o;

    o = tvb_pbrk_guint8(tvb, offset, -1, " \t\r\n", NULL);
    if (o != -1) {
        l = o - offset;
        s = tvb_get_ptr(tvb, offset, l);
        offset = o;
    }

    *next_offset = offset;
    *len = l;

    return s;
}
Exemple #6
0
static const guint8*
get_unquoted_string(tvbuff_t *tvb, gint offset, gint *next_offset, guint *len)
{
    const guint8* s = NULL;
    guint l = 0;
    gint o;

    o = tvb_pbrk_guint8(tvb, offset, -1, " \t\r\n", NULL);
    if (o != -1) {
        l = o - offset;
        s = tvb_get_string_enc(wmem_packet_scope(), tvb, offset, l, ENC_ASCII);
        offset = o;
    }

    *next_offset = offset;
    *len = l;

    return s;
}
Exemple #7
0
static void
dissect_irc_response(proto_tree *tree, tvbuff_t *tvb, packet_info *pinfo, int offset, int linelen)
{
    proto_tree *response_tree, *command_tree = NULL;
    proto_item *response_item, *command_item, *hidden_item;
    int         start_offset                 = offset;
    int         end_offset                   = start_offset+linelen;
    gint        eop_offset                   = -1,
                eoc_offset                   = -1,
                eocp_offset,
                tag_start_offset, tag_end_offset;
    guint8*     str_command;
    guint16     num_command;
    guchar      found_needle                 = 0,
                found_tag_needle             = 0;
    gboolean    first_command_param          = TRUE;

    response_item = proto_tree_add_item(tree, hf_irc_response, tvb, offset, linelen, ENC_ASCII|ENC_NA);
    if (linelen <= 0)
        return;

    response_tree = proto_item_add_subtree(response_item, ett_irc_response );

    /* Check if message has a prefix */
    if (tvb_get_guint8(tvb, offset) == ':')
    {
        /* find the end of the prefix */
        eop_offset = tvb_pbrk_guint8(tvb, offset+1, linelen-1, " ", &found_needle);
        if (eop_offset == -1)
        {
            expert_add_info_format(pinfo, response_item, PI_MALFORMED, PI_ERROR, "Prefix missing ending <space>");
            return;
        }

        proto_tree_add_item(response_tree, hf_irc_response_prefix, tvb, offset+1, eop_offset-offset-1, ENC_ASCII|ENC_NA);
        found_needle = 0;
        offset = eop_offset+1;
    }

    /* clear out any whitespace before command */
    while(offset < end_offset && tvb_get_guint8(tvb, offset) == ' ')
    {
        offset++;
    }
    if (offset == end_offset)
    {
        expert_add_info_format(pinfo, response_item, PI_MALFORMED, PI_ERROR, "Response has no command");
        return;
    }

    eoc_offset = tvb_pbrk_guint8(tvb, offset, end_offset-offset, " ", &found_needle);
    if (eoc_offset == -1)
    {
        proto_tree_add_item(response_tree, hf_irc_response_command, tvb, offset, end_offset-offset, ENC_ASCII|ENC_NA);
        col_append_fstr( pinfo->cinfo, COL_INFO, " (%s)", tvb_get_ephemeral_string(tvb, offset, end_offset-offset));

        /* if response command is numeric, allow it to be filtered as an integer */
        if ((end_offset-offset == 3) &&
            (isdigit(tvb_get_guint8(tvb, offset))) &&
            (isdigit(tvb_get_guint8(tvb, offset+1))) &&
            (isdigit(tvb_get_guint8(tvb, offset+2))))
        {
            num_command = ((tvb_get_guint8(tvb, offset)-0x30)*100) + ((tvb_get_guint8(tvb, offset+1)-0x30)*10) + (tvb_get_guint8(tvb, offset+2)-0x30);
            hidden_item = proto_tree_add_uint(response_tree, hf_irc_response_num_command, tvb, offset, end_offset-offset, num_command);
            PROTO_ITEM_SET_HIDDEN(hidden_item);
        }
        return;
    }

    proto_tree_add_item(response_tree, hf_irc_response_command, tvb, offset, eoc_offset-offset, ENC_ASCII|ENC_NA);
    str_command = tvb_get_ephemeral_string(tvb, offset, eoc_offset-offset);
    col_append_fstr( pinfo->cinfo, COL_INFO, " (%s)", str_command);

    /* if response command is numeric, allow it to be filtered as an integer */
    if ((eoc_offset-offset == 3) &&
       (isdigit(tvb_get_guint8(tvb, offset))) &&
       (isdigit(tvb_get_guint8(tvb, offset+1))) &&
       (isdigit(tvb_get_guint8(tvb, offset+2))))
    {
        num_command = ((tvb_get_guint8(tvb, offset)-0x30)*100) + ((tvb_get_guint8(tvb, offset+1)-0x30)*10) + (tvb_get_guint8(tvb, offset+2)-0x30);
        hidden_item = proto_tree_add_uint(response_tree, hf_irc_response_num_command, tvb, offset, eoc_offset-offset, num_command);
        PROTO_ITEM_SET_HIDDEN(hidden_item);
    }

    found_needle = 0;
    offset = eoc_offset+1;

    /* clear out any whitespace before command parameter */
    while(offset < end_offset && tvb_get_guint8(tvb, offset) == ' ')
    {
        offset++;
    }
    if (offset == end_offset)
    {
        /* No command parameters */
        return;
    }

    /* Check if message has a trailer */
    if (tvb_get_guint8(tvb, offset) == ':')
    {
        proto_tree_add_item(response_tree, hf_irc_response_trailer, tvb, offset+1, end_offset-offset-1, ENC_ASCII|ENC_NA);
        dissect_irc_tag_data(response_tree, response_item, tvb, offset+1, end_offset-offset-1, pinfo, str_command);
        return;
    }

    while(offset < end_offset)
    {
        eocp_offset = tvb_pbrk_guint8(tvb, offset, end_offset-offset, " ", &found_needle);
        tag_start_offset = tvb_pbrk_guint8(tvb, offset, end_offset-offset, TAG_DELIMITER, &found_tag_needle);

        /* Create subtree when the first parameter is found */
        if (first_command_param)
        {
            command_item = proto_tree_add_text(response_tree, tvb, offset, end_offset-offset, "Command parameters");
            command_tree = proto_item_add_subtree(command_item, ett_irc_response_command );
            first_command_param = FALSE;
        }

        if ((tag_start_offset == -1) || (eocp_offset < tag_start_offset))
        {
            /* regular message should be dissected */

            found_needle = 0;
            if (eocp_offset == -1)
            {
                proto_tree_add_item(command_tree, hf_irc_response_command_param, tvb, offset, end_offset-offset, ENC_ASCII|ENC_NA);
                return;
            }

            proto_tree_add_item(command_tree, hf_irc_response_command_param, tvb, offset, eocp_offset-offset, ENC_ASCII|ENC_NA);
            offset = eocp_offset+1;

            /* clear out any whitespace before next command parameter */
            while(offset < end_offset && tvb_get_guint8(tvb, offset) == ' ')
            {
                offset++;
            }
            if (offset == end_offset)
            {
                break;
            }

            /* Check if message has a trailer */
            if (tvb_get_guint8(tvb, offset) == ':')
            {
                proto_tree_add_item(response_tree, hf_irc_response_trailer, tvb, offset+1, end_offset-offset-1, ENC_ASCII|ENC_NA);
                dissect_irc_tag_data(response_tree, response_item, tvb, offset+1, end_offset-offset-1, pinfo, str_command);
                return;
            }
        }
        else if ((eocp_offset == -1) || (eocp_offset > tag_start_offset))
        {
            /* tag data dissected */

            found_tag_needle = 0;
            tag_end_offset = tvb_pbrk_guint8(tvb, tag_start_offset+1, end_offset-tag_start_offset-1, TAG_DELIMITER, &found_tag_needle);
            if (tag_end_offset == -1)
            {
                expert_add_info_format(pinfo, response_item, PI_MALFORMED, PI_ERROR, "Missing ending tag delimited (0x01)");
                return;
            }

            dissect_irc_tag_data(response_tree, response_item, tvb, tag_start_offset, tag_end_offset-tag_start_offset, pinfo, str_command);
            offset = tag_end_offset+1;
        }
    }
}
Exemple #8
0
static void
dissect_irc_request(proto_tree *tree, tvbuff_t *tvb, packet_info *pinfo, int offset, int linelen)
{
    proto_tree *request_tree, *command_tree = NULL;
    proto_item *request_item, *command_item;
    int         start_offset                = offset;
    int         end_offset                  = start_offset+linelen;
    gint        eop_offset                  = -1,
                eoc_offset                  = -1,
                eocp_offset,
                tag_start_offset, tag_end_offset;
    guint8*     str_command;
    guchar      found_needle                = 0,
                found_tag_needle            = 0;
    gboolean    first_command_param         = TRUE;

    request_item = proto_tree_add_item(tree, hf_irc_request, tvb, offset, linelen, ENC_ASCII|ENC_NA);
    if (linelen <= 0)
        return;

    request_tree = proto_item_add_subtree(request_item, ett_irc_request );

    /* Check if message has a prefix */
    if (tvb_get_guint8(tvb, offset) == ':')
    {
        /* find the end of the prefix */
        eop_offset = tvb_pbrk_guint8(tvb, offset+1, linelen-1, " ", &found_needle);
        if (eop_offset == -1)
        {
            expert_add_info(pinfo, request_item, &ei_irc_prefix_missing_ending_space);
            return;
        }

        proto_tree_add_item(request_tree, hf_irc_request_prefix, tvb, offset+1, eop_offset-offset-1, ENC_ASCII|ENC_NA);
        found_needle = 0;
        offset = eop_offset+1;
    }

    /* clear out any whitespace before command */
    while(offset < end_offset && tvb_get_guint8(tvb, offset) == ' ')
    {
        offset++;
    }
    if (offset == end_offset)
    {
        expert_add_info(pinfo, request_item, &ei_irc_request_command);
        return;
    }

    eoc_offset = tvb_pbrk_guint8(tvb, offset, end_offset-offset, " ", &found_needle);
    if (eoc_offset == -1)
    {
        proto_tree_add_item(request_tree, hf_irc_request_command, tvb, offset, end_offset-offset, ENC_ASCII|ENC_NA);
        col_append_fstr( pinfo->cinfo, COL_INFO, " (%s)", tvb_get_string(wmem_packet_scope(), tvb, offset, end_offset-offset));

        /* Warn if there is a "numeric" command */
        if ((end_offset-offset == 3) &&
            (isdigit(tvb_get_guint8(tvb, offset))) &&
            (isdigit(tvb_get_guint8(tvb, offset+1))) &&
            (isdigit(tvb_get_guint8(tvb, offset+2))))
        {
            expert_add_info(pinfo, request_item, &ei_irc_numeric_request_command);
        }
        return;
    }

    proto_tree_add_item(request_tree, hf_irc_request_command, tvb, offset, eoc_offset-offset, ENC_ASCII|ENC_NA);
    str_command = tvb_get_string(wmem_packet_scope(), tvb, offset, eoc_offset-offset);
    col_append_fstr( pinfo->cinfo, COL_INFO, " (%s)", str_command);

    /* Warn if there is a "numeric" command */
    if ((eoc_offset-offset == 3) &&
       (isdigit(tvb_get_guint8(tvb, offset))) &&
       (isdigit(tvb_get_guint8(tvb, offset+1))) &&
       (isdigit(tvb_get_guint8(tvb, offset+2))))
    {
        expert_add_info(pinfo, request_item, &ei_irc_numeric_request_command);
    }

    found_needle = 0;
    offset = eoc_offset+1;

    /* clear out any whitespace before command parameter */
    while(offset < end_offset && tvb_get_guint8(tvb, offset) == ' ')
    {
        offset++;
    }
    if (offset == end_offset)
    {
        /* No command parameters */
        return;
    }

    /* Check if message has a trailer */
    if (tvb_get_guint8(tvb, offset) == ':')
    {
        proto_tree_add_item(request_tree, hf_irc_request_trailer, tvb, offset+1, end_offset-offset-1, ENC_ASCII|ENC_NA);
        dissect_irc_tag_data(request_tree, request_item, tvb, offset+1, end_offset-offset-1, pinfo, str_command);
        return;
    }

    while(offset < end_offset)
    {
        eocp_offset = tvb_pbrk_guint8(tvb, offset, end_offset-offset, " ", &found_needle);
        tag_start_offset = tvb_pbrk_guint8(tvb, offset, end_offset-offset, TAG_DELIMITER, &found_tag_needle);

        /* Create subtree when the first parameter is found */
        if (first_command_param)
        {
            command_item = proto_tree_add_text(request_tree, tvb, offset, end_offset-offset, "Command parameters");
            command_tree = proto_item_add_subtree(command_item, ett_irc_request_command );
            first_command_param = FALSE;
        }

        if (((eocp_offset == -1) && (tag_start_offset == -1)) ||
            ((eocp_offset != -1) && (tag_start_offset == -1)) ||
            (eocp_offset < tag_start_offset))
        {
            /* regular message should be dissected */

            found_needle = 0;
            if (eocp_offset == -1)
            {
                proto_tree_add_item(command_tree, hf_irc_request_command_param, tvb, offset, end_offset-offset, ENC_ASCII|ENC_NA);
                return;
            }

            proto_tree_add_item(command_tree, hf_irc_request_command_param, tvb, offset, eocp_offset-offset, ENC_ASCII|ENC_NA);
            offset = eocp_offset+1;

            /* clear out any whitespace before next command parameter */
            while(offset < end_offset && tvb_get_guint8(tvb, offset) == ' ')
            {
                offset++;
            }
            if (offset == end_offset)
            {
                break;
            }

            /* Check if message has a trailer */
            if (tvb_get_guint8(tvb, offset) == ':')
            {
                proto_tree_add_item(request_tree, hf_irc_request_trailer, tvb, offset+1, end_offset-offset-1, ENC_ASCII|ENC_NA);
                dissect_irc_tag_data(request_tree, request_item, tvb, offset+1, end_offset-offset-1, pinfo, str_command);
                return;
            }
        }
        else if (((eocp_offset == -1) && (tag_start_offset != -1)) ||
               (eocp_offset > tag_start_offset))
        {
            /* tag data dissected */

            found_tag_needle = 0;
            tag_end_offset = tvb_pbrk_guint8(tvb, tag_start_offset+1, end_offset-tag_start_offset-1, TAG_DELIMITER, &found_tag_needle);
            if (tag_end_offset == -1)
            {
                expert_add_info(pinfo, request_item, &ei_irc_missing_end_delimiter);
                return;
            }

            dissect_irc_tag_data(request_tree, request_item, tvb, tag_start_offset, tag_end_offset-tag_start_offset, pinfo, str_command);
            offset = tag_end_offset+1;
        }
    }
}