1/* Copyright (c) 2013 The Chromium OS 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
6#include <pthread.h>
7#include <sys/param.h>
8#include <syslog.h>
9
10#include "byte_buffer.h"
11#include "cras_audio_area.h"
12#include "cras_config.h"
13#include "cras_iodev.h"
14#include "cras_iodev_list.h"
15#include "cras_types.h"
16#include "cras_util.h"
17#include "sfh.h"
18#include "utlist.h"
19
20#define LOOPBACK_BUFFER_SIZE 8192
21
22static const char *loopdev_names[LOOPBACK_NUM_TYPES] = {
23	"Post Mix Pre DSP Loopback",
24	"Post DSP Loopback",
25};
26
27static size_t loopback_supported_rates[] = {
28	48000, 0
29};
30
31static size_t loopback_supported_channel_counts[] = {
32	2, 0
33};
34
35static snd_pcm_format_t loopback_supported_formats[] = {
36	SND_PCM_FORMAT_S16_LE,
37	0
38};
39
40/* loopack iodev.  Keep state of a loopback device.
41 *    sample_buffer - Pointer to sample buffer.
42 */
43struct loopback_iodev {
44	struct cras_iodev base;
45	enum CRAS_LOOPBACK_TYPE loopback_type;
46	struct timespec last_filled;
47	struct byte_buffer *sample_buffer;
48};
49
50static int sample_hook(const uint8_t *frames, unsigned int nframes,
51		       const struct cras_audio_format *fmt,
52		       void *cb_data)
53{
54	struct loopback_iodev *loopdev = (struct loopback_iodev *)cb_data;
55	struct byte_buffer *sbuf = loopdev->sample_buffer;
56	unsigned int frame_bytes = cras_get_format_bytes(fmt);
57	unsigned int frames_to_copy, bytes_to_copy;
58	struct cras_iodev *edev = cras_iodev_list_get_first_enabled_iodev(
59			CRAS_STREAM_OUTPUT);
60
61	/* If there's no active streams, the logic in frames_queued will fill
62	 * zeros for loopback capture, do not accept zeros for draining device.
63	 */
64	if (!edev || !edev->streams)
65		return 0;
66
67	frames_to_copy = MIN(buf_writable_bytes(sbuf) / frame_bytes, nframes);
68	if (!frames_to_copy)
69		return 0;
70
71	bytes_to_copy = frames_to_copy * frame_bytes;
72	memcpy(buf_write_pointer(sbuf), frames, bytes_to_copy);
73	buf_increment_write(sbuf, bytes_to_copy);
74	clock_gettime(CLOCK_MONOTONIC_RAW, &loopdev->last_filled);
75
76	return frames_to_copy;
77}
78
79static void register_loopback_hook(enum CRAS_LOOPBACK_TYPE loopback_type,
80				   struct cras_iodev *iodev,
81				   loopback_hook_t hook, void *cb_data)
82{
83	if (!iodev) {
84		syslog(LOG_ERR, "Failed to register loopback hook.");
85		return;
86	}
87
88	if (loopback_type == LOOPBACK_POST_MIX_PRE_DSP)
89		cras_iodev_register_pre_dsp_hook(iodev, hook, cb_data);
90	else if (loopback_type == LOOPBACK_POST_DSP)
91		cras_iodev_register_post_dsp_hook(iodev, hook, cb_data);
92}
93
94static void device_enabled_hook(struct cras_iodev *iodev, int enabled,
95				void *cb_data)
96{
97	struct loopback_iodev *loopdev = (struct loopback_iodev *)cb_data;
98	struct cras_iodev *edev;
99
100	if (iodev->direction != CRAS_STREAM_OUTPUT)
101		return;
102
103	if (!enabled) {
104		/* Unregister loopback hook from disabled iodev. */
105		register_loopback_hook(loopdev->loopback_type, iodev, NULL,
106				       NULL);
107	} else {
108		/* Register loopback hook onto first enabled iodev. */
109		edev = cras_iodev_list_get_first_enabled_iodev(
110				CRAS_STREAM_OUTPUT);
111		register_loopback_hook(loopdev->loopback_type, edev,
112				       sample_hook, cb_data);
113	}
114}
115
116/*
117 * iodev callbacks.
118 */
119
120static int frames_queued(const struct cras_iodev *iodev,
121			 struct timespec *hw_tstamp)
122{
123	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
124	struct byte_buffer *sbuf = loopdev->sample_buffer;
125	unsigned int frame_bytes = cras_get_format_bytes(iodev->format);
126	struct cras_iodev *edev = cras_iodev_list_get_first_enabled_iodev(
127			CRAS_STREAM_OUTPUT);
128
129	if (!edev || !edev->streams) {
130		unsigned int frames_since_last, frames_to_fill, bytes_to_fill;
131
132		frames_since_last = cras_frames_since_time(
133				&loopdev->last_filled,
134				iodev->format->frame_rate);
135		frames_to_fill = MIN(buf_writable_bytes(sbuf) / frame_bytes,
136				     frames_since_last);
137		if (frames_to_fill > 0) {
138			bytes_to_fill = frames_to_fill * frame_bytes;
139			memset(buf_write_pointer(sbuf), 0, bytes_to_fill);
140			buf_increment_write(sbuf, bytes_to_fill);
141			clock_gettime(CLOCK_MONOTONIC_RAW,
142				      &loopdev->last_filled);
143		}
144	}
145	*hw_tstamp = loopdev->last_filled;
146	return buf_queued_bytes(sbuf) / frame_bytes;
147}
148
149static int delay_frames(const struct cras_iodev *iodev)
150{
151	struct timespec tstamp;
152
153	return frames_queued(iodev, &tstamp);
154}
155
156static int close_record_dev(struct cras_iodev *iodev)
157{
158	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
159	struct byte_buffer *sbuf = loopdev->sample_buffer;
160	struct cras_iodev *edev;
161
162	cras_iodev_free_format(iodev);
163	cras_iodev_free_audio_area(iodev);
164	buf_reset(sbuf);
165
166	edev = cras_iodev_list_get_first_enabled_iodev(CRAS_STREAM_OUTPUT);
167	register_loopback_hook(loopdev->loopback_type, edev, NULL, NULL);
168	cras_iodev_list_set_device_enabled_callback(NULL, NULL);
169
170	return 0;
171}
172
173static int open_record_dev(struct cras_iodev *iodev)
174{
175	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
176	struct cras_iodev *edev;
177
178	cras_iodev_init_audio_area(iodev, iodev->format->num_channels);
179	clock_gettime(CLOCK_MONOTONIC_RAW, &loopdev->last_filled);
180
181	edev = cras_iodev_list_get_first_enabled_iodev(CRAS_STREAM_OUTPUT);
182	register_loopback_hook(loopdev->loopback_type, edev, sample_hook,
183			       (void *)iodev);
184	cras_iodev_list_set_device_enabled_callback(device_enabled_hook,
185						    (void *)iodev);
186
187	return 0;
188}
189
190static int get_record_buffer(struct cras_iodev *iodev,
191		      struct cras_audio_area **area,
192		      unsigned *frames)
193{
194	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
195	struct byte_buffer *sbuf = loopdev->sample_buffer;
196	unsigned int frame_bytes = cras_get_format_bytes(iodev->format);
197	unsigned int avail_frames = buf_readable_bytes(sbuf) / frame_bytes;
198
199	*frames = MIN(avail_frames, *frames);
200	iodev->area->frames = *frames;
201	cras_audio_area_config_buf_pointers(iodev->area, iodev->format,
202					    buf_read_pointer(sbuf));
203	*area = iodev->area;
204
205	return 0;
206}
207
208static int put_record_buffer(struct cras_iodev *iodev, unsigned nframes)
209{
210	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
211	struct byte_buffer *sbuf = loopdev->sample_buffer;
212	unsigned int frame_bytes = cras_get_format_bytes(iodev->format);
213
214	buf_increment_read(sbuf, nframes * frame_bytes);
215
216	return 0;
217}
218
219static int flush_record_buffer(struct cras_iodev *iodev)
220{
221	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
222	struct byte_buffer *sbuf = loopdev->sample_buffer;
223	unsigned int queued_bytes = buf_queued_bytes(sbuf);
224	buf_increment_read(sbuf, queued_bytes);
225	return 0;
226}
227
228static void update_active_node(struct cras_iodev *iodev, unsigned node_idx,
229			       unsigned dev_enabled)
230{
231}
232
233static struct cras_iodev *create_loopback_iodev(enum CRAS_LOOPBACK_TYPE type)
234{
235	struct loopback_iodev *loopback_iodev;
236	struct cras_iodev *iodev;
237
238	loopback_iodev = calloc(1, sizeof(*loopback_iodev));
239	if (loopback_iodev == NULL)
240		return NULL;
241
242	loopback_iodev->sample_buffer = byte_buffer_create(1024*16*4);
243	if (loopback_iodev->sample_buffer == NULL) {
244		free(loopback_iodev);
245		return NULL;
246	}
247
248	loopback_iodev->loopback_type = type;
249
250	iodev = &loopback_iodev->base;
251	iodev->direction = CRAS_STREAM_INPUT;
252	snprintf(iodev->info.name, ARRAY_SIZE(iodev->info.name), "%s",
253		 loopdev_names[type]);
254	iodev->info.name[ARRAY_SIZE(iodev->info.name) - 1] = '\0';
255	iodev->info.stable_id = SuperFastHash(iodev->info.name,
256					      strlen(iodev->info.name),
257					      strlen(iodev->info.name));
258	iodev->info.stable_id_new = iodev->info.stable_id;
259
260	iodev->supported_rates = loopback_supported_rates;
261	iodev->supported_channel_counts = loopback_supported_channel_counts;
262	iodev->supported_formats = loopback_supported_formats;
263	iodev->buffer_size = LOOPBACK_BUFFER_SIZE;
264
265	iodev->frames_queued = frames_queued;
266	iodev->delay_frames = delay_frames;
267	iodev->update_active_node = update_active_node;
268	iodev->open_dev = open_record_dev;
269	iodev->close_dev = close_record_dev;
270	iodev->get_buffer = get_record_buffer;
271	iodev->put_buffer = put_record_buffer;
272	iodev->flush_buffer = flush_record_buffer;
273
274	return iodev;
275}
276
277/*
278 * Exported Interface.
279 */
280
281struct cras_iodev *loopback_iodev_create(enum CRAS_LOOPBACK_TYPE type)
282{
283	struct cras_iodev *iodev;
284	struct cras_ionode *node;
285	enum CRAS_NODE_TYPE node_type;
286
287	switch (type) {
288	case LOOPBACK_POST_MIX_PRE_DSP:
289		node_type = CRAS_NODE_TYPE_POST_MIX_PRE_DSP;
290		break;
291	case LOOPBACK_POST_DSP:
292		node_type = CRAS_NODE_TYPE_POST_DSP;
293		break;
294	default:
295		return NULL;
296	}
297
298	iodev = create_loopback_iodev(type);
299	if (iodev == NULL)
300		return NULL;
301
302	/* Create a dummy ionode */
303	node = (struct cras_ionode *)calloc(1, sizeof(*node));
304	node->dev = iodev;
305	node->type = node_type;
306	node->plugged = 1;
307	node->volume = 100;
308	node->stable_id = iodev->info.stable_id;
309	node->stable_id_new = iodev->info.stable_id_new;
310	node->software_volume_needed = 0;
311	node->max_software_gain = 0;
312	strcpy(node->name, loopdev_names[type]);
313	cras_iodev_add_node(iodev, node);
314	cras_iodev_set_active_node(iodev, node);
315
316	cras_iodev_list_add_input(iodev);
317
318	return iodev;
319}
320
321void loopback_iodev_destroy(struct cras_iodev *iodev)
322{
323	struct loopback_iodev *loopdev = (struct loopback_iodev *)iodev;
324	struct byte_buffer *sbuf = loopdev->sample_buffer;
325
326	cras_iodev_list_rm_input(iodev);
327
328	byte_buffer_destroy(sbuf);
329	free(loopdev);
330}
331