mirror of
https://gitlab.freedesktop.org/pipewire/pipewire.git
synced 2025-10-29 05:40:27 -04:00
remove spalib
This commit is contained in:
parent
f532fd8681
commit
a6ad8f747f
69 changed files with 612 additions and 1250 deletions
469
spa/lib/debug.c
469
spa/lib/debug.c
|
|
@ -1,469 +0,0 @@
|
|||
/* Simple Plugin API
|
||||
* Copyright (C) 2016 Wim Taymans <wim.taymans@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
* Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <unistd.h>
|
||||
#include <errno.h>
|
||||
#include <sys/eventfd.h>
|
||||
|
||||
#include <spa/support/loop.h>
|
||||
#include <spa/pod/parser.h>
|
||||
|
||||
#include "debug.h"
|
||||
|
||||
static const struct spa_type_map *map;
|
||||
|
||||
void spa_debug_set_type_map(const struct spa_type_map *m)
|
||||
{
|
||||
map = m;
|
||||
}
|
||||
|
||||
int spa_debug_port_info(const struct spa_port_info *info)
|
||||
{
|
||||
if (info == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
fprintf(stderr, "struct spa_port_info %p:\n", info);
|
||||
fprintf(stderr, " flags: \t%08x\n", info->flags);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int spa_debug_buffer(const struct spa_buffer *buffer)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (buffer == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
fprintf(stderr, "spa_buffer %p:\n", buffer);
|
||||
fprintf(stderr, " id: %08X\n", buffer->id);
|
||||
fprintf(stderr, " n_metas: %u (at %p)\n", buffer->n_metas, buffer->metas);
|
||||
for (i = 0; i < buffer->n_metas; i++) {
|
||||
struct spa_meta *m = &buffer->metas[i];
|
||||
const char *type_name;
|
||||
|
||||
type_name = spa_type_map_get_type(map, m->type);
|
||||
fprintf(stderr, " meta %d: type %d (%s), data %p, size %d:\n", i, m->type,
|
||||
type_name, m->data, m->size);
|
||||
|
||||
if (!strcmp(type_name, SPA_TYPE_META__Header)) {
|
||||
struct spa_meta_header *h = m->data;
|
||||
fprintf(stderr, " struct spa_meta_header:\n");
|
||||
fprintf(stderr, " flags: %08x\n", h->flags);
|
||||
fprintf(stderr, " seq: %u\n", h->seq);
|
||||
fprintf(stderr, " pts: %" PRIi64 "\n", h->pts);
|
||||
fprintf(stderr, " dts_offset: %" PRIi64 "\n", h->dts_offset);
|
||||
} else if (strstr(type_name, SPA_TYPE_META_REGION_BASE) == type_name) {
|
||||
struct spa_meta_region *h = m->data;
|
||||
fprintf(stderr, " struct spa_meta_region:\n");
|
||||
fprintf(stderr, " x: %d\n", h->region.position.x);
|
||||
fprintf(stderr, " y: %d\n", h->region.position.y);
|
||||
fprintf(stderr, " width: %d\n", h->region.size.width);
|
||||
fprintf(stderr, " height: %d\n", h->region.size.height);
|
||||
} else if (strstr(type_name, SPA_TYPE_META_REGION_ARRAY_BASE) == type_name) {
|
||||
struct spa_meta_region *p;
|
||||
fprintf(stderr, " struct spa_meta_region_array:\n");
|
||||
spa_meta_region_for_each(p, m) {
|
||||
fprintf(stderr, " x: %d\n", p->region.position.x);
|
||||
fprintf(stderr, " y: %d\n", p->region.position.y);
|
||||
fprintf(stderr, " width: %d\n", p->region.size.width);
|
||||
fprintf(stderr, " height: %d\n", p->region.size.height);
|
||||
}
|
||||
} else {
|
||||
fprintf(stderr, " Unknown:\n");
|
||||
spa_debug_dump_mem(m->data, m->size);
|
||||
}
|
||||
}
|
||||
fprintf(stderr, " n_datas: \t%u (at %p)\n", buffer->n_datas, buffer->datas);
|
||||
for (i = 0; i < buffer->n_datas; i++) {
|
||||
struct spa_data *d = &buffer->datas[i];
|
||||
fprintf(stderr, " type: %d (%s)\n", d->type,
|
||||
spa_type_map_get_type(map, d->type));
|
||||
fprintf(stderr, " flags: %d\n", d->flags);
|
||||
fprintf(stderr, " data: %p\n", d->data);
|
||||
fprintf(stderr, " fd: %d\n", d->fd);
|
||||
fprintf(stderr, " offset: %d\n", d->mapoffset);
|
||||
fprintf(stderr, " maxsize: %u\n", d->maxsize);
|
||||
fprintf(stderr, " chunk: %p\n", d->chunk);
|
||||
fprintf(stderr, " offset: %d\n", d->chunk->offset);
|
||||
fprintf(stderr, " size: %u\n", d->chunk->size);
|
||||
fprintf(stderr, " stride: %d\n", d->chunk->stride);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int spa_debug_dump_mem(const void *mem, size_t size)
|
||||
{
|
||||
const uint8_t *t = mem;
|
||||
int i;
|
||||
|
||||
if (mem == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
for (i = 0; i < size; i++) {
|
||||
if (i % 16 == 0)
|
||||
fprintf(stderr,"%p: ", &t[i]);
|
||||
fprintf(stderr,"%02x ", t[i]);
|
||||
if (i % 16 == 15 || i == size - 1)
|
||||
fprintf(stderr,"\n");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const char *pod_type_names[] = {
|
||||
[SPA_POD_TYPE_INVALID] = "invalid",
|
||||
[SPA_POD_TYPE_NONE] = "none",
|
||||
[SPA_POD_TYPE_BOOL] = "bool",
|
||||
[SPA_POD_TYPE_ID] = "id",
|
||||
[SPA_POD_TYPE_INT] = "int",
|
||||
[SPA_POD_TYPE_LONG] = "long",
|
||||
[SPA_POD_TYPE_FLOAT] = "float",
|
||||
[SPA_POD_TYPE_DOUBLE] = "double",
|
||||
[SPA_POD_TYPE_STRING] = "string",
|
||||
[SPA_POD_TYPE_BYTES] = "bytes",
|
||||
[SPA_POD_TYPE_RECTANGLE] = "rectangle",
|
||||
[SPA_POD_TYPE_FRACTION] = "fraction",
|
||||
[SPA_POD_TYPE_BITMAP] = "bitmap",
|
||||
[SPA_POD_TYPE_ARRAY] = "array",
|
||||
[SPA_POD_TYPE_STRUCT] = "struct",
|
||||
[SPA_POD_TYPE_OBJECT] = "object",
|
||||
[SPA_POD_TYPE_POINTER] = "pointer",
|
||||
[SPA_POD_TYPE_FD] = "fd",
|
||||
[SPA_POD_TYPE_PROP] = "prop",
|
||||
[SPA_POD_TYPE_POD] = "pod"
|
||||
};
|
||||
|
||||
static void
|
||||
print_pod_value(uint32_t size, uint32_t type, void *body, int prefix)
|
||||
{
|
||||
switch (type) {
|
||||
case SPA_POD_TYPE_BOOL:
|
||||
fprintf(stderr,"%-*sBool %d\n", prefix, "", *(int32_t *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_ID:
|
||||
fprintf(stderr,"%-*sId %d %s\n", prefix, "", *(int32_t *) body,
|
||||
spa_type_map_get_type(map, *(int32_t *) body));
|
||||
break;
|
||||
case SPA_POD_TYPE_INT:
|
||||
fprintf(stderr,"%-*sInt %d\n", prefix, "", *(int32_t *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_LONG:
|
||||
fprintf(stderr,"%-*sLong %" PRIi64 "\n", prefix, "", *(int64_t *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_FLOAT:
|
||||
fprintf(stderr,"%-*sFloat %f\n", prefix, "", *(float *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_DOUBLE:
|
||||
fprintf(stderr,"%-*sDouble %f\n", prefix, "", *(double *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_STRING:
|
||||
fprintf(stderr,"%-*sString \"%s\"\n", prefix, "", (char *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_FD:
|
||||
fprintf(stderr,"%-*sFd %d\n", prefix, "", *(int *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_POINTER:
|
||||
{
|
||||
struct spa_pod_pointer_body *b = body;
|
||||
fprintf(stderr,"%-*sPointer %s %p\n", prefix, "",
|
||||
map ? spa_type_map_get_type(map, b->type) : "*no map*", b->value);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_RECTANGLE:
|
||||
{
|
||||
struct spa_rectangle *r = body;
|
||||
fprintf(stderr,"%-*sRectangle %dx%d\n", prefix, "", r->width, r->height);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_FRACTION:
|
||||
{
|
||||
struct spa_fraction *f = body;
|
||||
fprintf(stderr,"%-*sFraction %d/%d\n", prefix, "", f->num, f->denom);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_BITMAP:
|
||||
fprintf(stderr,"%-*sBitmap\n", prefix, "");
|
||||
break;
|
||||
case SPA_POD_TYPE_ARRAY:
|
||||
{
|
||||
struct spa_pod_array_body *b = body;
|
||||
void *p;
|
||||
fprintf(stderr,"%-*sArray: child.size %d, child.type %d\n", prefix, "",
|
||||
b->child.size, b->child.type);
|
||||
|
||||
SPA_POD_ARRAY_BODY_FOREACH(b, size, p)
|
||||
print_pod_value(b->child.size, b->child.type, p, prefix + 2);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_STRUCT:
|
||||
{
|
||||
struct spa_pod *b = body, *p;
|
||||
fprintf(stderr,"%-*sStruct: size %d\n", prefix, "", size);
|
||||
SPA_POD_FOREACH(b, size, p)
|
||||
print_pod_value(p->size, p->type, SPA_POD_BODY(p), prefix + 2);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_OBJECT:
|
||||
{
|
||||
struct spa_pod_object_body *b = body;
|
||||
struct spa_pod *p;
|
||||
|
||||
fprintf(stderr,"%-*sObject: size %d, id %s, type %s\n", prefix, "", size,
|
||||
map ? spa_type_map_get_type(map, b->id) : "*no map*",
|
||||
map ? spa_type_map_get_type(map, b->type) : "*no map*");
|
||||
SPA_POD_OBJECT_BODY_FOREACH(b, size, p)
|
||||
print_pod_value(p->size, p->type, SPA_POD_BODY(p), prefix + 2);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_PROP:
|
||||
{
|
||||
struct spa_pod_prop_body *b = body;
|
||||
void *alt;
|
||||
int i;
|
||||
|
||||
fprintf(stderr,"%-*sProp: key %s, flags %d\n", prefix, "",
|
||||
map ? spa_type_map_get_type(map, b->key) : "*no map*", b->flags);
|
||||
if (b->flags & SPA_POD_PROP_FLAG_UNSET)
|
||||
fprintf(stderr,"%-*sUnset (Default):\n", prefix + 2, "");
|
||||
else
|
||||
fprintf(stderr,"%-*sValue: size %u\n", prefix + 2, "", b->value.size);
|
||||
print_pod_value(b->value.size, b->value.type, SPA_POD_BODY(&b->value),
|
||||
prefix + 4);
|
||||
|
||||
i = 0;
|
||||
switch (b->flags & SPA_POD_PROP_RANGE_MASK) {
|
||||
case SPA_POD_PROP_RANGE_NONE:
|
||||
break;
|
||||
case SPA_POD_PROP_RANGE_MIN_MAX:
|
||||
SPA_POD_PROP_ALTERNATIVE_FOREACH(b, size, alt) {
|
||||
if (i == 0)
|
||||
fprintf(stderr,"%-*sMin: ", prefix + 2, "");
|
||||
else if (i == 1)
|
||||
fprintf(stderr,"%-*sMax: ", prefix + 2, "");
|
||||
else
|
||||
break;
|
||||
print_pod_value(b->value.size, b->value.type, alt, 0);
|
||||
i++;
|
||||
}
|
||||
break;
|
||||
case SPA_POD_PROP_RANGE_STEP:
|
||||
SPA_POD_PROP_ALTERNATIVE_FOREACH(b, size, alt) {
|
||||
if (i == 0)
|
||||
fprintf(stderr,"%-*sMin: ", prefix + 2, "");
|
||||
else if (i == 1)
|
||||
fprintf(stderr,"%-*sMax: ", prefix + 2, "");
|
||||
else if (i == 2)
|
||||
fprintf(stderr,"%-*sStep: ", prefix + 2, "");
|
||||
else
|
||||
break;
|
||||
print_pod_value(b->value.size, b->value.type, alt, 0);
|
||||
i++;
|
||||
}
|
||||
break;
|
||||
case SPA_POD_PROP_RANGE_ENUM:
|
||||
SPA_POD_PROP_ALTERNATIVE_FOREACH(b, size, alt) {
|
||||
if (i == 0)
|
||||
fprintf(stderr,"%-*sEnum:\n", prefix + 2, "");
|
||||
print_pod_value(b->value.size, b->value.type, alt, prefix + 4);
|
||||
i++;
|
||||
}
|
||||
break;
|
||||
case SPA_POD_PROP_RANGE_FLAGS:
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_BYTES:
|
||||
fprintf(stderr,"%-*sBytes\n", prefix, "");
|
||||
spa_debug_dump_mem(body, size);
|
||||
break;
|
||||
case SPA_POD_TYPE_NONE:
|
||||
fprintf(stderr,"%-*sNone\n", prefix, "");
|
||||
spa_debug_dump_mem(body, size);
|
||||
break;
|
||||
default:
|
||||
fprintf(stderr,"unhandled POD type %d\n", type);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
print_format_value(uint32_t size, uint32_t type, void *body)
|
||||
{
|
||||
switch (type) {
|
||||
case SPA_POD_TYPE_BOOL:
|
||||
fprintf(stderr, "%s", *(int32_t *) body ? "true" : "false");
|
||||
break;
|
||||
case SPA_POD_TYPE_ID:
|
||||
{
|
||||
const char *str = map ? spa_type_map_get_type(map, *(int32_t *) body) : NULL;
|
||||
if (str) {
|
||||
const char *h = rindex(str, ':');
|
||||
if (h)
|
||||
str = h + 1;
|
||||
} else {
|
||||
str = "unknown";
|
||||
}
|
||||
fprintf(stderr, "%s", str);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_INT:
|
||||
fprintf(stderr, "%" PRIi32, *(int32_t *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_LONG:
|
||||
fprintf(stderr, "%" PRIi64, *(int64_t *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_FLOAT:
|
||||
fprintf(stderr, "%f", *(float *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_DOUBLE:
|
||||
fprintf(stderr, "%g", *(double *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_STRING:
|
||||
fprintf(stderr, "%s", (char *) body);
|
||||
break;
|
||||
case SPA_POD_TYPE_RECTANGLE:
|
||||
{
|
||||
struct spa_rectangle *r = body;
|
||||
fprintf(stderr, "%" PRIu32 "x%" PRIu32, r->width, r->height);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_FRACTION:
|
||||
{
|
||||
struct spa_fraction *f = body;
|
||||
fprintf(stderr, "%" PRIu32 "/%" PRIu32, f->num, f->denom);
|
||||
break;
|
||||
}
|
||||
case SPA_POD_TYPE_BITMAP:
|
||||
fprintf(stderr, "Bitmap");
|
||||
break;
|
||||
case SPA_POD_TYPE_BYTES:
|
||||
fprintf(stderr, "Bytes");
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static int spa_debug_format(const struct spa_pod *format)
|
||||
{
|
||||
int i;
|
||||
const char *media_type;
|
||||
const char *media_subtype;
|
||||
struct spa_pod *pod;
|
||||
uint32_t mtype, mstype;
|
||||
|
||||
if (format == NULL || SPA_POD_TYPE(format) != SPA_POD_TYPE_OBJECT)
|
||||
return -EINVAL;
|
||||
|
||||
if (spa_pod_object_parse(format, "I", &mtype,
|
||||
"I", &mstype) < 0)
|
||||
return -EINVAL;
|
||||
|
||||
media_type = spa_type_map_get_type(map, mtype);
|
||||
media_subtype = spa_type_map_get_type(map, mstype);
|
||||
|
||||
fprintf(stderr, "%-6s %s/%s\n", "", rindex(media_type, ':') + 1,
|
||||
rindex(media_subtype, ':') + 1);
|
||||
|
||||
SPA_POD_OBJECT_FOREACH((struct spa_pod_object*)format, pod) {
|
||||
struct spa_pod_prop *prop;
|
||||
const char *key;
|
||||
|
||||
if (pod->type != SPA_POD_TYPE_PROP)
|
||||
continue;
|
||||
|
||||
prop = (struct spa_pod_prop *)pod;
|
||||
|
||||
if ((prop->body.flags & SPA_POD_PROP_FLAG_UNSET) &&
|
||||
(prop->body.flags & SPA_POD_PROP_FLAG_OPTIONAL))
|
||||
continue;
|
||||
|
||||
key = spa_type_map_get_type(map, prop->body.key);
|
||||
|
||||
fprintf(stderr, " %20s : (%s) ", rindex(key, ':') + 1,
|
||||
pod_type_names[prop->body.value.type]);
|
||||
|
||||
if (!(prop->body.flags & SPA_POD_PROP_FLAG_UNSET)) {
|
||||
print_format_value(prop->body.value.size,
|
||||
prop->body.value.type, SPA_POD_BODY(&prop->body.value));
|
||||
} else {
|
||||
const char *ssep, *esep, *sep;
|
||||
void *alt;
|
||||
|
||||
switch (prop->body.flags & SPA_POD_PROP_RANGE_MASK) {
|
||||
case SPA_POD_PROP_RANGE_MIN_MAX:
|
||||
case SPA_POD_PROP_RANGE_STEP:
|
||||
ssep = "[ ";
|
||||
sep = ", ";
|
||||
esep = " ]";
|
||||
break;
|
||||
default:
|
||||
case SPA_POD_PROP_RANGE_ENUM:
|
||||
case SPA_POD_PROP_RANGE_FLAGS:
|
||||
ssep = "{ ";
|
||||
sep = ", ";
|
||||
esep = " }";
|
||||
break;
|
||||
}
|
||||
|
||||
fprintf(stderr, "%s", ssep);
|
||||
|
||||
i = 0;
|
||||
SPA_POD_PROP_ALTERNATIVE_FOREACH(&prop->body, prop->pod.size, alt) {
|
||||
if (i > 0)
|
||||
fprintf(stderr, "%s", sep);
|
||||
print_format_value(prop->body.value.size,
|
||||
prop->body.value.type, alt);
|
||||
i++;
|
||||
}
|
||||
fprintf(stderr, "%s", esep);
|
||||
}
|
||||
fprintf(stderr, "\n");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int spa_debug_pod(const struct spa_pod *pod, uint32_t flags)
|
||||
{
|
||||
int res = 0;
|
||||
|
||||
if (flags & SPA_DEBUG_FLAG_FORMAT)
|
||||
res = spa_debug_format(pod);
|
||||
else
|
||||
print_pod_value(pod->size, pod->type, SPA_POD_BODY(pod), 0);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
|
||||
int spa_debug_dict(const struct spa_dict *dict)
|
||||
{
|
||||
unsigned int i;
|
||||
|
||||
if (dict == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
for (i = 0; i < dict->n_items; i++)
|
||||
fprintf(stderr, " %s = \"%s\"\n", dict->items[i].key,
|
||||
dict->items[i].value);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
|
@ -1,42 +0,0 @@
|
|||
/* Simple Plugin API
|
||||
* Copyright (C) 2016 Wim Taymans <wim.taymans@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
* Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __SPA_LIBDEBUG_H__
|
||||
#define __SPA_LIBDEBUG_H__
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <spa/node/node.h>
|
||||
#include <spa/pod/pod.h>
|
||||
|
||||
void spa_debug_set_type_map(const struct spa_type_map *map);
|
||||
|
||||
int spa_debug_port_info(const struct spa_port_info *info);
|
||||
int spa_debug_buffer(const struct spa_buffer *buffer);
|
||||
#define SPA_DEBUG_FLAG_FORMAT (1 << 0)
|
||||
int spa_debug_pod(const struct spa_pod *pod, uint32_t flags);
|
||||
int spa_debug_dump_mem(const void *data, size_t size);
|
||||
int spa_debug_dict(const struct spa_dict *dict);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* extern "C" */
|
||||
#endif
|
||||
#endif /* __SPA_LIBDEBUG_H__ */
|
||||
|
|
@ -1,18 +0,0 @@
|
|||
spalib_headers = [
|
||||
'debug.h',
|
||||
]
|
||||
|
||||
install_headers(spalib_headers, subdir : 'spa/lib')
|
||||
|
||||
spalib_sources = ['debug.c' ]
|
||||
|
||||
spalib = shared_library('spa-lib-@0@'.format(spaversion),
|
||||
spalib_sources,
|
||||
version : libversion,
|
||||
soversion : soversion,
|
||||
include_directories : [ spa_inc, spa_libinc ],
|
||||
install : true)
|
||||
|
||||
spalib_dep = declare_dependency(link_with : spalib,
|
||||
include_directories : spa_inc,
|
||||
)
|
||||
491
spa/lib/pod.c
491
spa/lib/pod.c
|
|
@ -1,491 +0,0 @@
|
|||
/* Simple Plugin API
|
||||
* Copyright (C) 2016 Wim Taymans <wim.taymans@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
* Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdint.h>
|
||||
#include <stddef.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <spa/param/props.h>
|
||||
#include <spa/pod/iter.h>
|
||||
#include <spa/pod/builder.h>
|
||||
|
||||
static int compare_value(enum spa_pod_type type, const void *r1, const void *r2)
|
||||
{
|
||||
switch (type) {
|
||||
case SPA_POD_TYPE_INVALID:
|
||||
return 0;
|
||||
case SPA_POD_TYPE_BOOL:
|
||||
case SPA_POD_TYPE_ID:
|
||||
return *(int32_t *) r1 == *(uint32_t *) r2 ? 0 : 1;
|
||||
case SPA_POD_TYPE_INT:
|
||||
return *(int32_t *) r1 - *(int32_t *) r2;
|
||||
case SPA_POD_TYPE_LONG:
|
||||
return *(int64_t *) r1 - *(int64_t *) r2;
|
||||
case SPA_POD_TYPE_FLOAT:
|
||||
return *(float *) r1 - *(float *) r2;
|
||||
case SPA_POD_TYPE_DOUBLE:
|
||||
return *(double *) r1 - *(double *) r2;
|
||||
case SPA_POD_TYPE_STRING:
|
||||
return strcmp(r1, r2);
|
||||
case SPA_POD_TYPE_RECTANGLE:
|
||||
{
|
||||
const struct spa_rectangle *rec1 = (struct spa_rectangle *) r1,
|
||||
*rec2 = (struct spa_rectangle *) r2;
|
||||
if (rec1->width == rec2->width && rec1->height == rec2->height)
|
||||
return 0;
|
||||
else if (rec1->width < rec2->width || rec1->height < rec2->height)
|
||||
return -1;
|
||||
else
|
||||
return 1;
|
||||
}
|
||||
case SPA_POD_TYPE_FRACTION:
|
||||
{
|
||||
const struct spa_fraction *f1 = (struct spa_fraction *) r1,
|
||||
*f2 = (struct spa_fraction *) r2;
|
||||
int64_t n1, n2;
|
||||
n1 = ((int64_t) f1->num) * f2->denom;
|
||||
n2 = ((int64_t) f2->num) * f1->denom;
|
||||
if (n1 < n2)
|
||||
return -1;
|
||||
else if (n1 > n2)
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void fix_default(struct spa_pod_prop *prop)
|
||||
{
|
||||
void *val = SPA_MEMBER(prop, sizeof(struct spa_pod_prop), void),
|
||||
*alt = SPA_MEMBER(val, prop->body.value.size, void);
|
||||
int i, nalt = SPA_POD_PROP_N_VALUES(prop) - 1;
|
||||
|
||||
switch (prop->body.flags & SPA_POD_PROP_RANGE_MASK) {
|
||||
case SPA_POD_PROP_RANGE_NONE:
|
||||
break;
|
||||
case SPA_POD_PROP_RANGE_MIN_MAX:
|
||||
case SPA_POD_PROP_RANGE_STEP:
|
||||
if (compare_value(prop->body.value.type, val, alt) < 0)
|
||||
memcpy(val, alt, prop->body.value.size);
|
||||
alt = SPA_MEMBER(alt, prop->body.value.size, void);
|
||||
if (compare_value(prop->body.value.type, val, alt) > 0)
|
||||
memcpy(val, alt, prop->body.value.size);
|
||||
break;
|
||||
case SPA_POD_PROP_RANGE_ENUM:
|
||||
{
|
||||
void *best = NULL;
|
||||
|
||||
for (i = 0; i < nalt; i++) {
|
||||
if (compare_value(prop->body.value.type, val, alt) == 0) {
|
||||
best = alt;
|
||||
break;
|
||||
}
|
||||
if (best == NULL)
|
||||
best = alt;
|
||||
alt = SPA_MEMBER(alt, prop->body.value.size, void);
|
||||
}
|
||||
if (best)
|
||||
memcpy(val, best, prop->body.value.size);
|
||||
|
||||
if (nalt <= 1) {
|
||||
prop->body.flags &= ~SPA_POD_PROP_FLAG_UNSET;
|
||||
prop->body.flags &= ~SPA_POD_PROP_RANGE_MASK;
|
||||
prop->body.flags |= SPA_POD_PROP_RANGE_NONE;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case SPA_POD_PROP_RANGE_FLAGS:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static inline struct spa_pod_prop *find_prop(const struct spa_pod *pod, uint32_t size, uint32_t key)
|
||||
{
|
||||
const struct spa_pod *res;
|
||||
SPA_POD_FOREACH(pod, size, res) {
|
||||
if (res->type == SPA_POD_TYPE_PROP
|
||||
&& ((struct spa_pod_prop *) res)->body.key == key)
|
||||
return (struct spa_pod_prop *) res;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static inline int
|
||||
filter_prop(struct spa_pod_builder *b,
|
||||
const struct spa_pod_prop *p1,
|
||||
const struct spa_pod_prop *p2)
|
||||
{
|
||||
struct spa_pod_prop *np;
|
||||
int nalt1, nalt2;
|
||||
void *alt1, *alt2, *a1, *a2;
|
||||
uint32_t rt1, rt2;
|
||||
int j, k;
|
||||
|
||||
/* incompatible property types */
|
||||
if (p1->body.value.type != p2->body.value.type)
|
||||
return -EINVAL;
|
||||
|
||||
rt1 = p1->body.flags & SPA_POD_PROP_RANGE_MASK;
|
||||
rt2 = p2->body.flags & SPA_POD_PROP_RANGE_MASK;
|
||||
|
||||
alt1 = SPA_MEMBER(p1, sizeof(struct spa_pod_prop), void);
|
||||
nalt1 = SPA_POD_PROP_N_VALUES(p1);
|
||||
alt2 = SPA_MEMBER(p2, sizeof(struct spa_pod_prop), void);
|
||||
nalt2 = SPA_POD_PROP_N_VALUES(p2);
|
||||
|
||||
if (p1->body.flags & SPA_POD_PROP_FLAG_UNSET) {
|
||||
alt1 = SPA_MEMBER(alt1, p1->body.value.size, void);
|
||||
nalt1--;
|
||||
} else {
|
||||
nalt1 = 1;
|
||||
rt1 = SPA_POD_PROP_RANGE_NONE;
|
||||
}
|
||||
|
||||
if (p2->body.flags & SPA_POD_PROP_FLAG_UNSET) {
|
||||
alt2 = SPA_MEMBER(alt2, p2->body.value.size, void);
|
||||
nalt2--;
|
||||
} else {
|
||||
nalt2 = 1;
|
||||
rt2 = SPA_POD_PROP_RANGE_NONE;
|
||||
}
|
||||
|
||||
/* start with copying the property */
|
||||
np = spa_pod_builder_deref(b, spa_pod_builder_push_prop(b, p1->body.key, 0));
|
||||
|
||||
/* default value */
|
||||
spa_pod_builder_raw(b, &p1->body.value, sizeof(p1->body.value) + p1->body.value.size);
|
||||
|
||||
if ((rt1 == SPA_POD_PROP_RANGE_NONE && rt2 == SPA_POD_PROP_RANGE_NONE) ||
|
||||
(rt1 == SPA_POD_PROP_RANGE_NONE && rt2 == SPA_POD_PROP_RANGE_ENUM) ||
|
||||
(rt1 == SPA_POD_PROP_RANGE_ENUM && rt2 == SPA_POD_PROP_RANGE_NONE) ||
|
||||
(rt1 == SPA_POD_PROP_RANGE_ENUM && rt2 == SPA_POD_PROP_RANGE_ENUM)) {
|
||||
int n_copied = 0;
|
||||
/* copy all equal values but don't copy the default value again */
|
||||
for (j = 0, a1 = alt1; j < nalt1; j++, a1 += p1->body.value.size) {
|
||||
for (k = 0, a2 = alt2; k < nalt2; k++, a2 += p2->body.value.size) {
|
||||
if (compare_value(p1->body.value.type, a1, a2) == 0) {
|
||||
if (rt1 == SPA_POD_PROP_RANGE_ENUM || j > 0)
|
||||
spa_pod_builder_raw(b, a1, p1->body.value.size);
|
||||
n_copied++;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (n_copied == 0)
|
||||
return -EINVAL;
|
||||
np->body.flags |= SPA_POD_PROP_RANGE_ENUM | SPA_POD_PROP_FLAG_UNSET;
|
||||
}
|
||||
|
||||
if ((rt1 == SPA_POD_PROP_RANGE_NONE && rt2 == SPA_POD_PROP_RANGE_MIN_MAX) ||
|
||||
(rt1 == SPA_POD_PROP_RANGE_ENUM && rt2 == SPA_POD_PROP_RANGE_MIN_MAX)) {
|
||||
int n_copied = 0;
|
||||
/* copy all values inside the range */
|
||||
for (j = 0, a1 = alt1, a2 = alt2; j < nalt1; j++, a1 += p1->body.value.size) {
|
||||
if (compare_value(p1->body.value.type, a1, a2) < 0)
|
||||
continue;
|
||||
if (compare_value(p1->body.value.type, a1, a2 + p2->body.value.size) > 0)
|
||||
continue;
|
||||
spa_pod_builder_raw(b, a1, p1->body.value.size);
|
||||
n_copied++;
|
||||
}
|
||||
if (n_copied == 0)
|
||||
return -EINVAL;
|
||||
np->body.flags |= SPA_POD_PROP_RANGE_ENUM | SPA_POD_PROP_FLAG_UNSET;
|
||||
}
|
||||
|
||||
if ((rt1 == SPA_POD_PROP_RANGE_NONE && rt2 == SPA_POD_PROP_RANGE_STEP) ||
|
||||
(rt1 == SPA_POD_PROP_RANGE_ENUM && rt2 == SPA_POD_PROP_RANGE_STEP)) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
if ((rt1 == SPA_POD_PROP_RANGE_MIN_MAX && rt2 == SPA_POD_PROP_RANGE_NONE) ||
|
||||
(rt1 == SPA_POD_PROP_RANGE_MIN_MAX && rt2 == SPA_POD_PROP_RANGE_ENUM)) {
|
||||
int n_copied = 0;
|
||||
/* copy all values inside the range */
|
||||
for (k = 0, a1 = alt1, a2 = alt2; k < nalt2; k++, a2 += p2->body.value.size) {
|
||||
if (compare_value(p1->body.value.type, a2, a1) < 0)
|
||||
continue;
|
||||
if (compare_value(p1->body.value.type, a2, a1 + p1->body.value.size) > 0)
|
||||
continue;
|
||||
spa_pod_builder_raw(b, a2, p2->body.value.size);
|
||||
n_copied++;
|
||||
}
|
||||
if (n_copied == 0)
|
||||
return -EINVAL;
|
||||
np->body.flags |= SPA_POD_PROP_RANGE_ENUM | SPA_POD_PROP_FLAG_UNSET;
|
||||
}
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_MIN_MAX && rt2 == SPA_POD_PROP_RANGE_MIN_MAX) {
|
||||
if (compare_value(p1->body.value.type, alt1, alt2) < 0)
|
||||
spa_pod_builder_raw(b, alt2, p2->body.value.size);
|
||||
else
|
||||
spa_pod_builder_raw(b, alt1, p1->body.value.size);
|
||||
|
||||
alt1 += p1->body.value.size;
|
||||
alt2 += p2->body.value.size;
|
||||
|
||||
if (compare_value(p1->body.value.type, alt1, alt2) < 0)
|
||||
spa_pod_builder_raw(b, alt1, p1->body.value.size);
|
||||
else
|
||||
spa_pod_builder_raw(b, alt2, p2->body.value.size);
|
||||
|
||||
np->body.flags |= SPA_POD_PROP_RANGE_MIN_MAX | SPA_POD_PROP_FLAG_UNSET;
|
||||
}
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_NONE && rt2 == SPA_POD_PROP_RANGE_FLAGS)
|
||||
return -ENOTSUP;
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_MIN_MAX && rt2 == SPA_POD_PROP_RANGE_STEP)
|
||||
return -ENOTSUP;
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_MIN_MAX && rt2 == SPA_POD_PROP_RANGE_FLAGS)
|
||||
return -ENOTSUP;
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_ENUM && rt2 == SPA_POD_PROP_RANGE_FLAGS)
|
||||
return -ENOTSUP;
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_STEP && rt2 == SPA_POD_PROP_RANGE_NONE)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_STEP && rt2 == SPA_POD_PROP_RANGE_MIN_MAX)
|
||||
return -ENOTSUP;
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_STEP && rt2 == SPA_POD_PROP_RANGE_STEP)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_STEP && rt2 == SPA_POD_PROP_RANGE_ENUM)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_STEP && rt2 == SPA_POD_PROP_RANGE_FLAGS)
|
||||
return -ENOTSUP;
|
||||
|
||||
if (rt1 == SPA_POD_PROP_RANGE_FLAGS && rt2 == SPA_POD_PROP_RANGE_NONE)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_FLAGS && rt2 == SPA_POD_PROP_RANGE_MIN_MAX)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_FLAGS && rt2 == SPA_POD_PROP_RANGE_STEP)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_FLAGS && rt2 == SPA_POD_PROP_RANGE_ENUM)
|
||||
return -ENOTSUP;
|
||||
if (rt1 == SPA_POD_PROP_RANGE_FLAGS && rt2 == SPA_POD_PROP_RANGE_FLAGS)
|
||||
return -ENOTSUP;
|
||||
|
||||
spa_pod_builder_pop(b);
|
||||
fix_default(np);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pod_filter(struct spa_pod_builder *b,
|
||||
const struct spa_pod *pod, uint32_t pod_size,
|
||||
const struct spa_pod *filter, uint32_t filter_size)
|
||||
{
|
||||
const struct spa_pod *pp, *pf;
|
||||
int res = 0;
|
||||
|
||||
pf = filter;
|
||||
|
||||
SPA_POD_FOREACH(pod, pod_size, pp) {
|
||||
bool do_copy = false, do_advance = false;
|
||||
uint32_t filter_offset = 0;
|
||||
|
||||
switch (SPA_POD_TYPE(pp)) {
|
||||
case SPA_POD_TYPE_STRUCT:
|
||||
case SPA_POD_TYPE_OBJECT:
|
||||
if (pf != NULL) {
|
||||
if (SPA_POD_TYPE(pf) != SPA_POD_TYPE(pp))
|
||||
return -EINVAL;
|
||||
|
||||
if (SPA_POD_TYPE(pp) == SPA_POD_TYPE_STRUCT) {
|
||||
filter_offset = sizeof(struct spa_pod_struct);
|
||||
spa_pod_builder_push_struct(b);
|
||||
} else {
|
||||
struct spa_pod_object *p1 = (struct spa_pod_object *) pp;
|
||||
filter_offset = sizeof(struct spa_pod_object);
|
||||
spa_pod_builder_push_object(b, p1->body.id, p1->body.type);
|
||||
}
|
||||
do_advance = true;
|
||||
}
|
||||
else
|
||||
do_copy = true;
|
||||
break;
|
||||
|
||||
case SPA_POD_TYPE_PROP:
|
||||
{
|
||||
struct spa_pod_prop *p1, *p2;
|
||||
|
||||
p1 = (struct spa_pod_prop *) pp;
|
||||
p2 = find_prop(filter, filter_size, p1->body.key);
|
||||
|
||||
if (p2 != NULL)
|
||||
res = filter_prop(b, p1, p2);
|
||||
else
|
||||
do_copy = true;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
if (pf != NULL) {
|
||||
if (SPA_POD_SIZE(pp) != SPA_POD_SIZE(pf))
|
||||
return -EINVAL;
|
||||
if (memcmp(pp, pf, SPA_POD_SIZE(pp)) != 0)
|
||||
return -EINVAL;
|
||||
do_advance = true;
|
||||
}
|
||||
do_copy = true;
|
||||
break;
|
||||
}
|
||||
if (do_copy)
|
||||
spa_pod_builder_raw_padded(b, pp, SPA_POD_SIZE(pp));
|
||||
else if (filter_offset) {
|
||||
res = pod_filter(b,
|
||||
SPA_MEMBER(pp,filter_offset,void),
|
||||
SPA_POD_SIZE(pp) - filter_offset,
|
||||
SPA_MEMBER(pf,filter_offset,void),
|
||||
SPA_POD_SIZE(pf) - filter_offset);
|
||||
spa_pod_builder_pop(b);
|
||||
}
|
||||
if (do_advance) {
|
||||
pf = spa_pod_next(pf);
|
||||
if (!spa_pod_is_inside(filter, filter_size, pf))
|
||||
pf = NULL;
|
||||
}
|
||||
if (res < 0)
|
||||
break;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
int
|
||||
spa_pod_filter(struct spa_pod_builder *b,
|
||||
struct spa_pod **result,
|
||||
const struct spa_pod *pod,
|
||||
const struct spa_pod *filter)
|
||||
{
|
||||
int res;
|
||||
struct spa_pod_builder_state state;
|
||||
|
||||
spa_return_val_if_fail(pod != NULL, -EINVAL);
|
||||
spa_return_val_if_fail(b != NULL, -EINVAL);
|
||||
|
||||
if (filter == NULL) {
|
||||
*result = spa_pod_builder_deref(b,
|
||||
spa_pod_builder_raw_padded(b, pod, SPA_POD_SIZE(pod)));
|
||||
return 0;
|
||||
}
|
||||
|
||||
spa_pod_builder_get_state(b, &state);
|
||||
if ((res = pod_filter(b, pod, SPA_POD_SIZE(pod), filter, SPA_POD_SIZE(filter))) < 0)
|
||||
spa_pod_builder_reset(b, &state);
|
||||
else
|
||||
*result = spa_pod_builder_deref(b, state.offset);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
int pod_compare(const struct spa_pod *pod1, uint32_t pod1_size,
|
||||
const struct spa_pod *pod2, uint32_t pod2_size)
|
||||
{
|
||||
const struct spa_pod *p1, *p2;
|
||||
int res;
|
||||
|
||||
p2 = pod2;
|
||||
|
||||
SPA_POD_FOREACH(pod1, pod1_size, p1) {
|
||||
bool do_advance = true;
|
||||
uint32_t recurse_offset = 0;
|
||||
|
||||
if (p2 == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
switch (SPA_POD_TYPE(p1)) {
|
||||
case SPA_POD_TYPE_STRUCT:
|
||||
case SPA_POD_TYPE_OBJECT:
|
||||
if (SPA_POD_TYPE(p2) != SPA_POD_TYPE(p1))
|
||||
return -EINVAL;
|
||||
|
||||
if (SPA_POD_TYPE(p1) == SPA_POD_TYPE_STRUCT)
|
||||
recurse_offset = sizeof(struct spa_pod_struct);
|
||||
else
|
||||
recurse_offset = sizeof(struct spa_pod_object);
|
||||
|
||||
do_advance = true;
|
||||
break;
|
||||
case SPA_POD_TYPE_PROP:
|
||||
{
|
||||
struct spa_pod_prop *pr1, *pr2;
|
||||
void *a1, *a2;
|
||||
|
||||
pr1 = (struct spa_pod_prop *) p1;
|
||||
pr2 = find_prop(pod2, pod2_size, pr1->body.key);
|
||||
|
||||
if (pr2 == NULL)
|
||||
return -EINVAL;
|
||||
|
||||
/* incompatible property types */
|
||||
if (pr1->body.value.type != pr2->body.value.type)
|
||||
return -EINVAL;
|
||||
|
||||
if (pr1->body.flags & SPA_POD_PROP_FLAG_UNSET ||
|
||||
pr2->body.flags & SPA_POD_PROP_FLAG_UNSET)
|
||||
return -EINVAL;
|
||||
|
||||
a1 = SPA_MEMBER(pr1, sizeof(struct spa_pod_prop), void);
|
||||
a2 = SPA_MEMBER(pr2, sizeof(struct spa_pod_prop), void);
|
||||
|
||||
res = compare_value(pr1->body.value.type, a1, a2);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
if (SPA_POD_TYPE(p1) != SPA_POD_TYPE(p2))
|
||||
return -EINVAL;
|
||||
|
||||
res = compare_value(SPA_POD_TYPE(p1), SPA_POD_BODY(p1), SPA_POD_BODY(p2));
|
||||
do_advance = true;
|
||||
break;
|
||||
}
|
||||
if (recurse_offset) {
|
||||
res = pod_compare(SPA_MEMBER(p1,recurse_offset,void),
|
||||
SPA_POD_SIZE(p1) - recurse_offset,
|
||||
SPA_MEMBER(p2,recurse_offset,void),
|
||||
SPA_POD_SIZE(p2) - recurse_offset);
|
||||
}
|
||||
if (do_advance) {
|
||||
p2 = spa_pod_next(p2);
|
||||
if (!spa_pod_is_inside(pod2, pod2_size, p2))
|
||||
p2 = NULL;
|
||||
}
|
||||
if (res != 0)
|
||||
return res;
|
||||
}
|
||||
if (p2 != NULL)
|
||||
return -EINVAL;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int spa_pod_compare(const struct spa_pod *pod1,
|
||||
const struct spa_pod *pod2)
|
||||
{
|
||||
spa_return_val_if_fail(pod1 != NULL, -EINVAL);
|
||||
spa_return_val_if_fail(pod2 != NULL, -EINVAL);
|
||||
|
||||
return pod_compare(pod1, SPA_POD_SIZE(pod1), pod2, SPA_POD_SIZE(pod2));
|
||||
}
|
||||
|
|
@ -1,42 +0,0 @@
|
|||
/* Simple Plugin API
|
||||
* Copyright (C) 2017 Wim Taymans <wim.taymans@gmail.com>
|
||||
*
|
||||
* This library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
*
|
||||
* This library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this library; if not, write to the
|
||||
* Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
|
||||
* Boston, MA 02110-1301, USA.
|
||||
*/
|
||||
|
||||
#ifndef __SPA_LIBPOD_H__
|
||||
#define __SPA_LIBPOD_H__
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <spa/param/props.h>
|
||||
#include <spa/pod/builder.h>
|
||||
|
||||
int spa_pod_filter(struct spa_pod_builder *b,
|
||||
struct spa_pod **result,
|
||||
const struct spa_pod *pod,
|
||||
const struct spa_pod *filter);
|
||||
|
||||
int spa_pod_compare(const struct spa_pod *pod1,
|
||||
const struct spa_pod *pod2);
|
||||
|
||||
#ifdef __cplusplus
|
||||
} /* extern "C" */
|
||||
#endif
|
||||
|
||||
#endif /* __SPA_LIBPOD_H__ */
|
||||
Loading…
Add table
Add a link
Reference in a new issue