diff options
Diffstat (limited to 'arch/mips/fw')
| -rw-r--r-- | arch/mips/fw/arc/cmdline.c | 10 | ||||
| -rw-r--r-- | arch/mips/fw/arc/env.c | 2 | ||||
| -rw-r--r-- | arch/mips/fw/arc/file.c | 5 | ||||
| -rw-r--r-- | arch/mips/fw/arc/identify.c | 19 | ||||
| -rw-r--r-- | arch/mips/fw/arc/init.c | 10 | ||||
| -rw-r--r-- | arch/mips/fw/arc/memory.c | 2 | ||||
| -rw-r--r-- | arch/mips/fw/arc/misc.c | 4 | ||||
| -rw-r--r-- | arch/mips/fw/arc/promlib.c | 4 | ||||
| -rw-r--r-- | arch/mips/fw/arc/salone.c | 2 | ||||
| -rw-r--r-- | arch/mips/fw/arc/time.c | 2 | ||||
| -rw-r--r-- | arch/mips/fw/arc/tree.c | 2 | ||||
| -rw-r--r-- | arch/mips/fw/cfe/cfe_api.c | 188 | ||||
| -rw-r--r-- | arch/mips/fw/cfe/cfe_api_int.h | 186 | ||||
| -rw-r--r-- | arch/mips/fw/lib/Makefile | 7 | ||||
| -rw-r--r-- | arch/mips/fw/lib/call_o32.S | 108 | ||||
| -rw-r--r-- | arch/mips/fw/lib/cmdline.c | 101 | ||||
| -rw-r--r-- | arch/mips/fw/sni/Makefile | 5 | ||||
| -rw-r--r-- | arch/mips/fw/sni/sniprom.c | 152 |
18 files changed, 553 insertions, 256 deletions
diff --git a/arch/mips/fw/arc/cmdline.c b/arch/mips/fw/arc/cmdline.c index fd604ef2882..c0122a1dc58 100644 --- a/arch/mips/fw/arc/cmdline.c +++ b/arch/mips/fw/arc/cmdline.c @@ -5,8 +5,9 @@ * * cmdline.c: Kernel command line creation using ARCS argc/argv. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) */ +#include <linux/bug.h> #include <linux/init.h> #include <linux/kernel.h> #include <linux/string.h> @@ -16,11 +17,6 @@ #undef DEBUG_CMDLINE -char * __init prom_getcmdline(void) -{ - return arcs_cmdline; -} - static char *ignored[] = { "ConsoleIn=", "ConsoleOut=", @@ -52,7 +48,7 @@ static char * __init move_firmware_args(char* cp) strcat(cp, used_arc[i][1]); cp += strlen(used_arc[i][1]); /* ... and now the argument */ - s = strstr(prom_argv(actr), "="); + s = strchr(prom_argv(actr), '='); if (s) { s++; strcpy(cp, s); diff --git a/arch/mips/fw/arc/env.c b/arch/mips/fw/arc/env.c index 6f5dd42b96e..1118a26b32e 100644 --- a/arch/mips/fw/arc/env.c +++ b/arch/mips/fw/arc/env.c @@ -5,7 +5,7 @@ * * env.c: ARCS environment variable routines. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) */ #include <linux/init.h> #include <linux/kernel.h> diff --git a/arch/mips/fw/arc/file.c b/arch/mips/fw/arc/file.c index 30335341b44..49fd3ff13fe 100644 --- a/arch/mips/fw/arc/file.c +++ b/arch/mips/fw/arc/file.c @@ -8,14 +8,13 @@ * Copyright (C) 1994, 1995, 1996, 1999 Ralf Baechle * Copyright (C) 1999 Silicon Graphics, Inc. */ -#include <linux/init.h> #include <asm/fw/arc/types.h> #include <asm/sgialib.h> LONG ArcGetDirectoryEntry(ULONG FileID, struct linux_vdirent *Buffer, - ULONG N, ULONG *Count) + ULONG N, ULONG *Count) { return ARC_CALL4(get_vdirent, FileID, Buffer, N, Count); } @@ -69,7 +68,7 @@ ArcGetFileInformation(ULONG FileID, struct linux_finfo *Information) } LONG ArcSetFileInformation(ULONG FileID, ULONG AttributeFlags, - ULONG AttributeMask) + ULONG AttributeMask) { return ARC_CALL3(set_finfo, FileID, AttributeFlags, AttributeMask); } diff --git a/arch/mips/fw/arc/identify.c b/arch/mips/fw/arc/identify.c index 28dfd2e2989..f90266c02c9 100644 --- a/arch/mips/fw/arc/identify.c +++ b/arch/mips/fw/arc/identify.c @@ -9,8 +9,9 @@ * * This code is based on arch/mips/sgi/kernel/system.c, which is * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) */ +#include <linux/bug.h> #include <linux/init.h> #include <linux/kernel.h> #include <linux/types.h> @@ -22,7 +23,6 @@ struct smatch { char *arcname; char *liname; - int type; int flags; }; @@ -30,42 +30,38 @@ static struct smatch mach_table[] = { { .arcname = "SGI-IP22", .liname = "SGI Indy", - .type = MACH_SGI_IP22, .flags = PROM_FLAG_ARCS, }, { .arcname = "SGI-IP27", .liname = "SGI Origin", - .type = MACH_SGI_IP27, .flags = PROM_FLAG_ARCS, }, { .arcname = "SGI-IP28", .liname = "SGI IP28", - .type = MACH_SGI_IP28, .flags = PROM_FLAG_ARCS, }, { .arcname = "SGI-IP30", .liname = "SGI Octane", - .type = MACH_SGI_IP30, .flags = PROM_FLAG_ARCS, }, { .arcname = "SGI-IP32", .liname = "SGI O2", - .type = MACH_SGI_IP32, .flags = PROM_FLAG_ARCS, }, { .arcname = "Microsoft-Jazz", .liname = "Jazz MIPS_Magnum_4000", - .type = MACH_MIPS_MAGNUM_4000, .flags = 0, }, { .arcname = "PICA-61", .liname = "Jazz Acer_PICA_61", - .type = MACH_ACER_PICA_61, .flags = 0, }, { .arcname = "RM200PCI", .liname = "SNI RM200_PCI", - .type = MACH_SNI_RM200_PCI, + .flags = PROM_FLAG_DONT_FREE_TEMP, + }, { + .arcname = "RM200PCI-R5K", + .liname = "SNI RM200_PCI-R5K", .flags = PROM_FLAG_DONT_FREE_TEMP, } }; @@ -104,7 +100,7 @@ void __init prom_identify_arch(void) if (p == NULL) { #ifdef CONFIG_SGI_IP27 /* IP27 PROM misbehaves, seems to not implement ARC - GetChild(). So we just assume it's an IP27. */ + GetChild(). So we just assume it's an IP27. */ iname = "SGI-IP27"; #else iname = "Unknown"; @@ -116,6 +112,5 @@ void __init prom_identify_arch(void) mach = string_to_mach(iname); system_type = mach->liname; - mips_machtype = mach->type; prom_flags = mach->flags; } diff --git a/arch/mips/fw/arc/init.c b/arch/mips/fw/arc/init.c index e2f75b13312..629b24db0d3 100644 --- a/arch/mips/fw/arc/init.c +++ b/arch/mips/fw/arc/init.c @@ -5,13 +5,14 @@ * * PROM library initialisation code. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) */ #include <linux/init.h> #include <linux/kernel.h> #include <asm/bootinfo.h> #include <asm/sgialib.h> +#include <asm/smp-ops.h> #undef DEBUG_PROM_INIT @@ -48,4 +49,11 @@ void __init prom_init(void) ArcRead(0, &c, 1, &cnt); ArcEnterInteractiveMode(); #endif +#ifdef CONFIG_SGI_IP27 + { + extern struct plat_smp_ops ip27_smp_ops; + + register_smp_ops(&ip27_smp_ops); + } +#endif } diff --git a/arch/mips/fw/arc/memory.c b/arch/mips/fw/arc/memory.c index 8b8eea2b6cf..5537b94572b 100644 --- a/arch/mips/fw/arc/memory.c +++ b/arch/mips/fw/arc/memory.c @@ -1,6 +1,6 @@ /* * memory.c: PROM library functions for acquiring/using memory descriptors - * given to us from the ARCS firmware. + * given to us from the ARCS firmware. * * Copyright (C) 1996 by David S. Miller * Copyright (C) 1999, 2000, 2001 by Ralf Baechle diff --git a/arch/mips/fw/arc/misc.c b/arch/mips/fw/arc/misc.c index e527c5fd5a3..f9f5307434c 100644 --- a/arch/mips/fw/arc/misc.c +++ b/arch/mips/fw/arc/misc.c @@ -5,19 +5,19 @@ * * Miscellaneous ARCS PROM routines. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) * Copyright (C) 1999 Ralf Baechle (ralf@gnu.org) * Copyright (C) 1999 Silicon Graphics, Inc. */ #include <linux/init.h> #include <linux/kernel.h> +#include <linux/irqflags.h> #include <asm/bcache.h> #include <asm/fw/arc/types.h> #include <asm/sgialib.h> #include <asm/bootinfo.h> -#include <asm/system.h> VOID ArcHalt(VOID) diff --git a/arch/mips/fw/arc/promlib.c b/arch/mips/fw/arc/promlib.c index c508c00dbb6..7e8ba5ce95b 100644 --- a/arch/mips/fw/arc/promlib.c +++ b/arch/mips/fw/arc/promlib.c @@ -4,14 +4,14 @@ * for more details. * * Copyright (C) 1996 David S. Miller (dm@sgi.com) - * Compability with board caches, Ulf Carlsson + * Compatibility with board caches, Ulf Carlsson */ #include <linux/kernel.h> #include <asm/sgialib.h> #include <asm/bcache.h> /* - * IP22 boardcache is not compatible with board caches. Thus we disable it + * IP22 boardcache is not compatible with board caches. Thus we disable it * during romvec action. Since r4xx0.c is always compiled and linked with your * kernel, this shouldn't cause any harm regardless what MIPS processor you * have. diff --git a/arch/mips/fw/arc/salone.c b/arch/mips/fw/arc/salone.c index e6afb64723d..9b568950d1f 100644 --- a/arch/mips/fw/arc/salone.c +++ b/arch/mips/fw/arc/salone.c @@ -2,7 +2,7 @@ * Routines to load into memory and execute stand-along program images using * ARCS PROM firmware. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) */ #include <linux/init.h> #include <asm/sgialib.h> diff --git a/arch/mips/fw/arc/time.c b/arch/mips/fw/arc/time.c index 42138c837d4..190cdb50b89 100644 --- a/arch/mips/fw/arc/time.c +++ b/arch/mips/fw/arc/time.c @@ -5,7 +5,7 @@ * * Extracting time information from ARCS prom. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) */ #include <linux/init.h> diff --git a/arch/mips/fw/arc/tree.c b/arch/mips/fw/arc/tree.c index d68e5a59c1f..924a37dc256 100644 --- a/arch/mips/fw/arc/tree.c +++ b/arch/mips/fw/arc/tree.c @@ -5,7 +5,7 @@ * * PROM component device tree code. * - * Copyright (C) 1996 David S. Miller (dm@engr.sgi.com) + * Copyright (C) 1996 David S. Miller (davem@davemloft.net) * Copyright (C) 1999 Ralf Baechle (ralf@gnu.org) * Copyright (C) 1999 Silicon Graphics, Inc. */ diff --git a/arch/mips/fw/cfe/cfe_api.c b/arch/mips/fw/cfe/cfe_api.c index a9f69e4e40a..cf84f01931c 100644 --- a/arch/mips/fw/cfe/cfe_api.c +++ b/arch/mips/fw/cfe/cfe_api.c @@ -16,19 +16,16 @@ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ -/* ********************************************************************* - * - * Broadcom Common Firmware Environment (CFE) - * - * Device Function stubs File: cfe_api.c - * - * This module contains device function stubs (small routines to - * call the standard "iocb" interface entry point to CFE). - * There should be one routine here per iocb function call. - * - * Authors: Mitch Lichtenberg, Chris Demetriou - * - ********************************************************************* */ +/* + * + * Broadcom Common Firmware Environment (CFE) + * + * This module contains device function stubs (small routines to + * call the standard "iocb" interface entry point to CFE). + * There should be one routine here per iocb function call. + * + * Authors: Mitch Lichtenberg, Chris Demetriou + */ #include <asm/fw/cfe/cfe_api.h> #include "cfe_api_int.h" @@ -37,12 +34,8 @@ #define XPTR_FROM_NATIVE(n) ((cfe_xptr_t) (intptr_t) (n)) #define NATIVE_FROM_XPTR(x) ((void *) (intptr_t) (x)) -#ifdef CFE_API_IMPL_NAMESPACE -#define cfe_iocb_dispatch(a) __cfe_iocb_dispatch(a) -#endif -int cfe_iocb_dispatch(cfe_xiocb_t * xiocb); +int cfe_iocb_dispatch(struct cfe_xiocb *xiocb); -#if defined(CFE_API_common) || defined(CFE_API_ALL) /* * Declare the dispatch function with args of "intptr_t". * This makes sure whatever model we're compiling in @@ -52,28 +45,26 @@ int cfe_iocb_dispatch(cfe_xiocb_t * xiocb); * passed in two registers each, and CFE expects one. */ -static int (*cfe_dispfunc) (intptr_t handle, intptr_t xiocb) = 0; -static cfe_xuint_t cfe_handle = 0; +static int (*cfe_dispfunc) (intptr_t handle, intptr_t xiocb); +static u64 cfe_handle; -int cfe_init(cfe_xuint_t handle, cfe_xuint_t ept) +int cfe_init(u64 handle, u64 ept) { cfe_dispfunc = NATIVE_FROM_XPTR(ept); cfe_handle = handle; return 0; } -int cfe_iocb_dispatch(cfe_xiocb_t * xiocb) +int cfe_iocb_dispatch(struct cfe_xiocb * xiocb) { if (!cfe_dispfunc) return -1; return (*cfe_dispfunc) ((intptr_t) cfe_handle, (intptr_t) xiocb); } -#endif /* CFE_API_common || CFE_API_ALL */ -#if defined(CFE_API_close) || defined(CFE_API_ALL) int cfe_close(int handle) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_CLOSE; xiocb.xiocb_status = 0; @@ -86,18 +77,16 @@ int cfe_close(int handle) return xiocb.xiocb_status; } -#endif /* CFE_API_close || CFE_API_ALL */ -#if defined(CFE_API_cpu_start) || defined(CFE_API_ALL) int cfe_cpu_start(int cpu, void (*fn) (void), long sp, long gp, long a1) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_CPUCTL; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_cpuctl_t); + xiocb.xiocb_psize = sizeof(struct xiocb_cpuctl); xiocb.plist.xiocb_cpuctl.cpu_number = cpu; xiocb.plist.xiocb_cpuctl.cpu_command = CFE_CPU_CMD_START; xiocb.plist.xiocb_cpuctl.gp_val = gp; @@ -109,18 +98,16 @@ int cfe_cpu_start(int cpu, void (*fn) (void), long sp, long gp, long a1) return xiocb.xiocb_status; } -#endif /* CFE_API_cpu_start || CFE_API_ALL */ -#if defined(CFE_API_cpu_stop) || defined(CFE_API_ALL) int cfe_cpu_stop(int cpu) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_CPUCTL; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_cpuctl_t); + xiocb.xiocb_psize = sizeof(struct xiocb_cpuctl); xiocb.plist.xiocb_cpuctl.cpu_number = cpu; xiocb.plist.xiocb_cpuctl.cpu_command = CFE_CPU_CMD_STOP; @@ -128,18 +115,16 @@ int cfe_cpu_stop(int cpu) return xiocb.xiocb_status; } -#endif /* CFE_API_cpu_stop || CFE_API_ALL */ -#if defined(CFE_API_enumenv) || defined(CFE_API_ALL) int cfe_enumenv(int idx, char *name, int namelen, char *val, int vallen) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_ENV_SET; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_envbuf_t); + xiocb.xiocb_psize = sizeof(struct xiocb_envbuf); xiocb.plist.xiocb_envbuf.enum_idx = idx; xiocb.plist.xiocb_envbuf.name_ptr = XPTR_FROM_NATIVE(name); xiocb.plist.xiocb_envbuf.name_length = namelen; @@ -150,20 +135,17 @@ int cfe_enumenv(int idx, char *name, int namelen, char *val, int vallen) return xiocb.xiocb_status; } -#endif /* CFE_API_enumenv || CFE_API_ALL */ -#if defined(CFE_API_enummem) || defined(CFE_API_ALL) int -cfe_enummem(int idx, int flags, cfe_xuint_t * start, cfe_xuint_t * length, - cfe_xuint_t * type) +cfe_enummem(int idx, int flags, u64 *start, u64 *length, u64 *type) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_MEMENUM; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = flags; - xiocb.xiocb_psize = sizeof(xiocb_meminfo_t); + xiocb.xiocb_psize = sizeof(struct xiocb_meminfo); xiocb.plist.xiocb_meminfo.mi_idx = idx; cfe_iocb_dispatch(&xiocb); @@ -177,30 +159,26 @@ cfe_enummem(int idx, int flags, cfe_xuint_t * start, cfe_xuint_t * length, return 0; } -#endif /* CFE_API_enummem || CFE_API_ALL */ -#if defined(CFE_API_exit) || defined(CFE_API_ALL) int cfe_exit(int warm, int status) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_RESTART; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = warm ? CFE_FLG_WARMSTART : 0; - xiocb.xiocb_psize = sizeof(xiocb_exitstat_t); + xiocb.xiocb_psize = sizeof(struct xiocb_exitstat); xiocb.plist.xiocb_exitstat.status = status; cfe_iocb_dispatch(&xiocb); return xiocb.xiocb_status; } -#endif /* CFE_API_exit || CFE_API_ALL */ -#if defined(CFE_API_flushcache) || defined(CFE_API_ALL) int cfe_flushcache(int flg) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_FLUSHCACHE; xiocb.xiocb_status = 0; @@ -212,34 +190,30 @@ int cfe_flushcache(int flg) return xiocb.xiocb_status; } -#endif /* CFE_API_flushcache || CFE_API_ALL */ -#if defined(CFE_API_getdevinfo) || defined(CFE_API_ALL) int cfe_getdevinfo(char *name) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_GETINFO; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_buffer_t); + xiocb.xiocb_psize = sizeof(struct xiocb_buffer); xiocb.plist.xiocb_buffer.buf_offset = 0; xiocb.plist.xiocb_buffer.buf_ptr = XPTR_FROM_NATIVE(name); - xiocb.plist.xiocb_buffer.buf_length = cfe_strlen(name); + xiocb.plist.xiocb_buffer.buf_length = strlen(name); cfe_iocb_dispatch(&xiocb); if (xiocb.xiocb_status < 0) return xiocb.xiocb_status; - return xiocb.plist.xiocb_buffer.buf_devflags; + return xiocb.plist.xiocb_buffer.buf_ioctlcmd; } -#endif /* CFE_API_getdevinfo || CFE_API_ALL */ -#if defined(CFE_API_getenv) || defined(CFE_API_ALL) int cfe_getenv(char *name, char *dest, int destlen) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; *dest = 0; @@ -247,10 +221,10 @@ int cfe_getenv(char *name, char *dest, int destlen) xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_envbuf_t); + xiocb.xiocb_psize = sizeof(struct xiocb_envbuf); xiocb.plist.xiocb_envbuf.enum_idx = 0; xiocb.plist.xiocb_envbuf.name_ptr = XPTR_FROM_NATIVE(name); - xiocb.plist.xiocb_envbuf.name_length = cfe_strlen(name); + xiocb.plist.xiocb_envbuf.name_length = strlen(name); xiocb.plist.xiocb_envbuf.val_ptr = XPTR_FROM_NATIVE(dest); xiocb.plist.xiocb_envbuf.val_length = destlen; @@ -258,18 +232,16 @@ int cfe_getenv(char *name, char *dest, int destlen) return xiocb.xiocb_status; } -#endif /* CFE_API_getenv || CFE_API_ALL */ -#if defined(CFE_API_getfwinfo) || defined(CFE_API_ALL) int cfe_getfwinfo(cfe_fwinfo_t * info) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_GETINFO; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_fwinfo_t); + xiocb.xiocb_psize = sizeof(struct xiocb_fwinfo); cfe_iocb_dispatch(&xiocb); @@ -292,12 +264,10 @@ int cfe_getfwinfo(cfe_fwinfo_t * info) return 0; } -#endif /* CFE_API_getfwinfo || CFE_API_ALL */ -#if defined(CFE_API_getstdhandle) || defined(CFE_API_ALL) int cfe_getstdhandle(int flg) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_GETHANDLE; xiocb.xiocb_status = 0; @@ -311,23 +281,17 @@ int cfe_getstdhandle(int flg) return xiocb.xiocb_status; return xiocb.xiocb_handle; } -#endif /* CFE_API_getstdhandle || CFE_API_ALL */ -#if defined(CFE_API_getticks) || defined(CFE_API_ALL) int64_t -#ifdef CFE_API_IMPL_NAMESPACE -__cfe_getticks(void) -#else cfe_getticks(void) -#endif { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_FW_GETTIME; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_time_t); + xiocb.xiocb_psize = sizeof(struct xiocb_time); xiocb.plist.xiocb_time.ticks = 0; cfe_iocb_dispatch(&xiocb); @@ -335,18 +299,16 @@ cfe_getticks(void) return xiocb.plist.xiocb_time.ticks; } -#endif /* CFE_API_getticks || CFE_API_ALL */ -#if defined(CFE_API_inpstat) || defined(CFE_API_ALL) int cfe_inpstat(int handle) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_INPSTAT; xiocb.xiocb_status = 0; xiocb.xiocb_handle = handle; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_inpstat_t); + xiocb.xiocb_psize = sizeof(struct xiocb_inpstat); xiocb.plist.xiocb_inpstat.inp_status = 0; cfe_iocb_dispatch(&xiocb); @@ -355,20 +317,18 @@ int cfe_inpstat(int handle) return xiocb.xiocb_status; return xiocb.plist.xiocb_inpstat.inp_status; } -#endif /* CFE_API_inpstat || CFE_API_ALL */ -#if defined(CFE_API_ioctl) || defined(CFE_API_ALL) int cfe_ioctl(int handle, unsigned int ioctlnum, unsigned char *buffer, - int length, int *retlen, cfe_xuint_t offset) + int length, int *retlen, u64 offset) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_IOCTL; xiocb.xiocb_status = 0; xiocb.xiocb_handle = handle; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_buffer_t); + xiocb.xiocb_psize = sizeof(struct xiocb_buffer); xiocb.plist.xiocb_buffer.buf_offset = offset; xiocb.plist.xiocb_buffer.buf_ioctlcmd = ioctlnum; xiocb.plist.xiocb_buffer.buf_ptr = XPTR_FROM_NATIVE(buffer); @@ -380,21 +340,19 @@ cfe_ioctl(int handle, unsigned int ioctlnum, unsigned char *buffer, *retlen = xiocb.plist.xiocb_buffer.buf_retlen; return xiocb.xiocb_status; } -#endif /* CFE_API_ioctl || CFE_API_ALL */ -#if defined(CFE_API_open) || defined(CFE_API_ALL) int cfe_open(char *name) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_OPEN; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_buffer_t); + xiocb.xiocb_psize = sizeof(struct xiocb_buffer); xiocb.plist.xiocb_buffer.buf_offset = 0; xiocb.plist.xiocb_buffer.buf_ptr = XPTR_FROM_NATIVE(name); - xiocb.plist.xiocb_buffer.buf_length = cfe_strlen(name); + xiocb.plist.xiocb_buffer.buf_length = strlen(name); cfe_iocb_dispatch(&xiocb); @@ -402,27 +360,21 @@ int cfe_open(char *name) return xiocb.xiocb_status; return xiocb.xiocb_handle; } -#endif /* CFE_API_open || CFE_API_ALL */ -#if defined(CFE_API_read) || defined(CFE_API_ALL) int cfe_read(int handle, unsigned char *buffer, int length) { return cfe_readblk(handle, 0, buffer, length); } -#endif /* CFE_API_read || CFE_API_ALL */ -#if defined(CFE_API_readblk) || defined(CFE_API_ALL) -int -cfe_readblk(int handle, cfe_xint_t offset, unsigned char *buffer, - int length) +int cfe_readblk(int handle, s64 offset, unsigned char *buffer, int length) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_READ; xiocb.xiocb_status = 0; xiocb.xiocb_handle = handle; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_buffer_t); + xiocb.xiocb_psize = sizeof(struct xiocb_buffer); xiocb.plist.xiocb_buffer.buf_offset = offset; xiocb.plist.xiocb_buffer.buf_ptr = XPTR_FROM_NATIVE(buffer); xiocb.plist.xiocb_buffer.buf_length = length; @@ -433,62 +385,41 @@ cfe_readblk(int handle, cfe_xint_t offset, unsigned char *buffer, return xiocb.xiocb_status; return xiocb.plist.xiocb_buffer.buf_retlen; } -#endif /* CFE_API_readblk || CFE_API_ALL */ -#if defined(CFE_API_setenv) || defined(CFE_API_ALL) int cfe_setenv(char *name, char *val) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_ENV_SET; xiocb.xiocb_status = 0; xiocb.xiocb_handle = 0; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_envbuf_t); + xiocb.xiocb_psize = sizeof(struct xiocb_envbuf); xiocb.plist.xiocb_envbuf.enum_idx = 0; xiocb.plist.xiocb_envbuf.name_ptr = XPTR_FROM_NATIVE(name); - xiocb.plist.xiocb_envbuf.name_length = cfe_strlen(name); + xiocb.plist.xiocb_envbuf.name_length = strlen(name); xiocb.plist.xiocb_envbuf.val_ptr = XPTR_FROM_NATIVE(val); - xiocb.plist.xiocb_envbuf.val_length = cfe_strlen(val); + xiocb.plist.xiocb_envbuf.val_length = strlen(val); cfe_iocb_dispatch(&xiocb); return xiocb.xiocb_status; } -#endif /* CFE_API_setenv || CFE_API_ALL */ -#if (defined(CFE_API_strlen) || defined(CFE_API_ALL)) \ - && !defined(CFE_API_STRLEN_CUSTOM) -int cfe_strlen(char *name) -{ - int count = 0; - - while (*name++) - count++; - - return count; -} -#endif /* CFE_API_strlen || CFE_API_ALL */ - -#if defined(CFE_API_write) || defined(CFE_API_ALL) -int cfe_write(int handle, unsigned char *buffer, int length) +int cfe_write(int handle, const char *buffer, int length) { return cfe_writeblk(handle, 0, buffer, length); } -#endif /* CFE_API_write || CFE_API_ALL */ -#if defined(CFE_API_writeblk) || defined(CFE_API_ALL) -int -cfe_writeblk(int handle, cfe_xint_t offset, unsigned char *buffer, - int length) +int cfe_writeblk(int handle, s64 offset, const char *buffer, int length) { - cfe_xiocb_t xiocb; + struct cfe_xiocb xiocb; xiocb.xiocb_fcode = CFE_CMD_DEV_WRITE; xiocb.xiocb_status = 0; xiocb.xiocb_handle = handle; xiocb.xiocb_flags = 0; - xiocb.xiocb_psize = sizeof(xiocb_buffer_t); + xiocb.xiocb_psize = sizeof(struct xiocb_buffer); xiocb.plist.xiocb_buffer.buf_offset = offset; xiocb.plist.xiocb_buffer.buf_ptr = XPTR_FROM_NATIVE(buffer); xiocb.plist.xiocb_buffer.buf_length = length; @@ -499,4 +430,3 @@ cfe_writeblk(int handle, cfe_xint_t offset, unsigned char *buffer, return xiocb.xiocb_status; return xiocb.plist.xiocb_buffer.buf_retlen; } -#endif /* CFE_API_writeblk || CFE_API_ALL */ diff --git a/arch/mips/fw/cfe/cfe_api_int.h b/arch/mips/fw/cfe/cfe_api_int.h index f7e5a64b55f..d9759e64695 100644 --- a/arch/mips/fw/cfe/cfe_api_int.h +++ b/arch/mips/fw/cfe/cfe_api_int.h @@ -15,28 +15,12 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ - -/* ********************************************************************* - * - * Broadcom Common Firmware Environment (CFE) - * - * Device function prototypes File: cfe_api_int.h - * - * This header defines all internal types and macros for the - * library. This is stuff that's not exported to an app - * using the library. - * - * Authors: Mitch Lichtenberg, Chris Demetriou - * - ********************************************************************* */ - #ifndef CFE_API_INT_H #define CFE_API_INT_H -/* ********************************************************************* - * Constants - ********************************************************************* */ - +/* + * Constants. + */ #define CFE_CMD_FW_GETINFO 0 #define CFE_CMD_FW_RESTART 1 #define CFE_CMD_FW_BOOT 2 @@ -64,89 +48,101 @@ #define CFE_CMD_VENDOR_USE 0x8000 /* codes above this are for customer use */ -/* ********************************************************************* - * Structures - ********************************************************************* */ +/* + * Structures. + */ -typedef uint64_t cfe_xuint_t; -typedef int64_t cfe_xint_t; -typedef int64_t cfe_xptr_t; +/* eeek, signed "pointers" */ +typedef s64 cfe_xptr_t; -typedef struct xiocb_buffer_s { - cfe_xuint_t buf_offset; /* offset on device (bytes) */ +struct xiocb_buffer { + u64 buf_offset; /* offset on device (bytes) */ cfe_xptr_t buf_ptr; /* pointer to a buffer */ - cfe_xuint_t buf_length; /* length of this buffer */ - cfe_xuint_t buf_retlen; /* returned length (for read ops) */ - cfe_xuint_t buf_ioctlcmd; /* IOCTL command (used only for IOCTLs) */ -} xiocb_buffer_t; - -#define buf_devflags buf_ioctlcmd /* returned device info flags */ + u64 buf_length; /* length of this buffer */ + u64 buf_retlen; /* returned length (for read ops) */ + u64 buf_ioctlcmd; /* IOCTL command (used only for IOCTLs) */ +}; -typedef struct xiocb_inpstat_s { - cfe_xuint_t inp_status; /* 1 means input available */ -} xiocb_inpstat_t; +struct xiocb_inpstat { + u64 inp_status; /* 1 means input available */ +}; -typedef struct xiocb_envbuf_s { - cfe_xint_t enum_idx; /* 0-based enumeration index */ +struct xiocb_envbuf { + s64 enum_idx; /* 0-based enumeration index */ cfe_xptr_t name_ptr; /* name string buffer */ - cfe_xint_t name_length; /* size of name buffer */ + s64 name_length; /* size of name buffer */ cfe_xptr_t val_ptr; /* value string buffer */ - cfe_xint_t val_length; /* size of value string buffer */ -} xiocb_envbuf_t; - -typedef struct xiocb_cpuctl_s { - cfe_xuint_t cpu_number; /* cpu number to control */ - cfe_xuint_t cpu_command; /* command to issue to CPU */ - cfe_xuint_t start_addr; /* CPU start address */ - cfe_xuint_t gp_val; /* starting GP value */ - cfe_xuint_t sp_val; /* starting SP value */ - cfe_xuint_t a1_val; /* starting A1 value */ -} xiocb_cpuctl_t; - -typedef struct xiocb_time_s { - cfe_xint_t ticks; /* current time in ticks */ -} xiocb_time_t; - -typedef struct xiocb_exitstat_s { - cfe_xint_t status; -} xiocb_exitstat_t; - -typedef struct xiocb_meminfo_s { - cfe_xint_t mi_idx; /* 0-based enumeration index */ - cfe_xint_t mi_type; /* type of memory block */ - cfe_xuint_t mi_addr; /* physical start address */ - cfe_xuint_t mi_size; /* block size */ -} xiocb_meminfo_t; - -typedef struct xiocb_fwinfo_s { - cfe_xint_t fwi_version; /* major, minor, eco version */ - cfe_xint_t fwi_totalmem; /* total installed mem */ - cfe_xint_t fwi_flags; /* various flags */ - cfe_xint_t fwi_boardid; /* board ID */ - cfe_xint_t fwi_bootarea_va; /* VA of boot area */ - cfe_xint_t fwi_bootarea_pa; /* PA of boot area */ - cfe_xint_t fwi_bootarea_size; /* size of boot area */ - cfe_xint_t fwi_reserved1; - cfe_xint_t fwi_reserved2; - cfe_xint_t fwi_reserved3; -} xiocb_fwinfo_t; - -typedef struct cfe_xiocb_s { - cfe_xuint_t xiocb_fcode; /* IOCB function code */ - cfe_xint_t xiocb_status; /* return status */ - cfe_xint_t xiocb_handle; /* file/device handle */ - cfe_xuint_t xiocb_flags; /* flags for this IOCB */ - cfe_xuint_t xiocb_psize; /* size of parameter list */ + s64 val_length; /* size of value string buffer */ +}; + +struct xiocb_cpuctl { + u64 cpu_number; /* cpu number to control */ + u64 cpu_command; /* command to issue to CPU */ + u64 start_addr; /* CPU start address */ + u64 gp_val; /* starting GP value */ + u64 sp_val; /* starting SP value */ + u64 a1_val; /* starting A1 value */ +}; + +struct xiocb_time { + s64 ticks; /* current time in ticks */ +}; + +struct xiocb_exitstat{ + s64 status; +}; + +struct xiocb_meminfo { + s64 mi_idx; /* 0-based enumeration index */ + s64 mi_type; /* type of memory block */ + u64 mi_addr; /* physical start address */ + u64 mi_size; /* block size */ +}; + +struct xiocb_fwinfo { + s64 fwi_version; /* major, minor, eco version */ + s64 fwi_totalmem; /* total installed mem */ + s64 fwi_flags; /* various flags */ + s64 fwi_boardid; /* board ID */ + s64 fwi_bootarea_va; /* VA of boot area */ + s64 fwi_bootarea_pa; /* PA of boot area */ + s64 fwi_bootarea_size; /* size of boot area */ + s64 fwi_reserved1; + s64 fwi_reserved2; + s64 fwi_reserved3; +}; + +struct cfe_xiocb { + u64 xiocb_fcode; /* IOCB function code */ + s64 xiocb_status; /* return status */ + s64 xiocb_handle; /* file/device handle */ + u64 xiocb_flags; /* flags for this IOCB */ + u64 xiocb_psize; /* size of parameter list */ union { - xiocb_buffer_t xiocb_buffer; /* buffer parameters */ - xiocb_inpstat_t xiocb_inpstat; /* input status parameters */ - xiocb_envbuf_t xiocb_envbuf; /* environment function parameters */ - xiocb_cpuctl_t xiocb_cpuctl; /* CPU control parameters */ - xiocb_time_t xiocb_time; /* timer parameters */ - xiocb_meminfo_t xiocb_meminfo; /* memory arena info parameters */ - xiocb_fwinfo_t xiocb_fwinfo; /* firmware information */ - xiocb_exitstat_t xiocb_exitstat; /* Exit Status */ + /* buffer parameters */ + struct xiocb_buffer xiocb_buffer; + + /* input status parameters */ + struct xiocb_inpstat xiocb_inpstat; + + /* environment function parameters */ + struct xiocb_envbuf xiocb_envbuf; + + /* CPU control parameters */ + struct xiocb_cpuctl xiocb_cpuctl; + + /* timer parameters */ + struct xiocb_time xiocb_time; + + /* memory arena info parameters */ + struct xiocb_meminfo xiocb_meminfo; + + /* firmware information */ + struct xiocb_fwinfo xiocb_fwinfo; + + /* Exit Status */ + struct xiocb_exitstat xiocb_exitstat; } plist; -} cfe_xiocb_t; +}; -#endif /* CFE_API_INT_H */ +#endif /* CFE_API_INT_H */ diff --git a/arch/mips/fw/lib/Makefile b/arch/mips/fw/lib/Makefile new file mode 100644 index 00000000000..52915051677 --- /dev/null +++ b/arch/mips/fw/lib/Makefile @@ -0,0 +1,7 @@ +# +# Makefile for generic prom monitor library routines under Linux. +# + +lib-y += cmdline.o + +lib-$(CONFIG_64BIT) += call_o32.o diff --git a/arch/mips/fw/lib/call_o32.S b/arch/mips/fw/lib/call_o32.S new file mode 100644 index 00000000000..4703fe4dbd9 --- /dev/null +++ b/arch/mips/fw/lib/call_o32.S @@ -0,0 +1,108 @@ +/* + * O32 interface for the 64 (or N32) ABI. + * + * Copyright (C) 2002, 2014 Maciej W. Rozycki + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version + * 2 of the License, or (at your option) any later version. + */ + +#include <asm/asm.h> +#include <asm/regdef.h> + +/* O32 register size. */ +#define O32_SZREG 4 +/* Maximum number of arguments supported. Must be even! */ +#define O32_ARGC 32 +/* Number of static registers we save. */ +#define O32_STATC 11 +/* Argument area frame size. */ +#define O32_ARGSZ (O32_SZREG * O32_ARGC) +/* Static register save area frame size. */ +#define O32_STATSZ (SZREG * O32_STATC) +/* Stack pointer register save area frame size. */ +#define O32_SPSZ SZREG +/* Combined area frame size. */ +#define O32_FRAMESZ (O32_ARGSZ + O32_SPSZ + O32_STATSZ) +/* Switched stack frame size. */ +#define O32_NFRAMESZ (O32_ARGSZ + O32_SPSZ) + + .text + +/* + * O32 function call dispatcher, for interfacing 32-bit ROM routines. + * + * The standard 64 (N32) calling sequence is supported, with a0 holding + * a function pointer, a1 a pointer to the new stack to call the + * function with or 0 if no stack switching is requested, a2-a7 -- the + * function call's first six arguments, and the stack -- the remaining + * arguments (up to O32_ARGC, including a2-a7). Static registers, gp + * and fp are preserved, v0 holds the result. This code relies on the + * called o32 function for sp and ra restoration and this dispatcher has + * to be placed in a KSEGx (or KUSEG) address space. Any pointers + * passed have to point to addresses within one of these spaces as well. + */ +NESTED(call_o32, O32_FRAMESZ, ra) + REG_SUBU sp,O32_FRAMESZ + + REG_S ra,O32_FRAMESZ-1*SZREG(sp) + REG_S fp,O32_FRAMESZ-2*SZREG(sp) + REG_S gp,O32_FRAMESZ-3*SZREG(sp) + REG_S s7,O32_FRAMESZ-4*SZREG(sp) + REG_S s6,O32_FRAMESZ-5*SZREG(sp) + REG_S s5,O32_FRAMESZ-6*SZREG(sp) + REG_S s4,O32_FRAMESZ-7*SZREG(sp) + REG_S s3,O32_FRAMESZ-8*SZREG(sp) + REG_S s2,O32_FRAMESZ-9*SZREG(sp) + REG_S s1,O32_FRAMESZ-10*SZREG(sp) + REG_S s0,O32_FRAMESZ-11*SZREG(sp) + + move jp,a0 + + move fp,sp + beqz a1,0f + REG_SUBU fp,a1,O32_NFRAMESZ +0: + REG_S sp,O32_NFRAMESZ-1*SZREG(fp) + + sll a0,a2,zero + sll a1,a3,zero + sll a2,a4,zero + sll a3,a5,zero + sw a6,4*O32_SZREG(fp) + sw a7,5*O32_SZREG(fp) + + PTR_LA t0,O32_FRAMESZ(sp) + PTR_LA t1,6*O32_SZREG(fp) + li t2,O32_ARGC-6 +1: + lw t3,(t0) + REG_ADDU t0,SZREG + sw t3,(t1) + REG_SUBU t2,1 + REG_ADDU t1,O32_SZREG + bnez t2,1b + + move sp,fp + + jalr jp + + REG_L sp,O32_NFRAMESZ-1*SZREG(sp) + + REG_L s0,O32_FRAMESZ-11*SZREG(sp) + REG_L s1,O32_FRAMESZ-10*SZREG(sp) + REG_L s2,O32_FRAMESZ-9*SZREG(sp) + REG_L s3,O32_FRAMESZ-8*SZREG(sp) + REG_L s4,O32_FRAMESZ-7*SZREG(sp) + REG_L s5,O32_FRAMESZ-6*SZREG(sp) + REG_L s6,O32_FRAMESZ-5*SZREG(sp) + REG_L s7,O32_FRAMESZ-4*SZREG(sp) + REG_L gp,O32_FRAMESZ-3*SZREG(sp) + REG_L fp,O32_FRAMESZ-2*SZREG(sp) + REG_L ra,O32_FRAMESZ-1*SZREG(sp) + + REG_ADDU sp,O32_FRAMESZ + jr ra +END(call_o32) diff --git a/arch/mips/fw/lib/cmdline.c b/arch/mips/fw/lib/cmdline.c new file mode 100644 index 00000000000..ffd0345780a --- /dev/null +++ b/arch/mips/fw/lib/cmdline.c @@ -0,0 +1,101 @@ +/* + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + * + * Copyright (C) 2012 MIPS Technologies, Inc. All rights reserved. + */ +#include <linux/init.h> +#include <linux/kernel.h> +#include <linux/string.h> + +#include <asm/addrspace.h> +#include <asm/fw/fw.h> + +int fw_argc; +int *_fw_argv; +int *_fw_envp; + +void __init fw_init_cmdline(void) +{ + int i; + + /* Validate command line parameters. */ + if ((fw_arg0 >= CKSEG0) || (fw_arg1 < CKSEG0)) { + fw_argc = 0; + _fw_argv = NULL; + } else { + fw_argc = (fw_arg0 & 0x0000ffff); + _fw_argv = (int *)fw_arg1; + } + + /* Validate environment pointer. */ + if (fw_arg2 < CKSEG0) + _fw_envp = NULL; + else + _fw_envp = (int *)fw_arg2; + + for (i = 1; i < fw_argc; i++) { + strlcat(arcs_cmdline, fw_argv(i), COMMAND_LINE_SIZE); + if (i < (fw_argc - 1)) + strlcat(arcs_cmdline, " ", COMMAND_LINE_SIZE); + } +} + +char * __init fw_getcmdline(void) +{ + return &(arcs_cmdline[0]); +} + +char *fw_getenv(char *envname) +{ + char *result = NULL; + + if (_fw_envp != NULL) { + /* + * Return a pointer to the given environment variable. + * YAMON uses "name", "value" pairs, while U-Boot uses + * "name=value". + */ + int i, yamon, index = 0; + + yamon = (strchr(fw_envp(index), '=') == NULL); + i = strlen(envname); + + while (fw_envp(index)) { + if (strncmp(envname, fw_envp(index), i) == 0) { + if (yamon) { + result = fw_envp(index + 1); + break; + } else if (fw_envp(index)[i] == '=') { + result = (fw_envp(index + 1) + i); + break; + } + } + + /* Increment array index. */ + if (yamon) + index += 2; + else + index += 1; + } + } + + return result; +} + +unsigned long fw_getenvl(char *envname) +{ + unsigned long envl = 0UL; + char *str; + long val; + int tmp; + + str = fw_getenv(envname); + if (str) { + tmp = kstrtol(str, 0, &val); + envl = (unsigned long)val; + } + + return envl; +} diff --git a/arch/mips/fw/sni/Makefile b/arch/mips/fw/sni/Makefile new file mode 100644 index 00000000000..3f01dd36e6b --- /dev/null +++ b/arch/mips/fw/sni/Makefile @@ -0,0 +1,5 @@ +# +# Makefile for the SNI prom monitor routines under Linux. +# + +lib-$(CONFIG_FW_SNIPROM) += sniprom.o diff --git a/arch/mips/fw/sni/sniprom.c b/arch/mips/fw/sni/sniprom.c new file mode 100644 index 00000000000..6aa264b9856 --- /dev/null +++ b/arch/mips/fw/sni/sniprom.c @@ -0,0 +1,152 @@ +/* + * Big Endian PROM code for SNI RM machines + * + * This file is subject to the terms and conditions of the GNU General Public + * License. See the file "COPYING" in the main directory of this archive + * for more details. + * + * Copyright (C) 2005-2006 Florian Lohoff (flo@rfc822.org) + * Copyright (C) 2005-2006 Thomas Bogendoerfer (tsbogend@alpha.franken.de) + */ + +#include <linux/kernel.h> +#include <linux/init.h> +#include <linux/string.h> +#include <linux/console.h> + +#include <asm/addrspace.h> +#include <asm/sni.h> +#include <asm/mipsprom.h> +#include <asm/mipsregs.h> +#include <asm/bootinfo.h> + +/* special SNI prom calls */ +/* + * This does not exist in all proms - SINIX compares + * the prom env variable "version" against "2.0008" + * or greater. If lesser it tries to probe interesting + * registers + */ +#define PROM_GET_MEMCONF 58 +#define PROM_GET_HWCONF 61 + +#define PROM_VEC (u64 *)CKSEG1ADDR(0x1fc00000) +#define PROM_ENTRY(x) (PROM_VEC + (x)) + +#define ___prom_putchar ((int *(*)(int))PROM_ENTRY(PROM_PUTCHAR)) +#define ___prom_getenv ((char *(*)(char *))PROM_ENTRY(PROM_GETENV)) +#define ___prom_get_memconf ((void (*)(void *))PROM_ENTRY(PROM_GET_MEMCONF)) +#define ___prom_get_hwconf ((u32 (*)(void))PROM_ENTRY(PROM_GET_HWCONF)) + +#ifdef CONFIG_64BIT + +/* O32 stack has to be 8-byte aligned. */ +static u64 o32_stk[4096]; +#define O32_STK &o32_stk[sizeof(o32_stk)] + +#define __PROM_O32(fun, arg) fun arg __asm__(#fun); \ + __asm__(#fun " = call_o32") + +int __PROM_O32(__prom_putchar, (int *(*)(int), void *, int)); +char *__PROM_O32(__prom_getenv, (char *(*)(char *), void *, char *)); +void __PROM_O32(__prom_get_memconf, (void (*)(void *), void *, void *)); +u32 __PROM_O32(__prom_get_hwconf, (u32 (*)(void), void *)); + +#define _prom_putchar(x) __prom_putchar(___prom_putchar, O32_STK, x) +#define _prom_getenv(x) __prom_getenv(___prom_getenv, O32_STK, x) +#define _prom_get_memconf(x) __prom_get_memconf(___prom_get_memconf, O32_STK, x) +#define _prom_get_hwconf() __prom_get_hwconf(___prom_get_hwconf, O32_STK) + +#else +#define _prom_putchar(x) ___prom_putchar(x) +#define _prom_getenv(x) ___prom_getenv(x) +#define _prom_get_memconf(x) ___prom_get_memconf(x) +#define _prom_get_hwconf(x) ___prom_get_hwconf(x) +#endif + +void prom_putchar(char c) +{ + _prom_putchar(c); +} + + +char *prom_getenv(char *s) +{ + return _prom_getenv(s); +} + +void *prom_get_hwconf(void) +{ + u32 hwconf = _prom_get_hwconf(); + + if (hwconf == 0xffffffff) + return NULL; + + return (void *)CKSEG1ADDR(hwconf); +} + +void __init prom_free_prom_memory(void) +{ +} + +/* + * /proc/cpuinfo system type + * + */ +char *system_type = "Unknown"; +const char *get_system_type(void) +{ + return system_type; +} + +static void __init sni_mem_init(void) +{ + int i, memsize; + struct membank { + u32 size; + u32 base; + u32 size2; + u32 pad1; + u32 pad2; + } memconf[8]; + int brd_type = *(unsigned char *)SNI_IDPROM_BRDTYPE; + + + /* MemSIZE from prom in 16MByte chunks */ + memsize = *((unsigned char *) SNI_IDPROM_MEMSIZE) * 16; + + pr_debug("IDProm memsize: %u MByte\n", memsize); + + /* get memory bank layout from prom */ + _prom_get_memconf(&memconf); + + pr_debug("prom_get_mem_conf memory configuration:\n"); + for (i = 0; i < 8 && memconf[i].size; i++) { + if (brd_type == SNI_BRD_PCI_TOWER || + brd_type == SNI_BRD_PCI_TOWER_CPLUS) { + if (memconf[i].base >= 0x20000000 && + memconf[i].base < 0x30000000) + memconf[i].base -= 0x20000000; + } + pr_debug("Bank%d: %08x @ %08x\n", i, + memconf[i].size, memconf[i].base); + add_memory_region(memconf[i].base, memconf[i].size, + BOOT_MEM_RAM); + } +} + +void __init prom_init(void) +{ + int argc = fw_arg0; + u32 *argv = (u32 *)CKSEG0ADDR(fw_arg1); + int i; + + sni_mem_init(); + + /* copy prom cmdline parameters to kernel cmdline */ + for (i = 1; i < argc; i++) { + strcat(arcs_cmdline, (char *)CKSEG0ADDR(argv[i])); + if (i < (argc - 1)) + strcat(arcs_cmdline, " "); + } +} |
