diff --git a/src/modules/audio_coding/neteq/neteq.gypi b/src/modules/audio_coding/neteq/neteq.gypi index c72efdd1af..5c0d080e1b 100644 --- a/src/modules/audio_coding/neteq/neteq.gypi +++ b/src/modules/audio_coding/neteq/neteq.gypi @@ -1,4 +1,4 @@ -# Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. +# Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. # # Use of this source code is governed by a BSD-style license # that can be found in the LICENSE file in the root of the source @@ -105,8 +105,8 @@ 'target_name': 'NetEqRTPplay', 'type': 'executable', 'dependencies': [ - 'NetEq', # NetEQ library defined above - 'NetEqTestTools',# Test helpers + 'NetEq', # NetEQ library defined above + 'NetEqTestTools', # Test helpers 'G711', 'G722', 'PCM16B', @@ -229,10 +229,25 @@ 'test/RTPcat.cc', ], }, + { + 'target_name': 'rtp_to_text', + 'type': 'executable', + 'dependencies': [ + 'NetEqTestTools', + '<(webrtc_root)/system_wrappers/source/system_wrappers.gyp:system_wrappers', + ], + 'sources': [ + 'test/rtp_to_text.cc', + ], + }, { 'target_name': 'NetEqTestTools', # Collection of useful functions used in other tests 'type': '<(library)', + 'variables': { + # Expects RTP packets without payloads when enabled. + 'neteq_dummy_rtp%': 0, + }, 'dependencies': [ 'G711', 'G722', @@ -269,21 +284,17 @@ 'test', ], 'sources': [ - 'test/NETEQTEST_NetEQClass.cc', - 'test/NETEQTEST_RTPpacket.cc', 'test/NETEQTEST_CodecClass.cc', - 'test/NETEQTEST_NetEQClass.h', - 'test/NETEQTEST_RTPpacket.h', 'test/NETEQTEST_CodecClass.h', + 'test/NETEQTEST_DummyRTPpacket.cc', + 'test/NETEQTEST_DummyRTPpacket.h', + 'test/NETEQTEST_NetEQClass.cc', + 'test/NETEQTEST_NetEQClass.h', + 'test/NETEQTEST_RTPpacket.cc', + 'test/NETEQTEST_RTPpacket.h', ], }, ], # targets }], # build_with_chromium ], # conditions } - -# Local Variables: -# tab-width:2 -# indent-tabs-mode:nil -# End: -# vim: set expandtab tabstop=2 shiftwidth=2: diff --git a/src/modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.cc b/src/modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.cc new file mode 100644 index 0000000000..e8d153b22e --- /dev/null +++ b/src/modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.cc @@ -0,0 +1,191 @@ +/* + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +#include "NETEQTEST_DummyRTPpacket.h" + +#include +#include +#include + +#ifdef WIN32 +#include +#else +#include // for htons, htonl, etc +#endif + +int NETEQTEST_DummyRTPpacket::readFromFile(FILE *fp) +{ + if (!fp) + { + return -1; + } + + WebRtc_UWord16 length, plen; + WebRtc_UWord32 offset; + + if (fread(&length, 2, 1, fp) == 0) + { + reset(); + return -2; + } + length = ntohs(length); + + if (fread(&plen, 2, 1, fp) == 0) + { + reset(); + return -1; + } + int packetLen = ntohs(plen); + + if (fread(&offset, 4, 1, fp) == 0) + { + reset(); + return -1; + } + // Store in local variable until we have passed the reset below. + WebRtc_UWord32 receiveTime = ntohl(offset); + + // Use length here because a plen of 0 specifies rtcp. + length = (WebRtc_UWord16) (length - _kRDHeaderLen); + + // check buffer size + if (_datagram && _memSize < length) + { + reset(); + } + + if (!_datagram) + { + _datagram = new WebRtc_UWord8[length]; + _memSize = length; + } + memset(_datagram, 0, length); + + if (length == 0) + { + _datagramLen = 0; + return packetLen; + } + + // Read basic header + if (fread((unsigned short *) _datagram, 1, _kBasicHeaderLen, fp) + != (size_t)_kBasicHeaderLen) + { + reset(); + return -1; + } + _receiveTime = receiveTime; + _datagramLen = _kBasicHeaderLen; + + // Parse the basic header + WebRtcNetEQ_RTPInfo tempRTPinfo; + int P, X, CC; + parseBasicHeader(&tempRTPinfo, &P, &X, &CC); + + // Check if we have to extend the header + if (X != 0 || CC != 0) + { + int newLen = _kBasicHeaderLen + CC * 4 + X * 4; + assert(_memSize >= newLen); + + // Read extension from file + size_t readLen = newLen - _kBasicHeaderLen; + if (fread((unsigned short *) _datagram + _kBasicHeaderLen, 1, readLen, + fp) != readLen) + { + reset(); + return -1; + } + _datagramLen = newLen; + + if (X != 0) + { + int totHdrLen = calcHeaderLength(X, CC); + assert(_memSize >= totHdrLen); + + // Read extension from file + size_t readLen = totHdrLen - newLen; + if (fread((unsigned short *) _datagram + newLen, 1, readLen, fp) + != readLen) + { + reset(); + return -1; + } + _datagramLen = totHdrLen; + } + } + _datagramLen = length; + + if (!_blockList.empty() && _blockList.count(payloadType()) > 0) + { + // discard this payload + return readFromFile(fp); + } + + return packetLen; + +} + +int NETEQTEST_DummyRTPpacket::writeToFile(FILE *fp) +{ + if (!fp) + { + return -1; + } + + WebRtc_UWord16 length, plen; + WebRtc_UWord32 offset; + + // length including RTPplay header + length = htons(_datagramLen + _kRDHeaderLen); + if (fwrite(&length, 2, 1, fp) != 1) + { + return -1; + } + + // payload length + plen = htons(_datagramLen); + if (fwrite(&plen, 2, 1, fp) != 1) + { + return -1; + } + + // offset (=receive time) + offset = htonl(_receiveTime); + if (fwrite(&offset, 4, 1, fp) != 1) + { + return -1; + } + + // Figure out the length of the RTP header. + int headerLen; + if (_datagramLen == 0) + { + // No payload at all; we are done writing to file. + headerLen = 0; + } + else + { + parseHeader(); + headerLen = _payloadPtr - _datagram; + assert(headerLen >= 0); + } + + // write RTP header + if (fwrite((unsigned short *) _datagram, 1, headerLen, fp) != + static_cast(headerLen)) + { + return -1; + } + + return (headerLen + _kRDHeaderLen); // total number of bytes written + +} + diff --git a/src/modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.h b/src/modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.h new file mode 100644 index 0000000000..ef7442199c --- /dev/null +++ b/src/modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.h @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +#ifndef NETEQTEST_DUMMYRTPPACKET_H +#define NETEQTEST_DUMMYRTPPACKET_H + +#include "NETEQTEST_RTPpacket.h" + +class NETEQTEST_DummyRTPpacket : public NETEQTEST_RTPpacket +{ +public: + virtual int readFromFile(FILE *fp); + virtual int writeToFile(FILE *fp); +}; + +#endif //NETEQTEST_DUMMYRTPPACKET_H diff --git a/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.cc b/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.cc index 2e60658cf8..6ff6a46589 100644 --- a/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.cc +++ b/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.cc @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -20,7 +20,8 @@ NETEQTEST_NetEQClass::NETEQTEST_NetEQClass() _bufferMem(NULL), _preparseRTP(false), _fsmult(1), - _isMaster(true) + _isMaster(true), + _noDecode(false) { #ifdef WINDOWS_TIMING _totTimeRecIn.QuadPart = 0; @@ -283,7 +284,14 @@ WebRtc_Word16 NETEQTEST_NetEQClass::recOut(WebRtc_Word16 *outData, void *msInfo, if (!msInfo) { // no msInfo given, do mono mode - err = WebRtcNetEQ_RecOut(_inst, outData, &outLen); + if (_noDecode) + { + err = WebRtcNetEQ_RecOutNoDecode(_inst, outData, &outLen); + } + else + { + err = WebRtcNetEQ_RecOut(_inst, outData, &outLen); + } } else { diff --git a/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.h b/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.h index c425b58f72..3e43125a38 100644 --- a/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.h +++ b/src/modules/audio_coding/neteq/test/NETEQTEST_NetEQClass.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -47,8 +47,10 @@ public: bool usingPreparseRTP() { return (_preparseRTP); }; void setMaster( bool isMaster = true ) { _isMaster = isMaster; }; void setSlave() { _isMaster = false; }; + void setNoDecode(bool noDecode = true) { _noDecode = noDecode; }; bool isMaster() { return (_isMaster); }; bool isSlave() { return (!_isMaster); }; + bool isNoDecode() { return _noDecode; }; #ifdef WINDOWS_TIMING double getRecInTime() { return (static_cast( _totTimeRecIn.QuadPart )); }; @@ -69,24 +71,11 @@ private: bool _preparseRTP; int _fsmult; bool _isMaster; + bool _noDecode; #ifdef WINDOWS_TIMING LARGE_INTEGER _totTimeRecIn; LARGE_INTEGER _totTimeRecOut; #endif }; - - -//class NETEQTEST_NetEQVector -//{ -//public: -// NETEQTEST_NetEQVector(int numChannels); -// NETEQTEST_NetEQVector(int numChannels, enum WebRtcNetEQDecoder *usedCodec, int noOfCodecs, -// WebRtc_UWord16 fs = 8000, WebRtcNetEQNetworkType nwType = kTCPLargeJitter); -// ~NETEQTEST_NetEQVector(); -// -//private: -// std::vector channels; -//}; - #endif //NETEQTEST_NETEQCLASS_H diff --git a/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.cc b/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.cc index 0412f06578..79e6b479b7 100644 --- a/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.cc +++ b/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.cc @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -19,12 +19,8 @@ #include // for htons, htonl, etc #endif -#include - -#include "gtest/gtest.h" - -#define HDR_SIZE 8 // rtpplay packet header size in bytes - +const int NETEQTEST_RTPpacket::_kRDHeaderLen = 8; +const int NETEQTEST_RTPpacket::_kBasicHeaderLen = 12; NETEQTEST_RTPpacket::NETEQTEST_RTPpacket() : @@ -41,88 +37,14 @@ _lost(false) _blockList.clear(); } -NETEQTEST_RTPpacket::NETEQTEST_RTPpacket(const NETEQTEST_RTPpacket& copyFromMe) -{ - - memcpy(this, ©FromMe, sizeof(NETEQTEST_RTPpacket)); - - _datagram = NULL; - _payloadPtr = NULL; - - if(copyFromMe._datagram) - { - _datagram = new WebRtc_UWord8[_memSize]; - - if(_datagram) - { - memcpy(_datagram, copyFromMe._datagram, _memSize); - } - } - - if(copyFromMe._payloadPtr) - { - _payloadPtr = _datagram + (copyFromMe._payloadPtr - copyFromMe._datagram); - } - - _blockList = copyFromMe._blockList; - -} - - -NETEQTEST_RTPpacket & NETEQTEST_RTPpacket::operator = (const NETEQTEST_RTPpacket & other) -{ - if (this != &other) // protect against invalid self-assignment - { - - // deallocate datagram memory if allocated - if(_datagram) - { - delete [] _datagram; - } - - // do shallow copy - memcpy(this, &other, sizeof(NETEQTEST_RTPpacket)); - - // reset pointers - _datagram = NULL; - _payloadPtr = NULL; - - if(other._datagram) - { - _datagram = new WebRtc_UWord8[other._memSize]; - _memSize = other._memSize; - - if(_datagram) - { - memcpy(_datagram, other._datagram, _memSize); - } - } - - if(other._payloadPtr) - { - _payloadPtr = _datagram + (other._payloadPtr - other._datagram); - } - - // copy the blocking list (map) - _blockList = other._blockList; - - } - - // by convention, always return *this - return *this; -} - - - NETEQTEST_RTPpacket::~NETEQTEST_RTPpacket() { - if(_datagram) + if(_datagram) { delete [] _datagram; } } - void NETEQTEST_RTPpacket::reset() { if(_datagram) { @@ -180,7 +102,7 @@ int NETEQTEST_RTPpacket::readFromFile(FILE *fp) return(-1); } - WebRtc_UWord16 length, plen; + WebRtc_UWord16 length, plen; WebRtc_UWord32 offset; if (fread(&length,2,1,fp)==0) @@ -203,9 +125,9 @@ int NETEQTEST_RTPpacket::readFromFile(FILE *fp) return(-1); } WebRtc_UWord32 receiveTime = ntohl(offset); // store in local variable until we have passed the reset below - - // Use length here because a plen of 0 specifies rtcp - length = (WebRtc_UWord16) (length - HDR_SIZE); + + // Use length here because a plen of 0 specifies rtcp + length = (WebRtc_UWord16) (length - _kRDHeaderLen); // check buffer size if (_datagram && _memSize < length) @@ -219,10 +141,10 @@ int NETEQTEST_RTPpacket::readFromFile(FILE *fp) _memSize = length; } - if (fread((unsigned short *) _datagram,1,length,fp) != length) + if (fread((unsigned short *) _datagram,1,length,fp) != length) { reset(); - return(-1); + return(-1); } _datagramLen = length; @@ -234,7 +156,7 @@ int NETEQTEST_RTPpacket::readFromFile(FILE *fp) return(readFromFile(fp)); } - return(packetLen); + return(packetLen); } @@ -289,7 +211,7 @@ int NETEQTEST_RTPpacket::writeToFile(FILE *fp) WebRtc_UWord32 offset; // length including RTPplay header - length = htons(_datagramLen + HDR_SIZE); + length = htons(_datagramLen + _kRDHeaderLen); if (fwrite(&length, 2, 1, fp) != 1) { return -1; @@ -301,7 +223,7 @@ int NETEQTEST_RTPpacket::writeToFile(FILE *fp) { return -1; } - + // offset (=receive time) offset = htonl(_receiveTime); if (fwrite(&offset, 4, 1, fp) != 1) @@ -317,7 +239,7 @@ int NETEQTEST_RTPpacket::writeToFile(FILE *fp) return -1; } - return _datagramLen + HDR_SIZE; // total number of bytes written + return _datagramLen + _kRDHeaderLen; // total number of bytes written } @@ -336,13 +258,13 @@ void NETEQTEST_RTPpacket::parseHeader() return; } - if (_datagramLen < 12) + if (_datagramLen < _kBasicHeaderLen) { // corrupt packet? return; } - _payloadLen = parseRTPheader(_datagram, _datagramLen, &_rtpInfo, &_payloadPtr); + _payloadLen = parseRTPheader(&_payloadPtr); _rtpParsed = true; @@ -397,8 +319,9 @@ WebRtc_UWord8 * NETEQTEST_RTPpacket::payload() const } } -WebRtc_Word16 NETEQTEST_RTPpacket::payloadLen() const +WebRtc_Word16 NETEQTEST_RTPpacket::payloadLen() { + parseHeader(); return _payloadLen; } @@ -420,10 +343,10 @@ bool NETEQTEST_RTPpacket::isLost() const WebRtc_UWord8 NETEQTEST_RTPpacket::payloadType() const { WebRtcNetEQ_RTPInfo tempRTPinfo; - - if(_datagram) + + if(_datagram && _datagramLen >= _kBasicHeaderLen) { - parseRTPheader(_datagram, _datagramLen, &tempRTPinfo); + parseRTPheader(&tempRTPinfo); } else { @@ -436,10 +359,10 @@ WebRtc_UWord8 NETEQTEST_RTPpacket::payloadType() const WebRtc_UWord16 NETEQTEST_RTPpacket::sequenceNumber() const { WebRtcNetEQ_RTPInfo tempRTPinfo; - - if(_datagram) + + if(_datagram && _datagramLen >= _kBasicHeaderLen) { - parseRTPheader(_datagram, _datagramLen, &tempRTPinfo); + parseRTPheader(&tempRTPinfo); } else { @@ -452,10 +375,10 @@ WebRtc_UWord16 NETEQTEST_RTPpacket::sequenceNumber() const WebRtc_UWord32 NETEQTEST_RTPpacket::timeStamp() const { WebRtcNetEQ_RTPInfo tempRTPinfo; - - if(_datagram) + + if(_datagram && _datagramLen >= _kBasicHeaderLen) { - parseRTPheader(_datagram, _datagramLen, &tempRTPinfo); + parseRTPheader(&tempRTPinfo); } else { @@ -468,10 +391,10 @@ WebRtc_UWord32 NETEQTEST_RTPpacket::timeStamp() const WebRtc_UWord32 NETEQTEST_RTPpacket::SSRC() const { WebRtcNetEQ_RTPInfo tempRTPinfo; - - if(_datagram) + + if(_datagram && _datagramLen >= _kBasicHeaderLen) { - parseRTPheader(_datagram, _datagramLen, &tempRTPinfo); + parseRTPheader(&tempRTPinfo); } else { @@ -484,10 +407,10 @@ WebRtc_UWord32 NETEQTEST_RTPpacket::SSRC() const WebRtc_UWord8 NETEQTEST_RTPpacket::markerBit() const { WebRtcNetEQ_RTPInfo tempRTPinfo; - - if(_datagram) + + if(_datagram && _datagramLen >= _kBasicHeaderLen) { - parseRTPheader(_datagram, _datagramLen, &tempRTPinfo); + parseRTPheader(&tempRTPinfo); } else { @@ -501,7 +424,7 @@ WebRtc_UWord8 NETEQTEST_RTPpacket::markerBit() const int NETEQTEST_RTPpacket::setPayloadType(WebRtc_UWord8 pt) { - + if (_datagramLen < 12) { return -1; @@ -520,7 +443,7 @@ int NETEQTEST_RTPpacket::setPayloadType(WebRtc_UWord8 pt) int NETEQTEST_RTPpacket::setSequenceNumber(WebRtc_UWord16 sn) { - + if (_datagramLen < 12) { return -1; @@ -540,7 +463,7 @@ int NETEQTEST_RTPpacket::setSequenceNumber(WebRtc_UWord16 sn) int NETEQTEST_RTPpacket::setTimeStamp(WebRtc_UWord32 ts) { - + if (_datagramLen < 12) { return -1; @@ -553,7 +476,7 @@ int NETEQTEST_RTPpacket::setTimeStamp(WebRtc_UWord32 ts) _datagram[4]=(unsigned char)((ts>>24)&0xFF); _datagram[5]=(unsigned char)((ts>>16)&0xFF); - _datagram[6]=(unsigned char)((ts>>8)&0xFF); + _datagram[6]=(unsigned char)((ts>>8)&0xFF); _datagram[7]=(unsigned char)(ts & 0xFF); return 0; @@ -562,7 +485,7 @@ int NETEQTEST_RTPpacket::setTimeStamp(WebRtc_UWord32 ts) int NETEQTEST_RTPpacket::setSSRC(WebRtc_UWord32 ssrc) { - + if (_datagramLen < 12) { return -1; @@ -584,7 +507,7 @@ int NETEQTEST_RTPpacket::setSSRC(WebRtc_UWord32 ssrc) int NETEQTEST_RTPpacket::setMarkerBit(WebRtc_UWord8 mb) { - + if (_datagramLen < 12) { return -1; @@ -616,10 +539,10 @@ int NETEQTEST_RTPpacket::setRTPheader(const WebRtcNetEQ_RTPInfo *RTPinfo) return -1; } - makeRTPheader(_datagram, - RTPinfo->payloadType, - RTPinfo->sequenceNumber, - RTPinfo->timeStamp, + makeRTPheader(_datagram, + RTPinfo->payloadType, + RTPinfo->sequenceNumber, + RTPinfo->timeStamp, RTPinfo->SSRC, RTPinfo->markerBit); @@ -627,7 +550,8 @@ int NETEQTEST_RTPpacket::setRTPheader(const WebRtcNetEQ_RTPInfo *RTPinfo) } -int NETEQTEST_RTPpacket::splitStereo(NETEQTEST_RTPpacket& slaveRtp, enum stereoModes mode) +int NETEQTEST_RTPpacket::splitStereo(NETEQTEST_RTPpacket* slaveRtp, + enum stereoModes mode) { // if mono, do nothing if (mode == stereoModeMono) @@ -639,7 +563,7 @@ int NETEQTEST_RTPpacket::splitStereo(NETEQTEST_RTPpacket& slaveRtp, enum stereoM parseHeader(); // start by copying the main rtp packet - slaveRtp = *this; + *slaveRtp = *this; if(_payloadLen == 0) { @@ -701,7 +625,7 @@ void NETEQTEST_RTPpacket::makeRTPheader(unsigned char* rtp_data, WebRtc_UWord8 p rtp_data[4]=(unsigned char)((timestamp>>24)&0xFF); rtp_data[5]=(unsigned char)((timestamp>>16)&0xFF); - rtp_data[6]=(unsigned char)((timestamp>>8)&0xFF); + rtp_data[6]=(unsigned char)((timestamp>>8)&0xFF); rtp_data[7]=(unsigned char)(timestamp & 0xFF); rtp_data[8]=(unsigned char)((ssrc>>24)&0xFF); @@ -711,65 +635,114 @@ void NETEQTEST_RTPpacket::makeRTPheader(unsigned char* rtp_data, WebRtc_UWord8 p rtp_data[11]=(unsigned char)(ssrc & 0xFF); } - -WebRtc_UWord16 NETEQTEST_RTPpacket::parseRTPheader(const WebRtc_UWord8 *datagram, int datagramLen, WebRtcNetEQ_RTPInfo *RTPinfo, WebRtc_UWord8 **payloadPtr) const +WebRtc_UWord16 + NETEQTEST_RTPpacket::parseRTPheader(WebRtcNetEQ_RTPInfo *RTPinfo, + WebRtc_UWord8 **payloadPtr) const { - WebRtc_Word16 *rtp_data = (WebRtc_Word16 *) datagram; - int i_P, i_X, i_CC, i_extlength=-1, i_padlength=0, i_startPosition; + WebRtc_Word16 *rtp_data = (WebRtc_Word16 *) _datagram; + int i_P, i_X, i_CC; - i_P=(((WebRtc_UWord16)(rtp_data[0] & 0x20))>>5); /* Extract the P bit */ - i_X=(((WebRtc_UWord16)(rtp_data[0] & 0x10))>>4); /* Extract the X bit */ - i_CC=(WebRtc_UWord16)(rtp_data[0] & 0xF); /* Get the CC number */ - RTPinfo->markerBit = (WebRtc_UWord8) ((rtp_data[0] >> 15) & 0x01); /* Get the marker bit */ - RTPinfo->payloadType = (WebRtc_UWord8) ((rtp_data[0] >> 8) & 0x7F); /* Get the coder type */ - RTPinfo->sequenceNumber = ((( ((WebRtc_UWord16)rtp_data[1]) >> 8) & 0xFF) | - ( ((WebRtc_UWord16)(rtp_data[1] & 0xFF)) << 8)); /* Get the packet number */ - RTPinfo->timeStamp = ((((WebRtc_UWord16)rtp_data[2]) & 0xFF) << 24) | - ((((WebRtc_UWord16)rtp_data[2]) & 0xFF00) << 8) | - ((((WebRtc_UWord16)rtp_data[3]) >> 8) & 0xFF) | - ((((WebRtc_UWord16)rtp_data[3]) & 0xFF) << 8); /* Get timestamp */ - RTPinfo->SSRC=((((WebRtc_UWord16)rtp_data[4]) & 0xFF) << 24) | - ((((WebRtc_UWord16)rtp_data[4]) & 0xFF00) << 8) | - ((((WebRtc_UWord16)rtp_data[5]) >> 8) & 0xFF) | - ((((WebRtc_UWord16)rtp_data[5]) & 0xFF) << 8); /* Get the SSRC */ + assert(_datagramLen >= 12); + parseBasicHeader(RTPinfo, &i_P, &i_X, &i_CC); - if (i_X==1) { - /* Extention header exists. Find out how many WebRtc_Word32 it consists of */ - i_extlength=((( ((WebRtc_UWord16)rtp_data[7+2*i_CC]) >> 8) & 0xFF) | - ( ((WebRtc_UWord16)(rtp_data[7+2*i_CC]&0xFF)) << 8)); - } - if (i_P==1) { - /* Padding exists. Find out how many bytes the padding consists of */ - if (datagramLen & 0x1) { - /* odd number of bytes => last byte in higher byte */ - i_padlength=(rtp_data[datagramLen>>1] & 0xFF); - } else { - /* even number of bytes => last byte in lower byte */ - i_padlength=(((WebRtc_UWord16)rtp_data[(datagramLen>>1)-1]) >> 8); - } - } + int i_startPosition = calcHeaderLength(i_X, i_CC); - i_startPosition=12+4*(i_extlength+1)+4*i_CC; + int i_padlength = calcPadLength(i_P); - if (payloadPtr) { - *payloadPtr = (WebRtc_UWord8*) &rtp_data[i_startPosition>>1]; + if (payloadPtr) + { + *payloadPtr = (WebRtc_UWord8*) &rtp_data[i_startPosition >> 1]; } - return (WebRtc_UWord16) (datagramLen-i_startPosition-i_padlength); + return (WebRtc_UWord16) (_datagramLen - i_startPosition - i_padlength); } -//void NETEQTEST_RTPpacket::splitStereoSample(WebRtc_UWord8 *data, WebRtc_UWord16 *lenBytes, WebRtc_UWord8 *slaveData, WebRtc_UWord16 *slaveLenBytes, int stride) -void NETEQTEST_RTPpacket::splitStereoSample(NETEQTEST_RTPpacket& slaveRtp, int stride) + +void NETEQTEST_RTPpacket::parseBasicHeader(WebRtcNetEQ_RTPInfo *RTPinfo, + int *i_P, int *i_X, int *i_CC) const { - if(!_payloadPtr || !slaveRtp._payloadPtr - || _payloadLen <= 0 || slaveRtp._memSize < _memSize) + WebRtc_Word16 *rtp_data = (WebRtc_Word16 *) _datagram; + if (_datagramLen < 12) + { + assert(false); + return; + } + + *i_P=(((WebRtc_UWord16)(rtp_data[0] & 0x20))>>5); /* Extract the P bit */ + *i_X=(((WebRtc_UWord16)(rtp_data[0] & 0x10))>>4); /* Extract the X bit */ + *i_CC=(WebRtc_UWord16)(rtp_data[0] & 0xF); /* Get the CC number */ + /* Get the marker bit */ + RTPinfo->markerBit = (WebRtc_UWord8) ((rtp_data[0] >> 15) & 0x01); + /* Get the coder type */ + RTPinfo->payloadType = (WebRtc_UWord8) ((rtp_data[0] >> 8) & 0x7F); + /* Get the packet number */ + RTPinfo->sequenceNumber = ((( ((WebRtc_UWord16)rtp_data[1]) >> 8) & 0xFF) | + ( ((WebRtc_UWord16)(rtp_data[1] & 0xFF)) << 8)); + /* Get timestamp */ + RTPinfo->timeStamp = ((((WebRtc_UWord16)rtp_data[2]) & 0xFF) << 24) | + ((((WebRtc_UWord16)rtp_data[2]) & 0xFF00) << 8) | + ((((WebRtc_UWord16)rtp_data[3]) >> 8) & 0xFF) | + ((((WebRtc_UWord16)rtp_data[3]) & 0xFF) << 8); + /* Get the SSRC */ + RTPinfo->SSRC=((((WebRtc_UWord16)rtp_data[4]) & 0xFF) << 24) | + ((((WebRtc_UWord16)rtp_data[4]) & 0xFF00) << 8) | + ((((WebRtc_UWord16)rtp_data[5]) >> 8) & 0xFF) | + ((((WebRtc_UWord16)rtp_data[5]) & 0xFF) << 8); +} + +int NETEQTEST_RTPpacket::calcHeaderLength(int i_X, int i_CC) const +{ + int i_extlength = 0; + WebRtc_Word16 *rtp_data = (WebRtc_Word16 *) _datagram; + + if (i_X == 1) + { + // Extension header exists. + // Find out how many WebRtc_Word32 it consists of. + assert(_datagramLen > 2 * (7 + 2 * i_CC)); + if (_datagramLen > 2 * (7 + 2 * i_CC)) + { + i_extlength = (((((WebRtc_UWord16) rtp_data[7 + 2 * i_CC]) >> 8) + & 0xFF) | (((WebRtc_UWord16) (rtp_data[7 + 2 * i_CC] & 0xFF)) + << 8)) + 1; + } + } + + return 12 + 4 * i_extlength + 4 * i_CC; +} + +int NETEQTEST_RTPpacket::calcPadLength(int i_P) const +{ + WebRtc_Word16 *rtp_data = (WebRtc_Word16 *) _datagram; + if (i_P == 1) + { + /* Padding exists. Find out how many bytes the padding consists of. */ + if (_datagramLen & 0x1) + { + /* odd number of bytes => last byte in higher byte */ + return rtp_data[_datagramLen >> 1] & 0xFF; + } + else + { + /* even number of bytes => last byte in lower byte */ + return ((WebRtc_UWord16) rtp_data[(_datagramLen >> 1) - 1]) >> 8; + } + } + return 0; +} + +void NETEQTEST_RTPpacket::splitStereoSample(NETEQTEST_RTPpacket* slaveRtp, + int stride) +{ + if(!_payloadPtr || !slaveRtp || !slaveRtp->_payloadPtr + || _payloadLen <= 0 || slaveRtp->_memSize < _memSize) { return; } WebRtc_UWord8 *readDataPtr = _payloadPtr; WebRtc_UWord8 *writeDataPtr = _payloadPtr; - WebRtc_UWord8 *slaveData = slaveRtp._payloadPtr; + WebRtc_UWord8 *slaveData = slaveRtp->_payloadPtr; while (readDataPtr - _payloadPtr < _payloadLen) { @@ -789,23 +762,22 @@ void NETEQTEST_RTPpacket::splitStereoSample(NETEQTEST_RTPpacket& slaveRtp, int s } _payloadLen /= 2; - slaveRtp._payloadLen = _payloadLen; + slaveRtp->_payloadLen = _payloadLen; } -//void NETEQTEST_RTPpacket::splitStereoFrame(WebRtc_UWord8 *data, WebRtc_UWord16 *lenBytes, WebRtc_UWord8 *slaveData, WebRtc_UWord16 *slaveLenBytes) -void NETEQTEST_RTPpacket::splitStereoFrame(NETEQTEST_RTPpacket& slaveRtp) +void NETEQTEST_RTPpacket::splitStereoFrame(NETEQTEST_RTPpacket* slaveRtp) { - if(!_payloadPtr || !slaveRtp._payloadPtr - || _payloadLen <= 0 || slaveRtp._memSize < _memSize) + if(!_payloadPtr || !slaveRtp || !slaveRtp->_payloadPtr + || _payloadLen <= 0 || slaveRtp->_memSize < _memSize) { return; } - memmove(slaveRtp._payloadPtr, _payloadPtr + _payloadLen/2, _payloadLen/2); + memmove(slaveRtp->_payloadPtr, _payloadPtr + _payloadLen/2, _payloadLen/2); _payloadLen /= 2; - slaveRtp._payloadLen = _payloadLen; + slaveRtp->_payloadLen = _payloadLen; } // Get the RTP header for the RED payload indicated by argument index. diff --git a/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.h b/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.h index 0478568620..16beb95dd4 100644 --- a/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.h +++ b/src/modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -27,15 +27,13 @@ class NETEQTEST_RTPpacket { public: NETEQTEST_RTPpacket(); - NETEQTEST_RTPpacket(const NETEQTEST_RTPpacket& copyFromMe); - NETEQTEST_RTPpacket & operator = (const NETEQTEST_RTPpacket & other); bool operator !() const { return (dataLen() < 0); }; - ~NETEQTEST_RTPpacket(); + virtual ~NETEQTEST_RTPpacket(); void reset(); static int skipFileHeader(FILE *fp); - int readFromFile(FILE *fp); + virtual int readFromFile(FILE *fp); int readFixedFromFile(FILE *fp, size_t len); - int writeToFile(FILE *fp); + virtual int writeToFile(FILE *fp); void blockPT(WebRtc_UWord8 pt); //WebRtc_Word16 payloadType(); void parseHeader(); @@ -43,7 +41,7 @@ public: WebRtcNetEQ_RTPInfo const * RTPinfo() const; WebRtc_UWord8 * datagram() const; WebRtc_UWord8 * payload() const; - WebRtc_Word16 payloadLen() const; + WebRtc_Word16 payloadLen(); WebRtc_Word16 dataLen() const; bool isParsed() const; bool isLost() const; @@ -64,7 +62,7 @@ public: int setRTPheader(const WebRtcNetEQ_RTPInfo *RTPinfo); - int splitStereo(NETEQTEST_RTPpacket& slaveRtp, enum stereoModes mode); + int splitStereo(NETEQTEST_RTPpacket* slaveRtp, enum stereoModes mode); int extractRED(int index, WebRtcNetEQ_RTPInfo& red); @@ -81,11 +79,25 @@ public: bool _lost; std::map _blockList; +protected: + static const int _kRDHeaderLen; + static const int _kBasicHeaderLen; + + void parseBasicHeader(WebRtcNetEQ_RTPInfo *RTPinfo, int *i_P, int *i_X, + int *i_CC) const; + int calcHeaderLength(int i_X, int i_CC) const; + private: - void makeRTPheader(unsigned char* rtp_data, WebRtc_UWord8 payloadType, WebRtc_UWord16 seqNo, WebRtc_UWord32 timestamp, WebRtc_UWord32 ssrc, WebRtc_UWord8 markerBit) const; - WebRtc_UWord16 parseRTPheader(const WebRtc_UWord8 *datagram, int datagramLen, WebRtcNetEQ_RTPInfo *RTPinfo, WebRtc_UWord8 **payloadPtr = NULL) const; - void splitStereoSample(NETEQTEST_RTPpacket& slaveRtp, int stride); - void splitStereoFrame(NETEQTEST_RTPpacket& slaveRtp); + void makeRTPheader(unsigned char* rtp_data, WebRtc_UWord8 payloadType, + WebRtc_UWord16 seqNo, WebRtc_UWord32 timestamp, + WebRtc_UWord32 ssrc, WebRtc_UWord8 markerBit) const; + WebRtc_UWord16 parseRTPheader(WebRtcNetEQ_RTPInfo *RTPinfo, + WebRtc_UWord8 **payloadPtr = NULL) const; + WebRtc_UWord16 parseRTPheader(WebRtc_UWord8 **payloadPtr = NULL) + { return parseRTPheader(&_rtpInfo, payloadPtr);}; + int calcPadLength(int i_P) const; + void splitStereoSample(NETEQTEST_RTPpacket* slaveRtp, int stride); + void splitStereoFrame(NETEQTEST_RTPpacket* slaveRtp); }; #endif //NETEQTEST_RTPPACKET_H diff --git a/src/modules/audio_coding/neteq/test/NetEqRTPplay.cc b/src/modules/audio_coding/neteq/test/NetEqRTPplay.cc index 09b0791d87..bb2d895aa9 100644 --- a/src/modules/audio_coding/neteq/test/NetEqRTPplay.cc +++ b/src/modules/audio_coding/neteq/test/NetEqRTPplay.cc @@ -19,6 +19,7 @@ #include "neteq_error_codes.h" // for the API test #include "NETEQTEST_RTPpacket.h" +#include "NETEQTEST_DummyRTPpacket.h" #include "NETEQTEST_NetEQClass.h" #include "NETEQTEST_CodecClass.h" @@ -67,7 +68,7 @@ #define TIME_STEP 1 #define FIRSTLINELEN 40 -#define MAX_NETEQ_BUFFERSIZE 170000 //100000 +#define MAX_NETEQ_BUFFERSIZE 170000 //100000 #define CHECK_ZERO(a) {int errCode = a; char tempErrName[WEBRTC_NETEQ_MAX_ERROR_NAME]; if((errCode)!=0){errCode = WebRtcNetEQ_GetErrorCode(inst); WebRtcNetEQ_GetErrorName(errCode, tempErrName, WEBRTC_NETEQ_MAX_ERROR_NAME); printf("\n %s \n line: %d \n error at %s\n Error Code = %d\n",__FILE__,__LINE__,#a, errCode); exit(0);}} #define CHECK_NOT_NULL(a) if((a)==NULL){printf("\n %s \n line: %d \nerror at %s\n",__FILE__,__LINE__,#a );return(-1);} //#define PLAY_CLEAN // ignore arrival times and let the packets arrive according to RTP timestamps @@ -113,8 +114,8 @@ typedef struct { void stereoInterleave(WebRtc_Word16 *data, WebRtc_Word16 totalLen); int getNextRecoutTime(FILE *fp, WebRtc_UWord32 *nextTime); void getNextExtraDelay(FILE *fp, WebRtc_UWord32 *t, int *d); -bool splitStereo(NETEQTEST_RTPpacket& rtp, NETEQTEST_RTPpacket& rtpSlave, - const WebRtc_Word16 *stereoPtype, const enum stereoModes *stereoMode, int noOfStereoCodecs, +bool splitStereo(NETEQTEST_RTPpacket* rtp, NETEQTEST_RTPpacket* rtpSlave, + const WebRtc_Word16 *stereoPtype, const enum stereoModes *stereoMode, int noOfStereoCodecs, const WebRtc_Word16 *cngPtype, int noOfCngCodecs, bool *isStereo); void parsePtypeFile(FILE *ptypeFile, std::map* decoders); @@ -134,10 +135,10 @@ WebRtc_Word16 NetEqPacketBuffer[MAX_NETEQ_BUFFERSIZE>>1]; WebRtc_Word16 NetEqPacketBufferSlave[MAX_NETEQ_BUFFERSIZE>>1]; #ifdef NETEQ_DELAY_LOGGING -extern "C" { - FILE *delay_fid2; /* file pointer */ - WebRtc_UWord32 tot_received_packets=0; -} +extern "C" { + FILE *delay_fid2; /* file pointer */ + WebRtc_UWord32 tot_received_packets=0; +} #endif #ifdef DEF_BUILD_DATE @@ -150,29 +151,25 @@ WebRtc_UWord32 simClock=0; int main(int argc, char* argv[]) { std::vector NetEQvector; - NETEQTEST_RTPpacket rtp; - char version[20]; + char version[20]; - NETEQTEST_RTPpacket slaveRtp; - //bool switchMS = false; - //bool duplicatePayload = false; - enum WebRtcNetEQDecoder usedCodec[kDecoderReservedEnd-1]; - int noOfCodecs; - int ok; - WebRtc_Word16 out_data[640*2]; - WebRtc_Word16 outLen, writeLen; + enum WebRtcNetEQDecoder usedCodec[kDecoderReservedEnd-1]; + int noOfCodecs; + int ok; + WebRtc_Word16 out_data[640*2]; + WebRtc_Word16 outLen, writeLen; int fs = 8000; - WebRtcNetEQ_RTCPStat RTCPstat; + WebRtcNetEQ_RTCPStat RTCPstat; #ifdef WIN32 - char outdrive[MY_MAX_DRIVE]; - char outpath[MY_MAX_PATH]; - char outfile[MY_MAX_FNAME]; - char outext[MY_MAX_EXT]; + char outdrive[MY_MAX_DRIVE]; + char outpath[MY_MAX_PATH]; + char outfile[MY_MAX_FNAME]; + char outext[MY_MAX_EXT]; #endif - char outfilename[MY_MAX_PATH]; + char outfilename[MY_MAX_PATH]; #ifdef NETEQ_DELAY_LOGGING - float clock_float; - int temp_var; + float clock_float; + int temp_var; #endif #ifdef JUNK_DATA FILE *seedfile; @@ -185,38 +182,40 @@ int main(int argc, char* argv[]) int packetLen = 0; int packetCount = 0; std::map decoders; + bool dummyRtp = false; + bool noDecode = false; - /* get the version string */ - WebRtcNetEQ_GetVersion(version); - printf("\n\nNetEq version: %s\n", version); + /* get the version string */ + WebRtcNetEQ_GetVersion(version); + printf("\n\nNetEq version: %s\n", version); #ifdef DEF_BUILD_DATE - printf("Build time: %s\n", __BUILD_DATE); + printf("Build time: %s\n", __BUILD_DATE); #endif - /* check number of parameters */ - if ((argc < 3) + /* check number of parameters */ + if ((argc < 3) #ifdef WIN32 // implicit output file name possible for windows && (argc < 2) #endif ) { - /* print help text and exit */ - printf("Test program for NetEQ.\n"); - printf("The program reads an RTP stream from file and inserts it into NetEQ.\n"); - printf("The format of the RTP stream file should be the same as for rtpplay,\n"); - printf("and can be obtained e.g., from Ethereal by using\n"); - printf("Statistics -> RTP -> Show All Streams -> [select a stream] -> Save As\n\n"); - printf("Usage:\n\n"); + /* print help text and exit */ + printf("Test program for NetEQ.\n"); + printf("The program reads an RTP stream from file and inserts it into NetEQ.\n"); + printf("The format of the RTP stream file should be the same as for rtpplay,\n"); + printf("and can be obtained e.g., from Ethereal by using\n"); + printf("Statistics -> RTP -> Show All Streams -> [select a stream] -> Save As\n\n"); + printf("Usage:\n\n"); #ifdef WIN32 - printf("%s RTPfile [outfile] [-options]\n", argv[0]); + printf("%s RTPfile [outfile] [-options]\n", argv[0]); #else printf("%s RTPfile outfile [-options]\n", argv[0]); #endif - printf("where:\n"); + printf("where:\n"); - printf("RTPfile : RTP stream input file\n\n"); + printf("RTPfile : RTP stream input file\n\n"); - printf("outfile : PCM speech output file\n"); - printf(" Output file name is derived from RTP file name if omitted\n\n"); + printf("outfile : PCM speech output file\n"); + printf(" Output file name is derived from RTP file name if omitted\n\n"); printf("-options are optional switches:\n"); printf("\t-recout datfile : supply recout times\n"); @@ -225,51 +224,52 @@ int main(int argc, char* argv[]) printf("\t-fax : engage fax mode\n"); printf("\t-preparsertp : use RecIn with pre-parsed RTP\n"); printf("\t-rtponly packLenBytes : input file consists of constant size RTP packets without RTPplay headers\n"); + printf("\t-dummyrtp : input file contains only RTP headers\n"); + printf("\t-nodecode : no decoding will be done\n"); //printf("\t-switchms : switch from mono to stereo (copy channel) after 10 seconds\n"); //printf("\t-duplicate : use two instances with identical input (2-channel mono)\n"); - return(0); - } + return(0); + } - if (strcmp(argv[1], "-apitest")==0) { - // do API test and then return - ok=doAPItest(); + if (strcmp(argv[1], "-apitest")==0) { + // do API test and then return + ok=doAPItest(); - if (ok==0) - printf("API test successful!\n"); - else - printf("API test failed!\n"); + if (ok==0) + printf("API test successful!\n"); + else + printf("API test failed!\n"); - return(ok); - } + return(ok); + } - FILE* in_file=fopen(argv[1],"rb"); - CHECK_NOT_NULL(in_file); - printf("Input file: %s\n",argv[1]); + FILE* in_file=fopen(argv[1],"rb"); + CHECK_NOT_NULL(in_file); + printf("Input file: %s\n",argv[1]); int argIx = 2; // index of next argument from command line - if ( argc >= 3 && argv[2][0] != '-' ) { // output name given on command line - strcpy(outfilename, argv[2]); + if ( argc >= 3 && argv[2][0] != '-' ) { // output name given on command line + strcpy(outfilename, argv[2]); argIx++; - } else { // derive output name from input name + } else { // derive output name from input name #ifdef WIN32 - _splitpath(argv[1],outdrive,outpath,outfile,outext); - _makepath(outfilename,outdrive,outpath,outfile,"pcm"); + _splitpath(argv[1],outdrive,outpath,outfile,outext); + _makepath(outfilename,outdrive,outpath,outfile,"pcm"); #else fprintf(stderr,"Output file name must be specified.\n"); - return(-1); + return(-1); #endif - } - FILE* out_file=fopen(outfilename,"wb"); - if (out_file==NULL) { - fprintf(stderr,"Could not open file %s for writing\n", outfilename); - return(-1); - } - printf("Output file: %s\n",outfilename); + } + FILE* out_file=fopen(outfilename,"wb"); + if (out_file==NULL) { + fprintf(stderr,"Could not open file %s for writing\n", outfilename); + return(-1); + } + printf("Output file: %s\n",outfilename); // Parse for more arguments, all beginning with '-' - while( argIx < argc ) { if (argv[argIx][0] != '-') { fprintf(stderr,"Unknown input argument %s\n", argv[argIx]); @@ -311,6 +311,18 @@ int main(int argc, char* argv[]) exit(1); } } + else if (strcmp(argv[argIx], "-dummyrtp") == 0 + || strcmp(argv[argIx], "-dummy") == 0) + { + argIx++; + dummyRtp = true; + noDecode = true; // force noDecode since there are no payloads + } + else if (strcmp(argv[argIx], "-nodecode") == 0) + { + argIx++; + noDecode = true; + } //else if( strcmp(argv[argIx], "-switchms") == 0 ) { // argIx++; // switchMS = true; @@ -328,23 +340,23 @@ int main(int argc, char* argv[]) #ifdef NETEQ_DELAY_LOGGING - char delayfile[MY_MAX_PATH]; + char delayfile[MY_MAX_PATH]; #ifdef WIN32 - _splitpath(outfilename,outdrive,outpath,outfile,outext); - _makepath(delayfile,outdrive,outpath,outfile,"d"); + _splitpath(outfilename,outdrive,outpath,outfile,outext); + _makepath(delayfile,outdrive,outpath,outfile,"d"); #else sprintf(delayfile, "%s.d", outfilename); #endif - delay_fid2 = fopen(delayfile,"wb"); - fprintf(delay_fid2, "#!NetEQ_Delay_Logging%s\n", NETEQ_DELAY_LOGGING_VERSION_STRING); + delay_fid2 = fopen(delayfile,"wb"); + fprintf(delay_fid2, "#!NetEQ_Delay_Logging%s\n", NETEQ_DELAY_LOGGING_VERSION_STRING); #endif - char ptypesfile[MY_MAX_PATH]; + char ptypesfile[MY_MAX_PATH]; #ifdef WIN32 _splitpath(argv[0],outdrive,outpath,outfile,outext); - _makepath(ptypesfile,outdrive,outpath,"ptypes","txt"); + _makepath(ptypesfile,outdrive,outpath,"ptypes","txt"); #else - // TODO(hlundin): Include path to ptypes, as for WIN32 above. + // TODO(hlundin): Include path to ptypes, as for WIN32 above. strcpy(ptypesfile, "ptypes.txt"); #endif FILE *ptypeFile = fopen(ptypesfile,"rt"); @@ -368,7 +380,7 @@ int main(int argc, char* argv[]) noOfCodecs = populateUsedCodec(&decoders, usedCodec); - /* read RTP file header */ + /* read RTP file header */ if (!rtpOnly) { if (NETEQTEST_RTPpacket::skipFileHeader(in_file) != 0) @@ -382,32 +394,45 @@ int main(int argc, char* argv[]) long tempFilePos = ftell(in_file); enum stereoModes stereoMode = stereoModeMono; + NETEQTEST_RTPpacket *rtp; + NETEQTEST_RTPpacket *slaveRtp; + if (!dummyRtp) + { + rtp = new NETEQTEST_RTPpacket(); + slaveRtp = new NETEQTEST_RTPpacket(); + } + else + { + rtp = new NETEQTEST_DummyRTPpacket(); + slaveRtp = new NETEQTEST_DummyRTPpacket(); + } + if (!rtpOnly) { - while (rtp.readFromFile(in_file) >= 0) + while (rtp->readFromFile(in_file) >= 0) { - if (decoders.count(rtp.payloadType()) > 0 - && decoders[rtp.payloadType()].codec != kDecoderRED - && decoders[rtp.payloadType()].codec != kDecoderAVT - && decoders[rtp.payloadType()].codec != kDecoderCNG ) + if (decoders.count(rtp->payloadType()) > 0 + && decoders[rtp->payloadType()].codec != kDecoderRED + && decoders[rtp->payloadType()].codec != kDecoderAVT + && decoders[rtp->payloadType()].codec != kDecoderCNG ) { - stereoMode = decoders[rtp.payloadType()].stereo; - fs = decoders[rtp.payloadType()].fs; + stereoMode = decoders[rtp->payloadType()].stereo; + fs = decoders[rtp->payloadType()].fs; break; } } } else { - while (rtp.readFixedFromFile(in_file, packetLen) >= 0) + while (rtp->readFixedFromFile(in_file, packetLen) >= 0) { - if (decoders.count(rtp.payloadType()) > 0 - && decoders[rtp.payloadType()].codec != kDecoderRED - && decoders[rtp.payloadType()].codec != kDecoderAVT - && decoders[rtp.payloadType()].codec != kDecoderCNG ) + if (decoders.count(rtp->payloadType()) > 0 + && decoders[rtp->payloadType()].codec != kDecoderRED + && decoders[rtp->payloadType()].codec != kDecoderAVT + && decoders[rtp->payloadType()].codec != kDecoderCNG ) { - stereoMode = decoders[rtp.payloadType()].stereo; - fs = decoders[rtp.payloadType()].fs; + stereoMode = decoders[rtp->payloadType()].stereo; + fs = decoders[rtp->payloadType()].fs; break; } } @@ -417,18 +442,18 @@ int main(int argc, char* argv[]) /* block some payload types */ - //rtp.blockPT(72); - //rtp.blockPT(23); + //rtp->blockPT(72); + //rtp->blockPT(23); - /* read first packet */ + /* read first packet */ if (!rtpOnly) { - rtp.readFromFile(in_file); + rtp->readFromFile(in_file); } else { - rtp.readFixedFromFile(in_file, packetLen); - rtp.setTime((1000 * rtp.timeStamp()) / fs); + rtp->readFixedFromFile(in_file, packetLen); + rtp->setTime((1000 * rtp->timeStamp()) / fs); } if (!rtp) { @@ -436,7 +461,7 @@ int main(int argc, char* argv[]) } - /* Initialize NetEQ instances */ + /* Initialize NetEQ instances */ int numInst = 1; if (stereoMode > stereoModeMono) { @@ -456,26 +481,28 @@ int main(int argc, char* argv[]) NetEQvector[i]->usePreparseRTP(preParseRTP); + NetEQvector[i]->setNoDecode(noDecode); + if (numInst > 1) { // we are using master/slave mode if (i == 0) { // first instance is master - NetEQvector[i]->isMaster(); + NetEQvector[i]->setMaster(); } else { // all other are slaves - NetEQvector[i]->isSlave(); + NetEQvector[i]->setSlave(); } } } #ifdef ZERO_TS_START - WebRtc_UWord32 firstTS = rtp.timeStamp(); - rtp.setTimeStamp(0); + WebRtc_UWord32 firstTS = rtp->timeStamp(); + rtp->setTimeStamp(0); #else WebRtc_UWord32 firstTS = 0; #endif @@ -483,15 +510,15 @@ int main(int argc, char* argv[]) // check stereo mode if (stereoMode > stereoModeMono) { - if(rtp.splitStereo(slaveRtp, stereoMode)) + if(rtp->splitStereo(slaveRtp, stereoMode)) { printf("Error in splitStereo\n"); } } #ifdef PLAY_CLEAN - WebRtc_UWord32 prevTS = rtp.timeStamp(); - WebRtc_UWord32 currTS, prev_time; + WebRtc_UWord32 prevTS = rtp->timeStamp(); + WebRtc_UWord32 currTS, prev_time; #endif #ifdef JUNK_DATA @@ -511,9 +538,9 @@ int main(int argc, char* argv[]) int lastRecout = getNextRecoutTime(recoutTimes, &nextRecoutTime); // does nothing if recoutTimes == NULL if (recoutTimes) - simClock = (rtp.time() < nextRecoutTime ? rtp.time(): nextRecoutTime); + simClock = (rtp->time() < nextRecoutTime ? rtp->time(): nextRecoutTime); else - simClock = rtp.time(); // start immediately with first packet + simClock = rtp->time(); // start immediately with first packet WebRtc_UWord32 start_clock = simClock; @@ -526,14 +553,14 @@ int main(int argc, char* argv[]) if(msInfo == NULL) return(-1); - while(rtp.dataLen() >= 0 || (recoutTimes && !lastRecout)) { + while(rtp->dataLen() >= 0 || (recoutTimes && !lastRecout)) { // printf("simClock = %Lu\n", simClock); - + #ifdef NETEQ_DELAY_LOGGING - temp_var = NETEQ_DELAY_LOGGING_SIGNAL_CLOCK; - clock_float = (float) simClock; - fwrite(&temp_var,sizeof(int),1,delay_fid2); - fwrite(&clock_float, sizeof(float),1,delay_fid2); + temp_var = NETEQ_DELAY_LOGGING_SIGNAL_CLOCK; + clock_float = (float) simClock; + fwrite(&temp_var,sizeof(int),1,delay_fid2); + fwrite(&clock_float, sizeof(float),1,delay_fid2); #endif /* time to set extra delay */ if (extraDelay > -1 && simClock >= nextExtraDelayTime) { @@ -545,67 +572,67 @@ int main(int argc, char* argv[]) getNextExtraDelay(extraDelays, &nextExtraDelayTime, &extraDelay); } - /* check if time to receive */ - while (simClock >= rtp.time() && rtp.dataLen() >= 0) + /* check if time to receive */ + while (simClock >= rtp->time() && rtp->dataLen() >= 0) { - if (rtp.dataLen() > 0) + if (rtp->dataLen() > 0) { // insert main packet - NetEQvector[0]->recIn(rtp); + NetEQvector[0]->recIn(*rtp); if (stereoMode > stereoModeMono - && slaveRtp.dataLen() > 0) + && slaveRtp->dataLen() > 0) { // insert slave packet - NetEQvector[1]->recIn(slaveRtp); + NetEQvector[1]->recIn(*slaveRtp); } - } + } - /* get next packet */ + /* get next packet */ #ifdef PLAY_CLEAN - prev_time = rtp.time(); + prev_time = rtp->time(); #endif if (!rtpOnly) { - rtp.readFromFile(in_file); + rtp->readFromFile(in_file); } else { - rtp.readFixedFromFile(in_file, packetLen); - rtp.setTime((1000 * rtp.timeStamp()) / fs); + rtp->readFixedFromFile(in_file, packetLen); + rtp->setTime((1000 * rtp->timeStamp()) / fs); } - if (rtp.dataLen() >= 0) + if (rtp->dataLen() >= 0) { - rtp.setTimeStamp(rtp.timeStamp() - firstTS); + rtp->setTimeStamp(rtp->timeStamp() - firstTS); } packetCount++; - if (changeStereoMode(rtp, decoders, &stereoMode)) + if (changeStereoMode(*rtp, decoders, &stereoMode)) { printf("Warning: stereo mode changed\n"); } if (stereoMode > stereoModeMono) { - if(rtp.splitStereo(slaveRtp, stereoMode)) + if(rtp->splitStereo(slaveRtp, stereoMode)) { printf("Error in splitStereo\n"); } } #ifdef PLAY_CLEAN - currTS = rtp.timeStamp(); - rtp.setTime(prev_time + (currTS-prevTS)/(fs/1000)); - prevTS = currTS; + currTS = rtp->timeStamp(); + rtp->setTime(prev_time + (currTS-prevTS)/(fs/1000)); + prevTS = currTS; #endif - } - - /* check if time to RecOut */ - if ( (!recoutTimes && (simClock%10)==0) // recout times not given from file + } + + /* check if time to RecOut */ + if ( (!recoutTimes && (simClock%10)==0) // recout times not given from file || ( recoutTimes && (simClock >= nextRecoutTime) ) ) // recout times given from file { if (stereoMode > stereoModeMono) @@ -640,27 +667,27 @@ int main(int argc, char* argv[]) } - /* increase time */ - simClock+=TIME_STEP; - } + /* increase time */ + simClock+=TIME_STEP; + } - fclose(in_file); - fclose(out_file); + fclose(in_file); + fclose(out_file); #ifdef NETEQ_DELAY_LOGGING - temp_var = NETEQ_DELAY_LOGGING_SIGNAL_EOF; - fwrite(&temp_var,sizeof(int),1,delay_fid2); - fwrite(&tot_received_packets,sizeof(WebRtc_UWord32),1,delay_fid2); - fprintf(delay_fid2,"End of file\n"); - fclose(delay_fid2); + temp_var = NETEQ_DELAY_LOGGING_SIGNAL_EOF; + fwrite(&temp_var,sizeof(int),1,delay_fid2); + fwrite(&tot_received_packets,sizeof(WebRtc_UWord32),1,delay_fid2); + fprintf(delay_fid2,"End of file\n"); + fclose(delay_fid2); #endif - WebRtcNetEQ_GetRTCPStats(NetEQvector[0]->instance(), &RTCPstat); - printf("RTCP statistics:\n"); - printf(" cum_lost : %d\n", (int) RTCPstat.cum_lost); - printf(" ext_max : %d\n", (int) RTCPstat.ext_max); - printf(" fraction_lost : %d (%f%%)\n", RTCPstat.fraction_lost, (float)(100.0*RTCPstat.fraction_lost/256.0)); - printf(" jitter : %d\n", (int) RTCPstat.jitter); + WebRtcNetEQ_GetRTCPStats(NetEQvector[0]->instance(), &RTCPstat); + printf("RTCP statistics:\n"); + printf(" cum_lost : %d\n", (int) RTCPstat.cum_lost); + printf(" ext_max : %d\n", (int) RTCPstat.ext_max); + printf(" fraction_lost : %d (%f%%)\n", RTCPstat.fraction_lost, (float)(100.0*RTCPstat.fraction_lost/256.0)); + printf(" jitter : %d\n", (int) RTCPstat.jitter); printf("\n Call duration ms : %u\n", simClock-start_clock); @@ -668,8 +695,11 @@ int main(int argc, char* argv[]) printf(" RecIn complexity : %.2f MCPS\n", NetEQvector[0]->getRecInTime() / ((float) 1000*(simClock-start_clock))); printf(" RecOut complexity : %.2f MCPS\n", NetEQvector[0]->getRecOutTime() / ((float) 1000*(simClock-start_clock))); + delete rtp; + delete slaveRtp; + free_coders(decoders); - //free_coders(0 /* first channel */); + //free_coders(0 /* first channel */); // if (stereoMode > stereoModeMono) { // free_coders(1 /* second channel */); // } @@ -678,7 +708,7 @@ int main(int argc, char* argv[]) for (std::vector::iterator it = NetEQvector.begin(); it < NetEQvector.end(); delete *it++); - printf("\nSimulation done!\n"); + printf("\nSimulation done!\n"); #ifdef JUNK_DATA if ( (seedfile = fopen(SEED_FILE, "a+t") ) == NULL ) { @@ -697,7 +727,7 @@ int main(int argc, char* argv[]) fprintf(statfile,"%.4f, %.4f\n", (float) totTime_RecIn.QuadPart / ((float) 1000*(simClock-start_clock)), (float) totTime_RecOut.QuadPart / ((float) 1000*(simClock-start_clock))); fclose(statfile);*/ - return(0); + return(0); } @@ -709,8 +739,8 @@ int main(int argc, char* argv[]) /* Subfunctions */ /****************/ -bool splitStereo(NETEQTEST_RTPpacket& rtp, NETEQTEST_RTPpacket& rtpSlave, - const WebRtc_Word16 *stereoPtype, const enum stereoModes *stereoMode, int noOfStereoCodecs, +bool splitStereo(NETEQTEST_RTPpacket* rtp, NETEQTEST_RTPpacket* rtpSlave, + const WebRtc_Word16 *stereoPtype, const enum stereoModes *stereoMode, int noOfStereoCodecs, const WebRtc_Word16 *cngPtype, int noOfCngCodecs, bool *isStereo) { @@ -721,13 +751,13 @@ bool splitStereo(NETEQTEST_RTPpacket& rtp, NETEQTEST_RTPpacket& rtpSlave, bool isCng = false; // check payload length - if (rtp.dataLen() <= 0) { + if (rtp->dataLen() <= 0) { //*isStereo = false; // don't change return(*isStereo); } // check payload type - WebRtc_Word16 ptype = rtp.payloadType(); + WebRtc_Word16 ptype = rtp->payloadType(); // is this a cng payload? for (int k = 0; k < noOfCngCodecs; k++) { @@ -756,7 +786,7 @@ bool splitStereo(NETEQTEST_RTPpacket& rtp, NETEQTEST_RTPpacket& rtpSlave, { // split the payload if stereo - if(rtp.splitStereo(rtpSlave, tempStereoMode)) + if(rtp->splitStereo(rtpSlave, tempStereoMode)) { printf("Error in splitStereo\n"); } @@ -792,7 +822,7 @@ int getNextRecoutTime(FILE *fp, WebRtc_UWord32 *nextTime) { *nextTime = (WebRtc_UWord32) tempTime; return 0; } - + *nextTime = 0; fclose(fp); @@ -814,13 +844,13 @@ void getNextExtraDelay(FILE *fp, WebRtc_UWord32 *t, int *d) { *d = (int) temp[1]; return; } - + *d = -1; fclose(fp); return; } - + void parsePtypeFile(FILE *ptypeFile, std::map* decoders) { @@ -1461,7 +1491,7 @@ void createAndInsertDecoders (NETEQTEST_NetEQClass *neteq, std::map= 1400) && !defined(_WIN64) // only for Visual 2005 or later, and not for x64 *dec = new decoder_SILK8( pt ); #endif - break; + break; #endif #ifdef CODEC_SILK_WB case NETEQ_CODEC_SILK_12: @@ -1527,213 +1557,213 @@ void free_coders(std::map & decoders) int doAPItest() { - char version[20]; - void *inst; - enum WebRtcNetEQDecoder usedCodec; - int NetEqBufferMaxPackets, BufferSizeInBytes; - WebRtcNetEQ_CodecDef codecInst; - WebRtcNetEQ_RTCPStat RTCPstat; - WebRtc_UWord32 timestamp; - int memorySize; - int ok; - - printf("API-test:\n"); + char version[20]; + void *inst; + enum WebRtcNetEQDecoder usedCodec; + int NetEqBufferMaxPackets, BufferSizeInBytes; + WebRtcNetEQ_CodecDef codecInst; + WebRtcNetEQ_RTCPStat RTCPstat; + WebRtc_UWord32 timestamp; + int memorySize; + int ok; - /* get the version string */ - WebRtcNetEQ_GetVersion(version); - printf("NetEq version: %s\n\n", version); + printf("API-test:\n"); - /* test that API functions return -1 if instance is NULL */ + /* get the version string */ + WebRtcNetEQ_GetVersion(version); + printf("NetEq version: %s\n\n", version); + + /* test that API functions return -1 if instance is NULL */ #define CHECK_MINUS_ONE(x) {int errCode = x; if((errCode)!=-1){printf("\n API test failed at line %d: %s. Function did not return -1 as expected\n",__LINE__,#x); return(-1);}} //#define RESET_ERROR(x) ((MainInst_t*) x)->ErrorCode = 0; - inst = NULL; + inst = NULL; - CHECK_MINUS_ONE(WebRtcNetEQ_GetErrorCode(inst)) - CHECK_MINUS_ONE(WebRtcNetEQ_Assign(&inst, NULL)) -// printf("WARNING: Test of WebRtcNetEQ_Assign() is disabled due to a bug.\n"); - usedCodec=kDecoderPCMu; - CHECK_MINUS_ONE(WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, kTCPLargeJitter, &NetEqBufferMaxPackets, &BufferSizeInBytes)) - CHECK_MINUS_ONE(WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NetEqPacketBuffer, BufferSizeInBytes)) + CHECK_MINUS_ONE(WebRtcNetEQ_GetErrorCode(inst)) + CHECK_MINUS_ONE(WebRtcNetEQ_Assign(&inst, NULL)) +// printf("WARNING: Test of WebRtcNetEQ_Assign() is disabled due to a bug.\n"); + usedCodec=kDecoderPCMu; + CHECK_MINUS_ONE(WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, kTCPLargeJitter, &NetEqBufferMaxPackets, &BufferSizeInBytes)) + CHECK_MINUS_ONE(WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NetEqPacketBuffer, BufferSizeInBytes)) - CHECK_MINUS_ONE(WebRtcNetEQ_Init(inst, 8000)) - CHECK_MINUS_ONE(WebRtcNetEQ_SetAVTPlayout(inst, 0)) - CHECK_MINUS_ONE(WebRtcNetEQ_SetExtraDelay(inst, 17)) - CHECK_MINUS_ONE(WebRtcNetEQ_SetPlayoutMode(inst, kPlayoutOn)) - - CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbReset(inst)) - CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) - CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbRemove(inst, usedCodec)) - WebRtc_Word16 temp1, temp2; - CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbGetSizeInfo(inst, &temp1, &temp2)) - CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbGetCodecInfo(inst, 0, &usedCodec)) + CHECK_MINUS_ONE(WebRtcNetEQ_Init(inst, 8000)) + CHECK_MINUS_ONE(WebRtcNetEQ_SetAVTPlayout(inst, 0)) + CHECK_MINUS_ONE(WebRtcNetEQ_SetExtraDelay(inst, 17)) + CHECK_MINUS_ONE(WebRtcNetEQ_SetPlayoutMode(inst, kPlayoutOn)) - CHECK_MINUS_ONE(WebRtcNetEQ_RecIn(inst, &temp1, 17, 4711)) - CHECK_MINUS_ONE(WebRtcNetEQ_RecOut(inst, &temp1, &temp2)) - CHECK_MINUS_ONE(WebRtcNetEQ_GetRTCPStats(inst, &RTCPstat)); // error here!!! - CHECK_MINUS_ONE(WebRtcNetEQ_GetSpeechTimeStamp(inst, ×tamp)) - WebRtcNetEQOutputType temptype; - CHECK_MINUS_ONE(WebRtcNetEQ_GetSpeechOutputType(inst, &temptype)) + CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbReset(inst)) + CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) + CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbRemove(inst, usedCodec)) + WebRtc_Word16 temp1, temp2; + CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbGetSizeInfo(inst, &temp1, &temp2)) + CHECK_MINUS_ONE(WebRtcNetEQ_CodecDbGetCodecInfo(inst, 0, &usedCodec)) - WebRtc_UWord8 tempFlags; - WebRtc_UWord16 utemp1, utemp2; - CHECK_MINUS_ONE(WebRtcNetEQ_VQmonRecOutStatistics(inst, &utemp1, &utemp2, &tempFlags)) - CHECK_MINUS_ONE(WebRtcNetEQ_VQmonGetRxStatistics(inst, &utemp1, &utemp2)) + CHECK_MINUS_ONE(WebRtcNetEQ_RecIn(inst, &temp1, 17, 4711)) + CHECK_MINUS_ONE(WebRtcNetEQ_RecOut(inst, &temp1, &temp2)) + CHECK_MINUS_ONE(WebRtcNetEQ_GetRTCPStats(inst, &RTCPstat)); // error here!!! + CHECK_MINUS_ONE(WebRtcNetEQ_GetSpeechTimeStamp(inst, ×tamp)) + WebRtcNetEQOutputType temptype; + CHECK_MINUS_ONE(WebRtcNetEQ_GetSpeechOutputType(inst, &temptype)) - WebRtcNetEQ_AssignSize(&memorySize); - CHECK_ZERO(WebRtcNetEQ_Assign(&inst, malloc(memorySize))) + WebRtc_UWord8 tempFlags; + WebRtc_UWord16 utemp1, utemp2; + CHECK_MINUS_ONE(WebRtcNetEQ_VQmonRecOutStatistics(inst, &utemp1, &utemp2, &tempFlags)) + CHECK_MINUS_ONE(WebRtcNetEQ_VQmonGetRxStatistics(inst, &utemp1, &utemp2)) - /* init with wrong sample frequency */ - CHECK_MINUS_ONE(WebRtcNetEQ_Init(inst, 17)) - - /* init with correct fs */ - CHECK_ZERO(WebRtcNetEQ_Init(inst, 8000)) + WebRtcNetEQ_AssignSize(&memorySize); + CHECK_ZERO(WebRtcNetEQ_Assign(&inst, malloc(memorySize))) - /* GetRecommendedBufferSize with wrong codec */ - usedCodec=kDecoderReservedStart; - ok = WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, kTCPLargeJitter , &NetEqBufferMaxPackets, &BufferSizeInBytes); - if((ok!=-1) || ((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNKNOWN_CODEC))){ - printf("WebRtcNetEQ_GetRecommendedBufferSize() did not return proper error code for wrong codec.\n"); - printf("return value = %d; error code = %d\n", ok, WebRtcNetEQ_GetErrorCode(inst)); - } - //RESET_ERROR(inst) + /* init with wrong sample frequency */ + CHECK_MINUS_ONE(WebRtcNetEQ_Init(inst, 17)) - /* GetRecommendedBufferSize with wrong network type */ - usedCodec = kDecoderPCMu; - ok=WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, (enum WebRtcNetEQNetworkType) 4711 , &NetEqBufferMaxPackets, &BufferSizeInBytes); - if ((ok!=-1) || ((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_NETWORK_TYPE))) { - printf("WebRtcNetEQ_GetRecommendedBufferSize() did not return proper error code for wrong network type.\n"); - printf("return value = %d; error code = %d\n", ok, WebRtcNetEQ_GetErrorCode(inst)); - //RESET_ERROR(inst) - } - CHECK_ZERO(WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, kTCPLargeJitter , &NetEqBufferMaxPackets, &BufferSizeInBytes)) + /* init with correct fs */ + CHECK_ZERO(WebRtcNetEQ_Init(inst, 8000)) - /* try to do RecIn before assigning the packet buffer */ -/* makeRTPheader(rtp_data, NETEQ_CODEC_AVT_PT, 17,4711, 1235412312); - makeDTMFpayload(&rtp_data[12], 1, 1, 10, 100); - ok = WebRtcNetEQ_RecIn(inst, (short *) rtp_data, 12+4, 4711); - printf("return value = %d; error code = %d\n", ok, WebRtcNetEQ_GetErrorCode(inst));*/ - - /* check all limits of WebRtcNetEQ_AssignBuffer */ - ok=WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NetEqPacketBuffer, 149<<1); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { - printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for wrong sizeinbytes\n"); - } - ok=WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NULL, BufferSizeInBytes); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { - printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for NULL memory pointer\n"); - } - ok=WebRtcNetEQ_AssignBuffer(inst, 1, NetEqPacketBuffer, BufferSizeInBytes); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { - printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for wrong MaxNoOfPackets\n"); - } - ok=WebRtcNetEQ_AssignBuffer(inst, 601, NetEqPacketBuffer, BufferSizeInBytes); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { - printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for wrong MaxNoOfPackets\n"); - } + /* GetRecommendedBufferSize with wrong codec */ + usedCodec=kDecoderReservedStart; + ok = WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, kTCPLargeJitter , &NetEqBufferMaxPackets, &BufferSizeInBytes); + if((ok!=-1) || ((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNKNOWN_CODEC))){ + printf("WebRtcNetEQ_GetRecommendedBufferSize() did not return proper error code for wrong codec.\n"); + printf("return value = %d; error code = %d\n", ok, WebRtcNetEQ_GetErrorCode(inst)); + } + //RESET_ERROR(inst) - /* do correct assignbuffer */ - CHECK_ZERO(WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NetEqPacketBuffer, BufferSizeInBytes)) + /* GetRecommendedBufferSize with wrong network type */ + usedCodec = kDecoderPCMu; + ok=WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, (enum WebRtcNetEQNetworkType) 4711 , &NetEqBufferMaxPackets, &BufferSizeInBytes); + if ((ok!=-1) || ((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_NETWORK_TYPE))) { + printf("WebRtcNetEQ_GetRecommendedBufferSize() did not return proper error code for wrong network type.\n"); + printf("return value = %d; error code = %d\n", ok, WebRtcNetEQ_GetErrorCode(inst)); + //RESET_ERROR(inst) + } + CHECK_ZERO(WebRtcNetEQ_GetRecommendedBufferSize(inst, &usedCodec, 1, kTCPLargeJitter , &NetEqBufferMaxPackets, &BufferSizeInBytes)) - ok=WebRtcNetEQ_SetExtraDelay(inst, -1); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_DELAYVALUE))) { - printf("WebRtcNetEQ_SetExtraDelay() did not return proper error code for too small delay\n"); - } - ok=WebRtcNetEQ_SetExtraDelay(inst, 1001); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_DELAYVALUE))) { - printf("WebRtcNetEQ_SetExtraDelay() did not return proper error code for too large delay\n"); - } + /* try to do RecIn before assigning the packet buffer */ +/* makeRTPheader(rtp_data, NETEQ_CODEC_AVT_PT, 17,4711, 1235412312); + makeDTMFpayload(&rtp_data[12], 1, 1, 10, 100); + ok = WebRtcNetEQ_RecIn(inst, (short *) rtp_data, 12+4, 4711); + printf("return value = %d; error code = %d\n", ok, WebRtcNetEQ_GetErrorCode(inst));*/ - ok=WebRtcNetEQ_SetPlayoutMode(inst,(enum WebRtcNetEQPlayoutMode) 4711); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_PLAYOUTMODE))) { - printf("WebRtcNetEQ_SetPlayoutMode() did not return proper error code for wrong mode\n"); - } + /* check all limits of WebRtcNetEQ_AssignBuffer */ + ok=WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NetEqPacketBuffer, 149<<1); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { + printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for wrong sizeinbytes\n"); + } + ok=WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NULL, BufferSizeInBytes); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { + printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for NULL memory pointer\n"); + } + ok=WebRtcNetEQ_AssignBuffer(inst, 1, NetEqPacketBuffer, BufferSizeInBytes); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { + printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for wrong MaxNoOfPackets\n"); + } + ok=WebRtcNetEQ_AssignBuffer(inst, 601, NetEqPacketBuffer, BufferSizeInBytes); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-PBUFFER_INIT_ERROR))) { + printf("WebRtcNetEQ_AssignBuffer() did not return proper error code for wrong MaxNoOfPackets\n"); + } - /* number of codecs should return zero before adding any codecs */ - WebRtcNetEQ_CodecDbGetSizeInfo(inst, &temp1, &temp2); - if(temp1!=0) - printf("WebRtcNetEQ_CodecDbGetSizeInfo() return non-zero number of codecs in DB before adding any codecs\n"); + /* do correct assignbuffer */ + CHECK_ZERO(WebRtcNetEQ_AssignBuffer(inst, NetEqBufferMaxPackets, NetEqPacketBuffer, BufferSizeInBytes)) - /* get info from empty database */ - ok=WebRtcNetEQ_CodecDbGetCodecInfo(inst, 17, &usedCodec); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_NOT_EXIST1))) { - printf("WebRtcNetEQ_CodecDbGetCodecInfo() did not return proper error code for out-of-range entry number\n"); - } + ok=WebRtcNetEQ_SetExtraDelay(inst, -1); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_DELAYVALUE))) { + printf("WebRtcNetEQ_SetExtraDelay() did not return proper error code for too small delay\n"); + } + ok=WebRtcNetEQ_SetExtraDelay(inst, 1001); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_DELAYVALUE))) { + printf("WebRtcNetEQ_SetExtraDelay() did not return proper error code for too large delay\n"); + } - /* remove codec from empty database */ - ok=WebRtcNetEQ_CodecDbRemove(inst,kDecoderPCMa); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_NOT_EXIST4))) { - printf("WebRtcNetEQ_CodecDbRemove() did not return proper error code when removing codec that has not been added\n"); - } + ok=WebRtcNetEQ_SetPlayoutMode(inst,(enum WebRtcNetEQPlayoutMode) 4711); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-FAULTY_PLAYOUTMODE))) { + printf("WebRtcNetEQ_SetPlayoutMode() did not return proper error code for wrong mode\n"); + } - /* add codec with unsupported fs */ + /* number of codecs should return zero before adding any codecs */ + WebRtcNetEQ_CodecDbGetSizeInfo(inst, &temp1, &temp2); + if(temp1!=0) + printf("WebRtcNetEQ_CodecDbGetSizeInfo() return non-zero number of codecs in DB before adding any codecs\n"); + + /* get info from empty database */ + ok=WebRtcNetEQ_CodecDbGetCodecInfo(inst, 17, &usedCodec); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_NOT_EXIST1))) { + printf("WebRtcNetEQ_CodecDbGetCodecInfo() did not return proper error code for out-of-range entry number\n"); + } + + /* remove codec from empty database */ + ok=WebRtcNetEQ_CodecDbRemove(inst,kDecoderPCMa); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_NOT_EXIST4))) { + printf("WebRtcNetEQ_CodecDbRemove() did not return proper error code when removing codec that has not been added\n"); + } + + /* add codec with unsupported fs */ #ifdef CODEC_PCM16B #ifndef NETEQ_48KHZ_WIDEBAND - SET_CODEC_PAR(codecInst,kDecoderPCM16Bswb48kHz,77,NULL,48000); - SET_PCM16B_SWB48_FUNCTIONS(codecInst); - ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNSUPPORTED_FS))) { - printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding codec with unsupported sample freq\n"); - } + SET_CODEC_PAR(codecInst,kDecoderPCM16Bswb48kHz,77,NULL,48000); + SET_PCM16B_SWB48_FUNCTIONS(codecInst); + ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNSUPPORTED_FS))) { + printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding codec with unsupported sample freq\n"); + } #else - printf("Could not test adding codec with unsupported sample frequency since NetEQ is compiled with 48kHz support.\n"); + printf("Could not test adding codec with unsupported sample frequency since NetEQ is compiled with 48kHz support.\n"); #endif #else printf("Could not test adding codec with unsupported sample frequency since NetEQ is compiled without PCM16B support.\n"); #endif - /* add two codecs with identical payload types */ - SET_CODEC_PAR(codecInst,kDecoderPCMa,17,NULL,8000); - SET_PCMA_FUNCTIONS(codecInst); - CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) + /* add two codecs with identical payload types */ + SET_CODEC_PAR(codecInst,kDecoderPCMa,17,NULL,8000); + SET_PCMA_FUNCTIONS(codecInst); + CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) - SET_CODEC_PAR(codecInst,kDecoderPCMu,17,NULL,8000); - SET_PCMU_FUNCTIONS(codecInst); - ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_PAYLOAD_TAKEN))) { - printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding two codecs with identical payload types\n"); - } + SET_CODEC_PAR(codecInst,kDecoderPCMu,17,NULL,8000); + SET_PCMU_FUNCTIONS(codecInst); + ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_PAYLOAD_TAKEN))) { + printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding two codecs with identical payload types\n"); + } - /* try adding several payload types for CNG codecs */ - SET_CODEC_PAR(codecInst,kDecoderCNG,105,NULL,16000); - SET_CNG_FUNCTIONS(codecInst); - CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) - SET_CODEC_PAR(codecInst,kDecoderCNG,13,NULL,8000); - SET_CNG_FUNCTIONS(codecInst); - CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) + /* try adding several payload types for CNG codecs */ + SET_CODEC_PAR(codecInst,kDecoderCNG,105,NULL,16000); + SET_CNG_FUNCTIONS(codecInst); + CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) + SET_CODEC_PAR(codecInst,kDecoderCNG,13,NULL,8000); + SET_CNG_FUNCTIONS(codecInst); + CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) /* try adding a speech codec over a CNG codec */ SET_CODEC_PAR(codecInst,kDecoderISAC,105,NULL,16000); /* same as WB CNG above */ - SET_ISAC_FUNCTIONS(codecInst); - ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_PAYLOAD_TAKEN))) { - printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding a speech codec over a CNG codec\n"); - } + SET_ISAC_FUNCTIONS(codecInst); + ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_PAYLOAD_TAKEN))) { + printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding a speech codec over a CNG codec\n"); + } /* try adding a CNG codec over a speech codec */ SET_CODEC_PAR(codecInst,kDecoderCNG,17,NULL,32000); /* same as PCMU above */ - SET_CNG_FUNCTIONS(codecInst); - ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_PAYLOAD_TAKEN))) { - printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding a speech codec over a CNG codec\n"); - } + SET_CNG_FUNCTIONS(codecInst); + ok=WebRtcNetEQ_CodecDbAdd(inst, &codecInst); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_PAYLOAD_TAKEN))) { + printf("WebRtcNetEQ_CodecDbAdd() did not return proper error code when adding a speech codec over a CNG codec\n"); + } - /* remove codec out of range */ - ok=WebRtcNetEQ_CodecDbRemove(inst,kDecoderReservedStart); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNSUPPORTED_CODEC))) { - printf("WebRtcNetEQ_CodecDbRemove() did not return proper error code when removing codec that is out of range\n"); - } - ok=WebRtcNetEQ_CodecDbRemove(inst,kDecoderReservedEnd); - if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNSUPPORTED_CODEC))) { - printf("WebRtcNetEQ_CodecDbRemove() did not return proper error code when removing codec that is out of range\n"); - } + /* remove codec out of range */ + ok=WebRtcNetEQ_CodecDbRemove(inst,kDecoderReservedStart); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNSUPPORTED_CODEC))) { + printf("WebRtcNetEQ_CodecDbRemove() did not return proper error code when removing codec that is out of range\n"); + } + ok=WebRtcNetEQ_CodecDbRemove(inst,kDecoderReservedEnd); + if((ok!=-1)||((ok==-1)&&(WebRtcNetEQ_GetErrorCode(inst)!=-CODEC_DB_UNSUPPORTED_CODEC))) { + printf("WebRtcNetEQ_CodecDbRemove() did not return proper error code when removing codec that is out of range\n"); + } - /*SET_CODEC_PAR(codecInst,kDecoderEG711a,NETEQ_CODEC_EG711A_PT,NetEqiPCMAState,8000); - SET_IPCMA_FUNCTIONS(codecInst); - CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) + /*SET_CODEC_PAR(codecInst,kDecoderEG711a,NETEQ_CODEC_EG711A_PT,NetEqiPCMAState,8000); + SET_IPCMA_FUNCTIONS(codecInst); + CHECK_ZERO(WebRtcNetEQ_CodecDbAdd(inst, &codecInst)) */ - free(inst); + free(inst); - return(0); + return(0); } diff --git a/src/modules/audio_coding/neteq/test/RTPanalyze.cc b/src/modules/audio_coding/neteq/test/RTPanalyze.cc index 12617dd230..4d7d57373b 100644 --- a/src/modules/audio_coding/neteq/test/RTPanalyze.cc +++ b/src/modules/audio_coding/neteq/test/RTPanalyze.cc @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -13,6 +13,9 @@ #include #include "modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.h" +#include "modules/audio_coding/neteq/test/NETEQTEST_DummyRTPpacket.h" + +//#define WEBRTC_DUMMY_RTP enum { kRedPayloadType = 127 @@ -38,7 +41,11 @@ int main(int argc, char* argv[]) { // Read file header. NETEQTEST_RTPpacket::skipFileHeader(in_file); +#ifdef WEBRTC_DUMMY_RTP + NETEQTEST_DummyRTPpacket packet; +#else NETEQTEST_RTPpacket packet; +#endif while (packet.readFromFile(in_file) >= 0) { // Write packet data to file. diff --git a/src/modules/audio_coding/neteq/test/RTPchange.cc b/src/modules/audio_coding/neteq/test/RTPchange.cc index ecbd81c6b9..93ad66bdaf 100644 --- a/src/modules/audio_coding/neteq/test/RTPchange.cc +++ b/src/modules/audio_coding/neteq/test/RTPchange.cc @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. * * Use of this source code is governed by a BSD-style license * that can be found in the LICENSE file in the root of the source @@ -13,10 +13,11 @@ #include #include -#include "gtest/gtest.h" #include "modules/audio_coding/neteq/test/NETEQTEST_RTPpacket.h" +#include "modules/audio_coding/neteq/test/NETEQTEST_DummyRTPPacket.h" #define FIRSTLINELEN 40 +//#define WEBRTC_DUMMY_RTP static bool pktCmp(NETEQTEST_RTPpacket *a, NETEQTEST_RTPpacket *b) { return (a->time() < b->time()); @@ -91,7 +92,11 @@ int main(int argc, char* argv[]) { while (1) { // Insert in vector. +#ifdef WEBRTC_DUMMY_RTP + NETEQTEST_RTPpacket *new_packet = new NETEQTEST_DummyRTPpacket(); +#else NETEQTEST_RTPpacket *new_packet = new NETEQTEST_RTPpacket(); +#endif if (new_packet->readFromFile(in_file) < 0) { // End of file. break; diff --git a/src/modules/audio_coding/neteq/test/rtp_to_text.cc b/src/modules/audio_coding/neteq/test/rtp_to_text.cc new file mode 100644 index 0000000000..7e9f4f59cf --- /dev/null +++ b/src/modules/audio_coding/neteq/test/rtp_to_text.cc @@ -0,0 +1,115 @@ +/* + * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. + * + * Use of this source code is governed by a BSD-style license + * that can be found in the LICENSE file in the root of the source + * tree. An additional intellectual property rights grant can be found + * in the file PATENTS. All contributing project authors may + * be found in the AUTHORS file in the root of the source tree. + */ + +/* + * Parses an rtpdump file and outputs a text table parsable by parseLog.m. + * The output file will have .txt appended to the specified base name. + * $ rtp_to_text [-d] + * + * -d RTP headers only + * + */ + +#include "data_log.h" +#include "NETEQTEST_DummyRTPpacket.h" +#include "NETEQTEST_RTPpacket.h" + +#include +#include + +#include +#include +#include + +/*********************/ +/* Misc. definitions */ +/*********************/ + +#define FIRSTLINELEN 40 + +using ::webrtc::DataLog; + +int main(int argc, char* argv[]) +{ + int arg_count = 1; + NETEQTEST_RTPpacket* packet; + + if (argc < 3) + { + printf("Usage: %s [-d] \n", argv[0]); + return -1; + } + + // Parse dummy option + if (argc >= 3 && strcmp(argv[arg_count], "-d") == 0) + { + packet = new NETEQTEST_DummyRTPpacket; + ++arg_count; + } + else + { + packet = new NETEQTEST_RTPpacket; + } + + std::string input_filename = argv[arg_count++]; + std::string table_name = argv[arg_count]; + + std::cout << "Input file: " << input_filename << std::endl; + std::cout << "Output file: " << table_name << ".txt" << std::endl; + + FILE *inFile=fopen(input_filename.c_str(),"rb"); + if (!inFile) + { + std::cout << "Cannot open input file " << input_filename << std::endl; + return -1; + } + + // Set up the DataLog and define the table + DataLog::CreateLog(); + if (DataLog::AddTable(table_name) < 0) + { + std::cout << "Error adding table " << table_name << ".txt" << std::endl; + return -1; + } + + DataLog::AddColumn(table_name, "seq", 1); + DataLog::AddColumn(table_name, "ssrc", 1); + DataLog::AddColumn(table_name, "payload type", 1); + DataLog::AddColumn(table_name, "length", 1); + DataLog::AddColumn(table_name, "timestamp", 1); + DataLog::AddColumn(table_name, "marker bit", 1); + DataLog::AddColumn(table_name, "arrival", 1); + + // read file header + char firstline[FIRSTLINELEN]; + fgets(firstline, FIRSTLINELEN, inFile); + // start_sec + start_usec + source + port + padding + fread(firstline, 4+4+4+2+2, 1, inFile); + + while (packet->readFromFile(inFile) >= 0) + { + // write packet headers to + DataLog::InsertCell(table_name, "seq", packet->sequenceNumber()); + DataLog::InsertCell(table_name, "ssrc", packet->SSRC()); + DataLog::InsertCell(table_name, "payload type", packet->payloadType()); + DataLog::InsertCell(table_name, "length", packet->dataLen()); + DataLog::InsertCell(table_name, "timestamp", packet->timeStamp()); + DataLog::InsertCell(table_name, "marker bit", packet->markerBit()); + DataLog::InsertCell(table_name, "arrival", packet->time()); + DataLog::NextRow(table_name); + return -1; + } + + DataLog::ReturnLog(); + + fclose(inFile); + + return 0; +}