* [patch 1/3] kexec: limit scope of the use of compat_kexec_range_t
2008-02-27 7:01 [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Simon Horman
@ 2008-02-27 7:01 ` Simon Horman
2008-02-27 7:01 ` [patch 2/3] kexec: Add machine_kexec_get() Simon Horman
` (2 subsequent siblings)
3 siblings, 0 replies; 10+ messages in thread
From: Simon Horman @ 2008-02-27 7:01 UTC (permalink / raw)
To: xen-devel, xen-ia64-devel; +Cc: Ian Campbell, Alex Williamson
[-- Attachment #1: kexec-compat-get.patch --]
[-- Type: text/plain, Size: 5816 bytes --]
Unless I am mistaken, the compat functions are provided a stable ABI. This
includes providing a stable version of xen_kexec_range_t in the form of
compat_kexec_range_t. However, internally it doesn't really matter how xen
represents the data.
Currently the code provides for the creation of a compat version of all
kexec range functions, which use the compat_kexec_range_t function. This
is difficult to extend if range code exists outside of xen/common/kexec.c.
The existence of "#ifdef CONFIG_X86_64" in the code suggests that some of
the range code might be better off in architecture specific code.
Furthermore, subsequent patches will introduce ia64-specific range handling
code, which really would be much better off somewhere in arch/ia64/ .
With this in mind, the handling of compat_kexec_range_t is changed such
that the code which reads and returns data from user-space translates
between compat_kexec_range_t and xen_kexec_range_t. As, padding aside, the
two structures are currently the same this is quite easy. Things may get
more tricky in the future, but I don't believe this change is likely to
make things significantly worse (or better) in that regard. In any case,
refactoring can occur again as required.
Subsequent patches will add architecture specific code under xen/arch/
Signed-off-by: Simon Horman <horms@verge.net.au>
---
xen/common/compat/kexec.c | 5 --
xen/common/kexec.c | 79 +++++++++++++++++++++++++++++++++++----------
2 files changed, 62 insertions(+), 22 deletions(-)
Index: xen-unstable.hg/xen/common/compat/kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/common/compat/kexec.c 2008-02-25 16:24:12.000000000 +0900
+++ xen-unstable.hg/xen/common/compat/kexec.c 2008-02-25 16:31:10.000000000 +0900
@@ -9,11 +9,6 @@
#define do_kexec_op compat_kexec_op
-#undef kexec_get
-#define kexec_get(x) compat_kexec_get_##x
-#define xen_kexec_range compat_kexec_range
-#define xen_kexec_range_t compat_kexec_range_t
-
#define kexec_load_unload compat_kexec_load_unload
#define xen_kexec_load compat_kexec_load
#define xen_kexec_load_t compat_kexec_load_t
Index: xen-unstable.hg/xen/common/kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/common/kexec.c 2008-02-25 16:06:24.000000000 +0900
+++ xen-unstable.hg/xen/common/kexec.c 2008-02-25 17:04:20.000000000 +0900
@@ -153,11 +153,7 @@ static int sizeof_note(const char *name,
ELFNOTE_ALIGN(descsz));
}
-#define kexec_get(x) kexec_get_##x
-
-#endif
-
-static int kexec_get(reserve)(xen_kexec_range_t *range)
+static int kexec_get_reserve(xen_kexec_range_t *range)
{
if ( kexec_crash_area.size > 0 && kexec_crash_area.start > 0) {
range->start = kexec_crash_area.start;
@@ -168,7 +164,7 @@ static int kexec_get(reserve)(xen_kexec_
return 0;
}
-static int kexec_get(xen)(xen_kexec_range_t *range)
+static int kexec_get_xen(xen_kexec_range_t *range)
{
#ifdef CONFIG_X86_64
range->start = xenheap_phys_start;
@@ -179,7 +175,7 @@ static int kexec_get(xen)(xen_kexec_rang
return 0;
}
-static int kexec_get(cpu)(xen_kexec_range_t *range)
+static int kexec_get_cpu(xen_kexec_range_t *range)
{
int nr = range->nr;
int nr_bytes = 0;
@@ -223,33 +219,78 @@ static int kexec_get(cpu)(xen_kexec_rang
return 0;
}
-static int kexec_get(range)(XEN_GUEST_HANDLE(void) uarg)
+static int kexec_get_range_internal(xen_kexec_range_t *range)
{
- xen_kexec_range_t range;
int ret = -EINVAL;
- if ( unlikely(copy_from_guest(&range, uarg, 1)) )
- return -EFAULT;
-
- switch ( range.range )
+ switch ( range->range )
{
case KEXEC_RANGE_MA_CRASH:
- ret = kexec_get(reserve)(&range);
+ ret = kexec_get_reserve(range);
break;
case KEXEC_RANGE_MA_XEN:
- ret = kexec_get(xen)(&range);
+ ret = kexec_get_xen(range);
break;
case KEXEC_RANGE_MA_CPU:
- ret = kexec_get(cpu)(&range);
+ ret = kexec_get_cpu(range);
break;
}
+ return ret;
+}
+
+static int kexec_get_range(XEN_GUEST_HANDLE(void) uarg)
+{
+ xen_kexec_range_t range;
+ int ret = -EINVAL;
+
+ if ( unlikely(copy_from_guest(&range, uarg, 1)) )
+ return -EFAULT;
+
+ ret = kexec_get_range_internal(&range);
+
if ( ret == 0 && unlikely(copy_to_guest(uarg, &range, 1)) )
return -EFAULT;
return ret;
}
+#else /* COMPAT */
+
+#ifdef CONFIG_COMPAT
+static int kexec_get_range_compat(XEN_GUEST_HANDLE(void) uarg)
+{
+ xen_kexec_range_t range;
+ compat_kexec_range_t compat_range;
+ int ret = -EINVAL;
+
+ if ( unlikely(copy_from_guest(&compat_range, uarg, 1)) )
+ return -EFAULT;
+
+ range.range = compat_range.range;
+ range.nr = compat_range.nr;
+ range.size = compat_range.size;
+ range.start = compat_range.start;
+
+ ret = kexec_get_range_internal(&range);
+
+ if ( ret == 0 ) {
+ range.range = compat_range.range;
+ range.nr = compat_range.nr;
+ range.size = compat_range.size;
+ range.start = compat_range.start;
+
+ if ( unlikely(copy_to_guest(uarg, &compat_range, 1)) )
+ return -EFAULT;
+ }
+
+ return ret;
+}
+#endif /* CONFIG_COMPAT */
+
+#endif /* COMPAT */
+
+
#ifndef COMPAT
static int kexec_load_get_bits(int type, int *base, int *bit)
@@ -375,7 +416,11 @@ ret_t do_kexec_op(unsigned long op, XEN_
switch ( op )
{
case KEXEC_CMD_kexec_get_range:
- ret = kexec_get(range)(uarg);
+#ifndef COMPAT
+ ret = kexec_get_range(uarg);
+#else
+ ret = kexec_get_range_compat(uarg);
+#endif
break;
case KEXEC_CMD_kexec_load:
case KEXEC_CMD_kexec_unload:
--
--
Horms
^ permalink raw reply [flat|nested] 10+ messages in thread* [patch 2/3] kexec: Add machine_kexec_get()
2008-02-27 7:01 [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Simon Horman
2008-02-27 7:01 ` [patch 1/3] kexec: limit scope of the use of compat_kexec_range_t Simon Horman
@ 2008-02-27 7:01 ` Simon Horman
2008-02-27 7:01 ` [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions Simon Horman
2008-02-27 19:55 ` [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Alex Williamson
3 siblings, 0 replies; 10+ messages in thread
From: Simon Horman @ 2008-02-27 7:01 UTC (permalink / raw)
To: xen-devel, xen-ia64-devel; +Cc: Ian Campbell, Alex Williamson
[-- Attachment #1: machine_kexec_get_xen.patch --]
[-- Type: text/plain, Size: 7927 bytes --]
Introduce machine_kexec_get to allow architecture-specific handling of the
xen region. x86_64 is currently different to x86_32 and ia64. A subsequent
patch will make ia64 different from x86_32.
Signed-off-by: Simon Horman <horms@verge.net.au>
---
xen/arch/ia64/xen/machine_kexec.c | 15 +++++++++++++++
xen/arch/powerpc/machine_kexec.c | 6 ++++++
xen/arch/x86/machine_kexec.c | 10 ++++++++++
xen/arch/x86/x86_32/Makefile | 1 +
xen/arch/x86/x86_32/machine_kexec.c | 33 +++++++++++++++++++++++++++++++++
xen/arch/x86/x86_64/Makefile | 1 +
xen/arch/x86/x86_64/machine_kexec.c | 32 ++++++++++++++++++++++++++++++++
xen/common/kexec.c | 18 ++++--------------
xen/include/xen/kexec.h | 1 +
9 files changed, 103 insertions(+), 14 deletions(-)
Index: xen-unstable.hg/xen/arch/ia64/xen/machine_kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/arch/ia64/xen/machine_kexec.c 2008-02-25 17:01:38.000000000 +0900
+++ xen-unstable.hg/xen/arch/ia64/xen/machine_kexec.c 2008-02-25 17:37:10.000000000 +0900
@@ -162,6 +162,21 @@ void machine_reboot_kexec(xen_kexec_imag
machine_kexec(image);
}
+static int machine_kexec_get_xen(xen_kexec_range_t *range)
+{
+ range->start = virt_to_maddr(_start);
+ range->size = (unsigned long)xenheap_phys_end -
+ (unsigned long)range->start;
+ return 0;
+}
+
+int machine_kexec_get(xen_kexec_range_t *range)
+{
+ if (range->range != KEXEC_RANGE_MA_XEN)
+ return -EINVAL;
+ return machine_kexec_get_xen(range);
+}
+
/*
* Local variables:
* mode: C
Index: xen-unstable.hg/xen/arch/powerpc/machine_kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/arch/powerpc/machine_kexec.c 2008-02-25 17:01:38.000000000 +0900
+++ xen-unstable.hg/xen/arch/powerpc/machine_kexec.c 2008-02-25 17:11:39.000000000 +0900
@@ -24,6 +24,12 @@ void machine_kexec(xen_kexec_image_t *im
printk("STUB: " __FILE__ ": %s: not implemented\n", __FUNCTION__);
}
+int machine_kexec_get(xen_kexec_image_t *image)
+{
+ printk("STUB: " __FILE__ ": %s: not implemented\n", __FUNCTION__);
+ return -1;
+}
+
/*
* Local variables:
* mode: C
Index: xen-unstable.hg/xen/common/kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/common/kexec.c 2008-02-25 17:04:20.000000000 +0900
+++ xen-unstable.hg/xen/common/kexec.c 2008-02-25 17:08:53.000000000 +0900
@@ -20,6 +20,7 @@
#include <xen/spinlock.h>
#include <xen/version.h>
#include <xen/console.h>
+#include <xen/kexec.h>
#include <public/elfnote.h>
#include <xsm/xsm.h>
@@ -164,17 +165,6 @@ static int kexec_get_reserve(xen_kexec_r
return 0;
}
-static int kexec_get_xen(xen_kexec_range_t *range)
-{
-#ifdef CONFIG_X86_64
- range->start = xenheap_phys_start;
-#else
- range->start = virt_to_maddr(_start);
-#endif
- range->size = (unsigned long)xenheap_phys_end - (unsigned long)range->start;
- return 0;
-}
-
static int kexec_get_cpu(xen_kexec_range_t *range)
{
int nr = range->nr;
@@ -228,12 +218,12 @@ static int kexec_get_range_internal(xen_
case KEXEC_RANGE_MA_CRASH:
ret = kexec_get_reserve(range);
break;
- case KEXEC_RANGE_MA_XEN:
- ret = kexec_get_xen(range);
- break;
case KEXEC_RANGE_MA_CPU:
ret = kexec_get_cpu(range);
break;
+ default:
+ ret = machine_kexec_get(range);
+ break;
}
return ret;
Index: xen-unstable.hg/xen/arch/x86/machine_kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/arch/x86/machine_kexec.c 2008-02-25 17:01:38.000000000 +0900
+++ xen-unstable.hg/xen/arch/x86/machine_kexec.c 2008-02-25 17:11:55.000000000 +0900
@@ -24,6 +24,9 @@ typedef void (*relocate_new_kernel_t)(
unsigned long *page_list,
unsigned long start_address);
+extern int machine_kexec_get_xen(xen_kexec_range_t *range);
+
+
int machine_kexec_load(int type, int slot, xen_kexec_image_t *image)
{
unsigned long prev_ma = 0;
@@ -135,6 +138,13 @@ void machine_kexec(xen_kexec_image_t *im
}
}
+int machine_kexec_get(xen_kexec_range_t *range)
+{
+ if (range->range != KEXEC_RANGE_MA_XEN)
+ return -EINVAL;
+ return machine_kexec_get_xen(range);
+}
+
/*
* Local variables:
* mode: C
Index: xen-unstable.hg/xen/arch/x86/x86_32/Makefile
===================================================================
--- xen-unstable.hg.orig/xen/arch/x86/x86_32/Makefile 2008-02-25 17:01:38.000000000 +0900
+++ xen-unstable.hg/xen/arch/x86/x86_32/Makefile 2008-02-25 17:08:10.000000000 +0900
@@ -4,6 +4,7 @@ obj-y += gpr_switch.o
obj-y += mm.o
obj-y += seg_fixup.o
obj-y += traps.o
+obj-y += machine_kexec.o
obj-$(crash_debug) += gdbstub.o
Index: xen-unstable.hg/xen/arch/x86/x86_32/machine_kexec.c
===================================================================
--- /dev/null 1970-01-01 00:00:00.000000000 +0000
+++ xen-unstable.hg/xen/arch/x86/x86_32/machine_kexec.c 2008-02-25 17:08:10.000000000 +0900
@@ -0,0 +1,33 @@
+/******************************************************************************
+ * machine_kexec.c
+ *
+ * Xen port written by:
+ * - Simon 'Horms' Horman <horms@verge.net.au>
+ * - Magnus Damm <magnus@valinux.co.jp>
+ */
+
+#ifndef CONFIG_COMPAT
+
+#include <xen/types.h>
+#include <xen/kernel.h>
+#include <asm/page.h>
+#include <public/kexec.h>
+
+int machine_kexec_get_xen(xen_kexec_range_t *range)
+{
+ range->start = virt_to_maddr(_start);
+ range->size = (unsigned long)xenheap_phys_end -
+ (unsigned long)range->start;
+ return 0;
+}
+#endif
+
+/*
+ * Local variables:
+ * mode: C
+ * c-set-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
Index: xen-unstable.hg/xen/include/xen/kexec.h
===================================================================
--- xen-unstable.hg.orig/xen/include/xen/kexec.h 2008-02-25 17:01:38.000000000 +0900
+++ xen-unstable.hg/xen/include/xen/kexec.h 2008-02-25 17:08:10.000000000 +0900
@@ -31,6 +31,7 @@ void kexec_disable_iosapic(void);
void kexec_crash_save_cpu(void);
crash_xen_info_t *kexec_crash_save_info(void);
void machine_crash_shutdown(void);
+int machine_kexec_get(xen_kexec_range_t *range);
#endif /* __XEN_KEXEC_H__ */
Index: xen-unstable.hg/xen/arch/x86/x86_64/Makefile
===================================================================
--- xen-unstable.hg.orig/xen/arch/x86/x86_64/Makefile 2008-02-25 17:01:38.000000000 +0900
+++ xen-unstable.hg/xen/arch/x86/x86_64/Makefile 2008-02-25 17:11:06.000000000 +0900
@@ -4,6 +4,7 @@ obj-y += entry.o
obj-y += gpr_switch.o
obj-y += mm.o
obj-y += traps.o
+obj-y += machine_kexec.o
obj-$(crash_debug) += gdbstub.o
obj-$(CONFIG_COMPAT) += compat.o
Index: xen-unstable.hg/xen/arch/x86/x86_64/machine_kexec.c
===================================================================
--- /dev/null 1970-01-01 00:00:00.000000000 +0000
+++ xen-unstable.hg/xen/arch/x86/x86_64/machine_kexec.c 2008-02-25 17:08:10.000000000 +0900
@@ -0,0 +1,32 @@
+/******************************************************************************
+ * machine_kexec.c
+ *
+ * Xen port written by:
+ * - Simon 'Horms' Horman <horms@verge.net.au>
+ * - Magnus Damm <magnus@valinux.co.jp>
+ */
+
+#ifndef CONFIG_COMPAT
+
+#include <xen/types.h>
+#include <asm/page.h>
+#include <public/kexec.h>
+
+int machine_kexec_get_xen(xen_kexec_range_t *range)
+{
+ range->start = xenheap_phys_start;
+ range->size = (unsigned long)xenheap_phys_end -
+ (unsigned long)range->start;
+ return 0;
+}
+#endif
+
+/*
+ * Local variables:
+ * mode: C
+ * c-set-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
--
--
Horms
^ permalink raw reply [flat|nested] 10+ messages in thread* [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions
2008-02-27 7:01 [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Simon Horman
2008-02-27 7:01 ` [patch 1/3] kexec: limit scope of the use of compat_kexec_range_t Simon Horman
2008-02-27 7:01 ` [patch 2/3] kexec: Add machine_kexec_get() Simon Horman
@ 2008-02-27 7:01 ` Simon Horman
2008-02-28 7:50 ` [Xen-ia64-devel] " Simon Horman
2008-02-27 19:55 ` [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Alex Williamson
3 siblings, 1 reply; 10+ messages in thread
From: Simon Horman @ 2008-02-27 7:01 UTC (permalink / raw)
To: xen-devel, xen-ia64-devel; +Cc: Ian Campbell, Alex Williamson
[-- Attachment #1: hypervisor-regions.2.patch --]
[-- Type: text/plain, Size: 4555 bytes --]
Extend the kexec hypercall to allow it to return the efi memory map, boot
parameter and xen heap regions.
The efi memory map and boot parameter regions need to be supplied
by xen to dom0, rather than established by dom0 as dom0's memory
is not machine memory and thus the regions are not in the correct location.
These regions are inserted into machine_iomem by dom0.
The xen heap region is needed as on xen the hypervisor code and
heap exist in two different EFI memory regions, which are
reflected in machine_iomem. Thus a single xen code region can't be
inserted into machine_iomem.
* There is also a linux-xen portion of this patch.
Signed-off-by: Simon Horman <horms@verge.net.au>
---
xen/arch/ia64/xen/machine_kexec.c | 45 ++++++++++++++++++++++++++++++++-----
xen/include/public/kexec.h | 15 +++++++++---
2 files changed, 51 insertions(+), 9 deletions(-)
Index: xen-unstable.hg/xen/arch/ia64/xen/machine_kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/arch/ia64/xen/machine_kexec.c 2008-02-27 15:48:02.000000000 +0900
+++ xen-unstable.hg/xen/arch/ia64/xen/machine_kexec.c 2008-02-27 15:48:03.000000000 +0900
@@ -24,6 +24,7 @@
#include <linux/cpu.h>
#include <linux/notifier.h>
#include <asm/dom_fw_dom0.h>
+#include <asm-generic/sections.h>
typedef asmlinkage NORET_TYPE void (*relocate_new_kernel_t)(
unsigned long indirection_page,
@@ -167,17 +168,49 @@ void machine_reboot_kexec(xen_kexec_imag
static int machine_kexec_get_xen(xen_kexec_range_t *range)
{
- range->start = virt_to_maddr(_start);
- range->size = (unsigned long)xenheap_phys_end -
- (unsigned long)range->start;
+ range->start = range->start = ia64_tpa(_text);
+ range->size = (unsigned long)_end - (unsigned long)_text;
+ return 0;
+}
+
+#define ELF_PAGE_SHIFT 16
+#define ELF_PAGE_SIZE (__IA64_UL_CONST(1) << ELF_PAGE_SHIFT)
+#define ELF_PAGE_MASK (~(ELF_PAGE_SIZE - 1))
+
+static int machine_kexec_get_xenheap(xen_kexec_range_t *range)
+{
+ range->start = (ia64_tpa(_end) + (ELF_PAGE_SIZE - 1)) & ELF_PAGE_MASK;
+ range->size = (unsigned long)xenheap_phys_end - (unsigned long)range->start;
+ return 0;
+}
+
+static int machine_kexec_get_boot_param(xen_kexec_range_t *range)
+{
+ range->start = __pa(ia64_boot_param);
+ range->size = sizeof(*ia64_boot_param);
+ return 0;
+}
+
+static int machine_kexec_get_efi_memmap(xen_kexec_range_t *range)
+{
+ range->start = ia64_boot_param->efi_memmap;
+ range->size = ia64_boot_param->efi_memmap_size;
return 0;
}
int machine_kexec_get(xen_kexec_range_t *range)
{
- if (range->range != KEXEC_RANGE_MA_XEN)
- return -EINVAL;
- return machine_kexec_get_xen(range);
+ switch (range->range) {
+ case KEXEC_RANGE_MA_XEN:
+ return machine_kexec_get_xen(range);
+ case KEXEC_RANGE_MA_XENHEAP:
+ return machine_kexec_get_xenheap(range);
+ case KEXEC_RANGE_MA_BOOT_PARAM:
+ return machine_kexec_get_boot_param(range);
+ case KEXEC_RANGE_MA_EFI_MEMMAP:
+ return machine_kexec_get_efi_memmap(range);
+ }
+ return -EINVAL;
}
/*
Index: xen-unstable.hg/xen/include/public/kexec.h
===================================================================
--- xen-unstable.hg.orig/xen/include/public/kexec.h 2008-02-27 12:54:37.000000000 +0900
+++ xen-unstable.hg/xen/include/public/kexec.h 2008-02-27 15:48:03.000000000 +0900
@@ -126,9 +126,18 @@ typedef struct xen_kexec_load {
xen_kexec_image_t image;
} xen_kexec_load_t;
-#define KEXEC_RANGE_MA_CRASH 0 /* machine address and size of crash area */
-#define KEXEC_RANGE_MA_XEN 1 /* machine address and size of Xen itself */
-#define KEXEC_RANGE_MA_CPU 2 /* machine address and size of a CPU note */
+#define KEXEC_RANGE_MA_CRASH 0 /* machine address and size of crash area */
+#define KEXEC_RANGE_MA_XEN 1 /* machine address and size of Xen itself */
+#define KEXEC_RANGE_MA_CPU 2 /* machine address and size of a CPU note */
+#define KEXEC_RANGE_MA_XENHEAP 3 /* machine address and size of xenheap
+ * Note that although this is adjacent
+ * to Xen it exists in a separate EFI
+ * region on ia64, and thus needs to be
+ * inserted into iomem_machine separately */
+#define KEXEC_RANGE_MA_BOOT_PARAM 4 /* machine address and size of
+ * the ia64_boot_param */
+#define KEXEC_RANGE_MA_EFI_MEMMAP 5 /* machine address and size of
+ * of the EFI Memory Map */
/*
* Find the address and size of certain memory areas
--
--
Horms
^ permalink raw reply [flat|nested] 10+ messages in thread* Re: [Xen-ia64-devel] [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions
2008-02-27 7:01 ` [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions Simon Horman
@ 2008-02-28 7:50 ` Simon Horman
0 siblings, 0 replies; 10+ messages in thread
From: Simon Horman @ 2008-02-28 7:50 UTC (permalink / raw)
To: xen-devel, xen-ia64-devel; +Cc: Ian Campbell, Alex Williamson
Extend the kexec hypercall to allow it to return the efi memory map, boot
parameter and xen heap regions.
The efi memory map and boot parameter regions need to be supplied
by xen to dom0, rather than established by dom0 as dom0's memory
is not machine memory and thus the regions are not in the correct location.
These regions are inserted into machine_iomem by dom0.
The xen heap region is needed as on xen the hypervisor code and
heap exist in two different EFI memory regions, which are
reflected in machine_iomem. Thus a single xen code region can't be
inserted into machine_iomem.
* There is also a linux-xen portion of this patch.
Signed-off-by: Simon Horman <horms@verge.net.au>
---
xen/arch/ia64/xen/machine_kexec.c | 45 ++++++++++++++++++++++++++++++++-----
xen/include/public/kexec.h | 15 +++++++++---
2 files changed, 51 insertions(+), 9 deletions(-)
Thu, 28 Feb 2008 16:30:07 +0900
- Consistently use tabs or spaces for indentation. Thanks to Alex Williamson
Index: xen-unstable.hg/xen/arch/ia64/xen/machine_kexec.c
===================================================================
--- xen-unstable.hg.orig/xen/arch/ia64/xen/machine_kexec.c 2008-02-27 15:48:02.000000000 +0900
+++ xen-unstable.hg/xen/arch/ia64/xen/machine_kexec.c 2008-02-27 15:48:03.000000000 +0900
@@ -24,6 +24,7 @@
#include <linux/cpu.h>
#include <linux/notifier.h>
#include <asm/dom_fw_dom0.h>
+#include <asm-generic/sections.h>
typedef asmlinkage NORET_TYPE void (*relocate_new_kernel_t)(
unsigned long indirection_page,
@@ -167,17 +168,50 @@ void machine_reboot_kexec(xen_kexec_imag
static int machine_kexec_get_xen(xen_kexec_range_t *range)
{
- range->start = virt_to_maddr(_start);
- range->size = (unsigned long)xenheap_phys_end -
- (unsigned long)range->start;
+ range->start = range->start = ia64_tpa(_text);
+ range->size = (unsigned long)_end - (unsigned long)_text;
+ return 0;
+}
+
+#define ELF_PAGE_SHIFT 16
+#define ELF_PAGE_SIZE (__IA64_UL_CONST(1) << ELF_PAGE_SHIFT)
+#define ELF_PAGE_MASK (~(ELF_PAGE_SIZE - 1))
+
+static int machine_kexec_get_xenheap(xen_kexec_range_t *range)
+{
+ range->start = (ia64_tpa(_end) + (ELF_PAGE_SIZE - 1)) & ELF_PAGE_MASK;
+ range->size = (unsigned long)xenheap_phys_end -
+ (unsigned long)range->start;
+ return 0;
+}
+
+static int machine_kexec_get_boot_param(xen_kexec_range_t *range)
+{
+ range->start = __pa(ia64_boot_param);
+ range->size = sizeof(*ia64_boot_param);
+ return 0;
+}
+
+static int machine_kexec_get_efi_memmap(xen_kexec_range_t *range)
+{
+ range->start = ia64_boot_param->efi_memmap;
+ range->size = ia64_boot_param->efi_memmap_size;
return 0;
}
int machine_kexec_get(xen_kexec_range_t *range)
{
- if (range->range != KEXEC_RANGE_MA_XEN)
- return -EINVAL;
- return machine_kexec_get_xen(range);
+ switch (range->range) {
+ case KEXEC_RANGE_MA_XEN:
+ return machine_kexec_get_xen(range);
+ case KEXEC_RANGE_MA_XENHEAP:
+ return machine_kexec_get_xenheap(range);
+ case KEXEC_RANGE_MA_BOOT_PARAM:
+ return machine_kexec_get_boot_param(range);
+ case KEXEC_RANGE_MA_EFI_MEMMAP:
+ return machine_kexec_get_efi_memmap(range);
+ }
+ return -EINVAL;
}
/*
Index: xen-unstable.hg/xen/include/public/kexec.h
===================================================================
--- xen-unstable.hg.orig/xen/include/public/kexec.h 2008-02-27 12:54:37.000000000 +0900
+++ xen-unstable.hg/xen/include/public/kexec.h 2008-02-27 15:48:03.000000000 +0900
@@ -126,9 +126,18 @@ typedef struct xen_kexec_load {
xen_kexec_image_t image;
} xen_kexec_load_t;
-#define KEXEC_RANGE_MA_CRASH 0 /* machine address and size of crash area */
-#define KEXEC_RANGE_MA_XEN 1 /* machine address and size of Xen itself */
-#define KEXEC_RANGE_MA_CPU 2 /* machine address and size of a CPU note */
+#define KEXEC_RANGE_MA_CRASH 0 /* machine address and size of crash area */
+#define KEXEC_RANGE_MA_XEN 1 /* machine address and size of Xen itself */
+#define KEXEC_RANGE_MA_CPU 2 /* machine address and size of a CPU note */
+#define KEXEC_RANGE_MA_XENHEAP 3 /* machine address and size of xenheap
+ * Note that although this is adjacent
+ * to Xen it exists in a separate EFI
+ * region on ia64, and thus needs to be
+ * inserted into iomem_machine separately */
+#define KEXEC_RANGE_MA_BOOT_PARAM 4 /* machine address and size of
+ * the ia64_boot_param */
+#define KEXEC_RANGE_MA_EFI_MEMMAP 5 /* machine address and size of
+ * of the EFI Memory Map */
/*
* Find the address and size of certain memory areas
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
2008-02-27 7:01 [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Simon Horman
` (2 preceding siblings ...)
2008-02-27 7:01 ` [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions Simon Horman
@ 2008-02-27 19:55 ` Alex Williamson
2008-02-28 3:35 ` Simon Horman
3 siblings, 1 reply; 10+ messages in thread
From: Alex Williamson @ 2008-02-27 19:55 UTC (permalink / raw)
To: Simon Horman; +Cc: xen-devel, Ian Campbell, xen-ia64-devel
Hi Simon,
I'm not seeing how this doesn't break the x86 COMPAT/CONFIG_COMPAT
code paths. Where does kexec_get_range_internal() get defined for
COMPAT in [1/3], and where is machine_kexec_get_xen() defined for
CONFIG_COMPAT in [2/3]? I'm fine with the ia64 parts if Ian/Keir want
to check them into the main tree, but there is some mixed indenting in
[3/3]. Thanks,
Alex
On Wed, 2008-02-27 at 16:01 +0900, Simon Horman wrote:
> Hi,
>
> this series starts off by reworking the hypercall a bit to
> allow it to have architecture-specific code under xen/arch/
>
> It then extends the hypercall for some extra regions that
> are needed for xen ia64.
>
> There are generic and ia64 specific patches in this series.
> I wanted to post them together as they don't make much sense
> without each other.
>
> There are related xen-linux patches that I will send as a separate series.
> There are related kexec-tools patches which I have posted to
> the kexec mailing list and intend to merge.
> http://lists.infradead.org/pipermail/kexec/2008-February/001348.html
>
>
> The end-game here is to make sure that all the reserved regions
> show up in /proc/iomem_machine on ia64. This currently does not happen.
> And manifests as kexec only being able to be performed once as
> the boot parameter ends up being overwritten in relocate_kernel before
> purgatory is reached.
>
> Xen--kexec-->Xen--kexec [hang in purgatory!]
>
>
> The EFI-RID patches for ia64 xen kexec are also needed for kexec
> to function on ia64. However they touch different code paths and can
> be merged separately.
>
--
Alex Williamson HP Open Source & Linux Org.
^ permalink raw reply [flat|nested] 10+ messages in thread* Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
2008-02-27 19:55 ` [patch 0/3] xen: Extend xen kexec hypercall to return additional regions Alex Williamson
@ 2008-02-28 3:35 ` Simon Horman
2008-02-28 8:55 ` Keir Fraser
2008-02-28 15:36 ` Alex Williamson
0 siblings, 2 replies; 10+ messages in thread
From: Simon Horman @ 2008-02-28 3:35 UTC (permalink / raw)
To: Alex Williamson; +Cc: xen-devel, Ian Campbell, xen-ia64-devel
On Wed, Feb 27, 2008 at 12:55:52PM -0700, Alex Williamson wrote:
> Hi Simon,
>
> I'm not seeing how this doesn't break the x86 COMPAT/CONFIG_COMPAT
> code paths. Where does kexec_get_range_internal() get defined for
> COMPAT in [1/3], and where is machine_kexec_get_xen() defined for
> CONFIG_COMPAT in [2/3]? I'm fine with the ia64 parts if Ian/Keir want
> to check them into the main tree, but there is some mixed indenting in
> [3/3]. Thanks,
Thanks for pointing out the white-space issue, I'll fix that up asap.
As for the compat stuff...
The way that I understand the code is that basically
xen/common/kexec.c gets compiled twice using the following mechanism
at the very bottom of the file:
#if defined(CONFIG_COMPAT) && !defined(COMPAT)
#include "compat/kexec.c"
#endif
Where xen/common/compat/kexec.c looks a bit like this:
#define COMPAT
...
#include "../kexec.c"
So on the first stage of the run through xen/common/kexec.c, before
we get to #include "compat/kexec.c", any code that
is not protected by #ifdef COMPAT will be compiled.
If CONFIG_COMPAT isn't defined (elsewhere) then that is the
end and all is well.
If CONFIG_COMPAT is defined, then we enter the second stage,
where any code in "compat/kexec.c" not protected by #ifndef COMPAT
is compiled.
The important thing to note is that during this second stage,
all the code compiled in the first stage still exists.
kexec_get_range_internal() and all the functions that it calls
either
a) exist in xen/common/kexec.c and are compiled during the first stage,
that is, they are protected by #ifndef COMPAT.
b) present in other files that and are compiled independent
of any CONFIG_COMPAT games.
This means that kexec_get_range_internal(), and all the functions
that it relies on can be called by both non-compat version
of do_kexec_op(), which is compiled during the first stage,
and the compat version of do_kexec_op() (compat_kexec_op()).
The creation of the first version of do_kexec_op() is fairly obvious,
it is compiled as you would expect on a casual glance. This occurs
during stage one. The compilation of compat_kexec_op() is achieved
by "#define do_kexec_op compat_kexec_op" in xen/common/compat/kexec.c,
which essentially changes the function name for compilation in the
second phase.
I'll come right out and say that I don't fancy this two stage .c
indirectly including itself approach. And I hope this change can help us
move away from there, as well as providing the functionality
extendability that this patch set describes.
As to the extent of testing this code. I have run it on ia64 and it
works. I have also compiled it on both i386 and x86_64. The latter
uses CONFIG_COMPAT by default, which is the configuration I tested.
--
Horms
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
2008-02-28 3:35 ` Simon Horman
@ 2008-02-28 8:55 ` Keir Fraser
2008-02-29 0:54 ` Simon Horman
2008-02-28 15:36 ` Alex Williamson
1 sibling, 1 reply; 10+ messages in thread
From: Keir Fraser @ 2008-02-28 8:55 UTC (permalink / raw)
To: Simon Horman, Alex Williamson; +Cc: xen-devel, Ian Campbell, xen-ia64-devel
On 28/2/08 03:35, "Simon Horman" <horms@verge.net.au> wrote:
> I'll come right out and say that I don't fancy this two stage .c
> indirectly including itself approach. And I hope this change can help us
> move away from there, as well as providing the functionality
> extendability that this patch set describes.
You're not alone. ;-) However, it does work and anybody competent to clean
it up seems to have plenty of other stuff to do!
-- Keir
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
2008-02-28 8:55 ` Keir Fraser
@ 2008-02-29 0:54 ` Simon Horman
0 siblings, 0 replies; 10+ messages in thread
From: Simon Horman @ 2008-02-29 0:54 UTC (permalink / raw)
To: Keir Fraser; +Cc: xen-devel, Ian Campbell, Alex Williamson, xen-ia64-devel
On Thu, Feb 28, 2008 at 08:55:18AM +0000, Keir Fraser wrote:
> On 28/2/08 03:35, "Simon Horman" <horms@verge.net.au> wrote:
>
> > I'll come right out and say that I don't fancy this two stage .c
> > indirectly including itself approach. And I hope this change can help us
> > move away from there, as well as providing the functionality
> > extendability that this patch set describes.
>
> You're not alone. ;-) However, it does work and anybody competent to clean
> it up seems to have plenty of other stuff to do!
I'm more than happy to clean it up if there is a chance the patches
will be accepted. I'll start working on that. But can we treat
that separately to this series?
--
Horms
^ permalink raw reply [flat|nested] 10+ messages in thread
* Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
2008-02-28 3:35 ` Simon Horman
2008-02-28 8:55 ` Keir Fraser
@ 2008-02-28 15:36 ` Alex Williamson
1 sibling, 0 replies; 10+ messages in thread
From: Alex Williamson @ 2008-02-28 15:36 UTC (permalink / raw)
To: Simon Horman; +Cc: xen-devel, Ian Campbell, xen-ia64-devel
On Thu, 2008-02-28 at 12:35 +0900, Simon Horman wrote:
> I'll come right out and say that I don't fancy this two stage .c
> indirectly including itself approach. And I hope this change can help us
> move away from there, as well as providing the functionality
> extendability that this patch set describes.
Wow, that's pretty nasty. Thanks for the explanation.
Alex
--
Alex Williamson HP Open Source & Linux Org.
^ permalink raw reply [flat|nested] 10+ messages in thread