WARNING - OLD ARCHIVES

This is an archived copy of the Xen.org mailing list, which we have preserved to ensure that existing links to archives are not broken. The live archive, which contains the latest emails, can be found at http://lists.xen.org/
   
 
 
Xen 
 
Home Products Support Community News
 
   
 

xen-changelog

[Xen-changelog] [xen-unstable] [XEN/LINUX] Define Xen ELF notes in kerne

To: xen-changelog@xxxxxxxxxxxxxxxxxxx
Subject: [Xen-changelog] [xen-unstable] [XEN/LINUX] Define Xen ELF notes in kernel header and update dom0 builder.
From: Xen patchbot-unstable <patchbot-unstable@xxxxxxxxxxxxxxxxxxx>
Date: Wed, 23 Aug 2006 19:00:36 +0000
Delivery-date: Wed, 23 Aug 2006 12:01:08 -0700
Envelope-to: www-data@xxxxxxxxxxxxxxxxxx
List-help: <mailto:xen-changelog-request@lists.xensource.com?subject=help>
List-id: BK change log <xen-changelog.lists.xensource.com>
List-post: <mailto:xen-changelog@lists.xensource.com>
List-subscribe: <http://lists.xensource.com/cgi-bin/mailman/listinfo/xen-changelog>, <mailto:xen-changelog-request@lists.xensource.com?subject=subscribe>
List-unsubscribe: <http://lists.xensource.com/cgi-bin/mailman/listinfo/xen-changelog>, <mailto:xen-changelog-request@lists.xensource.com?subject=unsubscribe>
Reply-to: xen-devel@xxxxxxxxxxxxxxxxxxx
Sender: xen-changelog-bounces@xxxxxxxxxxxxxxxxxxx
# HG changeset patch
# User Ian Campbell <ian.campbell@xxxxxxxxxxxxx>
# Node ID faadbf5ba8d6a823aa60b2a65f44cef0f576d3ce
# Parent  d57b174adfd63787198c7ba4ea64e957caf592d0
[XEN/LINUX] Define Xen ELF notes in kernel header and update dom0 builder.

ELF notes provide a cleaner interface for passing Xen specific
information from the kernel to the domain builder than the existing
__xen_guest section string. The __xen_guest string is retained in
kernels built with 3.0.2 compatability for domU however dom0 requires
the new interface.

Signed-off-by: Ian Campbell <ian.campbell@xxxxxxxxxxxxx>
---
 linux-2.6-xen-sparse/arch/i386/kernel/head-xen.S   |   28 ++
 linux-2.6-xen-sparse/arch/x86_64/kernel/head-xen.S |   23 +-
 xen/arch/x86/domain_build.c                        |   39 +--
 xen/common/elf.c                                   |  225 ++++++++++++++-------
 xen/include/xen/elf.h                              |    4 
 xen/include/xen/sched.h                            |    2 
 6 files changed, 226 insertions(+), 95 deletions(-)

diff -r d57b174adfd6 -r faadbf5ba8d6 
linux-2.6-xen-sparse/arch/i386/kernel/head-xen.S
--- a/linux-2.6-xen-sparse/arch/i386/kernel/head-xen.S  Wed Aug 23 14:37:39 
2006 +0100
+++ b/linux-2.6-xen-sparse/arch/i386/kernel/head-xen.S  Wed Aug 23 14:41:05 
2006 +0100
@@ -2,6 +2,7 @@
 
 .text
 #include <linux/config.h>
+#include <linux/elfnote.h>
 #include <linux/threads.h>
 #include <linux/linkage.h>
 #include <asm/segment.h>
@@ -9,6 +10,7 @@
 #include <asm/thread_info.h>
 #include <asm/asm-offsets.h>
 #include <xen/interface/arch-x86_32.h>
+#include <xen/interface/elfnote.h>
 
 /*
  * References to members of the new_cpu_data structure.
@@ -138,6 +140,7 @@ ENTRY(cpu_gdt_table)
        .quad 0x0000000000000000        /* 0xf0 - unused */
        .quad 0x0000000000000000        /* 0xf8 - GDT entry 31: double-fault 
TSS */
 
+#ifdef CONFIG_XEN_COMPAT_030002
 /*
  * __xen_guest information
  */
@@ -157,12 +160,8 @@ ENTRY(cpu_gdt_table)
        .ascii  ",XEN_VER=xen-3.0"
        .ascii  ",VIRT_BASE=0x"
                utoa __PAGE_OFFSET
-#ifdef CONFIG_XEN_COMPAT_030002
        .ascii  ",ELF_PADDR_OFFSET=0x"
                utoa __PAGE_OFFSET
-#else
-       .ascii  ",ELF_PADDR_OFFSET=0x0"
-#endif /* !CONFIG_XEN_COMPAT_030002 */
        .ascii  ",VIRT_ENTRY=0x"
                utoa (__PAGE_OFFSET + __PHYSICAL_START + VIRT_ENTRY_OFFSET)
        .ascii  ",HYPERCALL_PAGE=0x"
@@ -179,3 +178,24 @@ ENTRY(cpu_gdt_table)
 #endif
        .ascii  ",LOADER=generic"
        .byte   0
+#endif /* CONFIG_XEN_COMPAT_030002 */
+
+
+       ELFNOTE(Xen, XEN_ELFNOTE_GUEST_OS,       .asciz, "linux")       
+       ELFNOTE(Xen, XEN_ELFNOTE_GUEST_VERSION,  .asciz, "2.6")
+       ELFNOTE(Xen, XEN_ELFNOTE_XEN_VERSION,    .asciz, "xen-3.0")
+       ELFNOTE(Xen, XEN_ELFNOTE_VIRT_BASE,      .long,  __PAGE_OFFSET)
+#ifdef CONFIG_XEN_COMPAT_030002
+       ELFNOTE(Xen, XEN_ELFNOTE_PADDR_OFFSET,   .long,  __PAGE_OFFSET)
+#else
+       ELFNOTE(Xen, XEN_ELFNOTE_PADDR_OFFSET,   .long,  0)
+#endif /* !CONFIG_XEN_COMPAT_030002 */
+       ELFNOTE(Xen, XEN_ELFNOTE_ENTRY,          .long,  startup_32)
+       ELFNOTE(Xen, XEN_ELFNOTE_HYPERCALL_PAGE, .long,  hypercall_page)
+       ELFNOTE(Xen, XEN_ELFNOTE_FEATURES,       .asciz, 
"writable_page_tables|writable_descriptor_tables|auto_translated_physmap|pae_pgdir_above_4gb|supervisor_mode_kernel")
+#ifdef CONFIG_X86_PAE
+       ELFNOTE(Xen, XEN_ELFNOTE_PAE_MODE,       .asciz, "yes")
+#else
+       ELFNOTE(Xen, XEN_ELFNOTE_PAE_MODE,       .asciz, "no")
+#endif
+       ELFNOTE(Xen, XEN_ELFNOTE_LOADER,         .asciz, "generic")
diff -r d57b174adfd6 -r faadbf5ba8d6 
linux-2.6-xen-sparse/arch/x86_64/kernel/head-xen.S
--- a/linux-2.6-xen-sparse/arch/x86_64/kernel/head-xen.S        Wed Aug 23 
14:37:39 2006 +0100
+++ b/linux-2.6-xen-sparse/arch/x86_64/kernel/head-xen.S        Wed Aug 23 
14:41:05 2006 +0100
@@ -16,11 +16,14 @@
 #include <linux/linkage.h>
 #include <linux/threads.h>
 #include <linux/init.h>
+#include <linux/elfnote.h>
 #include <asm/desc.h>
 #include <asm/segment.h>
 #include <asm/page.h>
 #include <asm/msr.h>
 #include <asm/cache.h>
+
+#include <xen/interface/elfnote.h>
 
        .text
        .code64
@@ -131,6 +134,7 @@ gdt_end:
        /* zero the remaining page */
        .fill PAGE_SIZE / 8 - GDT_ENTRIES,8,0
 
+#ifdef CONFIG_XEN_COMPAT_030002
 /*
  * __xen_guest information
  */
@@ -150,12 +154,8 @@ gdt_end:
        .ascii  ",XEN_VER=xen-3.0"
        .ascii  ",VIRT_BASE=0x"
                utoh __START_KERNEL_map
-#ifdef CONFIG_XEN_COMPAT_030002
        .ascii  ",ELF_PADDR_OFFSET=0x"
                utoh __START_KERNEL_map
-#else
-       .ascii  ",ELF_PADDR_OFFSET=0x0"
-#endif /* !CONFIG_XEN_COMPAT_030002 */
        .ascii  ",VIRT_ENTRY=0x"
                utoh (__START_KERNEL_map + __PHYSICAL_START + VIRT_ENTRY_OFFSET)
        .ascii  ",HYPERCALL_PAGE=0x"
@@ -166,3 +166,18 @@ gdt_end:
        .ascii           "|supervisor_mode_kernel"
        .ascii  ",LOADER=generic"
        .byte   0
+#endif /* CONFIG_XEN_COMPAT_030002 */
+       
+       ELFNOTE(Xen, XEN_ELFNOTE_GUEST_OS,       .asciz, "linux")
+       ELFNOTE(Xen, XEN_ELFNOTE_GUEST_VERSION,  .asciz, "2.6")
+       ELFNOTE(Xen, XEN_ELFNOTE_XEN_VERSION,    .asciz, "xen-3.0")
+       ELFNOTE(Xen, XEN_ELFNOTE_VIRT_BASE,      .quad,  __START_KERNEL_map)
+#ifdef CONFIG_XEN_COMPAT_030002
+       ELFNOTE(Xen, XEN_ELFNOTE_PADDR_OFFSET,   .quad,  __START_KERNEL_map)
+#else
+       ELFNOTE(Xen, XEN_ELFNOTE_PADDR_OFFSET,   .quad,  0)
+#endif /* !CONFIG_XEN_COMPAT_030002 */
+       ELFNOTE(Xen, XEN_ELFNOTE_ENTRY,          .quad,  startup_64)
+       ELFNOTE(Xen, XEN_ELFNOTE_HYPERCALL_PAGE, .quad,  hypercall_page)
+       ELFNOTE(Xen, XEN_ELFNOTE_FEATURES,       .asciz, 
"writable_page_tables|writable_descriptor_tables|auto_translated_physmap|pae_pgdir_above_4gb|supervisor_mode_kernel")
+       ELFNOTE(Xen, XEN_ELFNOTE_LOADER,         .asciz, "generic")
diff -r d57b174adfd6 -r faadbf5ba8d6 xen/arch/x86/domain_build.c
--- a/xen/arch/x86/domain_build.c       Wed Aug 23 14:37:39 2006 +0100
+++ b/xen/arch/x86/domain_build.c       Wed Aug 23 14:41:05 2006 +0100
@@ -28,6 +28,7 @@
 #include <asm/shadow.h>
 
 #include <public/version.h>
+#include <public/elfnote.h>
 
 extern unsigned long initial_images_nrpages(void);
 extern void discard_initial_images(void);
@@ -210,8 +211,9 @@ int construct_dom0(struct domain *d,
     struct page_info *page = NULL;
     start_info_t *si;
     struct vcpu *v = d->vcpu[0];
-    char *p;
+    const char *p;
     unsigned long hypercall_page;
+    int hypercall_page_defined;
 #if defined(__i386__)
     char *image_start  = (char *)_image_start;  /* use lowmem mappings */
     char *initrd_start = (char *)_initrd_start; /* use lowmem mappings */
@@ -288,13 +290,14 @@ int construct_dom0(struct domain *d,
     if ( (rc = parseelfimage(&dsi)) != 0 )
         return rc;
 
-    if ( dsi.xen_section_string == NULL )
-    {
-        printk("Not a Xen-ELF image: '__xen_guest' section not found.\n");
+    if ( dsi.__elfnote_section == NULL )
+    {
+        printk("Not a Xen-ELF image: no Xen ELF notes were found.\n");
         return -EINVAL;
     }
 
-    dom0_pae = !!strstr(dsi.xen_section_string, "PAE=yes");
+    p = xen_elfnote_string(&dsi, XEN_ELFNOTE_PAE_MODE);
+    dom0_pae = !!(p != NULL && strcmp(p, "yes") == 0);
     xen_pae  = (CONFIG_PAGING_LEVELS == 3);
     if ( dom0_pae != xen_pae )
     {
@@ -303,15 +306,14 @@ int construct_dom0(struct domain *d,
         return -EINVAL;
     }
 
-    if ( xen_pae && !!strstr(dsi.xen_section_string, "PAE=yes[extended-cr3]") )
+    if ( xen_pae )
         set_bit(VMASST_TYPE_pae_extended_cr3, &d->vm_assist);
 
-    if ( (p = strstr(dsi.xen_section_string, "FEATURES=")) != NULL )
-    {
-        parse_features(
-            p + strlen("FEATURES="),
-            dom0_features_supported,
-            dom0_features_required);
+    if ( (p = xen_elfnote_string(&dsi, XEN_ELFNOTE_FEATURES)) != NULL )
+    {
+        parse_features(p,
+                       dom0_features_supported,
+                       dom0_features_required);
         printk("Domain 0 kernel supports features = { %08x }.\n",
                dom0_features_supported[0]);
         printk("Domain 0 kernel requires features = { %08x }.\n",
@@ -696,20 +698,17 @@ int construct_dom0(struct domain *d,
     /* Copy the OS image and free temporary buffer. */
     (void)loadelfimage(&dsi);
 
-    p = strstr(dsi.xen_section_string, "HYPERCALL_PAGE=");
-    if ( p != NULL )
-    {
-        p += strlen("HYPERCALL_PAGE=");
-        hypercall_page = simple_strtoul(p, NULL, 16);
-        hypercall_page = dsi.v_start + (hypercall_page << PAGE_SHIFT);
+    hypercall_page =
+        xen_elfnote_numeric(&dsi, XEN_ELFNOTE_HYPERCALL_PAGE, 
&hypercall_page_defined);
+    if ( hypercall_page_defined )
+    {
         if ( (hypercall_page < dsi.v_start) || (hypercall_page >= v_end) )
         {
             write_ptbase(current);
             local_irq_enable();
-            printk("Invalid HYPERCALL_PAGE field in guest header.\n");
+            printk("Invalid HYPERCALL_PAGE field in ELF notes.\n");
             return -1;
         }
-
         hypercall_page_initialise(d, (void *)hypercall_page);
     }
 
diff -r d57b174adfd6 -r faadbf5ba8d6 xen/common/elf.c
--- a/xen/common/elf.c  Wed Aug 23 14:37:39 2006 +0100
+++ b/xen/common/elf.c  Wed Aug 23 14:41:05 2006 +0100
@@ -11,12 +11,102 @@
 #include <xen/elf.h>
 #include <xen/sched.h>
 #include <xen/errno.h>
+#include <xen/inttypes.h>
+
+#include <public/elfnote.h>
 
 static void loadelfsymtab(struct domain_setup_info *dsi, int doload);
 static inline int is_loadable_phdr(Elf_Phdr *phdr)
 {
     return ((phdr->p_type == PT_LOAD) &&
             ((phdr->p_flags & (PF_W|PF_X)) != 0));
+}
+
+/*
+ * Interface to the Xen ELF notes.
+ */
+#define ELFNOTE_NAME(_n_)   ((void*)(_n_) + sizeof(*(_n_)))
+#define ELFNOTE_DESC(_n_)   (ELFNOTE_NAME(_n_) + (((_n_)->namesz+3)&~3))
+#define ELFNOTE_NEXT(_n_)   (ELFNOTE_DESC(_n_) + (((_n_)->descsz+3)&~3))
+
+static int is_xen_elfnote_section(const char *image, Elf_Shdr *shdr)
+{
+    Elf_Note *note;
+
+    if ( shdr->sh_type != SHT_NOTE )
+        return 0;
+
+    for ( note = (Elf_Note *)(image + shdr->sh_offset);
+          note < (Elf_Note *)(image + shdr->sh_offset + shdr->sh_size);
+          note = ELFNOTE_NEXT(note) )
+    {
+        if ( !strncmp(ELFNOTE_NAME(note), "Xen", 4) )
+            return 1;
+    }
+
+    return 0;
+}
+
+static Elf_Note *xen_elfnote_lookup(struct domain_setup_info *dsi, int type)
+{
+    Elf_Note *note;
+
+    if ( !dsi->__elfnote_section )
+        return NULL;
+
+    for ( note = (Elf_Note *)dsi->__elfnote_section;
+          note < (Elf_Note *)dsi->__elfnote_section_end;
+          note = ELFNOTE_NEXT(note) )
+    {
+        if ( strncmp(ELFNOTE_NAME(note), "Xen", 4) )
+            continue;
+
+        if ( note->type == type )
+            return note;
+    }
+
+    DPRINTK("unable to find Xen ELF note with type %#x\n", type);
+    return NULL;
+}
+
+const char *xen_elfnote_string(struct domain_setup_info *dsi, int type)
+{
+    Elf_Note *note;
+
+    note = xen_elfnote_lookup(dsi, type);
+    if ( note == NULL )
+        return NULL;
+
+    DPRINTK("found Xen ELF note type %#x = \"%s\"\n",
+            type, (char *)ELFNOTE_DESC(note));
+
+    return (const char *)ELFNOTE_DESC(note);
+}
+
+unsigned long long xen_elfnote_numeric(struct domain_setup_info *dsi,
+                                       int type, int *defined)
+{
+    Elf_Note *note;
+
+    *defined = 0;
+
+    note = xen_elfnote_lookup(dsi, type);
+    if ( note == NULL )
+    {
+        return 0;
+    }
+
+    switch ( note->descsz )
+    {
+    case 4:
+        *defined = 1;
+        return *(uint32_t*)ELFNOTE_DESC(note);
+    case 8:
+        *defined = 1;
+        return *(uint64_t*)ELFNOTE_DESC(note);
+    default:
+        return 0;
+    }
 }
 
 int parseelfimage(struct domain_setup_info *dsi)
@@ -24,21 +114,22 @@ int parseelfimage(struct domain_setup_in
     Elf_Ehdr *ehdr = (Elf_Ehdr *)dsi->image_addr;
     Elf_Phdr *phdr;
     Elf_Shdr *shdr;
-    Elf_Addr kernstart = ~0, kernend = 0, vaddr, virt_base, elf_pa_off;
-    char *shstrtab, *guestinfo=NULL, *p;
-    char *elfbase = (char *)dsi->image_addr;
-    int h, virt_base_defined, elf_pa_off_defined;
+    Elf_Addr kernstart = ~0, kernend = 0, vaddr, virt_entry;
+    const char *shstrtab, *p;
+    const char *image = (char *)dsi->image_addr;
+    const unsigned long image_len = dsi->image_len;
+    int h, virt_base_defined, elf_pa_off_defined, virt_entry_defined;
 
     if ( !elf_sanity_check(ehdr) )
         return -EINVAL;
 
-    if ( (ehdr->e_phoff + (ehdr->e_phnum*ehdr->e_phentsize)) > dsi->image_len )
+    if ( (ehdr->e_phoff + (ehdr->e_phnum*ehdr->e_phentsize)) > image_len )
     {
         printk("ELF program headers extend beyond end of image.\n");
         return -EINVAL;
     }
 
-    if ( (ehdr->e_shoff + (ehdr->e_shnum*ehdr->e_shentsize)) > dsi->image_len )
+    if ( (ehdr->e_shoff + (ehdr->e_shnum*ehdr->e_shentsize)) > image_len )
     {
         printk("ELF section headers extend beyond end of image.\n");
         return -EINVAL;
@@ -50,64 +141,71 @@ int parseelfimage(struct domain_setup_in
         printk("ELF image has no section-header strings table (shstrtab).\n");
         return -EINVAL;
     }
-    shdr = (Elf_Shdr *)(elfbase + ehdr->e_shoff + 
+    shdr = (Elf_Shdr *)(image + ehdr->e_shoff +
                         (ehdr->e_shstrndx*ehdr->e_shentsize));
-    shstrtab = elfbase + shdr->sh_offset;
-    
-    /* Find the special '__xen_guest' section and check its contents. */
+    shstrtab = image + shdr->sh_offset;
+
+    dsi->__elfnote_section = NULL;
+
+    /* Look for .notes segment containing at least one Xen note */
     for ( h = 0; h < ehdr->e_shnum; h++ )
     {
-        shdr = (Elf_Shdr *)(elfbase + ehdr->e_shoff + (h*ehdr->e_shentsize));
-        if ( strcmp(&shstrtab[shdr->sh_name], "__xen_guest") != 0 )
-            continue;
-
-        guestinfo = elfbase + shdr->sh_offset;
-
-        if ( (strstr(guestinfo, "LOADER=generic") == NULL) &&
-             (strstr(guestinfo, "GUEST_OS=linux") == NULL) )
-        {
-            printk("ERROR: Xen will only load images built for the generic "
-                   "loader or Linux images\n");
+        shdr = (Elf_Shdr *)(image + ehdr->e_shoff + (h*ehdr->e_shentsize));
+        if ( !is_xen_elfnote_section(image, shdr) )
+            continue;
+        dsi->__elfnote_section = (void *)image + shdr->sh_offset;
+        dsi->__elfnote_section_end =
+            (void *)image + shdr->sh_offset + shdr->sh_size;
+        break;
+    }
+
+    /* Check the contents of the Xen notes. */
+    if ( dsi->__elfnote_section )
+    {
+        const char *loader = xen_elfnote_string(dsi, XEN_ELFNOTE_LOADER);
+        const char *guest_os = xen_elfnote_string(dsi, XEN_ELFNOTE_GUEST_OS);
+        const char *xen_version =
+            xen_elfnote_string(dsi, XEN_ELFNOTE_XEN_VERSION);
+
+        if ( ( loader == NULL || strcmp(loader, "generic") ) &&
+             ( guest_os == NULL || strcmp(guest_os, "linux") ) )
+        {
+            printk("ERROR: Will only load images built for the generic "
+                   "loader or Linux images");
             return -EINVAL;
         }
 
-        if ( (strstr(guestinfo, "XEN_VER=xen-3.0") == NULL) )
+        if ( xen_version == NULL || strcmp(xen_version, "xen-3.0") )
         {
             printk("ERROR: Xen will only load images built for Xen v3.0\n");
-            return -EINVAL;
-        }
-
-        break;
-    }
-
-    dsi->xen_section_string = guestinfo;
-
-    if ( guestinfo == NULL )
-        guestinfo = "";
-
-    /* Initial guess for virt_base is 0 if it is not explicitly defined. */
-    p = strstr(guestinfo, "VIRT_BASE=");
-    virt_base_defined = (p != NULL);
-    virt_base = virt_base_defined ? simple_strtoul(p+10, &p, 0) : 0;
-
-    /* Initial guess for elf_pa_off is virt_base if not explicitly defined. */
-    p = strstr(guestinfo, "ELF_PADDR_OFFSET=");
-    elf_pa_off_defined = (p != NULL);
-    elf_pa_off = elf_pa_off_defined ? simple_strtoul(p+17, &p, 0) : virt_base;
+        }
+    }
+
+    /* Initial guess for v_start is 0 if it is not explicitly defined. */
+    dsi->v_start =
+        xen_elfnote_numeric(dsi, XEN_ELFNOTE_VIRT_BASE, &virt_base_defined);
+    if ( !virt_base_defined )
+        dsi->v_start = 0;
+
+    /* We are using the ELF notes interface so the default is 0. */
+    dsi->elf_paddr_offset =
+        xen_elfnote_numeric(dsi, XEN_ELFNOTE_PADDR_OFFSET, 
&elf_pa_off_defined);
+    if ( !elf_pa_off_defined )
+        dsi->elf_paddr_offset = 0;
 
     if ( elf_pa_off_defined && !virt_base_defined )
     {
         printk("ERROR: Neither ELF_PADDR_OFFSET nor VIRT_BASE found in"
-               " __xen_guest section.\n");
+               " Xen ELF notes.\n");
         return -EINVAL;
     }
 
     for ( h = 0; h < ehdr->e_phnum; h++ )
     {
-        phdr = (Elf_Phdr *)(elfbase + ehdr->e_phoff + (h*ehdr->e_phentsize));
+        phdr = (Elf_Phdr *)(image + ehdr->e_phoff + (h*ehdr->e_phentsize));
         if ( !is_loadable_phdr(phdr) )
             continue;
-        vaddr = phdr->p_paddr - elf_pa_off + virt_base;
+        vaddr = phdr->p_paddr - dsi->elf_paddr_offset + dsi->v_start;
         if ( (vaddr + phdr->p_memsz) < vaddr )
         {
             printk("ERROR: ELF program header %d is too large.\n", h);
@@ -120,19 +218,13 @@ int parseelfimage(struct domain_setup_in
             kernend = vaddr + phdr->p_memsz;
     }
 
-    /*
-     * Legacy compatibility and images with no __xen_guest section: assume
-     * header addresses are virtual addresses, and that guest memory should be
-     * mapped starting at kernel load address.
-     */
-    dsi->v_start          = virt_base_defined  ? virt_base  : kernstart;
-    dsi->elf_paddr_offset = elf_pa_off_defined ? elf_pa_off : dsi->v_start;
-
     dsi->v_kernentry = ehdr->e_entry;
-    if ( (p = strstr(guestinfo, "VIRT_ENTRY=")) != NULL )
-        dsi->v_kernentry = simple_strtoul(p+11, &p, 0);
-
-    if ( (kernstart > kernend) || 
+    virt_entry =
+        xen_elfnote_numeric(dsi, XEN_ELFNOTE_ENTRY, &virt_entry_defined);
+    if ( virt_entry_defined )
+        dsi->v_kernentry = virt_entry;
+
+    if ( (kernstart > kernend) ||
          (dsi->v_kernentry < kernstart) ||
          (dsi->v_kernentry > kernend) ||
          (dsi->v_start > kernstart) )
@@ -141,8 +233,9 @@ int parseelfimage(struct domain_setup_in
         return -EINVAL;
     }
 
-    if ( (p = strstr(guestinfo, "BSD_SYMTAB")) != NULL )
-            dsi->load_symtab = 1;
+    p = xen_elfnote_string(dsi, XEN_ELFNOTE_BSD_SYMTAB);
+    if ( p != NULL && strcmp(p, "yes") == 0 )
+        dsi->load_symtab = 1;
 
     dsi->v_kernstart = kernstart;
     dsi->v_kernend   = kernend;
@@ -155,7 +248,7 @@ int parseelfimage(struct domain_setup_in
 
 int loadelfimage(struct domain_setup_info *dsi)
 {
-    char *elfbase = (char *)dsi->image_addr;
+    char *image = (char *)dsi->image_addr;
     Elf_Ehdr *ehdr = (Elf_Ehdr *)dsi->image_addr;
     Elf_Phdr *phdr;
     unsigned long vaddr;
@@ -163,12 +256,12 @@ int loadelfimage(struct domain_setup_inf
   
     for ( h = 0; h < ehdr->e_phnum; h++ )
     {
-        phdr = (Elf_Phdr *)(elfbase + ehdr->e_phoff + (h*ehdr->e_phentsize));
+        phdr = (Elf_Phdr *)(image + ehdr->e_phoff + (h*ehdr->e_phentsize));
         if ( !is_loadable_phdr(phdr) )
             continue;
         vaddr = phdr->p_paddr - dsi->elf_paddr_offset + dsi->v_start;
         if ( phdr->p_filesz != 0 )
-            memcpy((char *)vaddr, elfbase + phdr->p_offset, phdr->p_filesz);
+            memcpy((char *)vaddr, image + phdr->p_offset, phdr->p_filesz);
         if ( phdr->p_memsz > phdr->p_filesz )
             memset((char *)vaddr + phdr->p_filesz, 0,
                    phdr->p_memsz - phdr->p_filesz);
@@ -186,7 +279,7 @@ static void loadelfsymtab(struct domain_
     Elf_Ehdr *ehdr = (Elf_Ehdr *)dsi->image_addr, *sym_ehdr;
     Elf_Shdr *shdr;
     unsigned long maxva, symva;
-    char *p, *elfbase = (char *)dsi->image_addr;
+    char *p, *image = (char *)dsi->image_addr;
     int h, i;
 
     if ( !dsi->load_symtab )
@@ -203,12 +296,12 @@ static void loadelfsymtab(struct domain_
     {
         p = (void *)symva;
         shdr = (Elf_Shdr *)(p + sizeof(int) + sizeof(Elf_Ehdr));
-        memcpy(shdr, elfbase + ehdr->e_shoff, ehdr->e_shnum*sizeof(Elf_Shdr));
+        memcpy(shdr, image + ehdr->e_shoff, ehdr->e_shnum*sizeof(Elf_Shdr));
     } 
     else
     {
         p = NULL;
-        shdr = (Elf_Shdr *)(elfbase + ehdr->e_shoff);
+        shdr = (Elf_Shdr *)(image + ehdr->e_shoff);
     }
 
     for ( h = 0; h < ehdr->e_shnum; h++ ) 
@@ -234,7 +327,7 @@ static void loadelfsymtab(struct domain_
              (shdr[h].sh_type == SHT_SYMTAB) )
         {
             if (doload) {
-                memcpy((void *)maxva, elfbase + shdr[h].sh_offset,
+                memcpy((void *)maxva, image + shdr[h].sh_offset,
                        shdr[h].sh_size);
 
                 /* Mangled to be based on ELF header location. */
diff -r d57b174adfd6 -r faadbf5ba8d6 xen/include/xen/elf.h
--- a/xen/include/xen/elf.h     Wed Aug 23 14:37:39 2006 +0100
+++ b/xen/include/xen/elf.h     Wed Aug 23 14:41:05 2006 +0100
@@ -529,6 +529,10 @@ extern int loadelfimage(struct domain_se
 extern int loadelfimage(struct domain_setup_info *);
 extern int parseelfimage(struct domain_setup_info *);
 
+extern unsigned long long xen_elfnote_numeric(struct domain_setup_info *dsi,
+                                             int type, int *defined);
+extern const char *xen_elfnote_string(struct domain_setup_info *dsi, int type);
+
 #ifdef Elf_Ehdr
 extern int elf_sanity_check(Elf_Ehdr *ehdr);
 #endif
diff -r d57b174adfd6 -r faadbf5ba8d6 xen/include/xen/sched.h
--- a/xen/include/xen/sched.h   Wed Aug 23 14:37:39 2006 +0100
+++ b/xen/include/xen/sched.h   Wed Aug 23 14:41:05 2006 +0100
@@ -185,7 +185,7 @@ struct domain_setup_info
     unsigned long symtab_addr;
     unsigned long symtab_len;
     /* Indicate whether it's xen specific image */
-    char *xen_section_string;
+    void *__elfnote_section, *__elfnote_section_end;
 };
 
 extern struct vcpu *idle_vcpu[NR_CPUS];

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog

<Prev in Thread] Current Thread [Next in Thread>
  • [Xen-changelog] [xen-unstable] [XEN/LINUX] Define Xen ELF notes in kernel header and update dom0 builder., Xen patchbot-unstable <=