[vlc-devel] [PATCH] rtp sout: ensure seq value in rtsp is accurate
Pierre Ynard
linkfanel at yahoo.fr
Fri Dec 11 18:59:41 CET 2009
Handle caching and fix race conditions
diff --git a/modules/stream_out/rtp.c b/modules/stream_out/rtp.c
index ff6388f..805b1ec 100644
--- a/modules/stream_out/rtp.c
+++ b/modules/stream_out/rtp.c
@@ -312,6 +312,9 @@ struct sout_stream_id_t
uint8_t i_payload_type;
uint8_t ssrc[4];
+ /* for rtsp */
+ uint16_t i_seq_sent_next;
+
/* for sdp */
const char *psz_enc;
char *psz_fmtp;
@@ -925,6 +928,8 @@ static sout_stream_id_t *Add( sout_stream_t *p_stream, es_format_t *p_fmt )
vlc_rand_bytes (&id->i_sequence, sizeof (id->i_sequence));
vlc_rand_bytes (id->ssrc, sizeof (id->ssrc));
+ id->i_seq_sent_next = id->i_sequence;
+
id->psz_enc = NULL;
id->psz_fmtp = NULL;
id->i_clock_rate = 90000; /* most common case for video */
@@ -1037,7 +1042,7 @@ static sout_stream_id_t *Add( sout_stream_t *p_stream, es_format_t *p_fmt )
* packets in case of rtcp-mux) */
setsockopt (fd, SOL_SOCKET, SO_RCVBUF, &(int){ 0 },
sizeof (int));
- rtp_add_sink( id, fd, p_sys->rtcp_mux );
+ rtp_add_sink( id, fd, p_sys->rtcp_mux, NULL );
}
}
@@ -1596,6 +1601,7 @@ static void* ThreadSend( vlc_object_t *p_this )
deadv[deadc++] = id->sinkv[i].rtp_fd;
}
+ id->i_seq_sent_next = ((uint16_t *) out->p_buffer)[1] + 1;
vlc_mutex_unlock( &id->lock_sink );
block_Release( out );
@@ -1623,7 +1629,7 @@ static void *rtp_listen_thread( void *data )
if( fd == -1 )
continue;
int canc = vlc_savecancel( );
- rtp_add_sink( id, fd, true );
+ rtp_add_sink( id, fd, true, NULL );
vlc_restorecancel( canc );
}
@@ -1631,7 +1637,7 @@ static void *rtp_listen_thread( void *data )
}
-int rtp_add_sink( sout_stream_id_t *id, int fd, bool rtcp_mux )
+int rtp_add_sink( sout_stream_id_t *id, int fd, bool rtcp_mux, uint16_t *seq )
{
rtp_sink_t sink = { fd, NULL };
sink.rtcp = OpenRTCP( VLC_OBJECT( id->p_stream ), fd, IPPROTO_UDP,
@@ -1641,6 +1647,8 @@ int rtp_add_sink( sout_stream_id_t *id, int fd, bool rtcp_mux )
vlc_mutex_lock( &id->lock_sink );
INSERT_ELEM( id->sinkv, id->sinkc, id->sinkc, sink );
+ if( seq != NULL )
+ *seq = id->i_seq_sent_next;
vlc_mutex_unlock( &id->lock_sink );
return VLC_SUCCESS;
}
@@ -1666,11 +1674,16 @@ void rtp_del_sink( sout_stream_id_t *id, int fd )
net_Close( sink.rtp_fd );
}
-uint16_t rtp_get_seq( const sout_stream_id_t *id )
+uint16_t rtp_get_seq( sout_stream_id_t *id )
{
- /* This will return values for the next packet.
- * Accounting for caching would not be totally trivial. */
- return id->i_sequence;
+ /* This will return values for the next packet. */
+ uint16_t seq;
+
+ vlc_mutex_lock( &id->lock_sink );
+ seq = id->i_seq_sent_next;
+ vlc_mutex_unlock( &id->lock_sink );
+
+ return seq;
}
/* FIXME: this is pretty bad - if we remove and then insert an ES
diff --git a/modules/stream_out/rtp.h b/modules/stream_out/rtp.h
index aec9dde..5372146 100644
--- a/modules/stream_out/rtp.h
+++ b/modules/stream_out/rtp.h
@@ -36,9 +36,9 @@ void RtspDelId( rtsp_stream_t *rtsp, rtsp_stream_id_t * );
char *SDPGenerate( const sout_stream_t *p_stream, const char *rtsp_url );
-int rtp_add_sink( sout_stream_id_t *id, int fd, bool rtcp_mux );
+int rtp_add_sink( sout_stream_id_t *id, int fd, bool rtcp_mux, uint16_t *seq );
void rtp_del_sink( sout_stream_id_t *id, int fd );
-uint16_t rtp_get_seq( const sout_stream_id_t *id );
+uint16_t rtp_get_seq( sout_stream_id_t *id );
unsigned rtp_get_num( const sout_stream_id_t *id );
/* RTP packetization */
diff --git a/modules/stream_out/rtsp.c b/modules/stream_out/rtsp.c
index 61d81fa..a8e3027 100644
--- a/modules/stream_out/rtsp.c
+++ b/modules/stream_out/rtsp.c
@@ -646,16 +646,19 @@ static int RtspHandler( rtsp_stream_t *rtsp, rtsp_stream_id_t *id,
rtsp_strack_t *tr = ses->trackv + i;
if( ( id == NULL ) || ( tr->id == id->sout_id ) )
{
+ uint16_t seq;
if( !tr->playing )
{
tr->playing = true;
- rtp_add_sink( tr->id, tr->fd, false );
+ rtp_add_sink( tr->id, tr->fd, false, &seq );
}
+ else
+ seq = rtp_get_seq( tr->id );
infolen += sprintf( info + infolen,
"url=%s/trackID=%u;seq=%u, ",
control,
rtp_get_num( tr->id ),
- rtp_get_seq( tr->id ) );
+ seq );
}
}
if( infolen > 0 )
Regards,
--
Pierre Ynard
"Une âme dans un corps, c'est comme un dessin sur une feuille de papier."
More information about the vlc-devel
mailing list