Tested and it works fine!

Thx Richard!

-of

Richard Henderson schrieb:
> Recent build changes have added a PT_NOTE entry to the kernel's
> ELF header.  A perfectly valid change, but Alpha's aboot loader
> is none too bright about examining these headers.
> 
> The following patch to aboot-1.0_pre20040408.tar.bz2 makes it
> so that only PT_LOAD entries are considered for loading, as well
> as several other changes required to get the damned thing to
> build again.
> 
> 
> r~
> 
> 
> diff -rup aboot-1.0_pre20040408/Makefile aboot-local/Makefile
> --- aboot-1.0_pre20040408/Makefile    2004-04-08 08:19:01.000000000 -0700
> +++ aboot-local/Makefile      2007-08-13 16:08:01.000000000 -0700
> @@ -32,15 +32,15 @@ export
>  #
>  LOADADDR     = 20000000
>  
> -ABOOT_LDFLAGS = -static -N -Taboot.lds
> +ABOOT_LDFLAGS = -static -N -Taboot.lds --relax
>  
>  CC           = gcc
>  TOP          = $(shell pwd)
>  ifeq ($(TESTING),)
> -CPPFLAGS     = $(CFGDEFS) -I$(TOP)/include
> -CFLAGS               = $(CPPFLAGS) -D__KERNEL__ -Os -Wall -fno-builtin 
> -mno-fp-regs -ffixed-8
> +CPPFLAGS     = $(CFGDEFS) -I$(TOP)/include -I$(KSRC)/include
> +CFLAGS               = $(CPPFLAGS) -D__KERNEL__ -Os -Wall -fno-builtin 
> -mno-fp-regs
>  else
> -CPPFLAGS     = -DTESTING $(CFGDEFS) -I$(TOP)/include
> +CPPFLAGS     = -DTESTING $(CFGDEFS) -I$(TOP)/include -I$(KSRC)/include
>  CFLAGS               = $(CPPFLAGS) -O -g3 -Wall -D__KERNEL__ -ffixed-8
>  endif
>  ASFLAGS              = $(CPPFLAGS)
> diff -rup aboot-1.0_pre20040408/aboot.c aboot-local/aboot.c
> --- aboot-1.0_pre20040408/aboot.c     2004-04-08 10:53:57.000000000 -0700
> +++ aboot-local/aboot.c       2007-08-13 15:46:33.000000000 -0700
> @@ -19,14 +19,13 @@
>   * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
>   */
>  
> -#include <linux/elf.h>
>  #include <linux/kernel.h>
>  #include <linux/version.h>
> -
>  #include <asm/console.h>
>  #include <asm/hwrpb.h>
>  #include <asm/system.h>
>  
> +#include <elf.h>
>  #include <alloca.h>
>  #include <errno.h>
>  
> @@ -37,16 +36,6 @@
>  #include "utils.h"
>  #include "string.h"
>  
> -#ifndef elf_check_arch
> -# define aboot_elf_check_arch(e)     1
> -#else
> -# if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0)
> -#  define aboot_elf_check_arch(e)        elf_check_arch(e)
> -# else
> -#  define aboot_elf_check_arch(e)        elf_check_arch(e->e_machine)
> -# endif
> -#endif
> -
>  struct bootfs *      bfs = 0;                /* filesystem to boot from */
>  char *               dest_addr = 0;
>  jmp_buf              jump_buffer;
> @@ -83,77 +72,86 @@ static unsigned long entry_addr = START_
>  long
>  first_block (const char *buf, long blocksize)
>  {
> -     struct elfhdr *elf;
> -     struct elf_phdr *phdrs;
> +     Elf64_Ehdr *elf;
> +     Elf64_Phdr *phdrs;
> +     int i, j;
>  
> -     elf  = (struct elfhdr *) buf;
> +     elf  = (Elf64_Ehdr *) buf;
>       
> -     if (elf->e_ident[0] == 0x7f
> -         && strncmp(elf->e_ident + 1, "ELF", 3) == 0)
> -     {
> -             int i;
> -             /* looks like an ELF binary: */
> -             if (elf->e_type != ET_EXEC) {
> -                     printf("aboot: not an executable ELF file\n");
> -                     return -1;
> -             }
> -             if (!aboot_elf_check_arch(elf)) {
> -                     printf("aboot: ELF executable not for this machine\n");
> -                     return -1;
> -             }
> -             if (elf->e_phoff + elf->e_phnum * sizeof(*phdrs) > (unsigned) 
> blocksize) {
> -                     printf("aboot: "
> -                            "ELF program headers not in first block (%ld)\n",
> -                            (long) elf->e_phoff);
> +     if (elf->e_ident[0] != 0x7f
> +         || elf->e_ident[1] != 'E'
> +         || elf->e_ident[2] != 'L'
> +         || elf->e_ident[3] != 'F') {
> +             /* Fail silently, it might be a compressed file */
> +             return -1;
> +     }
> +     if (elf->e_ident[EI_CLASS] != ELFCLASS64
> +         || elf->e_ident[EI_DATA] != ELFDATA2LSB
> +         || elf->e_machine != EM_ALPHA) {
> +             printf("aboot: ELF executable not for this machine\n");
> +             return -1;
> +     }
> +
> +     /* Looks like an ELF binary. */
> +     if (elf->e_type != ET_EXEC) {
> +             printf("aboot: not an executable ELF file\n");
> +             return -1;
> +     }
> +
> +     if (elf->e_phoff + elf->e_phnum * sizeof(*phdrs)
> +         > (unsigned) blocksize) {
> +             printf("aboot: ELF program headers not in first block (%ld)\n",
> +                    (long) elf->e_phoff);
> +             return -1;
> +     }
> +
> +     phdrs = (struct elf_phdr *) (buf + elf->e_phoff);
> +     chunks = malloc(sizeof(struct segment) * elf->e_phnum);
> +     start_addr = phdrs[0].p_vaddr; /* assume they are sorted */
> +     entry_addr = elf->e_entry;
> +
> +     for (i = j = 0; i < elf->e_phnum; ++i) {
> +             int status;
> +
> +             if (phdrs[i].p_type != PT_LOAD)
> +                     continue;
> +
> +             chunks[j].addr   = phdrs[i].p_vaddr;
> +             chunks[j].offset = phdrs[i].p_offset;
> +             chunks[j].size   = phdrs[i].p_filesz;
> +             printf("aboot: PHDR %d vaddr %#lx offset %#lx size %#lx\n",
> +                    i, chunks[j].addr, chunks[j].offset, chunks[j].size);
> +
> +             status = check_memory(chunks[j].addr, chunks[j].size);
> +             if (status) {
> +                     printf("aboot: Can't load kernel.\n"
> +                            "  Memory at %lx - %lx (PHDR %i) "
> +                              "is %s\n",
> +                            chunks[j].addr,
> +                            chunks[j].addr + chunks[j].size - 1,
> +                            i,
> +                            (status == -ENOMEM) ?
> +                               "Not Found" :
> +                               "Busy (Reserved)");
>                       return -1;
>               }
> -             phdrs = (struct elf_phdr *) (buf + elf->e_phoff);
> -             chunks = malloc(sizeof(struct segment) * elf->e_phnum);
> -             nchunks = elf->e_phnum;
> -             start_addr = phdrs[0].p_vaddr; /* assume they are sorted */
> -             entry_addr = elf->e_entry;
> -#ifdef DEBUG
> -             printf("aboot: %d program headers, start address %#lx, entry 
> %#lx\n",
> -                    nchunks, start_addr, entry_addr);
> -#endif
> -             for (i = 0; i < elf->e_phnum; ++i) {
> -                     int status;
> -
> -                     chunks[i].addr   = phdrs[i].p_vaddr;
> -                     chunks[i].offset = phdrs[i].p_offset;
> -                     chunks[i].size   = phdrs[i].p_filesz;
> -#ifdef DEBUG
> -                     printf("aboot: segment %d vaddr %#lx offset %#lx size 
> %#lx\n",
> -                            i, chunks[i].addr, chunks[i].offset, 
> chunks[i].size);
> -#endif
> -
> -#ifndef TESTING
> -                     status = check_memory(chunks[i].addr, chunks[i].size);
> -                     if (status) {
> +
> +             if (phdrs[i].p_memsz > phdrs[i].p_filesz) {
> +                     if (bss_size > 0) {
>                               printf("aboot: Can't load kernel.\n"
> -                                    "  Memory at %lx - %lx (chunk %i) "
> -                                      "is %s\n",
> -                                    chunks[i].addr,
> -                                    chunks[i].addr + chunks[i].size - 1,
> -                                    i,
> -                                    (status == -ENOMEM) ?
> -                                       "Not Found" :
> -                                       "Busy (Reserved)");
> +                                    "  Multiple BSS segments"
> +                                    " (PHDR %d)\n", i);
>                               return -1;
>                       }
> -#endif
> +                     bss_start = (char *) (phdrs[i].p_vaddr +
> +                                           phdrs[i].p_filesz);
> +                     bss_size = phdrs[i].p_memsz - phdrs[i].p_filesz;
>               }
> -             bss_start = (char *) (phdrs[elf->e_phnum - 1].p_vaddr +
> -                                   phdrs[elf->e_phnum - 1].p_filesz);
> -             bss_size = (phdrs[elf->e_phnum - 1].p_memsz -
> -                         phdrs[elf->e_phnum - 1].p_filesz);
> -#ifdef DEBUG
> -             printf("aboot: bss at 0x%p, size %#lx\n", bss_start, bss_size);
> -#endif
> -     } else {
> -             /* Fail silently, it might be a compressed file */
> -             return -1;
> +
> +             j++;
>       }
> +     nchunks = j;
> +     printf("aboot: bss at 0x%p, size %#lx\n", bss_start, bss_size);
>  
>       return 0;
>  }
> diff -rup aboot-1.0_pre20040408/aboot.lds aboot-local/aboot.lds
> --- aboot-1.0_pre20040408/aboot.lds   2001-10-08 16:03:50.000000000 -0700
> +++ aboot-local/aboot.lds     2007-08-13 15:59:46.000000000 -0700
> @@ -1,22 +1,25 @@
>  OUTPUT_FORMAT("elf64-alpha")
>  ENTRY(__start)
> +PHDRS { kernel PT_LOAD; }
>  SECTIONS
>  {
>    . = 0x20000000;
> -  .text : { *(.text) }
> +  .text : { *(.text) } :kernel
>    _etext = .;
>    PROVIDE (etext = .);
> -  .rodata : { *(.rodata) }
> -  .data : { *(.data) CONSTRUCTORS }
> -  .got : { *(.got) }
> -  .sdata : { *(.sdata) }
> +  .rodata : { *(.rodata*) } :kernel
> +  .data : { *(.data*) } :kernel
> +  .got : { *(.got) } :kernel
> +  .sdata : { *(.sdata) } :kernel
>    _edata = .;
>    PROVIDE (edata = .);
> -  .sbss : { *(.sbss) *(.scommon) }
> -  .bss : { *(.bss) *(COMMON) }
> +  .sbss : { *(.sbss) *(.scommon) } :kernel
> +  .bss : { *(.bss) *(COMMON) } :kernel
>    _end = . ;
>    PROVIDE (end = .);
>  
> +  /DISCARD/ : { *(.eh_frame) } 
> +
>    .mdebug 0 : { *(.mdebug) }
>    .note 0 : { *(.note) }
>    .comment 0 : { *(.comment) }
> diff -rup aboot-1.0_pre20040408/cons.c aboot-local/cons.c
> --- aboot-1.0_pre20040408/cons.c      2003-11-30 19:56:34.000000000 -0800
> +++ aboot-local/cons.c        2007-08-13 15:48:45.000000000 -0700
> @@ -1,5 +1,3 @@
> -#include <alloca.h>
> -
>  #include <linux/kernel.h>
>  
>  #include <asm/console.h>
> @@ -20,7 +18,7 @@
>  #endif
>  
>  long cons_dev;                       /* console device */
> -extern long int dispatch();  /* Need the full 64 bit return here...*/
> +extern long int dispatch(long, ...); /* Need the full 64 bit return here...*/
>  
>  long
>  cons_puts(const char *str, long len)
> @@ -82,7 +80,7 @@ cons_getenv(long index, char *envval, lo
>        * allocated on the stack (which guaranteed to by 8 byte
>        * aligned).
>        */
> -     char * tmp = alloca(maxlen);
> +     char tmp[maxlen];
>       long len;
>  
>       len = dispatch(CCB_GET_ENV, index, tmp, maxlen - 1);
> diff -rup aboot-1.0_pre20040408/disk.c aboot-local/disk.c
> --- aboot-1.0_pre20040408/disk.c      2004-04-08 11:14:06.000000000 -0700
> +++ aboot-local/disk.c        2007-08-13 15:50:22.000000000 -0700
> @@ -113,7 +113,7 @@ int
>  load_uncompressed (int fd)
>  {
>       long nread, nblocks;
> -     unsigned char *buf;
> +     char *buf;
>       int i;
>  
>       buf = malloc(bfs->blocksize);
> @@ -131,7 +131,7 @@ load_uncompressed (int fd)
>       
>               for(i = 0; i < 16; i++) {
>                       for (j = 0; j < 16; j++)
> -                             printf("%02X ", buf[j+16*i]);
> +                             printf("%02X ", (unsigned char) buf[j+16*i]);
>                       for(j = 0; j < 16; j++) {
>                               c = buf[j+16*i];
>                               printf("%c", (c >= ' ') ? c : ' ');
> diff -rup aboot-1.0_pre20040408/head.S aboot-local/head.S
> --- aboot-1.0_pre20040408/head.S      2001-10-08 16:03:51.000000000 -0700
> +++ aboot-local/head.S        2007-08-13 16:03:57.000000000 -0700
> @@ -19,8 +19,7 @@ __start:
>       .quad   0,0,0,0,0,0,0,0
>  1:   br      $27,2f
>  2:   ldgp    $29,0($27)
> -     lda     $27,main_
> -     jsr     $26,($27),main_
> +     bsr     $26,main_       !samegp
>       call_pal PAL_halt
>       .end __start
>  
> @@ -170,4 +169,4 @@ run_kernel:
>       mov     $16,$27
>       mov     $17,$30
>       jmp     $31,($27)
> -     .end run_kernel
> \ No newline at end of file
> +     .end run_kernel
> 
> _______________________________________________
> axp-list mailing list
> [EMAIL PROTECTED]
> https://www.redhat.com/mailman/listinfo/axp-list

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to [EMAIL PROTECTED]
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to