|
|
1.1 root 1: #include <sys/types.h>
2: #include <a.out.h>
3: #include <stdio.h>
4:
5: #include <exec/types.h>
6: #include <exec/execbase.h>
7: #include <exec/memory.h>
8: #include <libraries/configregs.h>
9: #include <libraries/expansionbase.h>
10:
11: #include <inline/exec.h>
12: #include <inline/expansion.h>
13:
14: struct ExpansionBase *ExpansionBase;
15:
16: #undef __LDPGSZ
17: #define __LDPGSZ 8192
18:
19: void get_mem_config (void **fastmem_start, u_long *fastmem_size, u_long *chipmem_size);
20:
21: int
22: main (int argc, char *argv[])
23: {
24: struct exec e;
25: int fd;
26:
27: if (argc >= 2)
28: {
29: if ((fd = open (argv[1], 0)) >= 0)
30: {
31: if (read (fd, &e, sizeof (e)) == sizeof (e))
32: {
33: if (e.a_magic == NMAGIC)
34: {
35: u_char *kernel;
36: int text_size;
37: struct ConfigDev *cd;
38: int num_cd;
39:
40: ExpansionBase= (struct ExpansionBase *) OpenLibrary ("expansion.library", 0);
41: if (! ExpansionBase) /* not supposed to fail... */
42: abort();
43: for (cd = 0, num_cd = 0; cd = FindConfigDev (cd, -1, -1); num_cd++) ;
44:
45: text_size = (e.a_text + __LDPGSZ - 1) & (-__LDPGSZ);
46: kernel = (u_char *) malloc (text_size + e.a_data + e.a_bss
47: + num_cd*sizeof(*cd) + 4);
48:
49: if (kernel)
50: {
51: if (read (fd, kernel, e.a_text) == e.a_text
52: && read (fd, kernel + text_size, e.a_data) == e.a_data)
53: {
54: int *knum_cd;
55: struct ConfigDev *kcd;
56: void *fastmem_start;
57: u_long fastmem_size, chipmem_size;
58:
59: get_mem_config (&fastmem_start, &fastmem_size, &chipmem_size);
60:
61: if (argc == 3 && !strcmp (argv[2], "-k"))
62: {
63: fastmem_start += 4*1024*1024;
64: fastmem_size -= 4*1024*1024;
65: }
66:
67: printf ("Using %dM FASTMEM at 0x%x, %dM CHIPMEM\n",
68: fastmem_size>>20, fastmem_start, chipmem_size>>20);
69: /* give them a chance to read the information... */
70: sleep(2);
71:
72: bzero (kernel + text_size + e.a_data, e.a_bss);
73: knum_cd = (int *) (kernel + text_size + e.a_data + e.a_bss);
74: *knum_cd = num_cd;
75: if (num_cd)
76: for (kcd = (struct ConfigDev *) (knum_cd+1);
77: cd = FindConfigDev (cd, -1, -1);
78: *kcd++ = *cd) ;
79: startit (kernel,
80: text_size + e.a_data + e.a_bss + num_cd*sizeof(*cd) + 4,
81: e.a_entry, fastmem_start,
82: fastmem_size, chipmem_size);
83: }
84: else
85: fprintf (stderr, "Executable corrupt!\n");
86: }
87: else
88: fprintf (stderr, "Out of memory! (%d)\n", text_size + e.a_data + e.a_bss
89: + num_cd*sizeof(*cd) + 4);
90: }
91: else
92: fprintf (stderr, "Unsupported executable: %o\n", e.a_magic);
93: }
94: else
95: fprintf (stderr, "Can't read header of %s\n", argv[1]);
96:
97: close (fd);
98: }
99: else
100: perror ("open");
101: }
102: else
103: fprintf (stderr, "%0 some-vmunix\n", argv[0]);
104: }
105:
106:
107: void
108: get_mem_config (void **fastmem_start, u_long *fastmem_size, u_long *chipmem_size)
109: {
110: extern struct ExecBase *SysBase;
111: struct MemHeader *mh, *nmh;
112:
113: *fastmem_size = 0;
114: *chipmem_size = 0;
115:
116: /* walk thru the exec memory list */
117: Forbid ();
118: for (mh = (struct MemHeader *) SysBase->MemList.lh_Head;
119: nmh = (struct MemHeader *) mh->mh_Node.ln_Succ;
120: mh = nmh)
121: {
122: if (mh->mh_Attributes & MEMF_CHIP)
123: {
124: /* there should hardly be more than one entry for chip mem, but
125: handle it the same nevertheless */
126: if ((u_int)mh->mh_Upper - (u_int)mh->mh_Lower > *chipmem_size)
127: {
128: *chipmem_size = (u_int)mh->mh_Upper - (u_int)mh->mh_Lower;
129: /* round to multiple of 512K */
130: *chipmem_size = (*chipmem_size + 512*1024 - 1) & -(512*1024);
131:
132: /* chipmem always starts at 0, so don't remember start
133: address */
134: }
135: }
136: else
137: {
138: if ((u_int)mh->mh_Upper - (u_int)mh->mh_Lower > *fastmem_size)
139: {
140: u_int start = (u_int) mh->mh_Lower;
141: u_int end = (u_int) mh->mh_Upper;
142:
143: /* some heuristics.. */
144: start &= -__LDPGSZ;
145: /* get the mem back stolen by incore kickstart on A3000 with
146: V36 bootrom. */
147: if (end == 0x07f80000)
148: end = 0x08000000;
149:
150: *fastmem_size = end - start;
151: *fastmem_start = (void *)start;
152: }
153: }
154: }
155: Permit();
156: }
157:
158:
159:
160:
161: asm ("
162: .set ABSEXECBASE,4
163:
164: .text
165: .globl _startit
166:
167: _startit:
168: movel sp,a3
169: movel 4:w,a6
170: lea pc@(start_super-.+2),a5
171: jmp a6@(-0x1e) | supervisor-call
172:
173: start_super:
174: movew #0x2700,sr
175:
176: | the BSD kernel wants values into the following registers:
177: | a0: fastmem-start
178: | d0: fastmem-size
179: | d1: chipmem-size
180:
181: movel a3@(4),a1 | loaded kernel
182: movel a3@(8),d2 | length of loaded kernel
183: movel a3@(12),a2 | entry point
184: movel a3@(16),a0 | fastmem-start
185: movel a3@(20),d0 | fastmem-size
186: movel a3@(24),d1 | chipmem-size
187: subl a4,a4 | target, load to 0
188:
189: lea pc@(zero-.+2),a3
190: pmove a3@,tc | Turn off MMU
191: lea pc@(nullrp-.+2),a3
192: pmove a3@,crp | Turn off MMU some more
193: pmove a3@,srp | Really, really, turn off MMU
194:
195: | Turn off 68030 TT registers
196:
197: btst #2,(ABSEXECBASE)@(0x129) | AFB_68030,SysBase->AttnFlags
198: beq nott | Skip TT registers if not 68030
199: lea pc@(zero-.+2),a3
200: .word 0xf013,0x0800 | pmove a3@,tt0 (gas only knows about 68851 ops..)
201: .word 0xf013,0x0c00 | pmove a3@,tt1 (gas only knows about 68851 ops..)
202:
203: nott:
204:
205: movew #(1<<9),0xdff096 | disable DMA
206:
207: L0:
208: moveb a1@+,a4@+
209: subl #1,d2
210: bcc L0
211:
212:
213: jmp a2@
214:
215:
216: | A do-nothing MMU root pointer (includes the following long as well)
217:
218: nullrp: .long 0x7fff0001
219: zero: .long 0
220:
221:
222: ");
223:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.