Blob


1 // See ../src/libmach/LICENSE
3 #ifndef _MACH_H_
4 #define _MACH_H_ 1
5 #if defined(__cplusplus)
6 extern "C" {
7 #endif
9 AUTOLIB(mach)
11 /*
12 * Architecture-dependent application data.
13 *
14 * The code assumes that u64int is big enough to hold
15 * an address on any system of interest as well as any
16 * register.
17 *
18 * Supported architectures:
19 *
20 * MIPS R3000
21 * Motorola 68020
22 * Intel 386
23 * SPARC
24 * PowerPC (limited)
25 * ARM (limited)
26 * Intel 960 (limited)
27 * AT&T 3210 DSP (limited)
28 * MIPS2 (R4000)
29 */
31 typedef struct Fhdr Fhdr;
32 typedef struct Loc Loc;
33 typedef struct Mach Mach;
34 typedef struct Map Map;
35 typedef struct Regdesc Regdesc;
36 typedef struct Regs Regs;
37 typedef struct Seg Seg;
38 typedef struct Symbol Symbol;
39 typedef struct Symtype Symtype;
41 typedef int (*Tracer)(Map*, Regs*, u64int, u64int, Symbol*, int);
43 extern Mach *mach;
44 extern Mach *machcpu;
46 /*
47 * Byte-order data layout manipulation.
48 * swap.c ieee.c
49 */
50 u16int beswap2(u16int u);
51 u32int beswap4(u32int u);
52 u64int beswap8(u64int u);
53 int beieeeftoa32(char*, uint, void*);
54 int beieeeftoa64(char*, uint, void*);
55 int beieeeftoa80(char*, uint, void*);
57 u16int leswap2(u16int u);
58 u32int leswap4(u32int u);
59 u64int leswap8(u64int u);
60 int leieeeftoa32(char *a, uint n, void *v);
61 int leieeeftoa64(char *a, uint n, void *v);
62 int leieeeftoa80(char *a, uint n, void *v);
64 u16int beload2(uchar*);
65 u32int beload4(uchar*);
66 u64int beload8(uchar*);
68 u16int leload2(uchar*);
69 u32int leload4(uchar*);
70 u64int leload8(uchar*);
72 int ieeeftoa32(char *a, uint n, u32int u);
73 int ieeeftoa64(char *a, uint n, u32int h, u32int u);
75 /*
76 * Machine-independent access to an executable image.
77 * map.c
78 */
79 struct Seg
80 {
81 char *name;
82 char *file;
83 uchar *p;
84 int fd;
85 int pid;
86 u64int base;
87 u64int size;
88 u64int offset;
89 int (*rw)(Map*, Seg*, u64int, void*, uint, int);
90 };
92 struct Map
93 {
94 int nseg;
95 Seg *seg;
96 };
98 struct Regs
99 {
100 int (*rw)(Regs*, char*, u64int*, int);
101 };
103 typedef struct UregRegs UregRegs;
104 struct UregRegs
106 Regs r;
107 uchar *ureg;
108 };
109 int _uregrw(Regs*, char*, u64int*, int);
111 typedef struct PidRegs PidRegs;
112 struct PidRegs
114 Regs r;
115 int pid;
116 };
118 Map* allocmap(void);
119 int addseg(Map *map, Seg seg);
120 int findseg(Map *map, char *name, char *file);
121 int addrtoseg(Map *map, u64int addr, Seg *seg);
122 int addrtosegafter(Map *map, u64int addr, Seg *seg);
123 void removeseg(Map *map, int i);
124 void freemap(Map*);
126 int get1(Map *map, u64int addr, uchar *a, uint n);
127 int get2(Map *map, u64int addr, u16int *u);
128 int get4(Map *map, u64int addr, u32int *u);
129 int get8(Map *map, u64int addr, u64int *u);
130 int geta(Map *map, u64int addr, u64int *u);
132 int put1(Map *map, u64int addr, uchar *a, uint n);
133 int put2(Map *map, u64int addr, u16int u);
134 int put4(Map *map, u64int addr, u32int u);
135 int put8(Map *map, u64int addr, u64int u);
137 int rget(Regs*, char*, u64int*);
138 int rput(Regs*, char*, u64int);
140 /*
141 * A location is either a memory address or a register.
142 * It is useful to be able to specify constant values that
143 * originate from outside the register set and memory,
144 * hence LCONST. If the register values are known, then
145 * we can dispense with LOFFSET, but it's useful to be able
146 * to look up local symbols (via findlsym) with locations
147 * like 8(BP).
149 * loc.c
150 */
152 enum
154 /* location type */
155 LNONE,
156 LREG, /* register */
157 LADDR, /* absolute address */
158 LCONST, /* constant (an anonymous readonly location) */
159 LOFFSET /* dereference offset + register ptr */
160 };
162 struct Loc
164 uint type; /* LNONE, ... */
165 char *reg; /* LREG */
166 u64int addr; /* LADDR, CONST */
167 long offset; /* LOFFSET */
168 };
170 int lget1(Map *map, Regs *regs, Loc loc, uchar *a, uint n);
171 int lget2(Map *map, Regs *regs, Loc loc, u16int *v);
172 int lget4(Map *map, Regs *regs, Loc loc, u32int *v);
173 int lget8(Map *map, Regs *regs, Loc loc, u64int *v);
174 int lgeta(Map *map, Regs *regs, Loc loc, u64int *v);
176 int lput1(Map *map, Regs *regs, Loc loc, uchar *a, uint n);
177 int lput2(Map *map, Regs *regs, Loc loc, u16int v);
178 int lput4(Map *map, Regs *regs, Loc loc, u32int v);
179 int lput8(Map *map, Regs *regs, Loc loc, u64int v);
181 Loc locnone(void);
182 Loc locaddr(u64int addr);
183 Loc locconst(u64int con);
184 Loc locreg(char*);
185 Loc locindir(char*, long);
187 /*
188 * Executable file parsing.
190 * An Fhdr represents an open file image.
191 * The contents are a grab bag of constants used for the
192 * various file types. Not all elements are used by all
193 * file types.
195 * crackadotplan9.c crackadotunix.c
196 * crackelf.c crackdwarf.c
197 */
198 enum
200 /* file types */
201 FNONE,
202 FEXEC, /* executable image */
203 FLIB, /* library */
204 FOBJ, /* object file */
205 FRELOC, /* relocatable executable */
206 FSHLIB, /* shared library */
207 FSHOBJ, /* shared object */
208 FCORE, /* core dump */
209 FBOOT, /* bootable image */
210 FKERNEL, /* kernel image */
211 NFTYPE,
213 /* abi types */
214 ANONE = 0,
215 APLAN9,
216 ALINUX,
217 AFREEBSD,
218 AMACH,
219 NATYPE
220 };
222 /* I wish this could be kept in stabs.h */
223 struct Stab
225 uchar *stabbase;
226 uint stabsize;
227 char *strbase;
228 uint strsize;
229 u16int (*e2)(uchar*);
230 u32int (*e4)(uchar*);
231 };
233 struct Fhdr
235 int fd; /* file descriptor */
236 char *filename; /* file name */
237 Mach *mach; /* machine */
238 char *mname; /* 386, power, ... */
239 uint mtype; /* machine type M386, ... */
240 char *fname; /* core, executable, boot image, ... */
241 uint ftype; /* file type FCORE, ... */
242 char *aname; /* abi name */
243 uint atype; /* abi type ALINUX, ... */
245 ulong magic; /* magic number */
246 u64int txtaddr; /* text address */
247 u64int entry; /* entry point */
248 u64int txtsz; /* text size */
249 u64int txtoff; /* text offset in file */
250 u64int dataddr; /* data address */
251 u64int datsz; /* data size */
252 u64int datoff; /* data offset in file */
253 u64int bsssz; /* bss size */
254 u64int symsz; /* symbol table size */
255 u64int symoff; /* symbol table offset in file */
256 u64int sppcsz; /* size of sp-pc table */
257 u64int sppcoff; /* offset of sp-pc table in file */
258 u64int lnpcsz; /* size of line number-pc table */
259 u64int lnpcoff; /* size of line number-pc table */
260 void *elf; /* handle to elf image */
261 void *dwarf; /* handle to dwarf image */
262 void *macho; /* handle to mach-o image */
263 struct Stab stabs;
264 uint pid; /* for core files */
265 char *prog; /* program name, for core files */
266 char *cmdline; /* command-line that produced core */
267 struct { /* thread state for core files */
268 uint id;
269 void *ureg;
270 } *thread;
271 uint nthread;
273 /* private */
274 Symbol *sym; /* cached list of symbols */
275 Symbol **byname;
276 Symbol **byxname;
277 uint nsym;
278 Symbol *esym; /* elf symbols */
279 uint nesym;
280 ulong base; /* base address for relocatables */
281 Fhdr *next; /* link to next fhdr (internal) */
283 /* file mapping */
284 int (*map)(Fhdr*, u64int, Map*, Regs**);
286 /* debugging symbol access; see below */
287 int (*syminit)(Fhdr*);
288 void (*symclose)(Fhdr*);
290 int (*pc2file)(Fhdr*, u64int, char*, uint, ulong*);
291 int (*file2pc)(Fhdr*, char*, u64int, u64int*);
292 int (*line2pc)(Fhdr*, u64int, ulong, u64int*);
294 int (*lookuplsym)(Fhdr*, Symbol*, char*, Symbol*);
295 int (*indexlsym)(Fhdr*, Symbol*, uint, Symbol*);
296 int (*findlsym)(Fhdr*, Symbol*, Loc, Symbol*);
298 int (*unwind)(Fhdr*, Map*, Regs*, u64int*, Symbol*);
299 };
301 Fhdr* crackhdr(char *file, int mode);
302 void uncrackhdr(Fhdr *hdr);
303 int crackelf(int fd, Fhdr *hdr);
304 int crackmacho(int fd, Fhdr *hdr);
305 Regs* coreregs(Fhdr*, uint);
307 int symopen(Fhdr*);
308 int symdwarf(Fhdr*);
309 int symelf(Fhdr*);
310 int symstabs(Fhdr*);
311 int symmacho(Fhdr*);
312 void symclose(Fhdr*);
314 int mapfile(Fhdr *fp, u64int base, Map *map, Regs **regs);
315 void unmapfile(Fhdr *fp, Map *map);
317 /*
318 * Process manipulation.
319 */
320 int mapproc(int pid, Map *map, Regs **regs);
321 void unmapproc(Map *map);
322 int detachproc(int pid);
323 int ctlproc(int pid, char *msg);
324 int procnotes(int pid, char ***notes);
325 char* proctextfile(int pid);
327 /*
328 * Command-line debugger help
329 */
330 extern Fhdr *symhdr;
331 extern Fhdr *corhdr;
332 extern char *symfil;
333 extern char *corfil;
334 extern int corpid;
335 extern Regs *correg;
336 extern Map *symmap;
337 extern Map *cormap;
339 int attachproc(int pid);
340 int attachcore(Fhdr *hdr);
341 int attachargs(int argc, char **argv, int omode, int);
342 int attachdynamic(int);
343 /*
344 * Machine descriptions.
346 * mach.c
347 * mach386.c dis386.c
348 * machsparc.c dissparc.c
349 * ...
350 */
352 /*
353 * Register sets. The Regs are opaque, accessed by using
354 * the reglist (and really the accessor functions).
355 */
356 enum
358 /* must be big enough for all machine register sets */
359 REGSIZE = 256,
361 RINT = 0<<0,
362 RFLT = 1<<0,
363 RRDONLY = 1<<1
364 };
366 struct Regdesc
368 char *name; /* register name */
369 uint offset; /* offset in b */
370 uint flags; /* RINT/RFLT/RRDONLY */
371 uint format; /* print format: 'x', 'X', 'f', 'z', 'Z' */
372 };
374 enum
376 /* machine types */
377 MNONE,
378 MMIPS, /* MIPS R3000 */
379 MSPARC, /* SUN SPARC */
380 M68000, /* Motorola 68000 */
381 M386, /* Intel 32-bit x86*/
382 M960, /* Intel 960 */
383 M3210, /* AT&T 3210 DSP */
384 MMIPS2, /* MIPS R4000 */
385 M29000, /* AMD 29000 */
386 MARM, /* ARM */
387 MPOWER, /* PowerPC */
388 MALPHA, /* DEC/Compaq Alpha */
389 MAMD64, /* AMD64 */
390 NMTYPE
391 };
393 struct Mach
395 char *name; /* "386", ... */
396 uint type; /* M386, ... */
397 Regdesc *reglist; /* register set */
398 uint regsize; /* size of register set in bytes */
399 uint fpregsize; /* size of fp register set in bytes */
400 char *pc; /* name of program counter */
401 char *sp; /* name of stack pointer */
402 char *fp; /* name of frame pointer */
403 char *link; /* name of link register */
404 char *sbreg; /* name of static base */
405 ulong sb; /* value of static base */
406 uint pgsize; /* page size */
407 u64int kbase; /* kernel base address for Plan 9 */
408 u64int ktmask; /* ktzero = kbase & ~ktmask */
409 uint pcquant; /* pc quantum */
410 uint szaddr; /* size of pointer in bytes */
411 uint szreg; /* size of integer register */
412 uint szfloat; /* size of float */
413 uint szdouble; /* size of double */
414 char** windreg; /* unwinding registers */
415 uint nwindreg;
417 uchar bpinst[4]; /* break point instruction */
418 uint bpsize; /* size of bp instruction */
420 int (*foll)(Map*, Regs*, u64int, u64int*); /* follow set */
421 char* (*exc)(Map*, Regs*); /* last exception */
422 int (*unwind)(Map*, Regs*, u64int*, Symbol*);
424 /* cvt to local byte order */
425 u16int (*swap2)(u16int);
426 u32int (*swap4)(u32int);
427 u64int (*swap8)(u64int);
428 int (*ftoa32)(char*, uint, void*);
429 int (*ftoa64)(char*, uint, void*);
430 int (*ftoa80)(char*, uint, void*);
432 /* disassembly */
433 int (*das)(Map*, u64int, char, char*, int); /* symbolic */
434 int (*kendas)(Map*, u64int, char, char*, int); /* symbolic */
435 int (*codas)(Map*, u64int, char, char*, int);
436 int (*hexinst)(Map*, u64int, char*, int); /* hex */
437 int (*instsize)(Map*, u64int); /* instruction size */
438 };
440 Mach *machbyname(char*);
441 Mach *machbytype(uint);
443 extern Mach mach386;
444 extern Mach machsparc;
445 extern Mach machmips;
446 extern Mach machpower;
447 extern Mach machamd64;
449 /*
450 * Debugging symbols and type information.
451 * (Not all objects include type information.)
453 * sym.c
454 */
456 enum
458 /* symbol table classes */
459 CNONE,
460 CAUTO, /* stack variable */
461 CPARAM, /* function parameter */
462 CTEXT, /* text segment */
463 CDATA, /* data segment */
464 CANY
465 };
467 struct Symbol
469 char *name; /* name of symbol */
470 char *xname; /* demangled name */
472 /* Symtype *typedesc; /* type info, if any */
473 Loc loc; /* location of symbol */
474 Loc hiloc; /* location of end of symbol */
475 char class; /* CAUTO, ... */
476 char type; /* type letter from a.out.h */
477 Fhdr *fhdr; /* where did this come from? */
478 uint index; /* in by-address list */
480 /* private use by various symbol implementations */
481 union {
482 struct {
483 uint unit;
484 uint uoff;
485 } dwarf;
486 struct {
487 uint i;
488 uint locals;
489 char *dir;
490 char *file;
491 schar frameptr;
492 uint framesize;
493 } stabs;
494 } u;
496 void *aux; /* for use by client */
497 };
499 /* look through all currently cracked Fhdrs calling their fns */
500 int pc2file(u64int pc, char *file, uint nfile, ulong *line);
501 int file2pc(char *file, ulong line, u64int *addr);
502 int line2pc(u64int basepc, ulong line, u64int *pc);
503 int fnbound(u64int pc, u64int *bounds);
504 int fileline(u64int pc, char *a, uint n);
505 int pc2line(u64int pc, ulong *line);
507 int lookupsym(char *fn, char *var, Symbol *s);
508 int indexsym(uint ndx, Symbol *s);
509 int findsym(Loc loc, uint class, Symbol *s);
510 int findexsym(Fhdr*, uint, Symbol*);
512 int lookuplsym(Symbol *s1, char *name, Symbol *s2);
513 int indexlsym(Symbol *s1, uint ndx, Symbol *s2);
514 int findlsym(Symbol *s1, Loc loc, Symbol *s);
515 int symoff(char *a, uint n, u64int addr, uint class);
516 int unwindframe(Map *map, Regs *regs, u64int *next, Symbol*);
518 void _addhdr(Fhdr*);
519 void _delhdr(Fhdr*);
520 extern Fhdr* fhdrlist;
521 Fhdr* findhdr(char*);
523 Symbol* flookupsym(Fhdr*, char*);
524 Symbol* ffindsym(Fhdr*, Loc, uint);
525 Symbol* _addsym(Fhdr*, Symbol*);
527 char* demangle(char*, char*, int);
528 char* demanglegcc3(char*, char*);
529 char* demanglegcc2(char*, char*);
530 /*
531 * Stack frame walking.
533 * frame.c
534 */
535 int stacktrace(Map*, Regs*, Tracer);
536 int windindex(char*);
537 Loc* windreglocs(void);
539 /*
540 * Debugger help.
541 */
542 int localaddr(Map *map, Regs *regs, char *fn, char *var, u64int *val);
543 int fpformat(Map *map, Regdesc *reg, char *a, uint n, uint code);
544 char* _hexify(char*, u64int, int);
545 int locfmt(Fmt*);
546 int loccmp(Loc*, Loc*);
547 int locsimplify(Map *map, Regs *regs, Loc loc, Loc *newloc);
548 Regdesc* regdesc(char*);
550 extern int machdebug;
551 #if defined(__cplusplus)
553 #endif
554 #endif