1// Copyright (c) 2012 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#ifndef CONTENT_RENDERER_MEDIA_AUDIO_RENDERER_MIXER_MANAGER_H_ 6#define CONTENT_RENDERER_MEDIA_AUDIO_RENDERER_MIXER_MANAGER_H_ 7 8#include <map> 9#include <utility> 10 11#include "base/synchronization/lock.h" 12#include "content/common/content_export.h" 13#include "media/audio/audio_parameters.h" 14 15namespace media { 16class AudioHardwareConfig; 17class AudioRendererMixer; 18class AudioRendererMixerInput; 19class AudioRendererSink; 20} 21 22namespace content { 23 24// Manages sharing of an AudioRendererMixer among AudioRendererMixerInputs based 25// on their AudioParameters configuration. Inputs with the same AudioParameters 26// configuration will share a mixer while a new AudioRendererMixer will be 27// lazily created if one with the exact AudioParameters does not exist. 28// 29// There should only be one instance of AudioRendererMixerManager per render 30// thread. 31// 32// TODO(dalecurtis): Right now we require AudioParameters to be an exact match 33// when we should be able to ignore bits per channel since we're only dealing 34// with floats. However, bits per channel is currently used to interleave the 35// audio data by AudioOutputDevice::AudioThreadCallback::Process for consumption 36// via the shared memory. See http://crbug.com/114700. 37class CONTENT_EXPORT AudioRendererMixerManager { 38 public: 39 // Construct an instance using the given audio hardware configuration. The 40 // provided |hardware_config| is not owned by AudioRendererMixerManager and 41 // must outlive it. 42 explicit AudioRendererMixerManager( 43 media::AudioHardwareConfig* hardware_config); 44 ~AudioRendererMixerManager(); 45 46 // Creates an AudioRendererMixerInput with the proper callbacks necessary to 47 // retrieve an AudioRendererMixer instance from AudioRendererMixerManager. 48 // |source_render_view_id| refers to the RenderView containing the entity 49 // rendering the audio. |source_render_frame_id| refers to the RenderFrame 50 // containing the entity rendering the audio. Caller must ensure 51 // AudioRendererMixerManager outlives the returned input. 52 media::AudioRendererMixerInput* CreateInput(int source_render_view_id, 53 int source_render_frame_id); 54 55 // Returns a mixer instance based on AudioParameters; an existing one if one 56 // with the provided AudioParameters exists or a new one if not. 57 media::AudioRendererMixer* GetMixer(int source_render_view_id, 58 int source_render_frame_id, 59 const media::AudioParameters& params); 60 61 // Remove a mixer instance given a mixer if the only other reference is held 62 // by AudioRendererMixerManager. Every AudioRendererMixer owner must call 63 // this method when it's done with a mixer. 64 void RemoveMixer(int source_render_view_id, 65 const media::AudioParameters& params); 66 67 private: 68 friend class AudioRendererMixerManagerTest; 69 70 // Define a key so that only those AudioRendererMixerInputs from the same 71 // RenderView and with the same AudioParameters can be mixed together. The 72 // first value is the RenderViewId. 73 typedef std::pair<int, media::AudioParameters> MixerKey; 74 75 // Custom compare operator for the AudioRendererMixerMap. Allows reuse of 76 // mixers where only irrelevant keys mismatch; e.g., effects, bits per sample. 77 struct MixerKeyCompare { 78 bool operator()(const MixerKey& a, const MixerKey& b) const { 79 if (a.first != b.first) 80 return a.first < b.first; 81 if (a.second.sample_rate() != b.second.sample_rate()) 82 return a.second.sample_rate() < b.second.sample_rate(); 83 if (a.second.channels() != b.second.channels()) 84 return a.second.channels() < b.second.channels(); 85 86 // Ignore effects(), bits_per_sample(), format(), and frames_per_buffer(), 87 // these parameters do not affect mixer reuse. All AudioRendererMixer 88 // units disable FIFO, so frames_per_buffer() can be safely ignored. 89 return a.second.channel_layout() < b.second.channel_layout(); 90 } 91 }; 92 93 // Map of MixerKey to <AudioRendererMixer, Count>. Count allows 94 // AudioRendererMixerManager to keep track explicitly (v.s. RefCounted which 95 // is implicit) of the number of outstanding AudioRendererMixers. 96 struct AudioRendererMixerReference { 97 media::AudioRendererMixer* mixer; 98 int ref_count; 99 }; 100 typedef std::map<MixerKey, AudioRendererMixerReference, MixerKeyCompare> 101 AudioRendererMixerMap; 102 103 // Overrides the AudioRendererSink implementation for unit testing. 104 void SetAudioRendererSinkForTesting(media::AudioRendererSink* sink); 105 106 // Active mixers. 107 AudioRendererMixerMap mixers_; 108 base::Lock mixers_lock_; 109 110 // Audio hardware configuration. Used to construct output AudioParameters for 111 // each AudioRendererMixer instance. 112 media::AudioHardwareConfig* const hardware_config_; 113 114 media::AudioRendererSink* sink_for_testing_; 115 116 DISALLOW_COPY_AND_ASSIGN(AudioRendererMixerManager); 117}; 118 119} // namespace content 120 121#endif // CONTENT_RENDERER_MEDIA_AUDIO_RENDERER_MIXER_MANAGER_H_ 122