diff options
author | Hsin-Yu Chao <hychao@chromium.org> | 2017-03-30 15:27:53 +0800 |
---|---|---|
committer | chrome-bot <chrome-bot@chromium.org> | 2017-03-30 07:29:42 -0700 |
commit | 2a609e202c8565477a73b5600ab12e86668cf232 (patch) | |
tree | 0d4c7f9cbae50da040aee9d9e5d4abf799db5130 | |
parent | b8ad07f933679a28fd1c740605942cc990b32de3 (diff) | |
download | adhd-2a609e202c8565477a73b5600ab12e86668cf232.tar.gz |
CRAS: iodev_list - Enable/disable active node for pinned stream
When a pinned stream is connected, the active node on the iodev-
to-pin might not work properly due to it was left in disabled
state when user's last action was switching to the other iodev.
Fix this problem by calling update_active_node() when a pinned
stream connected and removed.
BUG=chromium:700247
TEST=Plug 3.5mm headphone and a USB headset, select to headphone
in UI tray and then select to USB headset as output.
Execute 'cras_test_client --pin_device <id-of-internal-card>' to
play something, and verify audio coming out from headphone.
Next, click on UI to select to internal speaker and then select to
USB headset as output. Execute cras_test_client --pin_device to
play something, verify audio coming out from internal speaker this
time.
Change-Id: I438fdfc591b52186ed5a5079f8d3125b47f3499a
Reviewed-on: https://chromium-review.googlesource.com/462736
Commit-Ready: Hsinyu Chao <hychao@chromium.org>
Tested-by: Hsinyu Chao <hychao@chromium.org>
Reviewed-by: Chinyue Chen <chinyue@chromium.org>
-rw-r--r-- | cras/src/server/cras_iodev_list.c | 42 |
1 files changed, 27 insertions, 15 deletions
diff --git a/cras/src/server/cras_iodev_list.c b/cras/src/server/cras_iodev_list.c index 5eac3e68..b89767ec 100644 --- a/cras/src/server/cras_iodev_list.c +++ b/cras/src/server/cras_iodev_list.c @@ -593,6 +593,28 @@ static void schedule_init_device_retry(struct enabled_dev *edev) tm, INIT_DEV_DELAY_MS, init_device_cb, edev); } +static int pinned_stream_added(struct cras_rstream *rstream) +{ + struct cras_iodev *dev; + int rc; + + /* Check that the target device is valid for pinned streams. */ + dev = find_dev(rstream->pinned_dev_idx); + if (!dev) + return -EINVAL; + + /* Make sure the active node is configured properly, it could be + * disabled when last normal stream removed. */ + dev->update_active_node(dev, dev->active_node->idx, 1); + + /* Negative EAGAIN code indicates dev will be opened later. */ + rc = init_device(dev, rstream); + if (rc && (rc != -EAGAIN)) + return rc; + + return audio_thread_add_stream(audio_thread, rstream, &dev, 1); +} + static int stream_added_cb(struct cras_rstream *rstream) { struct enabled_dev *edev; @@ -603,20 +625,8 @@ static int stream_added_cb(struct cras_rstream *rstream) if (stream_list_suspended) return 0; - /* Check that the target device is valid for pinned streams. */ - if (rstream->is_pinned) { - struct cras_iodev *dev; - dev = find_dev(rstream->pinned_dev_idx); - if (!dev) - return -EINVAL; - - /* Negative EAGAIN code indicates dev will be opened later. */ - rc = init_device(dev, rstream); - if (rc && (rc != -EAGAIN)) - return rc; - - return audio_thread_add_stream(audio_thread, rstream, &dev, 1); - } + if (rstream->is_pinned) + return pinned_stream_added(rstream); /* Add the new stream to all enabled iodevs at once to avoid offset * in shm level between different ouput iodevs. */ @@ -697,8 +707,10 @@ static void pinned_stream_removed(struct cras_rstream *rstream) struct cras_iodev *dev; dev = find_dev(rstream->pinned_dev_idx); - if (!cras_iodev_list_dev_is_enabled(dev)) + if (!cras_iodev_list_dev_is_enabled(dev)) { close_dev(dev); + dev->update_active_node(dev, dev->active_node->idx, 0); + } } /* Returns the number of milliseconds left to drain this stream. This is passed |