aboutsummaryrefslogtreecommitdiff
path: root/usr.bin/kdump
diff options
context:
space:
mode:
authorDmitry Chagin <dchagin@FreeBSD.org>2022-06-22 11:15:20 +0000
committerDmitry Chagin <dchagin@FreeBSD.org>2022-06-22 11:15:20 +0000
commit3606a213bfa42e1970197ba9b3494c88d5827259 (patch)
tree26766129d3c4917b8ced56060e3aaf4d117154cd /usr.bin/kdump
parent9310737333eb9e1a15340c10ea3fd68e0ccdcfa9 (diff)
downloadsrc-3606a213bfa42e1970197ba9b3494c88d5827259.tar.gz
src-3606a213bfa42e1970197ba9b3494c88d5827259.zip
Diffstat (limited to 'usr.bin/kdump')
-rw-r--r--usr.bin/kdump/kdump.c5
-rw-r--r--usr.bin/kdump/kdump.h1
-rw-r--r--usr.bin/kdump/linux.c44
3 files changed, 49 insertions, 1 deletions
diff --git a/usr.bin/kdump/kdump.c b/usr.bin/kdump/kdump.c
index 79a5007bd1ec..5c05a82b53ba 100644
--- a/usr.bin/kdump/kdump.c
+++ b/usr.bin/kdump/kdump.c
@@ -2056,7 +2056,10 @@ ktrstruct(char *buf, size_t buflen)
ktrbitset(name, set, datalen);
free(set);
} else {
- printf("unknown structure\n");
+#ifdef SYSDECODE_HAVE_LINUX
+ if (ktrstruct_linux(name, data, datalen) == false)
+#endif
+ printf("unknown structure\n");
}
return;
invalid:
diff --git a/usr.bin/kdump/kdump.h b/usr.bin/kdump/kdump.h
index dc0515397f48..29bdb1dfbbaf 100644
--- a/usr.bin/kdump/kdump.h
+++ b/usr.bin/kdump/kdump.h
@@ -77,6 +77,7 @@ bool print_mask_arg_part(bool (*decoder)(FILE *, int, int *),
int value, int *rem);
#ifdef SYSDECODE_HAVE_LINUX
+bool ktrstruct_linux(const char *name, const char *data, size_t datalen);
void ktrsyscall_linux(struct ktr_syscall *ktr, register_t **resip,
int *resnarg, char *resc);
#ifdef __amd64__
diff --git a/usr.bin/kdump/linux.c b/usr.bin/kdump/linux.c
index e584b54db36c..ed057a6b8ef6 100644
--- a/usr.bin/kdump/linux.c
+++ b/usr.bin/kdump/linux.c
@@ -31,7 +31,11 @@ __FBSDID("$FreeBSD$");
#include <sys/param.h>
#include <sys/uio.h>
#include <sys/ktrace.h>
+#include <err.h>
+#include <errno.h>
#include <stddef.h>
+#include <stdlib.h>
+#include <string.h>
#include <sysdecode.h>
#include "kdump.h"
@@ -45,6 +49,8 @@ __FBSDID("$FreeBSD$");
#include <i386/linux/linux_syscall.h>
#endif
+#include <compat/linux/linux.h>
+
static void
print_linux_signal(int signo)
{
@@ -183,3 +189,41 @@ ktrsyscall_linux32(struct ktr_syscall *ktr, register_t **resip,
*resnarg = narg;
}
#endif /* __amd64__ */
+
+static void
+ktrsigset(const char *name, const l_sigset_t *mask, size_t sz)
+{
+ unsigned long i, c;
+
+ printf("%s [ ", name);
+ c = 0;
+ for (i = 1; i <= sz * CHAR_BIT; i++) {
+ if (!LINUX_SIGISMEMBER(*mask, i))
+ continue;
+ if (c != 0)
+ printf(", ");
+ printf("%s", sysdecode_linux_signal(i));
+ c++;
+ }
+ if (c == 0)
+ printf("empty ]\n");
+ else
+ printf(" ]\n");
+}
+
+bool
+ktrstruct_linux(const char *name, const char *data, size_t datalen)
+{
+ l_sigset_t mask;
+
+ if (strcmp(name, "l_sigset_t") == 0) {
+ /* Old Linux sigset_t is one word size. */
+ if (datalen < sizeof(int) || datalen > sizeof(l_sigset_t))
+ return (false);
+ memcpy(&mask, data, datalen);
+ ktrsigset(name, &mask, datalen);
+ } else
+ return (false);
+
+ return (true);
+}