Commit ac2f2181 authored by Damien Lucas's avatar Damien Lucas

. SAP/SDP packets parsing: ability to parse RFC compliant packets

  parse_sap returns the SAP header length
  parse_sdp only parse the SDP payload
  note that VLC will discard messages from the old miniSAP-server
  (You have to use CVS version of miniSAP-server)
  (Messages from the new miniSAP-server will be discarded with old VLC)
parent 567eba17
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
* sap.c : SAP interface module * sap.c : SAP interface module
***************************************************************************** *****************************************************************************
* Copyright (C) 2001 VideoLAN * Copyright (C) 2001 VideoLAN
* $Id: sap.c,v 1.10 2003/03/30 18:14:38 gbazin Exp $ * $Id: sap.c,v 1.11 2003/05/25 18:02:20 nitrox Exp $
* *
* Authors: Arnaud Schauly <gitan@via.ecp.fr> * Authors: Arnaud Schauly <gitan@via.ecp.fr>
* *
...@@ -89,7 +89,7 @@ static int sess_toitem( intf_thread_t *, sess_descr_t * ); ...@@ -89,7 +89,7 @@ static int sess_toitem( intf_thread_t *, sess_descr_t * );
/* sap/sdp related functions */ /* sap/sdp related functions */
static int parse_sap ( char * ); static int parse_sap ( char * );
static int packet_handle ( intf_thread_t *, char * ); static int packet_handle ( intf_thread_t *, char *, int );
static sess_descr_t * parse_sdp( intf_thread_t *, char * ) ; static sess_descr_t * parse_sdp( intf_thread_t *, char * ) ;
/* specific sdp fields parsing */ /* specific sdp fields parsing */
...@@ -212,7 +212,7 @@ static void Run( intf_thread_t *p_intf ) ...@@ -212,7 +212,7 @@ static void Run( intf_thread_t *p_intf )
} }
buffer[i_read] = '\0'; buffer[i_read] = '\0';
packet_handle( p_intf, buffer ); packet_handle( p_intf, buffer, i_read );
} }
...@@ -451,12 +451,20 @@ static void mfield_parse( char *psz_mfield, char **ppsz_proto, ...@@ -451,12 +451,20 @@ static void mfield_parse( char *psz_mfield, char **ppsz_proto,
* parse_sap : Takes care of the SAP headers * parse_sap : Takes care of the SAP headers
*********************************************************************** ***********************************************************************
* checks if the packet has the true headers ; * checks if the packet has the true headers ;
* returns the SAP header lenhth
***********************************************************************/ ***********************************************************************/
static int parse_sap( char *p_packet ) static int parse_sap( char *p_packet )
{ /* Dummy Parser : does nothing !*/ {
// According to RFC 2974
int i_hlen = 4; // Minimum header length is 4
i_hlen += (p_packet[0] & 0x10) ? 16 : 4; // Address type IPv6=16bytes
i_hlen += p_packet[1]; // Authentification length
//Looks for the first '\0' byte after length
for(;p_packet[i_hlen]!='\0'; i_hlen++);
return( VLC_TRUE ); return(i_hlen);
} }
/************************************************************************* /*************************************************************************
...@@ -464,18 +472,22 @@ static int parse_sap( char *p_packet ) ...@@ -464,18 +472,22 @@ static int parse_sap( char *p_packet )
* the understated session * the understated session
*************************************************************************/ *************************************************************************/
static int packet_handle( intf_thread_t * p_intf, char *p_packet ) static int packet_handle( intf_thread_t * p_intf, char *p_packet, int i_len )
{ {
sess_descr_t * p_sd; sess_descr_t * p_sd;
int i_hlen; // Header length
if( parse_sap( p_packet ) ) i_hlen = parse_sap(p_packet);
{
p_sd = parse_sdp( p_intf, p_packet);
sess_toitem ( p_intf, p_sd );
free_sd ( p_sd ); if( (i_hlen > 0) && (i_hlen < i_len) )
return VLC_TRUE; {
p_sd = parse_sdp( p_intf, p_packet + i_hlen +1);
if(p_sd)
{
sess_toitem ( p_intf, p_sd );
free_sd ( p_sd );
return VLC_TRUE;
}
} }
return VLC_FALSE; // Invalid Packet return VLC_FALSE; // Invalid Packet
...@@ -494,6 +506,13 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet ) ...@@ -494,6 +506,13 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet )
{ {
sess_descr_t * sd; sess_descr_t * sd;
// According to RFC 2327, the first bytes should be exactly "v="
if((p_packet[0] != 'v') || (p_packet[1] != '='))
{
msg_Warn(p_intf, "Bad SDP packet");
return NULL;
}
if( ( sd = malloc( sizeof(sess_descr_t) ) ) == NULL ) if( ( sd = malloc( sizeof(sess_descr_t) ) ) == NULL )
{ {
msg_Err( p_intf, "Not enough memory for sd in parse_sdp()" ); msg_Err( p_intf, "Not enough memory for sd in parse_sdp()" );
...@@ -514,7 +533,6 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet ) ...@@ -514,7 +533,6 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet )
sd->i_media = 0; sd->i_media = 0;
while( *p_packet != '\0' ) while( *p_packet != '\0' )
{ {
#define FIELD_COPY( p ) \ #define FIELD_COPY( p ) \
...@@ -578,7 +596,7 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet ) ...@@ -578,7 +596,7 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet )
{ {
sd->pp_media = sd->pp_media =
realloc( sd->pp_media, realloc( sd->pp_media,
sizeof( media_descr_t ) * ( sd->i_media + 1 ) ); sizeof( media_descr_t ) * ( sd->i_media + 1 ) );
} }
else else
{ {
...@@ -597,11 +615,11 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet ) ...@@ -597,11 +615,11 @@ static sess_descr_t * parse_sdp( intf_thread_t * p_intf, char *p_packet )
case( 'c' ): case( 'c' ):
if( sd->i_media <= 0 ) if( sd->i_media <= 0 )
{ {
sd->psz_connection = strndup( &p_packet[2], i_field_len ); FIELD_COPY(sd->psz_connection);
} }
else else
{ {
sd->pp_media[sd->i_media - 1]->psz_mediaconnection = strndup( &p_packet[2], i_field_len ); FIELD_COPY(sd->pp_media[sd->i_media - 1]->psz_mediaconnection);
} }
break; break;
default: default:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment