Simon Horman
2008-Feb-27 07:01 UTC
[Xen-devel] [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
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. -- Horms _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Simon Horman
2008-Feb-27 07:01 UTC
[Xen-devel] [patch 1/3] kexec: limit scope of the use of compat_kexec_range_t
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Simon Horman
2008-Feb-27 07:01 UTC
[Xen-devel] [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Alex Williamson
2008-Feb-27 19:55 UTC
[Xen-devel] Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
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. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Simon Horman
2008-Feb-28 03:35 UTC
[Xen-devel] Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Simon Horman
2008-Feb-28 07:50 UTC
[Xen-devel] Re: [Xen-ia64-devel] [patch 3/3] kexec: extend hypercall for efi memory map, boot parameter and xenheap regions
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Keir Fraser
2008-Feb-28 08:55 UTC
Re: [Xen-devel] Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Alex Williamson
2008-Feb-28 15:36 UTC
[Xen-devel] Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
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. _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel
Simon Horman
2008-Feb-29 00:54 UTC
Re: [Xen-devel] Re: [patch 0/3] xen: Extend xen kexec hypercall to return additional regions
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 _______________________________________________ Xen-devel mailing list Xen-devel@lists.xensource.com http://lists.xensource.com/xen-devel