All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2] fix Xen detection for xenfs in pv_ops kernel
@ 2011-08-03 18:07 Olaf Hering
  2011-08-03 23:44 ` Simon Horman
  0 siblings, 1 reply; 2+ messages in thread
From: Olaf Hering @ 2011-08-03 18:07 UTC (permalink / raw)
  To: kexec

The pv_ops kernel in mainline Linux provides xenfs which has to be
mounted at /proc/xen.  It creates /proc/xen/capabilities unconditionally
which makes it impossible to distinguish PVonHVM guests from PV guests.
Use code from xen-detect.c to check wether kexec runs on a PV guest.
Without this change PVonHVM guests will be detected incorrectly as plain
PV guests.

Signed-off-by: Olaf Hering <olaf@aepfle.de>

---
 kexec/crashdump-xen.c |   86 ++++++++++++++++++++++++++++++++++++++++++++++++--
 1 file changed, 84 insertions(+), 2 deletions(-)

Index: kexec-tools.git/kexec/crashdump-xen.c
===================================================================
--- kexec-tools.git.orig/kexec/crashdump-xen.c
+++ kexec-tools.git/kexec/crashdump-xen.c
@@ -10,6 +10,8 @@
 #include <sys/stat.h>
 #include <unistd.h>
 #include <fcntl.h>
+#include <setjmp.h>
+#include <signal.h>
 #include "kexec.h"
 #include "crashdump.h"
 #include "kexec-syscall.h"
@@ -27,13 +29,93 @@ struct crash_note_info {
 
 static int xen_phys_cpus;
 static struct crash_note_info *xen_phys_notes;
+
+/* based on code from xen-detect.c */
 static int is_dom0;
+#if defined(__i386__) || defined(__x86_64__)
+static jmp_buf xen_sigill_jmp;
+void xen_sigill_handler(int sig)
+{
+	longjmp(xen_sigill_jmp, 1);
+}
+
+static void xen_cpuid(uint32_t idx, uint32_t *regs, int pv_context)
+{
+	asm volatile (
+#ifdef __i386__
+#define R(x) "%%e"#x"x"
+#else
+#define R(x) "%%r"#x"x"
+#endif
+	"push "R(a)"; push "R(b)"; push "R(c)"; push "R(d)"\n\t"
+	"test %1,%1 ; jz 1f ; ud2a ; .ascii \"xen\" ; 1: cpuid\n\t"
+	"mov %%eax,(%2); mov %%ebx,4(%2)\n\t"
+	"mov %%ecx,8(%2); mov %%edx,12(%2)\n\t"
+	"pop "R(d)"; pop "R(c)"; pop "R(b)"; pop "R(a)"\n\t"
+	: : "a" (idx), "c" (pv_context), "S" (regs) : "memory" );
+}
+
+static int check_for_xen(int pv_context)
+{
+	uint32_t regs[4];
+	char signature[13];
+	uint32_t base;
+
+	for (base = 0x40000000; base < 0x40010000; base += 0x100)
+	{
+		xen_cpuid(base, regs, pv_context);
+
+		*(uint32_t *)(signature + 0) = regs[1];
+		*(uint32_t *)(signature + 4) = regs[2];
+		*(uint32_t *)(signature + 8) = regs[3];
+		signature[12] = '\0';
+
+		if (strcmp("XenVMMXenVMM", signature) == 0 && regs[0] >= (base + 2))
+			goto found;
+	}
+
+	return 0;
+
+found:
+	xen_cpuid(base + 1, regs, pv_context);
+	return regs[0];
+}
+
+static int xen_detect_pv_guest(void)
+{
+	struct sigaction act, oldact;
+	int is_pv = -1;
+
+	if (setjmp(xen_sigill_jmp))
+		return is_pv;
+
+	memset(&act, 0, sizeof(act));
+	act.sa_handler = xen_sigill_handler;
+	sigemptyset (&act.sa_mask);
+	if (sigaction(SIGILL, &act, &oldact))
+		return is_pv;
+	if (check_for_xen(1))
+		is_pv = 1;
+	sigaction(SIGILL, &oldact, NULL);
+	return is_pv;
+}
+#else
+static int xen_detect_pv_guest(void)
+{
+	return 1;
+}
+#endif
 
+/*
+ * Return 1 if its a PV guest.
+ * This includes dom0, which is the only PV guest where kexec/kdump works.
+ * HVM guests have to be handled as native hardware.
+ */
 int xen_present(void)
 {
 	if (!is_dom0) {
-		if (access("/proc/xen/capabilities", F_OK) == 0)
-			is_dom0 = 1;
+		if (access("/proc/xen", F_OK) == 0)
+			is_dom0 = xen_detect_pv_guest();
 		else
 			is_dom0 = -1;
 	}

_______________________________________________
kexec mailing list
kexec@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/kexec

^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: [PATCH v2] fix Xen detection for xenfs in pv_ops kernel
  2011-08-03 18:07 [PATCH v2] fix Xen detection for xenfs in pv_ops kernel Olaf Hering
@ 2011-08-03 23:44 ` Simon Horman
  0 siblings, 0 replies; 2+ messages in thread
From: Simon Horman @ 2011-08-03 23:44 UTC (permalink / raw)
  To: Olaf Hering; +Cc: kexec

On Wed, Aug 03, 2011 at 08:07:05PM +0200, Olaf Hering wrote:
> The pv_ops kernel in mainline Linux provides xenfs which has to be
> mounted at /proc/xen.  It creates /proc/xen/capabilities unconditionally
> which makes it impossible to distinguish PVonHVM guests from PV guests.
> Use code from xen-detect.c to check wether kexec runs on a PV guest.
> Without this change PVonHVM guests will be detected incorrectly as plain
> PV guests.

Thanks, applied.

_______________________________________________
kexec mailing list
kexec@lists.infradead.org
http://lists.infradead.org/mailman/listinfo/kexec

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2011-08-03 23:45 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2011-08-03 18:07 [PATCH v2] fix Xen detection for xenfs in pv_ops kernel Olaf Hering
2011-08-03 23:44 ` Simon Horman

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.