[Live-devel] [PATCH] Parse SDP bandwidth line and use to set the receive socket buffer size
Ben Hutchings
ben at decadent.org.uk
Sun Sep 20 09:12:32 PDT 2009
This is required to avoid packet loss for high-bandwidth codecs such as
DV video.
Ben.
diff --git a/liveMedia/MediaSession.cpp b/liveMedia/MediaSession.cpp
index 2768157..1a09f2c 100644
--- a/liveMedia/MediaSession.cpp
+++ b/liveMedia/MediaSession.cpp
@@ -211,6 +211,7 @@ Boolean MediaSession::initializeWithSDP(char const* sdpDescription) {
// Check for various special SDP lines that we understand:
if (subsession->parseSDPLine_c(sdpLine)) continue;
+ if (subsession->parseSDPLine_b(sdpLine)) continue;
if (subsession->parseSDPAttribute_rtpmap(sdpLine)) continue;
if (subsession->parseSDPAttribute_control(sdpLine)) continue;
if (subsession->parseSDPAttribute_range(sdpLine)) continue;
@@ -540,7 +541,7 @@ MediaSubsession::MediaSubsession(MediaSession& parent)
fClientPortNum(0), fRTPPayloadFormat(0xFF),
fSavedSDPLines(NULL), fMediumName(NULL), fCodecName(NULL), fProtocolName(NULL),
fRTPTimestampFrequency(0), fControlPath(NULL),
- fSourceFilterAddr(parent.sourceFilterAddr()),
+ fSourceFilterAddr(parent.sourceFilterAddr()), fBandwidth(0),
fAuxiliarydatasizelength(0), fConstantduration(0), fConstantsize(0),
fCRC(0), fCtsdeltalength(0), fDe_interleavebuffersize(0), fDtsdeltalength(0),
fIndexdeltalength(0), fIndexlength(0), fInterleaving(0), fMaxdisplacement(0),
@@ -690,6 +691,13 @@ Boolean MediaSubsession::initiate(int useSpecialRTPoffset) {
if (!success) break; // a fatal error occurred trying to create the RTP and RTCP sockets; we can't continue
}
+ // Try to use a big receive buffer for RTP - at least 0.1 second of
+ // specified bandwidth and at least 50 KB
+ unsigned rtpBufSize = fBandwidth * 25 / 2; // 1 kbps * 0.1 s = 12.5 bytes
+ if (rtpBufSize < 50 * 1024)
+ rtpBufSize = 50 * 1024;
+ increaseReceiveBufferTo(env(), fRTPSocket->socketNum(), rtpBufSize);
+
// ASSERT: fRTPSocket != NULL && fRTCPSocket != NULL
if (isSSM()) {
// Special case for RTCP SSM: Send RTCP packets back to the source via unicast:
@@ -892,7 +900,10 @@ Boolean MediaSubsession::initiate(int useSpecialRTPoffset) {
// Finally, create our RTCP instance. (It starts running automatically)
if (fRTPSource != NULL) {
- unsigned totSessionBandwidth = 500; // HACK - later get from SDP#####
+ // If bandwidth is specified, use it and add 5% for RTCP overhead.
+ // Otherwise make a guess at 500 kbps.
+ unsigned totSessionBandwidth
+ = fBandwidth ? fBandwidth + fBandwidth / 20 : 500;
fRTCPInstance = RTCPInstance::createNew(env(), fRTCPSocket,
totSessionBandwidth,
(unsigned char const*)
@@ -1028,6 +1039,12 @@ Boolean MediaSubsession::parseSDPLine_c(char const* sdpLine) {
return False;
}
+Boolean MediaSubsession::parseSDPLine_b(char const* sdpLine) {
+ // Check for "b=<bwtype>:<bandwidth>" line
+ // RTP applications are expected to use bwtype="AS"
+ return sscanf(sdpLine, "b=AS:%u", &fBandwidth) == 1;
+}
+
Boolean MediaSubsession::parseSDPAttribute_rtpmap(char const* sdpLine) {
// Check for a "a=rtpmap:<fmt> <codec>/<freq>" line:
// (Also check without the "/<freq>"; RealNetworks omits this)
diff --git a/liveMedia/MultiFramedRTPSource.cpp b/liveMedia/MultiFramedRTPSource.cpp
index dee9a53..1e4bdc4 100644
--- a/liveMedia/MultiFramedRTPSource.cpp
+++ b/liveMedia/MultiFramedRTPSource.cpp
@@ -68,9 +68,6 @@ MultiFramedRTPSource
: RTPSource(env, RTPgs, rtpPayloadFormat, rtpTimestampFrequency) {
reset();
fReorderingBuffer = new ReorderingPacketBuffer(packetFactory);
-
- // Try to use a big receive buffer for RTP:
- increaseReceiveBufferTo(env, RTPgs->socketNum(), 50*1024);
}
void MultiFramedRTPSource::reset() {
diff --git a/liveMedia/include/MediaSession.hh b/liveMedia/include/MediaSession.hh
index 5b9ad06..a73bb46 100644
--- a/liveMedia/include/MediaSession.hh
+++ b/liveMedia/include/MediaSession.hh
@@ -249,6 +249,7 @@ protected:
void setNext(MediaSubsession* next) { fNext = next; }
Boolean parseSDPLine_c(char const* sdpLine);
+ Boolean parseSDPLine_b(char const* sdpLine);
Boolean parseSDPAttribute_rtpmap(char const* sdpLine);
Boolean parseSDPAttribute_control(char const* sdpLine);
Boolean parseSDPAttribute_range(char const* sdpLine);
@@ -274,6 +275,7 @@ protected:
unsigned fRTPTimestampFrequency;
char* fControlPath; // holds optional a=control: string
struct in_addr fSourceFilterAddr; // used for SSM
+ unsigned fBandwidth; // in kilobits, from b= line
// Parameters set by "a=fmtp:" SDP lines:
unsigned fAuxiliarydatasizelength, fConstantduration, fConstantsize;
--
1.6.4.3
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 828 bytes
Desc: This is a digitally signed message part
URL: <http://lists.live555.com/pipermail/live-devel/attachments/20090920/8180187a/attachment-0001.bin>
More information about the live-devel
mailing list