/[gxemul]/trunk/src/file.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 /trunk/src/file.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 30 - (show annotations)
Mon Oct 8 16:20:40 2007 UTC (16 years, 6 months ago) by dpavlin
File MIME type: text/plain
File size: 58034 byte(s)
++ trunk/HISTORY	(local)
$Id: HISTORY,v 1.1325 2006/08/15 15:38:37 debug Exp $
20060723	More Transputer instructions (pfix, nfix, opr, mint, ldl, ldlp,
		eqc, rev, ajw, stl, stlf, sthf, sub, ldnl, ldnlp, ldpi, move,
		wcnt, add, bcnt).
		Adding more SPARC instructions (andcc, addcc, bl, rdpr).
		Progress on the igsfb framebuffer used by NetBSD/netwinder.
		Enabling 8-bit fills in dev_fb.
		NetBSD/netwinder 3.0.1 can now run from a disk image :-)
20060724	Cleanup/performance fix for 64-bit virtual translation table
		updates (by removing the "timestamp" stuff). A full NetBSD/pmax
		3.0.1 install for R4400 has dropped from 667 seconds to 584 :)
		Fixing the igsfb "almost vga" color (it is 24-bit, not 18-bit).
		Adding some MIPS instruction combinations (3*lw, and 3*addu).
		The 8048 keyboard now turns off interrupt enable between the
		KBR_ACK and the KBR_RSTDONE, to work better with Linux 2.6.
		Not causing PPC DEC interrupts if PPC_NO_DEC is set for a
		specific CPU; NetBSD/bebox gets slightly further than before.
		Adding some more SPARC instructions: branches, udiv.
20060725	Refreshing dev_pckbc.c a little.
		Cleanups for the SH emulation mode, and adding the first
		"compact" (16-bit) instructions: various simple movs, nop,
		shll, stc, or, ldc.
20060726	Adding dummy "pcn" (AMD PCnet NIC) PCI glue.
20060727	Various cleanups; removing stuff from cpu.h, such as
		running_translated (not really meaningful anymore), and
		page flags (breaking into the debugger clears all translations
		anyway).
		Minor MIPS instruction combination updates.
20060807	Expanding the 3*sw and 3*lw MIPS instruction combinations to
		work with 2* and 4* too, resulting in a minor performance gain.
		Implementing a usleep hack for the RM52xx/MIPS32/MIPS64 "wait"
		instruction (when emulating 1 cpu).
20060808	Experimenting with some more MIPS instruction combinations.
		Implementing support for showing a (hardcoded 12x22) text
		cursor in igsfb.
20060809	Simplifying the NetBSD/evbmips (Malta) install instructions
		somewhat (by using a NetBSD/pmax ramdisk install kernel).
20060812	Experimenting more with the MIPS 'wait' instruction.
		PCI configuration register writes can now be handled, which
		allow PCI IDE controllers to work with NetBSD/Malta 3.0.1 and
		NetBSD/cobalt 3.0.1. (Previously only NetBSD 2.1 worked.)
20060813	Updating dev_gt.c based on numbers from Alec Voropay, to enable
		Linux 2.6 to use PCI on Malta.
		Continuing on Algor interrupt stuff.
20060814	Adding support for routing ISA interrupts to two different
		interrupts, making it possible to run NetBSD/algor :-)
20060814-15	Testing for the release.

==============  RELEASE 0.4.2  ==============


1 /*
2 * Copyright (C) 2003-2006 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: file.c,v 1.134 2006/08/12 11:43:12 debug Exp $
29 *
30 * This file contains functions which load executable images into (emulated)
31 * memory. File formats recognized so far are:
32 *
33 * a.out old format used by OpenBSD 2.x pmax kernels
34 * Mach-O MacOS X format, etc.
35 * ecoff old format used by Ultrix, Windows NT, etc
36 * srec Motorola SREC format
37 * raw raw binaries, "address:[skiplen:[entrypoint:]]filename"
38 * ELF 32-bit and 64-bit ELFs
39 *
40 * If a file is not of one of the above mentioned formats, it is assumed
41 * to be symbol data generated by 'nm' or 'nm -S'.
42 */
43
44 #include <stdio.h>
45 #include <stdlib.h>
46 #include <string.h>
47 #include <sys/types.h>
48
49 #include "cpu.h"
50 #include "exec_aout.h"
51 #include "exec_ecoff.h"
52 #include "exec_elf.h"
53 #include "machine.h"
54 #include "memory.h"
55 #include "misc.h"
56 #include "symbol.h"
57
58
59 extern int quiet_mode;
60 extern int verbose;
61
62
63 /* ELF machine types as strings: (same as exec_elf.h) */
64 #define N_ELF_MACHINE_TYPES 84
65 static char *elf_machine_type[N_ELF_MACHINE_TYPES] = {
66 "NONE", "M32", "SPARC", "386", /* 0..3 */
67 "68K", "88K", "486", "860", /* 4..7 */
68 "MIPS", "S370", "MIPS_RS3_LE", "RS6000", /* 8..11 */
69 "unknown12", "unknown13", "unknown14", "PARISC", /* 12..15 */
70 "NCUBE", "VPP500", "SPARC32PLUS", "960", /* 16..19 */
71 "PPC", "PPC64", "unknown22", "unknown23", /* 20..23 */
72 "unknown24", "unknown25", "unknown26", "unknown27", /* 24..27 */
73 "unknown28", "unknown29", "unknown30", "unknown31", /* 28..31 */
74 "unknown32", "unknown33", "unknown34", "unknown35", /* 32..35 */
75 "V800", "FR20", "RH32", "RCE", /* 36..39 */
76 "ARM", "ALPHA", "SH", "SPARCV9", /* 40..43 */
77 "TRICORE", "ARC", "H8_300", "H8_300H", /* 44..47 */
78 "H8S", "H8_500", "IA_64", "MIPS_X", /* 48..51 */
79 "COLDFIRE", "68HC12", "unknown54", "unknown55", /* 52..55 */
80 "unknown56", "unknown57", "unknown58", "unknown59", /* 56..59 */
81 "unknown60", "unknown61", "AMD64", "unknown63", /* 60..63 */
82 "unknown64", "unknown65", "unknown66", "unknown67", /* 64..67 */
83 "unknown68", "unknown69", "unknown70", "unknown71", /* 68..71 */
84 "unknown72", "unknown73", "unknown74", "unknown75", /* 72..75 */
85 "unknown76", "unknown77", "unknown78", "unknown79", /* 76..79 */
86 "unknown80", "unknown81", "unknown82", "AVR" /* 80..83 */
87 };
88
89
90 /*
91 * This should be increased by every routine here that actually loads an
92 * executable file into memory. (For example, loading a symbol file should
93 * NOT increase this.)
94 */
95 static int n_executables_loaded = 0;
96
97
98 struct aout_symbol {
99 uint32_t strindex;
100 uint32_t type;
101 uint32_t addr;
102 };
103
104 /* Special symbol format used by Microsoft-ish COFF files: */
105 struct ms_sym {
106 unsigned char name[8];
107 unsigned char value[4];
108 unsigned char section[2];
109 unsigned char type[2];
110 unsigned char storage_class;
111 unsigned char n_aux_syms;
112 };
113
114
115 #define unencode(var,dataptr,typ) { \
116 int Wi; unsigned char Wb; \
117 unsigned char *Wp = (unsigned char *) dataptr; \
118 int Wlen = sizeof(typ); \
119 var = 0; \
120 for (Wi=0; Wi<Wlen; Wi++) { \
121 if (encoding == ELFDATA2LSB) \
122 Wb = Wp[Wlen-1 - Wi]; \
123 else \
124 Wb = Wp[Wi]; \
125 if (Wi == 0 && (Wb & 0x80)) { \
126 var --; /* set var to -1 :-) */ \
127 var <<= 8; \
128 } \
129 var |= Wb; \
130 if (Wi < Wlen-1) \
131 var <<= 8; \
132 } \
133 }
134
135
136 #define AOUT_FLAG_DECOSF1 1
137 #define AOUT_FLAG_FROM_BEGINNING 2
138 #define AOUT_FLAG_VADDR_ZERO_HACK 4
139 #define AOUT_FLAG_NO_SIZES 8
140 /*
141 * file_load_aout():
142 *
143 * Loads an a.out binary image into the emulated memory. The entry point
144 * (read from the a.out header) is stored in the specified CPU's registers.
145 *
146 * TODO: This has to be rewritten / corrected to support multiple a.out
147 * formats, where text/data are aligned differently.
148 */
149 static void file_load_aout(struct machine *m, struct memory *mem,
150 char *filename, int flags,
151 uint64_t *entrypointp, int arch, int *byte_orderp)
152 {
153 struct exec aout_header;
154 FILE *f;
155 int len;
156 int encoding = ELFDATA2LSB;
157 uint32_t entry, datasize, textsize;
158 int32_t symbsize = 0;
159 uint32_t vaddr, total_len;
160 unsigned char buf[65536];
161 unsigned char *syms;
162
163 if (m->cpus[0]->byte_order == EMUL_BIG_ENDIAN)
164 encoding = ELFDATA2MSB;
165
166 f = fopen(filename, "r");
167 if (f == NULL) {
168 perror(filename);
169 exit(1);
170 }
171
172 if (flags & AOUT_FLAG_DECOSF1) {
173 fread(&buf, 1, 32, f);
174 vaddr = buf[16] + (buf[17] << 8) +
175 (buf[18] << 16) + ((uint64_t)buf[19] << 24);
176 entry = buf[20] + (buf[21] << 8) +
177 (buf[22] << 16) + ((uint64_t)buf[23] << 24);
178 debug("OSF1 a.out, load address 0x%08lx, "
179 "entry point 0x%08x\n", (long)vaddr, (long)entry);
180 symbsize = 0;
181 fseek(f, 0, SEEK_END);
182 /* This is of course wrong, but should work anyway: */
183 textsize = ftello(f) - 512;
184 datasize = 0;
185 fseek(f, 512, SEEK_SET);
186 } else if (flags & AOUT_FLAG_NO_SIZES) {
187 fseek(f, 0, SEEK_END);
188 textsize = ftello(f) - 32;
189 datasize = 0;
190 vaddr = entry = 0;
191 fseek(f, 32, SEEK_SET);
192 } else {
193 len = fread(&aout_header, 1, sizeof(aout_header), f);
194 if (len != sizeof(aout_header)) {
195 fprintf(stderr, "%s: not a complete a.out image\n",
196 filename);
197 exit(1);
198 }
199
200 unencode(entry, &aout_header.a_entry, uint32_t);
201 debug("a.out, entry point 0x%08lx\n", (long)entry);
202 vaddr = entry;
203
204 if (flags & AOUT_FLAG_VADDR_ZERO_HACK)
205 vaddr = 0;
206
207 unencode(textsize, &aout_header.a_text, uint32_t);
208 unencode(datasize, &aout_header.a_data, uint32_t);
209 debug("text + data = %i + %i bytes\n", textsize, datasize);
210
211 unencode(symbsize, &aout_header.a_syms, uint32_t);
212 }
213
214 if (flags & AOUT_FLAG_FROM_BEGINNING) {
215 fseek(f, 0, SEEK_SET);
216 vaddr &= ~0xfff;
217 }
218
219 /* Load text and data: */
220 total_len = textsize + datasize;
221 while (total_len != 0) {
222 len = total_len > sizeof(buf) ? sizeof(buf) : total_len;
223 len = fread(buf, 1, len, f);
224
225 /* printf("fread len=%i vaddr=%x buf[0..]=%02x %02x %02x\n",
226 (int)len, (int)vaddr, buf[0], buf[1], buf[2]); */
227
228 if (len > 0) {
229 int len2 = 0;
230 uint64_t vaddr1 = vaddr &
231 ((1 << BITS_PER_MEMBLOCK) - 1);
232 uint64_t vaddr2 = (vaddr +
233 len) & ((1 << BITS_PER_MEMBLOCK) - 1);
234 if (vaddr2 < vaddr1) {
235 len2 = len - vaddr2;
236 m->cpus[0]->memory_rw(m->cpus[0], mem, vaddr,
237 &buf[0], len2, MEM_WRITE, NO_EXCEPTIONS);
238 }
239 m->cpus[0]->memory_rw(m->cpus[0], mem, vaddr + len2,
240 &buf[len2], len-len2, MEM_WRITE, NO_EXCEPTIONS);
241 } else {
242 if (flags & AOUT_FLAG_DECOSF1)
243 break;
244 else {
245 fprintf(stderr, "could not read from %s\n",
246 filename);
247 exit(1);
248 }
249 }
250
251 vaddr += len;
252 total_len -= len;
253 }
254
255 if (symbsize != 0) {
256 struct aout_symbol *aout_symbol_ptr;
257 int i, n_symbols;
258 uint32_t type, addr, str_index;
259 uint32_t strings_len;
260 char *string_symbols;
261 off_t oldpos;
262
263 debug("symbols: %i bytes @ 0x%x\n", symbsize, (int)ftello(f));
264 syms = malloc(symbsize);
265 if (syms == NULL) {
266 fprintf(stderr, "out of memory\n");
267 exit(1);
268 }
269 len = fread(syms, 1, symbsize, f);
270 if (len != symbsize) {
271 fprintf(stderr, "error reading symbols from %s\n",
272 filename);
273 exit(1);
274 }
275
276 oldpos = ftello(f);
277 fseek(f, 0, SEEK_END);
278 strings_len = ftello(f) - oldpos;
279 fseek(f, oldpos, SEEK_SET);
280 debug("strings: %i bytes @ 0x%x\n", strings_len,(int)ftello(f));
281 string_symbols = malloc(strings_len);
282 if (string_symbols == NULL) {
283 fprintf(stderr, "out of memory\n");
284 exit(1);
285 }
286 fread(string_symbols, 1, strings_len, f);
287
288 aout_symbol_ptr = (struct aout_symbol *) syms;
289 n_symbols = symbsize / sizeof(struct aout_symbol);
290 i = 0;
291 while (i < n_symbols) {
292 unencode(str_index, &aout_symbol_ptr[i].strindex,
293 uint32_t);
294 unencode(type, &aout_symbol_ptr[i].type, uint32_t);
295 unencode(addr, &aout_symbol_ptr[i].addr, uint32_t);
296
297 /* debug("symbol type 0x%04x @ 0x%08x: %s\n",
298 type, addr, string_symbols + str_index); */
299
300 if (type != 0 && addr != 0)
301 add_symbol_name(&m->symbol_context,
302 addr, 0, string_symbols + str_index, 0, -1);
303 i++;
304 }
305
306 free(string_symbols);
307 free(syms);
308 }
309
310 fclose(f);
311
312 *entrypointp = (int32_t)entry;
313
314 if (encoding == ELFDATA2LSB)
315 *byte_orderp = EMUL_LITTLE_ENDIAN;
316 else
317 *byte_orderp = EMUL_BIG_ENDIAN;
318
319 n_executables_loaded ++;
320 }
321
322
323 /*
324 * file_load_macho():
325 *
326 * Loads a Mach-O binary image into the emulated memory. The entry point
327 * is stored in the specified CPU's registers.
328 *
329 * TODO:
330 *
331 * o) Almost everything.
332 *
333 * o) I haven't had time to look into whether Apple's open source
334 * license is BSD-compatible or not. Perhaps it would be possible
335 * to use a header file containing symbolic names, and not use
336 * hardcoded values.
337 */
338 static void file_load_macho(struct machine *m, struct memory *mem,
339 char *filename, uint64_t *entrypointp, int arch, int *byte_orderp,
340 int is_64bit, int is_reversed)
341 {
342 FILE *f;
343 uint64_t entry = 0;
344 int entry_set = 0;
345 int encoding = ELFDATA2MSB;
346 unsigned char buf[65536];
347 char *symbols, *strings;
348 uint32_t cputype, cpusubtype, filetype, ncmds, sizeofcmds, flags;
349 uint64_t vmaddr, vmsize, fileoff, filesize;
350 int cmd_type, cmd_len, i, flavor;
351 int32_t symoff, nsyms, stroff, strsize;
352 size_t len, pos;
353
354 if (m->cpus[0]->byte_order == EMUL_BIG_ENDIAN)
355 encoding = ELFDATA2MSB;
356
357 f = fopen(filename, "r");
358 if (f == NULL) {
359 perror(filename);
360 exit(1);
361 }
362
363 if (is_64bit) {
364 fatal("TODO: 64-bit Mach-O. Not supported yet.\n");
365 exit(1);
366 }
367 if (is_reversed) {
368 fatal("TODO: Reversed-endianness. Not supported yet.\n");
369 exit(1);
370 }
371
372 len = fread(buf, 1, sizeof(buf), f);
373 if (len < 100) {
374 fatal("Bad Mach-O file?\n");
375 exit(1);
376 }
377
378 unencode(cputype, &buf[4], uint32_t);
379 unencode(cpusubtype, &buf[8], uint32_t);
380 unencode(filetype, &buf[12], uint32_t);
381 unencode(ncmds, &buf[16], uint32_t);
382 unencode(sizeofcmds, &buf[20], uint32_t);
383 unencode(flags, &buf[24], uint32_t);
384
385 /* debug("cputype=0x%x cpusubtype=0x%x filetype=0x%x\n",
386 cputype, cpusubtype, filetype);
387 debug("ncmds=%i sizeofcmds=0x%08x flags=0x%08x\n",
388 ncmds, sizeofcmds, flags); */
389
390 /*
391 * Compare to "normal" values.
392 * NOTE/TODO: These were for a Darwin (Macintosh PPC) kernel.
393 */
394 if (cputype != 0x12) {
395 fatal("Error: Unimplemented cputype 0x%x\n", cputype);
396 exit(1);
397 }
398 if (cpusubtype != 0) {
399 fatal("Error: Unimplemented cpusubtype 0x%x\n", cpusubtype);
400 exit(1);
401 }
402 /* Filetype 2 means an executable image. */
403 if (filetype != 2) {
404 fatal("Error: Unimplemented filetype 0x%x\n", filetype);
405 exit(1);
406 }
407 if (!(flags & 1)) {
408 fatal("Error: File has 'undefined references'. Cannot"
409 " be executed.\n", flags);
410 exit(1);
411 }
412
413 /* I've only encountered flags == 1 so far. */
414 if (flags != 1) {
415 fatal("Error: Unimplemented flags 0x%x\n", flags);
416 exit(1);
417 }
418
419 /*
420 * Read all load commands:
421 */
422 pos = is_64bit? 32 : 28;
423 cmd_type = 0;
424 do {
425 /* Read command type and length: */
426 unencode(cmd_type, &buf[pos], uint32_t);
427 unencode(cmd_len, &buf[pos+4], uint32_t);
428
429 #if 0
430 debug("cmd %i, len=%i\n", cmd_type, cmd_len);
431 for (i=8; i<cmd_len; i++) {
432 unsigned char ch = buf[pos+i];
433 if (ch >= ' ' && ch < 127)
434 debug("%c", ch);
435 else
436 debug(".");
437 }
438 #endif
439 switch (cmd_type) {
440 case 1: /* LC_SEGMENT */
441 debug("seg ");
442 for (i=0; i<16; i++) {
443 if (buf[pos + 8 + i] == 0)
444 break;
445 debug("%c", buf[pos + 8 + i]);
446 }
447 unencode(vmaddr, &buf[pos+8+16+0], uint32_t);
448 unencode(vmsize, &buf[pos+8+16+4], uint32_t);
449 unencode(fileoff, &buf[pos+8+16+8], uint32_t);
450 unencode(filesize, &buf[pos+8+16+12], uint32_t);
451 debug(": vmaddr=0x%x size=0x%x fileoff=0x%x",
452 (int)vmaddr, (int)vmsize, (int)fileoff);
453
454 if (filesize == 0) {
455 debug("\n");
456 break;
457 }
458
459 fseek(f, fileoff, SEEK_SET);
460
461 /* Load data from the file: */
462 while (filesize != 0) {
463 unsigned char buf[32768];
464 ssize_t len = filesize > sizeof(buf) ?
465 sizeof(buf) : filesize;
466 len = fread(buf, 1, len, f);
467
468 /* printf("fread len=%i vmaddr=%x buf[0..]="
469 "%02x %02x %02x\n", (int)len, (int)vmaddr,
470 buf[0], buf[1], buf[2]); */
471
472 if (len > 0) {
473 int len2 = 0;
474 uint64_t vaddr1 = vmaddr &
475 ((1 << BITS_PER_MEMBLOCK) - 1);
476 uint64_t vaddr2 = (vmaddr +
477 len) & ((1 << BITS_PER_MEMBLOCK)-1);
478 if (vaddr2 < vaddr1) {
479 len2 = len - vaddr2;
480 m->cpus[0]->memory_rw(m->cpus[
481 0], mem, vmaddr, &buf[0],
482 len2, MEM_WRITE,
483 NO_EXCEPTIONS);
484 }
485 m->cpus[0]->memory_rw(m->cpus[0], mem,
486 vmaddr + len2, &buf[len2], len-len2,
487 MEM_WRITE, NO_EXCEPTIONS);
488 } else {
489 fprintf(stderr, "error reading\n");
490 exit(1);
491 }
492
493 vmaddr += len;
494 filesize -= len;
495 }
496
497 debug("\n");
498 break;
499
500 case 2: /* LC_SYMTAB */
501 unencode(symoff, &buf[pos+8], uint32_t);
502 unencode(nsyms, &buf[pos+12], uint32_t);
503 unencode(stroff, &buf[pos+16], uint32_t);
504 unencode(strsize, &buf[pos+20], uint32_t);
505 debug("symtable: %i symbols @ 0x%x (strings at "
506 "0x%x)\n", nsyms, symoff, stroff);
507
508 symbols = malloc(12 * nsyms);
509 if (symbols == NULL) {
510 fprintf(stderr, "out of memory\n");
511 exit(1);
512 }
513 fseek(f, symoff, SEEK_SET);
514 fread(symbols, 1, 12 * nsyms, f);
515
516 strings = malloc(strsize);
517 if (strings == NULL) {
518 fprintf(stderr, "out of memory\n");
519 exit(1);
520 }
521 fseek(f, stroff, SEEK_SET);
522 fread(strings, 1, strsize, f);
523
524 for (i=0; i<nsyms; i++) {
525 int n_strx, n_type, n_sect, n_desc;
526 uint32_t n_value;
527 unencode(n_strx, &symbols[i*12+0], int32_t);
528 unencode(n_type, &symbols[i*12+4], uint8_t);
529 unencode(n_sect, &symbols[i*12+5], uint8_t);
530 unencode(n_desc, &symbols[i*12+6], int16_t);
531 unencode(n_value, &symbols[i*12+8], uint32_t);
532 /* debug("%i: strx=%i type=%i sect=%i desc=%i"
533 " value=0x%x\n", i, n_strx, n_type,
534 n_sect, n_desc, n_value); */
535 add_symbol_name(&m->symbol_context,
536 n_value, 0, strings + n_strx, 0, -1);
537 }
538
539 free(symbols);
540 free(strings);
541 break;
542
543 case 5: debug("unix thread context: ");
544 /* See http://cvs.sf.net/viewcvs.py/hte/
545 HT%20Editor/machostruc.h or similar for details
546 on the thread struct. */
547 unencode(flavor, &buf[pos+8], uint32_t);
548 if (flavor != 1) {
549 fatal("unimplemented flavor %i\n", flavor);
550 exit(1);
551 }
552
553 if (arch != ARCH_PPC) {
554 fatal("non-PPC arch? TODO\n");
555 exit(1);
556 }
557
558 unencode(entry, &buf[pos+16], uint32_t);
559 entry_set = 1;
560 debug("pc=0x%x\n", (int)entry);
561
562 for (i=1; i<40; i++) {
563 uint32_t x;
564 unencode(x, &buf[pos+16+i*4], uint32_t);
565 if (x != 0) {
566 fatal("Entry nr %i in the Mach-O"
567 " thread struct is non-zero"
568 " (0x%x). This is not supported"
569 " yet. TODO\n", i, x);
570 exit(1);
571 }
572 }
573 break;
574
575 default:fatal("WARNING! Unimplemented load command %i!\n",
576 cmd_type);
577 }
578
579 pos += cmd_len;
580 } while (pos < sizeofcmds && cmd_type != 0);
581
582 fclose(f);
583
584 if (!entry_set) {
585 fatal("No entry point? Aborting.\n");
586 exit(1);
587 }
588
589 *entrypointp = entry;
590
591 if (encoding == ELFDATA2LSB)
592 *byte_orderp = EMUL_LITTLE_ENDIAN;
593 else
594 *byte_orderp = EMUL_BIG_ENDIAN;
595
596 n_executables_loaded ++;
597 }
598
599
600 /*
601 * file_load_ecoff():
602 *
603 * Loads an ecoff binary image into the emulated memory. The entry point
604 * (read from the ecoff header) is stored in the specified CPU's registers.
605 */
606 static void file_load_ecoff(struct machine *m, struct memory *mem,
607 char *filename, uint64_t *entrypointp,
608 int arch, uint64_t *gpp, int *byte_orderp)
609 {
610 struct ecoff_exechdr exechdr;
611 int f_magic, f_nscns, f_nsyms;
612 int a_magic;
613 off_t f_symptr, a_tsize, a_dsize, a_bsize;
614 uint64_t a_entry, a_tstart, a_dstart, a_bstart, a_gp, end_addr=0;
615 char *format_name;
616 struct ecoff_scnhdr scnhdr;
617 FILE *f;
618 int len, secn, total_len, chunk_size;
619 int encoding = ELFDATA2LSB; /* Assume little-endian. See below */
620 int program_byte_order = -1;
621 unsigned char buf[8192];
622
623 f = fopen(filename, "r");
624 if (f == NULL) {
625 perror(filename);
626 exit(1);
627 }
628
629 len = fread(&exechdr, 1, sizeof(exechdr), f);
630 if (len != sizeof(exechdr)) {
631 fprintf(stderr, " not a complete ecoff image\n");
632 exit(1);
633 }
634
635 /*
636 * The following code looks a bit ugly, but it should work. The ECOFF
637 * 16-bit magic value seems to be stored in MSB byte order for
638 * big-endian binaries, and LSB byte order for little-endian binaries.
639 *
640 * The unencode() assumes little-endianness by default.
641 */
642 unencode(f_magic, &exechdr.f.f_magic, uint16_t);
643 switch (f_magic) {
644 case ((ECOFF_MAGIC_MIPSEB & 0xff) << 8) +
645 ((ECOFF_MAGIC_MIPSEB >> 8) & 0xff):
646 format_name = "MIPS1 BE";
647 encoding = ELFDATA2MSB;
648 break;
649 case ECOFF_MAGIC_MIPSEB:
650 /* NOTE: Big-endian header, little-endian code! */
651 format_name = "MIPS1 BE-LE";
652 encoding = ELFDATA2MSB;
653 program_byte_order = ELFDATA2LSB;
654 break;
655 case ECOFF_MAGIC_MIPSEL:
656 format_name = "MIPS1 LE";
657 encoding = ELFDATA2LSB;
658 break;
659 case ((ECOFF_MAGIC_MIPSEB2 & 0xff) << 8) +
660 ((ECOFF_MAGIC_MIPSEB2 >> 8) & 0xff):
661 format_name = "MIPS2 BE";
662 encoding = ELFDATA2MSB;
663 break;
664 case ECOFF_MAGIC_MIPSEL2:
665 format_name = "MIPS2 LE";
666 encoding = ELFDATA2LSB;
667 break;
668 case ((ECOFF_MAGIC_MIPSEB3 & 0xff) << 8) +
669 ((ECOFF_MAGIC_MIPSEB3 >> 8) & 0xff):
670 format_name = "MIPS3 BE";
671 encoding = ELFDATA2MSB;
672 break;
673 case ECOFF_MAGIC_MIPSEL3:
674 format_name = "MIPS3 LE";
675 encoding = ELFDATA2LSB;
676 break;
677 default:
678 fprintf(stderr, "%s: unimplemented ECOFF format, magic = "
679 "0x%04x\n", filename, (int)f_magic);
680 exit(1);
681 }
682
683 /* Read various header information: */
684 unencode(f_nscns, &exechdr.f.f_nscns, uint16_t);
685 unencode(f_symptr, &exechdr.f.f_symptr, uint32_t);
686 unencode(f_nsyms, &exechdr.f.f_nsyms, uint32_t);
687 debug("ECOFF, %s, %i sections, %i symbols @ 0x%lx\n",
688 format_name, f_nscns, f_nsyms, (long)f_symptr);
689
690 unencode(a_magic, &exechdr.a.magic, uint16_t);
691 unencode(a_tsize, &exechdr.a.tsize, uint32_t);
692 unencode(a_dsize, &exechdr.a.dsize, uint32_t);
693 unencode(a_bsize, &exechdr.a.bsize, uint32_t);
694 debug("magic 0x%04x, tsize 0x%x, dsize 0x%x, bsize 0x%x\n",
695 a_magic, (int)a_tsize, (int)a_dsize, (int)a_bsize);
696
697 unencode(a_tstart, &exechdr.a.text_start, uint32_t);
698 unencode(a_dstart, &exechdr.a.data_start, uint32_t);
699 unencode(a_bstart, &exechdr.a.bss_start, uint32_t);
700 debug("text @ 0x%08x, data @ 0x%08x, bss @ 0x%08x\n",
701 (int)a_tstart, (int)a_dstart, (int)a_bstart);
702
703 unencode(a_entry, &exechdr.a.entry, uint32_t);
704 unencode(a_gp, &exechdr.a.gp_value, uint32_t);
705 debug("entrypoint 0x%08x, gp = 0x%08x\n",
706 (int)a_entry, (int)a_gp);
707
708 /*
709 * Special hack for a MACH/pmax kernel, I don't know how applicable
710 * this is for other files:
711 * there are no sections (!), and a_magic = 0x0108 instead of
712 * 0x0107 as it is on most other (E)COFF files I've seen.
713 *
714 * Then load everything after the header to the text start address.
715 */
716 if (f_nscns == 0 && a_magic == 0x108) {
717 uint64_t where = a_tstart;
718 total_len = 0;
719 fseek(f, 0x50, SEEK_SET);
720 while (!feof(f)) {
721 chunk_size = 256;
722 len = fread(buf, 1, chunk_size, f);
723
724 if (len > 0)
725 m->cpus[0]->memory_rw(m->cpus[0], mem, where,
726 &buf[0], len, MEM_WRITE, NO_EXCEPTIONS);
727 where += len;
728 total_len += len;
729 }
730 debug("MACH/pmax hack (!), read 0x%x bytes\n", total_len);
731 }
732
733 /* Go through all the section headers: */
734 for (secn=0; secn<f_nscns; secn++) {
735 off_t s_scnptr, s_relptr, s_lnnoptr, oldpos;
736 int s_nreloc, s_nlnno, s_flags;
737 int s_size;
738 unsigned int i;
739 uint64_t s_paddr, s_vaddr;
740
741 /* Read a section header: */
742 len = fread(&scnhdr, 1, sizeof(scnhdr), f);
743 if (len != sizeof(scnhdr)) {
744 fprintf(stderr, "%s: incomplete section "
745 "header %i\n", filename, secn);
746 exit(1);
747 }
748
749 /* Show the section name: */
750 debug("section ");
751 for (i=0; i<sizeof(scnhdr.s_name); i++)
752 if (scnhdr.s_name[i] >= 32 && scnhdr.s_name[i] < 127)
753 debug("%c", scnhdr.s_name[i]);
754 else
755 break;
756 debug(" (");
757
758 unencode(s_paddr, &scnhdr.s_paddr, uint32_t);
759 unencode(s_vaddr, &scnhdr.s_vaddr, uint32_t);
760 unencode(s_size, &scnhdr.s_size, uint32_t);
761 unencode(s_scnptr, &scnhdr.s_scnptr, uint32_t);
762 unencode(s_relptr, &scnhdr.s_relptr, uint32_t);
763 unencode(s_lnnoptr, &scnhdr.s_lnnoptr, uint32_t);
764 unencode(s_nreloc, &scnhdr.s_nreloc, uint16_t);
765 unencode(s_nlnno, &scnhdr.s_nlnno, uint16_t);
766 unencode(s_flags, &scnhdr.s_flags, uint32_t);
767
768 debug("0x%x @ 0x%08x, offset 0x%lx, flags 0x%x)\n",
769 (int)s_size, (int)s_vaddr, (long)s_scnptr, (int)s_flags);
770
771 end_addr = s_vaddr + s_size;
772
773 if (s_relptr != 0) {
774 /*
775 * TODO: Read this url, or similar:
776 * http://www.iecc.com/linker/linker07.html
777 */
778 fprintf(stderr, "%s: relocatable code/data in "
779 "section nr %i: not yet implemented\n",
780 filename, secn);
781 exit(1);
782 }
783
784 /* Loadable? Then load the section: */
785 if (s_scnptr != 0 && s_size != 0 &&
786 s_vaddr != 0 && !(s_flags & 0x02)) {
787 /* Remember the current file offset: */
788 oldpos = ftello(f);
789
790 /* Load the section into emulated memory: */
791 fseek(f, s_scnptr, SEEK_SET);
792 total_len = 0;
793 chunk_size = 1;
794 if ((s_vaddr & 0xf) == 0) chunk_size = 0x10;
795 if ((s_vaddr & 0xff) == 0) chunk_size = 0x100;
796 if ((s_vaddr & 0xfff) == 0) chunk_size = 0x1000;
797 while (total_len < s_size) {
798 len = chunk_size;
799 if (total_len + len > s_size)
800 len = s_size - total_len;
801 len = fread(buf, 1, chunk_size, f);
802 if (len == 0) {
803 debug("!!! total_len = %i, "
804 "chunk_size = %i, len = %i\n",
805 total_len, chunk_size, len);
806 break;
807 }
808
809 m->cpus[0]->memory_rw(m->cpus[0], mem, s_vaddr,
810 &buf[0], len, MEM_WRITE, NO_EXCEPTIONS);
811 s_vaddr += len;
812 total_len += len;
813 }
814
815 /* Return to position inside the section headers: */
816 fseek(f, oldpos, SEEK_SET);
817 }
818 }
819
820 if (f_symptr != 0 && f_nsyms != 0) {
821 struct ecoff_symhdr symhdr;
822 int sym_magic, iextMax, issExtMax, issMax, crfd;
823 off_t cbRfdOffset, cbExtOffset, cbSsExtOffset, cbSsOffset;
824 char *symbol_data;
825 struct ecoff_extsym *extsyms;
826 int nsymbols, sym_nr;
827
828 fseek(f, f_symptr, SEEK_SET);
829
830 len = fread(&symhdr, 1, sizeof(symhdr), f);
831 if (len != sizeof(symhdr)) {
832 fprintf(stderr, "%s: not a complete "
833 "ecoff image: symhdr broken\n", filename);
834 exit(1);
835 }
836
837 unencode(sym_magic, &symhdr.magic, uint16_t);
838 unencode(crfd, &symhdr.crfd, uint32_t);
839 unencode(cbRfdOffset, &symhdr.cbRfdOffset, uint32_t);
840 unencode(issMax, &symhdr.issMax, uint32_t);
841 unencode(cbSsOffset, &symhdr.cbSsOffset, uint32_t);
842 unencode(issExtMax, &symhdr.issExtMax, uint32_t);
843 unencode(cbSsExtOffset, &symhdr.cbSsExtOffset, uint32_t);
844 unencode(iextMax, &symhdr.iextMax, uint32_t);
845 unencode(cbExtOffset, &symhdr.cbExtOffset, uint32_t);
846
847 if (sym_magic != MIPS_MAGIC_SYM) {
848 unsigned char *ms_sym_buf;
849 struct ms_sym *sym;
850 int n_real_symbols = 0;
851
852 debug("bad symbol magic, assuming Microsoft format: ");
853
854 /*
855 * See http://www.lisoleg.net/lisoleg/elfandlib/
856 * Microsoft%20Portable%20Executable%20COFF%20For
857 * mat%20Specification.txt
858 * for more details.
859 */
860 ms_sym_buf = malloc(sizeof(struct ms_sym) * f_nsyms);
861 if (ms_sym_buf == NULL) {
862 fprintf(stderr, "out of memory\n");
863 exit(1);
864 }
865 fseek(f, f_symptr, SEEK_SET);
866 len = fread(ms_sym_buf, 1,
867 sizeof(struct ms_sym) * f_nsyms, f);
868 sym = (struct ms_sym *) ms_sym_buf;
869 for (sym_nr=0; sym_nr<f_nsyms; sym_nr++) {
870 char name[300];
871 uint32_t v, t, altname;
872 /* debug("sym %5i: '", sym_nr);
873 for (i=0; i<8 && sym->name[i]; i++)
874 debug("%c", sym->name[i]); */
875 v = sym->value[0] + (sym->value[1] << 8)
876 + (sym->value[2] << 16)
877 + ((uint64_t)sym->value[3] << 24);
878 altname = sym->name[4] + (sym->name[5] << 8)
879 + (sym->name[6] << 16)
880 + ((uint64_t)sym->name[3] << 24);
881 t = (sym->type[1] << 8) + sym->type[0];
882 /* TODO: big endian COFF? */
883 /* debug("' value=0x%x type=0x%04x", v, t); */
884
885 if (t == 0x20 && sym->name[0]) {
886 memcpy(name, sym->name, 8);
887 name[8] = '\0';
888 add_symbol_name(&m->symbol_context,
889 v, 0, name, 0, -1);
890 n_real_symbols ++;
891 } else if (t == 0x20 && !sym->name[0]) {
892 off_t ofs;
893 ofs = f_symptr + altname +
894 sizeof(struct ms_sym) * f_nsyms;
895 fseek(f, ofs, SEEK_SET);
896 fread(name, 1, sizeof(name), f);
897 name[sizeof(name)-1] = '\0';
898 /* debug(" [altname=0x%x '%s']",
899 altname, name); */
900 add_symbol_name(&m->symbol_context,
901 v, 0, name, 0, -1);
902 n_real_symbols ++;
903 }
904
905
906 if (sym->n_aux_syms) {
907 int n = sym->n_aux_syms;
908 /* debug(" aux='"); */
909 while (n-- > 0) {
910 sym ++; sym_nr ++;
911 /* for (i=0; i<8 &&
912 sym->name[i]; i++)
913 debug("%c",
914 sym->name[i]); */
915 }
916 /* debug("'"); */
917 }
918 /* debug("\n"); */
919 sym ++;
920 }
921
922 debug("%i symbols\n", n_real_symbols);
923 free(ms_sym_buf);
924
925 goto skip_normal_coff_symbols;
926 }
927
928 debug("symbol header: magic = 0x%x\n", sym_magic);
929
930 debug("%i symbols @ 0x%08x (strings @ 0x%08x)\n",
931 iextMax, cbExtOffset, cbSsExtOffset);
932
933 symbol_data = malloc(issExtMax + 2);
934 if (symbol_data == NULL) {
935 fprintf(stderr, "out of memory\n");
936 exit(1);
937 }
938 memset(symbol_data, 0, issExtMax + 2);
939 fseek(f, cbSsExtOffset, SEEK_SET);
940 fread(symbol_data, 1, issExtMax + 1, f);
941
942 nsymbols = iextMax;
943
944 extsyms = malloc(iextMax * sizeof(struct ecoff_extsym));
945 if (extsyms == NULL) {
946 fprintf(stderr, "out of memory\n");
947 exit(1);
948 }
949 memset(extsyms, 0, iextMax * sizeof(struct ecoff_extsym));
950 fseek(f, cbExtOffset, SEEK_SET);
951 fread(extsyms, 1, iextMax * sizeof(struct ecoff_extsym), f);
952
953 /* Unencode the strindex and value first: */
954 for (sym_nr=0; sym_nr<nsymbols; sym_nr++) {
955 uint64_t value, strindex;
956
957 unencode(strindex, &extsyms[sym_nr].es_strindex,
958 uint32_t);
959 unencode(value, &extsyms[sym_nr].es_value, uint32_t);
960
961 extsyms[sym_nr].es_strindex = strindex;
962 extsyms[sym_nr].es_value = value;
963 }
964
965 for (sym_nr=0; sym_nr<nsymbols; sym_nr++) {
966 /* debug("symbol%6i: 0x%08x = %s\n",
967 sym_nr, (int)extsyms[sym_nr].es_value,
968 symbol_data + extsyms[sym_nr].es_strindex); */
969
970 add_symbol_name(&m->symbol_context,
971 extsyms[sym_nr].es_value, 0,
972 symbol_data + extsyms[sym_nr].es_strindex, 0, -1);
973 }
974
975 free(extsyms);
976 free(symbol_data);
977
978 skip_normal_coff_symbols:
979 ;
980 }
981
982 fclose(f);
983
984 *entrypointp = a_entry;
985 *gpp = a_gp;
986 m->file_loaded_end_addr = end_addr;
987
988 if (program_byte_order != -1)
989 encoding = program_byte_order;
990
991 if (encoding == ELFDATA2LSB)
992 *byte_orderp = EMUL_LITTLE_ENDIAN;
993 else
994 *byte_orderp = EMUL_BIG_ENDIAN;
995
996 n_executables_loaded ++;
997 }
998
999
1000 /*
1001 * file_load_srec():
1002 *
1003 * Loads a Motorola SREC file into emulated memory. Description of the SREC
1004 * file format can be found at here:
1005 *
1006 * http://www.ndsu.nodak.edu/instruct/tareski/373f98/notes/srecord.htm
1007 * or http://www.amelek.gda.pl/avr/uisp/srecord.htm
1008 */
1009 static void file_load_srec(struct machine *m, struct memory *mem,
1010 char *filename, uint64_t *entrypointp)
1011 {
1012 FILE *f;
1013 unsigned char buf[516];
1014 unsigned char bytes[270];
1015 uint64_t entry = 0, vaddr = 0;
1016 int i, j, count;
1017 char ch;
1018 int buf_len, data_start = 0;
1019 int entry_set = 0;
1020 int warning = 0;
1021 int warning_len = 0;
1022 int total_bytes_loaded = 0;
1023
1024 f = fopen(filename, "r");
1025 if (f == NULL) {
1026 perror(filename);
1027 exit(1);
1028 }
1029
1030 /* Load file contents: */
1031 while (!feof(f)) {
1032 memset(buf, 0, sizeof(buf));
1033 fgets((char *)buf, sizeof(buf)-1, f);
1034
1035 if (buf[0] == 0 || buf[0]=='\r' || buf[0]=='\n')
1036 continue;
1037
1038 if (buf[0] != 'S') {
1039 if (!warning)
1040 debug("WARNING! non-S-record found\n");
1041 warning = 1;
1042 continue;
1043 }
1044
1045 buf_len = strlen((char *)buf);
1046
1047 if (buf_len < 10) {
1048 if (!warning_len)
1049 debug("WARNING! invalid S-record found\n");
1050 warning_len = 1;
1051 continue;
1052 }
1053
1054 /*
1055 * Stype count address data checksum
1056 * 01 23 4.. .. (last 2 bytes)
1057 *
1058 * TODO: actually check the checksum
1059 */
1060
1061 j = 0;
1062 for (i=1; i<buf_len; i++) {
1063 if (buf[i]>='a' && buf[i]<='f')
1064 buf[i] += 10 - 'a';
1065 else if (buf[i] >= 'A' && buf[i] <= 'F')
1066 buf[i] += 10 - 'A';
1067 else if (buf[i] >= '0' && buf[i] <= '9')
1068 buf[i] -= '0';
1069 else if (buf[i] == '\r' || buf[i] == '\n') {
1070 } else
1071 fatal("invalid characters '%c' in S-record\n",
1072 buf[i]);
1073
1074 if (i >= 4) {
1075 if (i & 1)
1076 bytes[j++] += buf[i];
1077 else
1078 bytes[j] = buf[i] * 16;
1079 }
1080 }
1081
1082 count = buf[2] * 16 + buf[3];
1083 /* debug("count=%i j=%i\n", count, j); */
1084 /* count is j - 1. */
1085
1086 switch (buf[1]) {
1087 case 0:
1088 debug("SREC \"");
1089 for (i=2; i<count-1; i++) {
1090 ch = bytes[i];
1091 if (ch >= ' ' && ch < 127)
1092 debug("%c", ch);
1093 else
1094 debug("?");
1095 }
1096 debug("\"\n");
1097 break;
1098 case 1:
1099 case 2:
1100 case 3:
1101 /* switch again, to get the load address: */
1102 switch (buf[1]) {
1103 case 1: data_start = 2;
1104 vaddr = (bytes[0] << 8) + bytes[1];
1105 break;
1106 case 2: data_start = 3;
1107 vaddr = (bytes[0] << 16) + (bytes[1] << 8) +
1108 bytes[2];
1109 break;
1110 case 3: data_start = 4;
1111 vaddr = ((uint64_t)bytes[0] << 24) +
1112 (bytes[1] << 16) + (bytes[2]<<8) + bytes[3];
1113 }
1114 m->cpus[0]->memory_rw(m->cpus[0], mem, vaddr,
1115 &bytes[data_start], count - 1 - data_start,
1116 MEM_WRITE, NO_EXCEPTIONS);
1117 total_bytes_loaded += count - 1 - data_start;
1118 break;
1119 case 7:
1120 case 8:
1121 case 9:
1122 /* switch again, to get the entry point: */
1123 switch (buf[1]) {
1124 case 7: entry = ((uint64_t)bytes[0] << 24) +
1125 (bytes[1] << 16) + (bytes[2]<<8) + bytes[3];
1126 break;
1127 case 8: entry = (bytes[0] << 16) + (bytes[1] << 8) +
1128 bytes[2];
1129 break;
1130 case 9: entry = (bytes[0] << 8) + bytes[1];
1131 break;
1132 }
1133 entry_set = 1;
1134 debug("entry point 0x%08x\n", (unsigned int)entry);
1135 break;
1136 default:
1137 debug("unimplemented S-record type %i\n", buf[1]);
1138 }
1139 }
1140
1141 debug("0x%x bytes loaded\n", total_bytes_loaded);
1142
1143 fclose(f);
1144
1145 if (!entry_set)
1146 debug("WARNING! no entrypoint found!\n");
1147 else
1148 *entrypointp = entry;
1149
1150 n_executables_loaded ++;
1151 }
1152
1153
1154 /*
1155 * file_load_raw():
1156 *
1157 * Loads a raw binary into emulated memory. The filename should be
1158 * of the following form: loadaddress:filename
1159 * or loadaddress:skiplen:filename
1160 * or loadaddress:skiplen:pc:filename
1161 */
1162 static void file_load_raw(struct machine *m, struct memory *mem,
1163 char *filename, uint64_t *entrypointp)
1164 {
1165 FILE *f;
1166 int len, sign3264;
1167 unsigned char buf[16384];
1168 uint64_t entry, loadaddr, vaddr, skip = 0;
1169 char *p, *p2;
1170
1171 /* Special case for 32-bit MIPS: */
1172 sign3264 = 0;
1173 if (m->arch == ARCH_MIPS && m->cpus[0]->is_32bit)
1174 sign3264 = 1;
1175
1176 p = strchr(filename, ':');
1177 if (p == NULL) {
1178 fprintf(stderr, "\n");
1179 perror(filename);
1180 exit(1);
1181 }
1182
1183 loadaddr = vaddr = entry = strtoull(filename, NULL, 0);
1184 p2 = p+1;
1185
1186 /* A second value? That's the optional skip value */
1187 p = strchr(p2, ':');
1188 if (p != NULL) {
1189 skip = strtoull(p2, NULL, 0);
1190 p = p+1;
1191 /* A third value? That's the initial pc: */
1192 if (strchr(p, ':') != NULL) {
1193 entry = strtoull(p, NULL, 0);
1194 p = strchr(p, ':') + 1;
1195 }
1196 } else
1197 p = p2;
1198
1199 if (sign3264) {
1200 loadaddr = (int64_t)(int32_t)loadaddr;
1201 entry = (int64_t)(int32_t)entry;
1202 vaddr = (int64_t)(int32_t)vaddr;
1203 skip = (int64_t)(int32_t)skip;
1204 }
1205
1206 f = fopen(strrchr(filename, ':')+1, "r");
1207 if (f == NULL) {
1208 perror(p);
1209 exit(1);
1210 }
1211
1212 fseek(f, skip, SEEK_SET);
1213
1214 /* Load file contents: */
1215 while (!feof(f)) {
1216 size_t to_read = sizeof(buf);
1217
1218 /* If vaddr isn't buf-size aligned, then start with a
1219 smaller buffer: */
1220 if (vaddr & (sizeof(buf) - 1))
1221 to_read = sizeof(buf) - (vaddr & (sizeof(buf)-1));
1222
1223 len = fread(buf, 1, to_read, f);
1224
1225 if (len > 0)
1226 m->cpus[0]->memory_rw(m->cpus[0], mem, vaddr, &buf[0],
1227 len, MEM_WRITE, NO_EXCEPTIONS);
1228
1229 vaddr += len;
1230 }
1231
1232 debug("RAW: 0x%"PRIx64" bytes @ 0x%08"PRIx64,
1233 (uint64_t) (ftello(f) - skip), (uint64_t) loadaddr);
1234
1235 if (skip != 0)
1236 debug(" (0x%"PRIx64" bytes of header skipped)",
1237 (uint64_t) skip);
1238
1239 debug("\n");
1240
1241 fclose(f);
1242
1243 *entrypointp = entry;
1244
1245 n_executables_loaded ++;
1246 }
1247
1248
1249 /*
1250 * file_load_elf():
1251 *
1252 * Loads an ELF image into the emulated memory. The entry point (read from
1253 * the ELF header) and the initial value of the gp register (read from the
1254 * ELF symbol table) are stored in the specified CPU's registers.
1255 *
1256 * This is pretty heavy stuff, but is needed because of the heaviness of
1257 * ELF files. :-/ Hopefully it will be able to recognize most valid ELFs.
1258 */
1259 static void file_load_elf(struct machine *m, struct memory *mem,
1260 char *filename, uint64_t *entrypointp, int arch, uint64_t *gpp,
1261 int *byte_order, uint64_t *tocp)
1262 {
1263 Elf32_Ehdr hdr32;
1264 Elf64_Ehdr hdr64;
1265 FILE *f;
1266 uint64_t eentry;
1267 int len, i, ok;
1268 int elf64, encoding, eflags;
1269 int etype, emachine;
1270 int ephnum, ephentsize, eshnum, eshentsize;
1271 off_t ephoff, eshoff;
1272 Elf32_Phdr phdr32;
1273 Elf64_Phdr phdr64;
1274 Elf32_Shdr shdr32;
1275 Elf64_Shdr shdr64;
1276 Elf32_Sym sym32;
1277 Elf64_Sym sym64;
1278 int ofs;
1279 int chunk_len = 1024, align_len;
1280 char *symbol_strings = NULL; size_t symbol_length = 0;
1281 char *s;
1282 Elf32_Sym *symbols_sym32 = NULL; int n_symbols = 0;
1283 Elf64_Sym *symbols_sym64 = NULL;
1284
1285 f = fopen(filename, "r");
1286 if (f == NULL) {
1287 perror(filename);
1288 exit(1);
1289 }
1290
1291 len = fread(&hdr32, 1, sizeof(Elf32_Ehdr), f);
1292 if (len < (signed int)sizeof(Elf32_Ehdr)) {
1293 fprintf(stderr, "%s: not an ELF file image\n", filename);
1294 exit(1);
1295 }
1296
1297 if (memcmp(&hdr32.e_ident[EI_MAG0], ELFMAG, SELFMAG) != 0) {
1298 fprintf(stderr, "%s: not an ELF file image\n", filename);
1299 exit(1);
1300 }
1301
1302 switch (hdr32.e_ident[EI_CLASS]) {
1303 case ELFCLASS32:
1304 elf64 = 0;
1305 break;
1306 case ELFCLASS64:
1307 elf64 = 1;
1308 fseek(f, 0, SEEK_SET);
1309 len = fread(&hdr64, 1, sizeof(Elf64_Ehdr), f);
1310 if (len < (signed int)sizeof(Elf64_Ehdr)) {
1311 fprintf(stderr, "%s: not an ELF64 file image\n",
1312 filename);
1313 exit(1);
1314 }
1315 break;
1316 default:
1317 fprintf(stderr, "%s: unknown ELF class '%i'\n",
1318 filename, hdr32.e_ident[EI_CLASS]);
1319 exit(1);
1320 }
1321
1322 encoding = hdr32.e_ident[EI_DATA];
1323 if (encoding != ELFDATA2LSB && encoding != ELFDATA2MSB) {
1324 fprintf(stderr, "%s: unknown data encoding '%i'\n",
1325 filename, hdr32.e_ident[EI_DATA]);
1326 exit(1);
1327 }
1328
1329 if (elf64) {
1330 unencode(etype, &hdr64.e_type, Elf64_Quarter);
1331 unencode(eflags, &hdr64.e_flags, Elf64_Half);
1332 unencode(emachine, &hdr64.e_machine, Elf64_Quarter);
1333 unencode(eentry, &hdr64.e_entry, Elf64_Addr);
1334 unencode(ephnum, &hdr64.e_phnum, Elf64_Quarter);
1335 unencode(ephentsize, &hdr64.e_phentsize, Elf64_Quarter);
1336 unencode(ephoff, &hdr64.e_phoff, Elf64_Off);
1337 unencode(eshnum, &hdr64.e_shnum, Elf64_Quarter);
1338 unencode(eshentsize, &hdr64.e_shentsize, Elf64_Quarter);
1339 unencode(eshoff, &hdr64.e_shoff, Elf64_Off);
1340 if (ephentsize != sizeof(Elf64_Phdr)) {
1341 fprintf(stderr, "%s: incorrect phentsize? %i, should "
1342 "be %i\nPerhaps this is a dynamically linked "
1343 "binary (which isn't supported yet).\n", filename,
1344 (int)ephentsize, (int)sizeof(Elf64_Phdr));
1345 exit(1);
1346 }
1347 if (eshentsize != sizeof(Elf64_Shdr)) {
1348 fprintf(stderr, "%s: incorrect shentsize? %i, should "
1349 "be %i\nPerhaps this is a dynamically linked "
1350 "binary (which isn't supported yet).\n", filename,
1351 (int)eshentsize, (int)sizeof(Elf64_Shdr));
1352 exit(1);
1353 }
1354 } else {
1355 unencode(etype, &hdr32.e_type, Elf32_Half);
1356 unencode(eflags, &hdr32.e_flags, Elf32_Word);
1357 unencode(emachine, &hdr32.e_machine, Elf32_Half);
1358 unencode(eentry, &hdr32.e_entry, Elf32_Addr);
1359 unencode(ephnum, &hdr32.e_phnum, Elf32_Half);
1360 unencode(ephentsize, &hdr32.e_phentsize, Elf32_Half);
1361 unencode(ephoff, &hdr32.e_phoff, Elf32_Off);
1362 unencode(eshnum, &hdr32.e_shnum, Elf32_Half);
1363 unencode(eshentsize, &hdr32.e_shentsize, Elf32_Half);
1364 unencode(eshoff, &hdr32.e_shoff, Elf32_Off);
1365 if (ephentsize != sizeof(Elf32_Phdr)) {
1366 fprintf(stderr, "%s: incorrect phentsize? %i, should "
1367 "be %i\nPerhaps this is a dynamically linked "
1368 "binary (which isn't supported yet).\n", filename,
1369 (int)ephentsize, (int)sizeof(Elf32_Phdr));
1370 exit(1);
1371 }
1372 if (eshentsize != sizeof(Elf32_Shdr)) {
1373 fprintf(stderr, "%s: incorrect shentsize? %i, should "
1374 "be %i\nPerhaps this is a dynamically linked "
1375 "binary (which isn't supported yet).\n", filename,
1376 (int)eshentsize, (int)sizeof(Elf32_Shdr));
1377 exit(1);
1378 }
1379 }
1380
1381 if ( etype != ET_EXEC ) {
1382 fprintf(stderr, "%s is not an ELF Executable file, type = %i\n",
1383 filename, etype);
1384 exit(1);
1385 }
1386
1387 ok = 0;
1388 switch (arch) {
1389 case ARCH_ALPHA:
1390 switch (emachine) {
1391 case EM_ALPHA:
1392 case -28634:
1393 ok = 1;
1394 }
1395 break;
1396 case ARCH_ARM:
1397 switch (emachine) {
1398 case EM_ARM:
1399 ok = 1;
1400 }
1401 break;
1402 case ARCH_AVR:
1403 switch (emachine) {
1404 case EM_AVR:
1405 ok = 1;
1406 }
1407 break;
1408 case ARCH_HPPA:
1409 switch (emachine) {
1410 case EM_PARISC:
1411 ok = 1;
1412 }
1413 break;
1414 case ARCH_I960:
1415 switch (emachine) {
1416 case EM_960:
1417 ok = 1;
1418 }
1419 break;
1420 case ARCH_IA64:
1421 switch (emachine) {
1422 case EM_IA_64:
1423 ok = 1;
1424 }
1425 break;
1426 case ARCH_M68K:
1427 switch (emachine) {
1428 case EM_68K:
1429 ok = 1;
1430 }
1431 break;
1432 case ARCH_MIPS:
1433 switch (emachine) {
1434 case EM_MIPS:
1435 case EM_MIPS_RS3_LE:
1436 ok = 1;
1437 }
1438 break;
1439 case ARCH_PPC:
1440 switch (emachine) {
1441 case EM_PPC:
1442 case EM_PPC64:
1443 ok = 1;
1444 }
1445 break;
1446 case ARCH_SH:
1447 switch (emachine) {
1448 case EM_SH:
1449 ok = 1;
1450 }
1451 break;
1452 case ARCH_SPARC:
1453 switch (emachine) {
1454 case EM_SPARC:
1455 case EM_SPARCV9:
1456 ok = 1;
1457 }
1458 break;
1459 case ARCH_X86:
1460 switch (emachine) {
1461 case EM_386:
1462 case EM_486:
1463 *tocp = 1;
1464 ok = 1;
1465 break;
1466 case EM_AMD64:
1467 *tocp = 2;
1468 ok = 1;
1469 break;
1470 }
1471 break;
1472 default:
1473 fatal("file.c: INTERNAL ERROR: Unimplemented arch!\n");
1474 }
1475 if (!ok) {
1476 fprintf(stderr, "%s: this is a ", filename);
1477 if (emachine >= 0 && emachine < N_ELF_MACHINE_TYPES)
1478 fprintf(stderr, elf_machine_type[emachine]);
1479 else
1480 fprintf(stderr, "machine type '%i'", emachine);
1481 fprintf(stderr, " ELF binary!\n");
1482 exit(1);
1483 }
1484
1485 s = "entry point";
1486 if (elf64 && arch == ARCH_PPC)
1487 s = "function descriptor at";
1488
1489 debug("ELF%i %s, %s 0x", elf64? 64 : 32,
1490 encoding == ELFDATA2LSB? "LSB (LE)" : "MSB (BE)", s);
1491
1492 if (elf64)
1493 debug("%016"PRIx64"\n", (uint64_t) eentry);
1494 else
1495 debug("%08"PRIx32"\n", (uint32_t) eentry);
1496
1497 /*
1498 * SH64: 32-bit instruction encoding?
1499 */
1500 if (arch == ARCH_SH && (eentry & 1)) {
1501 debug("SH64: 32-bit instruction encoding\n");
1502 m->cpus[0]->cd.sh.compact = 0;
1503 m->cpus[0]->cd.sh.cpu_type.bits = 64;
1504 }
1505
1506 /* Read the program headers: */
1507
1508 for (i=0; i<ephnum; i++) {
1509 int p_type;
1510 uint64_t p_offset;
1511 uint64_t p_vaddr;
1512 uint64_t p_paddr;
1513 uint64_t p_filesz;
1514 uint64_t p_memsz;
1515 int p_flags;
1516 int p_align;
1517
1518 fseek(f, ephoff + i * ephentsize, SEEK_SET);
1519
1520 if (elf64) {
1521 fread(&phdr64, 1, sizeof(Elf64_Phdr), f);
1522 unencode(p_type, &phdr64.p_type, Elf64_Half);
1523 unencode(p_flags, &phdr64.p_flags, Elf64_Half);
1524 unencode(p_offset, &phdr64.p_offset, Elf64_Off);
1525 unencode(p_vaddr, &phdr64.p_vaddr, Elf64_Addr);
1526 unencode(p_paddr, &phdr64.p_paddr, Elf64_Addr);
1527 unencode(p_filesz, &phdr64.p_filesz, Elf64_Xword);
1528 unencode(p_memsz, &phdr64.p_memsz, Elf64_Xword);
1529 unencode(p_align, &phdr64.p_align, Elf64_Xword);
1530 } else {
1531 fread(&phdr32, 1, sizeof(Elf32_Phdr), f);
1532 unencode(p_type, &phdr32.p_type, Elf32_Word);
1533 unencode(p_offset, &phdr32.p_offset, Elf32_Off);
1534 unencode(p_vaddr, &phdr32.p_vaddr, Elf32_Addr);
1535 unencode(p_paddr, &phdr32.p_paddr, Elf32_Addr);
1536 unencode(p_filesz, &phdr32.p_filesz, Elf32_Word);
1537 unencode(p_memsz, &phdr32.p_memsz, Elf32_Word);
1538 unencode(p_flags, &phdr32.p_flags, Elf32_Word);
1539 unencode(p_align, &phdr32.p_align, Elf32_Word);
1540 }
1541
1542 /*
1543 * Hack for loading PPC kernels that are linked to high
1544 * addresses. (This requires enabling of instruction and
1545 * data virtual address translation.)
1546 */
1547 if (arch == ARCH_PPC) {
1548 if ( (elf64 && (p_vaddr >> 60) != 0) ||
1549 (!elf64 && (p_vaddr >> 28) != 0) )
1550 m->cpus[m->bootstrap_cpu]->
1551 cd.ppc.msr |= PPC_MSR_IR | PPC_MSR_DR;
1552 }
1553
1554 if (p_memsz != 0 && (p_type == PT_LOAD ||
1555 (p_type & PF_MASKPROC) == PT_MIPS_REGINFO)) {
1556 debug("chunk %i (", i);
1557 if (p_type == PT_LOAD)
1558 debug("load");
1559 else
1560 debug("0x%08"PRIx32, (uint32_t) p_type);
1561
1562 debug(") @ 0x%"PRIx64", vaddr 0x", (uint64_t) p_offset);
1563
1564 if (elf64)
1565 debug("%016"PRIx64, (uint64_t) p_vaddr);
1566 else
1567 debug("%08"PRIx32, (uint32_t) p_vaddr);
1568
1569 debug(" len=0x%"PRIx64"\n", (uint64_t) p_memsz);
1570
1571 if (p_vaddr != p_paddr) {
1572 if (elf64)
1573 debug("NOTE: vaddr (0x%"PRIx64") and "
1574 "paddr (0x%"PRIx64") differ; using "
1575 "vaddr\n", (uint64_t) p_vaddr,
1576 (uint64_t) p_paddr);
1577 else
1578 debug("NOTE: vaddr (0x%08"PRIx32") and "
1579 "paddr (0x%08"PRIx32") differ; usin"
1580 "g vaddr\n", (uint32_t) p_vaddr,
1581 (uint32_t)p_paddr);
1582 }
1583
1584 if (p_memsz < p_filesz) {
1585 fprintf(stderr, "%s: memsz < filesz. TODO: how"
1586 " to handle this? memsz=%016"PRIx64
1587 " filesz=%016"PRIx64"\n", filename,
1588 (uint64_t) p_memsz, (uint64_t) p_filesz);
1589 exit(1);
1590 }
1591
1592 fseek(f, p_offset, SEEK_SET);
1593 align_len = 1;
1594 if ((p_vaddr & 0xf)==0) align_len = 0x10;
1595 if ((p_vaddr & 0x3f)==0) align_len = 0x40;
1596 if ((p_vaddr & 0xff)==0) align_len = 0x100;
1597 if ((p_vaddr & 0xfff)==0) align_len = 0x1000;
1598 if ((p_vaddr & 0x3fff)==0) align_len = 0x4000;
1599 if ((p_vaddr & 0xffff)==0) align_len = 0x10000;
1600 ofs = 0; len = chunk_len = align_len;
1601 while (ofs < (int64_t)p_filesz && len==chunk_len) {
1602 unsigned char *ch = malloc(chunk_len);
1603 int i = 0;
1604
1605 /* Switch to larger size, if possible: */
1606 if (align_len < 0x10000 &&
1607 ((p_vaddr + ofs) & 0xffff)==0) {
1608 align_len = 0x10000;
1609 len = chunk_len = align_len;
1610 free(ch);
1611 ch = malloc(chunk_len);
1612 } else if (align_len < 0x1000 &&
1613 ((p_vaddr + ofs) & 0xfff)==0) {
1614 align_len = 0x1000;
1615 len = chunk_len = align_len;
1616 free(ch);
1617 ch = malloc(chunk_len);
1618 }
1619
1620 if (ch == NULL) {
1621 fprintf(stderr, "out of memory\n");
1622 exit(1);
1623 }
1624
1625 len = fread(&ch[0], 1, chunk_len, f);
1626 if (ofs + len > (int64_t)p_filesz)
1627 len = p_filesz - ofs;
1628
1629 while (i < len) {
1630 size_t len_to_copy;
1631 len_to_copy = (i + align_len) <= len?
1632 align_len : len - i;
1633 m->cpus[0]->memory_rw(m->cpus[0], mem,
1634 p_vaddr + ofs, &ch[i], len_to_copy,
1635 MEM_WRITE, NO_EXCEPTIONS);
1636 ofs += align_len;
1637 i += align_len;
1638 }
1639
1640 free(ch);
1641 }
1642 }
1643 }
1644
1645 /*
1646 * Read the section headers to find the address of the _gp
1647 * symbol (for MIPS):
1648 */
1649
1650 for (i=0; i<eshnum; i++) {
1651 int sh_name, sh_type, sh_flags, sh_link, sh_info, sh_entsize;
1652 uint64_t sh_addr, sh_size, sh_addralign;
1653 off_t sh_offset;
1654 int n_entries; /* for reading the symbol / string tables */
1655
1656 /* debug("section header %i at %016"PRIx64"\n", i,
1657 (uint64_t) eshoff+i*eshentsize); */
1658
1659 fseek(f, eshoff + i * eshentsize, SEEK_SET);
1660
1661 if (elf64) {
1662 len = fread(&shdr64, 1, sizeof(Elf64_Shdr), f);
1663 if (len != sizeof(Elf64_Shdr)) {
1664 fprintf(stderr, "couldn't read header\n");
1665 exit(1);
1666 }
1667 unencode(sh_name, &shdr64.sh_name, Elf64_Half);
1668 unencode(sh_type, &shdr64.sh_type, Elf64_Half);
1669 unencode(sh_flags, &shdr64.sh_flags, Elf64_Xword);
1670 unencode(sh_addr, &shdr64.sh_addr, Elf64_Addr);
1671 unencode(sh_offset, &shdr64.sh_offset, Elf64_Off);
1672 unencode(sh_size, &shdr64.sh_size, Elf64_Xword);
1673 unencode(sh_link, &shdr64.sh_link, Elf64_Half);
1674 unencode(sh_info, &shdr64.sh_info, Elf64_Half);
1675 unencode(sh_addralign, &shdr64.sh_addralign,
1676 Elf64_Xword);
1677 unencode(sh_entsize, &shdr64.sh_entsize, Elf64_Xword);
1678 } else {
1679 len = fread(&shdr32, 1, sizeof(Elf32_Shdr), f);
1680 if (len != sizeof(Elf32_Shdr)) {
1681 fprintf(stderr, "couldn't read header\n");
1682 exit(1);
1683 }
1684 unencode(sh_name, &shdr32.sh_name, Elf32_Word);
1685 unencode(sh_type, &shdr32.sh_type, Elf32_Word);
1686 unencode(sh_flags, &shdr32.sh_flags, Elf32_Word);
1687 unencode(sh_addr, &shdr32.sh_addr, Elf32_Addr);
1688 unencode(sh_offset, &shdr32.sh_offset, Elf32_Off);
1689 unencode(sh_size, &shdr32.sh_size, Elf32_Word);
1690 unencode(sh_link, &shdr32.sh_link, Elf32_Word);
1691 unencode(sh_info, &shdr32.sh_info, Elf32_Word);
1692 unencode(sh_addralign, &shdr32.sh_addralign,Elf32_Word);
1693 unencode(sh_entsize, &shdr32.sh_entsize, Elf32_Word);
1694 }
1695
1696 /* debug("sh_name=%04lx, sh_type=%08lx, sh_flags=%08lx"
1697 " sh_size=%06lx sh_entsize=%03lx\n",
1698 (long)sh_name, (long)sh_type, (long)sh_flags,
1699 (long)sh_size, (long)sh_entsize); */
1700
1701 /* Perhaps it is bad to reuse sh_entsize like this? TODO */
1702 if (elf64)
1703 sh_entsize = sizeof(Elf64_Sym);
1704 else
1705 sh_entsize = sizeof(Elf32_Sym);
1706
1707 if (sh_type == SHT_SYMTAB) {
1708 size_t len;
1709 n_entries = sh_size / sh_entsize;
1710
1711 fseek(f, sh_offset, SEEK_SET);
1712
1713 if (elf64) {
1714 if (symbols_sym64 != NULL)
1715 free(symbols_sym64);
1716 symbols_sym64 = malloc(sh_size);
1717 if (symbols_sym64 == NULL) {
1718 fprintf(stderr, "out of memory\n");
1719 exit(1);
1720 }
1721
1722 len = fread(symbols_sym64, 1, sh_entsize *
1723 n_entries, f);
1724 } else {
1725 if (symbols_sym32 != NULL)
1726 free(symbols_sym32);
1727 symbols_sym32 = malloc(sh_size);
1728 if (symbols_sym32 == NULL) {
1729 fprintf(stderr, "out of memory\n");
1730 exit(1);
1731 }
1732
1733 len = fread(symbols_sym32, 1,
1734 sh_entsize * n_entries, f);
1735 }
1736
1737 if (len != sh_size) {
1738 fprintf(stderr, "could not read symbols from "
1739 "%s\n", filename);
1740 exit(1);
1741 }
1742
1743 debug("%i symbol entries at 0x%"PRIx64"\n",
1744 (int) n_entries, (uint64_t) sh_offset);
1745
1746 n_symbols = n_entries;
1747 }
1748
1749 /*
1750 * TODO: This is incorrect, there may be several strtab
1751 * sections.
1752 *
1753 * For now, the simple/stupid guess that the largest string
1754 * table is the one to use seems to be good enough.
1755 */
1756
1757 if (sh_type == SHT_STRTAB && sh_size > symbol_length) {
1758 size_t len;
1759
1760 if (symbol_strings != NULL)
1761 free(symbol_strings);
1762
1763 symbol_strings = malloc(sh_size + 1);
1764 if (symbol_strings == NULL) {
1765 fprintf(stderr, "out of memory\n");
1766 exit(1);
1767 }
1768
1769 fseek(f, sh_offset, SEEK_SET);
1770 len = fread(symbol_strings, 1, sh_size, f);
1771 if (len != sh_size) {
1772 fprintf(stderr, "could not read symbols from "
1773 "%s\n", filename);
1774 exit(1);
1775 }
1776
1777 debug("%i bytes of symbol strings at 0x%"PRIx64"\n",
1778 (int) sh_size, (uint64_t) sh_offset);
1779
1780 symbol_strings[sh_size] = '\0';
1781 symbol_length = sh_size;
1782 }
1783 }
1784
1785 fclose(f);
1786
1787 /* Decode symbols: */
1788 if (symbol_strings != NULL) {
1789 for (i=0; i<n_symbols; i++) {
1790 uint64_t st_name, addr, size;
1791 int st_info;
1792
1793 if (elf64) {
1794 sym64 = symbols_sym64[i];
1795 unencode(st_name, &sym64.st_name, Elf64_Half);
1796 unencode(st_info, &sym64.st_info, Elf_Byte);
1797 unencode(addr, &sym64.st_value, Elf64_Addr);
1798 unencode(size, &sym64.st_size, Elf64_Xword);
1799 } else {
1800 sym32 = symbols_sym32[i];
1801 unencode(st_name, &sym32.st_name, Elf32_Word);
1802 unencode(st_info, &sym32.st_info, Elf_Byte);
1803 unencode(addr, &sym32.st_value, Elf32_Word);
1804 unencode(size, &sym32.st_size, Elf32_Word);
1805 }
1806
1807 /* debug("symbol info=0x%02x addr=0x%016"PRIx64
1808 " (%i) '%s'\n", st_info, (uint64_t) addr,
1809 st_name, symbol_strings + st_name); */
1810
1811 if (size == 0)
1812 size ++;
1813
1814 if (addr != 0) /* && ((st_info >> 4) & 0xf)
1815 >= STB_GLOBAL) */ {
1816 /* debug("symbol info=0x%02x addr=0x%016"PRIx64
1817 " '%s'\n", st_info, (uint64_t) addr,
1818 symbol_strings + st_name); */
1819 add_symbol_name(&m->symbol_context,
1820 addr, size, symbol_strings + st_name,
1821 0, -1);
1822 }
1823
1824 if (strcmp(symbol_strings + st_name, "_gp") == 0) {
1825 debug("found _gp address: 0x");
1826 if (elf64)
1827 debug("%016"PRIx64"\n", (uint64_t)addr);
1828 else
1829 debug("%08"PRIx32"\n", (uint32_t)addr);
1830 *gpp = addr;
1831 }
1832 }
1833 }
1834
1835 *entrypointp = eentry;
1836
1837 if (encoding == ELFDATA2LSB)
1838 *byte_order = EMUL_LITTLE_ENDIAN;
1839 else
1840 *byte_order = EMUL_BIG_ENDIAN;
1841
1842 if (elf64 && arch == ARCH_PPC) {
1843 /*
1844 * Special case for 64-bit PPC ELFs:
1845 *
1846 * The ELF starting symbol points to a ".opd" section
1847 * which contains a function descriptor:
1848 *
1849 * uint64_t start;
1850 * uint64_t toc_base;
1851 * uint64_t something_else; (?)
1852 */
1853 int res;
1854 unsigned char b[sizeof(uint64_t)];
1855 uint64_t toc_base;
1856
1857 debug("PPC64: ");
1858
1859 res = m->cpus[0]->memory_rw(m->cpus[0], mem, eentry, b,
1860 sizeof(b), MEM_READ, NO_EXCEPTIONS);
1861 if (!res)
1862 debug(" [WARNING: could not read memory?] ");
1863
1864 /* PPC are always big-endian: */
1865 *entrypointp = ((uint64_t)b[0] << 56) +
1866 ((uint64_t)b[1] << 48) + ((uint64_t)b[2] << 40) +
1867 ((uint64_t)b[3] << 32) + ((uint64_t)b[4] << 24) +
1868 ((uint64_t)b[5] << 16) + ((uint64_t)b[6] << 8) +
1869 (uint64_t)b[7];
1870
1871 res = m->cpus[0]->memory_rw(m->cpus[0], mem, eentry + 8,
1872 b, sizeof(b), MEM_READ, NO_EXCEPTIONS);
1873 if (!res)
1874 fatal(" [WARNING: could not read memory?] ");
1875
1876 toc_base = ((uint64_t)b[0] << 56) +
1877 ((uint64_t)b[1] << 48) + ((uint64_t)b[2] << 40) +
1878 ((uint64_t)b[3] << 32) + ((uint64_t)b[4] << 24) +
1879 ((uint64_t)b[5] << 16) + ((uint64_t)b[6] << 8) +
1880 (uint64_t)b[7];
1881
1882 debug("entrypoint 0x%016"PRIx64", toc_base 0x%016"PRIx64"\n",
1883 (uint64_t) *entrypointp, (uint64_t) toc_base);
1884 if (tocp != NULL)
1885 *tocp = toc_base;
1886 }
1887
1888 n_executables_loaded ++;
1889 }
1890
1891
1892 /*
1893 * file_n_executables_loaded():
1894 *
1895 * Returns the number of executable files loaded into emulated memory.
1896 */
1897 int file_n_executables_loaded(void)
1898 {
1899 return n_executables_loaded;
1900 }
1901
1902
1903 /*
1904 * file_load():
1905 *
1906 * Sense the file format of a file (ELF, a.out, ecoff), and call the
1907 * right file_load_XXX() function. If the file isn't of a recognized
1908 * binary format, assume that it contains symbol definitions.
1909 *
1910 * If the filename doesn't exist, try to treat the name as
1911 * "address:filename" and load the file as a raw binary.
1912 */
1913 void file_load(struct machine *machine, struct memory *mem,
1914 char *filename, uint64_t *entrypointp,
1915 int arch, uint64_t *gpp, int *byte_orderp, uint64_t *tocp)
1916 {
1917 int iadd = DEBUG_INDENTATION, old_quiet_mode;
1918 FILE *f;
1919 unsigned char buf[12];
1920 unsigned char buf2[2];
1921 size_t len, len2, i;
1922 off_t size;
1923
1924 if (byte_orderp == NULL) {
1925 fprintf(stderr, "file_load(): byte_order == NULL\n");
1926 exit(1);
1927 }
1928
1929 if (arch == ARCH_NOARCH) {
1930 fprintf(stderr, "file_load(): FATAL ERROR: no arch?\n");
1931 exit(1);
1932 }
1933
1934 if (mem == NULL || filename == NULL) {
1935 fprintf(stderr, "file_load(): mem or filename is NULL\n");
1936 exit(1);
1937 }
1938
1939 /* Skip configuration files: */
1940 if (filename[0] == '@')
1941 return;
1942
1943 debug("loading %s%s\n", filename, verbose >= 2? ":" : "");
1944 debug_indentation(iadd);
1945
1946 old_quiet_mode = quiet_mode;
1947 if (verbose < 2)
1948 quiet_mode = 1;
1949
1950 f = fopen(filename, "r");
1951 if (f == NULL) {
1952 file_load_raw(machine, mem, filename, entrypointp);
1953 goto ret;
1954 }
1955
1956 fseek(f, 0, SEEK_END);
1957 size = ftello(f);
1958 fseek(f, 0, SEEK_SET);
1959
1960 memset(buf, 0, sizeof(buf));
1961 len = fread(buf, 1, sizeof(buf), f);
1962 fseek(f, 510, SEEK_SET);
1963 len2 = fread(buf2, 1, sizeof(buf2), f);
1964 fclose(f);
1965
1966 if (len < (signed int)sizeof(buf)) {
1967 fprintf(stderr, "\nThis file is too small to contain "
1968 "anything useful\n");
1969 exit(1);
1970 }
1971
1972 /* Is it an ELF? */
1973 if (buf[0] == 0x7f && buf[1]=='E' && buf[2]=='L' && buf[3]=='F') {
1974 file_load_elf(machine, mem, filename,
1975 entrypointp, arch, gpp, byte_orderp, tocp);
1976 goto ret;
1977 }
1978
1979 /* Is it an a.out? */
1980 if (buf[0]==0x00 && buf[1]==0x8b && buf[2]==0x01 && buf[3]==0x07) {
1981 /* MIPS a.out */
1982 file_load_aout(machine, mem, filename, 0,
1983 entrypointp, arch, byte_orderp);
1984 goto ret;
1985 }
1986 if (buf[0]==0x00 && buf[1]==0x87 && buf[2]==0x01 && buf[3]==0x08) {
1987 /* M68K a.out */
1988 file_load_aout(machine, mem, filename,
1989 AOUT_FLAG_VADDR_ZERO_HACK /* for OpenBSD/mac68k */,
1990 entrypointp, arch, byte_orderp);
1991 goto ret;
1992 }
1993 if (buf[0]==0x00 && buf[1]==0x8f && buf[2]==0x01 && buf[3]==0x0b) {
1994 /* ARM a.out */
1995 file_load_aout(machine, mem, filename, AOUT_FLAG_FROM_BEGINNING,
1996 entrypointp, arch, byte_orderp);
1997 goto ret;
1998 }
1999 if (buf[0]==0x00 && buf[1]==0x86 && buf[2]==0x01 && buf[3]==0x0b) {
2000 /* i386 a.out (old OpenBSD and NetBSD etc) */
2001 file_load_aout(machine, mem, filename, AOUT_FLAG_FROM_BEGINNING,
2002 entrypointp, arch, byte_orderp);
2003 goto ret;
2004 }
2005 if (buf[0]==0x01 && buf[1]==0x03 && buf[2]==0x01 && buf[3]==0x07) {
2006 /* SPARC a.out (old 32-bit NetBSD etc) */
2007 file_load_aout(machine, mem, filename, AOUT_FLAG_NO_SIZES,
2008 entrypointp, arch, byte_orderp);
2009 goto ret;
2010 }
2011 if (buf[0]==0x00 && buf[2]==0x00 && buf[8]==0x7a && buf[9]==0x75) {
2012 /* DEC OSF1 on MIPS: */
2013 file_load_aout(machine, mem, filename, AOUT_FLAG_DECOSF1,
2014 entrypointp, arch, byte_orderp);
2015 goto ret;
2016 }
2017
2018 /*
2019 * Is it a Mach-O file?
2020 */
2021 if (buf[0] == 0xfe && buf[1] == 0xed && buf[2] == 0xfa &&
2022 (buf[3] == 0xce || buf[3] == 0xcf)) {
2023 file_load_macho(machine, mem, filename, entrypointp,
2024 arch, byte_orderp, buf[3] == 0xcf, 0);
2025 goto ret;
2026 }
2027 if ((buf[0] == 0xce || buf[0] == 0xcf) && buf[1] == 0xfa &&
2028 buf[2] == 0xed && buf[3] == 0xfe) {
2029 file_load_macho(machine, mem, filename, entrypointp,
2030 arch, byte_orderp, buf[0] == 0xcf, 1);
2031 goto ret;
2032 }
2033
2034 /*
2035 * Is it an ecoff?
2036 *
2037 * TODO: What's the deal with the magic value's byte order? Sometimes
2038 * it seems to be reversed for BE when compared to LE, but not always?
2039 */
2040 if (buf[0]+256*buf[1] == ECOFF_MAGIC_MIPSEB ||
2041 buf[0]+256*buf[1] == ECOFF_MAGIC_MIPSEL ||
2042 buf[0]+256*buf[1] == ECOFF_MAGIC_MIPSEB2 ||
2043 buf[0]+256*buf[1] == ECOFF_MAGIC_MIPSEL2 ||
2044 buf[0]+256*buf[1] == ECOFF_MAGIC_MIPSEB3 ||
2045 buf[0]+256*buf[1] == ECOFF_MAGIC_MIPSEL3 ||
2046 buf[1]+256*buf[0] == ECOFF_MAGIC_MIPSEB ||
2047 buf[1]+256*buf[0] == ECOFF_MAGIC_MIPSEL ||
2048 buf[1]+256*buf[0] == ECOFF_MAGIC_MIPSEB2 ||
2049 buf[1]+256*buf[0] == ECOFF_MAGIC_MIPSEL2 ||
2050 buf[1]+256*buf[0] == ECOFF_MAGIC_MIPSEB3 ||
2051 buf[1]+256*buf[0] == ECOFF_MAGIC_MIPSEL3) {
2052 file_load_ecoff(machine, mem, filename, entrypointp,
2053 arch, gpp, byte_orderp);
2054 goto ret;
2055 }
2056
2057 /* Is it a Motorola SREC file? */
2058 if ((buf[0]=='S' && buf[1]>='0' && buf[1]<='9')) {
2059 file_load_srec(machine, mem, filename, entrypointp);
2060 goto ret;
2061 }
2062
2063 /* gzipped files are not supported: */
2064 if (buf[0]==0x1f && buf[1]==0x8b) {
2065 fprintf(stderr, "\nYou need to gunzip the file before you"
2066 " try to use it.\n");
2067 exit(1);
2068 }
2069
2070 if (size > 24000000) {
2071 fprintf(stderr, "\nThis file is very large (%lli bytes)\n",
2072 (long long)size);
2073 fprintf(stderr, "Are you sure it is a kernel and not a disk "
2074 "image? (Use the -d option.)\n");
2075 exit(1);
2076 }
2077
2078 if (size == 1474560)
2079 fprintf(stderr, "Hm... this file is the size of a 1.44 MB "
2080 "floppy image. Maybe you forgot the\n-d switch?\n");
2081
2082 /*
2083 * Last resort: symbol definitions from nm (or nm -S):
2084 *
2085 * If the buf contains typical 'binary' characters, then print
2086 * an error message and quit instead of assuming that it is a
2087 * symbol file.
2088 */
2089 for (i=0; i<(signed)sizeof(buf); i++)
2090 if (buf[i] < 32 && buf[i] != '\t' &&
2091 buf[i] != '\n' && buf[i] != '\r' &&
2092 buf[i] != '\f') {
2093 fprintf(stderr, "\nThe file format of '%s' is "
2094 "unknown.\n\n ", filename);
2095 for (i=0; i<(signed)sizeof(buf); i++)
2096 fprintf(stderr, " %02x", buf[i]);
2097
2098 if (len2 == 2 && buf2[0] == 0x55 && buf2[1] == 0xaa)
2099 fprintf(stderr, "\n\nIt has a PC-style "
2100 "bootsector marker.");
2101
2102 fprintf(stderr, "\n\nPossible explanations:\n\n"
2103 " o) If this is a disk image, you forgot '-d' "
2104 "on the command line.\n"
2105 " o) This is an unsupported binary format.\n\n");
2106 exit(1);
2107 }
2108
2109 symbol_readfile(&machine->symbol_context, filename);
2110
2111 ret:
2112 debug_indentation(-iadd);
2113 quiet_mode = old_quiet_mode;
2114 }
2115

  ViewVC Help
Powered by ViewVC 1.1.26