• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2004 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 #ifndef WEBRTC_SOUND_AUTOMATICALLYCHOSENSOUNDSYSTEM_H_
12 #define WEBRTC_SOUND_AUTOMATICALLYCHOSENSOUNDSYSTEM_H_
13 
14 #include "webrtc/sound/soundsysteminterface.h"
15 #include "webrtc/sound/soundsystemproxy.h"
16 #include "webrtc/base/common.h"
17 #include "webrtc/base/logging.h"
18 #include "webrtc/base/scoped_ptr.h"
19 
20 namespace rtc {
21 
22 // A function type that creates an instance of a sound system implementation.
23 typedef SoundSystemInterface *(*SoundSystemCreator)();
24 
25 // An AutomaticallyChosenSoundSystem is a sound system proxy that defers to
26 // an instance of the first sound system implementation in a list that
27 // successfully initializes.
28 template <const SoundSystemCreator kSoundSystemCreators[], int kNumSoundSystems>
29 class AutomaticallyChosenSoundSystem : public SoundSystemProxy {
30  public:
31   // Chooses and initializes the underlying sound system.
32   virtual bool Init();
33   // Terminates the underlying sound system implementation, but caches it for
34   // future re-use.
35   virtual void Terminate();
36 
37   virtual const char *GetName() const;
38 
39  private:
40   rtc::scoped_ptr<SoundSystemInterface> sound_systems_[kNumSoundSystems];
41 };
42 
43 template <const SoundSystemCreator kSoundSystemCreators[], int kNumSoundSystems>
44 bool AutomaticallyChosenSoundSystem<kSoundSystemCreators,
Init()45                                     kNumSoundSystems>::Init() {
46   if (wrapped_) {
47     return true;
48   }
49   for (int i = 0; i < kNumSoundSystems; ++i) {
50     if (!sound_systems_[i].get()) {
51       sound_systems_[i].reset((*kSoundSystemCreators[i])());
52     }
53     if (sound_systems_[i]->Init()) {
54       // This is the first sound system in the list to successfully
55       // initialize, so we're done.
56       wrapped_ = sound_systems_[i].get();
57       break;
58     }
59     // Else it failed to initialize, so try the remaining ones.
60   }
61   if (!wrapped_) {
62     LOG(LS_ERROR) << "Failed to find a usable sound system";
63     return false;
64   }
65   LOG(LS_INFO) << "Selected " << wrapped_->GetName() << " sound system";
66   return true;
67 }
68 
69 template <const SoundSystemCreator kSoundSystemCreators[], int kNumSoundSystems>
70 void AutomaticallyChosenSoundSystem<kSoundSystemCreators,
Terminate()71                                     kNumSoundSystems>::Terminate() {
72   if (!wrapped_) {
73     return;
74   }
75   wrapped_->Terminate();
76   wrapped_ = NULL;
77   // We do not free the scoped_ptrs because we may be re-init'ed soon.
78 }
79 
80 template <const SoundSystemCreator kSoundSystemCreators[], int kNumSoundSystems>
81 const char *AutomaticallyChosenSoundSystem<kSoundSystemCreators,
GetName()82                                            kNumSoundSystems>::GetName() const {
83   return wrapped_ ? wrapped_->GetName() : "automatic";
84 }
85 
86 }  // namespace rtc
87 
88 #endif  // WEBRTC_SOUND_AUTOMATICALLYCHOSENSOUNDSYSTEM_H_
89