RtpReceiver.cxx
上传用户:sy_wanhua
上传日期:2013-07-25
资源大小:3048k
文件大小:27k
源码类别:

流媒体/Mpeg4/MP4

开发平台:

C/C++

  1. /* ====================================================================
  2.  * The Vovida Software License, Version 1.0 
  3.  * 
  4.  * Copyright (c) 2000 Vovida Networks, Inc.  All rights reserved.
  5.  * 
  6.  * Redistribution and use in source and binary forms, with or without
  7.  * modification, are permitted provided that the following conditions
  8.  * are met:
  9.  * 
  10.  * 1. Redistributions of source code must retain the above copyright
  11.  *    notice, this list of conditions and the following disclaimer.
  12.  * 
  13.  * 2. Redistributions in binary form must reproduce the above copyright
  14.  *    notice, this list of conditions and the following disclaimer in
  15.  *    the documentation and/or other materials provided with the
  16.  *    distribution.
  17.  * 
  18.  * 3. The names "VOCAL", "Vovida Open Communication Application Library",
  19.  *    and "Vovida Open Communication Application Library (VOCAL)" must
  20.  *    not be used to endorse or promote products derived from this
  21.  *    software without prior written permission. For written
  22.  *    permission, please contact vocal@vovida.org.
  23.  *
  24.  * 4. Products derived from this software may not be called "VOCAL", nor
  25.  *    may "VOCAL" appear in their name, without prior written
  26.  *    permission of Vovida Networks, Inc.
  27.  * 
  28.  * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESSED OR IMPLIED
  29.  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
  30.  * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND
  31.  * NON-INFRINGEMENT ARE DISCLAIMED.  IN NO EVENT SHALL VOVIDA
  32.  * NETWORKS, INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT DAMAGES
  33.  * IN EXCESS OF $1,000, NOR FOR ANY INDIRECT, INCIDENTAL, SPECIAL,
  34.  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  35.  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  36.  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
  37.  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
  38.  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
  39.  * USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
  40.  * DAMAGE.
  41.  * 
  42.  * ====================================================================
  43.  * 
  44.  * This software consists of voluntary contributions made by Vovida
  45.  * Networks, Inc. and many individuals on behalf of Vovida Networks,
  46.  * Inc.  For more information on Vovida Networks, Inc., please see
  47.  * <http://www.vovida.org/>.
  48.  *
  49.  */
  50. static const char* const RtpReceiver_cxx_Version =
  51.     "$Id: RtpReceiver.cxx,v 1.26 2001/07/26 21:50:42 kle Exp $";
  52. #include <iostream>
  53. #include <stdlib.h>
  54. #include <stdio.h>
  55. #include <assert.h>
  56. #include <time.h>
  57. #include <sys/types.h>
  58. #include "vtypes.h"
  59. #include <unistd.h>
  60. #include <string.h>
  61. #include "cpLog.h"
  62. #include "vsock.hxx"
  63. #include "NetworkAddress.h"
  64. #include "NtpTime.hxx"
  65. #include "rtpTypes.h"
  66. #include "rtpTools.hxx"
  67. #include "Rtp.hxx"
  68. #include "Rtcp.hxx"
  69. #include "rtpCodec.h"
  70. static NtpTime nowTime, pastTime;
  71. /* ----------------------------------------------------------------- */
  72. /* --- RtpReceiver Constructor ------------------------------------- */
  73. /* ----------------------------------------------------------------- */
  74. RtpReceiver::RtpReceiver (int localMinPort, int localMaxPort,
  75.                           RtpPayloadType newApiFormat,
  76.                           RtpPayloadType newNetworkFormat, int jitterNew)
  77. {
  78.     /// udp stack is a sendrecv stack
  79.     myStack = new UdpStack (NULL, localMinPort, localMaxPort) ;
  80.     freeStack = true;
  81.     constructRtpReceiver (newApiFormat, newNetworkFormat, jitterNew);
  82. }
  83. RtpReceiver::RtpReceiver (int localPort, RtpPayloadType newApiFormat,
  84.                           RtpPayloadType newNetworkFormat,
  85.                           int jitterNew)
  86. {
  87.     /// udp stack is a sendrecv stack
  88.     myStack = new UdpStack (NULL, localPort) ;
  89.     freeStack = true;
  90.     constructRtpReceiver (newApiFormat, newNetworkFormat, jitterNew);
  91. }
  92. RtpReceiver::RtpReceiver (UdpStack* udp, RtpPayloadType newApiFormat,
  93.                           RtpPayloadType newNetworkFormat, int jitterNew)
  94. {
  95.     /// udp stack is a sendrecv stack
  96.     myStack = udp;
  97.     freeStack = false;
  98.     constructRtpReceiver (newApiFormat, newNetworkFormat, jitterNew);
  99. }
  100. void RtpReceiver::constructRtpReceiver (RtpPayloadType newApiFormat,
  101.                                         RtpPayloadType newNetworkFormat,
  102.                                         int jitterNew)
  103. {
  104.     inPos = 0;
  105.     playPos = 0;
  106.     memset (inBuff, 0, IN_BUFFER_SIZE);
  107.     // set format and baseSampleRate
  108.     setApiFormat(newApiFormat, 160, 0, NULL, false);
  109.     setNetworkFormat(newNetworkFormat, 160, 0, NULL, false);
  110.     // set private variables
  111.     jitterSeed = jitterNew;
  112.     // no transmitter
  113.     sourceSet = false;
  114.     ssrc = 0;
  115.     probationSet = false;
  116.     srcProbation = 0;
  117.     probation = -2;
  118.     prevPacket = NULL;
  119.     rtcpRecv = NULL;
  120.     silenceCodec = 0;
  121.     cpLog(LOG_DEBUG_STACK, "Constructed receiver");
  122. }
  123. RtpReceiver::~RtpReceiver ()
  124. {
  125.     if (freeStack)
  126.     {
  127.         delete myStack;
  128.         myStack = NULL;
  129.     }
  130.     rtcpRecv = NULL;
  131.     cpLog (LOG_DEBUG_STACK, "Close receiver");
  132. }
  133. /* --- receive packet functions ------------------------------------ */
  134. RtpPacket* RtpReceiver::receive ()
  135. {
  136.     RtpPacket* p = NULL;
  137.     int len = 0;
  138.     int len1 = 0;
  139.     // empty network que
  140.     NtpTime arrival (0, 0);
  141.     while (1) // network empty or time to play return packet
  142.     {
  143.         p = getPacket();
  144.         if (p == NULL) break;
  145.         // only play packets for valid sources
  146.         if (probation < 0)
  147.         {
  148.             cpLog(LOG_ERR, "****Packet from invalid source");
  149.             delete p;
  150.             p = NULL;
  151.             continue;
  152.         }
  153.         arrival = getNtpTime();
  154.         int packetTransit = 0;
  155.         int delay = 0;
  156.         rtp_ntohl(p);
  157.         // convert codec
  158.         if (p->getPayloadType() != apiFormat)
  159.         {
  160. #ifndef __sparc
  161.             // replace p with a new packet
  162.             RtpPacket* oldp = p;
  163.             p = convertRtpPacketCodec (apiFormat, oldp);
  164.             assert (oldp->getSequence() == p->getSequence());
  165.             delete oldp;
  166. #endif
  167.         }
  168.         len = p->getPayloadUsage();
  169.         if (len <= 0 || len > 1012)
  170.         {
  171.             cpLog(LOG_ERR, "Got an invalid packet size");
  172.             delete p;
  173.             p = NULL;
  174.             continue;
  175.         }
  176.         // drop SID packets
  177.         if (len < ( networkFormat_payloadSize / 3 ) )
  178.         {
  179.             cpLog( LOG_DEBUG_STACK, "Dropping SID packet" );
  180.             prevSeqRecv = p->getSequence();
  181.             delete p;
  182.             p = NULL;
  183.             continue;
  184.         }
  185.         // fix frame boundry
  186.         if (len > networkFormat_payloadSize )
  187.         {
  188.             len =  ( len / networkFormat_payloadSize ) * networkFormat_payloadSize;
  189.             cpLog( LOG_DEBUG_STACK, "Fixing frame boundry to %d", len );
  190.             p->setPayloadUsage( len );
  191.         }
  192.         // bypass jitterBuffer
  193.         if (jitterTime == -1)
  194.         {
  195.             cpLog( LOG_DEBUG_STACK, "Skipping jitter buffer" );
  196.             // update counters
  197.             prevSeqRecv = p->getSequence();
  198.             prevSeqPlay = p->getSequence();
  199.             // update packet received
  200.             packetReceived++;
  201.             payloadReceived += p->getPayloadUsage();
  202.             // update jitter calculation
  203.             packetTransit = arrival - rtp2ntp(p->getRtpTime());
  204.             delay = packetTransit - transit;
  205.             transit = packetTransit;
  206.             if (delay < 0) delay = -delay;
  207.             jitter += delay - ((jitter + 8) >> 4);
  208.             return p;
  209.         }
  210.         // reordering the packets according to the seq no
  211.         // leave gaps and copy the next packet in all the gap
  212.         // when the late packets come copy it into the correct pos
  213.         if (RtpSeqGreater(p->getSequence(), prevSeqRecv))
  214.         {
  215.             // insert packet at end, repeat filling buffer if sequence skipping
  216.             //bool cycleEnd = false;
  217. //            int w=0;
  218.             while (RtpSeqGreater(p->getSequence(), prevSeqRecv))
  219.             {
  220.                 // silence patching
  221.                 prevPacketRtpTime += network_pktSampleSize;
  222.                 while( RtpTimeGreater( p->getRtpTime(), prevPacketRtpTime ) )
  223.                 {
  224.                     if( cpLogGetPriority() >= LOG_DEBUG_HB )
  225.                     {
  226.                         cerr<<"s"<<network_pktSampleSize;
  227.                     }
  228.                     if( silenceCodec == 0 )
  229.                     {
  230.                         cpLog( LOG_DEBUG_STACK, "Patching silence" );
  231.                         silenceCodec = findSilenceCodec( p->getPayloadType(), len );
  232.                         if( silenceCodec == 0 )
  233.                         {
  234.                             if( len > rtpCodecInfo[ numRtpCodecInfo - 1 ].length )
  235.                             {
  236.                                 cpLog( LOG_ERR, "Requested codec too big to fake %d", len );
  237.                                 assert( 0 );
  238.                             }
  239.                             cpLog( LOG_DEBUG_STACK, "Faking silence packet with 0x00" );
  240.                             silenceCodec = (char*)&rtpCodecInfo[ numRtpCodecInfo - 1 ].silence;
  241.                         }
  242.                     }
  243.                     assert( silenceCodec );
  244.                     if ((inPos + len) < IN_BUFFER_SIZE)
  245.                     {   
  246.                         memcpy (inBuff + inPos, silenceCodec, len);
  247.                         inPos += len;
  248.                     }
  249.                     else
  250.                     {
  251.                         // circular memory copy 
  252.                         len1 = IN_BUFFER_SIZE - inPos;
  253.                         memcpy (inBuff + inPos, silenceCodec, len1);
  254.                         memcpy (inBuff, silenceCodec + len1, len - len1);
  255.                         inPos = len - len1;
  256.                     }
  257.                     prevPacketRtpTime += network_pktSampleSize;
  258.                 }
  259.                 if( prevPacketRtpTime != p->getRtpTime() )
  260.                 {
  261.                     cpLog( LOG_DEBUG_STACK,
  262.                            "prevPacketRtpTime(%u) != p->getRtpTime()(%u), networkPacketSize(%d)",
  263.                            prevPacketRtpTime, p->getRtpTime(), network_pktSampleSize );
  264.                     prevPacketRtpTime = p->getRtpTime();
  265.                 }
  266.                 if ((inPos + len) < IN_BUFFER_SIZE)
  267.                 {
  268.                     memcpy (inBuff + inPos, p->getPayloadLoc(), len);
  269.                     inPos += len;
  270.                 }
  271.                 else
  272.                 {
  273.                     // circular memory copy
  274.                     len1 = IN_BUFFER_SIZE - inPos;
  275.                     memcpy (inBuff + inPos, p->getPayloadLoc(), len1);
  276.                     memcpy (inBuff, p->getPayloadLoc() + len1, len - len1);
  277.                     inPos = len - len1;
  278.                 }
  279.                 // update counters
  280.                 RtpSeqNumber tSeq = prevSeqRecv;
  281.                 prevSeqRecv++;
  282.                 if (prevSeqRecv < tSeq)
  283.                 {
  284.                     cpLog(LOG_DEBUG_STACK, "Recv cycle");
  285.                     assert(prevSeqRecv == 0);
  286.                     recvCycles += RTP_SEQ_MOD;
  287.                 }
  288. //                w++;
  289.             }
  290. //            if (w > 1) cerr << "missing " << w << endl;
  291.             if (p->getSequence() != prevSeqRecv)
  292.             {
  293.                 cpLog(LOG_DEBUG_STACK, "Unequal packet:%d stack:%d",
  294.                       prevSeqRecv, p->getSequence());
  295.             }
  296.         }
  297.         else
  298.         {
  299. //            cerr << "late 1 " << endl;
  300.             // insert packet in middle
  301.             cpLog(LOG_DEBUG_STACK, "insert middle packet: %d prevSeq %d",
  302.                   p->getSequence(), prevSeqRecv);
  303.             RtpSeqNumber base_prevSeqRecv = prevSeqRecv;
  304.             int inSeqRecv = 1;
  305.             while (RtpSeqGreater(base_prevSeqRecv, p->getSequence()))
  306.             {
  307.                 inSeqRecv++;
  308.                 base_prevSeqRecv--;
  309.             }
  310.             int inPosTemp = inPos - inSeqRecv * len;
  311.             if (inPosTemp < 0) inPosTemp = IN_BUFFER_SIZE + inPosTemp;
  312.             if ((inPosTemp + len) < IN_BUFFER_SIZE)
  313.             {
  314.                 memcpy (inBuff + inPosTemp, p->getPayloadLoc(), len);
  315.             }
  316.             else
  317.             {
  318.                 // circular memory copy
  319.                 len1 = IN_BUFFER_SIZE - inPosTemp;
  320.                 memcpy (inBuff + inPosTemp, p->getPayloadLoc(), len1);
  321.                 memcpy (inBuff, (p->getPayloadLoc()) + len1, len - len1);
  322.             }
  323.         }
  324.         // update packet received
  325.         packetReceived++;
  326.         payloadReceived += len;
  327.         // update jitter calculation
  328.         packetTransit = arrival - rtp2ntp(p->getRtpTime());
  329.         delay = packetTransit - transit;
  330.         transit = packetTransit;
  331.         if (delay < 0) delay = -delay;
  332.         jitter += delay - ((jitter + 8) >> 4);
  333.         //    fractional
  334.         // s->jitterTime += (1./16.) * ((double)deley - s->jitterTime);
  335.         //    integer
  336.         //jitterTime += delay - ((jitterTime+8) >> 4);
  337.         if (p)
  338.         {
  339.             delete p;
  340.             p = NULL;
  341.         }
  342.     }
  343.     // check if time to play packet
  344.     if (getNtpTime() < gotime)
  345.     {
  346. //        cpLog(LOG_ERR,"wait");
  347.         //cout <<"w";
  348.         return NULL;
  349.     }
  350.     int packetSize = apiFormat_payloadSize;
  351.     // Only do catchup for the beginning packets  (is this needed? - kle)
  352. /*
  353.     if (! doneCatchup )
  354.     {
  355.         if ( ( inPos > packetSize * 2 )
  356.                 && ( playPos == 0 ) )
  357.         {
  358.             playPos = inPos - packetSize * 2;
  359.             cpLog(LOG_ERR, "catch up");
  360.         }
  361.         doneCatchup = true;
  362.     }
  363. */
  364.     // deque next packet
  365.     if ( (inPos == 0) && (playPos == 0) )
  366.     {
  367. //        cpLog (LOG_ERR, "Recv buffer is empty");
  368.         receiverError = recv_bufferEmpty;
  369.         return NULL;
  370.     }
  371.     if (((inPos + IN_BUFFER_SIZE - playPos) % IN_BUFFER_SIZE) < packetSize)
  372.     {
  373. //        cpLog (LOG_ERR,"Not enough data for a api packet size %d", packetSize);
  374.         receiverError = recv_bufferEmpty;
  375.         return NULL;
  376.     }
  377.     // create next packect
  378.     assert (!p);
  379.     p = new RtpPacket (packetSize);
  380.     if ( (playPos + packetSize) < IN_BUFFER_SIZE)
  381.     {
  382.         memcpy (p->getPayloadLoc(), inBuff + playPos, packetSize);
  383.         playPos += packetSize;
  384.     }
  385.     else
  386.     {
  387.         // circular memory copy
  388.         len1 = IN_BUFFER_SIZE - playPos;
  389.         memcpy (p->getPayloadLoc(), inBuff + playPos, len1);
  390.         memcpy (p->getPayloadLoc() + len1, inBuff, packetSize - len1);
  391.         playPos = packetSize - len1;
  392.     }
  393.     // finish packet
  394.     p->setSSRC (ssrc);
  395.     p->setPayloadType (apiFormat);
  396.     p->setPayloadUsage (packetSize);
  397.     p->setRtpTime (prevRtpTime + api_pktSampleSize);
  398.     p->setSequence (prevSeqPlay + 1);
  399.     if (probation > 0) probation --;
  400.     receiverError = recv_success;
  401.     if( ( prevRtpTime + network_pktSampleSize ) != p->getRtpTime() )
  402.     {
  403.         network_pktSampleSize = p->getRtpTime() - prevRtpTime;
  404.         cpLog( LOG_DEBUG_STACK, "Fixing network_rtpTime to %d", network_pktSampleSize );
  405.     }
  406.     prevRtpTime += network_pktSampleSize;
  407.     prevNtpTime = getNtpTime();
  408.     gotime = rtp2ntp (p->getRtpTime() + api_pktSampleSize) + jitterTime;
  409.     // update counters
  410.     RtpSeqNumber sSeq = prevSeqPlay;
  411.     prevSeqPlay++;
  412.     if (prevSeqPlay < sSeq)
  413.     {
  414.         cpLog(LOG_DEBUG_STACK, "Play cycle");
  415.         assert (prevSeqPlay == 0);
  416.         playCycles += RTP_SEQ_MOD;
  417.     }
  418.     return p;
  419. }
  420. RtpPacket* RtpReceiver::getPacket ()
  421. {
  422.     // check for network activity
  423.     fd_set netFD;
  424.     FD_ZERO (&netFD);
  425.     FD_SET (myStack->getSocketFD(), &netFD);
  426.     struct timeval timeout;
  427.     timeout.tv_sec = 0;
  428.     timeout.tv_usec = 0;
  429.     int selret = select (myStack->getSocketFD() + 1, &netFD, NULL, NULL, &timeout);
  430.     if (selret <= 0)
  431.     {
  432.         // select error or no network activity
  433.         if (selret < 0) cpLog(LOG_ERR, "Select loop error");
  434.         else 
  435.         {
  436. //            cpLog(LOG_ERR, "RtpReceiver receives %d pkts", packetReceived);
  437. //            cpLog(LOG_ERR, "UdpStack receives %d pkts", myStack->getPacketsReceived());
  438.             return NULL;
  439.         }
  440.     }
  441.     // create packet
  442.     RtpPacket* p = new RtpPacket (RECV_BUF);
  443.     assert (p);
  444.     // receive packet
  445.     int len;
  446.     NetworkAddress sender;
  447.     len = myStack->receiveFrom ((char*)p->getHeader(), p->getPacketAlloc(), &sender);
  448.     p->setTotalUsage (len);
  449.     // check packet
  450.     if( !p->isValid() )
  451.     {
  452.         cpLog(LOG_ERR, "****Packet is not valid");
  453.         delete p; p = NULL;
  454.         return NULL;
  455.     }
  456.     // check if rtp event
  457.     if (p->getPayloadType() == rtpPayloadDTMF_RFC2833 ||
  458.             p->getPayloadType() == rtpPayloadCiscoRtp)
  459.     {
  460.         recvEvent( p );
  461.         delete p; p = NULL;
  462.         return NULL;
  463.     }
  464.     // update receiver info
  465.     //   function may return 1, meaning packet
  466.     //   out of seq tolr or source not valid
  467.     if (updateSource(p))
  468.     {
  469.         cpLog(LOG_ERR, "****Packet is out of seq or source not valid");
  470.         delete p; p = NULL;
  471.         return NULL;
  472.     }
  473.     return p;
  474. }
  475. int RtpReceiver::updateSource (RtpPacket* p)
  476. {
  477.     // check if ssrc in probation list
  478.     if (sourceSet && p->getSSRC() == srcProbation && probationSet)
  479.         // old probation packets still in que
  480.         return 1;
  481.     // new source found or resync old source
  482.     if (!sourceSet || p->getSSRC() != ssrc)
  483.     {
  484.         if (addSource(p))
  485.             return 1;
  486.     }
  487.     // no vaild source yet
  488.     assert (probation >= 0);
  489.     // check if receiving new payload format
  490.     /*
  491.     if (p->getPayloadType() != networkFormat ||
  492.             p->getPayloadUsage() != networkFormat_payloadSize)
  493.     {
  494.         cpLog(LOG_DEBUG, "Transmitter changing payload parameters(%d/%d) (%d/%d)",
  495.             p->getPayloadType(), networkFormat,
  496.             p->getPayloadUsage(), networkFormat_payloadSize );
  497.         p->printPacket();
  498.         initSource(p);
  499.     }
  500.     */
  501.     if (p->getPayloadType() != networkFormat )
  502.     {
  503.         cpLog(LOG_DEBUG, "Transmitter changing payload parameters(%d/%d) (%d/%d)",
  504.             p->getPayloadType(), networkFormat,
  505.             p->getPayloadUsage(), networkFormat_payloadSize );
  506.         p->printPacket();
  507.         initSource(p);
  508.     }
  509.     // check if valid sequence window
  510.     RtpSeqNumber seq = p->getSequence();
  511.     if ( RtpSeqGreater(seq, prevSeqRecv) )  // future packet
  512.     {
  513.         if (seq > prevSeqRecv)
  514.         {
  515.             if ( (seq - prevSeqRecv) > MISORDER )
  516.             {
  517.                 // large sequence jump forward, skip over packets less then seq
  518.                 cpLog(LOG_DEBUG_STACK, "jump to %d (%d jumps)", seq, seq - prevSeqRecv);
  519.                 initSource (p);
  520.             }
  521.         }
  522.         else if ( (seq + RTP_SEQ_MOD - prevSeqRecv) > MISORDER)
  523.         {
  524.             cpLog(LOG_DEBUG_STACK, "jump cycle to %d (%d jumps)", seq, seq + RTP_SEQ_MOD - prevSeqRecv );
  525.             initSource (p);
  526.         }
  527.     }
  528.     else if ( RtpSeqGreater(prevSeqRecv, seq) )  // past packet
  529.     {
  530.         // check if the pkt is too late comparing to the pkt already
  531.         // played. Since the prevSeqPlay is irrelavant due to diff
  532.         // api_payload Size, use inPos and playPos to calculate.
  533.         int size = networkFormat_payloadSize;
  534.         int backNoOfSeq = (prevSeqRecv > seq) ?
  535.                           (prevSeqRecv - seq) : (prevSeqRecv + RTP_SEQ_MOD - seq );
  536.         if (inPos > playPos)
  537.         {
  538.             if ((inPos - (backNoOfSeq + 1) * size) < playPos)
  539.             {
  540.                 cpLog(LOG_DEBUG_STACK, "too late now: discard seq %d", seq);
  541.                 return 1;
  542.             }
  543.         }
  544.         else
  545.         {
  546.             if ((inPos + IN_BUFFER_SIZE - (backNoOfSeq + 1) * size) < playPos)
  547.             {
  548.                 cpLog(LOG_DEBUG_STACK, "too late now: discard seq %d", seq);
  549.                 return 1;
  550.             }
  551.         }
  552.     }
  553.     else // (seq == prevSeqRecv)  // present packet
  554.     {
  555.         // duplicate with previous packet
  556.         //cpLog(LOG_DEBUG_STACK,"duplicate packet %d", seq);
  557.         //return 1;
  558.     }
  559.     /*
  560.         // check late packets
  561.         if (RtpSeqGreater(prevSeqPlay, p->getSequence()))
  562.         {
  563.             // packet arrived late
  564.             cpLog(LOG_DEBUG_STACK,"late now:%d packet:%d", prevSeqPlay, p->getSequence());
  565.             //return 1;
  566.         }
  567.     */
  568.     return 0;
  569. }
  570. int RtpReceiver::addSource(RtpPacket* p)
  571. {
  572.     // don't allow ssrc changes without removing first
  573.     if (sourceSet)
  574.     {
  575.         if (probation < 4)
  576.         {
  577.             probation ++;
  578.             cpLog(LOG_ERR, "Rejecting new transmitter %d, keeping %d",
  579.                   p->getSSRC(), ssrc);
  580.             return 1;
  581.         }
  582.         else removeSource(ssrc);
  583.     }
  584.     // check if ssrc in probation list
  585.     if (sourceSet && p->getSSRC() == srcProbation && probationSet)
  586.         return 1;
  587.     sourceSet = true;
  588.     ssrc = p->getSSRC();
  589.     cpLog(LOG_DEBUG_STACK, "Received ssrc = %d", ssrc);
  590.     probation = 0;
  591.     packetReceived = 0;
  592.     payloadReceived = 0;
  593.     // init SDES and RTCP fields
  594.     if (rtcpRecv) rtcpRecv->addTranInfo(ssrc, this);
  595.     initSource (p);
  596.     return 0;
  597. }
  598. void RtpReceiver::initSource (RtpPacket* p)
  599. {
  600.     assert (ssrc == p->getSSRC());
  601.     cpLog(LOG_DEBUG_STACK, "InitSource %d with sequence %d and rtp time %d",
  602.           ssrc, p->getSequence(), p->getRtpTime());
  603.     seedSeq = p->getSequence();
  604.     seedNtpTime = getNtpTime();
  605.     seedRtpTime = p->getRtpTime();
  606.     // set receiving codec
  607.     if(p->getPayloadType() != networkFormat)
  608.     {
  609.         setNetworkFormat(p->getPayloadType(), p->getPayloadUsage(), 0, p);
  610.         int network_pktSampleSize_org = network_pktSampleSize;
  611.         if (networkFormat_perSampleSize)
  612.             network_pktSampleSize = p->getPayloadUsage() / networkFormat_perSampleSize;
  613.         else
  614.            setNetworkFormatCodec ();
  615.         if (network_pktSampleSize_org != network_pktSampleSize)
  616.             cpLog (LOG_DEBUG, "  Number of network samples corrected to %d", network_pktSampleSize);
  617.     }
  618.     inPos = 0;
  619.     playPos = 0;
  620.     // set timing information
  621.     prevRtpTime = p->getRtpTime() - network_pktSampleSize;
  622.     prevPacketRtpTime = prevRtpTime;
  623.     prevNtpTime = rtp2ntp(p->getRtpTime()) - network_pktSampleSize * 1000 / networkFormat_clockRate;
  624.     prevSeqRecv = p->getSequence() - 1;
  625.     prevSeqPlay = p->getSequence() - 1;
  626.     recvCycles = 0;
  627.     playCycles = 0;
  628.     transit = 0;
  629.     jitter = 0;
  630.     jitterTime = jitterSeed;
  631.     // set up next gotime
  632.     gotime = rtp2ntp (p->getRtpTime()) + jitterTime;
  633. }
  634. void RtpReceiver::removeSource (RtpSrc s, int flag)
  635. {
  636.     if (s != ssrc)
  637.         cpLog(LOG_DEBUG_STACK, "Removing non active source: %d", s);
  638.     // no longer listen to this source
  639.     probationSet = true;
  640.     srcProbation = s;
  641.     // no transmitter
  642.     sourceSet = false;
  643.     ssrc = 0;
  644.     probation = -2;
  645.     // remove from RTCP receiver
  646.     if (rtcpRecv && !flag) rtcpRecv->removeTranInfo (s, 1);
  647.     cpLog (LOG_DEBUG_STACK, "Removing source: %d", s);
  648. }
  649. NtpTime RtpReceiver::rtp2ntp (RtpTime rtpTime)
  650. {
  651.     NtpTime ntptime = seedNtpTime +
  652.                       ((rtpTime - seedRtpTime) * 1000 / apiFormat_clockRate);
  653.     return ntptime;
  654. }
  655. /*
  656. void RtpReceiver::clearBuffer()
  657. {
  658.     map<RtpSeqNumber, RtpPacket*>::iterator i = jitterBuffer.begin();
  659.     while (i != jitterBuffer.end())
  660.     {
  661.       cout << "jitter deleting: " << (i->second) << endl;
  662.         delete (i->second);
  663.         jitterBuffer.erase(i);
  664.         i = jitterBuffer.begin();
  665.     }
  666.     assert (jitterBuffer.empty());
  667. }
  668.  
  669.  
  670.  
  671. void RtpReceiver::printBuffer ()
  672. {
  673.     map<RtpSeqNumber, RtpPacket*>::iterator i = jitterBuffer.begin();
  674.     while (i != jitterBuffer.end())
  675.     {
  676.         cerr << (i->second)->getSequence() <<" ";
  677.         i++;
  678.     }
  679.     cerr <<endl;
  680. }
  681. */
  682. /* --- Session state functions ------------------------------------- */
  683. void RtpReceiver::emptyNetwork ()
  684. {
  685.     // set up network activit
  686.     fd_set netFD;
  687.     FD_ZERO (&netFD);
  688.     FD_SET (myStack->getSocketFD(), &netFD);
  689.     struct timeval timeout;
  690.     timeout.tv_sec = 0;
  691.     timeout.tv_usec = 0;
  692.     // create empty holder packet
  693.     RtpPacket* p = new RtpPacket (RECV_BUF);
  694.     assert (p);
  695.     // receive packets until no more activity
  696.     int len;
  697.     int selret = select (myStack->getSocketFD() + 1,
  698.                          &netFD, NULL, NULL, &timeout);
  699.     while (selret > 0)
  700.     {
  701.         len = myStack->receive (p->getPacketData(), p->getPacketAlloc());
  702.         if (len <= 0) break;
  703.         FD_ZERO (&netFD);
  704.         FD_SET (myStack->getSocketFD(), &netFD);
  705.         selret = select (myStack->getSocketFD() + 1,
  706.                          &netFD, NULL, NULL, &timeout);
  707.     }
  708.     delete p; p = NULL;
  709.     cpLog (LOG_DEBUG_STACK, "RtpReceiver: Done empty network queue");
  710. }
  711. /* --- Private Information for RTCP -------------------------------- */
  712. void RtpReceiver::setRTCPrecv (RtcpReceiver* s)
  713. {
  714.     rtcpRecv = s;
  715. }
  716. void RtpReceiver::setApiFormat (RtpPayloadType newtype, int no_samples, int packetSize,
  717.                                 RtpPacket* p, bool print)
  718. {
  719.     apiFormat = newtype;
  720.     api_pktSampleSize = no_samples;
  721.     apiFormat_perSampleSize = 1;
  722.     switch (newtype)
  723.     {
  724.         case rtpPayloadPCMU:
  725.         case rtpPayloadPCMA:
  726.         if (print) cpLog(LOG_DEBUG, "Setting api format to: PCMU %d", no_samples);
  727.         apiFormat_clockRate = 8000;
  728.         break;
  729.         case rtpPayloadL16_mono:
  730.         if (print) cpLog(LOG_DEBUG, "Setting api format to: L16 %d", no_samples);
  731.         apiFormat_clockRate = 44100;
  732.         apiFormat_perSampleSize = 2;
  733.         break;
  734.         case rtpPayloadG729:
  735.         if (print) cpLog(LOG_DEBUG, "Setting api format to: G729 %d", no_samples);
  736.         apiFormat_clockRate = 8000;
  737.         break;
  738.         default:
  739.         cpLog(LOG_ERR, "Unknown apiFormat: codec(%d) at sampleSize(%d) packetSize(%d)",
  740.               (int)newtype, no_samples, packetSize);
  741.         apiFormat_clockRate = 8000;
  742.     }
  743.     if (p)
  744.         apiFormat_payloadSize = p->getPayloadUsage();
  745.     else
  746.         apiFormat_payloadSize = api_pktSampleSize * apiFormat_perSampleSize;
  747.     if( packetSize != 0 )
  748.         apiFormat_payloadSize = packetSize;
  749. }
  750. void RtpReceiver::setNetworkFormat (RtpPayloadType newtype, int no_samples, int packetSize, 
  751.                                     RtpPacket* p, bool print)
  752. {
  753.     networkFormat = newtype;
  754.     network_pktSampleSize = no_samples;
  755.     networkFormat_perSampleSize = 1;
  756.     switch (newtype)
  757.     {
  758.         case rtpPayloadPCMU:
  759.         case rtpPayloadPCMA:
  760.         if (print) cpLog(LOG_DEBUG, "Setting network format to: PCMU %d", no_samples);
  761.         networkFormat_clockRate = 8000;
  762.         break;
  763.         case rtpPayloadL16_mono:
  764.         if (print) cpLog(LOG_DEBUG, "Setting network format to: L16 %d", no_samples);
  765.         networkFormat_clockRate = 44100;
  766.         networkFormat_perSampleSize = 2;
  767.         break;
  768.         case rtpPayloadG729:
  769.         if (print) cpLog(LOG_DEBUG, "Setting network format to: G729 %d", no_samples);
  770.         networkFormat_clockRate = 8000;
  771.         break;
  772.         default:
  773.         cpLog(LOG_ERR, "Unknown networkFormat: codec(%d) at sampleSize(%d) packetSize(%d)",
  774.               (int)newtype, no_samples, packetSize);
  775.         networkFormat_clockRate = 8000;
  776.     }
  777.     if (p)
  778.         networkFormat_payloadSize = p->getPayloadUsage();
  779.     else
  780.         networkFormat_payloadSize = network_pktSampleSize * networkFormat_perSampleSize;
  781.     if( packetSize != 0 )
  782.         networkFormat_payloadSize = packetSize;
  783. }