tx39.c revision 1.5 1 /* $NetBSD: tx39.c,v 1.5 1999/12/08 15:54:11 uch Exp $ */
2
3 /*
4 * Copyright (c) 1999, by UCHIYAMA Yasushi
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. The name of the developer may NOT be used to endorse or promote products
13 * derived from this software without specific prior written permission.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
16 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
19 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
20 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
21 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
23 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
24 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 * SUCH DAMAGE.
26 *
27 */
28
29 #include "opt_tx39_debug.h"
30 #include "m38813c.h"
31 #include "p7416buf.h"
32
33 #include <sys/param.h>
34 #include <sys/systm.h>
35 #include <sys/device.h>
36
37 #include <machine/locore.h> /* cpu_id */
38 #include <machine/bootinfo.h> /* bootinfo */
39 #include <machine/sysconf.h> /* platform */
40
41 #include <machine/bus.h>
42 #include <machine/intr.h>
43
44 #include <hpcmips/hpcmips/machdep.h> /* cpu_model */
45 #include <hpcmips/dev/biconsvar.h>
46 #include <hpcmips/dev/bicons.h>
47
48 #include <hpcmips/tx/tx39biureg.h>
49 #include <hpcmips/tx/tx39reg.h>
50 #include <hpcmips/tx/tx39var.h>
51 #ifdef TX391X
52 #include <hpcmips/tx/tx3912videovar.h>
53 #endif
54
55 #include <sys/termios.h>
56 #include <sys/ttydefaults.h>
57 #include <hpcmips/tx/tx39uartvar.h>
58 #ifndef CONSPEED
59 #define CONSPEED TTYDEF_SPEED
60 #endif
61
62 /* console keyboard */
63 #if NP7416BUF > 0
64 #include <hpcmips/dev/p7416bufvar.h>
65 #endif
66 #if NM38813C > 0
67 #include <hpcmips/dev/m38813cvar.h>
68 #endif
69
70 extern unsigned nullclkread __P((void));
71 extern unsigned (*clkread) __P((void));
72
73 struct tx_chipset_tag tx_chipset;
74
75 #ifdef TX39_DEBUG
76 u_int32_t tx39debugflag;
77 #endif
78
79 void tx_init __P((void));
80 int tx39icu_intr __P((u_int32_t, u_int32_t, u_int32_t, u_int32_t));
81 int tx39_find_dram __P((u_int32_t, u_int32_t));
82
83 /* TX39-specific initialization vector */
84 void tx_os_init __P((void));
85 void tx_bus_reset __P((void));
86 void tx_cons_init __P((void));
87 void tx_device_register __P((struct device *, void *));
88 void tx_fb_init __P((caddr_t*));
89 int tx_mem_init __P((caddr_t));
90 void tx_reboot __P((int howto, char *bootstr));
91 int tx_intr __P((u_int32_t mask, u_int32_t pc, u_int32_t statusReg,
92 u_int32_t causeReg));
93
94 void
95 tx_init()
96 {
97 tx_chipset_tag_t tc;
98 int model, rev;
99
100 tc = tx_conf_get_tag();
101 /*
102 * Platform Specific Function Hooks
103 */
104 platform.os_init = tx_os_init;
105 platform.bus_reset = tx_bus_reset;
106 platform.cons_init = tx_cons_init;
107 platform.device_register = tx_device_register;
108 platform.fb_init = tx_fb_init;
109 platform.mem_init = tx_mem_init;
110 platform.reboot = tx_reboot;
111
112 model = (cpu_id.cpu.cp_majrev << 4)| cpu_id.cpu.cp_minrev;
113
114 switch (model) {
115 default:
116 /* Unknown TOSHIBA TX39-series */
117 sprintf(cpu_model, "Unknown TOSHIBA TX39-series %x.%x",
118 cpu_id.cpu.cp_majrev, cpu_id.cpu.cp_minrev);
119 break;
120 case TMPR3912:
121 sprintf(cpu_model, "TOSHIBA TMPR3912");
122 cpuspeed = 50; /* XXX Should calibrate XXX */
123 break;
124 case TMPR3922:
125 rev = tx_conf_read(tc, TX3922_REVISION_REG);
126 sprintf(cpu_model, "TOSHIBA TMPR3922 rev. %x.%x",
127 (rev >> 4) & 0xf, rev & 0xf);
128 cpuspeed = 100; /* XXX Should calibrate XXX */
129 break;
130 }
131 }
132
133 void
134 tx_os_init()
135 {
136 /*
137 * Set up interrupt handling and I/O addresses.
138 */
139 mips_hardware_intr = tx39icu_intr;
140
141 splvec.splbio = MIPS_SPL_2_4;
142 splvec.splnet = MIPS_SPL_2_4;
143 splvec.spltty = MIPS_SPL_2_4;
144 splvec.splimp = MIPS_SPL_2_4;
145 splvec.splclock = MIPS_SPL_2_4;
146 splvec.splstatclock = MIPS_SPL_2_4;
147
148 /* no high resolution timer circuit; possibly never called */
149 clkread = nullclkread;
150 }
151
152 void
153 tx_fb_init(kernend)
154 caddr_t *kernend;
155 {
156 #ifdef TX391X
157 tx_chipset_tag_t tc;
158 u_int32_t fb_start, fb_addr, fb_size, fb_line_bytes;
159
160 /* Initialize to access TX39 configuration register */
161 tc = tx_conf_get_tag();
162
163 fb_start = MIPS_KSEG0_TO_PHYS(*kernend);
164 tx3912video_init(tc, fb_start, bootinfo->fb_width,
165 bootinfo->fb_height, &fb_addr, &fb_size,
166 &fb_line_bytes);
167
168 /* Set bootinfo for bicons */
169 bootinfo->fb_line_bytes = fb_line_bytes;
170 bootinfo->fb_addr = (unsigned char*)MIPS_PHYS_TO_KSEG1(fb_addr);
171
172 /* Skip V-RAM area */
173 *kernend += fb_size;
174 #endif /* TX391X */
175 #ifdef TX392X
176 /*
177 * Plum V-RAM isn't accessible until pmap_bootstrap,
178 * at this time, bicons is disabled.
179 */
180 bootinfo->fb_addr = 0;
181 #endif /* TX392X */
182 }
183
184 int
185 tx_mem_init(kernend)
186 caddr_t kernend; /* kseg0 */
187 {
188 u_int32_t startaddr, endaddr;
189 int npage, xpage, kpage;
190
191 startaddr = MIPS_PHYS_TO_KSEG1(
192 (btoc((u_int32_t)kernend - MIPS_KSEG0_START)) << PGSHIFT);
193 endaddr = MIPS_PHYS_TO_KSEG1(TX39_SYSADDR_DRAMBANK0CS1 +
194 TX39_SYSADDR_DRAMBANK_LEN);
195 kpage = btoc(MIPS_KSEG1_TO_PHYS(startaddr));
196
197 /* D-RAM bank0 */
198 npage = tx39_find_dram(startaddr, endaddr);
199
200 printf("DRAM bank0: %d pages (%dMByte) reserved %d pages\n",
201 npage + 1, ((npage + 1) * NBPG) / 0x100000, kpage + 1);
202 npage -= kpage; /* exclude kernel area */
203
204 /* Clear DRAM area */
205 memset((void*)startaddr, 0, npage * NBPG);
206
207 /* D-RAM bank1 XXX find only. not usable yet */
208 startaddr = MIPS_PHYS_TO_KSEG1(TX39_SYSADDR_DRAMBANK1CS1);
209 endaddr = MIPS_PHYS_TO_KSEG1(TX39_SYSADDR_DRAMBANK1CS1 +
210 TX39_SYSADDR_DRAMBANK_LEN);
211 xpage = tx39_find_dram(startaddr, endaddr);
212 printf("DRAM bank1: %d pages (%dMByte) ...but not usable yet\n",
213 xpage + 1, ((xpage + 1) * NBPG) / 0x100000);
214
215 /*
216 * Clear currently unused D-RAM area
217 * (For reboot Windows CE clearly)
218 */
219 memset((void*)startaddr, 0, npage * NBPG);
220 memset((void*)(KERNBASE + 0x400), 0,
221 KERNTEXTOFF - KERNBASE - 0x800);
222
223 return npage; /* Return bank0's memory only */
224 }
225
226 void
227 tx_reboot(howto, bootstr)
228 int howto;
229 char *bootstr;
230 {
231 goto *(u_int32_t *)MIPS_RESET_EXC_VEC;
232 }
233
234 int
235 tx39_find_dram(startaddr, endaddr)
236 u_int32_t startaddr; /* kseg1 */
237 u_int32_t endaddr; /* kseg1 */
238 {
239 #define DRAM_MAGIC0 0xac1dcafe
240 #define DRAM_MAGIC1 0x19700220
241 u_int32_t page;
242 int npage;
243
244 page = startaddr;
245 ((volatile int *)page)[0] = DRAM_MAGIC0;
246 ((volatile int *)page)[4] = DRAM_MAGIC1;
247 page += NBPG;
248 for (npage = 0; page < endaddr; page += NBPG, npage++) {
249 if ((((volatile int *)page)[0] == DRAM_MAGIC0 &&
250 ((volatile int *)page)[4] == DRAM_MAGIC1)) {
251 return npage;
252 }
253 }
254 /* no memory in this bank */
255 return 0;
256 }
257
258 void
259 tx_bus_reset()
260 {
261 /* hpcmips port don't use */
262 }
263
264 void
265 tx_cons_init()
266 {
267 int slot;
268
269 #ifdef SERIALCONSSLOT
270 slot = SERIALCONSSLOT;
271 #else
272 slot = TX39_UARTA;
273 #endif
274 if (bootinfo->bi_cnuse & BI_CNUSE_SERIAL) {
275 if(txcom_cnattach(slot, CONSPEED,
276 (TTYDEF_CFLAG & ~(CSIZE | PARENB)) |
277 CS8)) {
278 panic("tx_cons_init: can't attach serial console.");
279 }
280 } else {
281 #if NP7416BUF > 0
282 if(p7416buf_cnattach(TX39_SYSADDR_CS3)) {
283 panic("tx_cons_init: can't init console");
284 }
285 #elif NM38813C > 0
286 if(m38813c_cnattach(TX39_SYSADDR_CARD1)) {
287 panic("tx_cons_init: can't init console");
288 }
289 #endif
290 }
291
292 }
293
294 void
295 tx_device_register(dev, aux)
296 struct device *dev;
297 void *aux;
298 {
299 /* hpcmips port don't use */
300 }
301
302 void
303 tx_conf_register_intr(t, intrt)
304 tx_chipset_tag_t t;
305 void *intrt;
306 {
307 if (tx_chipset.tc_intrt) {
308 panic("duplicate intrt");
309 }
310
311 if (t != &tx_chipset) {
312 panic("bogus tx_chipset_tag");
313 }
314
315 tx_chipset.tc_intrt = intrt;
316 }
317
318 #ifdef TX39_PREFER_FUNCTION
319 tx_chipset_tag_t
320 tx_conf_get_tag()
321 {
322 return (tx_chipset_tag_t)&tx_chipset;
323 }
324
325 txreg_t
326 tx_conf_read(t, reg)
327 tx_chipset_tag_t t;
328 int reg;
329 {
330 return *((txreg_t*)(TX39_SYSADDR_CONFIG_REG_KSEG1 + reg));
331 }
332
333 void
334 tx_conf_write(t, reg, val)
335 tx_chipset_tag_t t;
336 int reg;
337 txreg_t val;
338 {
339 *((txreg_t*)(TX39_SYSADDR_CONFIG_REG_KSEG1 + reg)) = val;
340 }
341 #endif /* TX39_PREFER_FUNCTION */
342
343 int
344 __is_set_print(reg, mask, name)
345 u_int32_t reg;
346 int mask;
347 char *name;
348 {
349 if (reg & mask) {
350 printf("%s ", name);
351 return 1;
352 }
353 return 0;
354 }
355