Blame SOURCES/0001-x86-Fix-failure-of-collecting-vsyscall-mapping-due-t.patch

bd4871
From 03f9360715731f18e4fdae7b30aa34b30dddcd57 Mon Sep 17 00:00:00 2001
bd4871
From: HATAYAMA Daisuke <d.hatayama@fujitsu.com>
bd4871
Date: Sat, 26 Mar 2022 21:42:02 +0900
bd4871
Subject: [PATCH 1/5] x86: Fix failure of collecting vsyscall mapping due to
bd4871
 change of enum type of vsyscall_mode
bd4871
bd4871
vsyscall mapping fails to get collected because the commit
bd4871
bd49e16e3339 (x86/vsyscall: Add a new vsyscall=xonly mode) merged at
bd4871
kernel v5.2-rc7 added constant XONLY to the anonymous enumeration type
bd4871
of variable vsyscall_mode, which made the value of constant NONE
bd4871
change from 1 to 2.
bd4871
bd4871
This commit fixes the issue by checking the value of constant NONE
bd4871
using gdb's print command and typeof operator since there's no utility
bd4871
function to handle such anonymous enumeration type currently in crash
bd4871
utility.
bd4871
bd4871
Signed-off-by: HATAYAMA Daisuke <d.hatayama@fujitsu.com>
bd4871
Signed-off-by: Lianbo Jiang <lijiang@redhat.com>
bd4871
---
bd4871
 src/libgcore/gcore_x86.c | 56 ++++++++++++++++++++++++++++++++++++++--
bd4871
 1 file changed, 54 insertions(+), 2 deletions(-)
bd4871
bd4871
diff --git a/src/libgcore/gcore_x86.c b/src/libgcore/gcore_x86.c
bd4871
index 08e573c741f6..f334a85d4240 100644
bd4871
--- a/src/libgcore/gcore_x86.c
bd4871
+++ b/src/libgcore/gcore_x86.c
bd4871
@@ -41,6 +41,9 @@ struct gcore_x86_table
bd4871
 static struct gcore_x86_table gcore_x86_table;
bd4871
 struct gcore_x86_table *gxt = &gcore_x86_table;
bd4871
 
bd4871
+static void gdb_run_command(char *cmd, char *buf, size_t size);
bd4871
+static int get_vsyscall_mode_none(void);
bd4871
+
bd4871
 #ifdef X86_64
bd4871
 static ulong gcore_x86_64_get_old_rsp(int cpu);
bd4871
 static ulong gcore_x86_64_get_per_cpu__old_rsp(int cpu);
bd4871
@@ -2367,6 +2370,54 @@ int gcore_is_arch_32bit_emulation(struct task_context *tc)
bd4871
 	return FALSE;
bd4871
 }
bd4871
 
bd4871
+static void gdb_run_command(char *cmd, char *buf, size_t size)
bd4871
+{
bd4871
+	open_tmpfile();
bd4871
+	if (!gdb_pass_through(cmd,
bd4871
+			      pc->tmpfile,
bd4871
+			      GNU_RETURN_ON_ERROR)) {
bd4871
+		close_tmpfile();
bd4871
+		error(FATAL, "gdb command failed: %s", cmd);
bd4871
+	}
bd4871
+	rewind(pc->tmpfile);
bd4871
+	fgets(buf, size, pc->tmpfile);
bd4871
+	close_tmpfile();
bd4871
+}
bd4871
+
bd4871
+static int get_vsyscall_mode_none(void)
bd4871
+{
bd4871
+	static int none = -1;
bd4871
+	char cmd[32], buf[BUFSIZE];
bd4871
+	int i;
bd4871
+
bd4871
+	if (none != -1)
bd4871
+		return none;
bd4871
+
bd4871
+	/*
bd4871
+	 * Variable vsyscall_mode is of anonymous enumeration
bd4871
+	 * type. Because there's no utility function in crash utility
bd4871
+	 * to get value of each constant in specified anonymous
bd4871
+	 * enumeration type, we have no choice but rely on gdb's print
bd4871
+	 * command in combination with typeof operator.
bd4871
+	 */
bd4871
+	for (i = 0; i < 10; ++i) {
bd4871
+		snprintf(cmd, sizeof(cmd), "p (typeof(vsyscall_mode))%d", i);
bd4871
+		gdb_run_command(cmd, buf, sizeof(buf));
bd4871
+		if (strstr(buf, "NONE"))
bd4871
+			return none = i;
bd4871
+	}
bd4871
+
bd4871
+	/*
bd4871
+	 * When the above logic doesn't work as expected, use 2, which
bd4871
+	 * is the value on the definition where vsyscall_mode was
bd4871
+	 * first introduced at the commit 3ae36655b97a (x86-64: Rework
bd4871
+	 * vsyscall emulation and add vsyscall= parameter).
bd4871
+	 */
bd4871
+	none = 2;
bd4871
+
bd4871
+	return none;
bd4871
+}
bd4871
+
bd4871
 /**
bd4871
  * Return an address to gate_vma.
bd4871
  */
bd4871
@@ -2377,7 +2428,8 @@ ulong gcore_arch_get_gate_vma(void)
bd4871
 		return 0UL;
bd4871
 
bd4871
 	if (symbol_exists("vsyscall_mode")) {
bd4871
-		enum { ENUMERATE, NONE } vsyscall_mode;
bd4871
+		int vsyscall_mode;
bd4871
+		int none = get_vsyscall_mode_none();
bd4871
 
bd4871
 		readmem(symbol_value("vsyscall_mode"),
bd4871
 			KVADDR,
bd4871
@@ -2386,7 +2438,7 @@ ulong gcore_arch_get_gate_vma(void)
bd4871
 			"gcore_arch_get_gate_vma: vsyscall_mode",
bd4871
 			gcore_verbose_error_handle());
bd4871
 
bd4871
-		if (vsyscall_mode == NONE)
bd4871
+		if (vsyscall_mode == none)
bd4871
 			return 0UL;
bd4871
 	}
bd4871
 
bd4871
-- 
bd4871
2.37.1
bd4871