summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPhilippe De Muyter <phdm@macqel.be>2020-02-11 09:33:57 +0100
committerEugene Syromyatnikov <evgsyr@gmail.com>2020-03-23 13:32:13 +0100
commit13ef3815467acc45548a45030ecd4c0a79b25c88 (patch)
tree895e327f22875c7d9b2b1c7b073f92df88f1f572
parented2686401038e5073a61eebbd709a3d9fe583a0a (diff)
downloadstrace-13ef3815467acc45548a45030ecd4c0a79b25c88.tar.gz
v4l2: decode VIDIOC_QUERY_EXT_CTRL:arg
* v4l2.c: add print_v4l2_query_ext_ctrl, and use it for VIDIOC_QUERY_EXT_CTRL:arg Signed-off-by: Philippe De Muyter <phdm@macqel.be>
-rw-r--r--v4l2.c66
1 files changed, 66 insertions, 0 deletions
diff --git a/v4l2.c b/v4l2.c
index ebe9a1a13..52d5b2a3c 100644
--- a/v4l2.c
+++ b/v4l2.c
@@ -837,6 +837,69 @@ print_v4l2_queryctrl(struct tcb *const tcp, const kernel_ulong_t arg)
return RVAL_IOCTL_DECODED;
}
+static void
+print_v4l2_query_ctrl_id(unsigned long id)
+{
+ if (id & V4L2_CTRL_FLAG_NEXT_CTRL) {
+ tprints("V4L2_CTRL_FLAG_NEXT_CTRL|");
+ id &= ~V4L2_CTRL_FLAG_NEXT_CTRL;
+ }
+ if (id & V4L2_CTRL_FLAG_NEXT_COMPOUND) {
+ tprints("V4L2_CTRL_FLAG_NEXT_COMPOUND|");
+ id &= ~V4L2_CTRL_FLAG_NEXT_COMPOUND;
+ }
+ printxval(v4l2_control_ids, id, NULL);
+}
+
+static int
+print_v4l2_query_ext_ctrl(struct tcb *const tcp, const kernel_ulong_t arg)
+{
+ struct v4l2_query_ext_ctrl c;
+
+#define NEXT_FLAGS (V4L2_CTRL_FLAG_NEXT_CTRL|V4L2_CTRL_FLAG_NEXT_COMPOUND)
+ if (entering(tcp)) {
+ tprints(", ");
+ if (umove_or_printaddr(tcp, arg, &c))
+ return RVAL_IOCTL_DECODED;
+ set_tcb_priv_ulong(tcp, c.id);
+ tprints("{id");
+ if (!(c.id & NEXT_FLAGS) || !abbrev(tcp)) {
+ tprints("=");
+ print_v4l2_query_ctrl_id(c.id);
+ }
+ } else {
+ unsigned long entry_id = get_tcb_priv_ulong(tcp);
+
+ if (syserror(tcp) || umove(tcp, arg, &c) < 0) {
+ if (abbrev(tcp) && (entry_id & NEXT_FLAGS)) {
+ tprints("=");
+ print_v4l2_query_ctrl_id(entry_id);
+ }
+ tprints("}");
+ return RVAL_IOCTL_DECODED;
+ }
+ if (entry_id & NEXT_FLAGS) {
+ tprints(" => ");
+ print_v4l2_query_ctrl_id(c.id);
+ }
+ }
+#undef NEXT_FLAGS
+
+ if (exiting(tcp)) {
+ tprints(", type=");
+ printxval(v4l2_control_types, c.type, "V4L2_CTRL_TYPE_???");
+ PRINT_FIELD_CSTRING(", ", c, name);
+ if (!abbrev(tcp)) {
+ tprintf(", minimum=%lld, maximum=%lld, step=%lld"
+ ", default_value=%lld, flags=",
+ c.minimum, c.maximum, c.step, c.default_value);
+ printflags(v4l2_control_flags, c.flags, "V4L2_CTRL_FLAG_???");
+ }
+ tprints("}");
+ }
+ return entering(tcp) ? 0 : RVAL_IOCTL_DECODED;
+}
+
static int
print_v4l2_cropcap(struct tcb *const tcp, const kernel_ulong_t arg)
{
@@ -1137,6 +1200,9 @@ MPERS_PRINTER_DECL(int, v4l2_ioctl, struct tcb *const tcp,
case VIDIOC_QUERYCTRL: /* RW */
return print_v4l2_queryctrl(tcp, arg);
+ case VIDIOC_QUERY_EXT_CTRL: /* RW */
+ return print_v4l2_query_ext_ctrl(tcp, arg);
+
case VIDIOC_G_INPUT: /* R */
if (entering(tcp))
return 0;