static int PrivateTable__newindex(lua_State* L) { /* Sets the text of a specific entry */ PrivateTable priv = checkPrivateTable(L,1); const gchar* name = luaL_checkstring(L,2); const gchar* string = NULL; if (! (priv && name) ) return 0; if (priv->expired) { luaL_error(L,"expired private_table"); return 0; } if (lua_isstring(L,3)) { /* This also catches numbers, which is converted to string */ string = luaL_checkstring(L,3); } else if (lua_isboolean(L,3)) { /* We support boolean by setting a empty string if true and NULL if false */ string = lua_toboolean(L,3) ? "" : NULL; } else if (!lua_isnil(L,3)) { luaL_error(L,"unsupported type: %s", lua_typename(L,3)); return 0; } if (string) { g_hash_table_replace (priv->table, (gpointer) ep_strdup(name), (gpointer) ep_strdup(string)); } else { g_hash_table_remove (priv->table, (gpointer) name); } return 1; }
/* Convert an FT_STRING using a callback function */ static gboolean string_walk(GList* arg1list, GList **retval, gchar(*conv_func)(gchar)) { GList *arg1; fvalue_t *arg_fvalue; fvalue_t *new_ft_string; char *s, *c; arg1 = arg1list; while (arg1) { arg_fvalue = arg1->data; switch (fvalue_ftype(arg_fvalue)->ftype) { case FT_STRING: s = ep_strdup(fvalue_get(arg1->data)); for (c = s; *c; c++) { /**c = string_ascii_to_lower(*c);*/ *c = conv_func(*c); } new_ft_string = fvalue_new(FT_STRING); fvalue_set(new_ft_string, s, FALSE); *retval = g_list_append(*retval, new_ft_string); break; /* XXX - it would be nice to handle FT_TVBUFF, too */ default: break; } arg1 = arg1->next; } return TRUE; }
static char *fld_tostr(void *rec, uat_field_t *f) { guint len; const char *ptr; char *out; f->cb.tostr(rec, &ptr, &len, f->cbdata.tostr, f->fld_data); switch(f->mode) { case PT_TXTMOD_STRING: case PT_TXTMOD_ENUM: case PT_TXTMOD_FILENAME: case PT_TXTMOD_DIRECTORYNAME: out = ep_strndup(ptr, len); break; case PT_TXTMOD_HEXBYTES: { GString *s = g_string_sized_new( len*2 + 1 ); guint i; for (i=0; i<len;i++) g_string_append_printf(s, "%.2X", ((guint8*)ptr)[i]); out = ep_strdup(s->str); g_string_free(s, TRUE); break; } default: g_assert_not_reached(); out = NULL; break; } return out; }
/* Convert an FT_STRING using a callback function */ static gboolean string_walk(GList* arg1list, GList **retval, gchar(*conv_func)(gchar)) { GList *arg1; fvalue_t *arg_fvalue; fvalue_t *new_ft_string; char *s, *c; arg1 = arg1list; while (arg1) { arg_fvalue = (fvalue_t *)arg1->data; /* XXX - it would be nice to handle FT_TVBUFF, too */ if (IS_FT_STRING(fvalue_type_ftenum(arg_fvalue))) { s = (char *)ep_strdup((gchar *)fvalue_get(arg_fvalue)); for (c = s; *c; c++) { /**c = string_ascii_to_lower(*c);*/ *c = conv_func(*c); } new_ft_string = fvalue_new(FT_STRING); fvalue_set_string(new_ft_string, s); *retval = g_list_append(*retval, new_ft_string); } arg1 = arg1->next; } return TRUE; }
static gboolean diam_tree_to_csv(proto_node* node, gpointer data) { char* val_str=NULL; char* val_tmp=NULL; ftenum_t ftype; field_info* fi; header_field_info *hfi; if(!node) { fprintf(stderr,"traverse end: empty node. node='%p' data='%p'\n",(void *)node,(void *)data); return FALSE; } fi=node->finfo; hfi=fi ? fi->hfinfo : NULL; if(!hfi) { fprintf(stderr,"traverse end: hfi not found. node='%p'\n",(void *)node); return FALSE; } ftype=fvalue_type_ftenum(&fi->value); if (ftype!=FT_NONE&&ftype!=FT_PROTOCOL) { /* convert value to string */ val_tmp=fvalue_to_string_repr(&fi->value,FTREPR_DISPLAY,NULL); if(val_tmp) { val_str=ep_strdup(val_tmp); g_free(val_tmp); } else val_str=ep_strdup_printf("unsupported type: %s",ftype_name(ftype)); /*printf("traverse: name='%s', abbrev='%s',desc='%s', val='%s'\n",hfi->name,hfi->abbrev,ftype_name(hfi->type),val_str);*/ printf("%s='%s' ",hfi->name,val_str); } return FALSE; }
static void expert_set_info_vformat(packet_info *pinfo, proto_item *pi, int group, int severity, const char *format, va_list ap) { char formatted[ITEM_LABEL_LENGTH]; int tap; expert_info_t *ei; proto_tree *tree; proto_item *ti; /* if this packet isn't loaded because of a read filter, don't output anything */ if (pinfo == NULL || PINFO_FD_NUM(pinfo) == 0) { return; } if (severity > highest_severity) { highest_severity = severity; } if (pi != NULL && PITEM_FINFO(pi) != NULL) { expert_set_item_flags(pi, group, severity); } col_add_str(pinfo->cinfo, COL_EXPERT, val_to_str(severity, expert_severity_vals, "Unknown (%u)")); g_vsnprintf(formatted, ITEM_LABEL_LENGTH, format, ap); tree = expert_create_tree(pi, group, severity, formatted); ti = proto_tree_add_string(tree, hf_expert_msg, NULL, 0, 0, formatted); PROTO_ITEM_SET_GENERATED(ti); ti = proto_tree_add_uint_format_value(tree, hf_expert_severity, NULL, 0, 0, severity, "%s", val_to_str_const(severity, expert_severity_vals, "Unknown")); PROTO_ITEM_SET_GENERATED(ti); ti = proto_tree_add_uint_format_value(tree, hf_expert_group, NULL, 0, 0, group, "%s", val_to_str_const(group, expert_group_vals, "Unknown")); PROTO_ITEM_SET_GENERATED(ti); tap = have_tap_listener(expert_tap); if (!tap) return; ei = ep_alloc(sizeof(expert_info_t)); ei->packet_num = PINFO_FD_NUM(pinfo); ei->group = group; ei->severity = severity; ei->protocol = pinfo->current_proto; ei->summary = ep_strdup(formatted); /* if we have a proto_item (not a faked item), set expert attributes to it */ if (pi != NULL && PITEM_FINFO(pi) != NULL) { ei->pitem = pi; } else { ei->pitem = NULL; } tap_queue_packet(expert_tap, pinfo, ei); }
static void xmpp_error(proto_tree *tree, tvbuff_t *tvb, packet_info *pinfo, element_t *element) { proto_item *error_item; proto_tree *error_tree; element_t *text_element, *cond_element; attr_info attrs_info[] = { {"type", hf_xmpp_error_type, TRUE, TRUE, NULL, NULL}, {"code", hf_xmpp_error_code, FALSE, TRUE, NULL, NULL}, {"condition", hf_xmpp_error_condition, TRUE, TRUE, NULL, NULL} /*TODO: validate list to the condition element*/ }; gchar *error_info; attr_t *fake_condition = NULL; error_info = ep_strdup("Stanza error"); error_item = proto_tree_add_item(tree, hf_xmpp_error, tvb, element->offset, element->length, FALSE); error_tree = proto_item_add_subtree(error_item, ett_xmpp_query_item); cond_element = steal_element_by_attr(element, "xmlns", "urn:ietf:params:xml:ns:xmpp-stanzas"); if(cond_element) { fake_condition = ep_init_attr_t(cond_element->name, cond_element->offset, cond_element->length); g_hash_table_insert(element->attrs,"condition", fake_condition); error_info = ep_strdup_printf("%s: %s;", error_info, cond_element->name); } display_attrs(error_tree, element, pinfo, tvb, attrs_info, array_length(attrs_info)); while((text_element = steal_element_by_name(element, "text")) != NULL) { xmpp_error_text(error_tree, tvb, text_element); error_info = ep_strdup_printf("%s Text: %s", error_info, text_element->data?text_element->data->value:""); } expert_add_info_format(pinfo, error_item, PI_RESPONSE_CODE, PI_CHAT,"%s", error_info); xmpp_unknown(error_tree, tvb, pinfo, element); }
void xmpp_iq_reqresp_track(packet_info *pinfo, xmpp_element_t *packet, xmpp_conv_info_t *xmpp_info) { xmpp_transaction_t *xmpp_trans = NULL; xmpp_attr_t *attr_id; char *id; attr_id = xmpp_get_attr(packet, "id"); if (!attr_id) { return; } id = ep_strdup(attr_id->value); if (!pinfo->fd->flags.visited) { xmpp_trans = (xmpp_transaction_t *)se_tree_lookup_string(xmpp_info->req_resp, id, EMEM_TREE_STRING_NOCASE); if (xmpp_trans) { xmpp_trans->resp_frame = pinfo->fd->num; } else { char *se_id = se_strdup(id); xmpp_trans = (xmpp_transaction_t *)se_alloc(sizeof (xmpp_transaction_t)); xmpp_trans->req_frame = pinfo->fd->num; xmpp_trans->resp_frame = 0; se_tree_insert_string(xmpp_info->req_resp, se_id, (void *) xmpp_trans, EMEM_TREE_STRING_NOCASE); } } else { se_tree_lookup_string(xmpp_info->req_resp, id, EMEM_TREE_STRING_NOCASE); } }
static void dissect_quakeworld_ConnectionlessPacket(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int direction) { proto_tree *cl_tree = NULL; proto_tree *text_tree = NULL; guint8 text[MAX_TEXT_SIZE+1]; int len; int offset; guint32 marker; int command_len; const char *command = ""; gboolean command_finished = FALSE; marker = tvb_get_ntohl(tvb, 0); if (tree) { proto_item *cl_item; cl_item = proto_tree_add_text(tree, tvb, 0, -1, "Connectionless"); cl_tree = proto_item_add_subtree(cl_item, ett_quakeworld_connectionless); proto_tree_add_uint(cl_tree, hf_quakeworld_connectionless_marker, tvb, 0, 4, marker); } /* all the rest of the packet is just text */ offset = 4; len = tvb_get_nstringz0(tvb, offset, sizeof(text), text); /* actually, we should look for a eol char and stop already there */ if (cl_tree) { proto_item *text_item; text_item = proto_tree_add_string(cl_tree, hf_quakeworld_connectionless_text, tvb, offset, len + 1, text); text_tree = proto_item_add_subtree(text_item, ett_quakeworld_connectionless_text); } if (direction == DIR_C2S) { /* client to server commands */ const char *c; Cmd_TokenizeString(text); c = Cmd_Argv(0); /* client to sever commands */ if (strcmp(c,"ping") == 0) { command = "Ping"; command_len = 4; } else if (strcmp(c,"status") == 0) { command = "Status"; command_len = 6; } else if (strcmp(c,"log") == 0) { command = "Log"; command_len = 3; } else if (strcmp(c,"connect") == 0) { int version; int qport; int challenge; const char *infostring; proto_tree *argument_tree = NULL; command = "Connect"; command_len = Cmd_Argv_length(0); if (text_tree) { proto_item *argument_item; proto_tree_add_string(text_tree, hf_quakeworld_connectionless_command, tvb, offset, command_len, command); argument_item = proto_tree_add_string(text_tree, hf_quakeworld_connectionless_arguments, tvb, offset + Cmd_Argv_start(1), len + 1 - Cmd_Argv_start(1), text + Cmd_Argv_start(1)); argument_tree = proto_item_add_subtree(argument_item, ett_quakeworld_connectionless_arguments); command_finished=TRUE; } version = atoi(Cmd_Argv(1)); qport = atoi(Cmd_Argv(2)); challenge = atoi(Cmd_Argv(3)); infostring = Cmd_Argv(4); if (argument_tree) { proto_item *info_item; proto_tree *info_tree; proto_tree_add_uint(argument_tree, hf_quakeworld_connectionless_connect_version, tvb, offset + Cmd_Argv_start(1), Cmd_Argv_length(1), version); proto_tree_add_uint(argument_tree, hf_quakeworld_connectionless_connect_qport, tvb, offset + Cmd_Argv_start(2), Cmd_Argv_length(2), qport); proto_tree_add_int(argument_tree, hf_quakeworld_connectionless_connect_challenge, tvb, offset + Cmd_Argv_start(3), Cmd_Argv_length(3), challenge); info_item = proto_tree_add_string(argument_tree, hf_quakeworld_connectionless_connect_infostring, tvb, offset + Cmd_Argv_start(4), Cmd_Argv_length(4), infostring); info_tree = proto_item_add_subtree( info_item, ett_quakeworld_connectionless_connect_infostring); dissect_id_infostring(tvb, info_tree, offset + Cmd_Argv_start(4), ep_strdup(infostring), ett_quakeworld_connectionless_connect_infostring_key_value, hf_quakeworld_connectionless_connect_infostring_key_value, hf_quakeworld_connectionless_connect_infostring_key, hf_quakeworld_connectionless_connect_infostring_value); } } else if (strcmp(c,"getchallenge") == 0) { command = "Get Challenge"; command_len = Cmd_Argv_length(0); } else if (strcmp(c,"rcon") == 0) { const char* password; int i; char remaining[MAX_TEXT_SIZE+1]; proto_tree *argument_tree = NULL; command = "Remote Command"; command_len = Cmd_Argv_length(0); if (text_tree) { proto_item *argument_item; proto_tree_add_string(text_tree, hf_quakeworld_connectionless_command, tvb, offset, command_len, command); argument_item = proto_tree_add_string(text_tree, hf_quakeworld_connectionless_arguments, tvb, offset + Cmd_Argv_start(1), len + 1 - Cmd_Argv_start(1), text + Cmd_Argv_start(1)); argument_tree = proto_item_add_subtree(argument_item, ett_quakeworld_connectionless_arguments); command_finished=TRUE; } password = Cmd_Argv(1); if (argument_tree) { proto_tree_add_string(argument_tree, hf_quakeworld_connectionless_rcon_password, tvb, offset + Cmd_Argv_start(1), Cmd_Argv_length(1), password); } remaining[0] = '\0'; for (i=2; i<Cmd_Argc() ; i++) { g_strlcat (remaining, Cmd_Argv(i), MAX_TEXT_SIZE+1); g_strlcat (remaining, " ", MAX_TEXT_SIZE+1); } if (text_tree) { proto_tree_add_string(argument_tree, hf_quakeworld_connectionless_rcon_command, tvb, offset + Cmd_Argv_start(2), Cmd_Argv_start(Cmd_Argc()-1) + Cmd_Argv_length(Cmd_Argc()-1) - Cmd_Argv_start(2), remaining); } } else if (c[0]==A2A_PING && ( c[1]=='\0' || c[1]=='\n')) { command = "Ping"; command_len = 1; } else if (c[0]==A2A_ACK && ( c[1]=='\0' || c[1]=='\n')) { command = "Ack"; command_len = 1; } else { command = "Unknown"; command_len = len; } } else { /* server to client commands */ if (text[0] == S2C_CONNECTION) { command = "Connected"; command_len = 1; } else if (text[0] == A2C_CLIENT_COMMAND) { command = "Client Command"; command_len = 1; /* stringz (command), stringz (localid) */ } else if (text[0] == A2C_PRINT) { command = "Print"; command_len = 1; /* string */ } else if (text[0] == A2A_PING) { command = "Ping"; command_len = 1; } else if (text[0] == S2C_CHALLENGE) { command = "Challenge"; command_len = 1; /* string, atoi */ } else { command = "Unknown"; command_len = len; } } if (check_col(pinfo->cinfo, COL_INFO)) { col_append_fstr(pinfo->cinfo, COL_INFO, " %s", command); } if (text_tree && !command_finished) { proto_tree_add_string(text_tree, hf_quakeworld_connectionless_command, tvb, offset, command_len, command); } offset += len + 1; }
/* * Process a multipart body-part: * MIME-part-headers [ line-end *OCTET ] * line-end dashed-boundary transport-padding line-end * * If applicable, call a media subdissector. * * Return the offset to the start of the next body-part. */ static gint process_body_part(proto_tree *tree, tvbuff_t *tvb, const guint8 *boundary, gint boundary_len, packet_info *pinfo, gint start, gboolean *last_boundary) { proto_tree *subtree = NULL; proto_item *ti = NULL; gint offset = start, next_offset = 0; char *parameters = NULL; gint body_start, boundary_start, boundary_line_len; char *content_type_str = NULL; char *content_encoding_str = NULL; char *filename = NULL; char *typename = NULL; int len = 0; gboolean last_field = FALSE; if (tree) { ti = proto_tree_add_item(tree, hf_multipart_part, tvb, start, 0, FALSE); subtree = proto_item_add_subtree(ti, ett_multipart_body); } /* * Process the MIME-part-headers */ while (!last_field) { gint colon_offset; char *hdr_str; char *header_str; /* Look for the end of the header (denoted by cr) * 3:d argument to imf_find_field_end() maxlen; must be last offset in the tvb. */ next_offset = imf_find_field_end(tvb, offset, tvb_length_remaining(tvb, offset)+offset, &last_field); /* If cr not found, won't have advanced - get out to avoid infinite loop! */ if (next_offset == offset) { break; } hdr_str = tvb_get_ephemeral_string(tvb, offset, next_offset - offset); header_str = unfold_and_compact_mime_header(hdr_str, &colon_offset); if (colon_offset <= 0) { if (tree) { proto_tree_add_text(subtree, tvb, offset, next_offset - offset, "%s", tvb_format_text(tvb, offset, next_offset - offset)); } } else { gint hf_index; /* Split header name from header value */ header_str[colon_offset] = '\0'; hf_index = is_known_multipart_header(header_str, colon_offset); if (hf_index == -1) { if (tree) { proto_tree_add_text(subtree, tvb, offset, next_offset - offset, "%s", tvb_format_text(tvb, offset, next_offset - offset)); } } else { char *value_str = header_str + colon_offset + 1; if (tree) { proto_tree_add_string_format(subtree, hf_header_array[hf_index], tvb, offset, next_offset - offset, (const char *)value_str, "%s", tvb_format_text(tvb, offset, next_offset - offset)); } switch (hf_index) { case POS_CONTENT_TYPE: { /* The Content-Type starts at colon_offset + 1 */ gint semicolon_offset = index_of_char( value_str, ';'); if (semicolon_offset > 0) { value_str[semicolon_offset] = '\0'; parameters = ep_strdup(value_str + semicolon_offset + 1); } else { parameters = NULL; } content_type_str = g_ascii_strdown(value_str, -1); /* Show content-type in root 'part' label */ proto_item_append_text(ti, " (%s)", content_type_str); /* find the "name" parameter in case we don't find a content disposition "filename" */ if((typename = find_parameter(parameters, "name=", &len)) != NULL) { typename = g_strndup(typename, len); } } break; case POS_CONTENT_TRANSFER_ENCODING: { /* The Content-Transfeing starts at colon_offset + 1 */ gint cr_offset = index_of_char(value_str, '\r'); if (cr_offset > 0) { value_str[cr_offset] = '\0'; } content_encoding_str = g_ascii_strdown(value_str, -1); } break; case POS_CONTENT_DISPOSITION: { /* find the "filename" parameter */ if((filename = find_parameter(value_str, "filename=", &len)) != NULL) { filename = g_strndup(filename, len); } } break; default: break; } } } g_free(header_str); offset = next_offset; } body_start = next_offset; /* * Process the body */ boundary_start = find_next_boundary(tvb, body_start, boundary, boundary_len, &boundary_line_len, last_boundary); if (boundary_start > 0) { gint body_len = boundary_start - body_start; tvbuff_t *tmp_tvb = tvb_new_subset(tvb, body_start, body_len, body_len); if (content_type_str) { /* * subdissection */ void *save_private_data = pinfo->private_data; gboolean dissected; /* * Try and remove any content transfer encoding so that each sub-dissector * doesn't have to do it itself * */ if(content_encoding_str && remove_base64_encoding) { if(!g_ascii_strncasecmp(content_encoding_str, "base64", 6)) tmp_tvb = base64_decode(pinfo, tmp_tvb, filename ? filename : (typename ? typename : content_type_str)); } pinfo->private_data = parameters; /* * First try the dedicated multipart dissector table */ dissected = dissector_try_string(multipart_media_subdissector_table, content_type_str, tmp_tvb, pinfo, subtree); if (! dissected) { /* * Fall back to the default media dissector table */ dissected = dissector_try_string(media_type_dissector_table, content_type_str, tmp_tvb, pinfo, subtree); } if (! dissected) { const char *save_match_string = pinfo->match_string; pinfo->match_string = content_type_str; call_dissector(media_handle, tmp_tvb, pinfo, subtree); pinfo->match_string = save_match_string; } pinfo->private_data = save_private_data; g_free(content_type_str); content_type_str = NULL; parameters = NULL; /* Shares same memory as content_type_str */ } else {
static void expert_set_info_vformat(packet_info *pinfo, proto_item *pi, int group, int severity, int hf_index, gboolean use_vaformat, const char *format, va_list ap) { char formatted[ITEM_LABEL_LENGTH]; int tap; expert_info_t *ei; proto_tree *tree; proto_item *ti; if (pinfo == NULL && pi && pi->tree_data) { pinfo = PTREE_DATA(pi)->pinfo; } /* if this packet isn't loaded because of a read filter, don't output anything */ if (pinfo == NULL || PINFO_FD_NUM(pinfo) == 0) { return; } if (severity > highest_severity) { highest_severity = severity; } /* XXX: can we get rid of these checks and make them programming errors instead now? */ if (pi != NULL && PITEM_FINFO(pi) != NULL) { expert_set_item_flags(pi, group, severity); } if ((pi == NULL) || (PITEM_FINFO(pi) == NULL) || ((guint)severity >= FI_GET_FLAG(PITEM_FINFO(pi), PI_SEVERITY_MASK))) { col_add_str(pinfo->cinfo, COL_EXPERT, val_to_str(severity, expert_severity_vals, "Unknown (%u)")); } if (use_vaformat) { g_vsnprintf(formatted, ITEM_LABEL_LENGTH, format, ap); } else { g_strlcpy(formatted, format, ITEM_LABEL_LENGTH); } tree = expert_create_tree(pi, group, severity, formatted); if (hf_index == -1) { /* If no filterable expert info, just add the message */ ti = proto_tree_add_string(tree, hf_expert_msg, NULL, 0, 0, formatted); PROTO_ITEM_SET_GENERATED(ti); } else { /* If filterable expert info, hide the "generic" form of the message, and generate the formatted filterable expert info */ ti = proto_tree_add_none_format(tree, hf_index, NULL, 0, 0, "%s", formatted); PROTO_ITEM_SET_GENERATED(ti); ti = proto_tree_add_string(tree, hf_expert_msg, NULL, 0, 0, formatted); PROTO_ITEM_SET_HIDDEN(ti); } ti = proto_tree_add_uint_format_value(tree, hf_expert_severity, NULL, 0, 0, severity, "%s", val_to_str_const(severity, expert_severity_vals, "Unknown")); PROTO_ITEM_SET_GENERATED(ti); ti = proto_tree_add_uint_format_value(tree, hf_expert_group, NULL, 0, 0, group, "%s", val_to_str_const(group, expert_group_vals, "Unknown")); PROTO_ITEM_SET_GENERATED(ti); tap = have_tap_listener(expert_tap); if (!tap) return; ei = ep_new(expert_info_t); ei->packet_num = PINFO_FD_NUM(pinfo); ei->group = group; ei->severity = severity; ei->protocol = pinfo->current_proto; ei->summary = ep_strdup(formatted); /* if we have a proto_item (not a faked item), set expert attributes to it */ if (pi != NULL && PITEM_FINFO(pi) != NULL) { ei->pitem = pi; } /* XXX: remove this because we don't have an internal-only function now? */ else { ei->pitem = NULL; } tap_queue_packet(expert_tap, pinfo, ei); }
/* Dissect an individual actrace CAS message */ static void dissect_actrace_cas(tvbuff_t *tvb, packet_info *pinfo, proto_tree *actrace_tree) { /* Declare variables */ gint32 value, function, trunk, bchannel, source, event, curr_state, next_state; gint32 par0, par1, par2; gchar *frame_label = NULL; int direction = 0; int offset = 0; col_set_str(pinfo->cinfo, COL_PROTOCOL, "AC_CAS"); value = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_time, tvb, offset, 4, value); offset += 4; source = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_source, tvb, offset, 4, source); offset += 4; curr_state = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_current_state, tvb, offset, 4, curr_state); offset += 4; event = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_event, tvb, offset, 4, event); offset += 4; next_state = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_next_state, tvb, offset, 4, next_state); offset += 4; function = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_function, tvb, offset, 4, function); offset += 4; col_append_fstr(pinfo->cinfo, COL_INFO, "%s|%d|%s|%d|%s|", val_to_str_const(source, actrace_cas_source_vals_short, "ukn"), curr_state, val_to_str_ext(event, &actrace_cas_event_vals_ext, "%d"), next_state, val_to_str_ext(function, &actrace_cas_function_vals_ext, "%d")); par0 = tvb_get_ntohl(tvb, offset); switch (function) { case SEND_EVENT: proto_tree_add_text(actrace_tree, tvb, offset, 4, "Parameter 0: %s", val_to_str_ext(par0, &actrace_cas_pstn_event_vals_ext, "Unknown (%d)")); col_append_fstr(pinfo->cinfo, COL_INFO, "%s|", val_to_str_ext(par0, &actrace_cas_pstn_event_vals_ext, "%d")); break; case CHANGE_COLLECT_TYPE: proto_tree_add_text(actrace_tree, tvb, offset, 4, "Parameter 0: %s", val_to_str(par0, actrace_cas_collect_type_vals, "Unknown (%d)")); col_append_fstr(pinfo->cinfo, COL_INFO, "%s|", val_to_str(par0, actrace_cas_collect_type_vals, "%d")); break; case SEND_MF: case SEND_DEST_NUM: proto_tree_add_text(actrace_tree, tvb, offset, 4, "Parameter 0: %s", val_to_str(par0, actrace_cas_send_type_vals, "Unknown (%d)")); col_append_fstr(pinfo->cinfo, COL_INFO, "%s|", val_to_str(par0, actrace_cas_send_type_vals, "%d")); break; default: proto_tree_add_int(actrace_tree, hf_actrace_cas_par0, tvb, offset, 4, par0); col_append_fstr(pinfo->cinfo, COL_INFO, "%d|", par0); } offset += 4; par1 = tvb_get_ntohl(tvb, offset); if (function == SEND_EVENT) { proto_tree_add_text(actrace_tree, tvb, offset, 4, "Parameter 1: %s", val_to_str_ext(par1, &actrace_cas_cause_vals_ext, "Unknown (%d)")); col_append_fstr(pinfo->cinfo, COL_INFO, "%s|", val_to_str_ext(par1, &actrace_cas_cause_vals_ext, "%d")); } else { proto_tree_add_int(actrace_tree, hf_actrace_cas_par1, tvb, offset, 4, par1); col_append_fstr(pinfo->cinfo, COL_INFO, "%d|", par1); } offset += 4; par2 = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_par2, tvb, offset, 4, par2); col_append_fstr(pinfo->cinfo, COL_INFO, "%d|", par2); offset += 4; trunk = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_trunk, tvb, offset, 4, trunk); offset += 4; bchannel = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_bchannel, tvb, offset, 4, bchannel); offset += 4; col_prepend_fstr(pinfo->cinfo, COL_INFO, "t%db%d|", trunk, bchannel); value = tvb_get_ntohl(tvb, offset); proto_tree_add_int(actrace_tree, hf_actrace_cas_connection_id, tvb, offset, 4, value); /* Add tap info for the Voip Graph */ if (source == ACTRACE_CAS_SOURCE_DSP) { direction = 1; if ( (event >= ACTRACE_CAS_EV_11) && (event <= ACTRACE_CAS_EV_00 ) ) { frame_label = ep_strdup_printf("AB: %s", val_to_str_const(event, actrace_cas_event_ab_vals, "ERROR") ); } else if ( (event >= 32) && (event <= 46 ) ) { /* is an MF tone */ frame_label = ep_strdup_printf("MF: %s", val_to_str_ext_const(event, &actrace_cas_mf_vals_ext, "ERROR") ); } else if ( (event == ACTRACE_CAS_EV_DTMF ) || (event == ACTRACE_CAS_EV_FIRST_DIGIT ) ) { /* DTMF digit */ frame_label = ep_strdup_printf("DTMF: %u", par0 ); } } else if (source == ACTRACE_CAS_SOURCE_TABLE) { direction = 0; if (function == SEND_MF) { if (par0 == SEND_TYPE_SPECIFIC ) { frame_label = ep_strdup_printf("MF: %u", par1); } else if (par0 == SEND_TYPE_ADDRESS ) { frame_label = ep_strdup("MF: DNIS digit"); } else if (par0 == SEND_TYPE_ANI ) { frame_label = ep_strdup("MF: ANI digit"); } else if (par0 == SEND_TYPE_SOURCE_CATEGORY ) { frame_label = ep_strdup("MF: src_category"); } else if (par0 == SEND_TYPE_TRANSFER_CAPABILITY ) { frame_label = ep_strdup("MF: trf_capability"); } else if (par0 == SEND_TYPE_INTER_EXCHANGE_SWITCH ) { frame_label = ep_strdup("MF: inter_exch_sw"); } } else if (function == SEND_CAS) { frame_label = ep_strdup_printf("AB: %s", val_to_str_const(ACTRACE_CAS_EV_00-par0, actrace_cas_event_ab_vals, "ERROR")); } else if (function == SEND_DEST_NUM) { if (par0 == SEND_TYPE_ADDRESS ) { frame_label = ep_strdup("DTMF/MF: sending DNIS"); } else if (par0 == SEND_TYPE_ANI ) { frame_label = ep_strdup("DTMF/MF: sending ANI"); } } } if (frame_label != NULL) { /* Initialise packet info for passing to tap */ actrace_pi = ep_new(actrace_info_t); actrace_pi->type = ACTRACE_CAS; actrace_pi->direction = direction; actrace_pi->trunk = trunk; actrace_pi->cas_bchannel = bchannel; actrace_pi->cas_frame_label = frame_label; /* Report this packet to the tap */ tap_queue_packet(actrace_tap, pinfo, actrace_pi); } }
/* * This function dissects an "Ice facet", adds hf(s) to "tree" and returns consumed * bytes in "*consumed", if errors "*consumed" is -1. */ static void dissect_ice_facet(packet_info *pinfo, proto_tree *tree, proto_item *item, int hf_icep, tvbuff_t *tvb, guint32 offset, gint32 *consumed) { /* p. 588, chapter 23.2.6: * "facet" is a StringSeq, a StringSeq is a: * sequence<string> * * * sequence == Size + SizeElements * sequence = 1byte (0..254) + SizeElements * or * sequence = 1byte (255) + 1int (255..2^32-1) + SizeElements * * * p.613. chapter 23.3.2 * "facet has either zero elements (empty) or one element" * * */ guint32 Size = 0; /* number of elements in the sequence */ char *s = NULL; (*consumed) = 0; /* check first byte */ if ( !tvb_bytes_exist(tvb, offset, 1) ) { if (item) expert_add_info_format(pinfo, item, PI_MALFORMED, PI_ERROR, "facet field missing"); col_append_str(mypinfo->cinfo, COL_INFO, " (facet field missing)"); (*consumed) = -1; return; } /* get first byte of Size */ Size = tvb_get_guint8(tvb, offset); offset++; (*consumed)++; if ( Size == 0 ) { if (tree) { s = ep_strdup( "(empty)" ); /* display the 0x00 Size byte when click on a empty ice_string */ proto_tree_add_string(tree, hf_icep, tvb, offset - 1, 1, s); } return; } if ( Size == 1 ) { gint32 consumed_facet = 0; dissect_ice_string(pinfo, tree, item, hf_icep, tvb, offset, &consumed_facet, NULL); if ( consumed_facet == -1 ) { (*consumed) = -1; return; } /*offset += consumed_facet;*/ (*consumed) += consumed_facet; return; } /* if here => Size > 1 => not possible */ if (item) /* display the XX Size byte when click here */ expert_add_info_format(pinfo, item, PI_PROTOCOL, PI_WARN, "facet can be max one element"); col_append_str(mypinfo->cinfo, COL_INFO, " (facet can be max one element)"); (*consumed) = -1; return; }
static int dissect_adwin(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree) { proto_item *ti, *ti2; proto_tree *adwin_tree, *adwin_debug_tree; gchar *info_string; guint32 length; length = tvb_reported_length(tvb); /* First do some heuristics to see if this packet belongs to us */ if(! (length == UDPH1_OLD_LENGTH || length == UDPH1_NEW_LENGTH || length == UDPR1_LENGTH || length == UDPH2_LENGTH || length == UDPR2_LENGTH || length == UDPR3_LENGTH || length == UDPR4_LENGTH || length == GetDataSHPacket_LENGTH || length == GetDataSHRequest_LENGTH)) return(0); col_set_str(pinfo->cinfo, COL_PROTOCOL, "ADwin"); col_clear(pinfo->cinfo, COL_INFO); if (tree) { ti = proto_tree_add_item(tree, proto_adwin, tvb, 0, -1, ENC_NA); adwin_tree = proto_item_add_subtree(ti, ett_adwin); ti2 = proto_tree_add_item(adwin_tree, proto_adwin, tvb, 0, -1, ENC_NA); adwin_debug_tree = proto_item_add_subtree(ti2, ett_adwin_debug); proto_item_set_text(ti2, "ADwin Debug information"); } else { adwin_tree = NULL; adwin_debug_tree = NULL; } switch (length) { case UDPH1_OLD_LENGTH: dissect_UDPH1_old(tvb, pinfo, adwin_tree, adwin_debug_tree, &info_string); break; case UDPH1_NEW_LENGTH: dissect_UDPH1_new(tvb, pinfo, adwin_tree, adwin_debug_tree, &info_string); break; case UDPR1_LENGTH: dissect_UDPR1(tvb, pinfo, adwin_tree, adwin_debug_tree, &info_string); break; case UDPH2_LENGTH: /* to the best of my knowledge, this struct * has never been used publically! */ /* dissect_UDPH2(tvb, pinfo, adwin_tree, adwin_debug_tree); */ info_string = ep_strdup("UDPH2 - UNUSED"); break; case UDPR2_LENGTH: dissect_UDPR2(tvb, pinfo, adwin_tree, adwin_debug_tree, &info_string); break; case UDPR3_LENGTH: dissect_UDPR3(tvb, pinfo, adwin_tree, adwin_debug_tree); info_string = ep_strdup("UDPR3"); break; case UDPR4_LENGTH: dissect_UDPR4(tvb, pinfo, adwin_tree, adwin_debug_tree, &info_string); break; case GetDataSHPacket_LENGTH: dissect_GDSHP(tvb, pinfo, adwin_tree, adwin_debug_tree); info_string = ep_strdup("GDSHP"); break; case GetDataSHRequest_LENGTH: dissect_GDSHR(tvb, pinfo, adwin_tree, adwin_debug_tree); info_string = ep_strdup("GDSHR"); break; default: info_string = ep_strdup_printf("Unknown ADwin packet, length: %d", length); break; } col_add_str(pinfo->cinfo, COL_INFO, info_string); return (tvb_reported_length(tvb)); }
static gboolean val_from_unparsed(fvalue_t *fv, char *s, gboolean allow_partial_value _U_, LogFunc logfunc) { guint32 addr; unsigned int nmask_bits; char *has_slash, *s_copy = NULL; char *net_str, *addr_str; fvalue_t *nmask_fvalue; /* Look for CIDR: Is there a single slash in the string? */ has_slash = strchr(s, '/'); if (has_slash) { /* Make a copy of the string and use strtok() to * get the address portion. */ s_copy = ep_strdup(s); addr_str = strtok(s_copy, "/"); /* I just checked for slash! I shouldn't get NULL here. * Double check just in case. */ if (!addr_str) { logfunc("Unexpected strtok() error parsing IP address: %s", s_copy); return FALSE; } } else { addr_str = s; } if (!get_host_ipaddr(addr_str, &addr)) { logfunc("\"%s\" is not a valid hostname or IPv4 address.", addr_str); return FALSE; } ipv4_addr_set_host_order_addr(&(fv->value.ipv4), addr); /* If CIDR, get netmask bits. */ if (has_slash) { net_str = strtok(NULL, "/"); /* I checked for slash! I shouldn't get NULL here. * Double check just in case. */ if (!net_str) { logfunc("Unexpected strtok() error parsing netmask: %s", s_copy); return FALSE; } /* XXX - this is inefficient */ nmask_fvalue = fvalue_from_unparsed(FT_UINT32, net_str, FALSE, logfunc); if (!nmask_fvalue) { return FALSE; } nmask_bits = fvalue_get_uinteger(nmask_fvalue); FVALUE_FREE(nmask_fvalue); if (nmask_bits > 32) { logfunc("Netmask bits in a CIDR IPv4 address should be <= 32, not %u", nmask_bits); return FALSE; } ipv4_addr_set_netmask_bits(&fv->value.ipv4, nmask_bits); } else { /* Not CIDR; mask covers entire address. */ ipv4_addr_set_netmask_bits(&(fv->value.ipv4), 32); } return TRUE; }