/[gxemul]/upstream/0.4.4/src/devices/dev_jazz.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Contents of /upstream/0.4.4/src/devices/dev_jazz.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 35 - (show annotations)
Mon Oct 8 16:21:26 2007 UTC (16 years, 8 months ago) by dpavlin
File MIME type: text/plain
File size: 18332 byte(s)
0.4.4
1 /*
2 * Copyright (C) 2004-2007 Anders Gavare. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are met:
6 *
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
12 * 3. The name of the author 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 * $Id: dev_jazz.c,v 1.27 2007/01/28 13:28:27 debug Exp $
29 *
30 * Microsoft Jazz-related stuff (Acer PICA-61, etc).
31 *
32 * TODO/NOTE: This is mostly a quick hack, it doesn't really implement
33 * much of the Jazz architecture. Also, the a0/20 isa-like stuff is
34 * not supposed to be here.
35 *
36 * TODO: Figure out how the int enable mask works; it seems to be shifted
37 * 10 bits (?) according to NetBSD/arc sources.
38 *
39 * TODO: Don't hardcode the timer to 100 Hz.
40 *
41 * JAZZ interrupts 0..14 are connected to MIPS irq 3,
42 * JAZZ interrupt 15 (the timer) is connected to MIPS irq 6,
43 * and ISA interrupts 0..15 are connected to MIPS irq 4.
44 */
45
46 #include <stdio.h>
47 #include <stdlib.h>
48 #include <string.h>
49
50 #include "cpu.h"
51 #include "device.h"
52 #include "devices.h"
53 #include "interrupt.h"
54 #include "machine.h"
55 #include "memory.h"
56 #include "misc.h"
57 #include "timer.h"
58
59 #include "jazz_r4030_dma.h"
60 #include "pica.h"
61
62
63 #define DEV_JAZZ_LENGTH 0x280
64 #define DEV_JAZZ_TICKSHIFT 14
65 #define PICA_TIMER_IRQ 15
66
67 struct jazz_data {
68 struct interrupt mips_irq_3;
69 struct interrupt mips_irq_4;
70 struct interrupt mips_irq_6;
71
72 struct cpu *cpu;
73
74 /* Jazz stuff: */
75 uint32_t int_enable_mask; /* TODO! */
76 uint32_t int_asserted;
77
78 /* ISA stuff: */
79 uint32_t isa_int_enable_mask;
80 uint32_t isa_int_asserted;
81
82 int interval;
83 int interval_start;
84
85 struct timer *timer;
86 int pending_timer_interrupts;
87 int jazz_timer_value;
88 int jazz_timer_current;
89 struct interrupt jazz_timer_irq;
90
91 uint64_t dma_translation_table_base;
92 uint64_t dma_translation_table_limit;
93
94 uint32_t dma0_mode;
95 uint32_t dma0_enable;
96 uint32_t dma0_count;
97 uint32_t dma0_addr;
98
99 uint32_t dma1_mode;
100 /* same for dma1,2,3 actually (TODO) */
101
102 int led;
103 };
104
105
106 void reassert_isa_interrupts(struct jazz_data *d)
107 {
108 if (d->isa_int_asserted & d->isa_int_enable_mask)
109 INTERRUPT_ASSERT(d->mips_irq_4);
110 else
111 INTERRUPT_DEASSERT(d->mips_irq_4);
112 }
113
114
115 void jazz_interrupt_assert(struct interrupt *interrupt)
116 {
117 struct jazz_data *d = interrupt->extra;
118 d->int_asserted |= (1 << interrupt->line);
119
120 if (d->int_asserted & 0x7fff)
121 INTERRUPT_ASSERT(d->mips_irq_3);
122 if (d->int_asserted & 0x8000)
123 INTERRUPT_ASSERT(d->mips_irq_6);
124 }
125 void jazz_interrupt_deassert(struct interrupt *interrupt)
126 {
127 struct jazz_data *d = interrupt->extra;
128 d->int_asserted &= ~(1 << interrupt->line);
129
130 if (!(d->int_asserted & 0x7fff))
131 INTERRUPT_DEASSERT(d->mips_irq_3);
132 if (!(d->int_asserted & 0x8000))
133 INTERRUPT_DEASSERT(d->mips_irq_6);
134 }
135 void jazz_isa_interrupt_assert(struct interrupt *interrupt)
136 {
137 struct jazz_data *d = interrupt->extra;
138 d->isa_int_asserted |= (1 << interrupt->line);
139 reassert_isa_interrupts(d);
140 }
141 void jazz_isa_interrupt_deassert(struct interrupt *interrupt)
142 {
143 struct jazz_data *d = interrupt->extra;
144 d->isa_int_asserted &= ~(1 << interrupt->line);
145 reassert_isa_interrupts(d);
146 }
147
148
149 /*
150 * dev_jazz_dma_controller():
151 */
152 size_t dev_jazz_dma_controller(void *dma_controller_data,
153 unsigned char *data, size_t len, int writeflag)
154 {
155 struct jazz_data *d = (struct jazz_data *) dma_controller_data;
156 struct cpu *cpu = d->cpu;
157 int i, enab_writeflag;
158 int res, ncpy;
159 uint32_t dma_addr;
160 unsigned char tr[sizeof(uint32_t)];
161 uint32_t phys_addr;
162
163 #if 0
164 fatal("[ dev_jazz_dma_controller(): writeflag=%i, len=%i, data =",
165 writeflag, (int)len);
166 for (i=0; i<len; i++)
167 fatal(" %02x", data[i]);
168 fatal(" mode=%08x enable=%08x count=%08x addr=%08x",
169 d->dma0_mode, d->dma0_enable, d->dma0_count, d->dma0_addr);
170 fatal(" table=%08x",
171 d->dma_translation_table_base);
172 fatal(" ]\n");
173 #endif
174
175 if (!(d->dma0_enable & R4030_DMA_ENAB_RUN)) {
176 fatal("[ dev_jazz_dma_controller(): dma not enabled? ]\n");
177 /* return 0; */
178 }
179
180 /* R4030 "write" means write to the device, writeflag as the
181 argument to this function means write to memory. */
182 enab_writeflag = (d->dma0_enable & R4030_DMA_ENAB_WRITE)? 0 : 1;
183 if (enab_writeflag != writeflag) {
184 fatal("[ dev_jazz_dma_controller(): wrong direction? ]\n");
185 return 0;
186 }
187
188 dma_addr = d->dma0_addr;
189 i = 0;
190 while (dma_addr < d->dma0_addr + d->dma0_count && i < (int32_t)len) {
191
192 res = cpu->memory_rw(cpu, cpu->mem,
193 d->dma_translation_table_base + (dma_addr >> 12) * 8,
194 tr, sizeof(tr), 0, PHYSICAL | NO_EXCEPTIONS);
195
196 if (cpu->byte_order==EMUL_BIG_ENDIAN)
197 phys_addr = (tr[0] << 24) + (tr[1] << 16) +
198 (tr[2] << 8) + tr[3];
199 else
200 phys_addr = (tr[3] << 24) + (tr[2] << 16) +
201 (tr[1] << 8) + tr[0];
202 phys_addr &= ~0xfff; /* just in case */
203 phys_addr += (dma_addr & 0xfff);
204
205 /* fatal(" !!! dma_addr = %08x, phys_addr = %08x\n",
206 (int)dma_addr, (int)phys_addr); */
207
208 /* Speed up the copying by copying 16 or 256 bytes: */
209 ncpy = 1;
210 if ((phys_addr & 15) == 0 && i + 15 <= (int32_t)len)
211 ncpy = 15;
212 if ((phys_addr & 255) == 0 && i + 255 <= (int32_t)len)
213 ncpy = 255;
214
215 res = cpu->memory_rw(cpu, cpu->mem, phys_addr,
216 &data[i], ncpy, writeflag, PHYSICAL | NO_EXCEPTIONS);
217
218 dma_addr += ncpy;
219 i += ncpy;
220 }
221
222 /* TODO: Is this correct? */
223 d->dma0_count = 0;
224
225 return len;
226 }
227
228
229 static void timer_tick(struct timer *t, void *extra)
230 {
231 struct jazz_data *d = extra;
232 d->pending_timer_interrupts ++;
233 }
234
235
236 DEVICE_TICK(jazz)
237 {
238 struct jazz_data *d = extra;
239
240 /* Used by NetBSD/arc and OpenBSD/arc: */
241 if (d->interval_start > 0 && d->interval > 0
242 && (d->int_enable_mask & 2) /* Hm? */ ) {
243 d->interval -= 2;
244 if (d->interval <= 0) {
245 /* debug("[ jazz: interval timer interrupt ]\n");
246 INTERRUPT_ASSERT(d->jazz_timer_irq); */
247 }
248
249 /* New timer system: */
250 if (d->pending_timer_interrupts > 0)
251 INTERRUPT_ASSERT(d->jazz_timer_irq);
252 }
253
254 /* Linux? */
255 if (d->jazz_timer_value != 0) {
256 d->jazz_timer_current -= 5;
257 if (d->jazz_timer_current < 1) {
258 d->jazz_timer_current = d->jazz_timer_value;
259 /* INTERRUPT_ASSERT(d->mips_irq_6); */
260 }
261
262 /* New timer system: */
263 if (d->pending_timer_interrupts > 0)
264 INTERRUPT_ASSERT(d->mips_irq_6);
265 }
266 }
267
268
269 DEVICE_ACCESS(jazz)
270 {
271 struct jazz_data *d = (struct jazz_data *) extra;
272 uint64_t idata = 0, odata = 0;
273 int regnr;
274
275 if (writeflag == MEM_WRITE)
276 idata = memory_readmax64(cpu, data, len);
277
278 regnr = relative_addr / sizeof(uint32_t);
279
280 switch (relative_addr) {
281 case R4030_SYS_CONFIG:
282 if (writeflag == MEM_WRITE) {
283 fatal("[ jazz: unimplemented write to R4030_SYS_CONFIG"
284 ", data=0x%08x ]\n", (int)idata);
285 } else {
286 /* Reading the config register should give
287 0x0104 or 0x0410. Why? TODO */
288 odata = 0x104;
289 }
290 break;
291 case R4030_SYS_TL_BASE:
292 if (writeflag == MEM_WRITE) {
293 d->dma_translation_table_base = idata;
294 } else {
295 odata = d->dma_translation_table_base;
296 }
297 break;
298 case R4030_SYS_TL_LIMIT:
299 if (writeflag == MEM_WRITE) {
300 d->dma_translation_table_limit = idata;
301 } else {
302 odata = d->dma_translation_table_limit;
303 }
304 break;
305 case R4030_SYS_TL_IVALID:
306 /* TODO: Does invalidation actually need to be implemented? */
307 break;
308 case R4030_SYS_DMA0_REGS:
309 if (writeflag == MEM_WRITE) {
310 d->dma0_mode = idata;
311 } else {
312 odata = d->dma0_mode;
313 }
314 break;
315 case R4030_SYS_DMA0_REGS + 0x8:
316 if (writeflag == MEM_WRITE) {
317 d->dma0_enable = idata;
318 } else {
319 odata = d->dma0_enable;
320 }
321 break;
322 case R4030_SYS_DMA0_REGS + 0x10:
323 if (writeflag == MEM_WRITE) {
324 d->dma0_count = idata;
325 } else {
326 odata = d->dma0_count;
327 }
328 break;
329 case R4030_SYS_DMA0_REGS + 0x18:
330 if (writeflag == MEM_WRITE) {
331 d->dma0_addr = idata;
332 } else {
333 odata = d->dma0_addr;
334 }
335 break;
336 case R4030_SYS_DMA1_REGS:
337 if (writeflag == MEM_WRITE) {
338 d->dma1_mode = idata;
339 } else {
340 odata = d->dma1_mode;
341 }
342 break;
343 case R4030_SYS_ISA_VECTOR:
344 /* ? */
345 printf("R4030_SYS_ISA_VECTOR: w=%i\n", writeflag);
346 {
347 uint32_t x = d->isa_int_asserted
348 & d->isa_int_enable_mask;
349 odata = 0;
350 while (odata < 16) {
351 if (x & (1 << odata))
352 break;
353 odata ++;
354 }
355 if (odata >= 16)
356 odata = 0;
357 }
358 break;
359 case R4030_SYS_IT_VALUE: /* Interval timer reload value */
360 if (writeflag == MEM_WRITE) {
361 d->interval_start = idata;
362 d->interval = d->interval_start;
363 } else
364 odata = d->interval_start;
365 break;
366 case R4030_SYS_IT_STAT:
367 /* Accessing this word seems to acknowledge interrupts? */
368 INTERRUPT_DEASSERT(d->jazz_timer_irq);
369 if (d->pending_timer_interrupts > 0)
370 d->pending_timer_interrupts --;
371
372 if (writeflag == MEM_WRITE)
373 d->interval = idata;
374 else
375 odata = d->interval;
376 d->interval = d->interval_start;
377 break;
378 case R4030_SYS_EXT_IMASK:
379 if (writeflag == MEM_WRITE) {
380 int old_assert_3 = (0x7fff &
381 d->int_asserted & d->int_enable_mask);
382 int old_assert_6 = (0x8000 &
383 d->int_asserted & d->int_enable_mask);
384 int new_assert_3, new_assert_6;
385
386 d->int_enable_mask = idata;
387
388 new_assert_3 =
389 d->int_asserted & d->int_enable_mask & 0x7fff;
390 new_assert_6 =
391 d->int_asserted & d->int_enable_mask & 0x8000;
392
393 if (old_assert_3 && !new_assert_3)
394 INTERRUPT_DEASSERT(d->mips_irq_3);
395 else if (!old_assert_3 && new_assert_3)
396 INTERRUPT_ASSERT(d->mips_irq_3);
397
398 if (old_assert_6 && !new_assert_6)
399 INTERRUPT_DEASSERT(d->mips_irq_6);
400 else if (!old_assert_6 && new_assert_6)
401 INTERRUPT_ASSERT(d->mips_irq_6);
402 } else
403 odata = d->int_enable_mask;
404 break;
405 default:
406 if (writeflag == MEM_WRITE) {
407 fatal("[ jazz: unimplemented write to address 0x%x"
408 ", data=0x%02x ]\n", (int)relative_addr,
409 (int)idata);
410 } else {
411 fatal("[ jazz: unimplemented read from address 0x%x"
412 " ]\n", (int)relative_addr);
413 }
414 }
415
416 if (writeflag == MEM_READ)
417 memory_writemax64(cpu, data, len, odata);
418
419 return 1;
420 }
421
422
423 DEVICE_ACCESS(jazz_led)
424 {
425 struct jazz_data *d = (struct jazz_data *) extra;
426 uint64_t idata = 0, odata = 0;
427 int regnr;
428
429 if (writeflag == MEM_WRITE)
430 idata = memory_readmax64(cpu, data, len);
431
432 regnr = relative_addr / sizeof(uint32_t);
433
434 switch (relative_addr) {
435 case 0:
436 if (writeflag == MEM_WRITE) {
437 d->led = idata;
438 debug("[ jazz_led: write to LED: 0x%02x ]\n",
439 (int)idata);
440 } else {
441 odata = d->led;
442 }
443 break;
444 default:
445 if (writeflag == MEM_WRITE) {
446 fatal("[ jazz_led: unimplemented write to address 0x%x"
447 ", data=0x%02x ]\n", (int)relative_addr,
448 (int)idata);
449 } else {
450 fatal("[ jazz_led: unimplemented read from address 0x%x"
451 " ]\n", (int)relative_addr);
452 }
453 }
454
455 if (writeflag == MEM_READ)
456 memory_writemax64(cpu, data, len, odata);
457
458 return 1;
459 }
460
461
462 /*
463 * dev_jazz_a0_access():
464 *
465 * ISA interrupt stuff, high 8 interrupts.
466 *
467 * TODO: use isa8 stuff instead!
468 */
469 DEVICE_ACCESS(jazz_a0)
470 {
471 struct jazz_data *d = (struct jazz_data *) extra;
472 uint64_t idata = 0, odata = 0;
473
474 if (writeflag == MEM_WRITE)
475 idata = memory_readmax64(cpu, data, len);
476
477 switch (relative_addr) {
478 case 0:
479 if (writeflag == MEM_WRITE) {
480 /* TODO: only if idata == 0x20? */
481 d->isa_int_asserted &= 0xff;
482
483 reassert_isa_interrupts(d);
484 }
485 break;
486 case 1:
487 if (writeflag == MEM_WRITE) {
488 idata = ((idata ^ 0xff) & 0xff) << 8;
489 d->isa_int_enable_mask =
490 (d->isa_int_enable_mask & 0xff) | idata;
491 debug("[ jazz_isa_a0: setting isa_int_enable_mask "
492 "to 0x%04x ]\n", (int)d->isa_int_enable_mask);
493
494 reassert_isa_interrupts(d);
495 } else
496 odata = d->isa_int_enable_mask;
497 break;
498 default:
499 if (writeflag == MEM_WRITE) {
500 fatal("[ jazz_isa_a0: unimplemented write to "
501 "address 0x%x, data=0x%02x ]\n",
502 (int)relative_addr, (int)idata);
503 } else {
504 fatal("[ jazz_isa_a0: unimplemented read from "
505 "address 0x%x ]\n", (int)relative_addr);
506 }
507 }
508
509 if (writeflag == MEM_READ)
510 memory_writemax64(cpu, data, len, odata);
511
512 return 1;
513 }
514
515
516 /*
517 * dev_jazz_20_access():
518 *
519 * ISA interrupt stuff, low 8 interrupts.
520 */
521 DEVICE_ACCESS(jazz_20)
522 {
523 struct jazz_data *d = (struct jazz_data *) extra;
524 uint64_t idata = 0, odata = 0;
525
526 if (writeflag == MEM_WRITE)
527 idata = memory_readmax64(cpu, data, len);
528
529 switch (relative_addr) {
530 case 0:
531 if (writeflag == MEM_WRITE) {
532 /* TODO: only if idata == 0x20? */
533 d->isa_int_asserted &= 0xff00;
534 reassert_isa_interrupts(d);
535 }
536 break;
537 case 1:
538 if (writeflag == MEM_WRITE) {
539 idata = (idata ^ 0xff) & 0xff;
540 d->isa_int_enable_mask =
541 (d->isa_int_enable_mask & 0xff00) | idata;
542 debug("[ jazz_isa_20: setting isa_int_enable_mask "
543 "to 0x%04x ]\n", (int)d->isa_int_enable_mask);
544
545 reassert_isa_interrupts(d);
546 } else
547 odata = d->isa_int_enable_mask;
548 break;
549 default:
550 if (writeflag == MEM_WRITE) {
551 fatal("[ jazz_isa_20: unimplemented write to "
552 "address 0x%x, data=0x%02x ]\n",
553 (int)relative_addr, (int)idata);
554 } else {
555 fatal("[ jazz_isa_20: unimplemented read from "
556 "address 0x%x ]\n", (int)relative_addr);
557 }
558 }
559
560 if (writeflag == MEM_READ)
561 memory_writemax64(cpu, data, len, odata);
562
563 return 1;
564 }
565
566
567 /*
568 * dev_jazz_jazzio_access():
569 *
570 * See jazzio_intr() in NetBSD's
571 * /usr/src/sys/arch/arc/jazz/jazzio.c for more info.
572 */
573 DEVICE_ACCESS(jazz_jazzio)
574 {
575 struct jazz_data *d = (struct jazz_data *) extra;
576 uint64_t idata = 0, odata = 0;
577 int i, v;
578
579 if (writeflag == MEM_WRITE)
580 idata = memory_readmax64(cpu, data, len);
581
582 switch (relative_addr) {
583 case 0:
584 v = 0;
585 for (i=0; i<15; i++) {
586 if (d->int_asserted & (1<<i)) {
587 v = i+1;
588 break;
589 }
590 }
591 odata = v << 2;
592 break;
593 case 2:
594 /* TODO: Should this be here?! */
595
596 if (writeflag == MEM_WRITE)
597 d->jazz_timer_value = idata;
598 else
599 odata = d->jazz_timer_value;
600 break;
601 default:
602 if (writeflag == MEM_WRITE) {
603 fatal("[ jazzio: unimplemented write to address 0x%x"
604 ", data=0x%02x ]\n", (int)relative_addr,
605 (int)idata);
606 } else {
607 fatal("[ jazzio: unimplemented read from address 0x%x"
608 " ]\n", (int)relative_addr);
609 }
610 }
611
612 /* This is needed by Windows NT during startup: */
613 INTERRUPT_DEASSERT(d->mips_irq_3);
614
615 if (writeflag == MEM_READ)
616 memory_writemax64(cpu, data, len, odata);
617
618 return 1;
619 }
620
621
622 DEVINIT(jazz)
623 {
624 char tmpstr[300];
625 int i;
626 struct jazz_data *d = malloc(sizeof(struct jazz_data));
627 if (d == NULL) {
628 fprintf(stderr, "out of memory\n");
629 exit(1);
630 }
631 memset(d, 0, sizeof(struct jazz_data));
632
633 d->cpu = devinit->machine->cpus[0]; /* TODO */
634
635 d->isa_int_enable_mask = 0xffff;
636
637 /*
638 * Register 16 native JAZZ irqs, and 16 ISA irqs:
639 *
640 * emul[x].machine[y].cpu[z].jazz.%i (native)
641 * emul[x].machine[y].cpu[z].jazz.isa.%i (ISA)
642 */
643 for (i=0; i<16; i++) {
644 struct interrupt template;
645 char n[300];
646 snprintf(n, sizeof(n), "%s.jazz.%i",
647 devinit->interrupt_path, i);
648 memset(&template, 0, sizeof(template));
649 template.line = i;
650 template.name = n;
651 template.extra = d;
652 template.interrupt_assert = jazz_interrupt_assert;
653 template.interrupt_deassert = jazz_interrupt_deassert;
654 interrupt_handler_register(&template);
655 }
656 for (i=0; i<16; i++) {
657 struct interrupt template;
658 char n[300];
659 snprintf(n, sizeof(n), "%s.jazz.isa.%i",
660 devinit->interrupt_path, i);
661 memset(&template, 0, sizeof(template));
662 template.line = i;
663 template.name = n;
664 template.extra = d;
665 template.interrupt_assert = jazz_isa_interrupt_assert;
666 template.interrupt_deassert = jazz_isa_interrupt_deassert;
667 interrupt_handler_register(&template);
668 }
669
670 /* Connect to MIPS CPU interrupt lines: */
671 snprintf(tmpstr, sizeof(tmpstr), "%s.3", devinit->interrupt_path);
672 INTERRUPT_CONNECT(tmpstr, d->mips_irq_3);
673 snprintf(tmpstr, sizeof(tmpstr), "%s.4", devinit->interrupt_path);
674 INTERRUPT_CONNECT(tmpstr, d->mips_irq_4);
675 snprintf(tmpstr, sizeof(tmpstr), "%s.6", devinit->interrupt_path);
676 INTERRUPT_CONNECT(tmpstr, d->mips_irq_6);
677
678 /* Connect to JAZZ timer interrupt: */
679 snprintf(tmpstr, sizeof(tmpstr), "%s.jazz.%i",
680 devinit->interrupt_path, PICA_TIMER_IRQ);
681 INTERRUPT_CONNECT(tmpstr, d->jazz_timer_irq);
682
683 memory_device_register(devinit->machine->memory, "jazz",
684 devinit->addr, DEV_JAZZ_LENGTH,
685 dev_jazz_access, (void *)d, DM_DEFAULT, NULL);
686
687 /* At least for Magnum and Pica-61: */
688 memory_device_register(devinit->machine->memory, "jazz_led",
689 0x08000f000ULL, 4, dev_jazz_led_access, (void *)d,
690 DM_DEFAULT, NULL);
691
692 memory_device_register(devinit->machine->memory, "jazz_isa_20",
693 0x90000020ULL, 2, dev_jazz_20_access, (void *)d, DM_DEFAULT, NULL);
694
695 memory_device_register(devinit->machine->memory, "jazz_isa_a0",
696 0x900000a0ULL, 2, dev_jazz_a0_access, (void *)d, DM_DEFAULT, NULL);
697
698 memory_device_register(devinit->machine->memory, "pica_jazzio",
699 0xf0000000ULL, 4, dev_jazz_jazzio_access, (void *)d,
700 DM_DEFAULT, NULL);
701
702 /* Add a timer, hardcoded to 100 Hz. TODO: Don't hardcode! */
703 d->timer = timer_add(100.0, timer_tick, d);
704 machine_add_tickfunction(devinit->machine, dev_jazz_tick,
705 d, DEV_JAZZ_TICKSHIFT, 0.0);
706
707 devinit->return_ptr = d;
708
709 return 1;
710 }
711

  ViewVC Help
Powered by ViewVC 1.1.26