aboutsummaryrefslogtreecommitdiffstats
path: root/plugins
diff options
context:
space:
mode:
authorAnders Broman <anders.broman@ericsson.com>2007-02-27 06:25:07 +0000
committerAnders Broman <anders.broman@ericsson.com>2007-02-27 06:25:07 +0000
commitc637027427d3cccfdf079f81e0be4a9435bfd517 (patch)
tree01c48aac3a834bc17e132f92ee58d52c4c53db92 /plugins
parentcf13f56dc8a74bd47e60f3ff37664c8321db715c (diff)
From Richard van der Hoff:
- Registers H.223 as a dissector for RTP CLEARMODE payloads - and makes some other modifications to the H.223 dissector to make this work correctly. -Allows a standalone binary, epan/reassemble_test, to be built; this can be run from the commandline and should end up printing out "success" if all goes well. svn path=/trunk/; revision=20935
Diffstat (limited to 'plugins')
-rw-r--r--plugins/h223/packet-h223.c184
1 files changed, 125 insertions, 59 deletions
diff --git a/plugins/h223/packet-h223.c b/plugins/h223/packet-h223.c
index 810172447c..9f9bde5997 100644
--- a/plugins/h223/packet-h223.c
+++ b/plugins/h223/packet-h223.c
@@ -388,100 +388,165 @@ static h223_vc_info* h223_vc_info_new( h223_call_info* call_info )
return vc_info;
}
-static void init_logical_channel( packet_info* pinfo, h223_call_info* call_info, int vc, int direction, h223_lc_params* params )
+static void init_logical_channel( guint32 start_frame, h223_call_info* call_info, int vc, int direction, h223_lc_params* params )
{
guint32 circuit_id = circuit_chain_lookup(call_info, vc);
circuit_t *subcircuit;
h223_vc_info *vc_info;
- subcircuit = find_circuit( CT_H223, circuit_id, pinfo->fd->num );
+ subcircuit = find_circuit( CT_H223, circuit_id, start_frame );
if( subcircuit == NULL ) {
- subcircuit = circuit_new( CT_H223, circuit_id, pinfo->fd->num );
+ subcircuit = circuit_new( CT_H223, circuit_id, start_frame );
#ifdef DEBUG_H223
- g_debug("%d: Created new circuit %d for call %p VC %d", pinfo->fd->num, circuit_id, call_info, vc);
+ g_debug("%d: Created new circuit %d for call %p VC %d", start_frame, circuit_id, call_info, vc);
#endif
vc_info = h223_vc_info_new( call_info );
circuit_add_proto_data( subcircuit, proto_h223, vc_info );
} else {
vc_info = circuit_get_proto_data( subcircuit, proto_h223 );
}
- add_h223_lc_params( vc_info, direction, params, pinfo->fd->num );
+ add_h223_lc_params( vc_info, direction, params, start_frame );
}
-static void init_control_channels( packet_info* pinfo, h223_call_info* call_info )
+/* create a brand-new h223_call_info structure */
+static h223_call_info *create_call_info( guint32 start_frame )
{
- h223_lc_params *vc0_params = se_alloc(sizeof(h223_lc_params));
+ h223_call_info *data;
+ h223_lc_params *vc0_params;
+
+ data = se_alloc(sizeof(h223_call_info));
+
+ /* initialise the call info */
+ init_direction_data(&data -> direction_data[0]);
+ init_direction_data(&data -> direction_data[1]);
+
+ /* FIXME shouldn't this be figured out dynamically? */
+ data -> h223_level = 2;
+
+ vc0_params = se_alloc(sizeof(h223_lc_params));
vc0_params->al_type = al1Framed;
vc0_params->al_params = NULL;
vc0_params->segmentable = TRUE;
vc0_params->subdissector = srp_handle;
- init_logical_channel( pinfo, call_info, 0, P2P_DIR_SENT, vc0_params );
- init_logical_channel( pinfo, call_info, 0, P2P_DIR_RECV, vc0_params );
+ init_logical_channel( start_frame, data, 0, P2P_DIR_SENT, vc0_params );
+ init_logical_channel( start_frame, data, 0, P2P_DIR_RECV, vc0_params );
+ return data;
}
-static h223_call_info *find_or_create_call_info ( packet_info * pinfo )
+/* find or create call_info struct for calls over circuits (eg, IAX) */
+static h223_call_info *find_or_create_call_info_circ(packet_info * pinfo)
{
- circuit_t *circ;
- conversation_t *conv = NULL;
h223_call_info *data;
+ circuit_t *circ = NULL;
- /* look for a circuit (eg, IAX call) first */
- circ = find_circuit( pinfo->ctype, pinfo->circuit_id, pinfo->fd->num );
- if( circ == NULL ) {
- /* assume we're running atop TCP; use the converstion support */
- conv = find_conversation( pinfo->fd->num,
- &pinfo->src,&pinfo->dst,
- pinfo->ptype,
- pinfo->srcport,pinfo->destport, 0 );
- if( conv == NULL ) {
- conv = conversation_new( pinfo->fd->num,
- &pinfo->src,&pinfo->dst,
- pinfo->ptype,
- pinfo->srcport,pinfo->destport, 0 );
- }
-
+ if(pinfo->ctype != CT_NONE)
+ circ = find_circuit( pinfo->ctype, pinfo->circuit_id, pinfo->fd->num );
+ if(circ == NULL)
+ return NULL;
+
+ data = (h223_call_info *)circuit_get_proto_data(circ, proto_h223);
+
+ if( data == NULL ) {
+ data = create_call_info(pinfo->fd->num);
+
+#ifdef DEBUG_H223
+ g_debug("%u: Created new call %p for circuit %p ctype %d, id %u",
+ pinfo->fd->num, data, circ, pinfo->ctype, pinfo->circuit_id);
+#endif
+ circuit_add_proto_data(circ, proto_h223, data);
}
+
+ /* work out what direction we're really going in */
+ if( pinfo->p2p_dir < 0 || pinfo->p2p_dir > 1)
+ pinfo->p2p_dir = P2P_DIR_SENT;
+
+ return data;
+}
- if( circ )
- data = (h223_call_info *)circuit_get_proto_data(circ, proto_h223);
- else
- data = (h223_call_info *)conversation_get_proto_data(conv, proto_h223);
+/* find or create call_info struct for calls over conversations (eg, RTP) */
+static h223_call_info *find_or_create_call_info_conv(packet_info * pinfo)
+{
+ h223_call_info *data;
+ conversation_t *conv;
- if( data == NULL ) {
- data = se_alloc(sizeof(h223_call_info));
+ /* assume we're running atop TCP or RTP; use the conversation support */
+ conv = find_conversation( pinfo->fd->num,
+ &pinfo->src,&pinfo->dst,
+ pinfo->ptype,
+ pinfo->srcport,pinfo->destport, 0 );
- if( circ ) {
- circuit_add_proto_data(circ, proto_h223, data);
- } else {
- conversation_add_proto_data(conv, proto_h223, data);
- /* add the source details so we can distinguish directions
- * in future */
- COPY_ADDRESS(&(data -> srcaddress), &(pinfo->src));
- data -> srcport = pinfo->srcport;
- }
+ /* both RTP and TCP track their conversations, so just assert here if
+ * we can't find one */
+ DISSECTOR_ASSERT(conv);
+
+ data = (h223_call_info *)conversation_get_proto_data(conv, proto_h223);
- /* initialise the call info */
- init_direction_data(&data -> direction_data[0]);
- init_direction_data(&data -> direction_data[1]);
+ if(data == NULL && pinfo->ptype == PT_UDP ) {
+ conversation_t *conv2;
- /* FIXME shouldn't this be figured out dynamically? */
- data -> h223_level = 2;
+ /* RTP tracks the two sides of the conversation totally separately;
+ * this messes us up totally.
+ *
+ * Look for another converstation, going in the opposite direction.
+ */
+ conv2 = find_conversation( pinfo->fd->num,
+ &pinfo->dst,&pinfo->src,
+ pinfo->ptype,
+ pinfo->destport,pinfo->srcport, 0 );
+ if(conv2 != NULL)
+ data = (h223_call_info *)conversation_get_proto_data(conv2, proto_h223);
+
+ if(data != NULL) {
+#ifdef DEBUG_H223
+ g_debug("%u: Identified conv %p as reverse of conv %p with call %p and type=%u src=%u.%u.%u.%u:%u dst=%u.%u.%u.%u:%u",
+ pinfo->fd->num, conv, conv2, data, pinfo->ptype,
+ pinfo->dst.data[0], pinfo->dst.data[1], pinfo->dst.data[2], pinfo->dst.data[3],
+ pinfo->destport,
+ pinfo->src.data[0], pinfo->src.data[1], pinfo->src.data[2], pinfo->src.data[3],
+ pinfo->srcport);
+#endif
+ conversation_add_proto_data(conv, proto_h223, data);
+ }
+ }
- init_control_channels( pinfo, data );
+ /* we still haven't found any call data - create a new one for this
+ * conversation */
+ if(data == NULL) {
+ data = create_call_info(pinfo->fd->num);
+
+#ifdef DEBUG_H223
+ g_debug("%u: Created new call %p for conv %p type=%u src=%u.%u.%u.%u:%u dst=%u.%u.%u.%u:%u",
+ pinfo->fd->num, data, conv, pinfo->ptype,
+ pinfo->src.data[0], pinfo->src.data[1], pinfo->src.data[2], pinfo->src.data[3],
+ pinfo->srcport,
+ pinfo->dst.data[0], pinfo->dst.data[1], pinfo->dst.data[2], pinfo->dst.data[3],
+ pinfo->destport);
+#endif
+
+ conversation_add_proto_data(conv, proto_h223, data);
+ /* add the source details so we can distinguish directions
+ * in future */
+ COPY_ADDRESS(&(data -> srcaddress), &(pinfo->src));
+ data -> srcport = pinfo->srcport;
}
/* work out what direction we're really going in */
- if( circ ) {
- if( pinfo->p2p_dir < 0 || pinfo->p2p_dir > 1)
- pinfo->p2p_dir = P2P_DIR_SENT;
- } else {
- if( ADDRESSES_EQUAL( &(pinfo->src), &(data->srcaddress))
- && pinfo->srcport == data->srcport )
- pinfo->p2p_dir = P2P_DIR_SENT;
- else
- pinfo->p2p_dir = P2P_DIR_RECV;
- }
+ if( ADDRESSES_EQUAL( &(pinfo->src), &(data->srcaddress))
+ && pinfo->srcport == data->srcport )
+ pinfo->p2p_dir = P2P_DIR_SENT;
+ else
+ pinfo->p2p_dir = P2P_DIR_RECV;
+
+ return data;
+}
+
+static h223_call_info *find_or_create_call_info ( packet_info * pinfo )
+{
+ h223_call_info *data;
+ data = find_or_create_call_info_circ(pinfo);
+ if(data == NULL)
+ data = find_or_create_call_info_conv(pinfo);
return data;
}
@@ -509,7 +574,7 @@ static void h223_add_lc( packet_info* pinfo, guint16 lc, h223_lc_params* params
* the new channel */
if(circ) {
vc_info = circuit_get_proto_data(circ, proto_h223);
- init_logical_channel( pinfo, vc_info->call_info, lc, pinfo->p2p_dir, params );
+ init_logical_channel( pinfo->fd->num, vc_info->call_info, lc, pinfo->p2p_dir, params );
}
}
@@ -1512,6 +1577,7 @@ void proto_reg_handoff_h223(void)
dissector_add_handle("tcp.port", h223);
dissector_add_handle("tcp.port", h223_bitswapped);
+ dissector_add_string("rtp_dyn_payload_type","CLEARMODE", h223_bitswapped);
dissector_add("iax2.dataformat", AST_DATAFORMAT_H223_H245, h223_bitswapped);
}
/* vim:set ts=8 et: */