1035 lines
37 KiB
C++
1035 lines
37 KiB
C++
/*
|
|
* Copyright (c) 2011 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 <cassert>
|
|
#include <windows.h>
|
|
#include <iostream>
|
|
#include <tchar.h>
|
|
|
|
#include "rtp_rtcp.h"
|
|
#include "common_types.h"
|
|
#include "rtcp_utility.h"
|
|
#include "tmmbr_help.h"
|
|
|
|
#define TEST_STR "Test TMMBR."
|
|
#define TEST_PASSED() std::cerr << TEST_STR << " : [OK]" << std::endl
|
|
#define PRINT_LINE std::cout << "------------------------------------------" << std::endl;
|
|
|
|
|
|
const int maxFileLen = 200;
|
|
WebRtc_UWord8* dataFile[maxFileLen];
|
|
|
|
|
|
struct InputSet
|
|
{
|
|
WebRtc_UWord32 TMMBR;
|
|
WebRtc_UWord32 packetOH;
|
|
WebRtc_UWord32 SSRC;
|
|
};
|
|
|
|
const InputSet set0 = {220, 80, 11111}; // bitRate, packetOH, ssrc
|
|
const InputSet set1 = {180, 90, 22222};
|
|
const InputSet set2 = {100, 210, 33333};
|
|
const InputSet set3 = { 35, 40, 44444};
|
|
const InputSet set4 = { 40, 60, 55555};
|
|
const InputSet set4_1 = {100, 60, 55555};
|
|
const InputSet set4_2 = { 10, 60, 55555};
|
|
const InputSet set5 = {200, 40, 66666};
|
|
const InputSet set00 = { 0, 40, 66666};
|
|
|
|
const int maxBitrate = 230; // if this is lower than max in the list above test should fail
|
|
|
|
void Verify(TMMBRSet* boundingSet, int index, InputSet set)
|
|
{
|
|
assert(boundingSet->ptrTmmbrSet[index] == set.TMMBR);
|
|
assert(boundingSet->ptrPacketOHSet[index] == set.packetOH);
|
|
assert(boundingSet->ptrSsrcSet[index] == set.SSRC);
|
|
};
|
|
|
|
int ParseRTCPPacket(const void *data, int len, TMMBRSet*& boundingSet)
|
|
{
|
|
int numItems = -1;
|
|
RTCPUtility::RTCPParserV2 rtcpParser((const WebRtc_UWord8*)data, len, true);
|
|
RTCPUtility::RTCPPacketTypes pktType = rtcpParser.Begin();
|
|
while (pktType != RTCPUtility::kRtcpNotValidCode)
|
|
{
|
|
const RTCPUtility::RTCPPacket& rtcpPacket = rtcpParser.Packet();
|
|
if (pktType == RTCPUtility::kRtcpRtpfbTmmbnCode)
|
|
{
|
|
assert(0 == rtcpPacket.TMMBN.SenderSSRC);
|
|
assert(0 == rtcpPacket.TMMBN.MediaSSRC);
|
|
numItems = 0;
|
|
}
|
|
if (pktType == RTCPUtility::kRtcpRtpfbTmmbnItemCode)
|
|
{
|
|
boundingSet->ptrTmmbrSet[numItems] = rtcpPacket.TMMBNItem.MaxTotalMediaBitRate;
|
|
boundingSet->ptrPacketOHSet[numItems] = rtcpPacket.TMMBNItem.MeasuredOverhead;
|
|
boundingSet->ptrSsrcSet[numItems] = rtcpPacket.TMMBNItem.SSRC;
|
|
++numItems;
|
|
}
|
|
pktType = rtcpParser.Iterate();
|
|
}
|
|
return numItems;
|
|
};
|
|
|
|
WebRtc_Word32 GetFile(char* fileName)
|
|
{
|
|
if (!fileName[0])
|
|
{
|
|
return 0;
|
|
}
|
|
|
|
FILE* openFile = fopen(fileName, "rb");
|
|
assert(openFile != NULL);
|
|
fseek(openFile, 0, SEEK_END);
|
|
int len = (WebRtc_Word16)(ftell(openFile));
|
|
rewind(openFile);
|
|
assert(len > 0 && len < maxFileLen);
|
|
fread(dataFile, 1, len, openFile);
|
|
fclose(openFile);
|
|
return len;
|
|
};
|
|
|
|
|
|
class LoopBackTransport2 : public webrtc::Transport, private TMMBRHelp
|
|
{
|
|
public:
|
|
LoopBackTransport2(RtpRtcp* rtpRtcpModule) :
|
|
TMMBRHelp(false),
|
|
_rtpRtcpModule(rtpRtcpModule),
|
|
_cnt(0)
|
|
{
|
|
}
|
|
virtual int SendPacket(int channel, const void *data, int len)
|
|
{
|
|
if( 0 == _rtpRtcpModule->IncomingPacket((const WebRtc_UWord8*)data, len))
|
|
{
|
|
return len;
|
|
}
|
|
return -1;
|
|
}
|
|
virtual int SendRTCPPacket(int channel, const void *data, int len)
|
|
{
|
|
char fileName[256] = {0};
|
|
TMMBRSet* boundingSet = BoundingSet();
|
|
boundingSet->VerifyAndAllocateSet(3);
|
|
|
|
if (_cnt == 0)
|
|
{
|
|
// TMMBN {}
|
|
// TMMBN {}
|
|
// TMMBN {}
|
|
// TMMBN {2,4,0} -> {4,2}
|
|
assert(2 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set4);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR3.bin");
|
|
}
|
|
|
|
++_cnt;
|
|
|
|
// Get stored rtcp packet w/ TMMBR
|
|
len = GetFile(fileName);
|
|
if (len == 0)
|
|
{
|
|
return 1;
|
|
}
|
|
|
|
// Send in bitrate request
|
|
if(_rtpRtcpModule->IncomingPacket((const WebRtc_UWord8*)dataFile, len) == 0)
|
|
{
|
|
return len;
|
|
}
|
|
return -1;
|
|
}
|
|
RtpRtcp* _rtpRtcpModule;
|
|
WebRtc_UWord32 _cnt;
|
|
};
|
|
|
|
|
|
class LoopBackTransportVideo : public webrtc::Transport, private TMMBRHelp
|
|
{
|
|
public:
|
|
LoopBackTransportVideo(RtpRtcp* rtpRtcpModule) :
|
|
TMMBRHelp(false),
|
|
_rtpRtcpModule(rtpRtcpModule),
|
|
_cnt(0)
|
|
{
|
|
}
|
|
virtual int SendPacket(int channel, const void *data, int len)
|
|
{
|
|
if(_rtpRtcpModule->IncomingPacket((const WebRtc_UWord8*)data, len)== 0)
|
|
{
|
|
return len;
|
|
}
|
|
return -1;
|
|
}
|
|
virtual int SendRTCPPacket(int channel, const void *data, int len)
|
|
{
|
|
char fileName[256] = {0};
|
|
TMMBRSet* boundingSet = BoundingSet();
|
|
boundingSet->VerifyAndAllocateSet(3);
|
|
|
|
if (_cnt == 0)
|
|
{
|
|
strcpy(fileName, "RTCPPacketTMMBR0.bin");
|
|
}
|
|
else if (_cnt == 1)
|
|
{
|
|
// TMMBN {0} -> {0}
|
|
assert(1 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set0);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR1.bin");
|
|
}
|
|
else if (_cnt == 2)
|
|
{
|
|
// TMMBN {0,1} -> {1}
|
|
assert(1 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set1);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR2.bin");
|
|
}
|
|
else if (_cnt == 3)
|
|
{
|
|
// TMMBN {0,1,2} -> {2}
|
|
assert(1 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR3.bin");
|
|
}
|
|
else if (_cnt == 4)
|
|
{
|
|
// TMMBN {0,1,2,3} -> {3,2}
|
|
assert(2 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR4.bin");
|
|
}
|
|
else if (_cnt == 5)
|
|
{
|
|
// TMMBN {0,1,2,3,4} -> {3,4,2}
|
|
assert(3 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
Verify(boundingSet, 2, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR5.bin");
|
|
}
|
|
else if (_cnt == 6)
|
|
{
|
|
// TMMBN {0,1,2,3,4,5} -> {3,4,2}
|
|
assert(3 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
Verify(boundingSet, 2, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR4_2.bin");
|
|
}
|
|
else if (_cnt == 7)
|
|
{
|
|
// TMMBN {0,1,2,3,4_2,5} -> {4_2}
|
|
assert(1 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set4_2);
|
|
|
|
++_cnt;
|
|
::Sleep(5*RTCP_INTERVAL_AUDIO_MS + 1000); // time out receiver
|
|
_rtpRtcpModule->Process(); // SendRTCP() (_cnt == 8)
|
|
// a receiver has timed out -> UpdateTMMBR()
|
|
}
|
|
else if (_cnt == 8)
|
|
{
|
|
// No TMMBN in this packet
|
|
assert(-1 == ParseRTCPPacket(data, len, boundingSet));
|
|
}
|
|
else if (_cnt == 10)
|
|
{
|
|
// TMMBN {} -> {}, empty set
|
|
assert(0 == ParseRTCPPacket(data, len, boundingSet));
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR2.bin");
|
|
}
|
|
else if (_cnt == 11)
|
|
{
|
|
// TMMBN {2} -> {2}
|
|
assert(1 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set2);
|
|
}
|
|
else if (_cnt == 12) // ----- multi module -------------
|
|
{
|
|
// No TMMBN in this packet
|
|
assert(-1 == ParseRTCPPacket(data, len, boundingSet));
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR4.bin");
|
|
}
|
|
else if (_cnt == 13)
|
|
{
|
|
// TMMBN {}
|
|
// TMMBN {}
|
|
// TMMBN {}
|
|
// TMMBN {2,4} -> {4,2}
|
|
assert(2 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set4);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR0.bin");
|
|
}
|
|
else if (_cnt == 14)
|
|
{
|
|
// TMMBN {}
|
|
// TMMBN {3}
|
|
// TMMBN {}
|
|
// TMMBN {2,4,0} -> {3,4,2}
|
|
assert(3 == ParseRTCPPacket(data, len, boundingSet));
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
Verify(boundingSet, 2, set2);
|
|
|
|
strcpy(fileName, "RTCPPacketTMMBR1.bin");
|
|
}
|
|
//else if (_cnt == 15)
|
|
//{
|
|
// // TMMBN {}
|
|
// // TMMBN {}
|
|
// // TMMBN {}
|
|
// // TMMBN {2,4,0,1} -> {4,2}
|
|
// //assert(2 == ParseRTCPPacket(data, len, boundingSet));
|
|
// //Verify(boundingSet, 0, set4);
|
|
// //Verify(boundingSet, 1, set2);
|
|
//}
|
|
//else if (_cnt == 15)
|
|
//{
|
|
// // No TMMBN in this packet
|
|
// assert(-1 == ParseRTCPPacket(data, len, boundingSet));
|
|
//}
|
|
else if (_cnt == 15)
|
|
{
|
|
// TMMBN {}
|
|
// TMMBN {}
|
|
// TMMBN {}
|
|
// TMMBN {} -> {}, empty set
|
|
assert(0 == ParseRTCPPacket(data, len, boundingSet));
|
|
}
|
|
|
|
++_cnt;
|
|
|
|
// Get stored rtcp packet w/ TMMBR
|
|
len = GetFile(fileName);
|
|
if (len == 0)
|
|
{
|
|
return 1;
|
|
}
|
|
|
|
// Send in bitrate request
|
|
if( 0 == _rtpRtcpModule->IncomingPacket((const WebRtc_UWord8*)dataFile, len))
|
|
{
|
|
return len;
|
|
}
|
|
return -1;
|
|
}
|
|
|
|
RtpRtcp* _rtpRtcpModule;
|
|
WebRtc_UWord32 _cnt;
|
|
};
|
|
|
|
class TestTMMBR : private TMMBRHelp
|
|
{
|
|
public:
|
|
TestTMMBR() : TMMBRHelp(false) {};
|
|
|
|
void Add(TMMBRSet* candidateSet, int index, InputSet set)
|
|
{
|
|
candidateSet->ptrTmmbrSet[index] = set.TMMBR;
|
|
candidateSet->ptrPacketOHSet[index] = set.packetOH;
|
|
candidateSet->ptrSsrcSet[index] = set.SSRC;
|
|
};
|
|
|
|
void Start()
|
|
{
|
|
// Get sets
|
|
TMMBRSet* candidateSet = CandidateSet();
|
|
assert(0 == candidateSet->sizeOfSet);
|
|
TMMBRSet* boundingSet = BoundingSet();
|
|
assert(0 == boundingSet->sizeOfSet);
|
|
TMMBRSet* boundingSetToSend = BoundingSetToSend();
|
|
assert(0 == boundingSetToSend->sizeOfSet);
|
|
|
|
WebRtc_Word32 numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(0 == numBoundingSet); // should be empty
|
|
|
|
assert( 0 == SetTMMBRBoundingSetToSend(NULL,0)); // ok to send empty set
|
|
assert( 0 == SetTMMBRBoundingSetToSend(boundingSet,0)); // ok to send empty set
|
|
|
|
WebRtc_UWord32 minBitrateKbit = 0;
|
|
WebRtc_UWord32 maxBitrateKbit = 0;
|
|
assert(-1 == CalcMinMaxBitRate(0, 0, 1, false, minBitrateKbit, maxBitrateKbit)); // no bounding set
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {0} -> {0}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(1);
|
|
assert(1 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set0);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(1 == numBoundingSet);
|
|
Verify(boundingSet, 0, set0);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, 0)); // incorrect length
|
|
assert(!IsOwner(set1.SSRC, 100)); // incorrect length
|
|
|
|
assert( IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set2.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set0);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert( 0 == CalcMinMaxBitRate(0, numBoundingSet, false,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set0.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
assert(0 == CalcMinMaxBitRate(0, 100, false,0, minBitrateKbit, maxBitrateKbit)); // incorrect length
|
|
assert(set0.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {0,1} -> {1}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(2);
|
|
assert(2 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set0);
|
|
Add(candidateSet, 1, set1);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(1 == numBoundingSet);
|
|
Verify(boundingSet, 0, set1);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert( IsOwner(set1.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set2.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set1);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set1.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {0,1,2} -> {2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(3);
|
|
assert(3 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set0);
|
|
Add(candidateSet, 1, set1);
|
|
Add(candidateSet, 2, set2);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(1 == numBoundingSet);
|
|
Verify(boundingSet, 0, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set2.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {0,1,2,3} -> {3,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(4);
|
|
assert(4 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set0);
|
|
Add(candidateSet, 1, set1);
|
|
Add(candidateSet, 2, set2);
|
|
Add(candidateSet, 3, set3);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(2 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {0,1,2,3,4} -> {3,4,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(5);
|
|
assert(5 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set0);
|
|
Add(candidateSet, 1, set1);
|
|
Add(candidateSet, 2, set2);
|
|
Add(candidateSet, 3, set3);
|
|
Add(candidateSet, 4, set4);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(3 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
Verify(boundingSet, 2, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set4);
|
|
Verify(boundingSetToSend, 2, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0,numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {0,1,2,3,4,5} -> {3,4,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(6);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set0);
|
|
Add(candidateSet, 1, set1);
|
|
Add(candidateSet, 2, set2);
|
|
Add(candidateSet, 3, set3);
|
|
Add(candidateSet, 4, set4);
|
|
Add(candidateSet, 5, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(3 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
Verify(boundingSet, 2, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set4);
|
|
Verify(boundingSetToSend, 2, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0,numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set0.TMMBR == maxBitrateKbit);
|
|
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {1,2,3,4,5} -> {3,4,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(5);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set1);
|
|
Add(candidateSet, 1, set2);
|
|
Add(candidateSet, 2, set3);
|
|
Add(candidateSet, 3, set4);
|
|
Add(candidateSet, 4, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(3 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
Verify(boundingSet, 2, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
assert(boundingSetToSend->sizeOfSet == numBoundingSet);
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set4);
|
|
Verify(boundingSetToSend, 2, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0,numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {1,3,4,5} -> {3,4}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(4);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set1);
|
|
Add(candidateSet, 1, set3);
|
|
Add(candidateSet, 2, set4);
|
|
Add(candidateSet, 3, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(2 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set4);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set4);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet,true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {1,2,4,5} -> {4,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(4);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set1);
|
|
Add(candidateSet, 1, set2);
|
|
Add(candidateSet, 2, set4);
|
|
Add(candidateSet, 3, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(2 == numBoundingSet);
|
|
Verify(boundingSet, 0, set4);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set4);
|
|
Verify(boundingSetToSend, 1, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set4.TMMBR == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {1,2,3,5} -> {3,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(4);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set1);
|
|
Add(candidateSet, 1, set2);
|
|
Add(candidateSet, 2, set3);
|
|
Add(candidateSet, 3, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(2 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {1,2,3,4_1,5} -> {3,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(5);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set1);
|
|
Add(candidateSet, 1, set2);
|
|
Add(candidateSet, 2, set3);
|
|
Add(candidateSet, 3, set4_1);
|
|
Add(candidateSet, 4, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(2 == numBoundingSet);
|
|
Verify(boundingSet, 0, set3);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert( IsOwner(set3.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set3);
|
|
Verify(boundingSetToSend, 1, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set3.TMMBR == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {1,2,3,4_2,5} -> {4_2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(5);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set1);
|
|
Add(candidateSet, 1, set2);
|
|
Add(candidateSet, 2, set3);
|
|
Add(candidateSet, 3, set4_2);
|
|
Add(candidateSet, 4, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(1 == numBoundingSet);
|
|
Verify(boundingSet, 0, set4_2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set2.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set4_2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0, numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(MIN_VIDEO_BW_MANAGEMENT_BITRATE == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {} -> {}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(0);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(0 == numBoundingSet);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set2.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set3.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(-1 == CalcMinMaxBitRate(0,numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {x0,5} -> {5}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(2);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set00);
|
|
Add(candidateSet, 1, set5);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(1 == numBoundingSet);
|
|
Verify(boundingSet, 0, set5);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set2.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set3.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set4.SSRC, numBoundingSet));
|
|
assert( IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set5);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0,numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set5.TMMBR == minBitrateKbit);
|
|
assert(set5.TMMBR == maxBitrateKbit);
|
|
|
|
// ---------------------------------
|
|
// Test candidate set {x0,4,2} -> {4,2}
|
|
// ---------------------------------
|
|
candidateSet = VerifyAndAllocateCandidateSet(3);
|
|
assert(6 == candidateSet->sizeOfSet);
|
|
Add(candidateSet, 0, set00);
|
|
Add(candidateSet, 1, set4);
|
|
Add(candidateSet, 2, set2);
|
|
|
|
// Find bounding set
|
|
numBoundingSet = FindTMMBRBoundingSet(boundingSet);
|
|
assert(2 == numBoundingSet);
|
|
Verify(boundingSet, 0, set4);
|
|
Verify(boundingSet, 1, set2);
|
|
|
|
// Is owner of set
|
|
assert(!IsOwner(set0.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set1.SSRC, numBoundingSet));
|
|
assert( IsOwner(set2.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set3.SSRC, numBoundingSet));
|
|
assert( IsOwner(set4.SSRC, numBoundingSet));
|
|
assert(!IsOwner(set5.SSRC, numBoundingSet));
|
|
|
|
// Set boundingSet to send
|
|
assert(0 == SetTMMBRBoundingSetToSend(boundingSet, maxBitrate));
|
|
|
|
// Get boundingSet to send
|
|
boundingSetToSend = BoundingSetToSend();
|
|
Verify(boundingSetToSend, 0, set4);
|
|
Verify(boundingSetToSend, 1, set2);
|
|
|
|
// Get net bitrate depending on packet rate
|
|
assert(0 == CalcMinMaxBitRate(0,numBoundingSet, true,0, minBitrateKbit, maxBitrateKbit));
|
|
assert(set4.TMMBR == minBitrateKbit);
|
|
assert(set2.TMMBR == maxBitrateKbit);
|
|
};
|
|
};
|
|
|
|
class NULLDataZink: public RtpData
|
|
{
|
|
virtual WebRtc_Word32 OnReceivedPayloadData(const WebRtc_UWord8* payloadData,
|
|
const WebRtc_UWord16 payloadSize,
|
|
const webrtc::WebRtcRTPHeader* rtpHeader,
|
|
const WebRtc_UWord8* incomingRtpPacket,
|
|
const WebRtc_UWord16 incomingRtpPacketLengt)
|
|
{
|
|
return 0;
|
|
};
|
|
};
|
|
|
|
|
|
int _tmain(int argc, _TCHAR* argv[])
|
|
{
|
|
|
|
std::string str;
|
|
std::cout << "------------------------" << std::endl;
|
|
std::cout << "------ Test TMMBR ------" << std::endl;
|
|
std::cout << "------------------------" << std::endl;
|
|
std::cout << " " << std::endl;
|
|
|
|
// --------------------
|
|
// Test TMMBRHelp class
|
|
// --------------------
|
|
TestTMMBR test;
|
|
test.Start();
|
|
|
|
printf("TMMBRHelp-class test done.\n");
|
|
|
|
// ------------------------
|
|
// Test TMMBR single module
|
|
// ------------------------
|
|
RtpRtcp* rtpRtcpModuleVideo = RtpRtcp::CreateRtpRtcp(0, false);
|
|
|
|
LoopBackTransportVideo* myLoopBackTransportVideo = new LoopBackTransportVideo(rtpRtcpModuleVideo);
|
|
assert(0 == rtpRtcpModuleVideo->RegisterSendTransport(myLoopBackTransportVideo));
|
|
|
|
assert(false == rtpRtcpModuleVideo->TMMBR());
|
|
rtpRtcpModuleVideo->SetTMMBRStatus(true);
|
|
assert(true == rtpRtcpModuleVideo->TMMBR());
|
|
|
|
assert(0 == rtpRtcpModuleVideo->RegisterSendPayload( "I420", 96));
|
|
assert(0 == rtpRtcpModuleVideo->RegisterReceivePayload( "I420", 96));
|
|
|
|
// send a RTP packet with SSRC 11111 to get 11111 as the received SSRC
|
|
assert(0 == rtpRtcpModuleVideo->SetSSRC(11111));
|
|
const WebRtc_UWord8 testStream[9] = "testtest";
|
|
assert(0 == rtpRtcpModuleVideo->RegisterIncomingDataCallback(new NULLDataZink())); // needed to avoid error from parsing the incoming stream
|
|
assert(0 == rtpRtcpModuleVideo->SendOutgoingData(webrtc::kVideoFrameKey,96, 0, testStream, 8));
|
|
|
|
// set the SSRC to 0
|
|
assert(0 == rtpRtcpModuleVideo->SetSSRC(0));
|
|
|
|
//
|
|
assert(0 == rtpRtcpModuleVideo->SetRTCPStatus(kRtcpCompound));
|
|
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {0} // should this make us remember a TMMBR?
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {1}, verify TMMBN {0}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {2}, verify TMMBN {1}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {3}, verify TMMBN {2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {4}, verify TMMBN {3,2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {5}, verify TMMBN {3,4,2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {4_2}, verify TMMBN {3,4,2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> time out receivers, verify TMMBN {4_2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> verify TMMBN {2}
|
|
|
|
printf("Single module test done.\n");
|
|
|
|
// ------------------------
|
|
// Test TMMBR multi module
|
|
// ------------------------
|
|
RtpRtcp* rtpRtcpModuleVideoDef = RtpRtcp::CreateRtpRtcp(10, false);
|
|
assert(0 == rtpRtcpModuleVideo->RegisterDefaultModule(rtpRtcpModuleVideoDef));
|
|
|
|
RtpRtcp* rtpRtcpModuleVideo1 = RtpRtcp::CreateRtpRtcp(1, false);
|
|
assert(0 == rtpRtcpModuleVideo1->RegisterDefaultModule(rtpRtcpModuleVideoDef));
|
|
|
|
RtpRtcp* rtpRtcpModuleVideo2 = RtpRtcp::CreateRtpRtcp(2, false);
|
|
assert(0 == rtpRtcpModuleVideo2->RegisterDefaultModule(rtpRtcpModuleVideoDef));
|
|
|
|
RtpRtcp* rtpRtcpModuleVideo3 = RtpRtcp::CreateRtpRtcp(3, false);
|
|
assert(0 == rtpRtcpModuleVideo3->RegisterDefaultModule(rtpRtcpModuleVideoDef));
|
|
|
|
LoopBackTransport2* myLoopBackTransport2 = new LoopBackTransport2(rtpRtcpModuleVideo2);
|
|
assert(0 == rtpRtcpModuleVideo2->RegisterSendTransport(myLoopBackTransport2));
|
|
|
|
assert(0 == rtpRtcpModuleVideo2->SetRTCPStatus(kRtcpCompound));
|
|
|
|
// set the SSRC to 0
|
|
assert(0 == rtpRtcpModuleVideo2->SetSSRC(0));
|
|
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {4}, verify no TMMBN in this packet
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {0}, verify TMMBN {4,2}
|
|
assert(0 == rtpRtcpModuleVideo2->SendRTCP()); // -> incoming TMMBR {3}, verify TMMBN {4,2}
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // -> incoming TMMBR {1}, verify TMMBN {3,4,2}
|
|
::Sleep(5*RTCP_INTERVAL_AUDIO_MS + 1000);
|
|
rtpRtcpModuleVideo2->Process(); // time out receiver2 -> UpdateTMMBR()
|
|
assert(0 == rtpRtcpModuleVideo->SendRTCP()); // verify TMMBN {}
|
|
|
|
printf("Multi module test done.\n");
|
|
|
|
|
|
RtpRtcp::DestroyRtpRtcp(rtpRtcpModuleVideo);
|
|
RtpRtcp::DestroyRtpRtcp(rtpRtcpModuleVideo1);
|
|
RtpRtcp::DestroyRtpRtcp(rtpRtcpModuleVideo2);
|
|
RtpRtcp::DestroyRtpRtcp(rtpRtcpModuleVideo3);
|
|
RtpRtcp::DestroyRtpRtcp(rtpRtcpModuleVideoDef);
|
|
|
|
TEST_PASSED();
|
|
::Sleep(5000);
|
|
|
|
return 0;
|
|
}
|
|
|