|
|
1.1 root 1: /*
2: * UAE - The Un*x Amiga Emulator
3: *
4: * A "replacement" for a missing Kickstart
5: * Warning! Q&D
6: *
7: * (c) 1995 Bernd Schmidt
8: */
9:
10: #include "sysconfig.h"
11: #include "sysdeps.h"
12:
13: #include "config.h"
14: #include "options.h"
15: #include "memory.h"
16: #include "custom.h"
1.1.1.2 ! root 17: #include "readcpu.h"
1.1 root 18: #include "newcpu.h"
19: #include "cia.h"
20: #include "disk.h"
21: #include "ersatz.h"
22:
23: #define EOP_INIT 0
24: #define EOP_NIMP 1
25: #define EOP_SERVEINT 2
26: #define EOP_DOIO 3
27: #define EOP_OPENLIB 4
28: #define EOP_AVAILMEM 5
29: #define EOP_ALLOCMEM 6
30: #define EOP_ALLOCABS 7
31:
32: void init_ersatz_rom (UBYTE *data)
33: {
34: fprintf(stderr, "Trying to use Kickstart replacement.\n");
35: *data++ = 0x00; *data++ = 0x08; /* initial SP */
36: *data++ = 0x00; *data++ = 0x00;
37: *data++ = 0x00; *data++ = 0xF8; /* initial PC */
38: *data++ = 0x00; *data++ = 0x08;
39:
40: *data++ = 0xFF; *data++ = 0x0D;
41: *data++ = 0x00; *data++ = EOP_INIT;
42: *data++ = 0xFF; *data++ = 0x0D;
43: *data++ = 0x00; *data++ = EOP_NIMP;
44:
45: *data++ = 0xFF; *data++ = 0x0D;
46: *data++ = 0x00; *data++ = EOP_DOIO;
47: *data++ = 0x4E; *data++ = 0x75;
48: *data++ = 0xFF; *data++ = 0x0D;
49:
50: *data++ = 0x00; *data++ = EOP_SERVEINT;
51: *data++ = 0x4E; *data++ = 0x73;
52: *data++ = 0xFF; *data++ = 0x0D;
53: *data++ = 0x00; *data++ = EOP_AVAILMEM;
54:
55: *data++ = 0x4E; *data++ = 0x75;
56: *data++ = 0xFF; *data++ = 0x0D;
57: *data++ = 0x00; *data++ = EOP_ALLOCMEM;
58: *data++ = 0x4E; *data++ = 0x75;
59:
60: *data++ = 0xFF; *data++ = 0x0D;
61: *data++ = 0x00; *data++ = EOP_ALLOCABS;
62: *data++ = 0x4E; *data++ = 0x75;
63: }
64:
65: static void ersatz_doio (void)
66: {
1.1.1.2 ! root 67: CPTR request = m68k_areg(regs, 1);
1.1 root 68: switch (get_word (request + 0x1C)) {
69: case 9: /* TD_MOTOR is harmless */
70: case 2: case 0x8002: /* READ commands */
71: break;
72:
73: default:
74: fprintf(stderr, "Only CMD_READ supported in DoIO()\n");
75: abort();
76: }
77: {
78: CPTR dest = get_long (request + 0x28);
79: int start = get_long (request + 0x2C) / 512;
80: int nsecs = get_long (request + 0x24) / 512;
81: int tr = start / 11;
82: int sec = start % 11;
83: while (nsecs--) {
84: DISK_ersatz_read (tr, sec, dest);
85: dest += 512;
86: if (++sec == 11)
87: sec = 0, tr++;
88: }
89: }
90: }
91:
92: static void ersatz_init (void)
93: {
94: int f;
95: CPTR request;
96: CPTR a;
97:
98: regs.s = 0;
99: /* Set some interrupt vectors */
100: for (a = 8; a < 0xC0; a += 4) {
101: put_long (a, 0xF80016);
102: }
103: regs.isp = regs.msp = regs.usp = 0x800;
1.1.1.2 ! root 104: m68k_areg(regs, 7) = 0x80000;
1.1 root 105: regs.intmask = 0;
106:
107: /* Build a dummy execbase */
1.1.1.2 ! root 108: put_long (4, m68k_areg(regs, 6) = 0x676);
1.1 root 109: put_byte (0x676 + 0x129, 0);
110: for (f = 1; f < 105; f++) {
111: put_word (0x676 - 6*f, 0x4EF9);
112: put_long (0x676 - 6*f + 2, 0xF8000C);
113: }
114: /* Some "supported" functions */
115: put_long (0x676 - 456 + 2, 0xF80010);
116: put_long (0x676 - 216 + 2, 0xF8001C);
117: put_long (0x676 - 198 + 2, 0xF80022);
118: put_long (0x676 - 204 + 2, 0xF80028);
119: put_long (0x676 - 210 + 2, 0xF80026);
120:
121: /* Build an IORequest */
122: request = 0x800;
123: put_word (request + 0x1C, 2);
124: put_long (request + 0x28, 0x4000);
125: put_long (request + 0x2C, 0);
126: put_long (request + 0x24, 0x200 * 4);
1.1.1.2 ! root 127: m68k_areg(regs, 1) = request;
1.1 root 128: ersatz_doio ();
129: m68k_setpc (0x400C);
130:
131: /* Init the hardware */
1.1.1.2 ! root 132: put_long (0x3000, 0xFFFFFFFEul);
1.1 root 133: put_long (0xDFF080, 0x3000);
134: put_word (0xDFF088, 0);
135: put_word (0xDFF096, 0xE390);
136: put_word (0xDFF09A, 0xE02C);
137: put_word (0xDFF09E, 0x0000);
138: put_word (0xDFF092, 0x0038);
139: put_word (0xDFF094, 0x00D0);
140: put_word (0xDFF08E, 0x2C81);
141: put_word (0xDFF090, 0xF4C1);
142: put_word (0xDFF02A, 0x8000);
143:
144: put_byte (0xBFD100, 0xF7);
145: put_byte (0xBFEE01, 0);
146: put_byte (0xBFEF01, 0x08);
147: put_byte (0xBFDE00, 0x04);
148: put_byte (0xBFDF00, 0x84);
149: put_byte (0xBFDD00, 0x9F);
150: put_byte (0xBFED01, 0x9F);
151: }
152:
153: void ersatz_perform (UWORD what)
154: {
155: switch (what) {
156: case EOP_INIT:
157: ersatz_init ();
158: break;
159:
160: case EOP_SERVEINT:
161: /* Just reset all the interrupt request bits */
162: put_word (0xDFF09C, get_word (0xDFF01E) & 0x3FFF);
163: break;
164:
165: case EOP_DOIO:
166: ersatz_doio ();
167: break;
168:
169: case EOP_AVAILMEM:
1.1.1.2 ! root 170: m68k_dreg(regs, 0) = m68k_dreg(regs, 1) & 4 ? 0 : 0x70000;
1.1 root 171: break;
172:
173: case EOP_ALLOCMEM:
1.1.1.2 ! root 174: m68k_dreg(regs, 0) = m68k_dreg(regs, 1) & 4 ? 0 : 0x0F000;
1.1 root 175: break;
176:
177: case EOP_ALLOCABS:
1.1.1.2 ! root 178: m68k_dreg(regs, 0) = m68k_areg(regs, 1);
1.1 root 179: break;
180:
181: case EOP_NIMP:
182: fprintf(stderr, "Unimplemented Kickstart function called\n");
183: abort ();
184: case EOP_OPENLIB:
185: default:
186: fprintf(stderr, "Internal error. Giving up.\n");
187: abort ();
188: }
189: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.