| /* |
| * 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 <stdio.h> |
| #include <string.h> |
| |
| #include <vector> |
| |
| #include "critical_section_wrapper.h" |
| #include "event_wrapper.h" |
| #include "thread_wrapper.h" |
| #include "voe_extended_test.h" |
| #include "../../source/voice_engine_defines.h" // defines build macros |
| #include "system_wrappers/interface/ref_count.h" |
| |
| #if defined(_WIN32) |
| #include <conio.h> |
| #include <winsock2.h> |
| #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) |
| #include <netdb.h> |
| #endif |
| |
| using namespace webrtc; |
| |
| namespace voetest { |
| |
| // Set this flag to ensure that test packets are transmitted to |
| // RemoteIP::RemotePort during tests of SetSendToS and SetSendGQos. Requires |
| // receiver at the remote side and Wireshark with a proper ip.src filter. |
| #define _SEND_TO_REMOTE_IP_ |
| |
| #ifdef _SEND_TO_REMOTE_IP_ |
| const int RemotePort = 12345; // transmit to this UDP port |
| const char* RemoteIP = "192.168.200.1"; // transmit to this IP address |
| #endif |
| |
| #ifdef MAC_IPHONE |
| #define SLEEP_IF_IPHONE(x) SLEEP(x) |
| #else |
| #define SLEEP_IF_IPHONE(x) |
| #endif |
| |
| #ifdef WEBRTC_ANDROID |
| // Global pointers |
| extern void* globalJavaVM; |
| extern void* globalContext; |
| #endif |
| |
| extern char* GetFilename(char* filename); |
| extern const char* GetFilename(const char* filename); |
| extern int GetResource(char* resource, char* dest, int destLen); |
| extern char* GetResource(char* resource); |
| extern const char* GetResource(const char* resource); |
| |
| // ---------------------------------------------------------------------------- |
| // External AudioDeviceModule implementation |
| // ---------------------------------------------------------------------------- |
| |
| // static |
| AudioDeviceModuleImpl* AudioDeviceModuleImpl::Create() { |
| AudioDeviceModuleImpl* xADM = new AudioDeviceModuleImpl(); |
| if (xADM) |
| xADM->AddRef(); |
| return xADM; |
| } |
| |
| // static |
| bool AudioDeviceModuleImpl::Destroy(AudioDeviceModuleImpl* adm) { |
| if (!adm) |
| return false; |
| int32_t count = adm->Release(); |
| if (count != 0) { |
| return false; |
| } else { |
| delete adm; |
| return true; |
| } |
| } |
| |
| AudioDeviceModuleImpl::AudioDeviceModuleImpl() : |
| _ref_count(0) { |
| } |
| |
| AudioDeviceModuleImpl::~AudioDeviceModuleImpl() { |
| } |
| |
| int32_t AudioDeviceModuleImpl::AddRef() { |
| return ++_ref_count; |
| } |
| |
| int32_t AudioDeviceModuleImpl::Release() { |
| // Avoid self destruction in this mock implementation. |
| // Ensures that we can always check the reference counter while alive. |
| return --_ref_count; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // External transport (Transport) implementations: |
| // ---------------------------------------------------------------------------- |
| |
| ExtendedTestTransport::ExtendedTestTransport(VoENetwork* ptr) : |
| myNetw(ptr), _thread(NULL), _lock(NULL), _event(NULL), _length(0), _channel(0) { |
| const char* threadName = "voe_extended_test_external_thread"; |
| _lock = CriticalSectionWrapper::CreateCriticalSection(); |
| _event = EventWrapper::Create(); |
| _thread = ThreadWrapper::CreateThread(Run, this, kHighPriority, threadName); |
| if (_thread) { |
| unsigned int id; |
| _thread->Start(id); |
| } |
| } |
| |
| ExtendedTestTransport::~ExtendedTestTransport() { |
| if (_thread) { |
| _thread->SetNotAlive(); |
| _event->Set(); |
| if (_thread->Stop()) { |
| delete _thread; |
| _thread = NULL; |
| delete _event; |
| _event = NULL; |
| delete _lock; |
| _lock = NULL; |
| } |
| } |
| } |
| |
| bool ExtendedTestTransport::Run(void* ptr) { |
| return static_cast<ExtendedTestTransport*> (ptr)->Process(); |
| } |
| |
| bool ExtendedTestTransport::Process() { |
| switch (_event->Wait(500)) { |
| case kEventSignaled: |
| _lock->Enter(); |
| myNetw->ReceivedRTPPacket(_channel, _packetBuffer, _length); |
| _lock->Leave(); |
| return true; |
| case kEventTimeout: |
| return true; |
| case kEventError: |
| break; |
| } |
| return true; |
| } |
| |
| int ExtendedTestTransport::SendPacket(int channel, const void *data, int len) { |
| _lock->Enter(); |
| if (len < 1612) { |
| memcpy(_packetBuffer, (const unsigned char*) data, len); |
| _length = len; |
| _channel = channel; |
| } |
| _lock->Leave(); |
| _event->Set(); // triggers ReceivedRTPPacket() from worker thread |
| return len; |
| } |
| |
| int ExtendedTestTransport::SendRTCPPacket(int channel, const void *data, int len) { |
| myNetw->ReceivedRTCPPacket(channel, data, len); |
| return len; |
| } |
| |
| XTransport::XTransport(VoENetwork* netw, VoEFile* file) : |
| _netw(netw), _file(file) { |
| } |
| |
| int XTransport::SendPacket(int channel, const void *data, int len) { |
| // loopback |
| // _netw->ReceivedRTPPacket(channel, data, len); |
| |
| return 0; |
| } |
| |
| int XTransport::SendRTCPPacket(int, const void *, int) { |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoERTPObserver |
| // ---------------------------------------------------------------------------- |
| |
| XRTPObserver::XRTPObserver() : |
| _SSRC(0) { |
| } |
| |
| XRTPObserver::~XRTPObserver() { |
| } |
| |
| void XRTPObserver::OnIncomingCSRCChanged(const int /*channel*/, const unsigned int /*CSRC*/, |
| const bool /*added*/) { |
| } |
| |
| void XRTPObserver::OnIncomingSSRCChanged(const int /*channel*/, const unsigned int SSRC) { |
| // char msg[128]; |
| // sprintf(msg, "OnIncomingSSRCChanged(channel=%d, SSRC=%lu)\n", |
| // channel, SSRC); |
| // TEST_LOG(msg); |
| |
| _SSRC = SSRC; // skip channel dependency for simplicty |
| |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::PrepareTest(const char* str) const { |
| TEST_LOG("\n\n================================================\n"); |
| TEST_LOG("\tExtended *%s* Test\n", str); |
| TEST_LOG("================================================\n\n"); |
| |
| return 0; |
| } |
| |
| int VoEExtendedTest::TestPassed(const char* str) const { |
| TEST_LOG("\n\n------------------------------------------------\n"); |
| TEST_LOG("\tExtended *%s* test passed!\n", str); |
| TEST_LOG("------------------------------------------------\n\n"); |
| |
| return 0; |
| } |
| |
| void VoEExtendedTest::OnPeriodicDeadOrAlive(const int /*channel*/, const bool alive) { |
| _alive = alive; |
| if (alive) { |
| TEST_LOG("=> ALIVE "); |
| } else { |
| TEST_LOG("=> DEAD "); |
| } |
| fflush(NULL); |
| } |
| |
| void VoEExtendedTest::CallbackOnError(const int errCode, int) { |
| _errCode = errCode; |
| TEST_LOG("\n************************\n"); |
| TEST_LOG(" RUNTIME ERROR: %d \n", errCode); |
| TEST_LOG("************************\n"); |
| } |
| |
| VoEExtendedTest::VoEExtendedTest(VoETestManager& mgr) : |
| _mgr(mgr) { |
| for (int i = 0; i < 32; i++) { |
| _listening[i] = false; |
| _playing[i] = false; |
| _sending[i] = false; |
| } |
| } |
| |
| VoEExtendedTest::~VoEExtendedTest() { |
| } |
| |
| void VoEExtendedTest::StartMedia(int channel, int rtpPort, bool listen, |
| bool playout, bool send) { |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| |
| _listening[channel] = false; |
| _playing[channel] = false; |
| _sending[channel] = false; |
| |
| voe_base_->SetLocalReceiver(channel, rtpPort); |
| voe_base_->SetSendDestination(channel, rtpPort, "127.0.0.1"); |
| if (listen) { |
| _listening[channel] = true; |
| voe_base_->StartReceive(channel); |
| } |
| if (playout) { |
| _playing[channel] = true; |
| voe_base_->StartPlayout(channel); |
| } |
| if (send) { |
| _sending[channel] = true; |
| voe_base_->StartSend(channel); |
| } |
| } |
| |
| void VoEExtendedTest::StopMedia(int channel) { |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| |
| if (_listening[channel]) { |
| _listening[channel] = false; |
| voe_base_->StopReceive(channel); |
| } |
| if (_playing[channel]) { |
| _playing[channel] = false; |
| voe_base_->StopPlayout(channel); |
| } |
| if (_sending[channel]) { |
| _sending[channel] = false; |
| voe_base_->StopSend(channel); |
| } |
| } |
| |
| void VoEExtendedTest::Play(int channel, unsigned int timeMillisec, bool addFileAsMicrophone, |
| bool addTimeMarker) { |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| |
| voe_base_->StartPlayout(channel); |
| TEST_LOG("[playing]"); |
| fflush(NULL); |
| if (addFileAsMicrophone) { |
| file->StartPlayingFileAsMicrophone(channel, _mgr.AudioFilename(), true, true); |
| TEST_LOG("[file as mic]"); |
| fflush(NULL); |
| } |
| if (addTimeMarker) { |
| float dtSec = (float) ((float) timeMillisec / 1000.0); |
| TEST_LOG("[dT=%.1f]", dtSec); |
| fflush(NULL); // print sleep time in seconds |
| } |
| SLEEP(timeMillisec); |
| voe_base_->StopPlayout(channel); |
| file->StopPlayingFileAsMicrophone(channel); |
| } |
| |
| void VoEExtendedTest::Sleep(unsigned int timeMillisec, bool addMarker) { |
| if (addMarker) { |
| float dtSec = (float) ((float) timeMillisec / 1000.0); |
| TEST_LOG("[dT=%.1f]", dtSec); // print sleep time in seconds |
| } |
| ::Sleep(timeMillisec); |
| } |
| |
| int VoEExtendedTest::TestBase() { |
| #ifndef _WIN32 |
| // Sleep a bit instead when pause not supported |
| #undef PAUSE |
| #define PAUSE SLEEP(2000); |
| #endif |
| |
| PrepareTest("Base"); |
| |
| // TODO(qhogpat): make this an actual instance variable. I think the |
| // macro black magic will make more sense then. This is named like an |
| // instance variable since it is required in order to appease the |
| // gods of darkness. |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoENetwork* netw = _mgr.NetworkPtr(); |
| #ifdef _TEST_RTP_RTCP_ |
| VoERTP_RTCP* rtp = _mgr.RTP_RTCPPtr(); |
| #endif |
| |
| ////////////////////////// |
| // SetTraceFileName |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST(SetTraceFileName - SetDebugTraceFileName); ANL(); |
| |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(NULL)); MARK(); |
| // don't use these files |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("" |
| "VoEBase_trace_dont_use.txt"))); MARK(); |
| // use these instead |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("" |
| "VoEBase_trace.txt"))); MARK(); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStream | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); MARK(); |
| |
| ANL(); AOK(); ANL(); ANL(); |
| #endif |
| |
| /////////////////////////////////////// |
| // RegisterVoiceEngineObserver |
| // DeRegisterVoiceEngineObserver |
| TEST(SetObserver); |
| ANL(); |
| |
| TEST_MUSTPASS(voe_base_->RegisterVoiceEngineObserver(*this)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->DeRegisterVoiceEngineObserver()); |
| MARK(); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| ///////////////////// |
| // GetVersion |
| TEST(GetVersion); |
| ANL(); |
| |
| char version[1024]; |
| // audio device module and AudioProcessing fail to getversion when they |
| // are not initiliazed |
| TEST_MUSTPASS(voe_base_->GetVersion(version)); |
| MARK(); |
| TEST_LOG("\n-----\n%s\n-----\n", version); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| /////////////// |
| // Init |
| TEST(Init); |
| ANL(); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| MARK(); |
| // ensure that no new memory is allocated at the second call (check |
| // trace file) |
| TEST_MUSTPASS(voe_base_->Init()); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| // verify AEC recording |
| TEST_MUSTPASS(voe_base_->Init()); |
| MARK(); // verify output dat-files |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| #endif |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| //////////////////// |
| // Terminate |
| TEST(Terminate); |
| ANL(); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| MARK(); // should be ignored |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| MARK(); // should terminate |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // ------------------------------------------------------------------------ |
| // >> Init(AudioDeviceModule) |
| // |
| // Note that our mock implementation of the ADM also mocks the |
| // reference counting part. This approach enables us to keep track |
| // of the internal reference counter without checking return values |
| // from the ADM and we also avoid the built-in self destruction. |
| // |
| // TODO(henrika): this test does not verify that external ADM methods |
| // are called by the VoiceEngine once registered. We could extend |
| // the mock implementation and add counters for each ADM API to ensure |
| // that they are called in the correct sequence and the correct number |
| // of times. |
| TEST_LOG("\nTesting: Init in combination with an external ADM\n"); |
| |
| // Create the ADM and call AddRef within the factory method. |
| AudioDeviceModuleImpl* xADM = AudioDeviceModuleImpl::Create(); |
| ASSERT_FALSE(xADM == NULL); |
| ASSERT_TRUE(xADM->ReferenceCounter() == 1); |
| |
| // Verify default usage case for external ADM. |
| TEST_MUSTPASS(voe_base_->Init(xADM));MARK(); |
| ASSERT_TRUE(xADM->ReferenceCounter() == 2); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| ASSERT_TRUE(xADM->ReferenceCounter() == 1); |
| |
| // Our reference-count implementation does not self destruct. |
| // We do it manually here instead by calling Release followed by delete. |
| ASSERT_TRUE(AudioDeviceModuleImpl::Destroy(xADM)); |
| ANL(); |
| AOK();ANL(); |
| |
| // >> end of Init(AudioDeviceModule) |
| // ------------------------------------------------------------------------ |
| |
| /////////////////////////// |
| // MaxNumOfChannels |
| TEST(MaxNumOfChannels); |
| ANL(); |
| TEST_MUSTPASS(voe_base_->MaxNumOfChannels() < 0); |
| MARK(); |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| //////////////////////// |
| // CreateChannel |
| // DeleteChannel |
| |
| int i; |
| int channel; |
| int nChannels(voe_base_->MaxNumOfChannels()); |
| |
| TEST(CreateChannel); |
| ANL(); |
| TEST(DeleteChannel); |
| ANL(); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| channel = voe_base_->CreateChannel(); |
| MARK(); |
| TEST_MUSTPASS(channel != 0); |
| channel = voe_base_->CreateChannel(); |
| MARK(); |
| TEST_MUSTPASS(channel != 1); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(1)); |
| MARK(); |
| |
| // create and delete one channel many times |
| for (i = 0; i < 10; i++) { |
| channel = voe_base_->CreateChannel(); |
| MARK(); |
| TEST_MUSTPASS(channel != 0); // should be 0 each time |
| TEST_MUSTPASS(voe_base_->DeleteChannel(channel)); |
| MARK(); |
| } |
| // create max number of channels |
| for (i = 0; i < nChannels; i++) { |
| channel = voe_base_->CreateChannel(); |
| MARK(); |
| TEST_MUSTPASS(channel != i); |
| } |
| channel = voe_base_->CreateChannel(); |
| MARK(); // should fail since no more channels can now be created |
| TEST_MUSTPASS(channel != -1); |
| |
| int aChannel = (((nChannels - 17) > 0) ? (nChannels - 17) : 0); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(aChannel)); |
| MARK(); |
| channel = voe_base_->CreateChannel(); |
| MARK(); // should reuse channel |
| TEST_MUSTPASS(channel != aChannel); |
| |
| // delete all created channels |
| for (i = 0; i < nChannels; i++) { |
| TEST_MUSTPASS(voe_base_->DeleteChannel(i)); |
| MARK(); |
| } |
| |
| // try to delete a non-existing channel |
| TEST_MUSTPASS(-1 != voe_base_->DeleteChannel(aChannel)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // ------------------------------------------------------------------------ |
| // >> SetLocalReceiver |
| // |
| // State: VE not initialized, no existing channels |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| int ch; |
| |
| TEST(SetLocalReceiver); |
| ANL(); |
| |
| // no channel created yet => should fail |
| TEST_MUSTPASS(!voe_base_->SetLocalReceiver(0, 100)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| ch = voe_base_->CreateChannel(); |
| |
| #ifdef MAC_IPHONE |
| printf("\nNOTE: Local IP must be set in source code (line %d) \n", |
| __LINE__ + 1); |
| char* localIp = "127.0.0.1"; |
| #else |
| char localIp[64] = { 0 }; |
| TEST_MUSTPASS(netw->GetLocalIP(localIp)); |
| MARK(); |
| // NOTE: This API is supported on Win, Mac and Linux and may fail or not |
| // return local IP for other platforms. |
| #endif |
| |
| // trivial invalid function calls |
| TEST_MUSTPASS(!voe_base_->SetLocalReceiver(ch+1, 12345)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(!voe_base_->SetLocalReceiver(ch, -1)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_PORT_NMBR); |
| |
| // check conflict with ongoing receiving |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(!voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| TEST_ERROR(VE_ALREADY_LISTENING); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // check conflict with ongoing transmission |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(!voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| TEST_ERROR(VE_ALREADY_SENDING); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| |
| // valid function calls |
| // Need to sleep between, otherwise it may fail for unknown reason |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, kVoEDefault, localIp)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, kVoEDefault, NULL, |
| "230.1.2.3")); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, kVoEDefault, localIp, |
| "230.1.2.3")); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, 5555, NULL)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| SLEEP(100); |
| |
| // STATE: no media but sockets exists and are binded to 12345 and 12346 |
| // respectively |
| |
| // Add some dynamic tests as well: |
| |
| // ensure that last setting is used (cancels old settings) |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 44444)); |
| MARK(); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 54321)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 54321, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| Play(ch, 1000, true, true); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(ch)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of SetLocalReceiver |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> GetLocalReceiver |
| // |
| // State: VE initialized, no existing channels |
| TEST(GetLocalReceiver); |
| ANL(); |
| |
| int port; |
| char ipaddr[64]; |
| int RTCPport; |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // verify non-configured (blank) local receiver |
| TEST_MUSTPASS(voe_base_->GetLocalReceiver(ch, port, RTCPport, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(port != 0); |
| TEST_MUSTPASS(RTCPport != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| // check some trivial set/get combinations |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)) |
| TEST_MUSTPASS(voe_base_->GetLocalReceiver(ch, port, RTCPport, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(port != 12345); |
| TEST_MUSTPASS(RTCPport != 12346); |
| TEST_MUSTPASS(strcmp(ipaddr, "0.0.0.0") != 0); // now binded to "any" IP |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, 55555)) |
| TEST_MUSTPASS(voe_base_->GetLocalReceiver(ch, port, RTCPport, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(port != 12345); |
| TEST_MUSTPASS(RTCPport != 55555); |
| TEST_MUSTPASS(strcmp(ipaddr, "0.0.0.0") != 0); |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, kVoEDefault, localIp)) |
| TEST_MUSTPASS(voe_base_->GetLocalReceiver(ch, port, RTCPport, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(port != 12345); |
| TEST_MUSTPASS(RTCPport != 12346); |
| TEST_MUSTPASS(strcmp(ipaddr, localIp) != 0); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(ch)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of GetLocalReceiver |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetSendDestination |
| // |
| // State: VE initialized, no existing channels |
| TEST(SetSendDestination); |
| ANL(); |
| |
| // call without existing channel |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // trivial fail tests |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(ch, 65536, "127.0.0.1")); |
| MARK(); |
| TEST_ERROR(VE_INVALID_PORT_NMBR); // invalid RTP port |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(ch, 12345, "127.0.0.1", 65536)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_PORT_NMBR); // invalid source port |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(ch, 12345, "127.0.0.1", kVoEDefault, |
| 65536)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_PORT_NMBR); // invalid RTCP port |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(ch, 12345, "127.0.0.300")); |
| MARK(); |
| TEST_ERROR(VE_INVALID_IP_ADDRESS); // invalid IP address |
| |
| // sockets must be created first to support multi-cast (not required |
| // otherwise) |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(ch, 55555, "230.0.0.1")); |
| MARK(); |
| TEST_ERROR(VE_SOCKET_ERROR); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 55555)); // create sockets |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 55555, "230.0.0.1")); |
| MARK(); // should work now |
| |
| voe_base_->DeleteChannel(0); |
| ch = voe_base_->CreateChannel(); |
| |
| // STATE: one channel created, no sockets exist |
| |
| // valid function calls |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333, "127.0.0.1")); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333, "127.0.0.1", 44444)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333, "127.0.0.1", kVoEDefault, |
| 55555)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333, "127.0.0.1", 44444, |
| 55555)); |
| MARK(); |
| |
| voe_base_->DeleteChannel(0); |
| ch = voe_base_->CreateChannel(); |
| |
| // create receive sockets first and then an extra pair of send sockets |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 44444)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 44444, "127.0.0.1", 11111)); |
| MARK(); // binds to 11111 |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(ch)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of SetSendDestination |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> GetSendDestination |
| // |
| // State: VE initialized, no existing channels |
| TEST(GetSendDestination); |
| ANL(); |
| |
| int sourcePort; |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // verify non-configured (blank) local receiver |
| TEST_MUSTPASS(voe_base_->GetSendDestination(ch, port, ipaddr, sourcePort, |
| RTCPport)); |
| MARK(); |
| TEST_MUSTPASS(port != 0); |
| TEST_MUSTPASS(sourcePort != 0); |
| TEST_MUSTPASS(RTCPport != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| // check some trivial set/get combinations |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 44444, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->GetSendDestination(ch, port, ipaddr, sourcePort, |
| RTCPport)); |
| MARK(); |
| TEST_MUSTPASS(port != 44444); |
| TEST_MUSTPASS(sourcePort != 0); // should be 0 since no local receiver has |
| // NOT been defined yet |
| TEST_MUSTPASS(RTCPport != 44445); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 55555)); |
| TEST_MUSTPASS(voe_base_->GetSendDestination(ch, port, ipaddr, sourcePort, |
| RTCPport)); |
| MARK(); |
| TEST_MUSTPASS(port != 44444); |
| TEST_MUSTPASS(sourcePort != 55555); // should be equal to local port |
| TEST_MUSTPASS(RTCPport != 44445); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| voe_base_->DeleteChannel(0); |
| ch = voe_base_->CreateChannel(); |
| |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 44444, "127.0.0.1")); |
| // NULL as IP-address input should work as well |
| TEST_MUSTPASS(voe_base_->GetSendDestination(ch, port, NULL, sourcePort, |
| RTCPport)); |
| MARK(); |
| TEST_MUSTPASS(port != 44444); |
| TEST_MUSTPASS(sourcePort != 0); |
| TEST_MUSTPASS(RTCPport != 44445); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(ch)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of GetLocalReceiver |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> StartReceive |
| // >> StopReceive |
| // |
| // State: VE initialized, no existing channels |
| TEST(StartReceive); |
| ANL(); |
| TEST(StopReceive); |
| ANL(); |
| |
| // call without existing channel |
| TEST_MUSTPASS(!voe_base_->StartReceive(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(!voe_base_->StopReceive(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // sockets must be created first |
| TEST_MUSTPASS(!voe_base_->StartReceive(0)); |
| MARK(); |
| TEST_ERROR(VE_SOCKETS_NOT_INITED); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 55555)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| MARK(); // should work this time |
| |
| // enable again (should work) |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| MARK(); |
| |
| // Stop/Start (should work) |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| MARK(); |
| |
| // Verify in loopback |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 55555, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| Play(ch, 1000, true, true); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| MARK(); |
| |
| voe_base_->DeleteChannel(0); |
| ch = voe_base_->CreateChannel(); |
| |
| // Ensure that it is OK to add delay between SetLocalReceiver and StarListen |
| TEST_LOG("\nspeak after 2 seconds and ensure that no delay is added:\n"); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 55555)); |
| |
| Sleep(2000, true); // adding emulated delay here |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 55555, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| Play(ch, 2000, true, true); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(ch)); |
| ANL(); |
| |
| // Multi-channel tests |
| |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 11111+2*i)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| MARK(); |
| } |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| TEST_MUSTPASS(voe_base_->StopReceive(i)); |
| MARK(); |
| voe_base_->DeleteChannel(i); |
| } |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 11111+2*i)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| MARK(); |
| voe_base_->DeleteChannel(ch); |
| } |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of StartReceive/StopReceive |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> StartPlayout |
| // >> StopPlayout |
| // |
| // State: VE initialized, no existing channels |
| TEST(StartPlayout); |
| ANL(); |
| TEST(StopPlayout); |
| ANL(); |
| |
| // call without existing channel |
| TEST_MUSTPASS(!voe_base_->StartPlayout(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(!voe_base_->StopPlayout(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| ch = voe_base_->CreateChannel(); |
| |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| MARK(); |
| |
| voe_base_->DeleteChannel(ch); |
| |
| // Multi-channel tests |
| const int MaxNumberOfPlayingChannels(kVoiceEngineMaxNumOfActiveChannels); |
| |
| for (i = 0; i < MaxNumberOfPlayingChannels; i++) { |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| MARK(); |
| } |
| for (i = 0; i < MaxNumberOfPlayingChannels; i++) { |
| TEST_MUSTPASS(voe_base_->StopPlayout(i)); |
| MARK(); |
| voe_base_->DeleteChannel(i); |
| } |
| for (i = 0; i < MaxNumberOfPlayingChannels; i++) { |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| MARK(); |
| voe_base_->DeleteChannel(ch); |
| } |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of StartPlayout/StopPlayout |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> StartSend |
| // >> StopSend |
| // |
| // State: VE initialized, no existing channels |
| TEST(StartSend); |
| ANL(); |
| TEST(StopSend); |
| ANL(); |
| |
| // call without existing channel |
| TEST_MUSTPASS(!voe_base_->StartSend(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(!voe_base_->StopSend(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // call without initialized destination |
| TEST_MUSTPASS(!voe_base_->StartSend(ch)); |
| MARK(); |
| TEST_ERROR(VE_DESTINATION_NOT_INITED); |
| |
| // initialize destination and try again (should work even without existing |
| // sockets) |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| MARK(); |
| SLEEP(100); |
| |
| // STATE: sockets should now have been created automatically at the first |
| // transmitted packet should be binded to 33333 and "0.0.0.0" |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| MARK(); |
| |
| voe_base_->DeleteChannel(ch); |
| ch = voe_base_->CreateChannel(); |
| |
| // try loopback with unique send sockets (closed when channel is deleted or |
| // new source is set) |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 33333)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333, "127.0.0.1", 44444)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| Play(ch, 2000, true, true); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| voe_base_->DeleteChannel(ch); |
| ANL(); |
| |
| // Multi-channel tests |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 33333 + 2*i)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33333 + 2*i, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| MARK(); |
| } |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| TEST_MUSTPASS(voe_base_->StopSend(i)); |
| MARK(); |
| voe_base_->DeleteChannel(i); |
| } |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 45633 + 2*i)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 45633 + 2*i, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| MARK(); |
| voe_base_->DeleteChannel(ch); |
| } |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of StartSend/StopSend |
| // ------------------------------------------------------------------------ |
| |
| ////////////////////////////// |
| // SetNetEQPlayoutMode |
| // GetNetEQPlayoutMode |
| TEST(SetNetEQPlayoutMode); |
| ANL(); |
| TEST(GetNetEQPlayoutMode); |
| ANL(); |
| |
| NetEqModes mode; |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // invalid function calls (should fail) |
| TEST_MUSTPASS(!voe_base_->GetNetEQPlayoutMode(ch+1, mode)); |
| MARK(); |
| TEST_MUSTPASS(!voe_base_->SetNetEQPlayoutMode(ch+1, kNetEqDefault)); |
| MARK(); |
| |
| // verify default mode (should be kNetEqDefault) |
| TEST_MUSTPASS(voe_base_->GetNetEQPlayoutMode(ch, mode)); |
| MARK(); |
| TEST_MUSTPASS(mode != kNetEqDefault); |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(ch, kNetEqStreaming)); |
| MARK(); |
| voe_base_->DeleteChannel(ch); |
| |
| // ensure that default mode is set as soon as new channel is created |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->GetNetEQPlayoutMode(ch, mode)); |
| MARK(); |
| TEST_MUSTPASS(mode != kNetEqDefault); |
| voe_base_->DeleteChannel(ch); |
| |
| // verify Set/Get for all supported modes and max number of channels |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| ch = voe_base_->CreateChannel(); |
| |
| // verify Set/Get for all supported modes |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(i, kNetEqDefault)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->GetNetEQPlayoutMode(i, mode)); |
| MARK(); |
| TEST_MUSTPASS(mode != kNetEqDefault); |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(i, kNetEqStreaming)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->GetNetEQPlayoutMode(i, mode)); |
| MARK(); |
| TEST_MUSTPASS(mode != kNetEqStreaming); |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(i, kNetEqFax)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->GetNetEQPlayoutMode(i, mode)); |
| MARK(); |
| TEST_MUSTPASS(mode != kNetEqFax); |
| SLEEP(50); |
| } |
| |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| voe_base_->DeleteChannel(i); |
| } |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| ////////////////////////////// |
| // SetNetEQBGNMode |
| // GetNetEQBGNMode |
| TEST(SetNetEQBGNMode); |
| ANL(); |
| TEST(GetNetEQBGNMode); |
| ANL(); |
| |
| NetEqBgnModes bgnMode; |
| |
| ch = voe_base_->CreateChannel(); |
| |
| // invalid function calls (should fail) |
| TEST_MUSTPASS(!voe_base_->GetNetEQBGNMode(ch+1, bgnMode)); |
| MARK(); |
| TEST_MUSTPASS(!voe_base_->SetNetEQBGNMode(ch+1, kBgnOn)); |
| MARK(); |
| |
| // verify default mode (should be kBgnOn) |
| TEST_MUSTPASS(voe_base_->GetNetEQBGNMode(ch, bgnMode)); |
| MARK(); |
| TEST_MUSTPASS(bgnMode != kBgnOn); |
| voe_base_->DeleteChannel(ch); |
| |
| // ensure that default mode is set as soon as new channel is created |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->GetNetEQBGNMode(ch, bgnMode)); |
| MARK(); |
| TEST_MUSTPASS(bgnMode != kBgnOn); |
| voe_base_->DeleteChannel(ch); |
| |
| // verify Set/Get for all supported modes and max number of channels |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| ch = voe_base_->CreateChannel(); |
| |
| // verify Set/Get for all supported modes |
| TEST_MUSTPASS(voe_base_->SetNetEQBGNMode(i, kBgnOn)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->GetNetEQBGNMode(i, bgnMode)); |
| MARK(); |
| TEST_MUSTPASS(bgnMode != kBgnOn); |
| TEST_MUSTPASS(voe_base_->SetNetEQBGNMode(i, kBgnFade)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->GetNetEQBGNMode(i, bgnMode)); |
| MARK(); |
| TEST_MUSTPASS(bgnMode != kBgnFade); |
| TEST_MUSTPASS(voe_base_->SetNetEQBGNMode(i, kBgnOff)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->GetNetEQBGNMode(i, bgnMode)); |
| MARK(); |
| TEST_MUSTPASS(bgnMode != kBgnOff); |
| SLEEP(50); |
| } |
| |
| for (i = 0; i < voe_base_->MaxNumOfChannels(); i++) { |
| voe_base_->DeleteChannel(i); |
| } |
| |
| // Verify real-time performance for all playout modes in full duplex |
| |
| ch = voe_base_->CreateChannel(); |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch , 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1")); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(ch, kNetEqDefault)); |
| MARK(); |
| TEST_LOG("\nenjoy full duplex using kNetEqDefault playout mode...\n"); |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(ch, kNetEqStreaming)); |
| MARK(); |
| TEST_LOG("\nenjoy full duplex using kNetEqStreaming playout mode...\n"); |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->SetNetEQPlayoutMode(ch, kNetEqFax)); |
| MARK(); |
| TEST_LOG("\nenjoy full duplex using kNetEqFax playout mode...\n"); |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| voe_base_->DeleteChannel(ch); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| ///////////////////// |
| // Full duplex tests |
| |
| ch = voe_base_->CreateChannel(); // We must delete this channel first to be able |
| // to reuse port 12345 |
| |
| // start with default case, also test non-default RTCP port |
| #ifdef _TEST_RTP_RTCP_ |
| TEST_MUSTPASS(rtp->SetRTCP_CNAME(ch, "Johnny")); |
| #endif |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345, 12349)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1", kVoEDefault, |
| 12349)); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| |
| TEST_LOG("full duplex is now activated (1)\n"); |
| TEST_LOG("waiting for RTCP packet...\n"); |
| |
| SLEEP(7000); // Make sure we get RTCP packet |
| PAUSE; |
| |
| // Verify that we got RTCP packet from correct source port |
| #ifdef _TEST_RTP_RTCP_ |
| char tmpStr[64] = { 0 }; |
| TEST_MUSTPASS(rtp->GetRemoteRTCP_CNAME(ch, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Johnny", tmpStr)); |
| #endif |
| int rtpPort(0), rtcpPort(0); |
| char ipAddr[64] = { 0 }; |
| TEST_MUSTPASS(netw->GetSourceInfo(ch, rtpPort, rtcpPort, ipAddr)); |
| TEST_MUSTPASS(12349 != rtcpPort); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // Call StartSend before StartReceive |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1")); |
| |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (2)\n"); |
| |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // Try again using same ports |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1")); |
| |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (3)\n"); |
| TEST_LOG("waiting for RTCP packet...\n"); |
| |
| SLEEP(7000); // Make sure we get RTCP packet |
| PAUSE |
| |
| // Verify correct RTCP source port |
| TEST_MUSTPASS(netw->GetSourceInfo(ch, rtpPort, rtcpPort, ipAddr)); |
| TEST_MUSTPASS(12345+1 != rtcpPort); |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| voe_base_->DeleteChannel(ch); |
| ch = voe_base_->CreateChannel(); |
| |
| // Try with extra send socket |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch , 22222)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 22222, "127.0.0.1", 11111)); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (4)\n"); |
| |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // repeat default case starting with a fresh channel |
| |
| voe_base_->DeleteChannel(ch); |
| ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch , 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1")); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (5)\n"); |
| |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // restart call again |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 12345)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (6)\n"); |
| |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // force sending from new socket |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch , 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 12345, "127.0.0.1", 12350, |
| 12359)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| TEST_LOG("\nfull duplex is now activated (7)\n"); |
| |
| PAUSE |
| |
| // Test getting send settings |
| TEST_MUSTPASS(voe_base_->GetSendDestination(ch, rtpPort, ipAddr, sourcePort, |
| rtcpPort)); |
| TEST_MUSTPASS(12345 != rtpPort); |
| TEST_MUSTPASS(_stricmp("127.0.0.1", ipAddr)); |
| TEST_MUSTPASS(12350 != sourcePort); |
| TEST_MUSTPASS(12359 != rtcpPort); |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| // new channel and new port |
| ch = voe_base_->CreateChannel(); |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch , 33221)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33221, "127.0.0.1")); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (8)\n"); |
| |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| |
| voe_base_->DeleteChannel(ch); |
| ch = voe_base_->CreateChannel(); |
| |
| #ifndef MAC_IPHONE |
| // bind to local IP and try again |
| strcpy(localIp, "127.0.0.1"); |
| #else |
| localIp = "127.0.0.1"; |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch, 33221, 12349, localIp)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch, 33221, localIp)); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(ch)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch)); |
| |
| TEST_LOG("\nfull duplex is now activated (9)\n"); |
| |
| PAUSE |
| |
| TEST_MUSTPASS(voe_base_->GetLocalReceiver(ch, rtpPort, rtcpPort, ipAddr)); |
| TEST_MUSTPASS(33221 != rtpPort); |
| TEST_MUSTPASS(_stricmp(localIp, ipAddr)); |
| TEST_MUSTPASS(12349 != rtcpPort); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| ////////////////////// |
| // Trace filter tests |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST(SetTraceFilter); ANL(); |
| |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("" |
| "VoEBase_trace_filter.txt"))); MARK(); |
| SLEEP(100); |
| |
| // Test a few different filters, verify in trace file |
| // Each SetTraceFilter calls should be seen once, no more, no less |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceNone)); MARK(); |
| SLEEP(300); |
| // API call and info should NOT be seen in log |
| TEST_MUSTPASS(voe_base_->SetOnHoldStatus(0, true)); MARK(); |
| // API call and error should NOT be seen in log |
| TEST_MUSTPASS(!voe_base_->SetOnHoldStatus(999, true)); MARK(); |
| |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceApiCall | |
| kTraceCritical | |
| kTraceError | |
| kTraceWarning)); MARK(); |
| SLEEP(300); |
| // API call should and info should NOT be seen in log |
| TEST_MUSTPASS(voe_base_->SetOnHoldStatus(0, false)); MARK(); |
| // API call and error should be seen in log |
| TEST_MUSTPASS(!voe_base_->SetOnHoldStatus(999, true)); MARK(); |
| |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceApiCall | kTraceInfo)); |
| MARK(); |
| SLEEP(300); |
| // API call and info should be seen in log |
| TEST_MUSTPASS(voe_base_->SetOnHoldStatus(0, true)); MARK(); |
| // API call should and error should NOT be seen in log |
| TEST_MUSTPASS(!voe_base_->SetOnHoldStatus(999, true)); MARK(); |
| |
| // Back to default |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceAll)); MARK(); |
| SLEEP(300); |
| |
| AOK(); ANL(); |
| #endif |
| |
| // ------------------------------------------------------------------------ |
| // >> Multiple instance testing |
| // |
| // We should support 8 instances simultaneously |
| // and at least one should be able to have a call running |
| |
| // One instance is already created |
| VoiceEngine* instVE[7]; |
| VoEBase* baseVE[7]; |
| for (int instNum = 0; instNum < 7; instNum++) { |
| instVE[instNum] = VoiceEngine::Create(); |
| baseVE[instNum] = VoEBase::GetInterface(instVE[instNum]); |
| TEST_MUSTPASS(baseVE[instNum]->Init()); |
| TEST_MUSTPASS(baseVE[instNum]->CreateChannel()); |
| } |
| |
| TEST_LOG("Created 7 more instances of VE, make sure audio is ok...\n\n"); |
| PAUSE |
| |
| for (int instNum = 0; instNum < 7; instNum++) { |
| TEST_MUSTPASS(baseVE[instNum]->DeleteChannel(0)); |
| TEST_MUSTPASS(baseVE[instNum]->Terminate()); |
| TEST_MUSTPASS(baseVE[instNum]->Release()); |
| VoiceEngine::Delete(instVE[instNum]); |
| } |
| |
| AOK(); |
| ANL(); |
| |
| ////////////// |
| // Close down |
| TEST_MUSTPASS(voe_base_->StopSend(ch)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| TEST_MUSTPASS(voe_base_->StopReceive(ch)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(ch)); |
| |
| voe_base_->DeleteChannel(0); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestCallReport |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestCallReport() { |
| // Get required sub-API pointers |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoECallReport* report = _mgr.CallReportPtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| VoEAudioProcessing* apm = _mgr.APMPtr(); |
| VoENetwork* netw = _mgr.NetworkPtr(); |
| |
| PrepareTest("CallReport"); |
| |
| // check if this interface is supported |
| if (!report) { |
| TEST_LOG("VoECallReport is not supported!"); |
| return -1; |
| } |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("VoECallReport_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| TEST(ResetCallReportStatistics); |
| ANL(); |
| TEST_MUSTPASS(!report->ResetCallReportStatistics(-2)); |
| MARK(); // not OK |
| TEST_MUSTPASS(!report->ResetCallReportStatistics(1)); |
| MARK(); // not OK |
| TEST_MUSTPASS(report->ResetCallReportStatistics(0)); |
| MARK(); // OK |
| TEST_MUSTPASS(report->ResetCallReportStatistics(-1)); |
| MARK(); // OK |
| AOK(); |
| ANL(); |
| |
| bool enabled = false; |
| EchoStatistics echo; |
| TEST(GetEchoMetricSummary); |
| ANL(); |
| TEST_MUSTPASS(apm->GetEcMetricsStatus(enabled)); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(true)); |
| TEST_MUSTPASS(report->GetEchoMetricSummary(echo)); // all outputs will be |
| // -100 in loopback (skip further tests) |
| AOK(); |
| ANL(); |
| |
| // TODO(xians): investigate the cause of test failure before enabling. |
| /* |
| StatVal delays; |
| TEST(GetRoundTripTimeSummary); |
| ANL(); |
| // All values should be >=0 since RTCP is now on |
| TEST_MUSTPASS(report->GetRoundTripTimeSummary(0, delays)); |
| MARK(); |
| TEST_MUSTPASS(delays.min == -1); |
| TEST_MUSTPASS(delays.max == -1); |
| TEST_MUSTPASS(delays.average == -1); |
| rtp_rtcp->SetRTCPStatus(0, false); |
| // All values should be -1 since RTCP is off |
| TEST_MUSTPASS(report->GetRoundTripTimeSummary(0, delays)); |
| MARK(); |
| TEST_MUSTPASS(delays.min != -1); |
| TEST_MUSTPASS(delays.max != -1); |
| TEST_MUSTPASS(delays.average != -1); |
| rtp_rtcp->SetRTCPStatus(0, true); |
| AOK(); |
| ANL(); |
| */ |
| |
| int nDead = 0; |
| int nAlive = 0; |
| TEST(GetDeadOrAliveSummary); |
| ANL(); |
| // All results should be -1 since dead-or-alive is not active |
| TEST_MUSTPASS(report->GetDeadOrAliveSummary(0, nDead, nAlive) != -1); |
| MARK(); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, true, 1)); |
| SLEEP(2000); |
| // All results should be >= 0 since dead-or-alive is active |
| TEST_MUSTPASS(report->GetDeadOrAliveSummary(0, nDead, nAlive)); |
| MARK(); |
| TEST_MUSTPASS(nDead == -1); |
| TEST_MUSTPASS(nAlive == -1) |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, false)); |
| AOK(); |
| ANL(); |
| |
| TEST(WriteReportToFile); |
| ANL(); |
| |
| // Greek and Coptic (see http://www.utf8-chartable.de/unicode-utf8-table.pl) |
| char fileNameUTF8[64]; |
| |
| fileNameUTF8[0] = (char) 0xce; |
| fileNameUTF8[1] = (char) 0xba; |
| fileNameUTF8[2] = (char) 0xce; |
| fileNameUTF8[3] = (char) 0xbb; |
| fileNameUTF8[4] = (char) 0xce; |
| fileNameUTF8[5] = (char) 0xbd; |
| fileNameUTF8[6] = (char) 0xce; |
| fileNameUTF8[7] = (char) 0xbe; |
| fileNameUTF8[8] = '.'; |
| fileNameUTF8[9] = 't'; |
| fileNameUTF8[10] = 'x'; |
| fileNameUTF8[11] = 't'; |
| fileNameUTF8[12] = 0; |
| |
| TEST_MUSTPASS(!report->WriteReportToFile(NULL)); |
| MARK(); |
| TEST_MUSTPASS(report->WriteReportToFile("call_report.txt")); |
| MARK(); |
| TEST_MUSTPASS(report->WriteReportToFile(fileNameUTF8)); |
| MARK(); // should work with UTF-8 as well (κλνξ.txt) |
| AOK(); |
| ANL(); |
| |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestCodec |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestCodec() { |
| PrepareTest("Codec"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoECodec* codec = _mgr.CodecPtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("VoECodec_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| #ifdef WEBRTC_EXTERNAL_TRANSPORT |
| ExtendedTestTransport* ptrTransport(NULL); |
| ptrTransport = new ExtendedTestTransport(netw); |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| #else |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| #endif |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| int i; |
| int err; |
| |
| CodecInst cinst; |
| |
| ///////////////////////// |
| // GetNumOfCodecs |
| |
| int nCodecs; |
| |
| TEST(GetNumOfCodecs); |
| ANL(); |
| // validate #codecs |
| nCodecs = codec->NumOfCodecs(); |
| MARK(); |
| TEST_MUSTPASS(nCodecs < 0); |
| AOK(); |
| ANL(); |
| |
| /////////////////// |
| // GetCodec |
| TEST(GetCodec); |
| ANL(); |
| // scan all supported codecs |
| nCodecs = codec->NumOfCodecs(); |
| for (int index = 0; index < nCodecs; index++) { |
| TEST_MUSTPASS(codec->GetCodec(index, cinst)); |
| TEST_LOG("[%2d] %16s: fs=%6d, pt=%4d, rate=%7d, ch=%2d, size=%5d", index, cinst.plname, |
| cinst.plfreq, cinst.pltype, cinst.rate, cinst.channels, cinst.pacsize); |
| if (cinst.pltype == -1) { |
| TEST_LOG(" <= NOTE pt=-1\n"); |
| } else { |
| ANL(); |
| } |
| } |
| |
| // ensure that an invalid index parameter is detected |
| TEST_MUSTPASS(-1 != codec->GetCodec(-1, cinst)); |
| nCodecs = codec->NumOfCodecs(); |
| TEST_MUSTPASS(-1 != codec->GetCodec(nCodecs, cinst)); |
| MARK(); |
| // ensure that error code is VE_INVALID_LISTNR |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_LISTNR); |
| AOK(); |
| ANL(); |
| |
| /////////////////////// |
| // GetSendCodec |
| TEST(GetSendCodec); |
| ANL(); |
| |
| CodecInst defaultCodec; |
| |
| // check the channel parameter |
| int nMaxChannels(voe_base_->MaxNumOfChannels()); |
| TEST_MUSTPASS(-1 != codec->GetSendCodec(nMaxChannels-1, cinst)); |
| MARK(); // not created |
| TEST_MUSTPASS(-1 != codec->GetSendCodec(nMaxChannels, cinst)); |
| MARK(); // out of range |
| TEST_MUSTPASS(-1 != codec->GetSendCodec(-1, cinst)); |
| MARK(); // out of range |
| TEST_MUSTPASS(codec->GetSendCodec(0, cinst)); |
| MARK(); // OK |
| |
| nCodecs = codec->NumOfCodecs(); |
| for (int index = 0; index < nCodecs; index++) { |
| TEST_MUSTPASS(codec->GetCodec(index, defaultCodec)); |
| if (codec->SetSendCodec(0, defaultCodec) == 0) { |
| TEST_MUSTPASS(codec->GetSendCodec(0, cinst)); |
| MARK(); |
| //TEST_LOG("[%2d] %s: fs=%d, pt=%d, rate=%d, ch=%d, size=%d\n", |
| // index, cinst.plname, cinst.plfreq, cinst.pltype, cinst.rate, |
| // cinst.channels, cinst.pacsize); |
| TEST_MUSTPASS(cinst.pacsize != defaultCodec.pacsize); |
| TEST_MUSTPASS(cinst.plfreq != defaultCodec.plfreq); |
| TEST_MUSTPASS(cinst.pltype != defaultCodec.pltype); |
| TEST_MUSTPASS(cinst.rate != defaultCodec.rate); |
| TEST_MUSTPASS(cinst.channels != defaultCodec.channels); |
| } |
| } |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| /////////////////////// |
| // SetSendCodec |
| TEST(SetSendCodec); |
| ANL(); |
| |
| // --- Scan all supported codecs and set default parameters |
| |
| nCodecs = codec->NumOfCodecs(); |
| for (int index = 0; index < nCodecs; index++) { |
| // Get default (ACM) settings |
| TEST_MUSTPASS(codec->GetCodec(index, cinst)); |
| defaultCodec = cinst; |
| TEST_LOG("[%2d] %s (default): fs=%d, pt=%d, rate=%d, ch=%d, size=%d\n", |
| index, cinst.plname, cinst.plfreq, cinst.pltype, cinst.rate, |
| cinst.channels, cinst.pacsize); |
| |
| // Verify invalid codec names |
| if (!_stricmp("CN", cinst.plname) || !_stricmp("telephone-event", |
| cinst.plname) |
| || !_stricmp("red", cinst.plname)) { |
| // default settings for invalid payload names (should give |
| // VE_INVALID_PLNAME) |
| TEST_MUSTPASS(!codec->SetSendCodec(0, cinst)); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| continue; |
| } |
| |
| // If we build the ACM with more codecs than we have payload types, |
| // some codecs will be given -1 as default payload type. This is a fix |
| // to ensure that we can complete these tests also for this case. |
| if (cinst.pltype == -1) { |
| cinst.pltype = 97; |
| } |
| |
| // --- Default settings |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| // --- Packet size |
| TEST_LOG("\npacsize : "); |
| |
| for (int pacsize = 80; pacsize < 1440; pacsize += 80) { |
| cinst.pacsize = pacsize; |
| if (-1 != codec->SetSendCodec(0, cinst)) { |
| // log valid packet size |
| TEST_LOG("%d ", pacsize); |
| } else { |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| } |
| cinst.pacsize = defaultCodec.pacsize; |
| |
| // --- Audio channels (1/mono or 2/stereo) |
| TEST_LOG("\nchannels: "); |
| for (int channels = 1; channels < 4; channels++) { |
| cinst.channels = channels; |
| if (-1 != codec->SetSendCodec(0, cinst)) { |
| // valid channels (only 1 should be OK) |
| TEST_LOG("%d ", channels); |
| } else { |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| } |
| cinst.channels = defaultCodec.channels; |
| |
| // --- Payload frequency |
| TEST_LOG("\nplfreq : "); |
| cinst.plfreq = defaultCodec.plfreq; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.plfreq); |
| |
| // --- Payload name |
| |
| strcpy(cinst.plname, "INVALID"); |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)) |
| { |
| // ensure that error code is VE_INVALID_PLNAME |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| |
| // restore default plname |
| strcpy(cinst.plname, defaultCodec.plname); |
| |
| // --- Payload type (dynamic range is 96-127) |
| TEST_LOG("\npltype : "); |
| // All PT should be OK, test a few different |
| cinst.pltype = defaultCodec.pltype; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.pltype); |
| cinst.pltype = defaultCodec.pltype + 1; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.pltype); |
| const int valid_pltypes[4] = { 0, 96, 117, 127 }; |
| for (i = 0; i < static_cast<int> (sizeof(valid_pltypes) / sizeof(int)); i++) { |
| cinst.pltype = valid_pltypes[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.pltype); |
| } |
| // Restore default |
| cinst.pltype = defaultCodec.pltype; |
| |
| // --- Codec rate |
| TEST_LOG("\nrate : "); |
| if (_stricmp("isac", cinst.plname) == 0) { |
| // ISAC |
| if (cinst.plfreq == 16000) { |
| int valid_rates[3] = { -1, 10000, 32000 }; |
| // failed in RegisterPayload when rate is 32000 |
| for (i = 0; i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| cinst.rate = 0; // invalid |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)) |
| { |
| // ensure that error code is VE_CANNOT_SET_SEND_CODEC |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| ANL(); |
| } else //ISACSWB |
| { |
| // rate changing fails in RegisterPayload |
| int valid_rates[8] = { -1, 10000, 25000, 32000, 35000, 45000, 50000, 52000 }; |
| for (i = 0; i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| int invalid_rates[3] = { 0, 5000, 57000 }; // invalid |
| for (i = 0; i < static_cast<int> (sizeof(invalid_rates) / sizeof(int)); i++) { |
| cinst.rate = invalid_rates[i]; |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)) |
| { |
| // ensure that error code is VE_CANNOT_SET_SEND_CODEC |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| } |
| ANL(); |
| } |
| } else if (_stricmp("amr", cinst.plname) == 0) { |
| int valid_rates[8] = { 4750, 5150, 5900, 6700, 7400, 7950, 10200, 12200 }; |
| for (i = 0; |
| i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); |
| i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| ANL(); |
| } else if (_stricmp("g7291", cinst.plname) == 0) { |
| int valid_rates[12] = { 8000, 12000, 14000, 16000, 18000, 20000, 22000, |
| 24000, 26000, 28000, 30000, 32000 }; |
| for (i = 0; |
| i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); |
| i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| ANL(); |
| } else if (_stricmp("amr-wb", cinst.plname) == 0) { |
| int valid_rates[9] = { 7000, 9000, 12000, 14000, 16000, 18000, 20000, |
| 23000, 24000 }; |
| for (i = 0; |
| i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); |
| i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| TEST_LOG(" <=> "); |
| ANL(); |
| } else if (_stricmp("speex", cinst.plname) == 0) { |
| // Valid speex rates are > 2000, testing some of them here |
| int valid_rates[9] = { 2001, 4000, 7000, 11000, 15000, 20000, 25000, |
| 33000, 46000 }; |
| for (i = 0; |
| i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); |
| i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| cinst.rate = 2000; // invalid |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)) |
| { |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| ANL(); |
| } else if (_stricmp("silk", cinst.plname) == 0) { |
| // Valid Silk rates are 6000 - 40000, listing some of them here |
| int valid_rates[7] = { 6000, 10000, 15000, 20000, 25000, 32000, 40000 }; |
| for (i = 0; |
| i < static_cast<int> (sizeof(valid_rates) / sizeof(int)); |
| i++) { |
| cinst.rate = valid_rates[i]; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| } |
| cinst.rate = 5999; // invalid |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)) |
| { |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| cinst.rate = 40001; // invalid |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)) |
| { |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| ANL(); |
| } else { |
| // Use default rate for all other codecs. |
| cinst.rate = defaultCodec.rate; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_LOG("%d ", cinst.rate); |
| cinst.rate = defaultCodec.rate + 17; |
| TEST_MUSTPASS(!codec->SetSendCodec(0, cinst)); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| ANL(); |
| } |
| cinst.rate = defaultCodec.rate; |
| |
| // run some extra tests for L16 |
| if (_stricmp("l16", cinst.plname) == 0) { |
| if (8000 == cinst.plfreq) { |
| // valid pacsizes: 80, 160, 240, 320 |
| cinst.pacsize = 480; // only supported in combination with 16kHz |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| cinst.pacsize = 640; // only supported in combination with 16kHz |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } else { |
| // valid pacsizes: 160, 320, 480, 640 |
| cinst.pacsize = 80; // only supported in combination with 8kHz |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| cinst.pacsize = 240; // only supported in combination with 8kHz |
| TEST_MUSTPASS(-1 != codec->SetSendCodec(0, cinst)); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| } |
| } |
| ANL(); |
| } // for (int index = 0; index < nCodecs; index++) |
| |
| // restore PCMU |
| const CodecInst tmp = { 0, "PCMU", 8000, 160, 1, 64000 }; |
| TEST_MUSTPASS(codec->SetSendCodec(0, tmp)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| /////// |
| // VAD |
| |
| const int VADSleep = 0; |
| |
| bool disabledDTX; |
| VadModes mode; |
| bool enabled; |
| |
| // verify default settings (should be OFF, kVadConventional and DTX enabled) |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(mode != kVadConventional); |
| TEST_MUSTPASS(disabledDTX != true); |
| |
| // enable default VAD settings |
| TEST_MUSTPASS(codec->SetVADStatus(0, true)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(mode != kVadConventional); |
| TEST_MUSTPASS(disabledDTX != false); |
| SLEEP(VADSleep); |
| |
| // set kVadConventional mode |
| TEST_MUSTPASS(codec->SetVADStatus(0, true, kVadConventional)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(mode != kVadConventional); |
| SLEEP(VADSleep); |
| |
| // set kVadAggressiveLow mode |
| TEST_MUSTPASS(codec->SetVADStatus(0, true, kVadAggressiveLow)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(mode != kVadAggressiveLow); |
| SLEEP(VADSleep); |
| |
| // set kVadAggressiveMid mode |
| TEST_MUSTPASS(codec->SetVADStatus(0, true, kVadAggressiveMid)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(mode != kVadAggressiveMid); |
| SLEEP(VADSleep); |
| |
| // set kVadAggressiveMid mode |
| TEST_MUSTPASS(codec->SetVADStatus(0, true, kVadAggressiveHigh)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(mode != kVadAggressiveHigh); |
| SLEEP(VADSleep); |
| |
| // turn DTX OFF (audio should not be affected by VAD decisions) |
| TEST_MUSTPASS(codec->SetVADStatus(0, true, kVadConventional, true)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(disabledDTX != true); |
| SLEEP(VADSleep); |
| |
| // try to enable DTX again (should fail since VAD is disabled) |
| TEST_MUSTPASS(codec->SetVADStatus(0, false, kVadConventional, false)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(disabledDTX == false); |
| SLEEP(VADSleep); |
| |
| // disable VAD |
| TEST_MUSTPASS(codec->SetVADStatus(0, false)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(enabled != false); |
| SLEEP(VADSleep); |
| |
| // restore default VAD |
| TEST_MUSTPASS(codec->SetVADStatus(0, true)); |
| TEST_MUSTPASS(codec->SetVADStatus(0, false)); |
| TEST_MUSTPASS(codec->GetVADStatus(0, enabled, mode, disabledDTX)); |
| TEST_LOG("VAD: enabled=%d, mode=%d, disabledDTX=%d\n", enabled, mode, |
| disabledDTX); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(mode != kVadConventional); |
| TEST_MUSTPASS(disabledDTX != true); |
| SLEEP(VADSleep); |
| |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| ////////////////////// |
| // GetRecCodec |
| TEST(GetRecCodec); |
| ANL(); |
| |
| // stop all streaming first |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| // start loopback streaming (PCMU is default) |
| #ifndef WEBRTC_EXTERNAL_TRANSPORT |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0,8000,"127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0,8000)); |
| #endif |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(100); // ensure that at least one packets is received |
| |
| // scan all supported and valid codecs |
| CodecInst newCodec; |
| for (i = 0; i < codec->NumOfCodecs(); i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, newCodec)); |
| // test all valid send codecs |
| if (!_stricmp("red", newCodec.plname) || !_stricmp("cn", newCodec.plname) |
| || !_stricmp("telephone-event", newCodec.plname)) { |
| continue; // Ignore these |
| } |
| if (-1 != codec->SetSendCodec(0, newCodec)) { |
| SLEEP(150); |
| // verify correct detection |
| TEST_MUSTPASS(codec->GetRecCodec(0, cinst)); |
| TEST_LOG("%s %s ", newCodec.plname, cinst.plname); |
| TEST_MUSTPASS(_stricmp(newCodec.plname, cinst.plname) != 0); |
| TEST_MUSTPASS(cinst.pltype != newCodec.pltype); |
| TEST_MUSTPASS(cinst.plfreq != newCodec.plfreq); |
| } |
| } |
| |
| // stop streaming |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| #ifdef WEBRTC_CODEC_GSMAMR |
| ////////////////////////// |
| // SetAMREncFormat |
| |
| // Fresh channel |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| TEST(SetAMREncFormat); ANL(); |
| |
| //set another codec which is not AMR |
| TEST_MUSTPASS(codec->GetCodec(0, cinst)); |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| //try to change the encode format, tests should fail |
| TEST_MUSTPASS(-1 != codec->SetAMREncFormat(0)); MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMREncFormat(0, kRfc3267BwEfficient)); |
| MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMREncFormat(0, kRfc3267OctetAligned)); |
| MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMREncFormat(0, kRfc3267FileStorage)); |
| MARK(); |
| |
| //set AMR as encoder |
| strcpy(cinst.plname,"AMR"); |
| cinst.channels=1; cinst.plfreq=8000; cinst.rate=12200; cinst.pltype=112; |
| cinst.pacsize=160; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| //try to change the encode format, tests should pass |
| TEST_MUSTPASS(codec->SetAMREncFormat(0)); MARK(); |
| TEST_MUSTPASS(codec->SetAMREncFormat(0, kRfc3267BwEfficient)); MARK(); |
| TEST_MUSTPASS(codec->SetAMREncFormat(0, kRfc3267OctetAligned)); MARK(); |
| TEST_MUSTPASS(codec->SetAMREncFormat(0, kRfc3267FileStorage)); MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMREncFormat(-1)); MARK(); |
| TEST_MUSTPASS(codec->SetAMREncFormat(0)); MARK(); // restore default |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| ////////////////////////// |
| // SetAMRDecFormat |
| |
| TEST(SetAMRDecFormat); ANL(); |
| |
| // It should not be possible to set AMR dec format before valid AMR decoder |
| // is registered |
| TEST_MUSTPASS(!codec->SetAMRDecFormat(0)); MARK(); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_AUDIO_CODING_MODULE_ERROR); |
| |
| // Ensure that ACM::RegisterReceiveCodec(AMR) is called |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| |
| // All these tests should now pass |
| TEST_MUSTPASS(codec->SetAMRDecFormat(0)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRDecFormat(0, kRfc3267BwEfficient)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRDecFormat(0, kRfc3267OctetAligned)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRDecFormat(0, kRfc3267FileStorage)); MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMRDecFormat(-1)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRDecFormat(0)); MARK(); // restore default |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| #endif // #ifdef WEBRTC_CODEC_GSMAMR |
| #ifdef WEBRTC_CODEC_GSMAMRWB |
| ////////////////////////// |
| // SetAMRWbEncFormat |
| |
| // Fresh channel |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| TEST(SetAMRWbEncFormat); ANL(); |
| |
| //set another codec which is not AMR-wb |
| TEST_MUSTPASS(codec->GetCodec(0, cinst)); |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| //try to change the encode format, tests should fail |
| TEST_MUSTPASS(-1 != codec->SetAMRWbEncFormat(0)); MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMRWbEncFormat(0, kRfc3267BwEfficient)); |
| MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMRWbEncFormat(0, kRfc3267OctetAligned)); |
| MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMRWbEncFormat(0, kRfc3267FileStorage)); |
| MARK(); |
| |
| //set AMR-wb as encoder |
| strcpy(cinst.plname,"AMR-WB"); |
| cinst.channels=1; cinst.plfreq=16000; cinst.rate=20000; |
| cinst.pltype=112; cinst.pacsize=320; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| //try to change the encode format, tests should pass |
| TEST_MUSTPASS(codec->SetAMRWbEncFormat(0)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbEncFormat(0, kRfc3267BwEfficient)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbEncFormat(0, kRfc3267OctetAligned)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbEncFormat(0, kRfc3267FileStorage)); MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMRWbEncFormat(-1)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbEncFormat(0)); MARK(); // restore default |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| ////////////////////////// |
| // SetAMRDecFormat |
| |
| TEST(SetAMRWbDecFormat); ANL(); |
| |
| // It should not be possible to set AMR dec format before valid AMR decoder |
| // is registered |
| TEST_MUSTPASS(!codec->SetAMRWbDecFormat(0)); MARK(); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_AUDIO_CODING_MODULE_ERROR); |
| |
| // Ensure that ACM::RegisterReceiveCodec(AMR) is called |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| |
| // All these tests should now pass |
| TEST_MUSTPASS(codec->SetAMRWbDecFormat(0)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbDecFormat(0, kRfc3267BwEfficient)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbDecFormat(0, kRfc3267OctetAligned)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbDecFormat(0, kRfc3267FileStorage)); MARK(); |
| TEST_MUSTPASS(-1 != codec->SetAMRWbDecFormat(-1)); MARK(); |
| TEST_MUSTPASS(codec->SetAMRWbDecFormat(0)); MARK(); // restore default |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| #endif // #ifdef WEBRTC_CODEC_GSMAMRWB |
| /////////////////////////////// |
| // SetSendCNPayloadType |
| TEST(SetSendCNPayloadType); |
| ANL(); |
| |
| TEST_MUSTPASS(-1 != codec->SetSendCNPayloadType(-1, 0)); |
| MARK(); // invalid channel |
| |
| // Invalid payload range (only dynamic range [96,127] |
| TEST_MUSTPASS(-1 != codec->SetSendCNPayloadType(0, 0)); |
| MARK(); // invalid PT |
| TEST_MUSTPASS(-1 != codec->SetSendCNPayloadType(0, 95)); |
| MARK(); // invalid PT |
| TEST_MUSTPASS(-1 != codec->SetSendCNPayloadType(0, 128)); |
| MARK(); // invalid PT |
| TEST_MUSTPASS(-1 != codec->SetSendCNPayloadType(0, -1)); |
| MARK(); // invalid PT |
| |
| // Not possible to change PT for 8000 |
| TEST_MUSTPASS(!codec->SetSendCNPayloadType(0, 96, kFreq8000Hz)); |
| MARK(); |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_PLFREQ); |
| |
| // Try some dynamic for 16000 and 32000 as well |
| TEST_MUSTPASS(codec->SetSendCNPayloadType(0, 96, kFreq16000Hz)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetSendCNPayloadType(0, 96, kFreq32000Hz)); |
| MARK(); // same should work |
| TEST_MUSTPASS(codec->SetSendCNPayloadType(0, 127, kFreq16000Hz)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetSendCNPayloadType(0, 127, kFreq32000Hz)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetSendCNPayloadType(0, 100, kFreq32000Hz)); |
| MARK(); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| ///////////////////////////// |
| // SetRecPayloadType |
| TEST(SetRecPayloadType); |
| ANL(); |
| |
| // scan all supported and valid codecs without changing payloads |
| nCodecs = codec->NumOfCodecs(); |
| for (i = 0; i < nCodecs; i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, newCodec)); |
| // If no default payload type is defined, we use 127 |
| if (-1 == newCodec.pltype) { |
| newCodec.pltype = 127; |
| } |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, newCodec)); |
| MARK(); // use default |
| newCodec.pltype = 99; |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, newCodec)); |
| MARK(); // use same PT on all |
| newCodec.pltype = -1; |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, newCodec)); |
| MARK(); // deregister all PTs |
| } |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| ///////////////////////////// |
| // GetRecPayloadType |
| TEST(GetRecPayloadType); |
| ANL(); |
| |
| CodecInst extraCodec; |
| for (i = 0; i < nCodecs; i++) { |
| // Set defaults |
| TEST_MUSTPASS(codec->GetCodec(i, newCodec)); |
| // If no default payload type is defined, we use 127 |
| if (-1 == newCodec.pltype) { |
| newCodec.pltype = 127; |
| } |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, newCodec)); |
| //TEST_LOG("[%2d] %s (SetRec): fs=%d, pt=%d, rate=%d, ch=%d, size=%d\n", |
| // i, newCodec.plname, newCodec.plfreq, newCodec.pltype, newCodec.rate, |
| // newCodec.channels, newCodec.pacsize); |
| extraCodec.pltype = -1; // don't know this yet |
| extraCodec.plfreq = newCodec.plfreq; |
| extraCodec.rate = newCodec.rate; |
| extraCodec.channels = newCodec.channels; |
| strcpy(extraCodec.plname, newCodec.plname); |
| // Verfify that setting is OK |
| TEST_MUSTPASS(codec->GetRecPayloadType(0, extraCodec)); |
| //TEST_LOG("[%2d] %s (GetRec): fs=%d, pt=%d, rate=%d, ch=%d, size=%d\n", |
| // i, extraCodec.plname, extraCodec.plfreq, extraCodec.pltype, |
| // extraCodec.rate, extraCodec.channels, extraCodec.pacsize); |
| TEST_MUSTPASS(newCodec.pltype != extraCodec.pltype); |
| TEST_MUSTPASS(newCodec.plfreq != extraCodec.plfreq); |
| TEST_MUSTPASS(newCodec.channels != extraCodec.channels); |
| } |
| |
| AOK(); |
| ANL(); |
| |
| //////////////////////////////////////////////////// |
| // SetRecPayloadType - remove receive codecs |
| TEST(SetRecPayloadType - removing receive codecs); |
| ANL(); |
| |
| #ifndef WEBRTC_EXTERNAL_TRANSPORT |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| #endif |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| if (file) { |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, |
| _mgr.AudioFilename(), |
| true, |
| true)); |
| } |
| |
| // Scan all supported and valid codecs and remove from receiving db, then |
| // restore |
| nCodecs = codec->NumOfCodecs(); |
| for (i = 0; i < nCodecs; i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, cinst)); |
| if (!_stricmp("red", cinst.plname) || !_stricmp("cn", cinst.plname) |
| || !_stricmp("telephone-event", cinst.plname)) { |
| continue; // Ignore these |
| } |
| TEST_LOG("Testing codec: %s", cinst.plname); |
| fflush(NULL); |
| |
| if (-1 == cinst.pltype) { |
| // If no default payload type is defined, we use 127, |
| // codec is not registered for receiving |
| cinst.pltype = 127; |
| } else { |
| // Remove codec |
| memcpy(&extraCodec, &cinst, sizeof(CodecInst)); |
| extraCodec.pltype = -1; |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, extraCodec)); |
| } |
| |
| // Set send codec |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| // Verify no audio |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_LOG(" silence"); |
| fflush(NULL); |
| SLEEP(800); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| // Restore codec |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| |
| // Verify audio |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_LOG(" audio"); |
| fflush(NULL); |
| SLEEP(800); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| if (127 == cinst.pltype) { |
| // If no default payload type is defined, i.e. we have set pt to |
| //127 above, |
| // make sure we remove codec from receiving |
| cinst.pltype = -1; |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| } |
| |
| ANL(); |
| } |
| |
| // Remove certain codecs |
| TEST_LOG("Removing receive codecs:"); |
| for (i = 0; i < nCodecs; i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, cinst)); |
| if (!_stricmp("ipcmwb", cinst.plname) || !_stricmp("pcmu", cinst.plname) |
| || !_stricmp("eg711a", cinst.plname)) { |
| TEST_LOG(" %s", cinst.plname); |
| memcpy(&extraCodec, &cinst, sizeof(CodecInst)); |
| extraCodec.pltype = -1; |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, extraCodec)); |
| } |
| } |
| ANL(); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| // Test sending all codecs - verify audio/no audio depending on codec |
| TEST_LOG("Looping through send codecs \n"); |
| TEST_LOG("Verify that removed codecs are not audible and the other are \n"); |
| for (i = 0; i < nCodecs; i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, cinst)); |
| if (!_stricmp("red", cinst.plname) || !_stricmp("cn", cinst.plname) |
| || !_stricmp("telephone-event", cinst.plname)) { |
| continue; // Ignore these |
| } |
| TEST_LOG("Testing codec: %s \n", cinst.plname); |
| |
| // If no default payload type is defined, we use 127 and set receive |
| // payload type |
| if (-1 == cinst.pltype) { |
| cinst.pltype = 127; |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| } |
| |
| // Set send codec |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| // Verify audio/no audio |
| SLEEP(800); |
| } |
| |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| // Restore codecs |
| TEST_LOG("Restoring receive codecs:"); |
| for (i = 0; i < nCodecs; i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, cinst)); |
| if (!_stricmp("ipcmwb", cinst.plname) || !_stricmp("pcmu", cinst.plname) |
| || !_stricmp("eg711a", cinst.plname)) { |
| TEST_LOG(" %s", cinst.plname); |
| memcpy(&extraCodec, &cinst, sizeof(CodecInst)); |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| } |
| } |
| ANL(); |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| // Test sending all codecs - verify audio |
| TEST_LOG("Looping through send codecs \n"); |
| TEST_LOG("Verify that all codecs are audible \n"); |
| for (i = 0; i < nCodecs; i++) { |
| TEST_MUSTPASS(codec->GetCodec(i, cinst)); |
| if (!_stricmp("red", cinst.plname) || !_stricmp("cn", cinst.plname) |
| || !_stricmp("telephone-event", cinst.plname)) { |
| continue; // Ignore these |
| } |
| TEST_LOG("Testing codec: %s \n", cinst.plname); |
| |
| // If no default payload type is defined, we use 127 and set receive |
| // payload type |
| if (-1 == cinst.pltype) { |
| cinst.pltype = 127; |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| } |
| |
| // Set send codec |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| // Verify audio/no audio |
| SLEEP(800); |
| } |
| |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| // Fresh channel |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| #if defined(WEBRTC_CODEC_ISAC) |
| |
| ///////////////////////////////////// |
| // SetISACInitTargetRate - wb |
| TEST(SetISACInitTargetRate); |
| ANL(); |
| |
| // set PCMU as sending codec |
| cinst.channels = 1; |
| cinst.pacsize = 160; |
| cinst.plfreq = 8000; |
| strcpy(cinst.plname, "PCMU"); |
| cinst.pltype = 0; |
| cinst.rate = 64000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, 10000)); |
| MARK(); // should fail since iSAC is not active |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_CODEC_ERROR); |
| |
| // set iSAC as sending codec (16kHz) |
| cinst.channels = 1; |
| cinst.plfreq = 16000; |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 103; |
| cinst.rate = -1; // adaptive rate |
| cinst.pacsize = 480; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(1, 10000)); |
| MARK(); // invalid channel |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, 500)); |
| MARK(); // invalid target rates (too small) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, 33000)); |
| MARK(); // invalid target rates (too large) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 10000)); |
| MARK(); // life is good now |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 0)); |
| MARK(); // 0 is a valid rate |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 32000)); |
| MARK(); // try max as well |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 32000, true)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 32000, false)); |
| MARK(); |
| |
| cinst.pacsize = 960; // 60ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 32000, false)); |
| MARK(); |
| |
| cinst.rate = 20000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, 32000)); |
| MARK(); // only works in adaptive mode |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_AUDIO_CODING_MODULE_ERROR); |
| |
| cinst.rate = -1; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 32000)); |
| MARK(); // back to adaptive mode |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| ///////////////////////////////////// |
| // SetISACInitTargetRate - swb |
| TEST(ISACSWB SetISACInitTargetRate); |
| ANL(); |
| |
| // set iSAC as sending codec |
| cinst.channels = 1; |
| cinst.plfreq = 32000; |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 104; |
| cinst.rate = -1; // default rate |
| cinst.pacsize = 960; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(1, 10000)); |
| MARK(); // invalid channel |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, -1)); |
| MARK(); // invalid target rates (too small) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, -1)); |
| MARK(); // invalid target rates (too small) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, 500)); |
| MARK(); // invalid target rates (too small) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACInitTargetRate(0, 57000)); |
| MARK(); // invalid target rates (valid range is [10000, 56000]) |
| |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 10000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 0)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 56000)); |
| MARK(); // try max as well |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 56000, true)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACInitTargetRate(0, 56000, false)); |
| MARK(); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| //////////////////////////////// |
| // SetISACMaxRate |
| TEST(SetISACMaxRate); |
| ANL(); |
| |
| // set PCMU as sending codec |
| cinst.channels = 1; |
| cinst.pacsize = 160; |
| cinst.plfreq = 8000; |
| strcpy(cinst.plname, "PCMU"); |
| cinst.pltype = 0; |
| cinst.rate = 64000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 48000)); |
| MARK(); // should fail since iSAC is not active |
| TEST_MUSTPASS(voe_base_->LastError() != VE_CODEC_ERROR); |
| |
| // set iSAC as sending codec |
| cinst.channels = 1; |
| cinst.plfreq = 16000; |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 103; |
| cinst.rate = -1; // adaptive rate |
| cinst.pacsize = 480; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(1, 48000)); |
| MARK(); // invalid channel |
| TEST_MUSTPASS(voe_base_->LastError() != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 31900)); |
| MARK(); // invalid target rates (too small) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 53500)); |
| MARK(); // invalid target rates (too large) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 32000)); |
| MARK(); // life is good now |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 40000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 48000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 53400)); |
| MARK(); // try max as well (default) |
| |
| cinst.pacsize = 960; // 60ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 48000)); |
| MARK(); |
| |
| cinst.rate = 20000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 40000)); |
| MARK(); // also works in non-adaptive mode |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| TEST(ISACSWB SetISACMaxRate); |
| ANL(); |
| // set iSAC as sending codec |
| cinst.channels = 1; |
| cinst.plfreq = 32000; |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 104; |
| cinst.rate = 45000; // instantaneous mode |
| cinst.pacsize = 960; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(1, 48000)); |
| MARK(); // invalid channel |
| TEST_MUSTPASS(voe_base_->LastError() != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 31900)); |
| MARK(); // invalid target rates (too small) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 107500)); |
| MARK(); // invalid target rates (too large) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 32000)); |
| MARK(); // life is good now |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 40000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 55000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 80000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 107000)); |
| MARK(); // try max as well (default) |
| |
| |
| cinst.rate = -1; // adaptive mode |
| cinst.pacsize = 960; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(1, 48000)); |
| MARK(); // invalid channel |
| TEST_MUSTPASS(voe_base_->LastError() != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 31900)); |
| MARK(); // invalid target rates (too small) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxRate(0, 107500)); |
| MARK(); // invalid target rates (too large) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 32000)); |
| MARK(); // life is good now |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 40000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 55000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 80000)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxRate(0, 107000)); |
| MARK(); // try max as well (default) |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| //////////////////////////////// |
| // SetISACMaxPayloadSize |
| TEST(SetISACMaxPayloadSize); |
| ANL(); |
| |
| // set PCMU as sending codec |
| cinst.channels = 1; |
| cinst.pacsize = 160; |
| cinst.plfreq = 8000; |
| strcpy(cinst.plname, "PCMU"); |
| cinst.pltype = 0; |
| cinst.rate = 64000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(0, 120)); |
| MARK(); // should fail since iSAC is not active |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_CODEC_ERROR); |
| |
| // set iSAC as sending codec |
| cinst.channels = 1; |
| cinst.plfreq = 16000; |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 103; |
| cinst.rate = -1; // adaptive rate |
| cinst.pacsize = 480; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(1, 120)); |
| MARK(); // invalid channel |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(0, 100)); |
| MARK(); // invalid size (too small) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(0, 410)); |
| MARK(); // invalid size (too large) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACMaxPayloadSize(0, 200)); |
| MARK(); // life is good now |
| TEST_MUSTPASS(codec->SetISACMaxPayloadSize(0, 120)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxPayloadSize(0, 400)); |
| MARK(); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| TEST(ISACSWB SetISACMaxPayloadSize); |
| ANL(); |
| // set iSAC as sending codec |
| cinst.channels = 1; |
| cinst.plfreq = 32000; |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 104; |
| cinst.rate = 45000; // default rate |
| cinst.pacsize = 960; // 30ms |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(1, 100)); |
| MARK(); // invalid channel |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(0, 100)); |
| MARK(); // invalid size (too small) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(!codec->SetISACMaxPayloadSize(0, 610)); |
| MARK(); // invalid size (too large) |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_INVALID_ARGUMENT); |
| |
| TEST_MUSTPASS(codec->SetISACMaxPayloadSize(0, 200)); |
| MARK(); // life is good now |
| TEST_MUSTPASS(codec->SetISACMaxPayloadSize(0, 120)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetISACMaxPayloadSize(0, 600)); |
| MARK(); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| // set iSAC as sending codec |
| // set iSAC-wb as sending codec |
| #ifdef WEBRTC_EXTERNAL_TRANSPORT |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| #else |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8001, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8001)); |
| #endif |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| 0, GetFilename("audio_long16.pcm"), true , true)); |
| cinst.channels = 1; |
| TEST_LOG("Testing codec: Switch between iSAC-wb and iSAC-swb \n"); |
| TEST_LOG("Testing codec: iSAC wideband \n"); |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 103; |
| cinst.rate = -1; // default rate |
| cinst.pacsize = 480; // 30ms |
| cinst.plfreq = 16000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| SLEEP(2000); |
| TEST_LOG(" : iSAC superwideband \n"); |
| cinst.pltype = 104; |
| cinst.rate = -1; // default rate |
| cinst.pacsize = 960; // 30ms |
| cinst.plfreq = 32000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| SLEEP(2000); |
| TEST_LOG(" : iSAC wideband \n"); |
| strcpy(cinst.plname, "ISAC"); |
| cinst.pltype = 103; |
| cinst.rate = -1; // default rate |
| cinst.pacsize = 480; // 30ms |
| cinst.plfreq = 16000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| SLEEP(2000); |
| TEST_LOG(" : iSAC superwideband \n"); |
| cinst.pltype = 104; |
| cinst.rate = -1; // default rate |
| cinst.pacsize = 960; // 30ms |
| cinst.plfreq = 32000; |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| SLEEP(2000); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| #else |
| TEST_LOG("Skipping extended iSAC API tests - " |
| "WEBRTC_CODEC_ISAC not defined\n"); |
| #endif // #if defined(WEBRTC_CODEC_ISAC) |
| #ifdef WEBRTC_EXTERNAL_TRANSPORT |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| delete ptrTransport; |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestDtmf |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestDtmf() { |
| PrepareTest("Dtmf"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEDtmf* dtmf = _mgr.DtmfPtr(); |
| VoECodec* codec = _mgr.CodecPtr(); |
| VoEVolumeControl* volume = _mgr.VolumeControlPtr(); |
| |
| //#ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("VoEDtmf_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| //#endif |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| // SetDtmfFeedbackStatus |
| TEST(SetDtmfFeedbackStatus & GetDtmfFeedbackStatus); |
| ANL(); |
| bool dtmfFeedback = false, dtmfDirectFeedback = true; |
| TEST_MUSTPASS(dtmf->GetDtmfFeedbackStatus(dtmfFeedback, |
| dtmfDirectFeedback)); |
| TEST_MUSTPASS(!dtmfFeedback); |
| TEST_MUSTPASS(dtmfDirectFeedback); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0)); |
| MARK(); |
| SLEEP(500); |
| |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(false, false)); |
| TEST_MUSTPASS(dtmf->GetDtmfFeedbackStatus(dtmfFeedback, |
| dtmfDirectFeedback)); |
| TEST_MUSTPASS(dtmfFeedback); |
| TEST_MUSTPASS(dtmfDirectFeedback); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0)); |
| MARK(); |
| SLEEP(500); |
| |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(false, true)); |
| TEST_MUSTPASS(dtmf->GetDtmfFeedbackStatus(dtmfFeedback, |
| dtmfDirectFeedback)); |
| TEST_MUSTPASS(dtmfFeedback); |
| TEST_MUSTPASS(!dtmfDirectFeedback); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0)); |
| MARK(); |
| SLEEP(500); |
| |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(true, false)); |
| TEST_MUSTPASS(dtmf->GetDtmfFeedbackStatus(dtmfFeedback, |
| dtmfDirectFeedback)); |
| TEST_MUSTPASS(!dtmfFeedback); |
| TEST_MUSTPASS(dtmfDirectFeedback); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0)); |
| MARK(); |
| SLEEP(500); |
| |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(true, true)); |
| TEST_MUSTPASS(dtmf->GetDtmfFeedbackStatus(dtmfFeedback, |
| dtmfDirectFeedback)); |
| TEST_MUSTPASS(!dtmfFeedback); |
| TEST_MUSTPASS(!dtmfDirectFeedback); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(false, false)); |
| |
| AOK(); |
| ANL(); |
| |
| // SendDtmf |
| TEST(SendDtmf); |
| ANL(); |
| |
| // Fail tests |
| // Event |
| // the eventcode is changed to unsigned char, so -1 will be interpreted as |
| // 255, 256->0 |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, -1, false, 160, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 16, false, 160, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| // Length |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 0, true, 99, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 0, true, 60001, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 20, true, -1, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| // Volume |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 0, true, 160, -1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 0, true, 160, 37)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| // Without sending |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(!dtmf->SendTelephoneEvent(0, 0, true)); |
| MARK(); |
| TEST_MUSTPASS(VE_NOT_SENDING != voe_base_->LastError()); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| // Testing Dtmf out-of-band: event, length and volume |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 16, true)); |
| MARK(); |
| SLEEP(500); // Flash, not audible |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 100, 10)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 400, 10)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 160, 0)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 160, 36)); |
| MARK(); |
| SLEEP(500); |
| |
| // Testing Dtmf inband: event, length and volume |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, false)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 15, false)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, false, 100, 10)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, false, 400, 10)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, false, 160, 0)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, false, 160, 36)); |
| MARK(); |
| SLEEP(500); |
| |
| // Testing other events out-of-band: event and length |
| // These are not audible |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 17, true, 100, 10)); |
| MARK(); |
| SLEEP(200); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 32, true, 100, 10)); |
| MARK(); |
| SLEEP(200); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 78, true, 100, 10)); |
| MARK(); |
| SLEEP(200); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 255, true, 100, 10)); |
| MARK(); |
| SLEEP(200); |
| // the minimum length is 100 for the telephoneevent |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 32, true, 100, 10)); |
| MARK(); |
| SLEEP(200); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 32, true, 1000, 10)); |
| MARK(); |
| SLEEP(1200); |
| |
| AOK(); |
| ANL(); |
| |
| // PlayDtmfTone |
| TEST(PlayDtmfTone); |
| ANL(); |
| TEST_MUSTPASS(!dtmf->PlayDtmfTone(-1, 200, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->PlayDtmfTone(16, 200, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->PlayDtmfTone(0, 9, 10)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->PlayDtmfTone(0, 200, -1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!dtmf->PlayDtmfTone(0, 200, 37)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| |
| TEST_MUSTPASS(dtmf->PlayDtmfTone(0)); |
| MARK(); |
| SLEEP(500); |
| // the minimum length fo the DtmfTone is 100 |
| TEST_MUSTPASS(dtmf->PlayDtmfTone(0, 100, 10)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->PlayDtmfTone(0, 2000, 10)); |
| MARK(); |
| SLEEP(2300); |
| TEST_MUSTPASS(dtmf->PlayDtmfTone(0, 200, 0)); |
| MARK(); |
| SLEEP(500); |
| TEST_MUSTPASS(dtmf->PlayDtmfTone(0, 200, 36)); |
| MARK(); |
| SLEEP(500); |
| |
| AOK(); |
| ANL(); |
| |
| // SetTelephoneEventDetection |
| TEST(SetTelephoneEventDetection); |
| ANL(); |
| AOK(); |
| ANL(); |
| |
| // Testing sending Dtmf under VAD/CN |
| TEST(SendDtmf - with VAD enabled); |
| ANL(); |
| // Mute mic |
| TEST_MUSTPASS(volume->SetInputMute(0, true)); |
| MARK(); |
| // Enable VAD |
| TEST_MUSTPASS(codec->SetVADStatus(0, true)); |
| MARK(); |
| // Send Dtmf |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 9, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 9, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| // Switch codec |
| CodecInst ci; |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| ci.channels = 1; |
| ci.pacsize = 480; |
| ci.plfreq = 16000; |
| strcpy(ci.plname, "ISAC"); |
| ci.pltype = 103; |
| ci.rate = -1; |
| #else |
| ci.pltype = 119; |
| strcpy(ci.plname, "isaclc"); |
| ci.plfreq = 16000; |
| ci.pacsize = 320; |
| ci.channels = 1; |
| ci.rate = 40000; |
| #endif |
| TEST_MUSTPASS(codec->SetSendCodec(0, ci)); |
| MARK(); |
| // Send Dtmf |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 9, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 0, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, 9, true, 400)); |
| MARK(); |
| SLEEP(1000); |
| SLEEP(4000); |
| // Disable VAD |
| TEST_MUSTPASS(codec->SetVADStatus(0, false)); |
| MARK(); |
| // Unmute |
| TEST_MUSTPASS(volume->SetInputMute(0, false)); |
| MARK(); |
| |
| AOK(); |
| ANL(); |
| |
| // SetSendTelephoneEventPayloadType |
| TEST(SetSendTelephoneEventPayloadType); |
| ANL(); |
| TEST_MUSTPASS(!dtmf->SetSendTelephoneEventPayloadType(0, 128)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| |
| TEST_MUSTPASS(dtmf->SetSendTelephoneEventPayloadType(0, 96)); |
| MARK(); |
| TEST_MUSTPASS(dtmf->SetSendTelephoneEventPayloadType(0, 127)); |
| MARK(); |
| TEST_MUSTPASS(dtmf->SetSendTelephoneEventPayloadType(0, 106)); |
| MARK(); // restore default |
| |
| AOK(); |
| ANL(); |
| |
| #ifdef WEBRTC_DTMF_DETECTION |
| TEST(RegisterTelephoneEventDetection - several channels); ANL(); |
| |
| ci.channels = 1; |
| ci.pacsize = 160; |
| ci.plfreq = 8000; |
| ci.pltype = 0; |
| ci.rate = 64000; |
| strcpy(ci.plname, "PCMU"); |
| TEST_MUSTPASS(codec->SetSendCodec(0, ci)); |
| |
| int ch2 = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(ch2, 8002, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(ch2, 8002)); |
| TEST_MUSTPASS(voe_base_->StartReceive(ch2)); |
| TEST_MUSTPASS(codec->SetSendCodec(ch2, ci)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(ch2)); |
| TEST_MUSTPASS(voe_base_->StartSend(ch2)); |
| MARK(); |
| |
| DtmfCallback *d = new DtmfCallback(); |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(false)); |
| |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| // In-band |
| TEST_MUSTPASS(dtmf->RegisterTelephoneEventDetection(0, kInBand, *d)); |
| TEST_MUSTPASS(dtmf->RegisterTelephoneEventDetection(ch2, kInBand, *d)); |
| TEST_LOG("\nSending in-band telephone events:"); |
| for(int i = 0; i < 16; i++) |
| { |
| TEST_LOG("\n %d ", i); fflush(NULL); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, i, false, 160, 10)); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(ch2, i, false, 160, 10)); |
| SLEEP(500); |
| } |
| TEST_LOG("\nDetected %d events \n", d->counter); |
| TEST_MUSTPASS(d->counter != 32); |
| TEST_MUSTPASS(dtmf->DeRegisterTelephoneEventDetection(0)); |
| TEST_MUSTPASS(dtmf->DeRegisterTelephoneEventDetection(ch2)); |
| |
| // Out-of-band |
| d->counter = 0; |
| TEST_MUSTPASS(dtmf->RegisterTelephoneEventDetection(0, kOutOfBand, *d)); |
| TEST_MUSTPASS(dtmf->RegisterTelephoneEventDetection(ch2, kOutOfBand, *d)); |
| TEST_LOG("\nSending out-band telephone events:"); |
| for(int i = 0; i < 16; i++) |
| { |
| TEST_LOG("\n %d ", i); fflush(NULL); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(0, i, true, 160, 10)); |
| TEST_MUSTPASS(dtmf->SendTelephoneEvent(ch2, i, true, 160, 10)); |
| SLEEP(500); |
| } |
| TEST_LOG("\nDetected %d events \n", d->counter); |
| TEST_MUSTPASS(d->counter != 32); |
| TEST_MUSTPASS(dtmf->DeRegisterTelephoneEventDetection(0)); |
| TEST_MUSTPASS(dtmf->DeRegisterTelephoneEventDetection(ch2)); |
| delete d; |
| |
| AOK(); ANL(); |
| #endif |
| |
| TEST_MUSTPASS(dtmf->SetDtmfFeedbackStatus(true, false)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestEncryption |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestEncryption() { |
| PrepareTest("Encryption"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| VoEEncryption* encrypt = _mgr.EncryptionPtr(); |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile( |
| GetFilename("VoEEncryption_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| unsigned char key1[30] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, |
| 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; |
| |
| #ifdef WEBRTC_SRTP |
| unsigned char key2[30]; // Different than key1 in first position |
| memcpy(key2, key1, 30); |
| key2[0] = 99; |
| unsigned char key3[30]; // Different than key1 in last position |
| memcpy(key3, key1, 30); |
| key3[29] = 99; |
| unsigned char key4[29]; // Same as key1 but shorter |
| memcpy(key4, key1, 29); |
| |
| TEST(SRTP - Fail tests); ANL(); |
| |
| // Send |
| // Incorrect parameters when not all protection is enabled |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kNoProtection, key1)); |
| TEST_MUSTPASS(VE_SRTP_ERROR != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kEncryption key1)); |
| TEST_MUSTPASS(VE_SRTP_ERROR != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kAuthentication, key1)); |
| TEST_MUSTPASS(VE_SRTP_ERROR != voe_base_->LastError()); |
| MARK(); |
| // Incorrect cipher key length |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 15, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 257, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherNull, 15, kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherNull, 257, kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // Incorrect auth key length |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 21, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 257, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // Incorrect auth tag length |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 21, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 20, 13, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| |
| // key NULL pointer |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, NULL)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| |
| // Same for receive |
| // Incorrect parameters when not all protection is enabled |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kNoProtection, key1)); |
| TEST_MUSTPASS(VE_SRTP_ERROR != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kEncryption key1)); |
| TEST_MUSTPASS(VE_SRTP_ERROR != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kAuthentication, key1)); |
| TEST_MUSTPASS(VE_SRTP_ERROR != voe_base_->LastError()); |
| MARK(); |
| // Incorrect cipher key length |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 15, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 257, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherNull, 15, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherNull, 257, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // Incorrect auth key length |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, |
| 30, kAuthHmacSha1, 21, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // it crashed the application |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 257, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // Incorrect auth tag length |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 21, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // it crashed the application |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 20, 13, |
| kEncryptionAndAuthentication, |
| key1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| // key NULL pointer |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| NULL)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| ANL(); |
| |
| TEST(SRTP - Should hear audio at all time); ANL(); |
| |
| // Authentication only |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherNull, 0, kAuthHmacSha1, 20, |
| 4, kAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherNull, 0, kAuthHmacSha1, |
| 20, 4, kAuthentication, key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| ANL(); |
| |
| // No protection |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherNull, 0, kAuthNull, 0, 0, |
| kNoProtection, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherNull, 0, kAuthNull, 0, 0, |
| kNoProtection, key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| |
| // Encryption only |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, kEncryption key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, |
| kEncryption key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| |
| // Authentication only |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherNull, 0, kAuthHmacSha1, 20, |
| 4, kAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherNull, 0, kAuthHmacSha1, |
| 20, 4, kAuthentication, key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| ANL(); |
| |
| // Switching between keys |
| TEST(SRTP - Different keys - should hear audio at all time); ANL(); |
| |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key2)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key2)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key2)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key2)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| ANL(); |
| |
| // Testing different keys that should be silent |
| TEST(SRTP - Should be silent or garbage); ANL(); |
| |
| // key1 and key2 |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key2)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key2)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, kEncryption key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, |
| kEncryption key2)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherNull, 0, kAuthHmacSha1, |
| 20, 4, kAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherNull, 0, kAuthHmacSha1, |
| 20, 4, kAuthentication, key2)); |
| MARK(); SLEEP(2000); |
| |
| // key1 and key3 |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key3)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key3)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, kEncryption key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, |
| kEncryption key3)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherNull, 0, kAuthHmacSha1, 20, |
| 4, kAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherNull, 0, kAuthHmacSha1, |
| 20, 4, kAuthentication, key3)); |
| MARK(); SLEEP(2000); |
| |
| // key1 and key4 |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key4)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, key4)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, 20, 4, |
| kEncryptionAndAuthentication, |
| key1)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, kEncryption key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthNull, 0, 0, |
| kEncryption key4)); |
| MARK(); SLEEP(2000); |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherNull, 0, kAuthHmacSha1, 20, |
| 4, kAuthentication, key1)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherNull, 0, kAuthHmacSha1, |
| 20, 4, kAuthentication, key4)); |
| MARK(); SLEEP(2000); |
| ANL(); |
| |
| // Back to normal |
| TEST(SRTP - Back to normal - should hear audio); ANL(); |
| |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| MARK(); SLEEP(2000); |
| ANL(); |
| |
| // SRTCP tests |
| TEST(SRTCP - Ignore voice or not); ANL(); |
| VoERTP_RTCP* rtp_rtcp = _mgr.RTP_RTCPPtr(); |
| char tmpStr[32]; |
| |
| // First test that RTCP packet is received and OK without encryption |
| |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik1")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik1", tmpStr)); |
| |
| // Enable SRTP and SRTCP send and receive |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1, true)); |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1, true)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik2")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik2", tmpStr)); |
| |
| // Disable SRTP and SRTCP send |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik3")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik2", tmpStr)); // Should not have changed |
| |
| // Enable SRTP send, but disable SRTCP send |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik4")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik2", tmpStr)); // Should not have changed |
| |
| // Enable SRTP and SRTCP send, disable SRTP and SRTCP receive |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->EnableSRTPSend(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1, true)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik5")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik2", tmpStr)); // Should not have changed |
| |
| // Enable SRTP receive, but disable SRTCP receive |
| TEST_MUSTPASS(encrypt->EnableSRTPReceive(0, kCipherAes128CounterMode, 30, |
| kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik6")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik2", tmpStr)); // Should not have changed |
| |
| // Disable all |
| TEST_MUSTPASS(encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCP_CNAME(0, "Henrik7")); |
| MARK(); SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCP_CNAME(0, tmpStr)); |
| TEST_MUSTPASS(_stricmp("Henrik7", tmpStr)); |
| ANL(); |
| |
| #else |
| TEST(SRTP disabled - Fail tests); |
| ANL(); |
| |
| TEST_MUSTPASS(!encrypt->EnableSRTPSend(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| TEST_MUSTPASS(!encrypt->EnableSRTPReceive(0, kCipherNull, 30, kAuthHmacSha1, |
| 20, 4, kEncryptionAndAuthentication, key1)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| TEST_MUSTPASS(!encrypt->DisableSRTPSend(0)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| TEST_MUSTPASS(!encrypt->DisableSRTPReceive(0)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| ANL(); |
| #endif |
| AOK(); |
| |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestExternalMedia |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestExternalMedia() { |
| PrepareTest("VoEExternalMedia"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEExternalMedia* xmedia = _mgr.ExternalMediaPtr(); |
| |
| // check if this interface is supported |
| if (!xmedia) { |
| TEST_LOG("VoEExternalMedia is not supported!"); |
| return -1; |
| } |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile( |
| GetFilename("VoEExternalMedia_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter( |
| kTraceStateInfo | kTraceStateInfo | kTraceWarning | |
| kTraceError | kTraceCritical | kTraceApiCall | |
| kTraceMemory | kTraceInfo)); |
| #endif |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| int getLen = 0; |
| WebRtc_Word16 vector[32000]; |
| memset(vector, 0, 32000 * sizeof(short)); |
| |
| #ifdef WEBRTC_VOE_EXTERNAL_REC_AND_PLAYOUT |
| |
| // ExternalPlayoutGetData |
| TEST(ExternalPlayoutGetData); |
| ANL(); |
| |
| TEST_MUSTPASS(!xmedia->SetExternalPlayoutStatus(true)); |
| TEST_MUSTPASS(VE_ALREADY_SENDING != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalPlayoutGetData(vector, 16000, 100, getLen)); |
| TEST_MUSTPASS(VE_INVALID_OPERATION != voe_base_->LastError()); |
| |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(xmedia->SetExternalPlayoutStatus(true)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| TEST_MUSTPASS(xmedia->ExternalPlayoutGetData(vector, 48000, 0, getLen)); |
| TEST_MUSTPASS(480 != getLen); |
| SLEEP(10); |
| TEST_MUSTPASS(xmedia->ExternalPlayoutGetData(vector, 16000, 3000, getLen)); |
| TEST_MUSTPASS(160 != getLen); |
| SLEEP(10); |
| |
| TEST_MUSTPASS(!xmedia->ExternalPlayoutGetData(vector, 8000, 100, getLen)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalPlayoutGetData(vector, 16000, -1, getLen)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(xmedia->SetExternalPlayoutStatus(false)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| // SetExternalRecording |
| TEST(SetExternalRecording); |
| ANL(); |
| |
| TEST_MUSTPASS(!xmedia->SetExternalRecordingStatus(true)); |
| TEST_MUSTPASS(VE_ALREADY_SENDING != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 160, 16000, 20)); |
| TEST_MUSTPASS(VE_INVALID_OPERATION != voe_base_->LastError()); |
| |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(xmedia->SetExternalRecordingStatus(true)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| TEST_MUSTPASS(xmedia->ExternalRecordingInsertData(vector, 480, 48000, 0)); |
| SLEEP(10); |
| TEST_MUSTPASS(xmedia->ExternalRecordingInsertData(vector, 640, 16000, 0)); |
| SLEEP(40); |
| |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 160, 16000, -1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 80, 8000, 20)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 0, 16000, 20)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 80, 16000, 20)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 500, 16000, 20)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(xmedia->SetExternalRecordingStatus(false)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| #else // #ifdef WEBRTC_VOE_EXTERNAL_REC_AND_PLAYOUT |
| TEST_MUSTPASS(!xmedia->SetExternalPlayoutStatus(true)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalPlayoutGetData(vector, 16000, 100, getLen)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->SetExternalRecordingStatus(true)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| TEST_MUSTPASS(!xmedia->ExternalRecordingInsertData(vector, 160, 16000, 20)); |
| TEST_MUSTPASS(VE_FUNC_NOT_SUPPORTED != voe_base_->LastError()); |
| |
| #endif // #ifdef WEBRTC_VOE_EXTERNAL_REC_AND_PLAYOUT |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| ANL(); |
| AOK(); |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestFile |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestFile() { |
| PrepareTest("File"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| VoECodec* codec = _mgr.CodecPtr(); |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile( |
| GetFilename("VoEFile_trace.txt"))); MARK(); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| const int dT(100); |
| |
| TEST(StartPlayingFileLocally); |
| ANL(); |
| TEST(StopPlayingFileLocally); |
| ANL(); |
| |
| voe_base_->StopPlayout(0); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm")));MARK(); |
| voe_base_->StartPlayout(0); |
| MARK(); // file should be mixed in and played out |
| SLEEP(dT); |
| TEST_MUSTPASS(!file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm"))); |
| MARK(); // should fail (must stop first) |
| TEST_MUSTPASS(voe_base_->LastError() != VE_ALREADY_PLAYING); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm"))); |
| MARK(); // should work again (restarts file) |
| SLEEP(dT); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm"), false, kFileFormatPcm16kHzFile)); |
| MARK(); |
| SLEEP(dT); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long8.pcm"), false, kFileFormatPcm8kHzFile)); |
| MARK(); |
| SLEEP(dT); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.wav"), false, kFileFormatPcm8kHzFile)); |
| MARK(); |
| SLEEP(dT); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long8mulaw.wav"), false, |
| kFileFormatPcm8kHzFile)); |
| MARK(); |
| SLEEP(dT); |
| |
| // add compressed tests here... |
| |
| // TEST_MUSTPASS(file->StopPlayingFileLocally(0)); MARK(); |
| // TEST_MUSTPASS(file->StartPlayingFileLocally( |
| // 0, GetResource("audio_short16.pcm"), true, |
| // kFileFormatPcm16kHzFile)); MARK(); // loop |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_short16.pcm"), false, |
| kFileFormatPcm16kHzFile, 1.0, 0, 2000)); |
| MARK(); // play segment |
| SLEEP(2500); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(!file->StartPlayingFileLocally( |
| 0, GetResource("audio_short16.pcm"), false, |
| kFileFormatPcm16kHzFile, 1.0, 2000, 1000)); |
| MARK(); // invalid segment |
| TEST_MUSTPASS(voe_base_->LastError() != VE_BAD_FILE); |
| TEST_MUSTPASS(!file->StartPlayingFileLocally( |
| 0, GetResource("audio_short16.pcm"), false, |
| kFileFormatPcm16kHzFile, 1.0, 21000, 30000)); |
| MARK(); // start > file size |
| TEST_MUSTPASS(voe_base_->LastError() != VE_BAD_FILE); |
| TEST_MUSTPASS(!file->StartPlayingFileLocally( |
| 0, GetResource("audio_short16.pcm"), false, |
| kFileFormatPcm16kHzFile, 1.0, 100, 100)); |
| MARK(); // invalid segment |
| TEST_MUSTPASS(voe_base_->LastError() != VE_BAD_FILE); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm"))); |
| MARK(); // should work again (restarts file) |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| TEST_MUSTPASS(!file->StartPlayingFileLocally(0, (InStream*)NULL)); |
| MARK(); // just do it |
| TEST_MUSTPASS(voe_base_->LastError() != VE_BAD_FILE); |
| |
| AOK(); |
| ANL(); |
| |
| TEST(IsPlayingFileLocally); |
| ANL(); |
| |
| TEST_MUSTPASS(0 != file->IsPlayingFileLocally(0)); |
| MARK(); // inactive |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm"))); |
| MARK(); |
| TEST_MUSTPASS(1 != file->IsPlayingFileLocally(0)); |
| MARK(); // active |
| AOK(); |
| ANL(); |
| |
| TEST(ScaleLocalFilePlayout); |
| ANL(); |
| TEST_MUSTPASS(file->ScaleLocalFilePlayout(0, 1.0)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->ScaleLocalFilePlayout(0, 0.0)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->ScaleLocalFilePlayout(0, 0.5)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->ScaleLocalFilePlayout(0, 0.25)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| MARK(); |
| AOK(); |
| ANL(); |
| |
| // Replace microphone with file and play out on remote side |
| // All channels, per channel |
| // Different mixing frequencies |
| TEST(StartPlayingFileAsMicrophone); |
| ANL(); |
| TEST(IsPlayingFileAsMicrophone); |
| ANL(); |
| TEST(ScaleFileAsMicrophonePlayout); |
| ANL(); |
| CodecInst tempCodec; |
| for (int ch = -1; ch < 1; ++ch) // Channel -1 and 0 |
| { |
| TEST_LOG("Testing channel = %d \n", ch); |
| for (int fs = 1; fs < 4; ++fs) // nb, wb and swb codecs |
| { |
| switch (fs) { |
| case 1: // nb |
| TEST_LOG("Testing with nb codec \n"); |
| tempCodec.channels = 1; |
| tempCodec.pacsize = 160; |
| tempCodec.plfreq = 8000; |
| strcpy(tempCodec.plname, "PCMU"); |
| tempCodec.pltype = 0; |
| tempCodec.rate = 64000; |
| break; |
| case 2: // wb |
| #ifdef WEBRTC_CODEC_ISAC |
| TEST_LOG("Testing with wb codec \n"); |
| tempCodec.channels = 1; |
| tempCodec.pacsize = 480; |
| tempCodec.plfreq = 16000; |
| strcpy(tempCodec.plname, "ISAC"); |
| tempCodec.pltype = 103; |
| tempCodec.rate = 32000; |
| break; |
| #else |
| TEST_LOG("NOT testing with wb codec - " |
| "WEBRTC_CODEC_ISAC not defined \n"); |
| continue; |
| #endif |
| case 3: // swb |
| #ifdef WEBRTC_CODEC_PCM16 |
| TEST_LOG("Testing with swb codec \n"); |
| tempCodec.channels = 1; |
| tempCodec.pacsize = 640; |
| tempCodec.plfreq = 32000; |
| strcpy(tempCodec.plname, "L16"); |
| tempCodec.pltype = 125; |
| tempCodec.rate = 512000; |
| break; |
| #else |
| TEST_LOG("NOT testing with swb codec -" |
| " WEBRTC_CODEC_PCM16 not defined \n"); |
| continue; |
| #endif |
| } |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, tempCodec)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(codec->SetSendCodec(0, tempCodec)); |
| |
| TEST_LOG("File 1 in 16 kHz no mix, 2 in 16 kHz mix," |
| " 3 in 8 kHz no mix, 4 in 8 kHz mix \n"); |
| |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| ch, GetResource("audio_long16.pcm"))); |
| MARK(); // don't mix |
| SLEEP(2000); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(ch)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| ch, GetResource("audio_long16.wav"), false, true, |
| kFileFormatWavFile)); |
| MARK(); // mix |
| SLEEP(2000); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(ch)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| ch, GetResource("audio_long8.pcm"), false, false, |
| kFileFormatPcm8kHzFile)); |
| MARK(); // don't mix |
| SLEEP(2000); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(ch)); |
| MARK(); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| ch, GetResource("audio_long8.pcm"), false, true, |
| kFileFormatPcm8kHzFile)); |
| MARK(); // mix |
| SLEEP(2000); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(ch)); |
| MARK(); |
| TEST_MUSTPASS(!file->StartPlayingFileAsMicrophone( |
| ch, (InStream*)NULL)); |
| MARK(); // force error |
| AOK(); |
| ANL(); |
| |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| ch, GetResource("audio_long16.pcm"))); |
| TEST_MUSTPASS(1 != file->IsPlayingFileAsMicrophone(ch)); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(ch)); |
| TEST_MUSTPASS(0 != file->IsPlayingFileAsMicrophone(ch)); |
| AOK(); |
| ANL(); |
| |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| ch, GetResource("audio_long16.pcm"))); |
| TEST_MUSTPASS(file->ScaleFileAsMicrophonePlayout(ch, 1.0)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->ScaleFileAsMicrophonePlayout(ch, 0.5)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->ScaleFileAsMicrophonePlayout(ch, 0.25)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->ScaleFileAsMicrophonePlayout(ch, 0.0)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(ch)); |
| MARK(); |
| AOK(); |
| ANL(); |
| } |
| } |
| |
| // Record speaker signal to file |
| |
| CodecInst fcomp = { 0, "L16", 8000, 80, 1, 128000 }; |
| |
| TEST(StartRecordingPlayout); |
| ANL(); |
| TEST(StopRecordingPlayout); |
| ANL(); |
| |
| TEST_MUSTPASS(file->StartRecordingPlayout(0, |
| GetFilename("rec_play16.pcm"))); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(0)); |
| MARK(); |
| |
| fcomp.plfreq = 8000; |
| strcpy(fcomp.plname, "L16"); |
| TEST_MUSTPASS(file->StartRecordingPlayout(0, GetFilename("rec_play8.wav"), |
| &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(0)); |
| MARK(); |
| |
| fcomp.plfreq = 16000; |
| strcpy(fcomp.plname, "L16"); |
| TEST_MUSTPASS(file->StartRecordingPlayout(0, GetFilename("rec_play16.wav"), |
| &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(0)); |
| MARK(); |
| |
| fcomp.pltype = 0; |
| fcomp.plfreq = 8000; |
| strcpy(fcomp.plname, "PCMU"); |
| fcomp.rate = 64000; |
| fcomp.pacsize = 160; |
| fcomp.channels = 1; |
| |
| TEST_MUSTPASS(file->StartRecordingPlayout(0, |
| GetFilename("rec_play_pcmu.wav"), |
| &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(0)); |
| MARK(); |
| |
| fcomp.pltype = 8; |
| fcomp.plfreq = 8000; |
| strcpy(fcomp.plname, "PCMA"); |
| TEST_MUSTPASS(file->StartRecordingPlayout(0, |
| GetFilename("rec_play_pcma.wav"), |
| &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(0)); |
| MARK(); |
| |
| fcomp.pltype = 97; |
| fcomp.pacsize = 240; |
| fcomp.rate = 13300; |
| fcomp.plfreq = 8000; |
| strcpy(fcomp.plname, "ILBC"); |
| TEST_MUSTPASS(file->StartRecordingPlayout(0, |
| GetFilename("rec_play.ilbc"), |
| &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(0)); |
| MARK(); |
| |
| TEST_MUSTPASS(file->StartRecordingPlayout( |
| -1, GetFilename("rec_play16_mixed.pcm"))); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(-1)); |
| MARK(); |
| |
| // TEST_MUSTPASS(file->StopPlayingFileLocally(0)); // Why should this work? |
| TEST_LOG("\nplaying out...\n"); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetFilename("rec_play.ilbc"), false, kFileFormatCompressedFile)); |
| MARK(); |
| SLEEP(2000); |
| |
| AOK(); |
| ANL(); |
| |
| // Record microphone signal to file |
| TEST(StartRecordingMicrophone); |
| ANL(); |
| TEST(StopRecordingMicrophone); |
| ANL(); |
| |
| TEST_MUSTPASS(file->StartRecordingMicrophone(GetFilename("rec_mic16.pcm"))); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| |
| voe_base_->StopSend(0); |
| TEST_MUSTPASS(file->StartRecordingMicrophone(GetFilename("rec_mic16.pcm"))); |
| MARK(); // record without sending as well |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| voe_base_->StartSend(0); // restore sending |
| |
| fcomp.plfreq = 8000; |
| strcpy(fcomp.plname, "L16"); |
| TEST_MUSTPASS(file->StartRecordingMicrophone( |
| GetFilename("rec_play8.wav"), &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| |
| fcomp.plfreq = 16000; |
| strcpy(fcomp.plname, "L16"); |
| TEST_MUSTPASS(file->StartRecordingMicrophone( |
| GetFilename("rec_play16.wav"), &fcomp)); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| |
| // FT#1810, the following test is to make sure StartRecordingCall will |
| // record both mic and file |
| TEST_LOG("StartRecordingCall, record both mic and file in specific" |
| " channels \n"); |
| TEST_LOG("Create maxnumofchannels \n"); |
| for (int i = 1; i < voe_base_->MaxNumOfChannels(); i++) { |
| int ch = voe_base_->CreateChannel(); |
| TEST_MUSTPASS(ch == -1); |
| TEST_MUSTPASS(voe_base_->StopPlayout(ch)); |
| } |
| |
| TEST_MUSTPASS(voe_base_->SetSendDestination(1, 12356, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(1, 12356)); |
| TEST_MUSTPASS(voe_base_->StartReceive(1)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(1)); |
| TEST_MUSTPASS(voe_base_->StartSend(1)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(1)); |
| |
| TEST_LOG("ALways playing audio_long16.pcm for " |
| "channel 0 in background \n"); |
| fcomp.plfreq = 16000; |
| strcpy(fcomp.plname, "L16"); |
| TEST_LOG("Recording microphone to L16, please speak \n"); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| 0, GetResource("audio_long16.pcm"), true , true)); |
| TEST_MUSTPASS(file->StartRecordingMicrophone( |
| GetFilename("rec_play_ch.wav"), &fcomp)); |
| MARK(); |
| SLEEP(3000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| TEST_LOG("Playing recording file, you should only hear what you said \n"); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetFilename("rec_play_ch.wav"), false, kFileFormatWavFile)); |
| SLEEP(2500); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| TEST_LOG("Recording microphone 0 to L16, please speak \n"); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| -1, GetResource("audio_long16.pcm"), true , true)); |
| TEST_MUSTPASS(file->StartRecordingMicrophone( |
| GetFilename("rec_play_ch_0.wav"), &fcomp)); |
| MARK(); |
| SLEEP(3000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(-1)); |
| TEST_LOG("Playing recording file, you should hear what you said and" |
| " audio_long16.pcm \n"); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetFilename("rec_play_ch_0.wav"), false, kFileFormatWavFile)); |
| SLEEP(2500); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| TEST_LOG("Recording microphone to ilbc, please speak \n"); |
| strcpy(fcomp.plname, "ilbc"); |
| fcomp.plfreq = 8000; |
| fcomp.pacsize = 160; |
| fcomp.rate = 15200; |
| fcomp.channels = 1; |
| fcomp.pltype = 97; |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone( |
| 0, GetResource("audio_long16.pcm"), true , true)); |
| TEST_MUSTPASS(file->StartRecordingMicrophone( |
| GetFilename("rec_play_ch_0.ilbc"), &fcomp)); |
| MARK(); |
| SLEEP(3000); |
| TEST_MUSTPASS(file->StopRecordingMicrophone()); |
| MARK(); |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| TEST_LOG("Playing recording file, you should only hear what you said \n"); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetFilename("rec_play_ch_0.ilbc"), false, |
| kFileFormatCompressedFile)); |
| SLEEP(2500); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| for (int i = 1; i < voe_base_->MaxNumOfChannels(); i++) { |
| TEST_MUSTPASS(voe_base_->DeleteChannel(i)); |
| } |
| |
| AOK(); |
| ANL(); |
| |
| // Record mixed (speaker + microphone) signal to file |
| |
| |
| #if !defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID) |
| TEST(StartRecordingSpeakerStereo); |
| ANL(); |
| TEST(StopRecordingSpeakerStereo); |
| ANL(); |
| |
| VoEHardware* hardware = _mgr.HardwarePtr(); |
| TEST_MUSTPASS(NULL == hardware); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| #if defined(_WIN32) |
| TEST_MUSTPASS(hardware->SetRecordingDevice(-1)); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(-1)); |
| #else |
| TEST_MUSTPASS(hardware->SetRecordingDevice(0)); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(0)); |
| #endif |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| MARK(); |
| |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| #if defined(_WIN32) |
| TEST_MUSTPASS(hardware->SetRecordingDevice(-1)); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(-1)); |
| #else |
| TEST_MUSTPASS(hardware->SetRecordingDevice(0)); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(0)); |
| #endif |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| AOK(); |
| ANL(); |
| #else |
| TEST_LOG("Skipping stereo record tests -" |
| " MAC_IPHONE or WEBRTC_ANDROID is defined \n"); |
| #endif // #if !defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID) |
| // Conversion between different file formats |
| |
| #if defined(MAC_IPHONE) || defined(WEBRTC_ANDROID) |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| #endif |
| |
| TEST(ConvertPCMToWAV); |
| ANL(); |
| |
| TEST_MUSTPASS(file->ConvertPCMToWAV( |
| GetResource("audio_long16.pcm"), |
| GetFilename("singleUserDemoConv.wav"))); |
| MARK(); |
| TEST_MUSTPASS(!file->ConvertPCMToWAV((InStream*)NULL, |
| (OutStream*)NULL));MARK(); // invalid stream handles |
| AOK(); |
| ANL(); |
| |
| TEST(ConvertWAVToPCM); |
| ANL(); |
| |
| TEST_MUSTPASS(file->ConvertWAVToPCM( |
| GetResource("audio_long16.wav"), |
| GetFilename("singleUserDemoConv.pcm"))); |
| MARK(); |
| TEST_MUSTPASS(!file->ConvertWAVToPCM((InStream*)NULL, (OutStream*)NULL)); |
| MARK(); // invalid stream handles |
| AOK(); |
| ANL(); |
| |
| TEST(ConvertPCMToCompressed); |
| ANL(); |
| |
| fcomp.plfreq = 16000; |
| strcpy(fcomp.plname, "L16"); |
| TEST_MUSTPASS(!file->ConvertPCMToCompressed( |
| GetResource("audio_long16.pcm"), |
| GetFilename("singleUserDemoConv16_dummy.wav"), &fcomp)); |
| MARK(); // should not be supported |
| |
| fcomp.plfreq = 8000; |
| strcpy(fcomp.plname, "ilbc"); |
| fcomp.pacsize = 160; |
| fcomp.rate = 15200; |
| fcomp.pltype = 97; |
| fcomp.channels = 1; |
| TEST_MUSTPASS(file->ConvertPCMToCompressed( |
| GetResource("audio_long16.pcm"), |
| GetFilename("singleUserDemoConv.ilbc"), &fcomp));MARK(); |
| AOK();ANL(); |
| |
| TEST(ConvertCompressedToPCM); |
| ANL(); |
| |
| TEST_MUSTPASS(file->ConvertCompressedToPCM( |
| GetFilename("singleUserDemoConv.ilbc"), |
| GetFilename("singleUserDemoConv_ilbc.pcm")));MARK(); |
| TEST_MUSTPASS(!file->ConvertCompressedToPCM( |
| GetResource("audio_long16.pcm"), |
| GetFilename("singleUserDemoConv_dummy.pcm")));MARK(); |
| AOK();ANL(); |
| |
| #if defined(MAC_IPHONE) || defined(WEBRTC_ANDROID) |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| #endif |
| |
| // Misc file functions |
| TEST(GetFileDuration); |
| ANL(); |
| |
| int dur; |
| |
| TEST_MUSTPASS(file->GetFileDuration( |
| GetResource("audio_long16.pcm"), dur)); |
| TEST_MUSTPASS(file->GetFileDuration( |
| GetResource("audio_long8.pcm"), dur, kFileFormatPcm8kHzFile)); |
| TEST_MUSTPASS(file->GetFileDuration( |
| GetResource("audio_long16.pcm"), dur, kFileFormatPcm16kHzFile)); |
| TEST_MUSTPASS(file->GetFileDuration( |
| GetResource("audio_long16.wav"), dur, kFileFormatPcm8kHzFile)); |
| TEST_MUSTPASS(file->GetFileDuration( |
| GetFilename("singleUserDemoConv.ilbc"), dur, |
| kFileFormatCompressedFile)); |
| |
| AOK(); |
| ANL(); |
| |
| TEST(GetPlaybackPosition); |
| ANL(); |
| |
| int pos; |
| |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource("audio_long16.pcm"))); |
| SLEEP(1000); |
| TEST_MUSTPASS(file->GetPlaybackPosition(0, pos)); |
| MARK(); // position should be ~1000 |
| SLEEP(1000); |
| TEST_MUSTPASS(file->GetPlaybackPosition(0, pos)); |
| MARK(); // position should be ~2000 |
| // SLEEP(70*1000); |
| // file is no longer playing |
| // TEST_MUSTPASS(file->GetPlaybackPosition(0, pos)); MARK(); |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| AOK(); |
| ANL(); |
| |
| // These tests are related to defect 5136 |
| // They play .wav files with different sample freq for 5s |
| char localFiles[7][50] = { "audio_tiny8.wav", "audio_tiny11.wav", |
| "audio_tiny16.wav", "audio_tiny22.wav", "audio_tiny32.wav", |
| "audio_tiny44.wav", "audio_tiny48.wav" }; |
| char freq[7][5] = { "8", "11", "16", "22", "32", "44.1", "48" }; |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| for (int i = 0; i < 7; i++) { |
| TEST_LOG("Playing file %s, in %s KHz \n", localFiles[i], freq[i]); |
| TEST_MUSTPASS(file->StartPlayingFileLocally( |
| 0, GetResource(localFiles[i]),false, kFileFormatWavFile, 1)); |
| SLEEP(4500); // The file should not end |
| TEST_MUSTPASS(file->StopPlayingFileLocally(0)); |
| } |
| |
| // TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); // Should not work |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| AOK(); |
| ANL(); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestMixing |
| // ---------------------------------------------------------------------------- |
| |
| // Creates and mixes |num_channels| with a constant amplitude of |input_value|. |
| // The mixed output is verified to always fall between |max_output_value| and |
| // |min_output_value|, after a startup phase. |
| int VoEExtendedTest::RunMixingTest(int num_channels, |
| int16_t input_value, |
| int16_t max_output_value, |
| int16_t min_output_value) { |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| VoECodec* codec = _mgr.CodecPtr(); |
| VoEAudioProcessing* apm = _mgr.APMPtr(); |
| |
| // Use L16 at 16kHz to minimize distortion (file recording is 16kHz |
| // and resampling will cause large distortions). |
| CodecInst codec_inst; |
| strcpy(codec_inst.plname, "L16"); |
| codec_inst.channels = 1; |
| codec_inst.rate = 256000; |
| codec_inst.plfreq = 16000; |
| codec_inst.pltype = 105; |
| codec_inst.pacsize = 160; |
| |
| apm->SetNsStatus(false); |
| apm->SetAgcStatus(false); |
| apm->SetEcStatus(false); |
| |
| const char file_to_generate_name[] = "dc_file.pcm"; |
| const char* input_filename = file_to_generate_name; |
| FILE* file_to_generate = fopen(file_to_generate_name, "wb"); |
| ASSERT_TRUE(file_to_generate != NULL); |
| for (int i = 0; i < 160 * 100 * 5; i++) { |
| fwrite(&input_value, sizeof(input_value), 1, file_to_generate); |
| } |
| fclose(file_to_generate); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| std::vector<int> channels(num_channels); |
| for (int channel_index = 0; channel_index < num_channels; ++channel_index) { |
| const int channel = voe_base_->CreateChannel(); |
| channels[channel_index] = channel; |
| ASSERT_TRUE(channel != -1); |
| TEST_MUSTPASS(codec->SetRecPayloadType(channel, codec_inst)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(channel, |
| 1234 + 2 * channel_index)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(channel, |
| 1234 + 2 * channel_index, |
| "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(channel)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(channel)); |
| TEST_MUSTPASS(codec->SetSendCodec(channel, codec_inst)); |
| TEST_MUSTPASS(voe_base_->StartSend(channel)); |
| } |
| for (int channel_index = 0; channel_index < num_channels; ++channel_index) { |
| const int channel = channels[channel_index]; |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(channel, |
| input_filename, |
| true)); |
| } |
| const char mix_result[] = "mix_result.pcm"; |
| TEST_MUSTPASS(file->StartRecordingPlayout(-1/*record meeting*/, |
| mix_result)); |
| TEST_LOG("Playing %d channels\n", num_channels); |
| SLEEP(5000); |
| TEST_MUSTPASS(file->StopRecordingPlayout(-1)); |
| TEST_LOG("Stopping\n"); |
| |
| for (int channel_index = 0; channel_index < num_channels; ++channel_index) { |
| const int channel = channels[channel_index]; |
| channels[channel_index] = channel; |
| TEST_MUSTPASS(voe_base_->StopSend(channel)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(channel)); |
| TEST_MUSTPASS(voe_base_->StopReceive(channel)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(channel)); |
| } |
| |
| FILE* verification_file = fopen(mix_result, "rb"); |
| ASSERT_TRUE(verification_file != NULL); |
| int16_t mix_value = 0; |
| // Skip the first 100 ms to avoid initialization and ramping-in effects. |
| ASSERT_TRUE(fseek(verification_file, sizeof(int16_t) * 1600, SEEK_SET) == 0); |
| while (fread(&mix_value, sizeof(mix_value), 1, verification_file)) { |
| ASSERT_TRUE(mix_value <= max_output_value) |
| ASSERT_TRUE(mix_value >= min_output_value); |
| } |
| fclose(verification_file); |
| |
| return 0; |
| } |
| |
| // TODO(andrew): move or copy these to the mixer module test when possible. |
| int VoEExtendedTest::TestMixing() { |
| // These tests assume a maxmium of three mixed participants. We allow a |
| // +/- 10% range around the expected output level to accout for distortion |
| // from coding and processing in the loopback chain. |
| |
| // Create four channels and make sure that only three are mixed. |
| TEST_LOG("Test max-three-participant mixing.\n"); |
| int16_t input_value = 1000; |
| int16_t expected_output = input_value * 3; |
| if (RunMixingTest(4, input_value, 1.1 * expected_output, |
| 0.9 * expected_output) != 0) { |
| return -1; |
| } |
| |
| // Ensure the mixing saturation protection is working. We can do this because |
| // the mixing limiter is given some headroom, so the expected output is less |
| // than full scale. |
| TEST_LOG("Test mixing saturation protection.\n"); |
| input_value = 20000; |
| expected_output = 29204; // = -1 dBFS, the limiter headroom. |
| // If this isn't satisfied, we're not testing anything. |
| assert(input_value * 3 > 32767); |
| assert(1.1 * expected_output < 32767); |
| if (RunMixingTest(3, input_value, 1.1 * expected_output, |
| 0.9 * expected_output) != 0) { |
| return -1; |
| } |
| |
| // Ensure the mixing saturation protection is not applied when only using a |
| // single channel. |
| TEST_LOG("Test saturation protection has no effect on one channel.\n"); |
| input_value = 32767; |
| expected_output = 32767; |
| // If this isn't satisfied, we're not testing anything. |
| assert(0.95 * expected_output > 29204); // = -1 dBFS, the limiter headroom. |
| if (RunMixingTest(1, input_value, expected_output, |
| 0.95 * expected_output) != 0) { |
| return -1; |
| } |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestHardware |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestHardware() { |
| PrepareTest("Hardware"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEHardware* hardware = _mgr.HardwarePtr(); |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename( |
| "VoEHardware_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| // Set/GetAudioDeviceLayer |
| TEST(Set/GetAudioDeviceLayer); |
| ANL(); |
| AudioLayers wantedLayer = kAudioPlatformDefault; |
| AudioLayers givenLayer; |
| |
| #if defined(_WIN32) |
| wantedLayer = kAudioWindowsCore; |
| hardware->SetAudioDeviceLayer(wantedLayer); |
| TEST_LOG("If you run on XP or below, CoreAudio " |
| "should not be able to set.\n"); |
| TEST_LOG("If you run on Vista or above, CoreAudio " |
| "should be able to set.\n"); |
| TEST_LOG("Verify that this is the case.\n"); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| TEST_MUSTPASS(hardware->GetAudioDeviceLayer(givenLayer)); |
| if(givenLayer == kAudioWindowsCore) |
| { |
| TEST_LOG("CoreAudio was set\n"); |
| } |
| else |
| { |
| TEST_LOG("CoreAudio was *not* set\n"); |
| } |
| |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| wantedLayer = kAudioWindowsWave; |
| TEST_MUSTPASS(hardware->SetAudioDeviceLayer(wantedLayer)); |
| TEST_LOG("Wave audio should always be able to set.\n"); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| TEST_MUSTPASS(hardware->GetAudioDeviceLayer(givenLayer)); |
| if(givenLayer == kAudioWindowsWave) |
| { |
| TEST_LOG("Wave audio was set\n"); |
| } |
| else |
| { |
| TEST_LOG("Wave audio was not set\n"); |
| } |
| |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| // end _WIN32 |
| #elif defined(WEBRTC_LINUX) && !defined(WEBRTC_ANDROID) |
| wantedLayer = kAudioLinuxPulse; |
| TEST_MUSTPASS(hardware->SetAudioDeviceLayer(wantedLayer)); |
| TEST_LOG("If you run on Linux with no/unsupported PA version, PulseAudio " |
| "7should not be able to set.\n"); |
| TEST_LOG("If you run on Linux with supported PA version running, PulseAudio" |
| " should be able to set.\n"); |
| TEST_LOG("Verify that this is the case.\n"); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| TEST_MUSTPASS(hardware->GetAudioDeviceLayer(givenLayer)); |
| if(givenLayer == kAudioLinuxPulse) |
| { |
| TEST_LOG("\nPulseAudio was set\n"); |
| } |
| else |
| { |
| TEST_LOG("\nPulseAudio was not set\n"); |
| } |
| |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| wantedLayer = kAudioLinuxAlsa; |
| TEST_MUSTPASS(hardware->SetAudioDeviceLayer(wantedLayer)); |
| TEST_LOG("ALSA audio should always be able to set.\n"); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| TEST_MUSTPASS(hardware->GetAudioDeviceLayer(givenLayer)); |
| if(givenLayer == kAudioLinuxAlsa) |
| { |
| TEST_LOG("\nALSA audio was set\n"); |
| } |
| else |
| { |
| TEST_LOG("\nALSA audio was not set\n"); |
| } |
| |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| #endif // defined(WEBRTC_LINUX) && !defined(WEBRTC_ANDROID) |
| // Invalid arguments |
| wantedLayer = (AudioLayers) 17; |
| TEST_MUSTPASS(-1 != hardware->SetAudioDeviceLayer(wantedLayer)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| |
| // Basic usage |
| wantedLayer = kAudioPlatformDefault; |
| TEST_MUSTPASS(hardware->SetAudioDeviceLayer(wantedLayer)); |
| TEST_MUSTPASS(hardware->GetAudioDeviceLayer(givenLayer)); |
| TEST_MUSTPASS(givenLayer != wantedLayer); |
| MARK(); |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| wantedLayer = kAudioPlatformDefault; |
| TEST_MUSTPASS(-1 != hardware->SetAudioDeviceLayer(wantedLayer)); |
| TEST_MUSTPASS(VE_ALREADY_INITED != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(hardware->GetAudioDeviceLayer(givenLayer)); |
| MARK(); |
| switch (givenLayer) { |
| case kAudioPlatformDefault: |
| // already set above |
| break; |
| case kAudioWindowsCore: |
| TEST_LOG("\nRunning kAudioWindowsCore\n"); |
| break; |
| case kAudioWindowsWave: |
| TEST_LOG("\nRunning kAudioWindowsWave\n"); |
| break; |
| case kAudioLinuxAlsa: |
| TEST_LOG("\nRunning kAudioLinuxAlsa\n"); |
| break; |
| case kAudioLinuxPulse: |
| TEST_LOG("\nRunning kAudioLinuxPulse\n"); |
| break; |
| default: |
| TEST_LOG("\nERROR: Running unknown audio layer!!\n"); |
| return -1; |
| } |
| ANL(); |
| |
| #if !defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID) |
| // GetRecording/PlayoutDeviceStatus |
| TEST(Getrecording/PlayoutDeviceStatus); |
| ANL(); |
| bool isRecAvailable = false; |
| bool isPlayAvailable = false; |
| TEST_MUSTPASS(hardware->GetRecordingDeviceStatus(isRecAvailable)); |
| TEST_MUSTPASS(!isRecAvailable); |
| MARK(); |
| TEST_MUSTPASS(hardware->GetPlayoutDeviceStatus(isPlayAvailable)); |
| TEST_MUSTPASS(!isPlayAvailable); |
| MARK(); |
| |
| ANL(); |
| |
| int nRec = 0, nPlay = 0; |
| char devName[128]; |
| char guidName[128]; |
| int idx; |
| |
| TEST_MUSTPASS(hardware->GetNumOfPlayoutDevices(nPlay)); |
| |
| // GetPlayoutDeviceName |
| TEST(GetPlayoutDeviceName); |
| ANL(); |
| TEST_MUSTPASS(-1 != hardware->GetPlayoutDeviceName(nPlay, devName, |
| guidName)); |
| TEST_MUSTPASS(VE_CANNOT_RETRIEVE_DEVICE_NAME != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(-1 != hardware->GetPlayoutDeviceName(-2, devName, guidName)); |
| TEST_MUSTPASS(VE_CANNOT_RETRIEVE_DEVICE_NAME != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(-1 != hardware->GetPlayoutDeviceName(nPlay+1, devName, |
| guidName)); |
| TEST_MUSTPASS(VE_CANNOT_RETRIEVE_DEVICE_NAME != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(-1 != hardware->GetPlayoutDeviceName(0, NULL, guidName)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(hardware->GetPlayoutDeviceName(0, devName, NULL)); |
| |
| // default tests |
| for (idx = 0; idx < nPlay; idx++) { |
| TEST_MUSTPASS(hardware->GetPlayoutDeviceName(idx, devName, guidName)); |
| MARK(); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(idx)); |
| } |
| |
| ANL(); |
| |
| TEST_MUSTPASS(hardware->GetNumOfRecordingDevices(nRec)); |
| |
| // GetRecordingDeviceName |
| TEST(GetRecordingDeviceName); |
| ANL(); |
| TEST_MUSTPASS(-1 != hardware->GetRecordingDeviceName(nRec, devName, |
| guidName)); |
| TEST_MUSTPASS(VE_CANNOT_RETRIEVE_DEVICE_NAME != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(-1 != hardware->GetRecordingDeviceName(-2, devName, guidName)); |
| TEST_MUSTPASS(VE_CANNOT_RETRIEVE_DEVICE_NAME != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(-1 != hardware->GetRecordingDeviceName(nRec+1, devName, |
| guidName)); |
| TEST_MUSTPASS(VE_CANNOT_RETRIEVE_DEVICE_NAME != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(-1 != hardware->GetRecordingDeviceName(0, NULL, guidName)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(hardware->GetRecordingDeviceName(0, devName, NULL)); |
| |
| // default tests |
| for (idx = 0; idx < nRec; idx++) { |
| TEST_MUSTPASS(hardware->GetRecordingDeviceName(idx, devName, guidName)); |
| MARK(); |
| TEST_MUSTPASS(hardware->SetRecordingDevice(idx)); |
| } |
| ANL(); |
| |
| // // SetRecordingDevice |
| TEST(SetRecordingDevice); |
| ANL(); |
| TEST_MUSTPASS(hardware->SetRecordingDevice(0)); |
| MARK(); |
| TEST_MUSTPASS(hardware->SetRecordingDevice(0, kStereoLeft)); |
| MARK(); |
| TEST_MUSTPASS(hardware->SetRecordingDevice(0, kStereoRight)); |
| MARK(); |
| ANL(); |
| |
| // SetPlayoutDevice |
| TEST(SetPlayoutDevice); |
| ANL(); |
| #if defined(_WIN32) |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(-1)); MARK(); |
| #else |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(0)); |
| MARK(); |
| #endif |
| ANL(); |
| #endif // #if !defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID) |
| #if defined(MAC_IPHONE) |
| TEST(ResetSoundDevice); ANL(); |
| |
| for (int p=0; p<=60; p+=20) |
| { |
| TEST_LOG("Resetting sound device several times with pause %d ms\n", p); |
| for (int l=0; l<50; ++l) |
| { |
| TEST_MUSTPASS(hardware->ResetAudioDevice()); MARK(); |
| SLEEP(p); |
| } |
| ANL(); |
| } |
| |
| TEST_LOG("Start streaming - verify the audio after each batch of resets \n"); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0,8000)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(2000); |
| |
| SLEEP(2000); |
| for (int p=0; p<=60; p+=20) |
| { |
| TEST_LOG("Resetting sound device several time with pause %d ms\n", p); |
| for (int l=0; l<20; ++l) |
| { |
| TEST_MUSTPASS(hardware->ResetAudioDevice()); MARK(); |
| SLEEP(p); |
| } |
| ANL(); |
| SLEEP(2000); |
| } |
| |
| TEST_LOG("Stop streaming \n"); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| #endif // defined(MAC_IPHONE)) |
| #ifdef MAC_IPHONE |
| TEST_LOG("\nNOTE: Always run hardware tests also without extended tests " |
| "enabled,\nsince the extended tests are pre-streaming tests only.\n"); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| ANL(); |
| AOK(); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestNetEqStats |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestNetEqStats() { |
| PrepareTest("NetEqStats (!EMPTY!)"); |
| |
| AOK(); |
| ANL(); |
| |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestNetwork |
| // |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestNetwork() { |
| PrepareTest("Network"); |
| |
| #ifdef WEBRTC_ANDROID |
| int sleepTime = 200; |
| int sleepTime2 = 250; |
| #elif defined(MAC_IPHONE) // MAC_IPHONE needs more delay for getSourceInfo() |
| int sleepTime = 150; |
| int sleepTime2 = 200; |
| #else |
| int sleepTime = 100; |
| int sleepTime2 = 200; |
| #endif |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| VoENetwork* netw = _mgr.NetworkPtr(); |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename( |
| "VoENetwork_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| |
| // ------------------------------------------------------------------------ |
| // >> GetLocalIP |
| // |
| // State: VE initialized, no existing channels |
| TEST(GetLocalIP); |
| ANL(); |
| |
| #ifdef MAC_IPHONE |
| // Should fail |
| TEST_MUSTPASS(!netw->GetLocalIP(NULL, 0)); MARK(); |
| TEST_ERROR(VE_FUNC_NOT_SUPPORTED); |
| |
| ANL(); |
| printf("NOTE: Local IP must be set in source code (line %d) \n", |
| __LINE__ + 1); |
| const char* localIP = "192.168.1.4"; |
| |
| #else |
| char localIP[64]; |
| |
| // invalid parameter |
| TEST_MUSTPASS(!netw->GetLocalIP(NULL)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| |
| // default function calls (IPv4) |
| TEST_MUSTPASS(netw->GetLocalIP(localIP)); |
| MARK(); |
| TEST_LOG("[local IPv4: %s]\n", localIP); |
| TEST_MUSTPASS(netw->GetLocalIP(localIP)); |
| MARK(); |
| |
| #if !defined(WEBRTC_MAC) && !defined(WEBRTC_ANDROID) |
| // default function calls (IPv6) |
| TEST_MUSTPASS(netw->GetLocalIP(localIP, true)); |
| MARK(); |
| TEST_LOG("[local IPv6: %s]\n", localIP); |
| TEST_MUSTPASS(netw->GetLocalIP(localIP, true)); |
| MARK(); |
| #endif |
| |
| // one last call to ensure that local |
| TEST_MUSTPASS(netw->GetLocalIP(localIP)); |
| MARK(); |
| #endif |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of GetLocalIP |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> GetSourceInfo |
| // |
| // - VE initialized |
| // - no existing channels |
| TEST(GetSourceInfo); |
| ANL(); |
| |
| int rtpPort(0); |
| int rtcpPort(0); |
| char ipaddr[64] = { 0 }; |
| ExtendedTestTransport* ptrTransport(NULL); |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // NULL as input string |
| TEST_MUSTPASS(!netw->GetSourceInfo(0, rtpPort, rtcpPort, NULL)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| |
| // call when external transport is enabled |
| ptrTransport = new ExtendedTestTransport(netw); |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| TEST_MUSTPASS(!netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| delete ptrTransport; |
| |
| // call when external transport is disabled (no packet received yet) |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 0); |
| TEST_MUSTPASS(rtcpPort != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| // send and receive packets with default settings for a while |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime2); // does not guarantee RTCP |
| |
| // verify remote parameters (exclude RTCP) |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 8000); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // ensure that valid results are maintained after StopListen |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 8000); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // verify that results are maintained after new call to SetLocalReceiver |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 8000); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // STATE: not listening, not sending |
| // send and receive packets with other settings for a while |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 9005)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 9005, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| |
| // STATE: listening, sending |
| |
| // verify new remote parameters |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 9005); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // restart sending to and from local IP |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 9005, kVoEDefault, localIP)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 9005, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| |
| // verify new remote parameters |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 9005); |
| TEST_MUSTPASS(strcmp(ipaddr, localIP) != 0); // should not be "127.0.0.1" |
| |
| // use non-default source port in outgoing packets |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 9005)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 9005, "127.0.0.1", 9010)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| |
| // verify new remote parameters |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 9010); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // STATE: listening and sending using an extra local socket |
| |
| // stop/start sending |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| |
| // verify that the unique source port is maintained for the extra socket |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 9010); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // set new source port for outgoing packets (9010 -> 9020) |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 9005, "127.0.0.1", 9020)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| #ifdef MAC_IPHONE |
| SLEEP(500); // Need extra pause for some reason |
| #endif |
| |
| // verify that the unique source port is set for the new extra socket |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 9020); |
| // STATE: listening and sending using an extra local socket |
| |
| // remove extra send socket and restart call again |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); // delete channel => destroys the |
| // extra socket |
| TEST_MUSTPASS(voe_base_->CreateChannel()); // new channel uses one socket only |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); // use new port as well |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| |
| // verify that remote info is correct |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 8000); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // STATE: listening and sending using shared socket |
| |
| // use non-default source port in outgoing packets to create extra send |
| // socket |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 7000)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 7000, "127.0.0.1", 7010)); |
| // RTP src is 7010 => RTCP src = 7011 |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| // verify new remote parameters |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 7010); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| |
| // check RTCP port as well (should be 7010 + 1 = 7011) |
| Sleep(8000, true); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 7010); |
| TEST_MUSTPASS(rtcpPort != 7011); |
| TEST_MUSTPASS(strcmp(ipaddr, "127.0.0.1") != 0); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of GetSourceInfo |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetExternalTransport |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| // |
| TEST(SetExternalTransport); |
| ANL(); |
| |
| ptrTransport = new ExtendedTestTransport(netw); |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // different valid call combinations |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| TEST_MUSTPASS(!netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); // must deregister first |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| |
| // STATE: external transport is disabled |
| |
| // initialize sending and ensure that external transport can't be enabled |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 1234, "127.0.0.2")); |
| TEST_MUSTPASS(!netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| TEST_ERROR(VE_SEND_SOCKETS_CONFLICT); |
| |
| // restart channel to ensure that "initialized sender" state is cleared |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // initialize receiving and ensure that external transport can't be enabled |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 5678)); |
| TEST_MUSTPASS(!netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| TEST_ERROR(VE_RECEIVE_SOCKETS_CONFLICT); |
| |
| // restart channel to ensure that "initialized receiver" state is cleared |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // enable external transport and verify that "emulated loopback" works |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); // should only start recording |
| TEST_MUSTPASS(!netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); // should fail |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| Play(0, 2000, true, true); // play file as mic and verify loopback audio |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| |
| // STATE: external transport is disabled |
| #if defined(WEBRTC_ANDROID) || defined(MAC_IPHONE) |
| int testError = VE_FUNC_NOT_SUPPORTED; |
| #else |
| int testError = VE_EXTERNAL_TRANSPORT_ENABLED; |
| #endif |
| |
| // check all APIs that should fail when external transport is enabled |
| int DSCP, priority, serviceType, overrideDSCP, nBytes(0); |
| bool useSetSockopt, enabled; |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| MARK(); |
| TEST_MUSTPASS(!voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!voe_base_->GetLocalReceiver(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!voe_base_->GetSendDestination(0, rtpPort, ipaddr, rtpPort, |
| rtcpPort)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!netw->EnableIPv6(0)) |
| TEST_ERROR(testError); |
| TEST_MUSTPASS(netw->IPv6IsEnabled(0) != false) |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!netw->SetSourceFilter(0, 12345, 12346)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(!netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| |
| // modified i VoE 3.4 (can be called also for external transport) |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| #if (!defined(_WIN32) && !defined(WEBRTC_LINUX) && !defined(WEBRTC_MAC)) || \ |
| defined(WEBRTC_EXTERNAL_TRANSPORT) |
| testError = VE_FUNC_NOT_SUPPORTED; |
| #else |
| testError = VE_EXTERNAL_TRANSPORT_ENABLED; |
| #endif |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 0)); |
| TEST_ERROR(testError); |
| TEST_MUSTPASS(!netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_ERROR(testError); |
| #if !defined(_WIN32) || defined(WEBRTC_EXTERNAL_TRANSPORT) |
| testError = VE_FUNC_NOT_SUPPORTED; |
| #else |
| testError = VE_EXTERNAL_TRANSPORT_ENABLED; |
| #endif |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, false, 0)); |
| TEST_ERROR(testError); |
| TEST_MUSTPASS(!netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_ERROR(testError); |
| char dummy[1] = { 'a' }; |
| TEST_MUSTPASS(!netw->SendUDPPacket(0, dummy, 1, nBytes)); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| |
| // always disable external transport before deleting the Transport object; |
| // will lead to crash for RTCP transmission otherwise |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| MARK(); |
| delete ptrTransport; |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of SetExternalTransport |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> EnableIPv6 |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| // - NOTE: set _ENABLE_IPV6_TESTS_ to include these tests |
| // - http://www.microsoft.com/resources/documentation/windows/xp/all/ |
| // proddocs/en-us/sag_ip_v6_pro_rt_enable.mspx?mfr=true |
| // >> ipv6 install |
| // >> ipv6 [-v] if [IfIndex] |
| // >> ping6 ::1 |
| // >> ping6 fe80::1 |
| |
| #ifdef _ENABLE_IPV6_TESTS_ |
| |
| TEST(EnableIPv6); ANL(); |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->EnableIPv6(0)); MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // call with enabled external transport |
| ptrTransport = new ExtendedTestTransport(netw); |
| TEST_MUSTPASS(netw->RegisterExternalTransport(0, *ptrTransport)); |
| TEST_MUSTPASS(!netw->EnableIPv6(0)); MARK(); |
| TEST_ERROR(VE_EXTERNAL_TRANSPORT_ENABLED); |
| TEST_MUSTPASS(netw->DeRegisterExternalTransport(0)); |
| delete ptrTransport; |
| |
| // Test "locking" to IPv4 |
| TEST_MUSTPASS(netw->IPv6IsEnabled(0)); MARK(); // After this call we cannot |
| // enable IPv6 |
| TEST_MUSTPASS(!netw->EnableIPv6(0)); MARK(); // Should fail |
| |
| // Check that IPv6 address is invalid |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(0, 8000, "::1")); MARK(); // fail |
| |
| // New channel |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // valid default call |
| TEST_MUSTPASS(netw->EnableIPv6(0)); MARK(); |
| TEST_MUSTPASS(netw->GetLocalIP(localIP)); MARK(); // should still read IPv4 |
| TEST_LOG("[local IPv4: %s]", localIP); |
| |
| // ensure that Ipv6 is enabled |
| TEST_MUSTPASS(netw->IPv6IsEnabled(0) != true); |
| |
| // check that IPv4 address is invalid |
| TEST_MUSTPASS(!voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_ERROR(VE_INVALID_IP_ADDRESS); |
| |
| // verify usage of IPv6 loopback address |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| // IPv6 loopback address is 0:0:0:0:0:0:0:1 |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "::1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(!netw->EnableIPv6(0)); MARK(); // Should fail |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); |
| ANL(); |
| |
| // Restart channel |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| TEST_MUSTPASS(netw->EnableIPv6(0)); MARK(); |
| // ensure that Ipv6 is enabled |
| TEST_MUSTPASS(netw->IPv6IsEnabled(0) != true); |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| // IPv6 loopback address is 0:0:0:0:0:0:0:1 |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "::1")); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), true, |
| true); |
| SLEEP(500); // ensure that we receieve some packets |
| |
| // SetSourceFilter and GetSourceFilter |
| TEST(SetSourceFilter and GetSourceFilter for IPv6); ANL(); |
| char sourceIp[64] = |
| { 0}; |
| char filterIp[64] = |
| { 0}; |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, sourceIp)); |
| TEST_LOG("Source port: %d \n", rtpPort); |
| TEST_LOG("Source RTCP port: %d \n", rtcpPort); |
| TEST_LOG("Source IP: %s \n", sourceIp); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, filterIp)); |
| TEST_LOG("Filter port RTP: %d \n", rtpPort); |
| TEST_LOG("Filter port RTCP: %d \n", rtcpPort); |
| TEST_LOG("Filter IP: %s \n", filterIp); |
| TEST_MUSTPASS(0 != rtpPort); |
| TEST_MUSTPASS(0 != rtcpPort); |
| TEST_MUSTPASS(filterIp[0] != '\0'); |
| TEST_LOG("Set filter IP to %s => should hear audio\n", sourceIp); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, sourceIp)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, filterIp)); |
| TEST_MUSTPASS(0 != rtpPort); |
| TEST_MUSTPASS(0 != rtcpPort); |
| TEST_MUSTPASS(_stricmp(filterIp, sourceIp)); |
| SLEEP(1500); |
| TEST_LOG("Set filter IP to ::10:10:10 => should *not* hear audio\n"); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "::10:10:10")); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, filterIp)); |
| TEST_MUSTPASS(_stricmp(filterIp, "::10:10:10")); |
| SLEEP(1500); |
| TEST_LOG("Disable IP filter => should hear audio again\n"); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "::0")); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, filterIp)); |
| TEST_MUSTPASS(_stricmp(filterIp, "::")); |
| SLEEP(1500); |
| TEST_LOG("Set filter IP to ::10:10:10 => should *not* hear audio\n"); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "::10:10:10")); |
| SLEEP(1500); |
| TEST_LOG("Disable IP filter => should hear audio again\n"); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, filterIp)); |
| TEST_MUSTPASS(filterIp[0] != '\0'); |
| SLEEP(1500); |
| TEST_LOG("Set filter IP to ::10:10:10 => should *not* hear audio\n"); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "::10:10:10")); |
| SLEEP(1500); |
| TEST_LOG("Disable IP filter => should hear audio again\n"); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "::")); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, filterIp)); |
| TEST_MUSTPASS(_stricmp(filterIp, "::")); |
| SLEEP(1500); |
| |
| file->StopPlayingFileAsMicrophone(0); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| |
| #endif // #ifdef _ENABLE_IPV6_TESTS_ |
| // >> end of EnableIPv6 |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetSourceFilter |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| TEST(SetSourceFilter); |
| ANL(); |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->SetSourceFilter(0, 12345)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // invalid parameters |
| TEST_MUSTPASS(!netw->SetSourceFilter(0, 65536)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_PORT_NMBR); |
| TEST_MUSTPASS(!netw->SetSourceFilter(0, 12345, 65536)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_PORT_NMBR); |
| TEST_MUSTPASS(!netw->SetSourceFilter(0, 12345, 12346, "300.300.300.300")); |
| MARK(); |
| TEST_ERROR(VE_INVALID_IP_ADDRESS); |
| |
| // STATE: RTP filter port is 12345, RTCP filter port is 12346 |
| |
| // disable all filters and ensure that media is received |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 2000, kVoEDefault, localIP)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 2000, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_MUSTPASS(rtpPort != 2000); |
| TEST_MUSTPASS(rtcpPort != 2001); |
| TEST_MUSTPASS(strcmp(ipaddr, localIP) != 0); |
| |
| // clear states and restart loopback session |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); // clear source info state |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // set RTP filter to port 2002 and verify that source 2000 is blocked |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 2002, 0, NULL));; |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 2000, kVoEDefault, localIP)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 2000, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_MUSTPASS(rtpPort != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| // ensure that received packets originates from 2002 and that they now pass |
| // the filter |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| // RTP source is 2002 |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 2002, kVoEDefault, localIP)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 2002, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_MUSTPASS(rtpPort != 2002); |
| TEST_MUSTPASS(strcmp(ipaddr, localIP) != 0); |
| |
| // clear states and restart loopback session |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); // clear source info state |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // set IP filter to local IP and verify that default loopback stream is |
| // blocked |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, localIP));; |
| MARK(); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 2000)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 2000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_MUSTPASS(rtpPort != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| // ensure that received packets originates from the local IP and that they |
| // now pass the filter |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| // should pass the filter |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 2000, kVoEDefault, localIP)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 2000, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| TEST_MUSTPASS(netw->GetSourceInfo(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_MUSTPASS(rtpPort != 2000); |
| TEST_MUSTPASS(strcmp(ipaddr, localIP) != 0); |
| |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| |
| // STATE: no active media, IP filter is active |
| |
| // disable all filters |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL));; |
| MARK(); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| TEST_MUSTPASS(rtpPort != 0); |
| TEST_MUSTPASS(rtcpPort != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of SetSourceFilter |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> GetSourceFilter |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| TEST(GetSourceFilter); |
| ANL(); |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // invalid input parameters |
| TEST_MUSTPASS(!netw->GetSourceFilter(0, rtpPort, rtcpPort, NULL)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| |
| // valid call without any filter set |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 0); |
| TEST_MUSTPASS(rtcpPort != 0); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| // STATE: no active media and no enabled filters |
| |
| // set different filters and verify that they "bite" |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 54321, 0, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 54321); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtpPort != 0); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 15425, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtcpPort != 15425); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(rtcpPort != 0); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "192.168.199.19")); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(strcmp(ipaddr, "192.168.199.19") != 0); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, "0.0.0.0")); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(strcmp(ipaddr, "0.0.0.0") != 0); |
| TEST_MUSTPASS(netw->SetSourceFilter(0, 0, 0, NULL)); |
| TEST_MUSTPASS(netw->GetSourceFilter(0, rtpPort, rtcpPort, ipaddr)); |
| MARK(); |
| TEST_MUSTPASS(strcmp(ipaddr, "") != 0); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of GetSourceFilter |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> RegisterDeadOrAliveObserver |
| // >> DeRegisterDeadOrAliveObserver |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| TEST(RegisterDeadOrAliveObserver); |
| ANL(); |
| TEST(DeRegisterDeadOrAliveObserver); |
| ANL(); |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->RegisterDeadOrAliveObserver(0, *this)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| TEST_MUSTPASS(netw->RegisterDeadOrAliveObserver(0, *this)); |
| MARK(); |
| TEST_MUSTPASS(!netw->RegisterDeadOrAliveObserver(0, *this)); |
| MARK(); // already registered |
| TEST_ERROR(VE_INVALID_OPERATION); |
| TEST_MUSTPASS(netw->DeRegisterDeadOrAliveObserver(0)); |
| MARK(); |
| TEST_MUSTPASS(netw->DeRegisterDeadOrAliveObserver(0)); |
| MARK(); // OK to do it again |
| TEST_MUSTPASS(netw->RegisterDeadOrAliveObserver(0, *this)); |
| MARK(); |
| TEST_MUSTPASS(netw->DeRegisterDeadOrAliveObserver(0)); |
| MARK(); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| |
| // STATE: dead-or-alive observer is disabled |
| |
| // >> end of RegisterDeadOrAliveObserver |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetPeriodicDeadOrAliveStatus |
| // >> GetPeriodicDeadOrAliveStatus |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| |
| // call without valid channel |
| TEST_MUSTPASS(!netw->SetPeriodicDeadOrAliveStatus(0, false)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // Invalid paramters |
| TEST_MUSTPASS(!netw->SetPeriodicDeadOrAliveStatus(0, true, 0)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetPeriodicDeadOrAliveStatus(0, true, 151)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetPeriodicDeadOrAliveStatus(1, true, 10)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| int sampleTime(0); |
| |
| // Valid parameters |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, true, 1)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPeriodicDeadOrAliveStatus(0, enabled, sampleTime)); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(sampleTime != 1); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, true, 150)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPeriodicDeadOrAliveStatus(0, enabled, sampleTime)); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(sampleTime != 150); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, false)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPeriodicDeadOrAliveStatus(0, enabled, sampleTime)); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(sampleTime != 150); // ensure last set time isnt modified |
| |
| StartMedia(0, 2000, true, true, true); |
| |
| // STATE: full duplex media is active |
| |
| // test the dead-or-alive mechanism |
| TEST_MUSTPASS(netw->RegisterDeadOrAliveObserver(0, *this)); |
| MARK(); |
| TEST_LOG("\nVerify that Alive callbacks are received (dT=2sec): "); |
| fflush(NULL); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, true, 2)); |
| SLEEP(6000); |
| TEST_LOG("\nChange dT to 1 second: "); |
| fflush(NULL); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, true, 1)); |
| SLEEP(6000); |
| TEST_LOG("\nDisable dead-or-alive callbacks: "); |
| fflush(NULL); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, false)); |
| SLEEP(6000); |
| TEST_LOG("\nStop sending and enable callbacks again.\n"); |
| TEST_LOG("Verify that Dead callbacks are received (dT=2sec): "); |
| fflush(NULL); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, true, 2)); |
| SLEEP(6000); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_LOG("\nRestart sending.\n"); |
| TEST_LOG("Verify that Alive callbacks are received again (dT=2sec): "); |
| fflush(NULL); |
| SLEEP(6000); |
| TEST_LOG("\nDisable dead-or-alive callbacks."); |
| fflush(NULL); |
| TEST_MUSTPASS(netw->SetPeriodicDeadOrAliveStatus(0, false)); |
| TEST_MUSTPASS(netw->DeRegisterDeadOrAliveObserver(0)); |
| MARK(); |
| |
| StopMedia(0); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of SetPeriodicDeadOrAliveStatus |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetPacketTimeoutNotification |
| // >> GetPacketTimeoutNotification |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| // - NOTE: dynamic tests are performed in standard test |
| |
| int timeOut(0); |
| |
| TEST(SetPacketTimeoutNotification); |
| ANL(); |
| TEST(GetPacketTimeoutNotification); |
| ANL(); |
| |
| // call without existing valid channel |
| TEST_MUSTPASS(!netw->SetPacketTimeoutNotification(0, false)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // invalid function calls |
| TEST_MUSTPASS(!netw->SetPacketTimeoutNotification(0, true, 0)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetPacketTimeoutNotification(0, true, 151)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| |
| // valid function calls (no active media) |
| TEST_MUSTPASS(netw->SetPacketTimeoutNotification(0, true, 2)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPacketTimeoutNotification(0, enabled, timeOut)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(timeOut != 2); |
| TEST_MUSTPASS(netw->SetPacketTimeoutNotification(0, false)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPacketTimeoutNotification(0, enabled, timeOut)); |
| MARK(); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(netw->SetPacketTimeoutNotification(0, true, 10)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPacketTimeoutNotification(0, enabled, timeOut)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(timeOut != 10); |
| TEST_MUSTPASS(netw->SetPacketTimeoutNotification(0, true, 2)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPacketTimeoutNotification(0, enabled, timeOut)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(timeOut != 2); |
| TEST_MUSTPASS(netw->SetPacketTimeoutNotification(0, false)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetPacketTimeoutNotification(0, enabled, timeOut)); |
| MARK(); |
| TEST_MUSTPASS(enabled != false); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| ANL(); |
| AOK(); |
| ANL(); |
| ANL(); |
| |
| // >> end of SetPacketTimeoutNotification |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SendUDPPacket |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| |
| |
| // >> end of SendUDPPacket |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetSendTOS |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| TEST(SetSendTOS); |
| ANL(); |
| #if defined(_WIN32) || defined(WEBRTC_MAC) || defined(WEBRTC_LINUX) |
| |
| // call without existing valid channel |
| |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 0)); MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // trivial invalid function calls |
| TEST_MUSTPASS(!netw->SetSendTOS(0, -1)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 64)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 1, -2)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 1, 8)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 1)); MARK(); |
| TEST_ERROR(VE_SOCKET_ERROR); // must create sockets first |
| |
| #ifdef _WIN32 |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 3000)); |
| |
| // enable ToS using SetSockopt (should work without local binding) |
| TEST_MUSTPASS(netw->SetSendTOS(0, 1, -1, true)); MARK(); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); MARK(); |
| TEST_MUSTPASS(DSCP != 1); |
| TEST_MUSTPASS(priority != 0); |
| TEST_MUSTPASS(useSetSockopt != true); |
| |
| // try to disable SetSockopt while ToS is enabled (should fail) |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 1, -1, false)); MARK(); |
| TEST_ERROR(VE_TOS_INVALID); // must disable ToS before enabling SetSockopt |
| |
| // disable ToS to be able to stop using SetSockopt |
| TEST_MUSTPASS(netw->SetSendTOS(0, 0, -1, true)); MARK(); // disable ToS |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); MARK(); |
| TEST_MUSTPASS(DSCP != 0); |
| TEST_MUSTPASS(priority != 0); |
| TEST_MUSTPASS(useSetSockopt != true); |
| |
| // to use the "non-SetSockopt" method, local binding is required, |
| // trying without it should fail |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 1, -1, false)); MARK(); |
| TEST_ERROR(VE_TOS_ERROR); // must bind to local IP first |
| |
| // bind to local IP and try again (should work this time) |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345, kVoEDefault, localIP)); |
| TEST_LOG("\nThis test needs to be run as administrator\n"); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 1, -1, false)); MARK(); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); MARK(); |
| TEST_MUSTPASS(DSCP != 1); |
| TEST_MUSTPASS(priority != 0); |
| TEST_MUSTPASS(useSetSockopt != false); |
| |
| // STATE: binded to local IP, local port is 12345 and DSCP is 1 (not using |
| // SetSockopt) |
| |
| // verify loopback audio with the current settings |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| #ifdef _SEND_TO_REMOTE_IP_ |
| // Send to remote destination and verify the DSCP using Wireshark. |
| // Use filter ip.src == "RemoteIP". |
| TEST_LOG("\nUse Wireshark and verify a correctly received DSCP at the " |
| "remote side!\n"); |
| TEST_LOG("Sending approx. 5 packets to %s:%d for each DSCP below:\n", |
| RemoteIP, RemotePort); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, RemotePort, RemoteIP)); |
| TEST_LOG(" DSCP is set to 0x%02x\n", 1); |
| SLEEP(100); |
| |
| // Change the DSCP while sending is active and verify on remote side. |
| TEST_MUSTPASS(netw->SetSendTOS(0, 2)); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x\n", DSCP); |
| SLEEP(100); |
| |
| // Change the DSCP while sending is active and verify on remote side. |
| TEST_MUSTPASS(netw->SetSendTOS(0, 63)); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x\n", DSCP); |
| SLEEP(100); |
| |
| // stop and resume sending |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x\n", DSCP); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 0)); |
| #endif // _SEND_TO_REMOTE_IP_ |
| // Windows priority tests (priority cannot be set using setsockopt on Win) |
| TEST_LOG("Testing priority\n"); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 0, 3, true)); // Should fail |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 0, 3, false)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); // file should be played out here... |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 1, 3, false)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| #endif // _WIN32 |
| // STATE: no media, disabled ToS, no defined receiver |
| |
| // Repeat tests above but using setsockopt() this time. |
| // Binding to local IP should not be required. |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345, kVoEDefault)); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 10, -1, true)); MARK(); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); MARK(); |
| TEST_MUSTPASS(DSCP != 10); |
| TEST_MUSTPASS(priority != 0); |
| TEST_MUSTPASS(useSetSockopt != true); |
| |
| // STATE: *not* binded to local IP, local port is 12345 and DSCP is 10 |
| // (using SetSockopt) |
| |
| // verify loopback audio with the current settings |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| #ifdef _SEND_TO_REMOTE_IP_ |
| // Send to remote destination and verify the DSCP using Wireshark. |
| // Use filter ip.src == "RemoteIP". |
| TEST_LOG("\nUse Wireshark and verify a correctly received DSCP at the" |
| " remote side!\n"); |
| TEST_LOG("Sending approx. 5 packets to %s:%d for each DSCP below:\n", |
| RemoteIP, RemotePort); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, RemotePort, RemoteIP)); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x (setsockopt)\n", DSCP); |
| SLEEP(100); |
| |
| // Change the DSCP while sending is active and verify on remote side. |
| TEST_MUSTPASS(netw->SetSendTOS(0, 20, -1, true)); // use setsockopt() |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x (setsockopt)\n", DSCP); |
| SLEEP(100); |
| |
| // Change the DSCP while sending is active and verify on remote side. |
| TEST_MUSTPASS(netw->SetSendTOS(0, 61, -1, true)); // use setsockopt() |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x (setsockopt)\n", DSCP); |
| SLEEP(100); |
| |
| // stop and resume sending |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(netw->GetSendTOS(0, DSCP, priority, useSetSockopt)); |
| TEST_LOG(" DSCP is set to 0x%02x (setsockopt)\n", DSCP); |
| SLEEP(100); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 0, -1, true)); |
| #endif // _SEND_TO_REMOTE_IP_ |
| #if defined(WEBRTC_LINUX) |
| // Linux priority tests (using setsockopt) |
| TEST_LOG("Testing priority\n"); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, localIP)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 0, 3, true)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); // file should be played out here... |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(netw->SetSendTOS(0, 1, 3, true)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| Play(0, 2000, true, true); // file should be played out here... |
| #endif // #if defined(WEBRTC_LINUX) |
| #if !defined(_WIN32) && !defined(WEBRTC_LINUX) |
| // Fail tests for other than Wind and Linux |
| TEST_MUSTPASS(!netw->SetSendTOS(0, 0, 3, false)); // Should fail |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| #endif // #if !defined(_WIN32) && !defined(WEBRTC_LINUX) |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| ANL(); AOK(); ANL(); ANL(); |
| |
| // END #if defined(_WIN32) || defined(WEBRTC_MAC) || defined(WEBRTC_LINUX) |
| #else |
| TEST_LOG("Skipping ToS tests - _WIN32, LINUX, MAC is not defined or " |
| "WEBRTC_ANDROID is defined"); |
| #endif |
| |
| // >> end of SetSendTOS |
| // ------------------------------------------------------------------------ |
| |
| // ------------------------------------------------------------------------ |
| // >> SetSendGQoS (Windows only) |
| // |
| // - VE initialized |
| // - no existing channels |
| // - no media |
| // |
| // From qos.h: |
| // |
| // #define SERVICETYPE_NOTRAFFIC 0x00000000 |
| // #define SERVICETYPE_BESTEFFORT 0x00000001 (*) |
| // #define SERVICETYPE_CONTROLLEDLOAD 0x00000002 (*) |
| // #define SERVICETYPE_GUARANTEED 0x00000003 (*) |
| // #define SERVICETYPE_NETWORK_UNAVAILABLE 0x00000004 |
| // #define SERVICETYPE_GENERAL_INFORMATION 0x00000005 |
| // #define SERVICETYPE_NOCHANGE 0x00000006 |
| // #define SERVICETYPE_NONCONFORMING 0x00000009 |
| // #define SERVICETYPE_NETWORK_CONTROL 0x0000000A |
| // #define SERVICETYPE_QUALITATIVE 0x0000000D (*) |
| // |
| // #define SERVICE_BESTEFFORT 0x80010000 |
| // #define SERVICE_CONTROLLEDLOAD 0x80020000 |
| // #define SERVICE_GUARANTEED 0x80040000 |
| // #define SERVICE_QUALITATIVE 0x80200000 |
| // |
| // (*) supported in WEBRTC VoE |
| TEST(SetSendGQoS); |
| ANL(); |
| #ifdef _WIN32 |
| |
| // call without existing valid channel |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, false, 0)); MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| // supported service type but no sockets |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT)); MARK(); |
| TEST_ERROR(VE_SOCKETS_NOT_INITED); |
| |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| |
| // supported service type but sender is not initialized |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT)); MARK(); |
| TEST_ERROR(VE_DESTINATION_NOT_INITED); |
| |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| |
| // invalid service types |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_NOTRAFFIC)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_NETWORK_UNAVAILABLE)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_GENERAL_INFORMATION)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_NOCHANGE)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_NONCONFORMING)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_NETWORK_CONTROL)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICE_BESTEFFORT)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICE_CONTROLLEDLOAD)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICE_GUARANTEED)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICE_QUALITATIVE)); MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| |
| // Is ToS enabled here? |
| |
| // Settings which don't require binding to local IP |
| |
| // set SERVICETYPE_BESTEFFORT |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT)); MARK(); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(serviceType != SERVICETYPE_BESTEFFORT); |
| TEST_MUSTPASS(overrideDSCP != false); |
| |
| // set SERVICETYPE_CONTROLLEDLOAD |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_CONTROLLEDLOAD)); |
| MARK(); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(serviceType != SERVICETYPE_CONTROLLEDLOAD); |
| TEST_MUSTPASS(overrideDSCP != false); |
| |
| // set SERVICETYPE_GUARANTEED |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_GUARANTEED)); MARK(); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(serviceType != SERVICETYPE_GUARANTEED); |
| TEST_MUSTPASS(overrideDSCP != false); |
| |
| // set SERVICETYPE_QUALITATIVE |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_QUALITATIVE)); MARK(); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(serviceType != SERVICETYPE_QUALITATIVE); |
| TEST_MUSTPASS(overrideDSCP != false); |
| |
| // disable GQoS |
| TEST_MUSTPASS(netw->SetSendGQoS(0, false, 0)); MARK(); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| MARK(); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(serviceType != SERVICETYPE_QUALITATIVE); |
| TEST_MUSTPASS(overrideDSCP != false); |
| |
| // STATE: diabled QGoS, sockets exists, sending side is initialized, no media |
| |
| // Loopback tests using the four different GQoS settings |
| |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT)); MARK(); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| ANL(); |
| TEST_LOG("[SERVICETYPE_BESTEFFORT]"); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_CONTROLLEDLOAD)); MARK(); |
| ANL(); |
| TEST_LOG("[SERVICETYPE_CONTROLLEDLOAD]"); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_GUARANTEED)); MARK(); |
| ANL(); |
| TEST_LOG("[SERVICETYPE_GUARANTEED]"); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_QUALITATIVE)); MARK(); |
| ANL(); |
| TEST_LOG("[SERVICETYPE_QUALITATIVE]"); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| #ifdef _SEND_TO_REMOTE_IP_ |
| // Send to remote destination and verify the DSCP mapping using Wireshark. |
| // Use filter ip.src == "RemoteIP". |
| |
| // Modify the send destination on the fly |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, RemotePort, RemoteIP)); |
| |
| TEST_LOG("\nUse Wireshark and verify a correctly received DSCP mapping at" |
| " the remote side!\n"); |
| TEST_LOG("Sending approx. 5 packets to %s:%d for each GQoS setting below:\n", |
| RemoteIP, RemotePort); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_BESTEFFORT (0x%02x), should " |
| "be mapped to DSCP = 0x00\n", serviceType); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_CONTROLLEDLOAD)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_CONTROLLEDLOAD (0x%02x), " |
| "should be mapped to DSCP = 0x18\n", serviceType); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, false, 0)); |
| TEST_LOG(" QoS is disabled, should give DSCP = 0x%02x\n", 0); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_GUARANTEED)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_GUARANTEED (0x%02x), should " |
| "be mapped to DSCP = 0x28\n", serviceType); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, false, 0)); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_QUALITATIVE)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_QUALITATIVE (0x%02x), should" |
| " be mapped to DSCP = 0x00\n", serviceType); |
| SLEEP(100); |
| #endif // _SEND_TO_REMOTE_IP_ |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| |
| // STATE: sockets exists, sending side is initialized, no media |
| |
| // Repeat test above but this time using overrideDSCP. |
| |
| // Some initial loopack tests. |
| // NOTE - override DSCP requres binding to local IP. |
| |
| // should not work since QoS is enabled |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 3)); |
| MARK(); |
| TEST_ERROR(VE_TOS_GQOS_CONFLICT); |
| |
| // disble QoS and try to override again (should fail again since local |
| // binding is not done yet) |
| TEST_MUSTPASS(netw->SetSendGQoS(0, false, 0)); |
| TEST_MUSTPASS(!netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 3)); |
| MARK(); |
| TEST_ERROR(VE_GQOS_ERROR); |
| |
| // make proper settings and try again (should work this time) |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345, kVoEDefault, localIP)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, localIP)); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 3)); |
| MARK(); |
| |
| // Now, let's try some loopback tests using override DSCP |
| |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| ANL(); |
| TEST_LOG("[overrideDSCP=3]"); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 17)); |
| MARK(); |
| ANL(); |
| TEST_LOG("[overrideDSCP=17]"); |
| Play(0, 2000, true, true); // file should be played out here... |
| |
| // And finally, send to remote side as well to verify that the new mapping |
| // works as it should. |
| |
| #ifdef _SEND_TO_REMOTE_IP_ |
| // Modify the send destination on the fly |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, RemotePort, RemoteIP)); |
| |
| TEST_LOG("\nUse Wireshark and verify a correctly received DSCP mapping at" |
| " the remote side!\n"); |
| TEST_LOG("Sending approx. 5 packets to %s:%d for each GQoS setting below:\n", |
| RemoteIP, RemotePort); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 18)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_BESTEFFORT, should be " |
| "overrided to DSCP = 0x%02x\n", overrideDSCP); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 62)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_BESTEFFORT, should be " |
| "overrided to DSCP = 0x%02x\n", overrideDSCP); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 32)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_BESTEFFORT, should be " |
| "overrided to DSCP = 0x%02x\n", overrideDSCP); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, true, SERVICETYPE_BESTEFFORT, 1)); |
| TEST_MUSTPASS(netw->GetSendGQoS(0, enabled, serviceType, overrideDSCP)); |
| TEST_LOG(" serviceType is set to SERVICETYPE_BESTEFFORT, should be " |
| "overrided to DSCP = 0x%02x\n", overrideDSCP); |
| SLEEP(100); |
| TEST_MUSTPASS(netw->SetSendGQoS(0, false, 0)); |
| TEST_LOG(" QoS is disabled, should give DSCP = 0x%02x\n", 0); |
| SLEEP(100); |
| #endif // _SEND_TO_REMOTE_IP_ |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| ANL(); AOK(); ANL(); ANL(); |
| |
| #else |
| TEST_LOG("Skipping GQoS tests - _WIN32 is not defined"); |
| #endif // #ifdef _WIN32 |
| // >> end of SetSendGQoS |
| // ------------------------------------------------------------------------ |
| |
| if (file) { |
| file->StopPlayingFileAsMicrophone(0); |
| } |
| voe_base_->StopSend(0); |
| voe_base_->StopPlayout(0); |
| voe_base_->StopReceive(0); |
| voe_base_->DeleteChannel(0); |
| voe_base_->Terminate(); |
| |
| ANL(); |
| AOK(); |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestRTP_RTCP |
| // ---------------------------------------------------------------------------- |
| |
| // Used to validate packets during the RTP audio level indication test. |
| class RTPAudioTransport: public Transport { |
| public: |
| |
| RTPAudioTransport() : |
| mute_(false) { |
| } |
| |
| virtual ~RTPAudioTransport() { |
| } |
| |
| void set_mute(bool mute) { |
| mute_ = mute; |
| } |
| bool mute() const { |
| return mute_; |
| } |
| |
| // TODO(andrew): use proper error checks here rather than asserts. |
| virtual int SendPacket(int channel, const void* data, int length) { |
| const uint8_t* packet = static_cast<const uint8_t*> (data); |
| |
| // Extension bit. |
| assert(packet[0] & 0x10); |
| int index = 12; // Assume standard RTP header. |
| // Header extension ID |
| assert(packet[index++] == 0xBE); |
| assert(packet[index++] == 0xDE); |
| // Header extension length |
| assert(packet[index++] == 0x00); |
| assert(packet[index++] == 0x01); |
| |
| // User-defined ID. |
| assert(((packet[index] & 0xf0) >> 4) == 1); |
| // Length |
| assert((packet[index++] & 0x0f) == 0); |
| |
| int vad = packet[index] >> 7; |
| int level = packet[index] & 0x7f; |
| if (channel == 0) { |
| printf("%d -%d\n", vad, level); |
| } else if (channel == 1) { |
| printf(" %d -%d\n", vad, level); |
| } else { |
| assert(false); |
| } |
| |
| if (mute_) { |
| assert(vad == 0); |
| assert(level == 127); |
| } else { |
| assert(vad == 0 || vad == 1); |
| assert(level >= 0 && level <= 127); |
| } |
| |
| return 0; |
| } |
| |
| virtual int SendRTCPPacket(int /*channel*/, const void* /*data*/, |
| int /*length*/) { |
| return 0; |
| } |
| |
| private: |
| bool mute_; |
| }; |
| |
| int VoEExtendedTest::TestRTP_RTCP() { |
| PrepareTest("RTP_RTCP"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEFile* file = _mgr.FilePtr(); |
| VoERTP_RTCP* rtp_rtcp = _mgr.RTP_RTCPPtr(); |
| VoENetwork* network = _mgr.NetworkPtr(); |
| VoEVolumeControl* volume = _mgr.VolumeControlPtr(); |
| VoECodec* codec = _mgr.CodecPtr(); |
| |
| XRTPObserver rtpObserver; |
| |
| #ifdef WEBRTC_ANDROID |
| int sleepTime = 200; |
| #else |
| int sleepTime = 100; |
| #endif |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename( |
| "VoERTP_RTCP_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| // ------------------------------------------------------------------------ |
| // >> Set/GetRTPAudioLevelIndicationStatus |
| TEST(SetRTPAudioLevelIndicationStatus); |
| ANL(); |
| TEST(GetRTPAudioLevelIndicationStatus); |
| |
| // test invalid input parameters |
| TEST_MUSTPASS(-1 != rtp_rtcp->SetRTPAudioLevelIndicationStatus(0, true, 0)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(-1 != rtp_rtcp->SetRTPAudioLevelIndicationStatus(0, true, 15)); |
| MARK(); |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(-1 != rtp_rtcp->SetRTPAudioLevelIndicationStatus(0, false, 15)); |
| MARK(); |
| TEST_MUSTPASS(-1 != rtp_rtcp->SetRTPAudioLevelIndicationStatus(1, true, 5)); |
| MARK(); |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| |
| // test complete valid input range [1,14] |
| bool audioLevelEnabled(false); |
| unsigned char ID(0); |
| for (int id = 1; id < 15; id++) { |
| TEST_MUSTPASS(rtp_rtcp->SetRTPAudioLevelIndicationStatus(0, true, id)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTPAudioLevelIndicationStatus( |
| 0, audioLevelEnabled, ID)); |
| MARK(); |
| TEST_MUSTPASS(audioLevelEnabled != true); |
| TEST_MUSTPASS(rtp_rtcp->SetRTPAudioLevelIndicationStatus(0, false, id)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTPAudioLevelIndicationStatus( |
| 0, audioLevelEnabled, ID)); |
| MARK(); |
| TEST_MUSTPASS(audioLevelEnabled != false); |
| TEST_MUSTPASS(ID != id); |
| } |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| |
| RTPAudioTransport rtpAudioTransport; |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(network->RegisterExternalTransport(0, rtpAudioTransport)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTPAudioLevelIndicationStatus(0, true)); |
| TEST_MUSTPASS(codec->SetVADStatus(0, true)); |
| |
| printf("\n\nReceving muted packets (expect VAD = 0, Level = -127)...\n"); |
| printf("VAD Level [dbFS]\n"); |
| SLEEP(2000); |
| rtpAudioTransport.set_mute(true); |
| TEST_MUSTPASS(volume->SetInputMute(0, true)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(5000); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| rtpAudioTransport.set_mute(false); |
| TEST_MUSTPASS(volume->SetInputMute(0, false)); |
| |
| printf("\nReceiving packets from mic (should respond to mic level)...\n"); |
| printf("VAD Level [dbFS]\n"); |
| SLEEP(2000); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(5000); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| |
| printf("\nReceiving packets from file (expect mostly VAD = 1)...\n"); |
| printf("VAD Level [dbFS]\n"); |
| SLEEP(2000); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(5000); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| |
| printf("\nMuted and mic on independent channels...\n"); |
| printf("Muted Mic\n"); |
| SLEEP(2000); |
| ASSERT_TRUE(1 == voe_base_->CreateChannel()); |
| TEST_MUSTPASS(network->RegisterExternalTransport(1, rtpAudioTransport)); |
| TEST_MUSTPASS(rtp_rtcp->SetRTPAudioLevelIndicationStatus(1, true)); |
| TEST_MUSTPASS(codec->SetVADStatus(1, true)); |
| TEST_MUSTPASS(volume->SetInputMute(0, true)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(1)); |
| SLEEP(5000); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(1)); |
| |
| TEST_MUSTPASS(network->DeRegisterExternalTransport(0)); |
| TEST_MUSTPASS(network->DeRegisterExternalTransport(1)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(1)); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| |
| MARK(); |
| ANL(); |
| |
| // ------------------------------------------------------------------------ |
| // >> InsertExtraRTPPacket |
| |
| int i(0); |
| |
| TEST(SetLocalSSRC); |
| TEST_MUSTPASS(!rtp_rtcp->SetLocalSSRC(0, 5678)); |
| MARK(); |
| TEST_MUSTPASS(VE_ALREADY_SENDING != voe_base_->LastError()); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(rtp_rtcp->SetLocalSSRC(0, 5678)); // force send SSRC to 5678 |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| MARK(); |
| ANL(); |
| |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| |
| // ------------------------------------------------------------------------ |
| // >> InsertExtraRTPPacket |
| TEST(InsertExtraRTPPacket); |
| ANL(); |
| |
| const char payloadData[8] = { 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H' }; |
| |
| TEST_MUSTPASS(-1 != rtp_rtcp->InsertExtraRTPPacket(-1, 0, false, |
| payloadData, 8)); |
| MARK(); // invalid channel |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(-1 != rtp_rtcp->InsertExtraRTPPacket(0, -1, false, |
| payloadData, 8)); |
| MARK(); // invalid payload type |
| TEST_ERROR(VE_INVALID_PLTYPE); |
| TEST_MUSTPASS(-1 != rtp_rtcp->InsertExtraRTPPacket(0, 128, false, |
| payloadData, 8)); |
| MARK(); // invalid payload type |
| TEST_ERROR(VE_INVALID_PLTYPE); |
| TEST_MUSTPASS(-1 != rtp_rtcp->InsertExtraRTPPacket(0, 99, false, |
| NULL, 8)); |
| MARK(); // invalid pointer |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(-1 != rtp_rtcp->InsertExtraRTPPacket(0, 99, false, |
| payloadData, 1500-28+1)); |
| MARK(); // invalid size |
| TEST_ERROR(VE_INVALID_ARGUMENT); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(-1 != rtp_rtcp->InsertExtraRTPPacket(0, 99, false, |
| payloadData, 8)); |
| MARK(); // not sending |
| TEST_ERROR(VE_NOT_SENDING); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| |
| SLEEP(1000); |
| for (int p = 0; p < 128; p++) { |
| TEST_MUSTPASS(rtp_rtcp->InsertExtraRTPPacket(0, p, false, |
| payloadData, 8)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->InsertExtraRTPPacket(0, p, true, |
| payloadData, 8)); |
| MARK(); |
| } |
| |
| // Ensure we have sent all extra packets before we move forward to avoid |
| //incorrect error code |
| SLEEP(1000); |
| |
| ANL(); |
| |
| // ------------------------------------------------------------------------ |
| // >> RTP dump APIs |
| TEST(Start/StopRtpDump); |
| ANL(); |
| TEST(Start/RTPDumpIsActive); |
| |
| TEST_MUSTPASS(-1 != rtp_rtcp->RTPDumpIsActive(-1, kRtpIncoming)); |
| MARK(); // invalid channel |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(false != rtp_rtcp->RTPDumpIsActive(0, kRtpIncoming)); |
| MARK(); // should be off by default |
| TEST_MUSTPASS(false != rtp_rtcp->RTPDumpIsActive(0, kRtpOutgoing)); |
| MARK(); // should be off by default |
| |
| TEST_MUSTPASS(-1 != rtp_rtcp->StartRTPDump(-1, NULL)); |
| MARK(); // invalid channel |
| TEST_ERROR(VE_CHANNEL_NOT_VALID); |
| TEST_MUSTPASS(-1 != rtp_rtcp->StartRTPDump(0, NULL)); |
| MARK(); // invalid file name |
| TEST_ERROR(VE_BAD_FILE); |
| |
| // Create two RTP dump files: |
| |
| // - dump_in_1sec.rtp <=> ~1 sec recording of input side |
| // - dump_in_2sec.rtp <=> ~2 sec recording of output side |
| // |
| TEST_MUSTPASS(rtp_rtcp->StopRTPDump(0)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->StopRTPDump(0, kRtpIncoming)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->StopRTPDump(0, kRtpOutgoing)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->StartRTPDump(0, GetFilename("dump_in_1sec.rtp"), |
| kRtpIncoming)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->StartRTPDump(0, GetFilename("dump_out_2sec.rtp"), |
| kRtpOutgoing)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(rtp_rtcp->StopRTPDump(0, kRtpIncoming)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(rtp_rtcp->StopRTPDump(0, kRtpOutgoing)); |
| MARK(); |
| |
| // Start/Stop tests: |
| // |
| // - only one file (called dump_in_200ms.rtp) should exist after this test |
| // |
| for (i = 0; i < 10; i++) { |
| TEST_MUSTPASS(rtp_rtcp->StartRTPDump(0, |
| GetFilename("dump_in_200ms.rtp"))); |
| MARK(); |
| SLEEP(200); |
| TEST_MUSTPASS(rtp_rtcp->StopRTPDump(0)); |
| MARK(); |
| } |
| |
| // >> end of RTP dump APIs |
| // ------------------------------------------------------------------------ |
| ANL(); |
| |
| TEST(GetRTCPStatus); |
| bool enabled; |
| TEST_MUSTPASS(!rtp_rtcp->GetRTCPStatus(-1, enabled)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatus(0, enabled)); |
| MARK(); // should be on by default |
| TEST_MUSTPASS(enabled != true); |
| ANL(); |
| |
| TEST(SetRTCPStatus); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCPStatus(0, false)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatus(0, enabled)); |
| TEST_MUSTPASS(enabled != false); |
| MARK(); |
| SLEEP(2000); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCPStatus(0, true)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatus(0, enabled)); |
| TEST_MUSTPASS(enabled != true); |
| MARK(); |
| SLEEP(6000); // Make sure we get an RTCP packet |
| ANL(); |
| |
| TEST(CNAME); |
| TEST_MUSTPASS(!rtp_rtcp->SetRTCP_CNAME(0, NULL)); |
| MARK(); |
| TEST_MUSTPASS(VE_RTP_RTCP_MODULE_ERROR != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!rtp_rtcp->GetRemoteRTCP_CNAME(0, NULL)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| ANL(); |
| |
| TEST(GetRemoteSSRC); |
| unsigned int ssrc(0); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteSSRC(0, ssrc)); |
| MARK(); |
| TEST_MUSTPASS(ssrc != 5678); |
| ANL(); |
| |
| TEST(GetRemoteCSRC); // only trivial tests added |
| unsigned int csrcs[2]; |
| int n(0); |
| TEST_MUSTPASS(!rtp_rtcp->GetRemoteCSRCs(1, csrcs)); |
| MARK(); |
| n = rtp_rtcp->GetRemoteCSRCs(0, csrcs); |
| MARK(); |
| TEST_MUSTPASS(n != 0); // should be empty |
| ANL(); |
| |
| TEST(SetRTPObserver); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(rtp_rtcp->RegisterRTPObserver(0, rtpObserver)); |
| TEST_MUSTPASS(rtp_rtcp->DeRegisterRTPObserver(0)); |
| TEST_MUSTPASS(rtp_rtcp->RegisterRTPObserver(0, rtpObserver)); |
| TEST_MUSTPASS(rtp_rtcp->SetLocalSSRC(0, 7777)); // force send SSRC to 7777 |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(sleepTime); |
| // verify that the new SSRC has been detected by the observer |
| TEST_MUSTPASS(rtpObserver._SSRC != 7777); |
| TEST_MUSTPASS(rtp_rtcp->DeRegisterRTPObserver(0)); |
| ANL(); |
| |
| TEST(GetRTPKeepaliveStatus); |
| unsigned char pt; |
| int dT; |
| TEST_MUSTPASS(!rtp_rtcp->GetRTPKeepaliveStatus(-1, enabled, pt, dT)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTPKeepaliveStatus(0, enabled, pt, dT)); |
| MARK(); // should be off by default |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(pt != 255); |
| TEST_MUSTPASS(dT != 0); |
| ANL(); |
| |
| TEST(SetRTPKeepaliveStatus); |
| // stop send before changing the settings |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| // verify invalid input parameters |
| TEST_MUSTPASS(!rtp_rtcp->SetRTPKeepaliveStatus(-1, true, 0, 15)); |
| MARK(); |
| TEST_MUSTPASS(!rtp_rtcp->SetRTPKeepaliveStatus(0, true, -1, 15)); |
| MARK(); |
| TEST_MUSTPASS(!rtp_rtcp->SetRTPKeepaliveStatus(0, true, 0, 61)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTPKeepaliveStatus(0, enabled, pt, dT)); |
| MARK(); // should still be off |
| TEST_MUSTPASS(enabled != false); |
| // try valid settings |
| TEST_MUSTPASS(rtp_rtcp->SetRTPKeepaliveStatus(0, true, 117)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->GetRTPKeepaliveStatus(0, enabled, pt, dT)); |
| MARK(); // should be on now |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(pt != 117); |
| TEST_MUSTPASS(dT != 15); |
| // change from PT 99 to 121, as 99 is occupied |
| TEST_MUSTPASS(rtp_rtcp->SetRTPKeepaliveStatus(0, true, 121, 3)); |
| MARK(); // on, PT=99, dT=3 |
| TEST_MUSTPASS(rtp_rtcp->GetRTPKeepaliveStatus(0, enabled, pt, dT)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(pt != 121); |
| TEST_MUSTPASS(dT != 3); |
| ANL(); |
| |
| // Make fresh restart (ensures that SSRC is randomized) |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| |
| SLEEP(100); |
| |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| |
| SLEEP(8000); |
| |
| TEST(GetRemoteRTCPData); |
| // Statistics based on received RTCP reports (i.e. statistics on the remote |
| // side sent to us). |
| unsigned int NTPHigh(0), NTPLow(0), timestamp(0), playoutTimestamp(0), |
| jitter(0); |
| unsigned short fractionLost(0); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCPData(0, NTPHigh, NTPLow, |
| timestamp, playoutTimestamp)); |
| TEST_LOG("\n NTPHigh = %u \n NTPLow = %u \n timestamp = %u \n " |
| " playoutTimestamp = %u \n jitter = %u \n fractionLost = %hu \n", |
| NTPHigh, NTPLow, timestamp, playoutTimestamp, jitter, fractionLost); |
| |
| unsigned int NTPHigh2(0), NTPLow2(0), timestamp2(0); |
| unsigned int playoutTimestamp2(0), jitter2(0); |
| unsigned short fractionLost2(0); |
| |
| TEST_LOG("take a new sample and ensure that the playout timestamp is " |
| "maintained"); |
| SLEEP(100); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCPData(0, NTPHigh2, NTPLow2, timestamp2, |
| playoutTimestamp2, &jitter2, |
| &fractionLost2)); |
| TEST_LOG("\n NTPHigh = %u \n NTPLow = %u \n timestamp = %u \n " |
| " playoutTimestamp = %u \n jitter = %u \n fractionLost = %hu \n", |
| NTPHigh2, NTPLow2, timestamp2, playoutTimestamp2, jitter2, fractionLost2); |
| TEST_MUSTPASS(playoutTimestamp != playoutTimestamp2); |
| |
| TEST_LOG("wait for 8 seconds and ensure that the RTCP statistics is" |
| " updated..."); |
| SLEEP(8000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCPData(0, NTPHigh2, NTPLow2, |
| timestamp2, playoutTimestamp2, |
| &jitter2, &fractionLost2)); |
| TEST_LOG("\n NTPHigh = %u \n NTPLow = %u \n timestamp = %u \n " |
| " playoutTimestamp = %u \n jitter = %u \n fractionLost = %hu \n", |
| NTPHigh2, NTPLow2, timestamp2, playoutTimestamp2, jitter2, fractionLost2); |
| TEST_MUSTPASS((NTPHigh == NTPHigh2) && (NTPLow == NTPLow2)); |
| TEST_MUSTPASS(timestamp == timestamp2); |
| TEST_MUSTPASS(playoutTimestamp == playoutTimestamp2); |
| |
| #ifdef WEBRTC_CODEC_RED |
| //The following test is related to defect 4985 and 4986 |
| TEST_LOG("Turn FEC and VAD on and wait for 4 seconds and ensure that " |
| "the jitter is still small..."); |
| CodecInst cinst; |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| cinst.pltype = 104; |
| strcpy(cinst.plname, "isac"); |
| cinst.plfreq = 32000; |
| cinst.pacsize = 960; |
| cinst.channels = 1; |
| cinst.rate = 45000; |
| #else |
| cinst.pltype = 119; |
| strcpy(cinst.plname, "isaclc"); |
| cinst.plfreq = 16000; |
| cinst.pacsize = 320; |
| cinst.channels = 1; |
| cinst.rate = 40000; |
| #endif |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| TEST_MUSTPASS(codec->SetSendCodec(0, cinst)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(rtp_rtcp->SetFECStatus(0, true, -1)); |
| MARK(); |
| TEST_MUSTPASS(codec->SetVADStatus(0,true)); |
| SLEEP(4000); |
| TEST_MUSTPASS(rtp_rtcp->GetRemoteRTCPData(0, NTPHigh2, NTPLow2, timestamp2, |
| playoutTimestamp2, &jitter2, |
| &fractionLost2)); |
| TEST_LOG("\n NTPHigh = %u \n NTPLow = %u \n timestamp = %u \n " |
| " playoutTimestamp = %u \n jitter = %u \n fractionLost = %hu \n", |
| NTPHigh2, NTPLow2, timestamp2, playoutTimestamp2, jitter2, fractionLost2); |
| TEST_MUSTPASS(jitter2 > 1000) |
| TEST_MUSTPASS(rtp_rtcp->SetFECStatus(0, false)); |
| MARK(); |
| //4985 and 4986 end |
| #endif // #ifdef WEBRTC_CODEC_RED |
| TEST(GetRTPStatistics); |
| ANL(); |
| // Statistics summarized on local side based on received RTP packets. |
| CallStatistics stats; |
| // Call GetRTPStatistics over a longer period than 7.5 seconds |
| // (=dT RTCP transmissions). |
| unsigned int averageJitterMs, maxJitterMs, discardedPackets; |
| SLEEP(1000); |
| for (i = 0; i < 8; i++) { |
| TEST_MUSTPASS(rtp_rtcp->GetRTPStatistics(0, averageJitterMs, |
| maxJitterMs, |
| discardedPackets)); |
| TEST_LOG(" %i) averageJitterMs = %u \n maxJitterMs = %u \n " |
| " discardedPackets = %u \n", i, averageJitterMs, maxJitterMs, |
| discardedPackets); |
| SLEEP(1000); |
| } |
| |
| TEST(RTCPStatistics #1); |
| ANL(); |
| unsigned int packetsSent(0); |
| unsigned int packetsReceived(0); |
| for (i = 0; i < 8; i++) |
| { |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatistics(0, stats)); |
| TEST_LOG(" %i) fractionLost = %hu \n cumulativeLost = %u \n " |
| " extendedMax = %u \n jitterSamples = %u \n rttMs = %d \n", |
| i, stats.fractionLost, stats.cumulativeLost, |
| stats.extendedMax, stats.jitterSamples, stats.rttMs); |
| TEST_LOG( " bytesSent = %d \n packetsSent = %d \n " |
| " bytesReceived = %d \n packetsReceived = %d \n", |
| stats.bytesSent, stats.packetsSent, stats.bytesReceived, |
| stats.packetsReceived); |
| if (i > 0) |
| { |
| TEST_LOG(" diff sent packets : %u (~50)\n", |
| stats.packetsSent - packetsSent); |
| TEST_LOG(" diff received packets: %u (~50)\n", |
| stats.packetsReceived - packetsReceived); |
| } |
| packetsSent = stats.packetsSent; |
| packetsReceived = stats.packetsReceived; |
| SLEEP(1000); |
| } |
| |
| TEST(RTCPStatistics #2); |
| ANL(); |
| TEST_LOG("restart sending and ensure that the statistics is reset"); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| SLEEP(50); // ensures approx. two received packets |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatistics(0, stats)); |
| TEST_LOG("\n fractionLost = %hu \n cumulativeLost = %u \n " |
| " extendedMax = %u \n jitterSamples = %u \n rttMs = %d \n", |
| stats.fractionLost, stats.cumulativeLost, |
| stats.extendedMax, stats.jitterSamples, stats.rttMs); |
| TEST_LOG( " bytesSent = %d \n packetsSent = %d \n " |
| " bytesReceived = %d \n packetsReceived = %d \n", |
| stats.bytesSent, stats.packetsSent, stats.bytesReceived, |
| stats.packetsReceived); |
| |
| TEST(RTCPStatistics #3); |
| ANL(); |
| TEST_LOG("disable RTCP and verify that statistics is not corrupt"); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCPStatus(0, false)); |
| SLEEP(250); |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatistics(0, stats)); |
| TEST_LOG("\n fractionLost = %hu \n cumulativeLost = %u \n " |
| " extendedMax = %u \n jitterSamples = %u \n rttMs = %d \n", |
| stats.fractionLost, stats.cumulativeLost, |
| stats.extendedMax, stats.jitterSamples, stats.rttMs); |
| TEST_LOG(" bytesSent = %d \n packetsSent = %d \n " |
| "bytesReceived = %d \n packetsReceived = %d \n", |
| stats.bytesSent, stats.packetsSent, |
| stats.bytesReceived, stats.packetsReceived); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCPStatus(0, true)); |
| |
| TEST(RTCPStatistics #4); |
| ANL(); |
| TEST_LOG("restart receiving and check RX statistics"); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| SLEEP(50); // ensures approx. two received packets |
| TEST_MUSTPASS(rtp_rtcp->GetRTCPStatistics(0, stats)); |
| TEST_LOG("\n fractionLost = %hu \n cumulativeLost = %u \n " |
| " extendedMax = %u \n jitterSamples = %u \n rttMs = %d \n", |
| stats.fractionLost, stats.cumulativeLost, |
| stats.extendedMax, stats.jitterSamples, |
| stats.rttMs); |
| TEST_LOG(" bytesSent = %d \n packetsSent = %d \n " |
| " bytesReceived = %d \n packetsReceived = %d \n", |
| stats.bytesSent, stats.packetsSent, |
| stats.bytesReceived, stats.packetsReceived); |
| |
| TEST(SendApplicationDefinedRTCPPacket); |
| // just do some fail tests here |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| // should fail since sending is off |
| TEST_MUSTPASS(!rtp_rtcp->SendApplicationDefinedRTCPPacket( |
| 0, 0, 0, "abcdabcdabcdabcdabcdabcdabcdabcd", 32)); |
| MARK(); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_MUSTPASS(rtp_rtcp->SendApplicationDefinedRTCPPacket( |
| 0, 0, 0, "abcdabcdabcdabcdabcdabcdabcdabcd", 32)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCPStatus(0, false)); |
| // should fail since RTCP is off |
| TEST_MUSTPASS(!rtp_rtcp->SendApplicationDefinedRTCPPacket( |
| 0, 0, 0, "abcdabcdabcdabcdabcdabcdabcdabcd", 32)); |
| MARK(); |
| TEST_MUSTPASS(rtp_rtcp->SetRTCPStatus(0, true)); |
| TEST_MUSTPASS(rtp_rtcp->SendApplicationDefinedRTCPPacket( |
| 0, 0, 0, "abcdabcdabcdabcdabcdabcdabcdabcd", 32)); |
| MARK(); |
| // invalid data length |
| TEST_MUSTPASS(!rtp_rtcp->SendApplicationDefinedRTCPPacket( |
| 0, 0, 0, "abcdabcdabcdabcdabcdabcdabcdabc", 31)); |
| MARK(); |
| // invalid data vector |
| TEST_MUSTPASS(!rtp_rtcp->SendApplicationDefinedRTCPPacket(0, 0, 0, NULL, 0)); |
| MARK(); |
| ANL(); |
| |
| #ifdef WEBRTC_CODEC_RED |
| TEST(SetFECStatus); |
| ANL(); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| cinst.pltype = 126; |
| strcpy(cinst.plname, "red"); |
| cinst.plfreq = 8000; |
| cinst.pacsize = 0; |
| cinst.channels = 1; |
| cinst.rate = 0; |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| cinst.pltype = 104; |
| strcpy(cinst.plname, "isac"); |
| cinst.plfreq = 32000; |
| cinst.pacsize = 960; |
| cinst.channels = 1; |
| cinst.rate = 45000; |
| #else |
| cinst.pltype = 119; |
| strcpy(cinst.plname, "isaclc"); |
| cinst.plfreq = 16000; |
| cinst.pacsize = 320; |
| cinst.channels = 1; |
| cinst.rate = 40000; |
| #endif |
| // We have to re-register the audio codec payload type as stopReceive will |
| // clean the database |
| TEST_MUSTPASS(codec->SetRecPayloadType(0, cinst)); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 8000)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 8000, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| TEST_LOG("Start playing a file as microphone again \n"); |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| TEST_MUSTPASS(rtp_rtcp->SetFECStatus(0, true, 126)); |
| MARK(); |
| TEST_LOG("Should sound OK with FEC enabled\n"); |
| SLEEP(4000); |
| TEST_MUSTPASS(rtp_rtcp->SetFECStatus(0, false)); |
| MARK(); |
| #endif // #ifdef WEBRTC_CODEC_RED |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| ANL(); |
| AOK(); |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestVideoSync |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestVideoSync() |
| { |
| PrepareTest("VideoSync"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEVideoSync* vsync = _mgr.VideoSyncPtr(); |
| |
| // check if this interface is supported |
| if (!vsync) |
| { |
| TEST_LOG("VoEVideoSync is not supported!"); |
| return -1; |
| } |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename( |
| "VoEVideoSync_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| TEST(SetInitTimestamp); |
| ANL(); |
| TEST_MUSTPASS(!vsync->SetInitTimestamp(0, 12345)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(vsync->SetInitTimestamp(0, 12345)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| MARK(); |
| SLEEP(1000); |
| AOK(); |
| ANL(); |
| |
| TEST(SetInitSequenceNumber); |
| ANL(); |
| TEST_MUSTPASS(!vsync->SetInitSequenceNumber(0, 123)); |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| MARK(); |
| SLEEP(1000); |
| TEST_MUSTPASS(vsync->SetInitSequenceNumber(0, 123)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| MARK(); |
| SLEEP(1000); |
| AOK(); |
| ANL(); |
| |
| unsigned int timeStamp; |
| TEST(GetPlayoutTimestamp); |
| ANL(); |
| TEST_MUSTPASS(vsync->GetPlayoutTimestamp(0, timeStamp)); |
| TEST_LOG("GetPlayoutTimestamp: %u", timeStamp); |
| SLEEP(1000); |
| TEST_MUSTPASS(vsync->GetPlayoutTimestamp(0, timeStamp)); |
| TEST_LOG(" %u", timeStamp); |
| SLEEP(1000); |
| TEST_MUSTPASS(vsync->GetPlayoutTimestamp(0, timeStamp)); |
| TEST_LOG(" %u\n", timeStamp); |
| AOK(); |
| ANL(); |
| |
| TEST(SetMinimumPlayoutDelay); |
| ANL(); |
| TEST_MUSTPASS(!vsync->SetMinimumPlayoutDelay(0, -1)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| TEST_MUSTPASS(!vsync->SetMinimumPlayoutDelay(0, 5000)); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| MARK(); |
| |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| AOK(); |
| ANL(); |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestVolumeControl |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestVolumeControl() |
| { |
| PrepareTest("TestVolumeControl"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEVolumeControl* volume = _mgr.VolumeControlPtr(); |
| #ifdef _TEST_FILE_ |
| VoEFile* file = _mgr.FilePtr(); |
| #endif |
| #ifdef _TEST_HARDWARE_ |
| VoEHardware* hardware = _mgr.HardwarePtr(); |
| #endif |
| |
| #ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile( |
| GetFilename("VoEVolumeControl_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| #endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| #if (defined _TEST_HARDWARE_ && (!defined(MAC_IPHONE) && \ |
| !defined(WEBRTC_ANDROID))) |
| #if defined(_WIN32) |
| TEST_MUSTPASS(hardware->SetRecordingDevice(-1)); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(-1)); |
| #else |
| TEST_MUSTPASS(hardware->SetRecordingDevice(0)); |
| TEST_MUSTPASS(hardware->SetPlayoutDevice(0)); |
| #endif |
| #endif |
| TEST_MUSTPASS(voe_base_->SetLocalReceiver(0, 12345)); |
| TEST_MUSTPASS(voe_base_->SetSendDestination(0, 12345, "127.0.0.1")); |
| TEST_MUSTPASS(voe_base_->StartReceive(0)); |
| TEST_MUSTPASS(voe_base_->StartPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StartSend(0)); |
| #ifdef _TEST_FILE_ |
| TEST_MUSTPASS(file->StartPlayingFileAsMicrophone(0, _mgr.AudioFilename(), |
| true, true)); |
| #endif |
| |
| //////////////////////////// |
| // Actual test starts here |
| |
| #if !defined(MAC_IPHONE) |
| TEST(SetSpeakerVolume); |
| ANL(); |
| TEST_MUSTPASS(-1 != volume->SetSpeakerVolume(256)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| ANL(); |
| #endif // #if !defined(MAC_IPHONE) |
| |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| TEST(SetMicVolume); ANL(); |
| TEST_MUSTPASS(-1 != volume->SetMicVolume(256)); MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| ANL(); |
| #endif // #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| |
| #if !defined(MAC_IPHONE) |
| TEST(SetChannelOutputVolumeScaling); |
| ANL(); |
| TEST_MUSTPASS(-1 != volume->SetChannelOutputVolumeScaling(0, (float)-0.1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetChannelOutputVolumeScaling(0, (float)10.1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| ANL(); |
| #endif // #if !defined(MAC_IPHONE) |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| TEST(SetOutputVolumePan); |
| ANL(); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(-1, (float)-0.1, |
| (float)1.0)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(-1, (float)1.1, |
| (float)1.0)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(-1, (float)1.0, |
| (float)-0.1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(-1, (float)1.0, |
| (float)1.1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| ANL(); |
| |
| TEST(SetChannelOutputVolumePan); |
| ANL(); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(0, (float)-0.1, |
| (float)1.0)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(0, (float)1.1, |
| (float)1.0)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(0, (float)1.0, |
| (float)-0.1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| TEST_MUSTPASS(-1 != volume->SetOutputVolumePan(0, (float)1.0, |
| (float)1.1)); |
| MARK(); |
| TEST_MUSTPASS(VE_INVALID_ARGUMENT != voe_base_->LastError()); |
| ANL(); |
| #endif // #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| #ifdef _TEST_FILE_ |
| TEST_MUSTPASS(file->StopPlayingFileAsMicrophone(0)); |
| #endif |
| TEST_MUSTPASS(voe_base_->StopSend(0)); |
| TEST_MUSTPASS(voe_base_->StopPlayout(0)); |
| TEST_MUSTPASS(voe_base_->StopReceive(0)); |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| AOK(); |
| ANL(); |
| return 0; |
| } |
| |
| // ---------------------------------------------------------------------------- |
| // VoEExtendedTest::TestAPM |
| // ---------------------------------------------------------------------------- |
| |
| int VoEExtendedTest::TestAPM() { |
| PrepareTest("AudioProcessing"); |
| |
| VoEBase* voe_base_ = _mgr.BasePtr(); |
| VoEAudioProcessing* apm = _mgr.APMPtr(); |
| |
| //#ifdef _USE_EXTENDED_TRACE_ |
| TEST_MUSTPASS(VoiceEngine::SetTraceFile(GetFilename("apm_trace.txt"))); |
| TEST_MUSTPASS(VoiceEngine::SetTraceFilter(kTraceStateInfo | |
| kTraceStateInfo | |
| kTraceWarning | |
| kTraceError | |
| kTraceCritical | |
| kTraceApiCall | |
| kTraceMemory | |
| kTraceInfo)); |
| //#endif |
| |
| TEST_MUSTPASS(voe_base_->Init()); |
| TEST_MUSTPASS(voe_base_->CreateChannel()); |
| |
| /////////////////////////// |
| // Actual test starts here |
| |
| int i; |
| bool enabled; |
| |
| ////// |
| // EC |
| |
| const int ECSleep = 0; |
| const int ECIterations = 10; |
| |
| EcModes ECmode(kEcAec); |
| AecmModes AECMmode(kAecmSpeakerphone); |
| bool enabledCNG(false); |
| |
| #if (defined(MAC_IPHONE) || defined(WEBRTC_ANDROID)) |
| const EcModes ECmodeDefault(kEcAecm); |
| #else |
| const EcModes ECmodeDefault(kEcAec); |
| #endif |
| |
| // verify default settings (should be OFF and mode as above) |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(ECmode != ECmodeDefault); |
| |
| // set EC defaults |
| TEST_MUSTPASS(apm->SetEcStatus(false, kEcDefault)); |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(ECmode != ECmodeDefault); |
| SLEEP(ECSleep); |
| |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| // set kEcAec mode |
| TEST_MUSTPASS(apm->SetEcStatus(true, kEcAec)); |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(ECmode != kEcAec); |
| SLEEP(ECSleep); |
| |
| // set kEcConference mode |
| TEST_MUSTPASS(apm->SetEcStatus(true, kEcConference)); |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(ECmode != kEcAec); |
| SLEEP(ECSleep); |
| #endif // #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| // get default AECM mode, should the kAecmSpeakerphone as default |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_MUSTPASS(AECMmode != kAecmSpeakerphone); |
| TEST_MUSTPASS(enabledCNG != true); |
| TEST_MUSTPASS(apm->SetAecmMode(kAecmQuietEarpieceOrHeadset, false)); |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_LOG("AECM: mode=%d, CNG: mode=%d\n", AECMmode, |
| enabledCNG); |
| TEST_MUSTPASS(AECMmode != kAecmQuietEarpieceOrHeadset); |
| TEST_MUSTPASS(enabledCNG != false); |
| |
| // set kEcAecm mode |
| TEST_MUSTPASS(apm->SetEcStatus(true, kEcAecm)); |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != true); |
| TEST_MUSTPASS(ECmode != kEcAecm); |
| SLEEP(ECSleep); |
| |
| // AECM mode, get and set |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_MUSTPASS(AECMmode != kAecmQuietEarpieceOrHeadset); |
| TEST_MUSTPASS(enabledCNG != false); |
| TEST_MUSTPASS(apm->SetAecmMode(kAecmEarpiece, true)); |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_LOG("AECM: mode=%d, CNG: mode=%d\n", AECMmode, |
| enabledCNG); |
| TEST_MUSTPASS(AECMmode != kAecmEarpiece); |
| TEST_MUSTPASS(enabledCNG != true); |
| TEST_MUSTPASS(apm->SetAecmMode(kAecmEarpiece, false)); |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_LOG("AECM: mode=%d, CNG: mode=%d\n", AECMmode, |
| enabledCNG); |
| TEST_MUSTPASS(AECMmode != kAecmEarpiece); |
| TEST_MUSTPASS(enabledCNG != false); |
| TEST_MUSTPASS(apm->SetAecmMode(kAecmLoudEarpiece, true)); |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_LOG("AECM: mode=%d, CNG: mode=%d\n", AECMmode, |
| enabledCNG); |
| TEST_MUSTPASS(AECMmode != kAecmLoudEarpiece); |
| TEST_MUSTPASS(enabledCNG != true); |
| TEST_MUSTPASS(apm->SetAecmMode(kAecmSpeakerphone, false)); |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_LOG("AECM: mode=%d, CNG: mode=%d\n", AECMmode, |
| enabledCNG); |
| TEST_MUSTPASS(AECMmode != kAecmSpeakerphone); |
| TEST_MUSTPASS(enabledCNG != false); |
| TEST_MUSTPASS(apm->SetAecmMode(kAecmLoudSpeakerphone, true)); |
| TEST_MUSTPASS(apm->GetAecmMode(AECMmode, enabledCNG)); |
| TEST_LOG("AECM: mode=%d, CNG: mode=%d\n", AECMmode, |
| enabledCNG); |
| TEST_MUSTPASS(AECMmode != kAecmLoudSpeakerphone); |
| TEST_MUSTPASS(enabledCNG != true); |
| |
| // verify that all modes are maintained when EC is disabled |
| TEST_MUSTPASS(apm->SetEcStatus(false)); |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(ECmode != kEcAecm); |
| SLEEP(ECSleep); |
| |
| // restore defaults |
| TEST_MUSTPASS(apm->SetEcStatus(true, kEcDefault)); |
| TEST_MUSTPASS(apm->SetEcStatus(false, kEcUnchanged)); |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(ECmode != ECmodeDefault); |
| SLEEP(ECSleep); |
| |
| // enable/disable many times in a row |
| for (i = 0; i < ECIterations; i++) { |
| TEST_MUSTPASS(apm->SetEcStatus(true)); |
| TEST_MUSTPASS(apm->SetEcStatus(false)); |
| } |
| TEST_MUSTPASS(apm->GetEcStatus(enabled, ECmode)); |
| TEST_LOG("EC: enabled=%d, ECmode=%d\n", enabled, ECmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(ECmode != ECmodeDefault); |
| SLEEP(ECSleep); |
| |
| /////// |
| // AGC |
| |
| const int AGCSleep = 0; |
| const int AGCIterations = 10; |
| |
| AgcModes AGCmode(kAgcAdaptiveAnalog); |
| |
| #if (defined(MAC_IPHONE) || defined(WEBRTC_ANDROID)) |
| bool enabledDefault = false; |
| AgcModes AGCmodeDefault(kAgcAdaptiveDigital); |
| #else |
| bool enabledDefault = true; |
| AgcModes AGCmodeDefault(kAgcAdaptiveAnalog); |
| #endif |
| |
| // verify default settings (should be as above) |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(enabled != enabledDefault); |
| TEST_MUSTPASS(AGCmode != AGCmodeDefault); |
| |
| // set default AGC mode |
| TEST_MUSTPASS(apm->SetAgcStatus(false, kAgcDefault)); |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(AGCmode != AGCmodeDefault); |
| SLEEP(AGCSleep); |
| |
| // set kAgcFixedDigital mode |
| TEST_MUSTPASS(apm->SetAgcStatus(true, kAgcFixedDigital)); |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(AGCmode != kAgcFixedDigital); |
| SLEEP(AGCSleep); |
| |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| // set kAgcAdaptiveAnalog mode |
| TEST_MUSTPASS(apm->SetAgcStatus(true, kAgcAdaptiveAnalog)); |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(AGCmode != kAgcAdaptiveAnalog); |
| SLEEP(AGCSleep); |
| #endif // #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| // set kAgcAdaptiveDigital mode |
| TEST_MUSTPASS(apm->SetAgcStatus(true, kAgcAdaptiveDigital)); |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(AGCmode != kAgcAdaptiveDigital); |
| SLEEP(AGCSleep); |
| |
| // verify that mode is maintained when AGC is disabled |
| TEST_MUSTPASS(apm->SetAgcStatus(false)); |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(AGCmode != kAgcAdaptiveDigital); |
| SLEEP(AGCSleep); |
| |
| // restore default AGC |
| TEST_MUSTPASS(apm->SetAgcStatus(enabledDefault, kAgcDefault)); |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(enabled != enabledDefault); |
| TEST_MUSTPASS(AGCmode != AGCmodeDefault); |
| SLEEP(AGCSleep); |
| |
| // enable/disable many times in a row |
| for (i = 0; i < AGCIterations; i++) |
| { |
| TEST_MUSTPASS(apm->SetAgcStatus(true)); |
| TEST_MUSTPASS(apm->SetAgcStatus(false)); |
| } |
| TEST_MUSTPASS(apm->GetAgcStatus(enabled, AGCmode)); |
| TEST_LOG("AGC: enabled=%d, AGCmode=%d\n", enabled, AGCmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(AGCmode != AGCmodeDefault); |
| |
| // --- Set/AGCConfig -- |
| |
| // |
| // targetLeveldBOv : [0, 31] (default 3) |
| // digitalCompressionGaindB: [0, 90] (default 9) |
| // limiterEnable : 0: Off, 1: On (default) |
| |
| AgcConfig agcConfig; |
| AgcConfig agcConfigDefault; |
| |
| const unsigned short targetLeveldBOvDefault = 3; |
| const unsigned short digitalCompressionGaindBDefault = 9; |
| const bool limiterEnableDefault = true; |
| |
| const unsigned short targetLeveldBOvMax = 31; |
| const unsigned short digitalCompressionGaindBMax = 90; |
| |
| // verify default configuration |
| TEST_MUSTPASS(apm->GetAgcConfig(agcConfigDefault)); |
| TEST_LOG("AGC: targetLeveldBOv=%d, digitalCompressionGaindB=%d, " |
| "limiterEnable=%d\n", |
| agcConfigDefault.targetLeveldBOv, |
| agcConfigDefault.digitalCompressionGaindB, |
| agcConfigDefault.limiterEnable); |
| TEST_MUSTPASS(agcConfigDefault.targetLeveldBOv != targetLeveldBOvDefault); |
| TEST_MUSTPASS(agcConfigDefault.digitalCompressionGaindB != |
| digitalCompressionGaindBDefault); |
| TEST_MUSTPASS(agcConfigDefault.limiterEnable != limiterEnableDefault); |
| |
| // verify that invalid (out-of-range) parameters are detected |
| agcConfig = agcConfigDefault; |
| agcConfig.targetLeveldBOv = targetLeveldBOvMax + 1; |
| TEST_MUSTPASS(!apm->SetAgcConfig(agcConfig)); |
| int err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_APM_ERROR); |
| agcConfig = agcConfigDefault; |
| agcConfig.digitalCompressionGaindB |
| = digitalCompressionGaindBMax + 1; |
| TEST_MUSTPASS(!apm->SetAgcConfig(agcConfig)); |
| |
| AgcConfig agcConfigSet; |
| agcConfigSet.digitalCompressionGaindB = 17; |
| agcConfigSet.targetLeveldBOv = 11; |
| agcConfigSet.limiterEnable = false; |
| |
| // try some set/get operations using valid settings |
| TEST_MUSTPASS(apm->SetAgcConfig(agcConfigDefault)); |
| TEST_MUSTPASS(apm->GetAgcConfig(agcConfig)); |
| TEST_MUSTPASS(agcConfig.targetLeveldBOv != targetLeveldBOvDefault); |
| TEST_MUSTPASS(agcConfig.digitalCompressionGaindB != |
| digitalCompressionGaindBDefault); |
| TEST_MUSTPASS(agcConfig.limiterEnable != limiterEnableDefault); |
| |
| TEST_MUSTPASS(apm->SetAgcConfig(agcConfigSet)); |
| TEST_MUSTPASS(apm->GetAgcConfig(agcConfig)); |
| TEST_MUSTPASS(agcConfig.targetLeveldBOv != agcConfigSet.targetLeveldBOv); |
| TEST_MUSTPASS(agcConfig.digitalCompressionGaindB != |
| agcConfigSet.digitalCompressionGaindB); |
| TEST_MUSTPASS(agcConfig.limiterEnable != agcConfigSet.limiterEnable); |
| |
| // restore default AGC config |
| TEST_MUSTPASS(apm->SetAgcConfig(agcConfigDefault)); |
| SLEEP(AGCSleep); |
| |
| ////// |
| // NS |
| |
| const int NSSleep = 0; |
| const int NSIterations = 10; |
| |
| NsModes NSmode(kNsHighSuppression); |
| NsModes NSmodeDefault(kNsModerateSuppression); |
| |
| // verify default settings (should be OFF and mode as above) |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(NSmode != NSmodeDefault); |
| |
| // enable default NS settings |
| // must set a value first time! |
| TEST_MUSTPASS(apm->SetNsStatus(false, kNsDefault)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(NSmode != NSmodeDefault); |
| SLEEP(NSSleep); |
| |
| // set kNsLowSuppression mode |
| TEST_MUSTPASS(apm->SetNsStatus(true, kNsLowSuppression)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(NSmode != kNsLowSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsModerateSuppression mode |
| TEST_MUSTPASS(apm->SetNsStatus(true, kNsModerateSuppression)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(NSmode != kNsModerateSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsHighSuppression mode |
| TEST_MUSTPASS(apm->SetNsStatus(true, kNsHighSuppression)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(NSmode != kNsHighSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsVeryHighSuppression mode |
| TEST_MUSTPASS(apm->SetNsStatus(true, kNsVeryHighSuppression)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(NSmode != kNsVeryHighSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsVeryHighSuppression mode |
| TEST_MUSTPASS(apm->SetNsStatus(true, kNsConference)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(NSmode != kNsHighSuppression); |
| SLEEP(NSSleep); |
| |
| // verify that mode is maintained when NS is disabled |
| TEST_MUSTPASS(apm->SetNsStatus(false)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(NSmode != kNsHighSuppression); |
| SLEEP(NSSleep); |
| |
| // restore default NS |
| TEST_MUSTPASS(apm->SetNsStatus(true, kNsDefault)); |
| TEST_MUSTPASS(apm->SetNsStatus(false)); |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(NSmode != NSmodeDefault); |
| SLEEP(NSSleep); |
| |
| // enable/disable many times in a row |
| for (i = 0; i < NSIterations; i++) { |
| TEST_MUSTPASS(apm->SetNsStatus(true)); |
| TEST_MUSTPASS(apm->SetNsStatus(false)); |
| } |
| TEST_MUSTPASS(apm->GetNsStatus(enabled, NSmode)); |
| TEST_LOG("NS: enabled=%d, NSmode=%d\n", enabled, NSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(NSmode != NSmodeDefault); |
| SLEEP(NSSleep); |
| |
| ////////////////////////////////// |
| // Ec Metrics |
| |
| #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| TEST(GetEcMetricsStatus); |
| ANL(); |
| TEST(SetEcMetricsStatus); |
| ANL(); |
| TEST_MUSTPASS(apm->GetEcMetricsStatus(enabled)); |
| MARK(); |
| TEST_MUSTPASS(enabled != false); |
| MARK(); // should be OFF by default |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(true)); |
| MARK(); |
| TEST_MUSTPASS(apm->GetEcMetricsStatus(enabled)); |
| MARK(); |
| TEST_MUSTPASS(enabled != true); |
| MARK(); |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(false)); |
| MARK(); |
| TEST_MUSTPASS(apm->GetEcMetricsStatus(enabled)); |
| MARK(); |
| TEST_MUSTPASS(enabled != false); |
| MARK(); |
| AOK(); |
| ANL(); |
| |
| TEST(GetEchoMetrics); |
| ANL(); |
| |
| int ERL, ERLE, RERL, A_NLP; |
| TEST_MUSTPASS(-1 != apm->GetEchoMetrics(ERL, ERLE, RERL, A_NLP)); |
| MARK(); // Should fail since not activated. |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_APM_ERROR); |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(true)); |
| TEST_MUSTPASS(-1 != apm->GetEchoMetrics(ERL, ERLE, RERL, A_NLP)); |
| MARK(); // Should fail since AEC is off. |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_APM_ERROR); |
| TEST_MUSTPASS(apm->SetEcStatus(true)); |
| TEST_MUSTPASS(apm->GetEchoMetrics(ERL, ERLE, RERL, A_NLP)); |
| MARK(); // Should work now. |
| TEST_LOG("\nEcho: ERL=%d, ERLE=%d, RERL=%d, A_NLP=%d [dB]\n", |
| ERL, ERLE, RERL, A_NLP); |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(false)); |
| TEST_MUSTPASS(apm->SetEcStatus(false)); |
| AOK(); |
| ANL(); |
| |
| TEST(GetEcDelayMetrics); |
| ANL(); |
| |
| int delay_median = 0; |
| int delay_std = 0; |
| TEST_MUSTPASS(-1 != apm->GetEcDelayMetrics(delay_median, delay_std)); |
| MARK(); // Should fail since not activated. |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_APM_ERROR); |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(true)); |
| TEST_MUSTPASS(-1 != apm->GetEcDelayMetrics(delay_median, delay_std)); |
| MARK(); // Should fail since AEC is off. |
| err = voe_base_->LastError(); |
| TEST_MUSTPASS(err != VE_APM_ERROR); |
| TEST_MUSTPASS(apm->SetEcStatus(true)); |
| TEST_MUSTPASS(apm->GetEcDelayMetrics(delay_median, delay_std)); |
| MARK(); // Should work now. |
| TEST_LOG("\nEC Delay: median=%d, std=%d [ms]\n", delay_median, delay_std); |
| TEST_MUSTPASS(apm->SetEcMetricsStatus(false)); |
| TEST_MUSTPASS(apm->SetEcStatus(false)); |
| AOK(); |
| ANL(); |
| |
| #endif // #if (!defined(MAC_IPHONE) && !defined(WEBRTC_ANDROID)) |
| // far-end AudioProcessing |
| /////// |
| // AGC |
| |
| AgcModes rxAGCmode(kAgcAdaptiveDigital); |
| AgcModes rxAGCmodeDefault(kAgcAdaptiveDigital); |
| bool rxEnabledDefault = false; |
| |
| // verify default settings (should be as above) |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(enabled != rxEnabledDefault); |
| TEST_MUSTPASS(rxAGCmode != rxAGCmodeDefault); |
| |
| // set default AGC mode |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, false, kAgcDefault)); |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxAGCmode != rxAGCmodeDefault); |
| SLEEP(AGCSleep); |
| |
| // set kAgcAdaptiveAnalog mode, should fail |
| TEST_MUSTPASS(!apm->SetRxAgcStatus(0, true, kAgcAdaptiveAnalog)); |
| |
| // set kAgcFixedDigital mode |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, true, kAgcFixedDigital)); |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(rxAGCmode != kAgcFixedDigital); |
| SLEEP(AGCSleep); |
| |
| // set kAgcAdaptiveDigital mode |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, true, kAgcAdaptiveDigital)); |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(rxAGCmode != kAgcAdaptiveDigital); |
| SLEEP(AGCSleep); |
| |
| // verify that mode is maintained when AGC is disabled |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, false)); |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxAGCmode != kAgcAdaptiveDigital); |
| SLEEP(AGCSleep); |
| |
| // restore default AGC |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, enabledDefault, kAgcDefault)); |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(enabled != enabledDefault); |
| TEST_MUSTPASS(rxAGCmode != rxAGCmodeDefault); |
| SLEEP(AGCSleep); |
| |
| // enable/disable many times in a row |
| for (i = 0; i < AGCIterations; i++) { |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, true)); |
| TEST_MUSTPASS(apm->SetRxAgcStatus(0, false)); |
| } |
| TEST_MUSTPASS(apm->GetRxAgcStatus(0, enabled, rxAGCmode)); |
| TEST_LOG("rxAGC: enabled=%d, AGCmode=%d\n", enabled, |
| rxAGCmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxAGCmode != rxAGCmodeDefault); |
| |
| // --- Set/GetAgcConfig -- |
| |
| |
| // targetLeveldBOv : [0, 31] (default 3) |
| // digitalCompressionGaindB: [0, 90] (default 9) |
| // limiterEnable : 0: Off, 1: On (default) |
| |
| AgcConfig rxAGCConfig; |
| AgcConfig rxAGCConfigDefault; |
| |
| const unsigned short rxTargetLeveldBOvDefault = 3; |
| const unsigned short rxDigitalCompressionGaindBDefault = 9; |
| const bool rxLimiterEnableDefault = true; |
| |
| const unsigned short rxTargetLeveldBOvMax = 31; |
| const unsigned short rxDigitalCompressionGaindBMax = 90; |
| |
| // verify default configuration |
| TEST_MUSTPASS(apm->GetRxAgcConfig(0, rxAGCConfigDefault)); |
| TEST_LOG( |
| "rxAGC: targetLeveldBOv=%u, digitalCompressionGaindB=%u, " |
| "limiterEnable=%d\n", |
| rxAGCConfigDefault.targetLeveldBOv, |
| rxAGCConfigDefault.digitalCompressionGaindB, |
| rxAGCConfigDefault.limiterEnable); |
| TEST_MUSTPASS(rxAGCConfigDefault.targetLeveldBOv != |
| rxTargetLeveldBOvDefault); |
| TEST_MUSTPASS(rxAGCConfigDefault.digitalCompressionGaindB != |
| rxDigitalCompressionGaindBDefault); |
| TEST_MUSTPASS(rxAGCConfigDefault.limiterEnable != rxLimiterEnableDefault); |
| |
| // verify that invalid (out-of-range) parameters are detected |
| rxAGCConfig = rxAGCConfigDefault; |
| rxAGCConfig.targetLeveldBOv = rxTargetLeveldBOvMax + 1; |
| TEST_MUSTPASS(!apm->SetRxAgcConfig(0, rxAGCConfig)); |
| int rxErr = voe_base_->LastError(); |
| TEST_MUSTPASS(rxErr != VE_APM_ERROR); |
| rxAGCConfig = rxAGCConfigDefault; |
| rxAGCConfig.digitalCompressionGaindB |
| = rxDigitalCompressionGaindBMax + 1; |
| TEST_MUSTPASS(!apm->SetRxAgcConfig(0, rxAGCConfig)); |
| |
| AgcConfig rxAGCConfigSet; |
| rxAGCConfigSet.digitalCompressionGaindB = 17; |
| rxAGCConfigSet.targetLeveldBOv = 11; |
| rxAGCConfigSet.limiterEnable = false; |
| |
| // try some set/get operations using valid settings |
| TEST_MUSTPASS(apm->SetRxAgcConfig(0, rxAGCConfigDefault)); |
| TEST_MUSTPASS(apm->GetRxAgcConfig(0, rxAGCConfig)); |
| TEST_MUSTPASS(rxAGCConfig.targetLeveldBOv != rxTargetLeveldBOvDefault); |
| TEST_MUSTPASS(rxAGCConfig.digitalCompressionGaindB != |
| rxDigitalCompressionGaindBDefault); |
| TEST_MUSTPASS(rxAGCConfig.limiterEnable != rxLimiterEnableDefault); |
| |
| TEST_MUSTPASS(apm->SetRxAgcConfig(0, rxAGCConfigSet)); |
| TEST_MUSTPASS(apm->GetRxAgcConfig(0, rxAGCConfig)); |
| TEST_MUSTPASS(rxAGCConfig.targetLeveldBOv != |
| rxAGCConfigSet.targetLeveldBOv); |
| TEST_MUSTPASS(rxAGCConfig.digitalCompressionGaindB != |
| rxAGCConfigSet.digitalCompressionGaindB); |
| TEST_MUSTPASS(rxAGCConfig.limiterEnable != rxAGCConfigSet.limiterEnable); |
| |
| // restore default AGC config |
| TEST_MUSTPASS(apm->SetRxAgcConfig(0, rxAGCConfigDefault)); |
| SLEEP(AGCSleep); |
| |
| ////// |
| // NS |
| |
| NsModes rxNSmode(kNsHighSuppression); |
| NsModes rxNSmodeDefault(kNsModerateSuppression); |
| |
| // verify default settings (should be OFF and mode as above) |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxNSmode != rxNSmodeDefault); |
| |
| // enable default NS settings |
| // must set a value first time! |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, false, kNsDefault)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxNSmode != rxNSmodeDefault); |
| SLEEP(NSSleep); |
| |
| // set kNsLowSuppression mode |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true, kNsLowSuppression)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(rxNSmode != kNsLowSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsModerateSuppression mode |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true, kNsModerateSuppression)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(rxNSmode != kNsModerateSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsHighSuppression mode |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true, kNsHighSuppression)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(rxNSmode != kNsHighSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsVeryHighSuppression mode |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true, kNsVeryHighSuppression)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(rxNSmode != kNsVeryHighSuppression); |
| SLEEP(NSSleep); |
| |
| // set kNsVeryHighSuppression mode |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true, kNsConference)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(rxNSmode != kNsHighSuppression); |
| SLEEP(NSSleep); |
| |
| // verify that mode is maintained when NS is disabled |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, false)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxNSmode != kNsHighSuppression); |
| SLEEP(NSSleep); |
| |
| // restore default NS |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true, kNsDefault)); |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, false)); |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxNSmode != NSmodeDefault); |
| SLEEP(NSSleep); |
| |
| // enable/disable many times in a row |
| for (i = 0; i < NSIterations; i++) |
| { |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, true)); |
| TEST_MUSTPASS(apm->SetRxNsStatus(0, false)); |
| } |
| TEST_MUSTPASS(apm->GetRxNsStatus(0, enabled, rxNSmode)); |
| TEST_LOG("rxNS: enabled=%d, NSmode=%d\n", enabled, rxNSmode); |
| TEST_MUSTPASS(enabled != false); |
| TEST_MUSTPASS(rxNSmode != NSmodeDefault); |
| SLEEP(NSSleep); |
| |
| ///////////////////////////// |
| // StartDebugRecording |
| //////////////////////////// |
| // StopDebugRecording |
| TEST_LOG("StartDebugRecording"); |
| TEST_MUSTPASS(apm->StartDebugRecording(GetFilename("apm_debug.txt"))); |
| SLEEP(1000); |
| TEST_LOG("StopDebugRecording"); |
| TEST_MUSTPASS(apm->StopDebugRecording()); |
| |
| TEST_MUSTPASS(voe_base_->DeleteChannel(0)); |
| TEST_MUSTPASS(voe_base_->Terminate()); |
| |
| return 0; |
| } |
| |
| } // namespace voetest |