Date: Mon, 29 Mar 2010 16:14:22 +0000 (UTC) From: Nathan Whitehorn <nwhitehorn@FreeBSD.org> To: src-committers@freebsd.org, svn-src-projects@freebsd.org Subject: svn commit: r205839 - in projects/ppc64/sys/boot/powerpc: . ps3 Message-ID: <201003291614.o2TGEMMb005239@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: nwhitehorn Date: Mon Mar 29 16:14:22 2010 New Revision: 205839 URL: http://svn.freebsd.org/changeset/base/205839 Log: Judging by this morning's news, we may be a bit late to this party, but: Add the beginnings of a PS3 loader. This is sufficient to be started from Mambo, LV1, or kboot, and can print "Hello World" to the Mambo console. More features will come later. Added: projects/ppc64/sys/boot/powerpc/ps3/ projects/ppc64/sys/boot/powerpc/ps3/Makefile projects/ppc64/sys/boot/powerpc/ps3/conf.c projects/ppc64/sys/boot/powerpc/ps3/help.ps3 projects/ppc64/sys/boot/powerpc/ps3/ldscript.powerpc projects/ppc64/sys/boot/powerpc/ps3/main.c projects/ppc64/sys/boot/powerpc/ps3/metadata.c projects/ppc64/sys/boot/powerpc/ps3/start.S projects/ppc64/sys/boot/powerpc/ps3/version Modified: projects/ppc64/sys/boot/powerpc/Makefile Modified: projects/ppc64/sys/boot/powerpc/Makefile ============================================================================== --- projects/ppc64/sys/boot/powerpc/Makefile Mon Mar 29 15:59:44 2010 (r205838) +++ projects/ppc64/sys/boot/powerpc/Makefile Mon Mar 29 16:14:22 2010 (r205839) @@ -1,5 +1,5 @@ # $FreeBSD$ -SUBDIR= boot1.chrp ofw uboot +SUBDIR= boot1.chrp ofw uboot ps3 .include <bsd.subdir.mk> Added: projects/ppc64/sys/boot/powerpc/ps3/Makefile ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/Makefile Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,108 @@ +# $FreeBSD: projects/ppc64/sys/boot/powerpc/ofw/Makefile 204217 2010-02-22 18:07:41Z nwhitehorn $ + +.include <bsd.own.mk> +MK_SSP= no + +PROG= loader.ps3 +NEWVERSWHAT= "Playstation 3 loader" ${MACHINE_ARCH} +BINDIR?= /boot +INSTALLFLAGS= -b + +# Architecture-specific loader code +SRCS= start.S conf.c metadata.c vers.c main.c +SRCS+= ucmpdi2.c + +LOADER_DISK_SUPPORT?= no +LOADER_UFS_SUPPORT?= no +LOADER_CD9660_SUPPORT?= no +LOADER_EXT2FS_SUPPORT?= no +LOADER_NET_SUPPORT?= no +LOADER_NFS_SUPPORT?= no +LOADER_TFTP_SUPPORT?= no +LOADER_GZIP_SUPPORT?= no +LOADER_BZIP2_SUPPORT?= no + +.if ${LOADER_DISK_SUPPORT} == "yes" +CFLAGS+= -DLOADER_DISK_SUPPORT +.endif +.if ${LOADER_UFS_SUPPORT} == "yes" +CFLAGS+= -DLOADER_UFS_SUPPORT +.endif +.if ${LOADER_CD9660_SUPPORT} == "yes" +CFLAGS+= -DLOADER_CD9660_SUPPORT +.endif +.if ${LOADER_EXT2FS_SUPPORT} == "yes" +CFLAGS+= -DLOADER_EXT2FS_SUPPORT +.endif +.if ${LOADER_GZIP_SUPPORT} == "yes" +CFLAGS+= -DLOADER_GZIP_SUPPORT +.endif +.if ${LOADER_BZIP2_SUPPORT} == "yes" +CFLAGS+= -DLOADER_BZIP2_SUPPORT +.endif +.if ${LOADER_NET_SUPPORT} == "yes" +CFLAGS+= -DLOADER_NET_SUPPORT +.endif +.if ${LOADER_NFS_SUPPORT} == "yes" +CFLAGS+= -DLOADER_NFS_SUPPORT +.endif +.if ${LOADER_TFTP_SUPPORT} == "yes" +CFLAGS+= -DLOADER_TFTP_SUPPORT +.endif + +.if ${MK_FORTH} != "no" +# Enable BootForth +BOOT_FORTH= yes +CFLAGS+= -DBOOT_FORTH -I${.CURDIR}/../../ficl -I${.CURDIR}/../../ficl/powerpc +LIBFICL= ${.OBJDIR}/../../ficl/libficl.a +.endif + +# Avoid the open-close-dance for every file access as some firmwares perform +# an auto-negotiation on every open of the network interface and thus causes +# netbooting to take horribly long. +CFLAGS+= -DNETIF_OPEN_CLOSE_ONCE + +# Always add MI sources +.PATH: ${.CURDIR}/../../common ${.CURDIR}/../../../libkern +.include "${.CURDIR}/../../common/Makefile.inc" +CFLAGS+= -I${.CURDIR}/../../common -I${.CURDIR}/../../.. +CFLAGS+= -I. + +CLEANFILES+= vers.c loader.help + +CFLAGS+= -ffreestanding -msoft-float +# load address. set in linker script +RELOC?= 0x0 +CFLAGS+= -DRELOC=${RELOC} + +LDFLAGS= -nostdlib -static -T ${.CURDIR}/ldscript.powerpc + +# 64-bit bridge extensions +CFLAGS+= -Wa,-mppc64bridge + +# Pull in common loader code +#.PATH: ${.CURDIR}/../../ofw/common +#.include "${.CURDIR}/../../ofw/common/Makefile.inc" + +# where to get libstand from +CFLAGS+= -I${.CURDIR}/../../../../lib/libstand/ + +DPADD= ${LIBFICL} ${LIBOFW} ${LIBSTAND} +LDADD= ${LIBFICL} ${LIBOFW} -lstand + +vers.c: ${.CURDIR}/../../common/newvers.sh ${.CURDIR}/version + sh ${.CURDIR}/../../common/newvers.sh ${.CURDIR}/version ${NEWVERSWHAT} + +loader.help: help.common help.ps3 + cat ${.ALLSRC} | \ + awk -f ${.CURDIR}/../../common/merge_help.awk > ${.TARGET} + +.PATH: ${.CURDIR}/../../forth +FILES= loader.help loader.4th support.4th loader.conf +FILESDIR_loader.conf= /boot/defaults + +.if !exists(${DESTDIR}/boot/loader.rc) +FILES+= loader.rc +.endif + +.include <bsd.prog.mk> Added: projects/ppc64/sys/boot/powerpc/ps3/conf.c ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/conf.c Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,120 @@ +/*- + * Copyright (c) 1999 Michael Smith <msmith@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. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD: projects/ppc64/sys/boot/powerpc/ofw/conf.c 196951 2009-09-07 20:39:04Z nwhitehorn $"); + +#include <stand.h> +#include "bootstrap.h" + +#if defined(LOADER_NET_SUPPORT) +#include "dev_net.h" +#endif + +/* + * 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[] = { +#if defined(LOADER_DISK_SUPPORT) || defined(LOADER_CD9660_SUPPORT) + &ofwdisk, +#endif +#if defined(LOADER_NET_SUPPORT) + &netdev, +#endif + NULL +}; + +struct fs_ops *file_system[] = { +#if defined(LOADER_UFS_SUPPORT) + &ufs_fsops, +#endif +#if defined(LOADER_CD9660_SUPPORT) + &cd9660_fsops, +#endif +#if defined(LOADER_EXT2FS_SUPPORT) + &ext2fs_fsops, +#endif +#if defined(LOADER_NFS_SUPPORT) + &nfs_fsops, +#endif +#if defined(LOADER_TFTP_SUPPORT) + &tftp_fsops, +#endif +#if defined(LOADER_GZIP_SUPPORT) + &gzipfs_fsops, +#endif +#if defined(LOADER_BZIP2_SUPPORT) + &bzipfs_fsops, +#endif + NULL +}; + +struct netif_driver *netif_drivers[] = { +#if defined(LOADER_NET_SUPPORT) + &ofwnet, +#endif + NULL, +}; + +/* Exported for PowerPC only */ +/* + * Sort formats so that those that can detect based on arguments + * rather than reading the file go first. + */ + +struct file_format *file_formats[] = { +#if 0 + &ofw_elf64, +#endif + NULL +}; + +/* + * Consoles + * + * We don't prototype these in libofw.h because they require + * data structures from bootstrap.h as well. + */ +extern struct console ofwconsole; + +struct console *consoles[] = { +#if 0 + &mamboconsole, +#endif + NULL +}; + +/* + * reloc - our load address + */ +vm_offset_t reloc = RELOC; Added: projects/ppc64/sys/boot/powerpc/ps3/help.ps3 ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/help.ps3 Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1 @@ +$FreeBSD: projects/ppc64/sys/boot/powerpc/ofw/help.ofw 174722 2007-12-17 22:18:07Z marcel $ Added: projects/ppc64/sys/boot/powerpc/ps3/ldscript.powerpc ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/ldscript.powerpc Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,147 @@ +/* $FreeBSD: projects/ppc64/sys/boot/powerpc/ofw/ldscript.powerpc 204915 2010-03-09 17:26:50Z nwhitehorn $ */ + +OUTPUT_FORMAT("elf32-powerpc", "elf32-powerpc", "elf32-powerpc") +OUTPUT_ARCH(powerpc:common) +ENTRY(_start) +SEARCH_DIR(/usr/lib); +/* Do we need any of these for elf? + __DYNAMIC = 0; */ +PROVIDE (__stack = 0); +SECTIONS +{ + /* Read-only sections, merged into text segment: */ + . = 0x0; + .text : + { + *(.text) + /* .gnu.warning sections are handled specially by elf32.em. */ + *(.gnu.warning) + *(.gnu.linkonce.t*) + } =0 + _etext = .; + .interp : { *(.interp) } + .hash : { *(.hash) } + .dynsym : { *(.dynsym) } + .dynstr : { *(.dynstr) } + .gnu.version : { *(.gnu.version) } + .gnu.version_d : { *(.gnu.version_d) } + .gnu.version_r : { *(.gnu.version_r) } + .rela.text : + { *(.rela.text) *(.rela.gnu.linkonce.t*) } + .rela.data : + { *(.rela.data) *(.rela.gnu.linkonce.d*) } + .rela.rodata : + { *(.rela.rodata) *(.rela.gnu.linkonce.r*) } + .rela.got : { *(.rela.got) } + .rela.got1 : { *(.rela.got1) } + .rela.got2 : { *(.rela.got2) } + .rela.ctors : { *(.rela.ctors) } + .rela.dtors : { *(.rela.dtors) } + .rela.init : { *(.rela.init) } + .rela.fini : { *(.rela.fini) } + .rela.bss : { *(.rela.bss) } + .rela.plt : { *(.rela.plt) } + .rela.sdata : { *(.rela.sdata) } + .rela.sbss : { *(.rela.sbss) } + .rela.sdata2 : { *(.rela.sdata2) } + .rela.sbss2 : { *(.rela.sbss2) } + .text : + { + *(.text) + /* .gnu.warning sections are handled specially by elf32.em. */ + *(.gnu.warning) + *(.gnu.linkonce.t*) + } =0 + _etext = .; + PROVIDE (etext = .); + .init : { *(.init) } =0 + .fini : { *(.fini) } =0 + .rodata : { *(.rodata) *(.gnu.linkonce.r*) } + .rodata1 : { *(.rodata1) } + .sdata2 : { *(.sdata2) } + .sbss2 : { *(.sbss2) } + /* Adjust the address for the data segment to the next page up. */ + . = ((. + 0x1000) & ~(0x1000 - 1)); + .data : + { + *(.data) + *(.gnu.linkonce.d*) + CONSTRUCTORS + } + .data1 : { *(.data1) } + .got1 : { *(.got1) } + .dynamic : { *(.dynamic) } + /* Put .ctors and .dtors next to the .got2 section, so that the pointers + get relocated with -mrelocatable. Also put in the .fixup pointers. + The current compiler no longer needs this, but keep it around for 2.7.2 */ + PROVIDE (_GOT2_START_ = .); + .got2 : { *(.got2) } + PROVIDE (__CTOR_LIST__ = .); + .ctors : { *(.ctors) } + PROVIDE (__CTOR_END__ = .); + PROVIDE (__DTOR_LIST__ = .); + .dtors : { *(.dtors) } + PROVIDE (__DTOR_END__ = .); + PROVIDE (_FIXUP_START_ = .); + .fixup : { *(.fixup) } + PROVIDE (_FIXUP_END_ = .); + PROVIDE (_GOT2_END_ = .); + PROVIDE (_GOT_START_ = .); + .got : { *(.got) } + .got.plt : { *(.got.plt) } + PROVIDE (_GOT_END_ = .); + /* We want the small data sections together, so single-instruction offsets + can access them all, and initialized data all before uninitialized, so + we can shorten the on-disk segment size. */ + .sdata : { *(.sdata) } + _edata = .; + PROVIDE (edata = .); + .sbss : + { + PROVIDE (__sbss_start = .); + *(.sbss) + *(.scommon) + *(.dynsbss) + PROVIDE (__sbss_end = .); + } + .plt : { *(.plt) } + .bss : + { + PROVIDE (__bss_start = .); + *(.dynbss) + *(.bss) + *(COMMON) + } + _end = . ; + PROVIDE (end = .); + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + /* DWARF debug sections. + Symbols in the DWARF debugging sections are relative to the beginning + of the section so we begin them at 0. */ + /* DWARF 1 */ + .debug 0 : { *(.debug) } + .line 0 : { *(.line) } + /* GNU DWARF 1 extensions */ + .debug_srcinfo 0 : { *(.debug_srcinfo) } + .debug_sfnames 0 : { *(.debug_sfnames) } + /* DWARF 1.1 and DWARF 2 */ + .debug_aranges 0 : { *(.debug_aranges) } + .debug_pubnames 0 : { *(.debug_pubnames) } + /* DWARF 2 */ + .debug_info 0 : { *(.debug_info) } + .debug_abbrev 0 : { *(.debug_abbrev) } + .debug_line 0 : { *(.debug_line) } + .debug_frame 0 : { *(.debug_frame) } + .debug_str 0 : { *(.debug_str) } + .debug_loc 0 : { *(.debug_loc) } + .debug_macinfo 0 : { *(.debug_macinfo) } + /* SGI/MIPS DWARF 2 extensions */ + .debug_weaknames 0 : { *(.debug_weaknames) } + .debug_funcnames 0 : { *(.debug_funcnames) } + .debug_typenames 0 : { *(.debug_typenames) } + .debug_varnames 0 : { *(.debug_varnames) } + /* These must appear regardless of . */ +} + Added: projects/ppc64/sys/boot/powerpc/ps3/main.c ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/main.c Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,68 @@ +/*- + * Copyright (C) 2010 Nathan Whitehorn + * 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 ``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 TOOLS GMBH 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 <sys/cdefs.h> +__FBSDID("$FreeBSD: head/sys/boot/powerpc/ofw/start.c 174722 2007-12-17 22:18:07Z marcel $"); + +#include <stand.h> +#include "bootstrap.h" + + int mambocall(int, ...); + __asm(".text; .globl mambocall; mambocall: .long 0x000EAEB0; blr"); + #define mambo_print(a) mambocall(0,a,strlen(a)); + +struct arch_switch archsw; + +int +main(void) +{ + mambo_print("Hello world\n"); + + return (0); +} + +void +exit(int code) +{ +} + +void +delay(int usecs) +{ +} + +int +getsecs() +{ + return (0); +} + +time_t +time(time_t *tloc) +{ + return (0); +} + + Added: projects/ppc64/sys/boot/powerpc/ps3/metadata.c ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/metadata.c Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,355 @@ +/*- + * Copyright (c) 1998 Michael Smith <msmith@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. + * + * from: FreeBSD: src/sys/boot/sparc64/loader/metadata.c,v 1.6 + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD: projects/ppc64/sys/boot/powerpc/ofw/metadata.c 197113 2009-09-12 05:39:51Z nwhitehorn $"); + +#include <stand.h> +#include <sys/param.h> +#include <sys/reboot.h> +#include <sys/linker.h> + +#include <machine/metadata.h> + +#include "bootstrap.h" + +/* + * Return a 'boothowto' value corresponding to the kernel arguments in + * (kargs) and any relevant environment variables. + */ +static struct +{ + const char *ev; + int mask; +} howto_names[] = { + {"boot_askname", RB_ASKNAME}, + {"boot_cdrom", RB_CDROM}, + {"boot_ddb", RB_KDB}, + {"boot_dfltroot", RB_DFLTROOT}, + {"boot_gdb", RB_GDB}, + {"boot_multicons", RB_MULTIPLE}, + {"boot_mute", RB_MUTE}, + {"boot_pause", RB_PAUSE}, + {"boot_serial", RB_SERIAL}, + {"boot_single", RB_SINGLE}, + {"boot_verbose", RB_VERBOSE}, + {NULL, 0} +}; + +int +md_getboothowto(char *kargs) +{ + char *cp; + int howto; + int active; + int i; + + /* Parse kargs */ + howto = 0; + if (kargs != NULL) { + cp = kargs; + active = 0; + while (*cp != 0) { + if (!active && (*cp == '-')) { + active = 1; + } else if (active) + switch (*cp) { + case 'a': + howto |= RB_ASKNAME; + break; + case 'C': + howto |= RB_CDROM; + break; + case 'd': + howto |= RB_KDB; + break; + case 'D': + howto |= RB_MULTIPLE; + break; + case 'm': + howto |= RB_MUTE; + break; + case 'g': + howto |= RB_GDB; + break; + case 'h': + howto |= RB_SERIAL; + break; + case 'p': + howto |= RB_PAUSE; + break; + case 'r': + howto |= RB_DFLTROOT; + break; + case 's': + howto |= RB_SINGLE; + break; + case 'v': + howto |= RB_VERBOSE; + break; + default: + active = 0; + break; + } + cp++; + } + } + /* get equivalents from the environment */ + for (i = 0; howto_names[i].ev != NULL; i++) + if (getenv(howto_names[i].ev) != NULL) + howto |= howto_names[i].mask; + if (!strcmp(getenv("console"), "comconsole")) + howto |= RB_SERIAL; + if (!strcmp(getenv("console"), "nullconsole")) + howto |= RB_MUTE; + return(howto); +} + +/* + * Copy the environment into the load area starting at (addr). + * Each variable is formatted as <name>=<value>, with a single nul + * separating each variable, and a double nul terminating the environment. + */ +vm_offset_t +md_copyenv(vm_offset_t addr) +{ + struct env_var *ep; + + /* traverse the environment */ + for (ep = environ; ep != NULL; ep = ep->ev_next) { + archsw.arch_copyin(ep->ev_name, addr, strlen(ep->ev_name)); + addr += strlen(ep->ev_name); + archsw.arch_copyin("=", addr, 1); + addr++; + if (ep->ev_value != NULL) { + archsw.arch_copyin(ep->ev_value, addr, strlen(ep->ev_value)); + addr += strlen(ep->ev_value); + } + archsw.arch_copyin("", addr, 1); + addr++; + } + archsw.arch_copyin("", addr, 1); + addr++; + return(addr); +} + +/* + * Copy module-related data into the load area, where it can be + * used as a directory for loaded modules. + * + * Module data is presented in a self-describing format. Each datum + * is preceded by a 32-bit identifier and a 32-bit size field. + * + * Currently, the following data are saved: + * + * MOD_NAME (variable) module name (string) + * MOD_TYPE (variable) module type (string) + * MOD_ARGS (variable) module parameters (string) + * MOD_ADDR sizeof(vm_offset_t) module load address + * MOD_SIZE sizeof(size_t) module size + * MOD_METADATA (variable) type-specific metadata + */ + +static int align; + +#define COPY32(v, a, c) { \ + u_int32_t x = (v); \ + if (c) \ + archsw.arch_copyin(&x, a, sizeof(x)); \ + a += sizeof(x); \ +} + +#define MOD_STR(t, a, s, c) { \ + COPY32(t, a, c); \ + COPY32(strlen(s) + 1, a, c) \ + if (c) \ + archsw.arch_copyin(s, a, strlen(s) + 1);\ + a += roundup(strlen(s) + 1, align); \ +} + +#define MOD_NAME(a, s, c) MOD_STR(MODINFO_NAME, a, s, c) +#define MOD_TYPE(a, s, c) MOD_STR(MODINFO_TYPE, a, s, c) +#define MOD_ARGS(a, s, c) MOD_STR(MODINFO_ARGS, a, s, c) + +#define MOD_VAR(t, a, s, c) { \ + COPY32(t, a, c); \ + COPY32(sizeof(s), a, c); \ + if (c) \ + archsw.arch_copyin(&s, a, sizeof(s)); \ + a += roundup(sizeof(s), align); \ +} + +#define MOD_ADDR(a, s, c) MOD_VAR(MODINFO_ADDR, a, s, c) +#define MOD_SIZE(a, s, c) MOD_VAR(MODINFO_SIZE, a, s, c) + +#define MOD_METADATA(a, mm, c) { \ + COPY32(MODINFO_METADATA | mm->md_type, a, c);\ + COPY32(mm->md_size, a, c); \ + if (c) \ + archsw.arch_copyin(mm->md_data, a, mm->md_size);\ + a += roundup(mm->md_size, align); \ +} + +#define MOD_END(a, c) { \ + COPY32(MODINFO_END, a, c); \ + COPY32(0, a, c); \ +} + +vm_offset_t +md_copymodules(vm_offset_t addr, int kern64) +{ + struct preloaded_file *fp; + struct file_metadata *md; + uint64_t scratch64; + int c; + + c = addr != 0; + /* start with the first module on the list, should be the kernel */ + for (fp = file_findfile(NULL, NULL); fp != NULL; fp = fp->f_next) { + + MOD_NAME(addr, fp->f_name, c); /* this field must come first */ + MOD_TYPE(addr, fp->f_type, c); + if (fp->f_args) + MOD_ARGS(addr, fp->f_args, c); + if (kern64) { + scratch64 = fp->f_addr; + MOD_ADDR(addr, scratch64, c); + scratch64 = fp->f_size; + MOD_SIZE(addr, scratch64, c); + } else { + MOD_ADDR(addr, fp->f_addr, c); + MOD_SIZE(addr, fp->f_size, c); + } + for (md = fp->f_metadata; md != NULL; md = md->md_next) { + if (!(md->md_type & MODINFOMD_NOCOPY)) { + MOD_METADATA(addr, md, c); + } + } + } + MOD_END(addr, c); + return(addr); +} + +/* + * Load the information expected by a powerpc kernel. + * + * - The 'boothowto' argument is constructed + * - The 'bootdev' argument is constructed + * - The kernel environment is copied into kernel space. + * - Module metadata are formatted and placed in kernel space. + */ +int +md_load_dual(char *args, vm_offset_t *modulep, int kern64) +{ + struct preloaded_file *kfp; + struct preloaded_file *xp; + struct file_metadata *md; + vm_offset_t kernend; + vm_offset_t addr; + vm_offset_t envp; + vm_offset_t size; + uint64_t scratch64; + char *rootdevname; + int howto; + + align = kern64 ? 8 : 4; + howto = md_getboothowto(args); + + /* + * Allow the environment variable 'rootdev' to override the supplied device + * This should perhaps go to MI code and/or have $rootdev tested/set by + * MI code before launching the kernel. + */ + rootdevname = getenv("rootdev"); + if (rootdevname == NULL) + rootdevname = getenv("currdev"); + /* Try reading the /etc/fstab file to select the root device */ + getrootmount(rootdevname); + + /* find the last module in the chain */ + addr = 0; + for (xp = file_findfile(NULL, NULL); xp != NULL; xp = xp->f_next) { + if (addr < (xp->f_addr + xp->f_size)) + addr = xp->f_addr + xp->f_size; + } + /* pad to a page boundary */ + addr = roundup(addr, PAGE_SIZE); + + /* copy our environment */ + envp = addr; + addr = md_copyenv(addr); + + /* pad to a page boundary */ + addr = roundup(addr, PAGE_SIZE); + + kernend = 0; + kfp = file_findfile(NULL, kern64 ? "elf64 kernel" : "elf32 kernel"); + if (kfp == NULL) + kfp = file_findfile(NULL, "elf kernel"); + if (kfp == NULL) + panic("can't find kernel file"); + file_addmetadata(kfp, MODINFOMD_HOWTO, sizeof howto, &howto); + if (kern64) { + scratch64 = envp; + file_addmetadata(kfp, MODINFOMD_ENVP, sizeof scratch64, &scratch64); + scratch64 = kernend; + file_addmetadata(kfp, MODINFOMD_KERNEND, sizeof scratch64, &scratch64); + } else { + file_addmetadata(kfp, MODINFOMD_ENVP, sizeof envp, &envp); + file_addmetadata(kfp, MODINFOMD_KERNEND, sizeof kernend, &kernend); + } + + *modulep = addr; + size = md_copymodules(0, kern64); + kernend = roundup(addr + size, PAGE_SIZE); + + md = file_findmetadata(kfp, MODINFOMD_KERNEND); + if (kern64) { + scratch64 = kernend; + bcopy(&scratch64, md->md_data, sizeof scratch64); + } else { + bcopy(&kernend, md->md_data, sizeof kernend); + } + + (void)md_copymodules(addr, kern64); + + return(0); +} + +int +md_load(char *args, vm_offset_t *modulep) +{ + return (md_load_dual(args, modulep, 0)); +} + +int +md_load64(char *args, vm_offset_t *modulep) +{ + return (md_load_dual(args, modulep, 1)); +} + Added: projects/ppc64/sys/boot/powerpc/ps3/start.S ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/start.S Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,109 @@ +/*- + * Copyright (C) 2010 Nathan Whitehorn + * 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 ``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 TOOLS GMBH 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. + */ + + +/* + * KBoot and simulators will start this program from the _start symbol, with + * r3 pointing to a flattened device tree (kexec), r4 the physical address + * at which we were loaded, and r5 0 (kexec) or a pointer to Open Firmware + * (simulator). If r4 is non-zero, the first order of business is relocating + * ourselves to 0. In the kboot case, the PPE secondary thread will enter + * at 0x60. + * + * If started directly by the LV1 hypervisor, we are loaded to address 0 + * and execution on both threads begins at 0x100 (EXC_RST). + */ + +#define CACHELINE_SIZE 128 +#define SPR_CTRL 136 +#define TMPSTKSZ 4096 + +/* KBoot thread 0 entry -- do relocation, then jump to main */ +.global _start +_start: + cmpwi %r4,0 + bne relocate_self +relocated_start: + lis %r1,(tmpstk+TMPSTKSZ-16)@ha + addi %r1,%r1,(tmpstk+TMPSTKSZ-16)@l + bl main + +. = 0x20 +.global secondary_spin_sem +secondary_spin_sem: + .long 0 + +. = 0x60 +thread1_start: + ba thread1_start /* kboot copies the first 256 bytes to + * address 0, so we are safe to jump + * (and stay) there */ + + li %r0,secondary_spin_sem@l +1: lwz %r1,0(%r0) /* Spin on SECONDARY_SPIN_SEM_ADDRESS */ + cmpwi %r1,0 + beq 1b + li %r0,0x100 /* Invalidate reset vector cache line */ + icbi 0,%r0 + ba 0x100 /* If non-zero, jump to the reset vector */ + +. = 0x100 +exc_rst: + mfspr %r0,SPR_CTRL + /* The first two bits of r0 are 01 (thread 1) or 10 (thread 0) */ + cntlzd %r0,%r0 /* Now 0 for thread 0, 1 for thread 1 */ + + cmpwi %r0,0 + bne thread1_start /* Send thread 1 to wait */ + + b relocated_start /* Main entry point for thread 0 */ + +relocate_self: + /* We enter this with r4 the physical offset for our relocation */ + lis %r8,_end@ha /* r8: copy length */ + addi %r8,%r8,_end@l + li %r5,0 /* r5: dest address */ +1: add %r6,%r4,%r5 /* r6: source address */ + ld %r7,0(%r6) + std %r7,0(%r5) + cmpw %r5,%r8 + addi %r5,%r5,8 + blt 1b + + /* Now invalidate the icache */ +2: li %r5,0 + dcbst 0,%r5 + icbi 0,%r5 + cmpw %r5,%r8 + addi %r5,%r5,CACHELINE_SIZE + blt 2b + + /* All done: absolute jump to relocated entry point */ + ba relocated_start + +.data +.align 4 +tmpstk: + .space TMPSTKSZ Added: projects/ppc64/sys/boot/powerpc/ps3/version ============================================================================== --- /dev/null 00:00:00 1970 (empty, because file is newly added) +++ projects/ppc64/sys/boot/powerpc/ps3/version Mon Mar 29 16:14:22 2010 (r205839) @@ -0,0 +1,6 @@ +$FreeBSD: projects/ppc64/sys/boot/powerpc/ofw/version 174722 2007-12-17 22:18:07Z marcel $ + +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 PS3/PowerPC version.
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201003291614.o2TGEMMb005239>