summaryrefslogtreecommitdiffstats
path: root/common.c
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2007-05-17 19:19:08 +0000
committerLennart Poettering <lennart@poettering.net>2007-05-17 19:19:08 +0000
commitc58ce0879c1cabfd31dd8657d2594d78f13b1360 (patch)
treeb9254d64d59da3037cec32a540583813c8d76b2e /common.c
parentacd9a2853021249bed55a8a47ef2a3d4d565b2c5 (diff)
add handling of watermarks
git-svn-id: file:///home/lennart/svn/public/libsydney/trunk@25 9ba3c220-e4d3-45a2-8aa3-73fcc9aff6ce
Diffstat (limited to 'common.c')
-rw-r--r--common.c49
1 files changed, 47 insertions, 2 deletions
diff --git a/common.c b/common.c
index 9810633..dfdde95 100644
--- a/common.c
+++ b/common.c
@@ -67,6 +67,7 @@ int sa_stream_create_pcm(
unsigned nchannels) {
int ret;
+ size_t lwm;
sa_return_val_if_fail(s, SA_ERROR_INVALID);
sa_return_val_if_fail(mode == SA_MODE_RDONLY || mode == SA_MODE_WRONLY || mode == SA_MODE_RDWR, SA_ERROR_INVALID);
@@ -93,7 +94,30 @@ int sa_stream_create_pcm(
if ((ret = sa_stream_change_rate(*s, rate)))
goto fail;
+
+ lwm = ((*s)->pcm_frame_size * (*s)->pcm_attrs.rate) / 20; /* 50 ms */
+
+ if (lwm <= 0)
+ lwm = (*s)->pcm_frame_size * (*s)->pcm_attrs.rate; /* 1s */
+
+ if (mode & SA_MODE_RDONLY) {
+
+ if ((ret = sa_stream_set_read_lower_watermark(*s, lwm)))
+ goto fail;
+
+ if ((ret = sa_stream_set_read_upper_watermark(*s, lwm*2)))
+ goto fail;
+ }
+
+ if (mode & SA_MODE_WRONLY) {
+ if ((ret = sa_stream_set_write_lower_watermark(*s, lwm)))
+ goto fail;
+
+ if ((ret = sa_stream_set_write_upper_watermark(*s, lwm*2)))
+ goto fail;
+ }
+
oil_init();
if (client_name)
@@ -113,6 +137,11 @@ int sa_stream_open(sa_stream_t *s) {
sa_return_val_if_fail(s, SA_ERROR_INVALID);
sa_return_val_if_fail(s->state == SA_STATE_INIT, SA_ERROR_STATE);
+ sa_return_val_if_fail(s->codec || s->pcm_attrs.channel_map, SA_ERROR_NO_INIT);
+ sa_return_val_if_fail(!(s->mode & SA_MODE_RDONLY) || (s->read_lower_watermark <= s->read_upper_watermark), SA_ERROR_INVALID);
+ sa_return_val_if_fail(!(s->mode & SA_MODE_WRONLY) || (s->write_lower_watermark <= s->write_upper_watermark), SA_ERROR_INVALID);
+ sa_return_val_if_fail(!(s->mode & SA_MODE_RDONLY) || !s->codec || (s->read_lower_watermark > 0 && s->read_upper_watermark > 0), SA_ERROR_NO_INIT);
+ sa_return_val_if_fail(!(s->mode & SA_MODE_WRONLY) || !s->codec || (s->write_lower_watermark > 0 && s->write_upper_watermark > 0), SA_ERROR_NO_INIT);
if ((ret = driver_open(s)) == 0)
s->state = SA_STATE_STOPPED;
@@ -256,7 +285,6 @@ int sa_stream_start_thread(sa_stream_t *s, sa_event_callback_t *callback) {
sa_return_val_if_fail(s, SA_ERROR_INVALID);
sa_return_val_if_fail(callback, SA_ERROR_INVALID);
sa_return_val_if_fail(s->state == SA_STATE_INIT, SA_ERROR_STATE);
- sa_return_val_if_fail(s->codec || s->pcm_attrs.channel_map, SA_ERROR_NO_INIT);
return driver_start_thread(s, callback);
}
@@ -396,6 +424,14 @@ int sa_stream_set_adjust_pcm_format(sa_stream_t *s, sa_adjust_t direction) {
return SA_SUCCESS;
}
+int sa_stream_set_adjust_watermarks(sa_stream_t *s, sa_adjust_t direction) {
+ sa_return_val_if_fail(s, SA_ERROR_INVALID);
+ sa_return_val_if_fail(s->state == SA_STATE_INIT, SA_ERROR_STATE);
+
+ s->adjust_watermarks = direction;
+ return SA_SUCCESS;
+}
+
int sa_stream_get_state(sa_stream_t *s, sa_state_t *state) {
sa_return_val_if_fail(s, SA_ERROR_INVALID);
sa_return_val_if_fail(state, SA_ERROR_INVALID);
@@ -581,6 +617,14 @@ int sa_stream_get_adjust_pcm_format(sa_stream_t *s, sa_adjust_t *direction) {
return SA_SUCCESS;
}
+int sa_stream_get_adjust_watermarks(sa_stream_t *s, sa_adjust_t *direction) {
+ sa_return_val_if_fail(s, SA_ERROR_INVALID);
+ sa_return_val_if_fail(direction, SA_ERROR_INVALID);
+
+ *direction = s->adjust_watermarks;
+ return SA_SUCCESS;
+}
+
int sa_stream_get_user_data(sa_stream_t *s, void **value) {
sa_return_val_if_fail(s, SA_ERROR_INVALID);
sa_return_val_if_fail(value, SA_ERROR_INVALID);
@@ -873,7 +917,8 @@ int sa_stream_change_meta_data(sa_stream_t *s, const char *name, const void *dat
sa_free(s->meta_data[m->idx]);
s->meta_data[m->idx] = d;
s->meta_data_size[m->idx] = size;
- }
+ } else
+ sa_free(d);
return ret;
}