diff options
Diffstat (limited to 'utils/8l')
| -rw-r--r-- | utils/8l/Nt.c | 77 | ||||
| -rw-r--r-- | utils/8l/Plan9.c | 57 | ||||
| -rw-r--r-- | utils/8l/Posix.c | 80 | ||||
| -rw-r--r-- | utils/8l/asm.c | 67 | ||||
| -rw-r--r-- | utils/8l/l.h | 31 | ||||
| -rw-r--r-- | utils/8l/list.c | 44 | ||||
| -rw-r--r-- | utils/8l/mkfile | 8 | ||||
| -rw-r--r-- | utils/8l/obj.c | 187 | ||||
| -rw-r--r-- | utils/8l/pass.c | 5 | ||||
| -rw-r--r-- | utils/8l/span.c | 46 |
10 files changed, 259 insertions, 343 deletions
diff --git a/utils/8l/Nt.c b/utils/8l/Nt.c deleted file mode 100644 index 73c6f795..00000000 --- a/utils/8l/Nt.c +++ /dev/null @@ -1,77 +0,0 @@ -#include <windows.h> -#include "l.h" - -/* - * fake malloc - */ -void* -malloc(uint n) -{ - void *p; - - while(n & 7) - n++; - while(nhunk < n) - gethunk(); - p = hunk; - nhunk -= n; - hunk += n; - return p; -} - -void -free(void *p) -{ - USED(p); -} - -void* -calloc(uint m, uint n) -{ - void *p; - - n *= m; - p = malloc(n); - memset(p, 0, n); - return p; -} - -void* -realloc(void *p, uint n) -{ - void *new; - - new = malloc(n); - if(new && p) - memmove(new, p, n); - return new; -} - -#define Chunk (1*1024*1024) - -void* -mysbrk(ulong size) -{ - void *v; - static int chunk; - static uchar *brk; - - if(chunk < size) { - chunk = Chunk; - if(chunk < size) - chunk = Chunk + size; - brk = VirtualAlloc(NULL, chunk, MEM_COMMIT, PAGE_EXECUTE_READWRITE); - if(brk == 0) - return (void*)-1; - } - v = brk; - chunk -= size; - brk += size; - return v; -} - -double -cputime(void) -{ - return ((double)0); -} diff --git a/utils/8l/Plan9.c b/utils/8l/Plan9.c deleted file mode 100644 index f4cf23f4..00000000 --- a/utils/8l/Plan9.c +++ /dev/null @@ -1,57 +0,0 @@ -#include "l.h" - -/* - * fake malloc - */ -void* -malloc(ulong n) -{ - void *p; - - while(n & 7) - n++; - while(nhunk < n) - gethunk(); - p = hunk; - nhunk -= n; - hunk += n; - return p; -} - -void -free(void *p) -{ - USED(p); -} - -void* -calloc(ulong m, ulong n) -{ - void *p; - - n *= m; - p = malloc(n); - memset(p, 0, n); - return p; -} - -void* -realloc(void *p, ulong n) -{ - USED(p); - USED(n); - fprint(2, "realloc called\n"); - abort(); - return 0; -} - -void* -mysbrk(ulong size) -{ - return sbrk(size); -} - -void -setmalloctag(void*, ulong) -{ -} diff --git a/utils/8l/Posix.c b/utils/8l/Posix.c deleted file mode 100644 index 0da0ee0c..00000000 --- a/utils/8l/Posix.c +++ /dev/null @@ -1,80 +0,0 @@ -#include "l.h" -#include <sys/types.h> -#include <sys/times.h> -#undef getwd -#include <unistd.h> /* For sysconf() and _SC_CLK_TCK */ - -/* - * fake malloc - */ -void* -malloc(size_t n) -{ - void *p; - - while(n & 7) - n++; - while(nhunk < n) - gethunk(); - p = hunk; - nhunk -= n; - hunk += n; - return p; -} - -void -free(void *p) -{ - USED(p); -} - -void* -calloc(size_t m, size_t n) -{ - void *p; - - n *= m; - p = malloc(n); - memset(p, 0, n); - return p; -} - -void* -realloc(void *p, size_t n) -{ - fprint(2, "realloc called\n", p, n); - abort(); - return 0; -} - -void* -mysbrk(ulong size) -{ - return (void*)sbrk(size); -} - -double -cputime(void) -{ - - struct tms tmbuf; - double ret_val; - - /* - * times() only fails if &tmbuf is invalid. - */ - (void)times(&tmbuf); - /* - * Return the total time (in system clock ticks) - * spent in user code and system - * calls by both the calling process and its children. - */ - ret_val = (double)(tmbuf.tms_utime + tmbuf.tms_stime + - tmbuf.tms_cutime + tmbuf.tms_cstime); - /* - * Convert to seconds. - */ - ret_val *= sysconf(_SC_CLK_TCK); - return ret_val; - -} diff --git a/utils/8l/asm.c b/utils/8l/asm.c index a1bb36ba..6d09ae7c 100644 --- a/utils/8l/asm.c +++ b/utils/8l/asm.c @@ -2,8 +2,6 @@ #define Dbufslop 100 -#define PADDR(a) ((ulong)(a) & ~0xF0000000) - long entryvalue(void) { @@ -28,15 +26,16 @@ entryvalue(void) return s->value; } +/* these need to take long arguments to be compatible with elf.c */ void -wputl(ushort w) +wputl(long w) { cput(w); cput(w>>8); } void -wput(ushort w) +wput(long w) { cput(w>>8); cput(w); @@ -61,6 +60,20 @@ lputl(long l) } void +llput(vlong v) +{ + lput(v>>32); + lput(v); +} + +void +llputl(vlong v) +{ + lputl(v); + lputl(v>>32); +} + +void strnput(char *s, int n) { for(; *s && n > 0; s++){ @@ -335,51 +348,7 @@ asmb(void) wputl(0x0000); /* overlay number */ break; case 5: - strnput("\177ELF", 4); /* e_ident */ - cput(1); /* class = 32 bit */ - cput(1); /* data = LSB */ - cput(1); /* version = CURRENT */ - strnput("", 9); - wputl(2); /* type = EXEC */ - wputl(3); /* machine = 386 */ - lputl(1L); /* version = CURRENT */ - lputl(PADDR(entryvalue())); /* entry vaddr */ - lputl(52L); /* offset to first phdr */ - lputl(0L); /* offset to first shdr */ - lputl(0L); /* flags = 386 */ - wputl(52); /* Ehdr size */ - wputl(32); /* Phdr size */ - wputl(3); /* # of Phdrs */ - wputl(0); /* Shdr size */ - wputl(0); /* # of Shdrs */ - wputl(0); /* Shdr string size */ - - lputl(1L); /* text - type = PT_LOAD */ - lputl(HEADR); /* file offset */ - lputl(INITTEXT); /* vaddr */ - lputl(PADDR(INITTEXT)); /* paddr */ - lputl(textsize); /* file size */ - lputl(textsize); /* memory size */ - lputl(0x05L); /* protections = RX */ - lputl(INITRND); /* alignment */ - - lputl(1L); /* data - type = PT_LOAD */ - lputl(HEADR+textsize); /* file offset */ - lputl(INITDAT); /* vaddr */ - lputl(PADDR(INITDAT)); /* paddr */ - lputl(datsize); /* file size */ - lputl(datsize+bsssize); /* memory size */ - lputl(0x06L); /* protections = RW */ - lputl(INITRND); /* alignment */ - - lputl(0L); /* data - type = PT_NULL */ - lputl(HEADR+textsize+datsize); /* file offset */ - lputl(0L); - lputl(0L); - lputl(symsize); /* symbol table size */ - lputl(lcsize); /* line number size */ - lputl(0x04L); /* protections = R */ - lputl(0x04L); /* alignment */ + elf32(I386, ELFDATA2LSB, 0, nil); break; } cflush(); diff --git a/utils/8l/l.h b/utils/8l/l.h index e3be6b17..c03f7adf 100644 --- a/utils/8l/l.h +++ b/utils/8l/l.h @@ -1,6 +1,7 @@ #include <lib9.h> #include <bio.h> #include "../8c/8.out.h" +#include "../8l/elf.h" #ifndef EXTERN #define EXTERN extern @@ -15,6 +16,8 @@ if(--cbc <= 0)\ cflush(); } +#define LIBNAMELEN 300 + typedef struct Adr Adr; typedef struct Prog Prog; typedef struct Sym Sym; @@ -36,7 +39,7 @@ struct Adr Sym* u1sym; } u1; short type; - char index; + uchar index; char scale; }; @@ -57,11 +60,12 @@ struct Prog Prog* pcond; /* work on this */ long pc; long line; - uchar mark; /* work on these */ - uchar back; - short as; char width; /* fake for DATA */ + char ft; /* oclass cache */ + char tt; + uchar mark; /* work on these */ + uchar back; }; struct Auto { @@ -188,7 +192,7 @@ EXTERN union { struct { - char obuf[MAXIO]; /* output buffer */ + uchar obuf[MAXIO]; /* output buffer */ uchar ibuf[MAXIO]; /* input buffer */ } u; char dbuf[1]; @@ -197,23 +201,28 @@ EXTERN union #define cbuf u.obuf #define xbuf u.ibuf +#pragma varargck type "A" int #pragma varargck type "A" uint #pragma varargck type "D" Adr* #pragma varargck type "P" Prog* #pragma varargck type "R" int +#pragma varargck type "R" uint #pragma varargck type "S" char* +#pragma varargck argpos diag 1 + EXTERN long HEADR; EXTERN long HEADTYPE; EXTERN long INITDAT; EXTERN long INITRND; EXTERN long INITTEXT; +EXTERN long INITTEXTP; EXTERN char* INITENTRY; /* entry point */ EXTERN Biobuf bso; EXTERN long bsssize; EXTERN long casepc; EXTERN int cbc; -EXTERN char* cbp; +EXTERN uchar* cbp; EXTERN char* pcstr; EXTERN int cout; EXTERN Auto* curauto; @@ -281,6 +290,7 @@ int Pconv(Fmt*); int Rconv(Fmt*); int Sconv(Fmt*); void addhist(long, int); +void addlibpath(char*); Prog* appendp(Prog*); void asmb(void); void asmdyn(void); @@ -306,8 +316,10 @@ void dynreloc(Sym*, ulong, int); long entryvalue(void); void errorexit(void); void export(void); +int fileexists(char*); int find1(long, int); int find2(long, int); +char* findlib(char*); void follow(void); void gethunk(void); void histtoauto(void); @@ -320,6 +332,8 @@ void listinit(void); Sym* lookup(char*, int); void lput(long); void lputl(long); +void llput(vlong v); +void llputl(vlong v); void main(int, char*[]); void mkfwd(void); void* mysbrk(ulong); @@ -333,10 +347,12 @@ int relinv(int); long reuse(Prog*, Sym*); long rnd(long, long); void span(void); +void strnput(char*, int); void undef(void); void undefsym(Sym*); long vaddr(Adr*); -void wput(ushort); +void wput(long); +void wputl(long); void xdefine(char*, int, long); void xfol(Prog*); int zaddr(uchar*, Adr*, Sym*[]); @@ -346,4 +362,3 @@ void zerosig(char*); #pragma varargck type "P" Prog* #pragma varargck type "R" int #pragma varargck type "A" int -#pragma varargck argpos diag 1 diff --git a/utils/8l/list.c b/utils/8l/list.c index f52477d5..f452b758 100644 --- a/utils/8l/list.c +++ b/utils/8l/list.c @@ -24,18 +24,18 @@ Pconv(Fmt *fp) switch(p->as) { case ATEXT: if(p->from.scale) { - sprint(str, "(%ld) %A %D,%d,%D", + snprint(str, sizeof(str), "(%ld) %A %D,%d,%D", p->line, p->as, &p->from, p->from.scale, &p->to); break; } default: - sprint(str, "(%ld) %A %D,%D", + snprint(str, sizeof(str), "(%ld) %A %D,%D", p->line, p->as, &p->from, &p->to); break; case ADATA: case AINIT: case ADYNT: - sprint(str, "(%ld) %A %D/%d,%D", + snprint(str, sizeof(str), "(%ld) %A %D/%d,%D", p->line, p->as, &p->from, p->from.scale, &p->to); break; } @@ -55,7 +55,7 @@ Aconv(Fmt *fp) int Dconv(Fmt *fp) { - char str[40], s[20]; + char str[STRINGSZ+40], s[20]; Adr *a; int i; @@ -63,15 +63,15 @@ Dconv(Fmt *fp) i = a->type; if(i >= D_INDIR) { if(a->offset) - sprint(str, "%ld(%R)", a->offset, i-D_INDIR); + snprint(str, sizeof(str), "%ld(%R)", a->offset, i-D_INDIR); else - sprint(str, "(%R)", i-D_INDIR); + snprint(str, sizeof(str), "(%R)", i-D_INDIR); goto brk; } switch(i) { default: - sprint(str, "%R", i); + snprint(str, sizeof(str), "%R", i); break; case D_NONE: @@ -81,57 +81,57 @@ Dconv(Fmt *fp) case D_BRANCH: if(bigP != P && bigP->pcond != P) if(a->sym != S) - sprint(str, "%lux+%s", bigP->pcond->pc, + snprint(str, sizeof(str), "%lux+%s", bigP->pcond->pc, a->sym->name); else - sprint(str, "%lux", bigP->pcond->pc); + snprint(str, sizeof(str), "%lux", bigP->pcond->pc); else - sprint(str, "%ld(PC)", a->offset); + snprint(str, sizeof(str), "%ld(PC)", a->offset); break; case D_EXTERN: - sprint(str, "%s+%ld(SB)", a->sym->name, a->offset); + snprint(str, sizeof(str), "%s+%ld(SB)", a->sym->name, a->offset); break; case D_STATIC: - sprint(str, "%s<%d>+%ld(SB)", a->sym->name, + snprint(str, sizeof(str), "%s<%d>+%ld(SB)", a->sym->name, a->sym->version, a->offset); break; case D_AUTO: - sprint(str, "%s+%ld(SP)", a->sym->name, a->offset); + snprint(str, sizeof(str), "%s+%ld(SP)", a->sym->name, a->offset); break; case D_PARAM: if(a->sym) - sprint(str, "%s+%ld(FP)", a->sym->name, a->offset); + snprint(str, sizeof(str), "%s+%ld(FP)", a->sym->name, a->offset); else - sprint(str, "%ld(FP)", a->offset); + snprint(str, sizeof(str), "%ld(FP)", a->offset); break; case D_CONST: - sprint(str, "$%ld", a->offset); + snprint(str, sizeof(str), "$%ld", a->offset); break; case D_FCONST: - sprint(str, "$(%.8lux,%.8lux)", a->ieee.h, a->ieee.l); + snprint(str, sizeof(str), "$(%.8lux,%.8lux)", a->ieee.h, a->ieee.l); break; case D_SCONST: - sprint(str, "$\"%S\"", a->scon); + snprint(str, sizeof(str), "$\"%S\"", a->scon); break; case D_ADDR: a->type = a->index; a->index = D_NONE; - sprint(str, "$%D", a); + snprint(str, sizeof(str), "$%D", a); a->index = a->type; a->type = D_ADDR; goto conv; } brk: if(a->index != D_NONE) { - sprint(s, "(%R*%d)", a->index, a->scale); + snprint(s, sizeof(s), "(%R*%d)", a->index, a->scale); strcat(str, s); } conv: @@ -218,9 +218,9 @@ Rconv(Fmt *fp) r = va_arg(fp->args, int); if(r >= D_AL && r <= D_NONE) - sprint(str, "%s", regstr[r-D_AL]); + snprint(str, sizeof(str), "%s", regstr[r-D_AL]); else - sprint(str, "gok(%d)", r); + snprint(str, sizeof(str), "gok(%d)", r); return fmtstrcpy(fp, str); } diff --git a/utils/8l/mkfile b/utils/8l/mkfile index aa383d07..8fbf064c 100644 --- a/utils/8l/mkfile +++ b/utils/8l/mkfile @@ -11,6 +11,7 @@ OFILES=\ list.$O\ enam.$O\ $TARGMODEL.$O\ + elf.$O\ HFILES=\ l.h\ @@ -23,7 +24,12 @@ BIN=$ROOT/$OBJDIR/bin <$ROOT/mkfiles/mkone-$SHELLTYPE -CFLAGS= $CFLAGS -I../include +CFLAGS= $CFLAGS -I../include -I. enam.$O: ../8c/enam.c $CC $CFLAGS ../8c/enam.c +elf.$O: ../ld/elf.c + $CC $CFLAGS ../ld/elf.c + +$TARGMODEL.$O: ../ld/$TARGMODEL.c + $CC $CFLAGS ../ld/$TARGMODEL.c diff --git a/utils/8l/obj.c b/utils/8l/obj.c index a2cd7c9a..d8a4bed1 100644 --- a/utils/8l/obj.c +++ b/utils/8l/obj.c @@ -11,6 +11,10 @@ char symname[] = SYMDEF; char thechar = '8'; char *thestring = "386"; +char** libdir; +int nlibdir = 0; +static int maxlibdir = 0; + /* * -H0 -T0x40004C -D0x10000000 is garbage unix * -H1 -T0xd0 -R4 is unix coff @@ -20,6 +24,13 @@ char *thestring = "386"; * -H5 -T0x80100020 -R4096 is ELF */ +void +usage(void) +{ + diag("usage: %s [-options] objects", argv0); + errorexit(); +} + static int isobjfile(char *f) { @@ -47,6 +58,7 @@ main(int argc, char *argv[]) { int i, c; char *a; + char name[LIBNAMELEN]; Binit(&bso, 1, OWRITE); cout = -1; @@ -56,6 +68,7 @@ main(int argc, char *argv[]) outfile = "8.out"; HEADTYPE = -1; INITTEXT = -1; + INITTEXTP = -1; INITDAT = -1; INITRND = -1; INITENTRY = 0; @@ -78,11 +91,19 @@ main(int argc, char *argv[]) if(a) HEADTYPE = atolwhex(a); break; + case 'L': + addlibpath(EARGF(usage())); + break; case 'T': a = ARGF(); if(a) INITTEXT = atolwhex(a); break; + case 'P': + a = ARGF(); + if(a) + INITTEXTP = atolwhex(a); + break; case 'D': a = ARGF(); if(a) @@ -111,12 +132,20 @@ main(int argc, char *argv[]) break; } ARGEND USED(argc); - if(*argv == 0) { - diag("usage: 8l [-options] objects"); - errorexit(); - } + if(*argv == 0) + usage(); if(!debug['9'] && !debug['U'] && !debug['B']) debug[DEFAULT] = 1; + a = getenv("ccroot"); + if(a != nil && *a != '\0') { + if(!fileexists(a)) { + diag("nonexistent $ccroot: %s", a); + errorexit(); + } + }else + a = ""; + snprint(name, sizeof(name), "%s/%s/lib", a, thestring); + addlibpath(name); if(HEADTYPE == -1) { if(debug['U']) HEADTYPE = 1; @@ -179,7 +208,7 @@ main(int argc, char *argv[]) Bprint(&bso, "HEADR = 0x%ld\n", HEADR); break; case 5: /* elf executable */ - HEADR = rnd(52L+3*32L, 16); + HEADR = rnd(Ehdr32sz+3*Phdr32sz, 16); if(INITTEXT == -1) INITTEXT = 0x80100020L; if(INITDAT == -1) @@ -188,6 +217,8 @@ main(int argc, char *argv[]) INITRND = 4096; break; } + if (INITTEXTP == -1) + INITTEXTP = INITTEXT; if(INITDAT != 0 && INITRND != 0) print("warning: -D0x%lux is ignored because of -R0x%lux\n", INITDAT, INITRND); @@ -269,7 +300,7 @@ main(int argc, char *argv[]) dtype = 4; cout = create(outfile, 1, 0775); if(cout < 0) { - diag("cannot create %s", outfile); + diag("cannot create %s: %r", outfile); errorexit(); } version = 0; @@ -284,7 +315,7 @@ main(int argc, char *argv[]) INITENTRY = "_mainp"; if(!debug['l']) lookup(INITENTRY, 0)->type = SXREF; - } else + } else if(!(*INITENTRY >= '0' && *INITENTRY <= '9')) lookup(INITENTRY, 0)->type = SXREF; while(*argv) @@ -335,6 +366,42 @@ main(int argc, char *argv[]) } void +addlibpath(char *arg) +{ + char **p; + + if(nlibdir >= maxlibdir) { + if(maxlibdir == 0) + maxlibdir = 8; + else + maxlibdir *= 2; + p = malloc(maxlibdir*sizeof(*p)); + if(p == nil) { + diag("out of memory"); + errorexit(); + } + memmove(p, libdir, nlibdir*sizeof(*p)); + free(libdir); + libdir = p; + } + libdir[nlibdir++] = strdup(arg); +} + +char* +findlib(char *file) +{ + int i; + char name[LIBNAMELEN]; + + for(i = 0; i < nlibdir; i++) { + snprint(name, sizeof(name), "%s/%s", libdir[i], file); + if(fileexists(name)) + return libdir[i]; + } + return nil; +} + +void loadlib(void) { int i; @@ -374,25 +441,26 @@ objfile(char *file) int f, work; Sym *s; char magbuf[SARMAG]; - char name[100], pname[150]; + char name[LIBNAMELEN], pname[LIBNAMELEN]; struct ar_hdr arhdr; char *e, *start, *stop; - if(file[0] == '-' && file[1] == 'l') { - if(debug['9']) - sprint(name, "/%s/lib/lib", thestring); - else - sprint(name, "/usr/%clib/lib", thechar); - strcat(name, file+2); - strcat(name, ".a"); - file = name; - } if(debug['v']) Bprint(&bso, "%5.2f ldobj: %s\n", cputime(), file); Bflush(&bso); + if(file[0] == '-' && file[1] == 'l') { + snprint(pname, sizeof(pname), "lib%s.a", file+2); + e = findlib(pname); + if(e == nil) { + diag("cannot find library: %s", file); + errorexit(); + } + snprint(name, sizeof(name), "%s/%s", e, pname); + file = name; + } f = open(file, 0); if(f < 0) { - diag("cannot open file: %s", file); + diag("cannot open %s: %r", file); errorexit(); } l = read(f, magbuf, SARMAG); @@ -451,7 +519,8 @@ objfile(char *file) l |= (e[3] & 0xff) << 16; l |= (e[4] & 0xff) << 24; seek(f, l, 0); - l = read(f, &arhdr, SAR_HDR); + /* need readn to read the dumps (at least) */ + l = readn(f, &arhdr, SAR_HDR); if(l != SAR_HDR) goto bad; if(strncmp(arhdr.fmag, ARFMAG, sizeof(arhdr.fmag))) @@ -478,7 +547,7 @@ int zaddr(uchar *p, Adr *a, Sym *h[]) { int c, t, i; - long l; + int l; Sym *s; Auto *u; @@ -554,25 +623,24 @@ zaddr(uchar *p, Adr *a, Sym *h[]) void addlib(char *obj) { - char name[1024], comp[256], *p; - int i; + char fn1[LIBNAMELEN], fn2[LIBNAMELEN], comp[LIBNAMELEN], *p, *name; + int i, search; if(histfrogp <= 0) return; + name = fn1; + search = 0; if(histfrog[0]->name[1] == '/') { sprint(name, ""); i = 1; - } else - if(histfrog[0]->name[1] == '.') { + } else if(histfrog[0]->name[1] == '.') { sprint(name, "."); i = 0; } else { - if(debug['9']) - sprint(name, "/%s/lib", thestring); - else - sprint(name, "/usr/%clib", thechar); + sprint(name, ""); i = 0; + search = 1; } for(; i<histfrogp; i++) { @@ -595,13 +663,25 @@ addlib(char *obj) memmove(p+strlen(thestring), p+2, strlen(p+2)+1); memmove(p, thestring, strlen(thestring)); } - if(strlen(name) + strlen(comp) + 3 >= sizeof(name)) { + if(strlen(fn1) + strlen(comp) + 3 >= sizeof(fn1)) { diag("library component too long"); return; } - strcat(name, "/"); - strcat(name, comp); + if(i > 0 || !search) + strcat(fn1, "/"); + strcat(fn1, comp); + } + + cleanname(name); + + if(search){ + p = findlib(name); + if(p != nil){ + snprint(fn2, sizeof(fn2), "%s/%s", p, name); + name = fn2; + } } + for(i=0; i<libraryp; i++) if(strcmp(name, library[i]) == 0) return; @@ -1087,8 +1167,7 @@ lookup(char *symb, int v) for(p=symb; c = *p; p++) h = h+h+h + c; l = (p - symb) + 1; - if(h < 0) - h = ~h; + h &= 0xffffff; h %= NHASH; for(s = hash[h]; s != S; s = s->link) if(s->version == v) @@ -1236,16 +1315,24 @@ void doprof2(void) { Sym *s2, *s4; - Prog *p, *q, *ps2, *ps4; + Prog *p, *q, *q2, *ps2, *ps4; if(debug['v']) Bprint(&bso, "%5.2f profile 2\n", cputime()); Bflush(&bso); - s2 = lookup("_profin", 0); - s4 = lookup("_profout", 0); + if(debug['e']){ + s2 = lookup("_tracein", 0); + s4 = lookup("_traceout", 0); + }else{ + s2 = lookup("_profin", 0); + s4 = lookup("_profout", 0); + } if(s2->type != STEXT || s4->type != STEXT) { - diag("_profin/_profout not defined"); + if(debug['e']) + diag("_tracein/_traceout not defined %d %d", s2->type, s4->type); + else + diag("_profin/_profout not defined"); return; } @@ -1286,7 +1373,20 @@ doprof2(void) q->line = p->line; q->pc = p->pc; q->link = p->link; - p->link = q; + if(debug['e']){ /* embedded tracing */ + q2 = prg(); + p->link = q2; + q2->link = q; + + q2->line = p->line; + q2->pc = p->pc; + + q2->as = AJMP; + q2->to.type = D_BRANCH; + q2->to.sym = p->to.sym; + q2->pcond = q->link; + }else + p->link = q; p = q; p->as = ACALL; p->to.type = D_BRANCH; @@ -1297,6 +1397,17 @@ doprof2(void) } if(p->as == ARET) { /* + * RET (default) + */ + if(debug['e']){ /* embedded tracing */ + q = prg(); + q->line = p->line; + q->pc = p->pc; + q->link = p->link; + p->link = q; + p = q; + } + /* * RET */ q = prg(); diff --git a/utils/8l/pass.c b/utils/8l/pass.c index 0e0ec346..6de027af 100644 --- a/utils/8l/pass.c +++ b/utils/8l/pass.c @@ -91,8 +91,10 @@ dodata(void) s->value = bsssize + datsize; bsssize += t; } + xdefine("bdata", SDATA, 0L); xdefine("edata", SBSS, datsize); xdefine("end", SBSS, bsssize + datsize); + /* etext is defined in span.c */ } Prog* @@ -308,7 +310,8 @@ patch(void) Bprint(&bso, "%s calls %s\n", TNAME, s->name); switch(s->type) { default: - diag("undefined: %s in %s", s->name, TNAME); + /* diag prints TNAME first */ + diag("undefined: %s", s->name); s->type = STEXT; s->value = vexit; break; /* or fall through to set offset? */ diff --git a/utils/8l/span.c b/utils/8l/span.c index 67ec929b..729ae8df 100644 --- a/utils/8l/span.c +++ b/utils/8l/span.c @@ -236,12 +236,12 @@ asmlc(void) if(p->line == oldlc || p->as == ATEXT || p->as == ANOP) { if(p->as == ATEXT) curtext = p; - if(debug['L']) + if(debug['V']) Bprint(&bso, "%6lux %P\n", p->pc, p); continue; } - if(debug['L']) + if(debug['V']) Bprint(&bso, "\t\t%6ld", lcsize); v = (p->pc - oldpc) / MINLC; while(v) { @@ -249,7 +249,7 @@ asmlc(void) if(v < 127) s = v; cput(s+128); /* 129-255 +pc */ - if(debug['L']) + if(debug['V']) Bprint(&bso, " pc+%ld*%d(%ld)", s, MINLC, s+128); v -= s; lcsize++; @@ -263,7 +263,7 @@ asmlc(void) cput(s>>16); cput(s>>8); cput(s); - if(debug['L']) { + if(debug['V']) { if(s > 0) Bprint(&bso, " lc+%ld(%d,%ld)\n", s, 0, s); @@ -278,14 +278,14 @@ asmlc(void) } if(s > 0) { cput(0+s); /* 1-64 +lc */ - if(debug['L']) { + if(debug['V']) { Bprint(&bso, " lc+%ld(%ld)\n", s, 0+s); Bprint(&bso, "%6lux %P\n", p->pc, p); } } else { cput(64-s); /* 65-128 -lc */ - if(debug['L']) { + if(debug['V']) { Bprint(&bso, " lc%ld(%ld)\n", s, 64-s); Bprint(&bso, "%6lux %P\n", p->pc, p); @@ -298,12 +298,30 @@ asmlc(void) cput(s); lcsize++; } - if(debug['v'] || debug['L']) + if(debug['v'] || debug['V']) Bprint(&bso, "lcsize = %ld\n", lcsize); Bflush(&bso); } int +prefixof(Adr *a) +{ + switch(a->type) { + case D_INDIR+D_CS: + return 0x2e; + case D_INDIR+D_DS: + return 0x3e; + case D_INDIR+D_ES: + return 0x26; + case D_INDIR+D_FS: + return 0x64; + case D_INDIR+D_GS: + return 0x65; + } + return 0; +} + +int oclass(Adr *a) { long v; @@ -608,7 +626,7 @@ asmand(Adr *a, int r) } if(t >= D_INDIR) { t -= D_INDIR; - if(t == D_NONE) { + if(t == D_NONE || D_CS <= t && t <= D_GS) { *andptr++ = (0 << 6) | (5 << 0) | (r << 3); put4(v); return; @@ -769,6 +787,7 @@ uchar ymovtab[] = ASHRL, Ycol, Yml, 6, 0xac,0xad,0,0, /* extra imul */ + AIMULW, Yml, Yrl, 7, Pq,0xaf,0,0, AIMULL, Yml, Yrl, 7, Pm,0xaf,0,0, 0 }; @@ -823,7 +842,14 @@ doasm(Prog *p) Prog *q, pp; uchar *t; int z, op, ft, tt; - long v; + long v, pre; + + pre = prefixof(&p->from); + if(pre) + *andptr++ = pre; + pre = prefixof(&p->to); + if(pre) + *andptr++ = pre; o = &optab[p->as]; ft = oclass(&p->from) * Ymax; @@ -1063,7 +1089,7 @@ found: q = p->pcond; if(q) { v = q->pc - p->pc - 2; - if(v < -128 && v > 127) + if(v < -128 || v > 127) diag("loop too far: %P", p); *andptr++ = op; *andptr++ = v; |
