Blob Blame History Raw
Index: strace-4.24/evdev.c
===================================================================
--- strace-4.24.orig/evdev.c	2019-06-13 23:42:43.294304862 +0200
+++ strace-4.24/evdev.c	2019-06-13 23:43:35.588294946 +0200
@@ -143,6 +143,14 @@
 	return RVAL_IOCTL_DECODED;
 }
 
+# ifndef ROUNDUP_DIV
+#  define ROUNDUP_DIV(val_, div_) (((val_) + (div_) - 1) / (div_))
+# endif
+
+# ifndef ROUNDUP
+#  define ROUNDUP(val_, div_) (ROUNDUP_DIV((val_), (div_)) * (div_))
+# endif
+
 static int
 decode_bitset_(struct tcb *const tcp, const kernel_ulong_t arg,
 	       const struct xlat decode_nr[], const unsigned int max_nr,
@@ -151,25 +159,36 @@
 	tprints(", ");
 
 	unsigned int size;
-	if ((kernel_ulong_t) tcp->u_rval > max_nr / 8)
-		size = max_nr;
+	unsigned int size_bits;
+
+	if ((kernel_ulong_t) tcp->u_rval > max_nr / CHAR_BIT)
+		size_bits = max_nr;
 	else
-		size = tcp->u_rval * 8;
+		size_bits = tcp->u_rval * CHAR_BIT;
+
+	size = ROUNDUP(ROUNDUP_DIV(size_bits, CHAR_BIT), current_wordsize);
+
+	if (syserror(tcp) || !size) {
+		printaddr(arg);
+
+		return RVAL_IOCTL_DECODED;
+	}
+
 	char decoded_arg[size];
 
-	if (umove_or_printaddr(tcp, arg, &decoded_arg))
+	if (umoven_or_printaddr(tcp, arg, size, decoded_arg))
 		return RVAL_IOCTL_DECODED;
 
 	tprints("[");
 
 	int bit_displayed = 0;
-	int i = next_set_bit(decoded_arg, 0, size);
+	int i = next_set_bit(decoded_arg, 0, size_bits);
 	if (i < 0) {
 		tprints(" 0 ");
 	} else {
 		printxval_dispatch(decode_nr, decode_nr_size, i, dflt, xt);
 
-		while ((i = next_set_bit(decoded_arg, i + 1, size)) > 0) {
+		while ((i = next_set_bit(decoded_arg, i + 1, size_bits)) > 0) {
 			if (abbrev(tcp) && bit_displayed >= 3) {
 				tprints(", ...");
 				break;