summaryrefslogtreecommitdiffstats
path: root/sys/boot/ia64/efi
diff options
context:
space:
mode:
authordfr <dfr@FreeBSD.org>2001-06-09 16:49:51 +0000
committerdfr <dfr@FreeBSD.org>2001-06-09 16:49:51 +0000
commit5398454adddabb365388617e5532a93e0790429c (patch)
tree0363e9594830da1c3f4c6b69d6fa954589ec10ab /sys/boot/ia64/efi
parent640330f7ff48a9ef43f959b570d9ad6fe5bd9fec (diff)
downloadFreeBSD-src-5398454adddabb365388617e5532a93e0790429c.zip
FreeBSD-src-5398454adddabb365388617e5532a93e0790429c.tar.gz
First approximation of an ia64 EFI loader. Not functional.
Diffstat (limited to 'sys/boot/ia64/efi')
-rw-r--r--sys/boot/ia64/efi/Makefile102
-rw-r--r--sys/boot/ia64/efi/conf.c88
-rw-r--r--sys/boot/ia64/efi/ldscript.ia6474
-rw-r--r--sys/boot/ia64/efi/main.c134
-rw-r--r--sys/boot/ia64/efi/start.S343
-rw-r--r--sys/boot/ia64/efi/version7
6 files changed, 748 insertions, 0 deletions
diff --git a/sys/boot/ia64/efi/Makefile b/sys/boot/ia64/efi/Makefile
new file mode 100644
index 0000000..4fb3f0e
--- /dev/null
+++ b/sys/boot/ia64/efi/Makefile
@@ -0,0 +1,102 @@
+# $FreeBSD$
+
+BASE= loader
+PROG= ${BASE}.efi
+NOMAN=
+NEWVERSWHAT= "EFI boot" ${MACHINE_ARCH}
+
+.PATH: ${.CURDIR}/../common
+
+SRCS+= main.c conf.c
+
+# Enable BootForth
+#BOOT_FORTH= yes
+CFLAGS+= -I${.CURDIR}/../../ficl -I${.CURDIR}/../../ficl/alpha
+.if BOOT_FORTH
+CFLAGS+= -DBOOT_FORTH
+.if exists(${.OBJDIR}/../../ficl/libficl.a)
+LIBFICL= ${.OBJDIR}/../../ficl/libficl.a
+.else
+LIBFICL= ${.CURDIR}/../../ficl/libficl.a
+.endif
+.else
+LIBFICL=
+.endif
+
+# Always add MI sources
+.PATH: ${.CURDIR}/../../common
+.include <${.CURDIR}/../../common/Makefile.inc>
+CFLAGS+= -I-
+CFLAGS+= -I${.CURDIR}/../include
+CFLAGS+= -I${.CURDIR}/../include/${MACHINE_ARCH}
+CFLAGS+= -I${.CURDIR}/../../common -I${.CURDIR}
+CFLAGS+= -I${.CURDIR}/../../.. -I.
+CFLAGS+= -I${.CURDIR}/../libefi
+CFLAGS+= -DLOADER
+CFLAGS+= -Wall
+
+LDSCRIPT= ${.CURDIR}/../libefi/arch/${MACHINE_ARCH}/ldscript.${MACHINE_ARCH}
+LDFLAGS= -nostdlib -T ${LDSCRIPT} -shared -Bsymbolic
+
+CLEANFILES+= setdef0.c setdef0.o setdef1.c setdef1.o setdefs.h start.o \
+ vers.c vers.o ${BASE}.efi ${BASE}.sym ${BASE}.list
+CLEANFILES+= loader.help
+CLEANFILES+= machine
+
+CRT= start.o
+
+all: ${PROG}
+
+vers.o: ${.CURDIR}/../../common/newvers.sh ${.CURDIR}/version
+ sh ${.CURDIR}/../../common/newvers.sh ${.CURDIR}/version ${NEWVERSWHAT}
+ ${CC} -c vers.c
+
+${BASE}.efi: ${BASE}.sym
+ ${OBJCOPY} -j .text \
+ -j .hash \
+ -j .data \
+ -j .sdata \
+ -j .dynamic \
+ -j .rela \
+ -j .reloc \
+ -j .dynsym \
+ --target=efi-app-${MACHINE_ARCH} \
+ ${BASE}.sym ${BASE}.efi
+
+${BASE}.sym: ${OBJS} ${LIBSTAND} ${LIBARC} ${CRT} vers.o setdef0.o setdef1.o
+ ${LD} ${LDFLAGS} -o ${BASE}.sym -M \
+ ${CRT} setdef0.o ${OBJS} setdef1.o vers.o \
+ ${LIBFICL} ${LIBSTAND} ${LIBEFI} ${LIBSTAND} \
+ > ${.OBJDIR}/${BASE}.list
+
+${BASE}.help: help.common help.efi
+ cat ${.ALLSRC} | awk -f ${.CURDIR}/../../common/merge_help.awk > ${.TARGET}
+
+beforeinstall:
+.if exists(${.OBJDIR}/loader.help)
+ ${INSTALL} -C -o ${BINOWN} -g ${BINGRP} -m 444 \
+ ${.OBJDIR}/${BASE}.help ${DESTDIR}/boot
+.else
+ ${INSTALL} -C -o ${BINOWN} -g ${BINGRP} -m 444 \
+ ${.CURDIR}/${BASE}.help ${DESTDIR}/boot
+.endif
+
+# Other fragments still to be brought in from ../Makfile.booters?
+start.o: ${.CURDIR}/../libefi/arch/${MACHINE_ARCH}/start.S
+ ${CC} -c ${CFLAGS} $<
+
+setdef0.o: setdefs.h
+
+setdef1.o: setdefs.h
+
+machine:
+ ln -sf ${.CURDIR}/../../../${MACHINE_ARCH}/include machine
+
+.include <bsd.prog.mk>
+
+.ORDER: setdefs.h setdef0.c setdef1.c
+setdefs.h setdef0.c setdef1.c: ${OBJS}
+ @echo Generating linker sets
+ @perl ${.CURDIR}/../../../kern/gensetdefs.pl ${OBJS}
+
+beforedepend ${OBJS}: machine
diff --git a/sys/boot/ia64/efi/conf.c b/sys/boot/ia64/efi/conf.c
new file mode 100644
index 0000000..49bfcc3
--- /dev/null
+++ b/sys/boot/ia64/efi/conf.c
@@ -0,0 +1,88 @@
+/*
+ * $FreeBSD$
+ * From $NetBSD: conf.c,v 1.2 1997/03/22 09:03:29 thorpej Exp $
+ */
+
+/*
+ * Copyright (c) 1997
+ * Matthias Drochner. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed for the NetBSD Project
+ * by Matthias Drochner.
+ * 4. The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+
+#include <stand.h>
+#include <efi.h>
+#include <efilib.h>
+
+#include "efiboot.h"
+
+/*
+ * We could use linker sets for some or all of these, but
+ * then we would have to control what ended up linked into
+ * the bootstrap. So it's easier to conditionalise things
+ * here.
+ *
+ * XXX rename these arrays to be consistent and less namespace-hostile
+ */
+
+/* Exported for libstand */
+struct devsw *devsw[] = {
+/* &efi_disk, */
+ NULL
+};
+
+struct fs_ops *file_system[] = {
+ &ufs_fsops,
+ &zipfs_fsops,
+ NULL
+};
+
+/* Exported for ia64 only */
+/*
+ * Sort formats so that those that can detect based on arguments
+ * rather than reading the file go first.
+ */
+extern struct file_format ia64_elf;
+
+struct file_format *file_formats[] = {
+/* &ia64_elf, */
+ NULL
+};
+
+/*
+ * Consoles
+ *
+ * We don't prototype these in libalpha.h because they require
+ * data structures from bootstrap.h as well.
+ */
+extern struct console efi_console;
+
+struct console *consoles[] = {
+ &efi_console,
+ NULL
+};
diff --git a/sys/boot/ia64/efi/ldscript.ia64 b/sys/boot/ia64/efi/ldscript.ia64
new file mode 100644
index 0000000..13d5971
--- /dev/null
+++ b/sys/boot/ia64/efi/ldscript.ia64
@@ -0,0 +1,74 @@
+/* $FreeBSD$ */
+OUTPUT_FORMAT("elf64-ia64-little", "elf64-ia64-little", "elf64-ia64-little")
+OUTPUT_ARCH(ia64)
+ENTRY(_start_plabel)
+SECTIONS
+{
+ /* Read-only sections, merged into text segment: */
+ . = 0;
+ ImageBase = .;
+ .text :
+ {
+ *(.text)
+ *(.stub)
+ /* .gnu.warning sections are handled specially by elf32.em. */
+ *(.gnu.warning)
+ *(.gnu.linkonce.t*)
+ }
+ . = ALIGN(4096);
+ .hash : { *(.hash) }
+ . = ALIGN(4096);
+ .data :
+ {
+ *(.rodata)
+ *(.rodata1)
+ *(.set.*)
+ *(.ctors)
+ *(.data)
+ *(.data1)
+ *(.gnu.linkonce.d*)
+ *(.plabel)
+ *(.IA_64.unwind)
+ *(.IA_64.unwind_info)
+ *(.bss)
+ *(.dynbss)
+ *(COMMON)
+ }
+ . = ALIGN(4096);
+ __gp = ALIGN(8) + 0x200000;
+ .sdata :
+ {
+ *(.got.plt)
+ *(.got)
+ *(.sdata)
+ *(.sbss)
+ *(.scommon)
+ }
+ . = ALIGN(4096);
+ .dynamic : { *(.dynamic) }
+ . = ALIGN(4096);
+ .rela :
+ {
+ *(.rela.text)
+ *(.rela.gnu.linkonce.t*)
+ *(.rela.set.*)
+ *(.rela.sdata)
+ *(.rela.data)
+ *(.rela.gnu.linkonce.d*)
+ *(.rela.got)
+ *(.rela.stab)
+ *(.rela.ctors)
+ }
+ . = ALIGN(4096);
+ .reloc : { *(.reloc) }
+ . = ALIGN(4096);
+ .dynsym : { *(.dynsym) }
+ . = ALIGN(4096);
+ .dynstr : { *(.dynstr) }
+ .ignored :
+ {
+ *(.rela.plabel)
+ *(.rela.reloc)
+ }
+}
+
diff --git a/sys/boot/ia64/efi/main.c b/sys/boot/ia64/efi/main.c
new file mode 100644
index 0000000..1caa84a
--- /dev/null
+++ b/sys/boot/ia64/efi/main.c
@@ -0,0 +1,134 @@
+/*-
+ * Copyright (c) 1998 Michael Smith <msmith@freebsd.org>
+ * Copyright (c) 1998,2000 Doug Rabson <dfr@freebsd.org>
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+#include <stand.h>
+#include <string.h>
+#include <setjmp.h>
+
+#include <efi.h>
+#include <efilib.h>
+
+#include "bootstrap.h"
+#include "efiboot.h"
+
+extern char bootprog_name[];
+extern char bootprog_rev[];
+extern char bootprog_date[];
+extern char bootprog_maker[];
+
+struct efi_devdesc currdev; /* our current device */
+struct arch_switch archsw; /* MI/MD interface boundary */
+
+EFI_STATUS
+efi_main (EFI_HANDLE image_handle, EFI_SYSTEM_TABLE *system_table)
+{
+ int i;
+ EFI_PHYSICAL_ADDRESS mem;
+
+ efi_init(image_handle, system_table);
+
+ /*
+ * Initialise the heap as early as possible. Once this is done,
+ * alloc() is usable. The stack is buried inside us, so this is
+ * safe.
+ */
+ BS->AllocatePages(AllocateAnyPages, EfiLoaderData,
+ 512*1024/4096, &mem);
+ setheap((void *)mem, (void *)(mem + 512*1024));
+
+ /*
+ * XXX Chicken-and-egg problem; we want to have console output
+ * early, but some console attributes may depend on reading from
+ * eg. the boot device, which we can't do yet. We can use
+ * printf() etc. once this is done.
+ */
+ cons_probe();
+
+ /*
+ * Initialise the block cache
+ */
+ bcache_init(32, 512); /* 16k XXX tune this */
+
+ /*
+ * March through the device switch probing for things.
+ */
+ for (i = 0; devsw[i] != NULL; i++)
+ if (devsw[i]->dv_init != NULL)
+ (devsw[i]->dv_init)();
+
+ printf("\n");
+ printf("%s, Revision %s\n", bootprog_name, bootprog_rev);
+ printf("(%s, %s)\n", bootprog_maker, bootprog_date);
+#if 0
+ printf("Memory: %ld k\n", memsize() / 1024);
+#endif
+
+ /* We're booting from an SRM disk, try to spiff this */
+ /* XXX presumes that biosdisk is first in devsw */
+ currdev.d_dev = devsw[0];
+ currdev.d_type = currdev.d_dev->dv_type;
+ currdev.d_kind.efidisk.unit = 0;
+ /* XXX should be able to detect this, default to autoprobe */
+ currdev.d_kind.efidisk.slice = -1;
+ /* default to 'a' */
+ currdev.d_kind.efidisk.partition = 0;
+
+#if 0
+ /* Create arc-specific variables */
+ bootfile = GetEnvironmentVariable(ARCENV_BOOTFILE);
+ if (bootfile)
+ setenv("bootfile", bootfile, 1);
+
+ env_setenv("currdev", EV_VOLATILE,
+ arc_fmtdev(&currdev), arc_setcurrdev, env_nounset);
+ env_setenv("loaddev", EV_VOLATILE,
+ arc_fmtdev(&currdev), env_noset, env_nounset);
+#endif
+
+ setenv("LINES", "24", 1); /* optional */
+
+ archsw.arch_autoload = efi_autoload;
+ archsw.arch_getdev = efi_getdev;
+ archsw.arch_copyin = efi_copyin;
+ archsw.arch_copyout = efi_copyout;
+ archsw.arch_readin = efi_readin;
+
+ interact(); /* doesn't return */
+
+ return EFI_SUCCESS; /* keep compiler happy */
+}
+
+COMMAND_SET(quit, "quit", "exit the loader", command_quit);
+
+static int
+command_quit(int argc, char *argv[])
+{
+ exit(0);
+ return(CMD_OK);
+}
diff --git a/sys/boot/ia64/efi/start.S b/sys/boot/ia64/efi/start.S
new file mode 100644
index 0000000..4bb41e2
--- /dev/null
+++ b/sys/boot/ia64/efi/start.S
@@ -0,0 +1,343 @@
+/*-
+ * Copyright (c) 2001 Doug Rabson
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * $FreeBSD$
+ */
+
+ .text
+
+#include <sys/cdefs.h>
+#include <machine/asm.h>
+
+#define EFI_SUCCESS 0
+#define EFI_LOAD_ERROR 1
+#define EFI_BUFFER_TOO_SMALL 5
+
+#define DT_NULL 0 /* Terminating entry. */
+#define DT_NEEDED 1 /* String table offset of a needed shared
+ library. */
+#define DT_PLTRELSZ 2 /* Total size in bytes of PLT relocations. */
+#define DT_PLTGOT 3 /* Processor-dependent address. */
+#define DT_HASH 4 /* Address of symbol hash table. */
+#define DT_STRTAB 5 /* Address of string table. */
+#define DT_SYMTAB 6 /* Address of symbol table. */
+#define DT_RELA 7 /* Address of ElfNN_Rela relocations. */
+#define DT_RELASZ 8 /* Total size of ElfNN_Rela relocations. */
+#define DT_RELAENT 9 /* Size of each ElfNN_Rela relocation entry. */
+#define DT_STRSZ 10 /* Size of string table. */
+#define DT_SYMENT 11 /* Size of each symbol table entry. */
+#define DT_INIT 12 /* Address of initialization function. */
+#define DT_FINI 13 /* Address of finalization function. */
+#define DT_SONAME 14 /* String table offset of shared object
+ name. */
+#define DT_RPATH 15 /* String table offset of library path. */
+#define DT_SYMBOLIC 16 /* Indicates "symbolic" linking. */
+#define DT_REL 17 /* Address of ElfNN_Rel relocations. */
+#define DT_RELSZ 18 /* Total size of ElfNN_Rel relocations. */
+#define DT_RELENT 19 /* Size of each ElfNN_Rel relocation. */
+#define DT_PLTREL 20 /* Type of relocation used for PLT. */
+#define DT_DEBUG 21 /* Reserved (not used). */
+#define DT_TEXTREL 22 /* Indicates there may be relocations in
+ non-writable segments. */
+#define DT_JMPREL 23 /* Address of PLT relocations. */
+
+#define DT_COUNT 24 /* Number of defined d_tag values. */
+
+#define R_IA64_NONE 0 /* None */
+#define R_IA64_DIR64MSB 0x26 /* word64 MSB S + A */
+#define R_IA64_DIR64LSB 0x27 /* word64 LSB S + A */
+#define R_IA64_FPTR64MSB 0x46 /* word64 MSB @fptr(S + A) */
+#define R_IA64_FPTR64LSB 0x47 /* word64 LSB @fptr(S + A) */
+#define R_IA64_REL64MSB 0x6e /* word64 MSB BD + A */
+#define R_IA64_REL64LSB 0x6f /* word64 LSB BD + A */
+
+ENTRY(_start, 2)
+ alloc loc0=ar.pfs,2,3,3,0
+ mov loc1=rp
+ movl loc2=@gprel(ImageBase)
+ ;;
+ br.sptk.few 9f
+ add loc2=gp,loc2
+ ;;
+ mov out0=loc2
+ mov out1=in1
+ ;;
+ br.call.sptk.few rp=_reloc // relocate image
+
+ cmp.ne p6,p0=EFI_SUCCESS,r8 // did it work?
+(p6) br.cond.dpnt.few 9f
+
+ mov out0=in0 // image_handle
+ mov out1=in1 // system_table
+ br.call.sptk.few rp=efi_main
+9:
+ mov ar.pfs=loc0
+ mov rp=loc1
+ ;;
+ br.ret.sptk.few rp
+END(_start)
+
+ // PLABEL for PE32+
+ .global _start_plabel
+ .section .plabel, "a"
+ .align 16
+_start_plabel:
+ .quad _start
+ .quad __gp
+ .previous
+
+ // A PE32+ relocation entry for the plabel
+
+ .section .reloc, "a"
+ .long _start_plabel
+ .long 12
+ .short (10 << 12) + 0
+ .short (10 << 12) + 8
+ .previous
+
+ // in0: image base
+ // in1: system table
+STATIC_ENTRY(_reloc, 2)
+ alloc loc0=ar.pfs,2,2,2,0
+ mov loc1=rp
+ ;;
+ movl r15=@gprel(_DYNAMIC) // find _DYNAMIC etc.
+ movl r2=@gprel(fptr_storage)
+ movl r3=@gprel(fptr_storage_end)
+ ;;
+ add r15=r15,gp // relocate _DYNAMIC etc.
+ add r2=r2,gp
+ add r3=r3,gp
+ ;;
+1: ld8 r16=[r15],8 // read r15->d_tag
+ ;;
+ ld8 r17=[r15],8 // and r15->d_val
+ ;;
+ cmp.eq p6,p0=DT_NULL,r16 // done?
+(p6) br.cond.dpnt.few 2f
+ ;;
+ cmp.eq p6,p0=DT_RELA,r16
+ ;;
+(p6) add r18=r17,in0 // found rela section
+ ;;
+ cmp.eq p6,p0=DT_RELASZ,r16
+ ;;
+(p6) mov r19=r17 // found rela size
+ ;;
+ cmp.eq p6,p0=DT_SYMTAB,r16
+ ;;
+(p6) add r20=r17,in0 // found symbol table
+ ;;
+(p6) setf.sig f8=r20
+ ;;
+ cmp.eq p6,p0=DT_SYMENT,r16
+ ;;
+(p6) setf.sig f9=r17 // found symbol entry size
+ ;;
+ cmp.eq p6,p0=DT_RELAENT,r16
+ ;;
+(p6) mov r22=r17 // found rela entry size
+ ;;
+ br.sptk.few 1b
+
+2:
+ ld8 r15=[r18],8 // read r_offset
+ ;;
+ ld8 r16=[r18],8 // read r_info
+ add r15=r15,in0 // relocate r_offset
+ ;;
+ ld8 r17=[r18],8 // read r_addend
+ sub r19=r19,r22 // update relasz
+
+ extr.u r23=r16,0,32 // ELF64_R_TYPE(r16)
+ ;;
+ cmp.eq p6,p0=R_IA64_NONE,r23
+(p6) br.cond.dpnt.few 3f
+ ;;
+ cmp.eq p6,p0=R_IA64_DIR64LSB,r23
+ ;;
+(p6) br.cond.dptk.few 4f
+ ;;
+ cmp.eq p6,p0=R_IA64_FPTR64LSB,r23
+ ;;
+(p6) br.cond.dptk.few 5f
+ ;;
+ cmp.eq p6,p0=R_IA64_REL64LSB,r23
+ ;;
+(p6) br.cond.dptk.few 4f
+ ;;
+
+3: cmp.ltu p6,p0=0,r19 // more?
+(p6) br.cond.dptk.few 2b // loop
+
+ mov r8=EFI_SUCCESS // success return value
+ ;;
+ br.cond.sptk.few 9f // done
+
+4:
+ ld8 r16=[r15] // read value
+ ;;
+ add r16=r16,in0 // relocate it
+ ;;
+ st8 [r15]=r16 // and store it back
+ br.cond.sptk.few 3b
+
+5:
+ extr.u r23=r16,32,32 // ELF64_R_SYM(r16)
+ ;;
+ setf.sig f10=r23 // so we can multiply
+ ;;
+ xma.lu f10=f10,f9,f8 // f10=symtab + r_sym*syment
+ ;;
+ getf.sig r16=f10
+ mov r8=EFI_BUFFER_TOO_SMALL // failure return value
+ ;;
+ cmp.geu p6,p0=r2,r3 // space left?
+(p6) br.cond.dpnt.few 9f // bail out
+
+ st8 [r15]=r2 // install fptr
+ add r16=8,r16 // address of st_value
+ ;;
+ ld8 r16=[r16] // read symbol value
+ ;;
+ add r16=r16,in0 // relocate symbol value
+ ;;
+ st8 [r2]=r16,8 // write fptr address
+ ;;
+ st8 [r2]=gp,8 // write fptr gp
+ br.cond.sptk.few 3b
+
+9:
+ mov ar.pfs=loc0
+ mov rp=loc1
+ ;;
+ br.ret.sptk.few rp
+
+END(_reloc)
+
+ // in0: system table
+ // in1: character
+ENTRY(_putchar, 2)
+ alloc loc0=ar.pfs,2,3,2,0
+ mov loc1=rp
+ mov loc2=gp
+ add sp=-32,sp
+ ;;
+ add r14=64,in0 // r14 = &in1->ConOut
+ ;;
+ ld8 r14=[r14] // r14 = in1->ConOut
+ ;;
+ add r15=8,r14 // r15 = &r14->OutputString
+ mov out0=r14
+ mov out1=sp
+ mov r16=sp
+ ;;
+ ld8 r15=[r15] // r15 = r14->OutputString
+ st2 [r16]=in1,2 // write character
+ ;;
+ st2 [r16]=r0 // terminate
+ ld8 r17=[r15],8 // function address
+ ;;
+ ld8 gp=[r15] // function gp
+ mov b6=r17 // transfer to branch register
+ ;;
+ br.call.sptk.few rp=b6 // call function
+ ;;
+ mov gp=loc2 // restore gp
+ mov ar.pfs=loc0
+ mov rp=loc1
+ add sp=32,sp
+ ;;
+ br.ret.sptk.few rp
+
+END(_putchar)
+
+ // in0: system table
+ // in1: string
+ENTRY(_puts, 2)
+ alloc loc0=ar.pfs,3,2,2,0
+ mov loc1=rp
+ ;;
+ mov out0=in0
+ ;;
+1: ld1 out1=[in1],1
+ ;;
+ cmp.eq p6,p0=r0,out1
+(p6) br.cond.dpnt.few 9f
+ ;;
+ br.call.sptk.few rp=_putchar
+ ;;
+ br.cond.sptk.few 1b
+9:
+ mov ar.pfs=loc0
+ mov rp=loc1
+ ;;
+ br.ret.sptk.few rp
+END(_puts)
+
+ // in0: system table
+ // in1: number
+ENTRY(_puthex, 2)
+ alloc loc0=ar.pfs,2,3,2,0
+ mov loc1=rp
+ mov loc2=ar.lc
+ ;;
+ mov out0=in0
+ mov ar.lc=15
+ ;;
+1: extr.u out1=in1,60,4
+ ;;
+ cmp.leu p6,p7=10,out1
+ ;;
+(p6) add out1='a'-10,out1
+(p7) add out1='0',out1
+ dep.z in1=in1,4,60
+ ;;
+ br.call.sptk.few rp=_putchar
+ ;;
+ br.cloop.sptk.few 1b
+ ;;
+ mov out1='\r'
+ ;;
+ br.call.sptk.few rp=_putchar
+ ;;
+ mov out1='\n'
+ ;;
+ br.call.sptk.few rp=_putchar
+ ;;
+9:
+ mov ar.pfs=loc0
+ mov rp=loc1
+ mov ar.lc=loc2
+ ;;
+ br.ret.sptk.few rp
+END(_puthex)
+
+ .data
+ .align 16
+
+fptr_storage:
+ .space 1024*16 // XXX
+fptr_storage_end:
diff --git a/sys/boot/ia64/efi/version b/sys/boot/ia64/efi/version
new file mode 100644
index 0000000..d49b5ef
--- /dev/null
+++ b/sys/boot/ia64/efi/version
@@ -0,0 +1,7 @@
+$FreeBSD$
+
+NOTE ANY CHANGES YOU MAKE TO THE BOOTBLOCKS HERE. The format of this
+file is important. Make sure the current version number is on line 6.
+
+0.1: Initial EFI version, germinated from the NetBSD i386
+ standalone, but enormously modified.
OpenPOWER on IntegriCloud