diff options
Diffstat (limited to 'arch/mips/sni/sniprom.c')
-rw-r--r-- | arch/mips/sni/sniprom.c | 158 |
1 files changed, 158 insertions, 0 deletions
diff --git a/arch/mips/sni/sniprom.c b/arch/mips/sni/sniprom.c new file mode 100644 index 000000000000..d1d0f1f493b4 --- /dev/null +++ b/arch/mips/sni/sniprom.c | |||
@@ -0,0 +1,158 @@ | |||
1 | /* | ||
2 | * Big Endian PROM code for SNI RM machines | ||
3 | * | ||
4 | * This file is subject to the terms and conditions of the GNU General Public | ||
5 | * License. See the file "COPYING" in the main directory of this archive | ||
6 | * for more details. | ||
7 | * | ||
8 | * Copyright (C) 2005-2006 Florian Lohoff (flo@rfc822.org) | ||
9 | * Copyright (C) 2005-2006 Thomas Bogendoerfer (tsbogend@alpha.franken.de) | ||
10 | */ | ||
11 | |||
12 | #include <linux/kernel.h> | ||
13 | #include <linux/init.h> | ||
14 | #include <linux/string.h> | ||
15 | |||
16 | #include <asm/addrspace.h> | ||
17 | #include <asm/sni.h> | ||
18 | #include <asm/mipsprom.h> | ||
19 | #include <asm/bootinfo.h> | ||
20 | |||
21 | /* special SNI prom calls */ | ||
22 | /* | ||
23 | * This does not exist in all proms - SINIX compares | ||
24 | * the prom env variable "version" against "2.0008" | ||
25 | * or greater. If lesser it tries to probe interesting | ||
26 | * registers | ||
27 | */ | ||
28 | #define PROM_GET_MEMCONF 58 | ||
29 | |||
30 | #define PROM_VEC (u64 *)CKSEG1ADDR(0x1fc00000) | ||
31 | #define PROM_ENTRY(x) (PROM_VEC + (x)) | ||
32 | |||
33 | |||
34 | #undef DEBUG | ||
35 | #ifdef DEBUG | ||
36 | #define DBG_PRINTF(x...) prom_printf(x) | ||
37 | #else | ||
38 | #define DBG_PRINTF(x...) | ||
39 | #endif | ||
40 | |||
41 | static int *(*__prom_putchar)(int) = (int *(*)(int))PROM_ENTRY(PROM_PUTCHAR); | ||
42 | static char *(*__prom_getenv)(char *) = (char *(*)(char *))PROM_ENTRY(PROM_GETENV); | ||
43 | static void (*__prom_get_memconf)(void *) = (void (*)(void *))PROM_ENTRY(PROM_GET_MEMCONF); | ||
44 | |||
45 | char *prom_getenv (char *s) | ||
46 | { | ||
47 | return __prom_getenv(s); | ||
48 | } | ||
49 | |||
50 | void prom_printf(char *fmt, ...) | ||
51 | { | ||
52 | va_list args; | ||
53 | char ppbuf[1024]; | ||
54 | char *bptr; | ||
55 | |||
56 | va_start(args, fmt); | ||
57 | vsprintf(ppbuf, fmt, args); | ||
58 | |||
59 | bptr = ppbuf; | ||
60 | |||
61 | while (*bptr != 0) { | ||
62 | if (*bptr == '\n') | ||
63 | __prom_putchar('\r'); | ||
64 | |||
65 | __prom_putchar(*bptr++); | ||
66 | } | ||
67 | va_end(args); | ||
68 | } | ||
69 | |||
70 | unsigned long prom_free_prom_memory(void) | ||
71 | { | ||
72 | return 0; | ||
73 | } | ||
74 | |||
75 | /* | ||
76 | * /proc/cpuinfo system type | ||
77 | * | ||
78 | */ | ||
79 | static const char *systype = "Unknown"; | ||
80 | const char *get_system_type(void) | ||
81 | { | ||
82 | return systype; | ||
83 | } | ||
84 | |||
85 | #define SNI_IDPROM_BASE 0xbff00000 | ||
86 | #define SNI_IDPROM_MEMSIZE (SNI_IDPROM_BASE+0x28) /* Memsize in 16MB quantities */ | ||
87 | #define SNI_IDPROM_BRDTYPE (SNI_IDPROM_BASE+0x29) /* Board Type */ | ||
88 | #define SNI_IDPROM_CPUTYPE (SNI_IDPROM_BASE+0x30) /* CPU Type */ | ||
89 | |||
90 | #define SNI_IDPROM_SIZE 0x1000 | ||
91 | |||
92 | #ifdef DEBUG | ||
93 | static void sni_idprom_dump(void) | ||
94 | { | ||
95 | int i; | ||
96 | |||
97 | prom_printf("SNI IDProm dump (first 128byte):\n"); | ||
98 | for(i=0;i<128;i++) { | ||
99 | if (i%16 == 0) | ||
100 | prom_printf("%04x ", i); | ||
101 | |||
102 | prom_printf("%02x ", *(unsigned char *) (SNI_IDPROM_BASE+i)); | ||
103 | |||
104 | if (i%16 == 15) | ||
105 | prom_printf("\n"); | ||
106 | } | ||
107 | } | ||
108 | #endif | ||
109 | |||
110 | static void sni_mem_init(void ) | ||
111 | { | ||
112 | int i, memsize; | ||
113 | struct membank { | ||
114 | u32 size; | ||
115 | u32 base; | ||
116 | u32 size2; | ||
117 | u32 pad1; | ||
118 | u32 pad2; | ||
119 | } memconf[8]; | ||
120 | |||
121 | /* MemSIZE from prom in 16MByte chunks */ | ||
122 | memsize=*((unsigned char *) SNI_IDPROM_MEMSIZE) * 16; | ||
123 | |||
124 | DBG_PRINTF("IDProm memsize: %lu MByte\n", memsize); | ||
125 | |||
126 | /* get memory bank layout from prom */ | ||
127 | __prom_get_memconf(&memconf); | ||
128 | |||
129 | DBG_PRINTF("prom_get_mem_conf memory configuration:\n"); | ||
130 | for(i=0;i<8 && memconf[i].size;i++) { | ||
131 | prom_printf("Bank%d: %08x @ %08x\n", i, | ||
132 | memconf[i].size, memconf[i].base); | ||
133 | add_memory_region(memconf[i].base, memconf[i].size, BOOT_MEM_RAM); | ||
134 | } | ||
135 | } | ||
136 | |||
137 | void __init prom_init(void) | ||
138 | { | ||
139 | int argc = fw_arg0; | ||
140 | char **argv = (void *)fw_arg1; | ||
141 | unsigned int sni_brd_type = *(unsigned char *) SNI_IDPROM_BRDTYPE; | ||
142 | int i; | ||
143 | |||
144 | DBG_PRINTF("Found SNI brdtype %02x\n", sni_brd_type); | ||
145 | |||
146 | #ifdef DEBUG | ||
147 | sni_idprom_dump(); | ||
148 | #endif | ||
149 | sni_mem_init(); | ||
150 | |||
151 | /* copy prom cmdline parameters to kernel cmdline */ | ||
152 | for (i = 1; i < argc; i++) { | ||
153 | strcat(arcs_cmdline, argv[i]); | ||
154 | if (i < (argc - 1)) | ||
155 | strcat(arcs_cmdline, " "); | ||
156 | } | ||
157 | } | ||
158 | |||