summaryrefslogtreecommitdiffstats
path: root/chromium/media/audio/mac/aggregate_device_manager.cc
diff options
context:
space:
mode:
Diffstat (limited to 'chromium/media/audio/mac/aggregate_device_manager.cc')
-rw-r--r--chromium/media/audio/mac/aggregate_device_manager.cc371
1 files changed, 0 insertions, 371 deletions
diff --git a/chromium/media/audio/mac/aggregate_device_manager.cc b/chromium/media/audio/mac/aggregate_device_manager.cc
deleted file mode 100644
index c7f323322e7..00000000000
--- a/chromium/media/audio/mac/aggregate_device_manager.cc
+++ /dev/null
@@ -1,371 +0,0 @@
-// Copyright 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "media/audio/mac/aggregate_device_manager.h"
-
-#include <CoreAudio/AudioHardware.h>
-#include <string>
-
-#include "base/mac/mac_logging.h"
-#include "base/mac/scoped_cftyperef.h"
-#include "media/audio/audio_parameters.h"
-#include "media/audio/mac/audio_manager_mac.h"
-
-using base::ScopedCFTypeRef;
-
-namespace media {
-
-AggregateDeviceManager::AggregateDeviceManager()
- : plugin_id_(kAudioObjectUnknown),
- input_device_(kAudioDeviceUnknown),
- output_device_(kAudioDeviceUnknown),
- aggregate_device_(kAudioObjectUnknown) {
-}
-
-AggregateDeviceManager::~AggregateDeviceManager() {
- DestroyAggregateDevice();
-}
-
-AudioDeviceID AggregateDeviceManager::GetDefaultAggregateDevice() {
- AudioDeviceID current_input_device;
- AudioDeviceID current_output_device;
- AudioManagerMac::GetDefaultInputDevice(&current_input_device);
- AudioManagerMac::GetDefaultOutputDevice(&current_output_device);
-
- if (AudioManagerMac::HardwareSampleRateForDevice(current_input_device) !=
- AudioManagerMac::HardwareSampleRateForDevice(current_output_device)) {
- // TODO(crogers): with some extra work we can make aggregate devices work
- // if the clock domain is the same but the sample-rate differ.
- // For now we fallback to the synchronized path.
- return kAudioDeviceUnknown;
- }
-
- // Use a lazily created aggregate device if it's already available
- // and still appropriate.
- if (aggregate_device_ != kAudioObjectUnknown) {
- // TODO(crogers): handle default device changes for synchronized I/O.
- // For now, we check to make sure the default devices haven't changed
- // since we lazily created the aggregate device.
- if (current_input_device == input_device_ &&
- current_output_device == output_device_)
- return aggregate_device_;
-
- // For now, once lazily created don't attempt to create another
- // aggregate device.
- return kAudioDeviceUnknown;
- }
-
- input_device_ = current_input_device;
- output_device_ = current_output_device;
-
- // Only create an aggregrate device if the clock domains match.
- UInt32 input_clockdomain = GetClockDomain(input_device_);
- UInt32 output_clockdomain = GetClockDomain(output_device_);
- DVLOG(1) << "input_clockdomain: " << input_clockdomain;
- DVLOG(1) << "output_clockdomain: " << output_clockdomain;
-
- if (input_clockdomain == 0 || input_clockdomain != output_clockdomain)
- return kAudioDeviceUnknown;
-
- OSStatus result = CreateAggregateDevice(
- input_device_,
- output_device_,
- &aggregate_device_);
- if (result != noErr)
- DestroyAggregateDevice();
-
- return aggregate_device_;
-}
-
-CFStringRef AggregateDeviceManager::GetDeviceUID(AudioDeviceID id) {
- static const AudioObjectPropertyAddress kDeviceUIDAddress = {
- kAudioDevicePropertyDeviceUID,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- // As stated in the CoreAudio header (AudioHardwareBase.h),
- // the caller is responsible for releasing the device_UID.
- CFStringRef device_UID;
- UInt32 size = sizeof(device_UID);
- OSStatus result = AudioObjectGetPropertyData(
- id,
- &kDeviceUIDAddress,
- 0,
- 0,
- &size,
- &device_UID);
-
- return (result == noErr) ? device_UID : NULL;
-}
-
-void AggregateDeviceManager::GetDeviceName(
- AudioDeviceID id, char* name, UInt32 size) {
- static const AudioObjectPropertyAddress kDeviceNameAddress = {
- kAudioDevicePropertyDeviceName,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- OSStatus result = AudioObjectGetPropertyData(
- id,
- &kDeviceNameAddress,
- 0,
- 0,
- &size,
- name);
-
- if (result != noErr && size > 0)
- name[0] = 0;
-}
-
-UInt32 AggregateDeviceManager::GetClockDomain(AudioDeviceID device_id) {
- static const AudioObjectPropertyAddress kClockDomainAddress = {
- kAudioDevicePropertyClockDomain,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- UInt32 clockdomain = 0;
- UInt32 size = sizeof(UInt32);
- OSStatus result = AudioObjectGetPropertyData(
- device_id,
- &kClockDomainAddress,
- 0,
- 0,
- &size,
- &clockdomain);
-
- return (result == noErr) ? clockdomain : 0;
-}
-
-OSStatus AggregateDeviceManager::GetPluginID(AudioObjectID* id) {
- DCHECK(id);
-
- // Get the audio hardware plugin.
- CFStringRef bundle_name = CFSTR("com.apple.audio.CoreAudio");
-
- AudioValueTranslation plugin_translation;
- plugin_translation.mInputData = &bundle_name;
- plugin_translation.mInputDataSize = sizeof(bundle_name);
- plugin_translation.mOutputData = id;
- plugin_translation.mOutputDataSize = sizeof(*id);
-
- static const AudioObjectPropertyAddress kPlugInAddress = {
- kAudioHardwarePropertyPlugInForBundleID,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- UInt32 size = sizeof(plugin_translation);
- OSStatus result = AudioObjectGetPropertyData(
- kAudioObjectSystemObject,
- &kPlugInAddress,
- 0,
- 0,
- &size,
- &plugin_translation);
-
- DVLOG(1) << "CoreAudio plugin ID: " << *id;
-
- return result;
-}
-
-CFMutableDictionaryRef
-AggregateDeviceManager::CreateAggregateDeviceDictionary(
- AudioDeviceID input_id,
- AudioDeviceID output_id) {
- CFMutableDictionaryRef aggregate_device_dict = CFDictionaryCreateMutable(
- NULL,
- 0,
- &kCFTypeDictionaryKeyCallBacks,
- &kCFTypeDictionaryValueCallBacks);
- if (!aggregate_device_dict)
- return NULL;
-
- const CFStringRef kAggregateDeviceName =
- CFSTR("ChromeAggregateAudioDevice");
- const CFStringRef kAggregateDeviceUID =
- CFSTR("com.google.chrome.AggregateAudioDevice");
-
- // Add name and UID of the device to the dictionary.
- CFDictionaryAddValue(
- aggregate_device_dict,
- CFSTR(kAudioAggregateDeviceNameKey),
- kAggregateDeviceName);
- CFDictionaryAddValue(
- aggregate_device_dict,
- CFSTR(kAudioAggregateDeviceUIDKey),
- kAggregateDeviceUID);
-
- // Add a "private aggregate key" to the dictionary.
- // The 1 value means that the created aggregate device will
- // only be accessible from the process that created it, and
- // won't be visible to outside processes.
- int value = 1;
- ScopedCFTypeRef<CFNumberRef> aggregate_device_number(CFNumberCreate(
- NULL,
- kCFNumberIntType,
- &value));
- CFDictionaryAddValue(
- aggregate_device_dict,
- CFSTR(kAudioAggregateDeviceIsPrivateKey),
- aggregate_device_number);
-
- return aggregate_device_dict;
-}
-
-CFMutableArrayRef
-AggregateDeviceManager::CreateSubDeviceArray(
- CFStringRef input_device_UID, CFStringRef output_device_UID) {
- CFMutableArrayRef sub_devices_array = CFArrayCreateMutable(
- NULL,
- 0,
- &kCFTypeArrayCallBacks);
-
- CFArrayAppendValue(sub_devices_array, input_device_UID);
- CFArrayAppendValue(sub_devices_array, output_device_UID);
-
- return sub_devices_array;
-}
-
-OSStatus AggregateDeviceManager::CreateAggregateDevice(
- AudioDeviceID input_id,
- AudioDeviceID output_id,
- AudioDeviceID* aggregate_device) {
- DCHECK(aggregate_device);
-
- const size_t kMaxDeviceNameLength = 256;
-
- scoped_ptr<char[]> input_device_name(new char[kMaxDeviceNameLength]);
- GetDeviceName(
- input_id,
- input_device_name.get(),
- sizeof(input_device_name));
- DVLOG(1) << "Input device: \n" << input_device_name;
-
- scoped_ptr<char[]> output_device_name(new char[kMaxDeviceNameLength]);
- GetDeviceName(
- output_id,
- output_device_name.get(),
- sizeof(output_device_name));
- DVLOG(1) << "Output device: \n" << output_device_name;
-
- OSStatus result = GetPluginID(&plugin_id_);
- if (result != noErr)
- return result;
-
- // Create a dictionary for the aggregate device.
- ScopedCFTypeRef<CFMutableDictionaryRef> aggregate_device_dict(
- CreateAggregateDeviceDictionary(input_id, output_id));
- if (!aggregate_device_dict)
- return -1;
-
- // Create the aggregate device.
- static const AudioObjectPropertyAddress kCreateAggregateDeviceAddress = {
- kAudioPlugInCreateAggregateDevice,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- UInt32 size = sizeof(*aggregate_device);
- result = AudioObjectGetPropertyData(
- plugin_id_,
- &kCreateAggregateDeviceAddress,
- sizeof(aggregate_device_dict),
- &aggregate_device_dict,
- &size,
- aggregate_device);
- if (result != noErr) {
- DLOG(ERROR) << "Error creating aggregate audio device!";
- return result;
- }
-
- // Set the sub-devices for the aggregate device.
- // In this case we use two: the input and output devices.
-
- ScopedCFTypeRef<CFStringRef> input_device_UID(GetDeviceUID(input_id));
- ScopedCFTypeRef<CFStringRef> output_device_UID(GetDeviceUID(output_id));
- if (!input_device_UID || !output_device_UID) {
- DLOG(ERROR) << "Error getting audio device UID strings.";
- return -1;
- }
-
- ScopedCFTypeRef<CFMutableArrayRef> sub_devices_array(
- CreateSubDeviceArray(input_device_UID, output_device_UID));
- if (sub_devices_array == NULL) {
- DLOG(ERROR) << "Error creating sub-devices array.";
- return -1;
- }
-
- static const AudioObjectPropertyAddress kSetSubDevicesAddress = {
- kAudioAggregateDevicePropertyFullSubDeviceList,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- size = sizeof(CFMutableArrayRef);
- result = AudioObjectSetPropertyData(
- *aggregate_device,
- &kSetSubDevicesAddress,
- 0,
- NULL,
- size,
- &sub_devices_array);
- if (result != noErr) {
- DLOG(ERROR) << "Error setting aggregate audio device sub-devices!";
- return result;
- }
-
- // Use the input device as the master device.
- static const AudioObjectPropertyAddress kSetMasterDeviceAddress = {
- kAudioAggregateDevicePropertyMasterSubDevice,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- size = sizeof(CFStringRef);
- result = AudioObjectSetPropertyData(
- *aggregate_device,
- &kSetMasterDeviceAddress,
- 0,
- NULL,
- size,
- &input_device_UID);
- if (result != noErr) {
- DLOG(ERROR) << "Error setting aggregate audio device master device!";
- return result;
- }
-
- DVLOG(1) << "New aggregate device: " << *aggregate_device;
- return noErr;
-}
-
-void AggregateDeviceManager::DestroyAggregateDevice() {
- if (aggregate_device_ == kAudioObjectUnknown)
- return;
-
- static const AudioObjectPropertyAddress kDestroyAddress = {
- kAudioPlugInDestroyAggregateDevice,
- kAudioObjectPropertyScopeGlobal,
- kAudioObjectPropertyElementMaster
- };
-
- UInt32 size = sizeof(aggregate_device_);
- OSStatus result = AudioObjectGetPropertyData(
- plugin_id_,
- &kDestroyAddress,
- 0,
- NULL,
- &size,
- &aggregate_device_);
- if (result != noErr) {
- DLOG(ERROR) << "Error destroying aggregate audio device!";
- return;
- }
-
- aggregate_device_ = kAudioObjectUnknown;
-}
-
-} // namespace media