EMIPLIB

miprtpdecoder.h

Go to the documentation of this file.
00001 /*
00002     
00003   This file is a part of EMIPLIB, the EDM Media over IP Library.
00004   
00005   Copyright (C) 2006-2011  Hasselt University - Expertise Centre for
00006                       Digital Media (EDM) (http://www.edm.uhasselt.be)
00007 
00008   This library is free software; you can redistribute it and/or
00009   modify it under the terms of the GNU Lesser General Public
00010   License as published by the Free Software Foundation; either
00011   version 2.1 of the License, or (at your option) any later version.
00012 
00013   This library is distributed in the hope that it will be useful,
00014   but WITHOUT ANY WARRANTY; without even the implied warranty of
00015   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00016   Lesser General Public License for more details.
00017 
00018   You should have received a copy of the GNU Lesser General Public
00019   License along with this library; if not, write to the Free Software
00020   Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  
00021   USA
00022 
00023 */
00024 
00029 #ifndef MIPRTPDECODER_H
00030 
00031 #define MIPRTPDECODER_H
00032 
00033 #include "mipconfig.h"
00034 #include "mipcomponent.h"
00035 #include "miptime.h"
00036 #if defined(WIN32) || defined(_WIN32_WCE)
00037         #include <hash_map>
00038 #else
00039         #include <ext/hash_map>
00040 #endif // Win32
00041 #include <cmath>
00042 #include <list>
00043 
00044 namespace jrtplib
00045 {
00046         class RTPSession;
00047 }
00048 
00049 class MIPRTPReceiveMessage;
00050 class MIPRTPSynchronizer;
00051 class MIPMediaMessage;
00052 class MIPRTPPacketDecoder;
00053 
00054 #define MIPRTPDECODER_MAXPAYLOADDECODERS                                                        256
00055 
00065 class EMIPLIB_IMPORTEXPORT MIPRTPDecoder : public MIPComponent
00066 {
00067 public:
00068         MIPRTPDecoder();
00069         ~MIPRTPDecoder();
00070 
00081         bool init(bool calcStreamTime = true, MIPRTPSynchronizer *pSynchronizer = 0, jrtplib::RTPSession *pRTPSess = 0);
00082 
00086         bool setDefaultPacketDecoder(MIPRTPPacketDecoder *pDec);
00087 
00092         bool setPacketDecoder(uint8_t payloadType, MIPRTPPacketDecoder *pDec);
00093 
00098         void setMaximumJitterBuffering(MIPTime t)                                                               { m_maxJitterBuffer = t; }
00099 
00100         bool push(const MIPComponentChain &chain, int64_t iteration, MIPMessage *pMsg);
00101         bool pull(const MIPComponentChain &chain, int64_t iteration, MIPMessage **pMsg);
00102         bool processFeedback(const MIPComponentChain &chain, int64_t feedbackChainID, MIPFeedback *feedback);
00103 private:
00104         void clearMessages();
00105         void cleanUp();
00106         void cleanUpSourceTable();
00107         bool lookUpStreamTime(uint32_t ssrc, uint32_t timestamp, const uint8_t *pCName, size_t cnameLength, real_t timestampUnit, MIPTime &streamTime, bool &shouldSync);
00108         bool adjustToPlaybackTime(MIPTime jitterValue, MIPTime &streamTime, MIPTime &insertOffset);
00109 
00110         bool m_init;    
00111         int64_t m_prevIteration;
00112         std::list<MIPMediaMessage *> m_messages;
00113         std::list<MIPMediaMessage *>::const_iterator m_msgIt;
00114 
00115         bool m_gotPlaybackFeedback;
00116         MIPTime m_playbackOffset;
00117 
00118         class SSRCInfo
00119         {
00120         public:
00121                 SSRCInfo(uint32_t baseTimestamp = 0) : m_lastAccessTime(0), m_playbackOffset(0), m_avgInsertTime(0),
00122                                                         m_insertTimeSpread(0), m_lastOffsetAdjustTime(0), m_lastSyncTime(0), m_syncOffset(0)
00123                                                                         { reset(baseTimestamp); m_syncStreamID = -1; }
00124                 void setSyncStreamID(int64_t id)                        { m_syncStreamID = id; }
00125                 int64_t getSyncStreamID() const                         { return m_syncStreamID; }
00126                 MIPTime getLastSyncTime() const                         { return m_lastSyncTime; }
00127                 void setLastSyncTime(MIPTime t)                         { m_lastSyncTime = t; }
00128                 MIPTime getSyncOffset() const                           { return m_syncOffset; }
00129                 void setSyncOffset(MIPTime t)                           { m_syncOffset = t; }
00130 
00131                 MIPTime getLastAccessTime() const                       { return m_lastAccessTime; }
00132                 uint64_t getBaseTimestamp() const                       { return m_baseTimestamp; }
00133                 uint64_t getExtendedTimestamp(uint32_t ts);
00134                 void setLastAccessTime(MIPTime t)                       { m_lastAccessTime = t; }
00135                 
00136                 MIPTime getPlaybackOffset() const                       { return m_playbackOffset; }
00137                 MIPTime getInsertTimeAverage() const                    { return m_avgInsertTime; }
00138                 MIPTime getInsertTimeVariance() const                   { return m_insertTimeSpread; }
00139                 MIPTime getLastOffsetAdjustTime() const                 { return m_lastOffsetAdjustTime; }
00140                 bool hasLastOffsetAdjustTime() const                    { return m_gotPlaybackOffset; }
00141                 int64_t getNumberOfRecentPacket() const                 { return m_recentPacksReceived; }
00142                 
00143                 int getNumberOfInsertTimes() const                      { return m_numInsertTimes; }
00144                         
00145                 void setPlaybackOffset(MIPTime offset)                  { clearAdjustmentInfo(); m_playbackOffset = offset; m_gotPlaybackOffset = true; m_lastOffsetAdjustTime = MIPTime::getCurrentTime(); }
00146                 void addInsertTime(MIPTime t)
00147                 {
00148 #define MIPRTPDECODER_HISTLEN 16
00149                         m_insertTimes[m_curInsertTimePos] = t;
00150                         m_curInsertTimePos++;
00151                         if (m_curInsertTimePos == MIPRTPDECODER_HISTLEN)
00152                                 m_curInsertTimePos = 0;
00153                         if (m_numInsertTimes < MIPRTPDECODER_HISTLEN)
00154                                 m_numInsertTimes++;
00155 
00156                         real_t avg = 0;
00157                         real_t sigma2 = 0;
00158                         for (int i = 0 ; i < m_numInsertTimes ; i++)
00159                                 avg += m_insertTimes[i].getValue();
00160                         avg /= (real_t)m_numInsertTimes;
00161 
00162                         for (int i = 0 ; i < m_numInsertTimes ; i++)
00163                         {
00164                                 real_t diff = m_insertTimes[i].getValue() - avg;
00165                                 real_t diff2 = diff*diff;
00166                                 sigma2 += diff2;
00167                         }
00168                         sigma2 /= (real_t)m_numInsertTimes;
00169                         real_t sigma = (real_t)sqrt(sigma2);
00170 
00171                         m_avgInsertTime = MIPTime(avg);
00172                         m_insertTimeSpread = MIPTime(sigma);
00173                 }
00174 
00175                 void clearAdjustmentInfo()
00176                 {
00177                         m_playbackOffset = MIPTime(0);
00178                         m_avgInsertTime = MIPTime(0);
00179                         m_insertTimeSpread = MIPTime(0);
00180                         m_lastOffsetAdjustTime = MIPTime(0);
00181                         m_gotPlaybackOffset = false;
00182                         m_recentPacksReceived = 0;
00183                         m_numInsertTimes = 0;
00184                         m_curInsertTimePos = 0;
00185                 }
00186                 
00187         private:
00188                 void reset(uint32_t baseTimestamp)                      
00189                 { 
00190                         m_baseTimestamp = (uint64_t)baseTimestamp; 
00191                         m_prevTimestamp = baseTimestamp; 
00192                         m_cycles = 0; 
00193                         m_lastAccessTime = MIPTime(0);
00194                         clearAdjustmentInfo();
00195                 }
00196 
00197                 uint64_t m_cycles;
00198                 uint64_t m_baseTimestamp;
00199                 uint32_t m_prevTimestamp;
00200                 MIPTime m_lastAccessTime;
00201                 MIPTime m_playbackOffset;
00202                 
00203                 MIPTime m_avgInsertTime;
00204                 MIPTime m_insertTimeSpread;
00205                 MIPTime m_insertTimes[MIPRTPDECODER_HISTLEN];
00206                 int m_numInsertTimes;
00207                 int m_curInsertTimePos;
00208                 
00209                 MIPTime m_lastOffsetAdjustTime;
00210                 bool m_gotPlaybackOffset;
00211                 int64_t m_recentPacksReceived;
00212 
00213                 int64_t m_syncStreamID;
00214                 MIPTime m_lastSyncTime;
00215                 MIPTime m_syncOffset;
00216         };
00217 
00218 #if defined(WIN32) || defined(_WIN32_WCE)
00219         stdext::hash_map<uint32_t, SSRCInfo> m_sourceTable;
00220 #else
00221         __gnu_cxx::hash_map<uint32_t, SSRCInfo> m_sourceTable;
00222 #endif // Win32
00223 
00224         MIPRTPPacketDecoder *m_pDecoders[MIPRTPDECODER_MAXPAYLOADDECODERS];
00225 
00226         MIPTime m_prevCleanTableTime;
00227         SSRCInfo *m_pSSRCInfo;
00228         bool m_calcStreamTime;
00229         MIPRTPSynchronizer *m_pSynchronizer;
00230         jrtplib::RTPSession *m_pRTPSess;
00231         MIPTime m_totalComponentDelay;
00232         MIPTime m_maxJitterBuffer;
00233 };
00234 
00235 #endif // MIPRTPDECODER_H
00236