summaryrefslogtreecommitdiffstats
path: root/third_party/pipewire/spa/debug
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 17:32:43 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 17:32:43 +0000
commit6bf0a5cb5034a7e684dcc3500e841785237ce2dd (patch)
treea68f146d7fa01f0134297619fbe7e33db084e0aa /third_party/pipewire/spa/debug
parentInitial commit. (diff)
downloadthunderbird-6bf0a5cb5034a7e684dcc3500e841785237ce2dd.tar.xz
thunderbird-6bf0a5cb5034a7e684dcc3500e841785237ce2dd.zip
Adding upstream version 1:115.7.0.upstream/1%115.7.0upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'third_party/pipewire/spa/debug')
-rw-r--r--third_party/pipewire/spa/debug/buffer.h129
-rw-r--r--third_party/pipewire/spa/debug/dict.h58
-rw-r--r--third_party/pipewire/spa/debug/format.h212
-rw-r--r--third_party/pipewire/spa/debug/log.h53
-rw-r--r--third_party/pipewire/spa/debug/mem.h67
-rw-r--r--third_party/pipewire/spa/debug/node.h63
-rw-r--r--third_party/pipewire/spa/debug/pod.h215
-rw-r--r--third_party/pipewire/spa/debug/types.h127
8 files changed, 924 insertions, 0 deletions
diff --git a/third_party/pipewire/spa/debug/buffer.h b/third_party/pipewire/spa/debug/buffer.h
new file mode 100644
index 0000000000..df6beaad43
--- /dev/null
+++ b/third_party/pipewire/spa/debug/buffer.h
@@ -0,0 +1,129 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_BUFFER_H
+#define SPA_DEBUG_BUFFER_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** \defgroup spa_debug Debug
+ * Debugging utilities
+ */
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/debug/log.h>
+#include <spa/debug/mem.h>
+#include <spa/debug/types.h>
+#include <spa/buffer/type-info.h>
+
+static inline int spa_debug_buffer(int indent, const struct spa_buffer *buffer)
+{
+ uint32_t i;
+
+ spa_debug("%*s" "struct spa_buffer %p:", indent, "", buffer);
+ spa_debug("%*s" " n_metas: %u (at %p)", indent, "", 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_debug_type_find_name(spa_type_meta_type, m->type);
+ spa_debug("%*s" " meta %d: type %d (%s), data %p, size %d:", indent, "", i, m->type,
+ type_name, m->data, m->size);
+
+ switch (m->type) {
+ case SPA_META_Header:
+ {
+ struct spa_meta_header *h = (struct spa_meta_header*)m->data;
+ spa_debug("%*s" " struct spa_meta_header:", indent, "");
+ spa_debug("%*s" " flags: %08x", indent, "", h->flags);
+ spa_debug("%*s" " offset: %u", indent, "", h->offset);
+ spa_debug("%*s" " seq: %" PRIu64, indent, "", h->seq);
+ spa_debug("%*s" " pts: %" PRIi64, indent, "", h->pts);
+ spa_debug("%*s" " dts_offset: %" PRIi64, indent, "", h->dts_offset);
+ break;
+ }
+ case SPA_META_VideoCrop:
+ {
+ struct spa_meta_region *h = (struct spa_meta_region*)m->data;
+ spa_debug("%*s" " struct spa_meta_region:", indent, "");
+ spa_debug("%*s" " x: %d", indent, "", h->region.position.x);
+ spa_debug("%*s" " y: %d", indent, "", h->region.position.y);
+ spa_debug("%*s" " width: %d", indent, "", h->region.size.width);
+ spa_debug("%*s" " height: %d", indent, "", h->region.size.height);
+ break;
+ }
+ case SPA_META_VideoDamage:
+ {
+ struct spa_meta_region *h;
+ spa_meta_for_each(h, m) {
+ spa_debug("%*s" " struct spa_meta_region:", indent, "");
+ spa_debug("%*s" " x: %d", indent, "", h->region.position.x);
+ spa_debug("%*s" " y: %d", indent, "", h->region.position.y);
+ spa_debug("%*s" " width: %d", indent, "", h->region.size.width);
+ spa_debug("%*s" " height: %d", indent, "", h->region.size.height);
+ }
+ break;
+ }
+ case SPA_META_Bitmap:
+ break;
+ case SPA_META_Cursor:
+ break;
+ default:
+ spa_debug("%*s" " Unknown:", indent, "");
+ spa_debug_mem(5, m->data, m->size);
+ }
+ }
+ spa_debug("%*s" " n_datas: \t%u (at %p)", indent, "", buffer->n_datas, buffer->datas);
+ for (i = 0; i < buffer->n_datas; i++) {
+ struct spa_data *d = &buffer->datas[i];
+ spa_debug("%*s" " type: %d (%s)", indent, "", d->type,
+ spa_debug_type_find_name(spa_type_data_type, d->type));
+ spa_debug("%*s" " flags: %d", indent, "", d->flags);
+ spa_debug("%*s" " data: %p", indent, "", d->data);
+ spa_debug("%*s" " fd: %" PRIi64, indent, "", d->fd);
+ spa_debug("%*s" " offset: %d", indent, "", d->mapoffset);
+ spa_debug("%*s" " maxsize: %u", indent, "", d->maxsize);
+ spa_debug("%*s" " chunk: %p", indent, "", d->chunk);
+ spa_debug("%*s" " offset: %d", indent, "", d->chunk->offset);
+ spa_debug("%*s" " size: %u", indent, "", d->chunk->size);
+ spa_debug("%*s" " stride: %d", indent, "", d->chunk->stride);
+ }
+ return 0;
+}
+
+/**
+ * \}
+ */
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_BUFFER_H */
diff --git a/third_party/pipewire/spa/debug/dict.h b/third_party/pipewire/spa/debug/dict.h
new file mode 100644
index 0000000000..10498f27c9
--- /dev/null
+++ b/third_party/pipewire/spa/debug/dict.h
@@ -0,0 +1,58 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_DICT_H
+#define SPA_DEBUG_DICT_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/debug/log.h>
+#include <spa/utils/dict.h>
+
+static inline int spa_debug_dict(int indent, const struct spa_dict *dict)
+{
+ const struct spa_dict_item *item;
+ spa_debug("%*sflags:%08x n_items:%d", indent, "", dict->flags, dict->n_items);
+ spa_dict_for_each(item, dict) {
+ spa_debug("%*s %s = \"%s\"", indent, "", item->key, item->value);
+ }
+ return 0;
+}
+
+/**
+ * \}
+ */
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_DICT_H */
diff --git a/third_party/pipewire/spa/debug/format.h b/third_party/pipewire/spa/debug/format.h
new file mode 100644
index 0000000000..6f9e0a3be0
--- /dev/null
+++ b/third_party/pipewire/spa/debug/format.h
@@ -0,0 +1,212 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_FORMAT_H
+#define SPA_DEBUG_FORMAT_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/pod/parser.h>
+#include <spa/debug/log.h>
+#include <spa/debug/types.h>
+#include <spa/param/type-info.h>
+#include <spa/param/format-utils.h>
+
+static inline int
+spa_debug_format_value(const struct spa_type_info *info,
+ uint32_t type, void *body, uint32_t size)
+{
+ switch (type) {
+ case SPA_TYPE_Bool:
+ spa_debugn("%s", *(int32_t *) body ? "true" : "false");
+ break;
+ case SPA_TYPE_Id:
+ {
+ const char *str = spa_debug_type_find_short_name(info, *(int32_t *) body);
+ char tmp[64];
+ if (str == NULL) {
+ snprintf(tmp, sizeof(tmp), "%d", *(int32_t*)body);
+ str = tmp;
+ }
+ spa_debugn("%s", str);
+ break;
+ }
+ case SPA_TYPE_Int:
+ spa_debugn("%d", *(int32_t *) body);
+ break;
+ case SPA_TYPE_Long:
+ spa_debugn("%" PRIi64, *(int64_t *) body);
+ break;
+ case SPA_TYPE_Float:
+ spa_debugn("%f", *(float *) body);
+ break;
+ case SPA_TYPE_Double:
+ spa_debugn("%f", *(double *) body);
+ break;
+ case SPA_TYPE_String:
+ spa_debugn("%s", (char *) body);
+ break;
+ case SPA_TYPE_Rectangle:
+ {
+ struct spa_rectangle *r = (struct spa_rectangle *)body;
+ spa_debugn("%" PRIu32 "x%" PRIu32, r->width, r->height);
+ break;
+ }
+ case SPA_TYPE_Fraction:
+ {
+ struct spa_fraction *f = (struct spa_fraction *)body;
+ spa_debugn("%" PRIu32 "/%" PRIu32, f->num, f->denom);
+ break;
+ }
+ case SPA_TYPE_Bitmap:
+ spa_debugn("Bitmap");
+ break;
+ case SPA_TYPE_Bytes:
+ spa_debugn("Bytes");
+ break;
+ case SPA_TYPE_Array:
+ {
+ void *p;
+ struct spa_pod_array_body *b = (struct spa_pod_array_body *)body;
+ int i = 0;
+ info = info && info->values ? info->values : info;
+ spa_debugn("< ");
+ SPA_POD_ARRAY_BODY_FOREACH(b, size, p) {
+ if (i++ > 0)
+ spa_debugn(", ");
+ spa_debug_format_value(info, b->child.type, p, b->child.size);
+ }
+ spa_debugn(" >");
+ break;
+ }
+ default:
+ spa_debugn("INVALID type %d", type);
+ break;
+ }
+ return 0;
+}
+
+static inline int spa_debug_format(int indent,
+ const struct spa_type_info *info, const struct spa_pod *format)
+{
+ const char *media_type;
+ const char *media_subtype;
+ struct spa_pod_prop *prop;
+ uint32_t mtype, mstype;
+
+ if (info == NULL)
+ info = spa_type_format;
+
+ if (format == NULL || SPA_POD_TYPE(format) != SPA_TYPE_Object)
+ return -EINVAL;
+
+ if (spa_format_parse(format, &mtype, &mstype) < 0)
+ return -EINVAL;
+
+ media_type = spa_debug_type_find_name(spa_type_media_type, mtype);
+ media_subtype = spa_debug_type_find_name(spa_type_media_subtype, mstype);
+
+ spa_debug("%*s %s/%s", indent, "",
+ media_type ? spa_debug_type_short_name(media_type) : "unknown",
+ media_subtype ? spa_debug_type_short_name(media_subtype) : "unknown");
+
+ SPA_POD_OBJECT_FOREACH((struct spa_pod_object*)format, prop) {
+ const char *key;
+ const struct spa_type_info *ti;
+ uint32_t i, type, size, n_vals, choice;
+ const struct spa_pod *val;
+ void *vals;
+
+ if (prop->key == SPA_FORMAT_mediaType ||
+ prop->key == SPA_FORMAT_mediaSubtype)
+ continue;
+
+ val = spa_pod_get_values(&prop->value, &n_vals, &choice);
+
+ type = val->type;
+ size = val->size;
+ vals = SPA_POD_BODY(val);
+
+ if (type < SPA_TYPE_None || type >= _SPA_TYPE_LAST)
+ continue;
+
+ ti = spa_debug_type_find(info, prop->key);
+ key = ti ? ti->name : NULL;
+
+ spa_debugn("%*s %16s : (%s) ", indent, "",
+ key ? spa_debug_type_short_name(key) : "unknown",
+ spa_debug_type_short_name(spa_types[type].name));
+
+ if (choice == SPA_CHOICE_None) {
+ spa_debug_format_value(ti ? ti->values : NULL, type, vals, size);
+ } else {
+ const char *ssep, *esep, *sep;
+
+ switch (choice) {
+ case SPA_CHOICE_Range:
+ case SPA_CHOICE_Step:
+ ssep = "[ ";
+ sep = ", ";
+ esep = " ]";
+ break;
+ default:
+ case SPA_CHOICE_Enum:
+ case SPA_CHOICE_Flags:
+ ssep = "{ ";
+ sep = ", ";
+ esep = " }";
+ break;
+ }
+
+ spa_debugn("%s", ssep);
+
+ for (i = 1; i < n_vals; i++) {
+ vals = SPA_PTROFF(vals, size, void);
+ if (i > 1)
+ spa_debugn("%s", sep);
+ spa_debug_format_value(ti ? ti->values : NULL, type, vals, size);
+ }
+ spa_debugn("%s", esep);
+ }
+ spa_debugn("\n");
+ }
+ return 0;
+}
+
+/**
+ * \}
+ */
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_FORMAT_H */
diff --git a/third_party/pipewire/spa/debug/log.h b/third_party/pipewire/spa/debug/log.h
new file mode 100644
index 0000000000..8311e95460
--- /dev/null
+++ b/third_party/pipewire/spa/debug/log.h
@@ -0,0 +1,53 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2022 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_LOG_H
+#define SPA_DEBUG_LOG_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <stdio.h>
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#ifndef spa_debug
+#define spa_debug(fmt,...) ({ printf(fmt"\n", ## __VA_ARGS__); })
+#endif
+#ifndef spa_debugn
+#define spa_debugn(fmt,...) ({ printf(fmt, ## __VA_ARGS__); })
+#endif
+
+/**
+ * \}
+ */
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_LOGH */
diff --git a/third_party/pipewire/spa/debug/mem.h b/third_party/pipewire/spa/debug/mem.h
new file mode 100644
index 0000000000..4999c00bd4
--- /dev/null
+++ b/third_party/pipewire/spa/debug/mem.h
@@ -0,0 +1,67 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_MEM_H
+#define SPA_DEBUG_MEM_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <inttypes.h>
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/debug/log.h>
+
+static inline int spa_debug_mem(int indent, const void *data, size_t size)
+{
+ const uint8_t *t = (const uint8_t*)data;
+ char buffer[512];
+ size_t i;
+ int pos = 0;
+
+ for (i = 0; i < size; i++) {
+ if (i % 16 == 0)
+ pos = sprintf(buffer, "%p: ", &t[i]);
+ pos += sprintf(buffer + pos, "%02x ", t[i]);
+ if (i % 16 == 15 || i == size - 1) {
+ spa_debug("%*s" "%s", indent, "", buffer);
+ }
+ }
+ return 0;
+}
+
+/**
+ * \}
+ */
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_MEM_H */
diff --git a/third_party/pipewire/spa/debug/node.h b/third_party/pipewire/spa/debug/node.h
new file mode 100644
index 0000000000..6ec14b4fa3
--- /dev/null
+++ b/third_party/pipewire/spa/debug/node.h
@@ -0,0 +1,63 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_NODE_H
+#define SPA_DEBUG_NODE_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/node/node.h>
+#include <spa/debug/log.h>
+#include <spa/debug/dict.h>
+
+static inline int spa_debug_port_info(int indent, const struct spa_port_info *info)
+{
+ spa_debug("%*s" "struct spa_port_info %p:", indent, "", info);
+ spa_debug("%*s" " flags: \t%08" PRIx64, indent, "", info->flags);
+ spa_debug("%*s" " rate: \t%d/%d", indent, "", info->rate.num, info->rate.denom);
+ spa_debug("%*s" " props:", indent, "");
+ if (info->props)
+ spa_debug_dict(indent + 2, info->props);
+ else
+ spa_debug("%*s" " none", indent, "");
+ return 0;
+}
+
+/**
+ * \}
+ */
+
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_NODE_H */
diff --git a/third_party/pipewire/spa/debug/pod.h b/third_party/pipewire/spa/debug/pod.h
new file mode 100644
index 0000000000..1468aab041
--- /dev/null
+++ b/third_party/pipewire/spa/debug/pod.h
@@ -0,0 +1,215 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_POD_H
+#define SPA_DEBUG_POD_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/debug/log.h>
+#include <spa/debug/mem.h>
+#include <spa/debug/types.h>
+#include <spa/pod/pod.h>
+#include <spa/pod/iter.h>
+
+static inline int
+spa_debug_pod_value(int indent, const struct spa_type_info *info,
+ uint32_t type, void *body, uint32_t size)
+{
+ switch (type) {
+ case SPA_TYPE_Bool:
+ spa_debug("%*s" "Bool %s", indent, "", (*(int32_t *) body) ? "true" : "false");
+ break;
+ case SPA_TYPE_Id:
+ spa_debug("%*s" "Id %-8d (%s)", indent, "", *(int32_t *) body,
+ spa_debug_type_find_name(info, *(int32_t *) body));
+ break;
+ case SPA_TYPE_Int:
+ spa_debug("%*s" "Int %d", indent, "", *(int32_t *) body);
+ break;
+ case SPA_TYPE_Long:
+ spa_debug("%*s" "Long %" PRIi64 "", indent, "", *(int64_t *) body);
+ break;
+ case SPA_TYPE_Float:
+ spa_debug("%*s" "Float %f", indent, "", *(float *) body);
+ break;
+ case SPA_TYPE_Double:
+ spa_debug("%*s" "Double %f", indent, "", *(double *) body);
+ break;
+ case SPA_TYPE_String:
+ spa_debug("%*s" "String \"%s\"", indent, "", (char *) body);
+ break;
+ case SPA_TYPE_Fd:
+ spa_debug("%*s" "Fd %d", indent, "", *(int *) body);
+ break;
+ case SPA_TYPE_Pointer:
+ {
+ struct spa_pod_pointer_body *b = (struct spa_pod_pointer_body *)body;
+ spa_debug("%*s" "Pointer %s %p", indent, "",
+ spa_debug_type_find_name(SPA_TYPE_ROOT, b->type), b->value);
+ break;
+ }
+ case SPA_TYPE_Rectangle:
+ {
+ struct spa_rectangle *r = (struct spa_rectangle *)body;
+ spa_debug("%*s" "Rectangle %dx%d", indent, "", r->width, r->height);
+ break;
+ }
+ case SPA_TYPE_Fraction:
+ {
+ struct spa_fraction *f = (struct spa_fraction *)body;
+ spa_debug("%*s" "Fraction %d/%d", indent, "", f->num, f->denom);
+ break;
+ }
+ case SPA_TYPE_Bitmap:
+ spa_debug("%*s" "Bitmap", indent, "");
+ break;
+ case SPA_TYPE_Array:
+ {
+ struct spa_pod_array_body *b = (struct spa_pod_array_body *)body;
+ void *p;
+ const struct spa_type_info *ti = spa_debug_type_find(SPA_TYPE_ROOT, b->child.type);
+
+ spa_debug("%*s" "Array: child.size %d, child.type %s", indent, "",
+ b->child.size, ti ? ti->name : "unknown");
+
+ info = info && info->values ? info->values : info;
+ SPA_POD_ARRAY_BODY_FOREACH(b, size, p)
+ spa_debug_pod_value(indent + 2, info, b->child.type, p, b->child.size);
+ break;
+ }
+ case SPA_TYPE_Choice:
+ {
+ struct spa_pod_choice_body *b = (struct spa_pod_choice_body *)body;
+ void *p;
+ const struct spa_type_info *ti = spa_debug_type_find(spa_type_choice, b->type);
+
+ spa_debug("%*s" "Choice: type %s, flags %08x %d %d", indent, "",
+ ti ? ti->name : "unknown", b->flags, size, b->child.size);
+
+ SPA_POD_CHOICE_BODY_FOREACH(b, size, p)
+ spa_debug_pod_value(indent + 2, info, b->child.type, p, b->child.size);
+ break;
+ }
+ case SPA_TYPE_Struct:
+ {
+ struct spa_pod *b = (struct spa_pod *)body, *p;
+ spa_debug("%*s" "Struct: size %d", indent, "", size);
+ SPA_POD_FOREACH(b, size, p)
+ spa_debug_pod_value(indent + 2, info, p->type, SPA_POD_BODY(p), p->size);
+ break;
+ }
+ case SPA_TYPE_Object:
+ {
+ struct spa_pod_object_body *b = (struct spa_pod_object_body *)body;
+ struct spa_pod_prop *p;
+ const struct spa_type_info *ti, *ii;
+
+ ti = spa_debug_type_find(info, b->type);
+ ii = ti ? spa_debug_type_find(ti->values, 0) : NULL;
+ ii = ii ? spa_debug_type_find(ii->values, b->id) : NULL;
+
+ spa_debug("%*s" "Object: size %d, type %s (%d), id %s (%d)", indent, "", size,
+ ti ? ti->name : "unknown", b->type, ii ? ii->name : "unknown", b->id);
+
+ info = ti ? ti->values : info;
+
+ SPA_POD_OBJECT_BODY_FOREACH(b, size, p) {
+ ii = spa_debug_type_find(info, p->key);
+
+ spa_debug("%*s" "Prop: key %s (%d), flags %08x", indent+2, "",
+ ii ? ii->name : "unknown", p->key, p->flags);
+
+ spa_debug_pod_value(indent + 4, ii ? ii->values : NULL,
+ p->value.type,
+ SPA_POD_CONTENTS(struct spa_pod_prop, p),
+ p->value.size);
+ }
+ break;
+ }
+ case SPA_TYPE_Sequence:
+ {
+ struct spa_pod_sequence_body *b = (struct spa_pod_sequence_body *)body;
+ const struct spa_type_info *ti, *ii;
+ struct spa_pod_control *c;
+
+ ti = spa_debug_type_find(info, b->unit);
+
+ spa_debug("%*s" "Sequence: size %d, unit %s", indent, "", size,
+ ti ? ti->name : "unknown");
+
+ SPA_POD_SEQUENCE_BODY_FOREACH(b, size, c) {
+ ii = spa_debug_type_find(spa_type_control, c->type);
+
+ spa_debug("%*s" "Control: offset %d, type %s", indent+2, "",
+ c->offset, ii ? ii->name : "unknown");
+
+ spa_debug_pod_value(indent + 4, ii ? ii->values : NULL,
+ c->value.type,
+ SPA_POD_CONTENTS(struct spa_pod_control, c),
+ c->value.size);
+ }
+ break;
+ }
+ case SPA_TYPE_Bytes:
+ spa_debug("%*s" "Bytes", indent, "");
+ spa_debug_mem(indent + 2, body, size);
+ break;
+ case SPA_TYPE_None:
+ spa_debug("%*s" "None", indent, "");
+ spa_debug_mem(indent + 2, body, size);
+ break;
+ default:
+ spa_debug("%*s" "unhandled POD type %d", indent, "", type);
+ break;
+ }
+ return 0;
+}
+
+static inline int spa_debug_pod(int indent,
+ const struct spa_type_info *info, const struct spa_pod *pod)
+{
+ return spa_debug_pod_value(indent, info ? info : SPA_TYPE_ROOT,
+ SPA_POD_TYPE(pod),
+ SPA_POD_BODY(pod),
+ SPA_POD_BODY_SIZE(pod));
+}
+
+/**
+ * \}
+ */
+
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_POD_H */
diff --git a/third_party/pipewire/spa/debug/types.h b/third_party/pipewire/spa/debug/types.h
new file mode 100644
index 0000000000..55fb379aa7
--- /dev/null
+++ b/third_party/pipewire/spa/debug/types.h
@@ -0,0 +1,127 @@
+/* Simple Plugin API
+ *
+ * Copyright © 2018 Wim Taymans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a
+ * copy of this software and associated documentation files (the "Software"),
+ * to deal in the Software without restriction, including without limitation
+ * the rights to use, copy, modify, merge, publish, distribute, sublicense,
+ * and/or sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice (including the next
+ * paragraph) shall be included in all copies or substantial portions of the
+ * Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+ * DEALINGS IN THE SOFTWARE.
+ */
+
+#ifndef SPA_DEBUG_TYPES_H
+#define SPA_DEBUG_TYPES_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * \addtogroup spa_debug
+ * \{
+ */
+
+#include <spa/utils/type-info.h>
+
+#include <string.h>
+
+static inline const struct spa_type_info *spa_debug_type_find(const struct spa_type_info *info, uint32_t type)
+{
+ const struct spa_type_info *res;
+
+ if (info == NULL)
+ info = SPA_TYPE_ROOT;
+
+ while (info && info->name) {
+ if (info->type == SPA_ID_INVALID) {
+ if (info->values && (res = spa_debug_type_find(info->values, type)))
+ return res;
+ }
+ else if (info->type == type)
+ return info;
+ info++;
+ }
+ return NULL;
+}
+
+static inline const char *spa_debug_type_short_name(const char *name)
+{
+ const char *h;
+ if ((h = strrchr(name, ':')) != NULL)
+ name = h + 1;
+ return name;
+}
+
+static inline const char *spa_debug_type_find_name(const struct spa_type_info *info, uint32_t type)
+{
+ if ((info = spa_debug_type_find(info, type)) == NULL)
+ return NULL;
+ return info->name;
+}
+
+static inline const char *spa_debug_type_find_short_name(const struct spa_type_info *info, uint32_t type)
+{
+ const char *str;
+ if ((str = spa_debug_type_find_name(info, type)) == NULL)
+ return NULL;
+ return spa_debug_type_short_name(str);
+}
+
+static inline uint32_t spa_debug_type_find_type(const struct spa_type_info *info, const char *name)
+{
+ if (info == NULL)
+ info = SPA_TYPE_ROOT;
+
+ while (info && info->name) {
+ uint32_t res;
+ if (strcmp(info->name, name) == 0)
+ return info->type;
+ if (info->values && (res = spa_debug_type_find_type(info->values, name)) != SPA_ID_INVALID)
+ return res;
+ info++;
+ }
+ return SPA_ID_INVALID;
+}
+
+static inline const struct spa_type_info *spa_debug_type_find_short(const struct spa_type_info *info, const char *name)
+{
+ while (info && info->name) {
+ if (strcmp(spa_debug_type_short_name(info->name), name) == 0)
+ return info;
+ if (strcmp(info->name, name) == 0)
+ return info;
+ if (info->type != 0 && info->type == (uint32_t)atoi(name))
+ return info;
+ info++;
+ }
+ return NULL;
+}
+
+static inline uint32_t spa_debug_type_find_type_short(const struct spa_type_info *info, const char *name)
+{
+ if ((info = spa_debug_type_find_short(info, name)) == NULL)
+ return SPA_ID_INVALID;
+ return info->type;
+}
+/**
+ * \}
+ */
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#endif /* SPA_DEBUG_NODE_H */