1 /* 2 * Copyright (c) 2012 The WebRTC project authors. All Rights Reserved. 3 * 4 * Use of this source code is governed by a BSD-style license 5 * that can be found in the LICENSE file in the root of the source 6 * tree. An additional intellectual property rights grant can be found 7 * in the file PATENTS. All contributing project authors may 8 * be found in the AUTHORS file in the root of the source tree. 9 */ 10 11 #if defined(WEBRTC_ANDROID) 12 #include "webrtc/modules/audio_device/android/audio_device_template.h" 13 #include "webrtc/modules/audio_device/android/audio_record_jni.h" 14 #include "webrtc/modules/audio_device/android/audio_track_jni.h" 15 #include "webrtc/modules/utility/include/jvm_android.h" 16 #endif 17 18 #include "webrtc/base/checks.h" 19 #include "webrtc/modules/audio_coding/include/audio_coding_module.h" 20 #include "webrtc/system_wrappers/include/critical_section_wrapper.h" 21 #include "webrtc/system_wrappers/include/trace.h" 22 #include "webrtc/voice_engine/channel_proxy.h" 23 #include "webrtc/voice_engine/voice_engine_impl.h" 24 25 namespace webrtc { 26 27 // Counter to be ensure that we can add a correct ID in all static trace 28 // methods. It is not the nicest solution, especially not since we already 29 // have a counter in VoEBaseImpl. In other words, there is room for 30 // improvement here. 31 static int32_t gVoiceEngineInstanceCounter = 0; 32 33 VoiceEngine* GetVoiceEngine(const Config* config, bool owns_config) { 34 VoiceEngineImpl* self = new VoiceEngineImpl(config, owns_config); 35 if (self != NULL) { 36 self->AddRef(); // First reference. Released in VoiceEngine::Delete. 37 gVoiceEngineInstanceCounter++; 38 } 39 return self; 40 } 41 42 int VoiceEngineImpl::AddRef() { 43 return ++_ref_count; 44 } 45 46 // This implements the Release() method for all the inherited interfaces. 47 int VoiceEngineImpl::Release() { 48 int new_ref = --_ref_count; 49 assert(new_ref >= 0); 50 if (new_ref == 0) { 51 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, -1, 52 "VoiceEngineImpl self deleting (voiceEngine=0x%p)", this); 53 54 // Clear any pointers before starting destruction. Otherwise worker- 55 // threads will still have pointers to a partially destructed object. 56 // Example: AudioDeviceBuffer::RequestPlayoutData() can access a 57 // partially deconstructed |_ptrCbAudioTransport| during destruction 58 // if we don't call Terminate here. 59 Terminate(); 60 delete this; 61 } 62 63 return new_ref; 64 } 65 66 rtc::scoped_ptr<voe::ChannelProxy> VoiceEngineImpl::GetChannelProxy( 67 int channel_id) { 68 RTC_DCHECK(channel_id >= 0); 69 CriticalSectionScoped cs(crit_sec()); 70 RTC_DCHECK(statistics().Initialized()); 71 return rtc::scoped_ptr<voe::ChannelProxy>( 72 new voe::ChannelProxy(channel_manager().GetChannel(channel_id))); 73 } 74 75 VoiceEngine* VoiceEngine::Create() { 76 Config* config = new Config(); 77 return GetVoiceEngine(config, true); 78 } 79 80 VoiceEngine* VoiceEngine::Create(const Config& config) { 81 return GetVoiceEngine(&config, false); 82 } 83 84 int VoiceEngine::SetTraceFilter(unsigned int filter) { 85 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, 86 VoEId(gVoiceEngineInstanceCounter, -1), 87 "SetTraceFilter(filter=0x%x)", filter); 88 89 // Remember old filter 90 uint32_t oldFilter = Trace::level_filter(); 91 Trace::set_level_filter(filter); 92 93 // If previous log was ignored, log again after changing filter 94 if (kTraceNone == oldFilter) { 95 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, -1, "SetTraceFilter(filter=0x%x)", 96 filter); 97 } 98 99 return 0; 100 } 101 102 int VoiceEngine::SetTraceFile(const char* fileNameUTF8, bool addFileCounter) { 103 int ret = Trace::SetTraceFile(fileNameUTF8, addFileCounter); 104 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, 105 VoEId(gVoiceEngineInstanceCounter, -1), 106 "SetTraceFile(fileNameUTF8=%s, addFileCounter=%d)", fileNameUTF8, 107 addFileCounter); 108 return (ret); 109 } 110 111 int VoiceEngine::SetTraceCallback(TraceCallback* callback) { 112 WEBRTC_TRACE(kTraceApiCall, kTraceVoice, 113 VoEId(gVoiceEngineInstanceCounter, -1), 114 "SetTraceCallback(callback=0x%x)", callback); 115 return (Trace::SetTraceCallback(callback)); 116 } 117 118 bool VoiceEngine::Delete(VoiceEngine*& voiceEngine) { 119 if (voiceEngine == NULL) 120 return false; 121 122 VoiceEngineImpl* s = static_cast<VoiceEngineImpl*>(voiceEngine); 123 // Release the reference that was added in GetVoiceEngine. 124 int ref = s->Release(); 125 voiceEngine = NULL; 126 127 if (ref != 0) { 128 WEBRTC_TRACE( 129 kTraceWarning, kTraceVoice, -1, 130 "VoiceEngine::Delete did not release the very last reference. " 131 "%d references remain.", 132 ref); 133 } 134 135 return true; 136 } 137 138 #if !defined(WEBRTC_CHROMIUM_BUILD) 139 // TODO(henrika): change types to JavaVM* and jobject instead of void*. 140 int VoiceEngine::SetAndroidObjects(void* javaVM, void* context) { 141 #ifdef WEBRTC_ANDROID 142 webrtc::JVM::Initialize(reinterpret_cast<JavaVM*>(javaVM), 143 reinterpret_cast<jobject>(context)); 144 return 0; 145 #else 146 return -1; 147 #endif 148 } 149 #endif 150 151 std::string VoiceEngine::GetVersionString() { 152 std::string version = "VoiceEngine 4.1.0"; 153 #ifdef WEBRTC_EXTERNAL_TRANSPORT 154 version += " (External transport build)"; 155 #endif 156 return version; 157 } 158 159 } // namespace webrtc 160