[Live-devel] [vlc] RTSP client in vlc 2.1

Gilles Chanteperdrix gilles.chanteperdrix at xenomai.org
Sat Dec 14 09:18:22 PST 2013


On 12/14/2013 05:40 PM, Ross Finlayson wrote:
> Unfortunately we can't do this, because it breaks the subsequent
> 'optimization' - at the end of the "handleCmd_TEARDOWN()" function.
> I.e., in the normal case, when an *entire* stream is torn down (using
> either a single aggregate "TEARDOWN" command, or via individual
> "TEARDOWN"s for each track), we immediately reclaim the
> "RTSPClientSession" structure.  (I don't want to rely upon the
> 'client liveness timeout' mechanism for this, because some people
> have disabled this mechanism, to allow for (broken) RTSP clients that
> don't send RTCP "RR" packets.)

Well, it seems to me the NULL pointer can be replaced with a Boolean flag.
So that the subsession pointer remains valid, but we can know if the
track has been set up or not.

>> I have done some modifications to live555 which could be submitted
>> as patches to this list if you are interested:
> 
>> - VorbisAudioRTPSink: fix memory corruption error (detected by
>> valgrind);
> 
> Yes please - I'm very much interested in this!

The thing is: I have not very well understood the error :-). I have 
disabled the code which packs several Vorbis frames into one packet, 
and the bug disappeared... I know exactly what stream causes the bug 
though.

> 
>> - Theora: implement RTPSink based on RFC draft (found in ffmpeg
>> sources).
> 
> This might also be useful.  Thanks.

Ok, will send.

> 
>> - H264VideoRTPSink: apply frame duration to the last RTP packet
>> instead of the first;
> 
> Are you referring to the "H264FUAFragmenter" code (that automatically
> fragments large NAL units into smaller NAL fragments, for
> transmission)?  Yes, lets see what you've done here; it might be
> fixing a bug.

It is not really a bug, it is just that the server sends the first RTP
packet, then pauses for duration, then sends the remaining packets, just
before starting the next frame. The patch is very simple:

diff --git a/liveMedia/H264VideoRTPSink.cpp b/liveMedia/H264VideoRTPSink.cpp
index 574610e..4bdfba1 100644
--- a/liveMedia/H264VideoRTPSink.cpp
+++ b/liveMedia/H264VideoRTPSink.cpp
@@ -276,6 +276,7 @@ void H264FUAFragmenter::doGetNextFrame() {
     if (fCurDataOffset >= fNumValidDataBytes) {
       // We're done with this data.  Reset the pointers for receiving new data:
       fNumValidDataBytes = fCurDataOffset = 1;
+      fDurationInMicroseconds = fSavedDuration;
     }
 
     // Complete delivery to the client:
@@ -299,7 +300,7 @@ void H264FUAFragmenter::afterGettingFrame1(unsigned frameSize,
   fNumValidDataBytes += frameSize;
   fSaveNumTruncatedBytes = numTruncatedBytes;
   fPresentationTime = presentationTime;
-  fDurationInMicroseconds = durationInMicroseconds;
+  fSavedDuration = durationInMicroseconds;
 
   // Deliver data to the client:
   doGetNextFrame();


diff --git a/liveMedia/include/H264VideoRTPSink.hh b/liveMedia/include/H264VideoRTPSink.hh
index fcb2fe5..64ce7bc 100644
--- a/liveMedia/include/H264VideoRTPSink.hh
+++ b/liveMedia/include/H264VideoRTPSink.hh
@@ -108,6 +108,7 @@ private:
   unsigned fCurDataOffset;
   unsigned fSaveNumTruncatedBytes;
   Boolean fLastFragmentCompletedNALUnit;
+  unsigned fSavedDuration;
 };
 
 
> 
> 
> However, I don't think I can make the other changes that you
> mentioned:
> 
>> - Groupsock: when a receiving interface address is defined, bind
>> all sockets to it, and skip the "send to ourself a multicast
>> packet" trick; this is to accomodate the situation of an RTSP
>> server running on a machine with multiple interface with internet
>> connectivity but where we want to use only one interface;
> 
> Unfortunately I don't want to remove the 'send ourself a multicast
> packet' trick, because it's often the only reliable way that a host
> can figure out its own IP address.  Note, though, that if you have
> multiple interfaces, and want to use one in particular, then you can
> do so simply by ensuring that the interface that you want is the one
> on which IP multicast routing is enabled - i.e., it has a route for
> 224/8

The point is: if the application has set ReceivingInterfaceAddr, 
we pretty much know what is our IP address: it is ReceivingInterfaceAddr.

> 
>> - RTP/RTCP use the "feedface"/first receiver report to fix the
>> client ports if NAT is running without "conntrack_rtsp";
> 
> This seems like a security risk - i.e., it would allow an attacker to
> send the server a bogus initial packet, in order to 'hijack' the
> stream's traffic.

I tried to implement this carefully, if I receive the feedface packet
or the first receiver report on the port which was negotiated, I do not
take any other changes into account. I would have to check for RTCP.
That said, it fixes a case where the user does not receive any stream, 
so, he will not see that his session is hijacked :-).

> 
>> - MultiFrameRTPSink: implement bitrate limiting, in order to allow
>> streaming from a machine with high-speed connectivity to another
>> machine with high-speed connectivity going through a path with a
>> "weak-link" with slow connectivity (typically, from an internet
>> address to my personal PC through a DSL line)
> 
> How are you figuring out that 'bitrate limiting' is needed?  By using
> feedback in RTCP "RR" reports (i.e., using the "RTPTransmissionStats"
> database)?  In any case, I don't see how this can be done in
> "MultiFramedRTPSink" as a general mechanism, because the choice of
> which outgoing packets to skip should really be codec dependent.
> I.e., some frames (especially 'key' frames) are more important to
> send than others, and the "MultiFramedRTPSink" code - being codec
> independent - can't know this.

I am always limiting bitrate. The source gives me the limit. I have used
this patch in two contexts:
- when streaming from a file, the bitrate can be computed precisely by 
reading ahead in the file;
- when streaming from a hardware encoder configured with constant bitrate,
I set the limit to a bit above the constant bitrate.

The idea is to always spread packets in time to avoid accumulation in
intermediary network equipments. This reduces greatly the UDP packets
loss.

Regards.


-- 
                                                                Gilles.


More information about the live-devel mailing list