diff options
Diffstat (limited to 'spa/plugins/v4l2/v4l2-source.c')
-rw-r--r-- | spa/plugins/v4l2/v4l2-source.c | 93 |
1 files changed, 61 insertions, 32 deletions
diff --git a/spa/plugins/v4l2/v4l2-source.c b/spa/plugins/v4l2/v4l2-source.c index 016092a1..a789321b 100644 --- a/spa/plugins/v4l2/v4l2-source.c +++ b/spa/plugins/v4l2/v4l2-source.c @@ -146,23 +146,33 @@ struct impl { #include "v4l2-utils.c" +static int impl_node_wait(struct spa_node *node, int res, struct spa_pending *pending, + spa_result_func_t func, void *data) +{ + return -ENOTSUP; +} + static int impl_node_enum_params(struct spa_node *node, - uint32_t id, uint32_t *index, + uint32_t id, uint32_t start, uint32_t num, const struct spa_pod *filter, - struct spa_pod **result, - struct spa_pod_builder *builder) + spa_result_func_t func, void *data) { struct impl *this; struct spa_pod *param; struct spa_pod_builder b = { 0 }; uint8_t buffer[1024]; + struct spa_result_node_enum_params result; + uint32_t count = 0; + int res; spa_return_val_if_fail(node != NULL, -EINVAL); - spa_return_val_if_fail(index != NULL, -EINVAL); - spa_return_val_if_fail(builder != NULL, -EINVAL); + spa_return_val_if_fail(num != 0, -EINVAL); + spa_return_val_if_fail(func != NULL, -EINVAL); this = SPA_CONTAINER_OF(node, struct impl, node); + result.next = start; + next: spa_pod_builder_init(&b, buffer, sizeof(buffer)); @@ -172,10 +182,10 @@ static int impl_node_enum_params(struct spa_node *node, uint32_t list[] = { SPA_PARAM_PropInfo, SPA_PARAM_Props }; - if (*index < SPA_N_ELEMENTS(list)) + if (result.next < SPA_N_ELEMENTS(list)) param = spa_pod_builder_add_object(&b, SPA_TYPE_OBJECT_ParamList, id, - SPA_PARAM_LIST_id, SPA_POD_Id(list[*index])); + SPA_PARAM_LIST_id, SPA_POD_Id(list[result.next])); else return 0; break; @@ -184,7 +194,7 @@ static int impl_node_enum_params(struct spa_node *node, { struct props *p = &this->props; - switch (*index) { + switch (result.next) { case 0: param = spa_pod_builder_add_object(&b, SPA_TYPE_OBJECT_PropInfo, id, @@ -215,7 +225,7 @@ static int impl_node_enum_params(struct spa_node *node, { struct props *p = &this->props; - switch (*index) { + switch (result.next) { case 0: param = spa_pod_builder_add_object(&b, SPA_TYPE_OBJECT_Props, id, @@ -232,12 +242,18 @@ static int impl_node_enum_params(struct spa_node *node, return -ENOENT; } - (*index)++; + result.next++; - if (spa_pod_filter(builder, result, param, filter) < 0) + if (spa_pod_filter(&b, &result.param, param, filter) < 0) goto next; - return 1; + if ((res = func(data, count, 1, &result)) != 0) + return res; + + if (++count != num) + goto next; + + return 0; } static int impl_node_set_param(struct spa_node *node, @@ -387,7 +403,7 @@ static int impl_node_remove_port(struct spa_node *node, static int port_get_format(struct spa_node *node, enum spa_direction direction, uint32_t port_id, - uint32_t *index, + uint32_t index, const struct spa_pod *filter, struct spa_pod **param, struct spa_pod_builder *builder) @@ -398,7 +414,7 @@ static int port_get_format(struct spa_node *node, if (!port->have_format) return -EIO; - if (*index > 0) + if (index > 0) return 0; spa_pod_builder_push_object(builder, &f, SPA_TYPE_OBJECT_Format, SPA_PARAM_Format); @@ -440,10 +456,9 @@ static int port_get_format(struct spa_node *node, static int impl_node_port_enum_params(struct spa_node *node, enum spa_direction direction, uint32_t port_id, - uint32_t id, uint32_t *index, + uint32_t id, uint32_t start, uint32_t num, const struct spa_pod *filter, - struct spa_pod **result, - struct spa_pod_builder *builder) + spa_result_func_t func, void *data) { struct impl *this; @@ -451,11 +466,13 @@ static int impl_node_port_enum_params(struct spa_node *node, struct spa_pod *param; struct spa_pod_builder b = { 0 }; uint8_t buffer[1024]; + struct spa_result_node_enum_params result; + uint32_t count = 0; int res; spa_return_val_if_fail(node != NULL, -EINVAL); - spa_return_val_if_fail(index != NULL, -EINVAL); - spa_return_val_if_fail(builder != NULL, -EINVAL); + spa_return_val_if_fail(num != 0, -EINVAL); + spa_return_val_if_fail(func != NULL, -EINVAL); this = SPA_CONTAINER_OF(node, struct impl, node); @@ -463,6 +480,8 @@ static int impl_node_port_enum_params(struct spa_node *node, port = GET_PORT(this, direction, port_id); + result.next = start; + next: spa_pod_builder_init(&b, buffer, sizeof(buffer)); @@ -476,28 +495,29 @@ static int impl_node_port_enum_params(struct spa_node *node, SPA_PARAM_Meta, SPA_PARAM_IO }; - if (*index < SPA_N_ELEMENTS(list)) + if (result.next < SPA_N_ELEMENTS(list)) param = spa_pod_builder_add_object(&b, SPA_TYPE_OBJECT_ParamList, id, - SPA_PARAM_LIST_id, SPA_POD_Id(list[*index])); + SPA_PARAM_LIST_id, SPA_POD_Id(list[result.next])); else return 0; break; } case SPA_PARAM_PropInfo: - return spa_v4l2_enum_controls(this, index, filter, result, builder); + return spa_v4l2_enum_controls(this, start, num, filter, func, data); case SPA_PARAM_EnumFormat: - return spa_v4l2_enum_format(this, index, filter, result, builder); + return spa_v4l2_enum_format(this, start, num, filter, func, data); case SPA_PARAM_Format: - if((res = port_get_format(node, direction, port_id, index, filter, ¶m, &b)) <= 0) + if((res = port_get_format(node, direction, port_id, + result.next, filter, ¶m, &b)) <= 0) return res; break; case SPA_PARAM_Buffers: if (!port->have_format) return -EIO; - if (*index > 0) + if (result.next > 0) return 0; param = spa_pod_builder_add_object(&b, @@ -510,7 +530,7 @@ static int impl_node_port_enum_params(struct spa_node *node, break; case SPA_PARAM_Meta: - switch (*index) { + switch (result.next) { case 0: param = spa_pod_builder_add_object(&b, SPA_TYPE_OBJECT_ParamMeta, id, @@ -522,7 +542,7 @@ static int impl_node_port_enum_params(struct spa_node *node, } break; case SPA_PARAM_IO: - switch (*index) { + switch (result.next) { case 0: param = spa_pod_builder_add_object(&b, SPA_TYPE_OBJECT_ParamIO, id, @@ -549,12 +569,18 @@ static int impl_node_port_enum_params(struct spa_node *node, return -ENOENT; } - (*index)++; + result.next++; - if (spa_pod_filter(builder, result, param, filter) < 0) + if (spa_pod_filter(&b, &result.param, param, filter) < 0) goto next; - return 1; + if ((res = func(data, count, 1, &result)) != 0) + return res; + + if (++count != num) + goto next; + + return 0; } static int port_set_format(struct spa_node *node, @@ -880,11 +906,12 @@ static int impl_node_process(struct spa_node *node) static const struct spa_node impl_node = { SPA_VERSION_NODE, + .set_callbacks = impl_node_set_callbacks, + .wait = impl_node_wait, .enum_params = impl_node_enum_params, .set_param = impl_node_set_param, .set_io = impl_node_set_io, .send_command = impl_node_send_command, - .set_callbacks = impl_node_set_callbacks, .add_port = impl_node_add_port, .remove_port = impl_node_remove_port, .port_enum_params = impl_node_port_enum_params, @@ -942,7 +969,9 @@ impl_init(const struct spa_handle_factory *factory, spa_return_val_if_fail(handle != NULL, -EINVAL); handle->get_interface = impl_get_interface; - handle->clear = impl_clear, this = (struct impl *) handle; + handle->clear = impl_clear; + + this = (struct impl *) handle; for (i = 0; i < n_support; i++) { if (support[i].type == SPA_TYPE_INTERFACE_Log) |