diff options
author | davej@chromium.org <davej@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-04-19 01:05:50 +0000 |
---|---|---|
committer | davej@chromium.org <davej@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-04-19 01:05:50 +0000 |
commit | 2c1ee604e1de20cf8aeaa4d22b6fee2c4b20b0b4 (patch) | |
tree | f5aeda26905e92ee794ac838ca46c890a7376a5f | |
parent | ba8732d8c062bd8e1a3f6871a77c6603ebc21ce0 (diff) | |
download | chromium_src-2c1ee604e1de20cf8aeaa4d22b6fee2c4b20b0b4.zip chromium_src-2c1ee604e1de20cf8aeaa4d22b6fee2c4b20b0b4.tar.gz chromium_src-2c1ee604e1de20cf8aeaa4d22b6fee2c4b20b0b4.tar.bz2 |
Open ALSA device using hw_params calls
Replaced using ALSA snd_pcm_set_params() with separate snd_pcm_hw_X() calls in order to use snd_pcm_hw_params_set_rate_near() which allows for setting rates on some devices that don't normally allow some rates like 22050Hz.
BUG=chromium-os:13231, chromium-os:13721
TEST=Manual, 22khz audio should play (test file in bug)
Review URL: http://codereview.chromium.org/6869037
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@82042 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r-- | media/audio/linux/alsa_wrapper.cc | 70 | ||||
-rw-r--r-- | media/audio/linux/alsa_wrapper.h | 6 |
2 files changed, 72 insertions, 4 deletions
diff --git a/media/audio/linux/alsa_wrapper.cc b/media/audio/linux/alsa_wrapper.cc index 8270430..563bccb 100644 --- a/media/audio/linux/alsa_wrapper.cc +++ b/media/audio/linux/alsa_wrapper.cc @@ -1,4 +1,4 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. +// Copyright (c) 2011 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. @@ -65,12 +65,76 @@ const char* AlsaWrapper::PcmName(snd_pcm_t* handle) { return snd_pcm_name(handle); } +int AlsaWrapper::ConfigureHwParams(snd_pcm_t* handle, + snd_pcm_hw_params_t* hw_params, + snd_pcm_format_t format, + snd_pcm_access_t access, + unsigned int channels, + unsigned int rate, + int soft_resample, + unsigned int latency) { + int err = 0; + if ((err = snd_pcm_hw_params_any(handle, hw_params)) < 0) + return err; + + if ((err = snd_pcm_hw_params_set_rate_resample(handle, hw_params, + soft_resample)) < 0) { + return err; + } + + if ((err = snd_pcm_hw_params_set_format(handle, hw_params, format)) < 0) + return err; + + int dir = 0; + unsigned new_rate = rate; + if ((err = snd_pcm_hw_params_set_rate_near(handle, hw_params, + &new_rate, &dir)) < 0) { + return err; + } + + if ((err = snd_pcm_hw_params_set_access(handle, hw_params, access)) < 0) + return err; + + if ((err = snd_pcm_hw_params_set_channels(handle, hw_params, channels)) < 0) + return err; + + unsigned buffer_time = latency; + if (buffer_time == 0) { + if ((err = snd_pcm_hw_params_get_buffer_time_max(hw_params, + &buffer_time, 0)) < 0) { + return err; + } + if (buffer_time > 500000) + buffer_time = 500000; + } + + unsigned period_time = buffer_time / 4; + if ((err = snd_pcm_hw_params_set_period_time_near(handle, hw_params, + &period_time, 0)) < 0) { + return err; + } + + err = snd_pcm_hw_params_set_buffer_time_near(handle, hw_params, + &buffer_time, 0); + return err; +} + int AlsaWrapper::PcmSetParams(snd_pcm_t* handle, snd_pcm_format_t format, snd_pcm_access_t access, unsigned int channels, unsigned int rate, int soft_resample, unsigned int latency) { - return snd_pcm_set_params(handle, format, access, channels, rate, - soft_resample, latency); + int err = 0; + snd_pcm_hw_params_t *hw_params; + if ((err = snd_pcm_hw_params_malloc(&hw_params)) < 0) + return err; + + if ((err = ConfigureHwParams(handle, hw_params, format, access, channels, + rate, soft_resample, latency)) >= 0) { + err = snd_pcm_hw_params(handle, hw_params); + } + + snd_pcm_hw_params_free(hw_params); + return err; } int AlsaWrapper::PcmGetParams(snd_pcm_t* handle, snd_pcm_uframes_t* buffer_size, diff --git a/media/audio/linux/alsa_wrapper.h b/media/audio/linux/alsa_wrapper.h index 88bdb5a..1fe1992 100644 --- a/media/audio/linux/alsa_wrapper.h +++ b/media/audio/linux/alsa_wrapper.h @@ -1,4 +1,4 @@ -// Copyright (c) 2010 The Chromium Authors. All rights reserved. +// Copyright (c) 2011 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. // @@ -46,5 +46,9 @@ class AlsaWrapper { virtual const char* StrError(int errnum); private: + int ConfigureHwParams(snd_pcm_t* handle, snd_pcm_hw_params_t* hw_params, + snd_pcm_format_t format, snd_pcm_access_t access, + unsigned int channels, unsigned int rate, + int soft_resample, unsigned int latency); DISALLOW_COPY_AND_ASSIGN(AlsaWrapper); }; |