From e5888a1ffdae813d7575f5fb02275c6bb07e5199 Mon Sep 17 00:00:00 2001 From: Taru Karttunen Date: Wed, 30 Mar 2011 15:46:40 +0300 Subject: Import sources from 2011-03-30 iso image --- sys/src/cmd/2a/a.h | 201 +++++++++++ sys/src/cmd/2a/a.y | 540 +++++++++++++++++++++++++++++ sys/src/cmd/2a/l.s | 479 ++++++++++++++++++++++++++ sys/src/cmd/2a/lex.c | 936 ++++++++++++++++++++++++++++++++++++++++++++++++++ sys/src/cmd/2a/mkfile | 19 + 5 files changed, 2175 insertions(+) create mode 100755 sys/src/cmd/2a/a.h create mode 100755 sys/src/cmd/2a/a.y create mode 100755 sys/src/cmd/2a/l.s create mode 100755 sys/src/cmd/2a/lex.c create mode 100755 sys/src/cmd/2a/mkfile (limited to 'sys/src/cmd/2a') diff --git a/sys/src/cmd/2a/a.h b/sys/src/cmd/2a/a.h new file mode 100755 index 000000000..52ed2b2fa --- /dev/null +++ b/sys/src/cmd/2a/a.h @@ -0,0 +1,201 @@ +#include +#include +#include +#include "../2c/2.out.h" + +#ifndef EXTERN +#define EXTERN extern +#endif + +typedef struct Sym Sym; +typedef struct Ref Ref; +typedef struct Gen Gen; +typedef struct Io Io; +typedef struct Hist Hist; +typedef struct Addr Addr; +typedef struct Gen2 Gen2; + +#define MAXALIGN 7 +#define FPCHIP 1 +#define NSYMB 500 +#define BUFSIZ 8192 +#define HISTSZ 20 +#define NINCLUDE 10 +#define NHUNK 10000 +#define EOF (-1) +#define IGN (-2) +#define GETC() ((--fi.c < 0)? filbuf(): *fi.p++ & 0xff) +#define NHASH 503 +#define STRINGSZ 200 +#define NMACRO 10 + +struct Sym +{ + Sym* link; + Ref* ref; + char* macro; + long value; + ushort type; + char *name; + char sym; +}; +#define S ((Sym*)0) + +struct Ref +{ + int class; +}; + +EXTERN struct +{ + char* p; + int c; +} fi; + +struct Io +{ + Io* link; + char b[BUFSIZ]; + char* p; + short c; + short f; +}; +#define I ((Io*)0) + +EXTERN struct +{ + Sym* sym; + short type; +} h[NSYM]; + +struct Addr +{ + Sym* sym; + long offset; + short type; +}; +struct Gen +{ + Addr; + double dval; + char sval[8]; + long displace; + short type; + short index; + short scale; + short field; +}; +struct Gen2 +{ + Gen from; + Gen to; +}; + +struct Hist +{ + Hist* link; + char* name; + long line; + long offset; +}; +#define H ((Hist*)0) + +enum +{ + CLAST, + CMACARG, + CMACRO, + CPREPROC +}; + +EXTERN char debug[256]; +EXTERN Sym* hash[NHASH]; +EXTERN char* Dlist[30]; +EXTERN int nDlist; +EXTERN Hist* ehist; +EXTERN int newflag; +EXTERN Hist* hist; +EXTERN char* hunk; +EXTERN char* include[NINCLUDE]; +EXTERN Io* iofree; +EXTERN Io* ionext; +EXTERN Io* iostack; +EXTERN long lineno; +EXTERN int nerrors; +EXTERN long nhunk; +EXTERN int ninclude; +EXTERN Gen nullgen; +EXTERN char* outfile; +EXTERN int pass; +EXTERN char* pathname; +EXTERN long pc; +EXTERN int peekc; +EXTERN int sym; +EXTERN char symb[NSYMB]; +EXTERN int thechar; +EXTERN char* thestring; +EXTERN long thunk; +EXTERN Biobuf obuf; + +void* allocn(void*, long, long); +void errorexit(void); +void pushio(void); +void newio(void); +void newfile(char*, int); +Sym* slookup(char*); +Sym* lookup(void); +void syminit(Sym*); +long yylex(void); +int getc(void); +int getnsc(void); +void unget(int); +int escchar(int); +void cinit(void); +void pinit(char*); +void cclean(void); +int isreg(Gen*); +void outcode(int, Gen2*); +void outhist(void); +void zaddr(Gen*, int); +void zname(char*, int, int); +void ieeedtod(Ieee*, double); +int filbuf(void); +Sym* getsym(void); +void domacro(void); +void macund(void); +void macdef(void); +void macexpand(Sym*, char*); +void macinc(void); +void macprag(void); +void maclin(void); +void macif(int); +void macend(void); +void dodefine(char*); +void prfile(long); +void linehist(char*, int); +void gethunk(void); +void yyerror(char*, ...); +int yyparse(void); +void setinclude(char*); +int assemble(char*); + +enum /* keep in synch with ../cc/cc.h */ +{ + Plan9 = 1<<0, + Unix = 1<<1, + Windows = 1<<2 +}; + +/* + * system-dependent stuff from ../cc/compat.c + */ +int mywait(int*); +int mycreat(char*, int); +int systemtype(int); +int pathchar(void); +char* mygetwd(char*, int); +int myexec(char*, char*[]); +int mydup(int, int); +int myfork(void); +int mypipe(int*); +void* mysbrk(ulong); diff --git a/sys/src/cmd/2a/a.y b/sys/src/cmd/2a/a.y new file mode 100755 index 000000000..2f0667613 --- /dev/null +++ b/sys/src/cmd/2a/a.y @@ -0,0 +1,540 @@ +%{ +#include "a.h" +%} +%union { + Sym *sym; + long lval; + double dval; + char sval[8]; + Addr addr; + Gen gen; + Gen2 gen2; +} +%left '|' +%left '^' +%left '&' +%left '<' '>' +%left '+' '-' +%left '*' '/' '%' +%token LTYPE1 LTYPE2 LTYPE3 LTYPE4 LTYPE5 +%token LTYPE6 LTYPE7 LTYPE8 LTYPE9 LTYPEA LTYPEB +%token LCONST LSP LSB LFP LPC LTOS LAREG LDREG LFREG LWID +%token LFCONST +%token LSCONST +%token LNAME LLAB LVAR +%type con expr scale type pointer reg offset +%type name areg xreg +%type gen rel +%type noaddr gengen dstgen spec1 spec2 spec3 srcgen dstrel genrel +%% +prog: +| prog line + +line: + LLAB ':' + { + if($1->value != pc) + yyerror("redeclaration of %s", $1->name); + $1->value = pc; + } + line +| LNAME ':' + { + $1->type = LLAB; + $1->value = pc; + } + line +| ';' +| inst ';' +| error ';' + +inst: + LNAME '=' expr + { + $1->type = LVAR; + $1->value = $3; + } +| LVAR '=' expr + { + if($1->value != $3) + yyerror("redeclaration of %s", $1->name); + $1->value = $3; + } +| LTYPE1 gengen { outcode($1, &$2); } +| LTYPE2 noaddr { outcode($1, &$2); } +| LTYPE3 dstgen { outcode($1, &$2); } +| LTYPE4 spec1 { outcode($1, &$2); } +| LTYPE5 srcgen { outcode($1, &$2); } +| LTYPE6 dstrel { outcode($1, &$2); } +| LTYPE7 genrel { outcode($1, &$2); } +| LTYPE8 dstgen { outcode($1, &$2); } +| LTYPE8 gengen { outcode($1, &$2); } +| LTYPE9 noaddr { outcode($1, &$2); } +| LTYPE9 dstgen { outcode($1, &$2); } +| LTYPEA spec2 { outcode($1, &$2); } +| LTYPEB spec3 { outcode($1, &$2); } + +noaddr: + { + $$.from = nullgen; + $$.to = nullgen; + } +| ',' + { + $$.from = nullgen; + $$.to = nullgen; + } + +srcgen: + gen + { + $$.from = $1; + $$.to = nullgen; + } +| gen ',' + { + $$.from = $1; + $$.to = nullgen; + } + +dstgen: + gen + { + $$.from = nullgen; + $$.to = $1; + } +| ',' gen + { + $$.from = nullgen; + $$.to = $2; + } + +gengen: + gen ',' gen + { + $$.from = $1; + $$.to = $3; + } + +dstrel: + rel + { + $$.from = nullgen; + $$.to = $1; + } +| ',' rel + { + $$.from = nullgen; + $$.to = $2; + } + +genrel: + gen ',' rel + { + $$.from = $1; + $$.to = $3; + } + +spec1: /* DATA opcode */ + gen '/' con ',' gen + { + $1.displace = $3; + $$.from = $1; + $$.to = $5; + } + +spec2: /* bit field opcodes */ + gen ',' gen ',' con ',' con + { + $1.field = $7; + $3.field = $5; + $$.from = $1; + $$.to = $3; + } + +spec3: /* TEXT opcode */ + gengen +| gen ',' con ',' gen + { + $1.displace = $3; + $$.from = $1; + $$.to = $5; + } + +rel: + con '(' LPC ')' + { + $$ = nullgen; + $$.type = D_BRANCH; + $$.offset = $1 + pc; + } +| LNAME offset + { + $$ = nullgen; + if(pass == 2) + yyerror("undefined label: %s", $1->name); + $$.type = D_BRANCH; + $$.sym = $1; + $$.offset = $2; + } +| LLAB offset + { + $$ = nullgen; + $$.type = D_BRANCH; + $$.sym = $1; + $$.offset = $1->value + $2; + } + +gen: + type + { + $$ = nullgen; + $$.type = $1; + } +| '$' con + { + $$ = nullgen; + $$.type = D_CONST; + $$.offset = $2; + } +| '$' name + { + $$ = nullgen; + { + Addr *a; + a = &$$; + *a = $2; + } + if($2.type == D_AUTO || $2.type == D_PARAM) + yyerror("constant cannot be automatic: %s", + $2.sym->name); + $$.type = $2.type | I_ADDR; + } +| '$' LSCONST + { + $$ = nullgen; + $$.type = D_SCONST; + memcpy($$.sval, $2, sizeof($$.sval)); + } +| '$' LFCONST + { + $$ = nullgen; + $$.type = D_FCONST; + $$.dval = $2; + } +| '$' '-' LFCONST + { + $$ = nullgen; + $$.type = D_FCONST; + $$.dval = -$3; + } +| LTOS '+' con + { + $$ = nullgen; + $$.type = D_STACK; + $$.offset = $3; + } +| LTOS '-' con + { + $$ = nullgen; + $$.type = D_STACK; + $$.offset = -$3; + } +| con + { + $$ = nullgen; + $$.type = D_CONST | I_INDIR; + $$.offset = $1; + } +| '-' '(' LAREG ')' + { + $$ = nullgen; + $$.type = $3 | I_INDDEC; + } +| '(' LAREG ')' '+' + { + $$ = nullgen; + $$.type = $2 | I_INDINC; + } +| areg + { + $$ = nullgen; + $$.type = $1.type; + { + Addr *a; + a = &$$; + *a = $1; + } + if(($$.type & D_MASK) == D_NONE) { + $$.index = D_NONE | I_INDEX1; + $$.scale = 0; + $$.displace = 0; + } + } +| areg xreg + { + $$ = nullgen; + $$.type = $1.type; + { + Addr *a; + a = &$$; + *a = $1; + } + $$.index = $2.type | I_INDEX1; + $$.scale = $2.offset; + } +| '(' areg ')' xreg + { + $$ = nullgen; + $$.type = $2.type; + { + Addr *a; + a = &$$; + *a = $2; + } + $$.index = $4.type | I_INDEX2; + $$.scale = $4.offset; + $$.displace = 0; + } +| con '(' areg ')' xreg + { + $$ = nullgen; + $$.type = $3.type; + { + Addr *a; + a = &$$; + *a = $3; + } + $$.index = $5.type | I_INDEX2; + $$.scale = $5.offset; + $$.displace = $1; + } +| '(' areg ')' + { + $$ = nullgen; + $$.type = $2.type; + { + Addr *a; + a = &$$; + *a = $2; + } + $$.index = D_NONE | I_INDEX3; + $$.scale = 0; + $$.displace = 0; + } +| con '(' areg ')' + { + $$ = nullgen; + $$.type = $3.type; + { + Addr *a; + a = &$$; + *a = $3; + } + $$.index = D_NONE | I_INDEX3; + $$.scale = 0; + $$.displace = $1; + } +| '(' areg xreg ')' + { + $$ = nullgen; + $$.type = $2.type; + { + Addr *a; + a = &$$; + *a = $2; + } + $$.index = $3.type | I_INDEX3; + $$.scale = $3.offset; + $$.displace = 0; + } +| con '(' areg xreg ')' + { + $$ = nullgen; + $$.type = $3.type; + { + Addr *a; + a = &$$; + *a = $3; + } + $$.index = $4.type | I_INDEX3; + $$.scale = $4.offset; + $$.displace = $1; + } + +type: + reg +| LFREG + +xreg: + /* + * .W*1 0 + * .W*2 1 + * .W*4 2 + * .W*8 3 + * .L*1 4 + * .L*2 5 + * .L*4 6 + * .L*8 7 + */ + '(' reg LWID scale ')' + { + $$.type = $2; + $$.offset = $3+$4; + $$.sym = S; + } + +reg: + LAREG +| LDREG +| LTOS + +scale: + '*' con + { + switch($2) { + case 1: + $$ = 0; + break; + + case 2: + $$ = 1; + break; + + default: + yyerror("bad scale: %ld", $2); + + case 4: + $$ = 2; + break; + + case 8: + $$ = 3; + break; + } + } + +areg: + '(' LAREG ')' + { + $$.type = $2 | I_INDIR; + $$.sym = S; + $$.offset = 0; + } +| con '(' LAREG ')' + { + $$.type = $3 | I_INDIR; + $$.sym = S; + $$.offset = $1; + } +| '(' ')' + { + $$.type = D_NONE | I_INDIR; + $$.sym = S; + $$.offset = 0; + } +| con '(' ')' + { + $$.type = D_NONE | I_INDIR; + $$.sym = S; + $$.offset = $1; + } +| name + +name: + LNAME offset '(' pointer ')' + { + $$.type = $4; + $$.sym = $1; + $$.offset = $2; + } +| LNAME '<' '>' offset '(' LSB ')' + { + $$.type = D_STATIC; + $$.sym = $1; + $$.offset = $4; + } + +offset: + { + $$ = 0; + } +| '+' con + { + $$ = $2; + } +| '-' con + { + $$ = -$2; + } + +pointer: + LSB +| LSP +| LFP + +con: + LCONST +| LVAR + { + $$ = $1->value; + } +| '-' con + { + $$ = -$2; + } +| '+' con + { + $$ = $2; + } +| '~' con + { + $$ = ~$2; + } +| '(' expr ')' + { + $$ = $2; + } + +expr: + con +| expr '+' expr + { + $$ = $1 + $3; + } +| expr '-' expr + { + $$ = $1 - $3; + } +| expr '*' expr + { + $$ = $1 * $3; + } +| expr '/' expr + { + $$ = $1 / $3; + } +| expr '%' expr + { + $$ = $1 % $3; + } +| expr '<' '<' expr + { + $$ = $1 << $4; + } +| expr '>' '>' expr + { + $$ = $1 >> $4; + } +| expr '&' expr + { + $$ = $1 & $3; + } +| expr '^' expr + { + $$ = $1 ^ $3; + } +| expr '|' expr + { + $$ = $1 | $3; + } diff --git a/sys/src/cmd/2a/l.s b/sys/src/cmd/2a/l.s new file mode 100755 index 000000000..6f3cca3a4 --- /dev/null +++ b/sys/src/cmd/2a/l.s @@ -0,0 +1,479 @@ + +/* + * Memory and machine-specific definitions. Used in C and assembler. + */ + +/* + * Sizes + */ + +#define BI2BY 8 /* bits per byte */ +#define BI2WD 32 /* bits per word */ +#define BY2WD 4 /* bytes per word */ +#define BY2PG 8192 /* bytes per page */ +#define WD2PG (BY2PG/BY2WD) /* words per page */ +#define PGSHIFT 13 /* log(BY2PG) */ +#define PGROUND(s) (((s)+(BY2PG-1))&~(BY2PG-1)) +#define ICACHESIZE 0 +#define MB4 (4*1024*1024) /* Lots of things are 4Mb in size */ + +#define MAXMACH 1 /* max # cpus system can run */ + +/* + * Time + */ +#define HZ (60) /* clock frequency */ +#define MS2HZ (1000/HZ) /* millisec per clock tick */ +#define TK2SEC(t) ((t)/HZ) /* ticks to seconds */ +#define TK2MS(t) ((((ulong)(t))*1000)/HZ) /* ticks to milliseconds */ +#define MS2TK(t) ((((ulong)(t))*HZ)/1000) /* milliseconds to ticks */ + +/* + * SR bits + */ +#define SUPER 0x2000 +#define SPL(n) (n<<8) + +/* + * CACR + */ +#define CCLEAR 0x08 +#define CENABLE 0x01 + +/* + * Magic registers (unused in current system) + */ + +#define MACH A5 /* A5 is m-> */ +#define USER A4 /* A4 is u-> */ + +/* + * Fundamental addresses + */ + +#define USERADDR 0x80000000 +/* assuming we're in a syscall, this is the address of the Ureg structure */ +#define UREGVARSZ (23*BY2WD) /* size of variable part of Ureg */ +#define UREGADDR (USERADDR+BY2PG-(UREGVARSZ+2+4+2+(8+8+1+1)*BY2WD)) + +/* + * Devices poked during bootstrap + */ +#define TACADDR 0x40600000 +#define MOUSE 0x40200000 + +/* + * MMU + */ + +#define VAMASK 0xCFFFFFFF /* clear balu bits in address */ +#define KUSEG 0x00000000 +#define KSEG 0x80000000 + +/* + * MMU entries + */ +#define PTEVALID (1<<13) +#define PTEWRITE 0 +#define PTERONLY (1<<14) +#define PTEKERNEL (1<<15) +#define PTEUNCACHED 0 +#define INVALIDPTE 0 +#define PTEMAPMEM (1024*1024) +#define PTEPERTAB (PTEMAPMEM/BY2PG) +#define SEGMAPSIZE 16 + +#define PPN(pa) ((pa>>13)&0x1FFF) + +#define KMAP ((unsigned long *)0xD0000000) +#define UMAP ((unsigned long *)0x50000000) + +/* + * Virtual addresses + */ +#define VTAG(va) ((va>>22)&0x03F) +#define VPN(va) ((va>>13)&0x1FF) + +#define PARAM ((char*)0x40500000) +#define TLBFLUSH_ 0x01 + +/* + * Address spaces + */ + +#define UZERO KUSEG /* base of user address space */ +#define UTZERO (UZERO+BY2PG) /* first address in user text */ +#define TSTKTOP 0x10000000 /* end of new stack in sysexec */ +#define TSTKSIZ 100 +#define USTKTOP (TSTKTOP-TSTKSIZ*BY2PG) /* byte just beyond user stack */ +#define KZERO KSEG /* base of kernel address space */ +#define KTZERO (KZERO+BY2PG) /* first address in kernel text */ +#define USTKSIZE (4*1024*1024) /* size of user stack */ + +#define MACHSIZE 4096 + + +#define isphys(p) ((((ulong)(p))&0xF0000000) == KSEG) +#define DBMAGIC 0xBADC0C0A + +/* + * Boot first processor + */ +TEXT start(SB), $-4 + + MOVW $(SUPER|SPL(7)), SR + MOVL $a6base(SB), A6 + MOVL $0, R0 + MOVL R0, CACR + MOVL R0, TACADDR /* zero tac counter (cause an intr?) */ + + MOVL $mach0(SB), A0 + MOVL A0, m(SB) + MOVL $0, 0(A0) + MOVL A0, A7 + ADDL $(MACHSIZE-4), A7 /* start stack under machine struct */ + MOVL $0, u(SB) + + MOVL $vectors(SB), A0 + MOVL A0, VBR + + BSR main(SB) + /* never returns */ +dead: + BRA dead + +/* + * Take first processor into user mode. Leave enough room on the stack + * for a full-sized Ureg (including long bus error format) to fit + */ + +TEXT touser(SB), $-4 + + MOVL $(USERADDR+BY2PG-UREGVARSZ), A7 + MOVW $0, -(A7) + MOVL $(UTZERO+32), -(A7) /* header is in text */ + MOVW $0, -(A7) + MOVL $(USTKTOP-6*BY2WD), A0 /* MAXSYSARG=6 */ + MOVL A0, USP + MOVW $(SUPER|SPL(0)), SR + MOVL $8, R0 + MOVL R0, CACR + RTE + +TEXT firmware(SB), $0 + + MOVL $0x40000090, A0 + JMP (A0) + +TEXT splhi(SB), $0 + + MOVL m(SB), A0 + MOVL (A7), 4(A0) + MOVL $0, R0 + MOVW SR, R0 + MOVW $(SUPER|SPL(7)), SR + RTS + +TEXT splduart(SB), $0 + + MOVL $0, R0 + MOVW SR, R0 + MOVW $(SUPER|SPL(5)), SR + RTS + +TEXT spllo(SB), $0 + + MOVL $0, R0 + MOVW SR, R0 + MOVW $(SUPER|SPL(0)), SR + RTS + +TEXT splx(SB), $0 + + MOVL sr+0(FP), R0 + MOVW R0, SR + RTS + +TEXT spldone(SB), $0 + + RTS + +TEXT spl1(SB), $0 + + MOVL $0, R0 + MOVW SR, R0 + MOVW $(SUPER|SPL(1)), SR + RTS + +TEXT flushcpucache(SB), $0 + + MOVL $(CCLEAR|CENABLE), R0 + MOVL R0, CACR + RTS + +TEXT cacrtrap(SB), $0 /* user entry point to control cache, e.g. flush */ + + MOVL R0, CACR + RTE + +TEXT setlabel(SB), $0 + + MOVL sr+0(FP), A0 + MOVL A7, (A0)+ /* stack pointer */ + MOVL (A7), (A0)+ /* pc of caller */ + MOVW SR, (A0)+ /* status register */ + CLRL R0 /* ret 0 => not returning */ + RTS + +TEXT gotolabel(SB), $0 + + MOVL p+0(FP), A0 + MOVW $(SUPER|SPL(7)), SR + MOVL (A0)+, A7 /* stack pointer */ + MOVL (A0)+, (A7) /* pc; stuff into stack frame */ + MOVW (A0)+, R0 /* status register */ + MOVW R0, SR + MOVL $1, R0 /* ret 1 => returning */ + RTS + +/* + * Test and set, as a subroutine + */ + +TEXT tas(SB), $0 + + MOVL $0, R0 + MOVL a+0(FP), A0 + TAS (A0) + BEQ tas_1 + MOVL $1, R0 +tas_1: + RTS + +/* + * Floating point + */ + +TEXT fpsave(SB), $0 + + FSAVE (fp+0(FP)) + RTS + +TEXT fprestore(SB), $0 + + FRESTORE (fp+0(FP)) + RTS + +TEXT fpregsave(SB), $0 + + FMOVEM $0xFF, (3*4)(fr+0(FP)) + FMOVEMC $0x7, (fr+0(FP)) + RTS + +TEXT fpregrestore(SB), $0 + + FMOVEMC (fr+0(FP)), $0x7 + FMOVEM (3*4)(fr+0(FP)), $0xFF + RTS + +TEXT fpcr(SB), $0 + + MOVL new+0(FP), R1 + MOVL FPCR, R0 + MOVL R1, FPCR + RTS + + +TEXT rfnote(SB), $0 + + MOVL uregp+0(FP), A7 + MOVL ((8+8)*BY2WD)(A7), A0 + MOVL A0, USP + MOVEM (A7), $0x7FFF + ADDL $((8+8+1+1)*BY2WD), A7 + RTE + +TEXT illegal(SB), $0 + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVEM $0x7FFF, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + MOVL A7, -(A7) + BSR trap(SB) + ADDL $4, A7 + MOVL ((8+8)*BY2WD)(A7), A0 + MOVL A0, USP + MOVEM (A7), $0x7FFF + ADDL $((8+8+1)*BY2WD+BY2WD), A7 + RTE + +TEXT systrap(SB), $0 + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVL A6, ((8+6)*BY2WD)(A7) + MOVL R0, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + MOVL A7, -(A7) + BSR syscall(SB) + MOVL ((1+8+8)*BY2WD)(A7), A0 + MOVL A0, USP + MOVL ((1+8+6)*BY2WD)(A7), A6 + ADDL $((1+8+8+1)*BY2WD+BY2WD), A7 + RTE + +TEXT buserror(SB), $0 + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVEM $0x7FFF, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + PEA ((8+8+1+3)*BY2WD)(A7) + PEA 4(A7) + BSR fault68020(SB) + ADDL $8, A7 + MOVL ((8+8)*BY2WD)(A7), A0 + MOVL A0, USP + MOVEM (A7), $0x7FFF + ADDL $((8+8+1)*BY2WD+BY2WD), A7 + RTE + +TEXT tacintr(SB), $0 /* level 1 */ + + MOVL R0, -(A7) + MOVL TACADDR, R0 + MOVL (A7)+, R0 + RTE + +TEXT portintr(SB), $0 /* level 2 */ + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVEM $0x7FFF, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + MOVL A7, -(A7) + BSR devportintr(SB) + BRA retintr + +TEXT dkintr(SB), $0 /* level 3 */ + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVEM $0x7FFF, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + MOVL A7, -(A7) + BSR inconintr(SB) + BRA retintr + +TEXT mouseintr(SB), $0 /* level 4 */ + + MOVEM $0x80C2, -(A7) /* D0, A0, A1, A6 */ + MOVL $a6base(SB), A6 + MOVL $15, R0 /* mask off hex switch */ + ANDB MOUSE,R0 /* clears quadrature interrupt */ + LEA mousetab(SB)(R0.W*8), A0 + LEA mouse(SB), A1 + MOVL (A0)+, R0 + ADDL R0, (A1)+ /* dx */ + MOVL (A0), R0 + ADDL R0, (A1)+ /* dy */ + ADDL $1, (A1) /* track */ + MOVEM (A7)+, $0x4301 + RTE + +TEXT uartintr(SB), $0 /* level 5 */ + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVEM $0x7FFF, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + MOVL A7, -(A7) + BSR duartintr(SB) + BRA retintr + +TEXT syncintr(SB), $0 /* level 6 */ + + MOVL $DBMAGIC, -(A7) + SUBL $((8+8+1)*BY2WD), A7 + MOVEM $0x7FFF, (A7) + MOVL $a6base(SB), A6 + MOVL USP, A0 + MOVL A0, ((8+8)*BY2WD)(A7) + MOVL A7, -(A7) + BSR clock(SB) + /* fall through */ +retintr: + BSR mousetry(SB) + ADDL $4, A7 + MOVL ((8+8)*BY2WD)(A7), A0 + MOVL A0, USP + MOVEM (A7), $0x7FFF + ADDL $((8+8+1)*BY2WD+BY2WD), A7 + RTE + +GLOBL duarttimer+0(SB),$4 + +TEXT duartreadtimer+0(SB), $0 + MOVW SR, R1 /* spl7() */ + MOVW $0x2700, SR + MOVL $0x40100000, A0 + CLRL R0 + TSTB 15(A0) /* stop timer */ + MOVW 6(A0), R0 /* read hi,lo */ + TSTB 14(A0) /* restart timer */ + NOTW R0 /* timer counts down from 0xffff */ + ADDL duarttimer(SB), R0 + MOVL R0, duarttimer(SB) + MOVW R1, SR + RTS + +GLOBL mousetab(SB), $128 +DATA mousetab+ 0(SB)/4, -1 /* x down, */ +DATA mousetab+ 4(SB)/4, 1 /* y up */ +DATA mousetab+ 8(SB)/4, 0 /* x - */ +DATA mousetab+ 12(SB)/4, 1 /* y up */ +DATA mousetab+ 16(SB)/4, 1 /* x up */ +DATA mousetab+ 20(SB)/4, 1 /* y up */ +DATA mousetab+ 24(SB)/4, 0 /* x - */ +DATA mousetab+ 28(SB)/4, 1 /* y up */ +DATA mousetab+ 32(SB)/4, -1 /* x down */ +DATA mousetab+ 36(SB)/4, 0 /* y - */ +DATA mousetab+ 40(SB)/4, 0 /* x - */ +DATA mousetab+ 44(SB)/4, 0 /* y - */ +DATA mousetab+ 48(SB)/4, 1 /* x up, */ +DATA mousetab+ 52(SB)/4, 0 /* y - */ +DATA mousetab+ 56(SB)/4, 0 /* x - */ +DATA mousetab+ 60(SB)/4, 0 /* y - */ +DATA mousetab+ 64(SB)/4, -1 /* x down */ +DATA mousetab+ 68(SB)/4, -1 /* y down */ +DATA mousetab+ 72(SB)/4, 0 /* x - */ +DATA mousetab+ 76(SB)/4, -1 /* y down */ +DATA mousetab+ 80(SB)/4, 1 /* x up */ +DATA mousetab+ 84(SB)/4, -1 /* y down */ +DATA mousetab+ 88(SB)/4, 0 /* x - */ +DATA mousetab+ 92(SB)/4, -1 /* y down */ +DATA mousetab+ 96(SB)/4, -1 /* x down */ +DATA mousetab+100(SB)/4, 0 /* y - */ +DATA mousetab+104(SB)/4, 0 /* x - */ +DATA mousetab+108(SB)/4, 0 /* y - */ +DATA mousetab+112(SB)/4, 1 /* x up */ +DATA mousetab+116(SB)/4, 0 /* y - */ +DATA mousetab+120(SB)/4, 0 /* x - */ +DATA mousetab+124(SB)/4, 0 /* y - */ + +GLOBL mach0+0(SB), $MACHSIZE +GLOBL u(SB), $4 +GLOBL m(SB), $4 diff --git a/sys/src/cmd/2a/lex.c b/sys/src/cmd/2a/lex.c new file mode 100755 index 000000000..6ef81e91d --- /dev/null +++ b/sys/src/cmd/2a/lex.c @@ -0,0 +1,936 @@ +#include +#define EXTERN +#include "a.h" +#include "y.tab.h" + +void +main(int argc, char *argv[]) +{ + char *p; + int nout, nproc, status, i, c; + + thechar = '2'; + thestring = "68020"; + memset(debug, 0, sizeof(debug)); + cinit(); + outfile = 0; + include[ninclude++] = "."; + ARGBEGIN { + default: + c = ARGC(); + if(c >= 0 || c < sizeof(debug)) + debug[c] = 1; + break; + + case 'o': + outfile = ARGF(); + break; + + case 'D': + p = ARGF(); + if(p) + Dlist[nDlist++] = p; + break; + + case 'I': + p = ARGF(); + setinclude(p); + break; + } ARGEND + if(*argv == 0) { + print("usage: %ca [-options] file.s\n", thechar); + errorexit(); + } + if(argc > 1 && systemtype(Windows)){ + print("can't assemble multiple files on windows\n"); + errorexit(); + } + if(argc > 1 && !systemtype(Windows)) { + nproc = 1; + if(p = getenv("NPROC")) + nproc = atol(p); /* */ + c = 0; + nout = 0; + for(;;) { + while(nout < nproc && argc > 0) { + i = myfork(); + if(i < 0) { + i = mywait(&status); + if(i < 0) + errorexit(); + if(status) + c++; + nout--; + continue; + } + if(i == 0) { + print("%s:\n", *argv); + if(assemble(*argv)) + errorexit(); + exits(0); + } + nout++; + argc--; + argv++; + } + i = mywait(&status); + if(i < 0) { + if(c) + errorexit(); + exits(0); + } + if(status) + c++; + nout--; + } + } + if(assemble(argv[0])) + errorexit(); + exits(0); +} + +int +assemble(char *file) +{ + char ofile[100], incfile[20], *p; + int i, of; + + strcpy(ofile, file); + p = utfrrune(ofile, pathchar()); + if(p) { + include[0] = ofile; + *p++ = 0; + } else + p = ofile; + if(outfile == 0) { + outfile = p; + if(outfile){ + p = utfrrune(outfile, '.'); + if(p) + if(p[1] == 's' && p[2] == 0) + p[0] = 0; + p = utfrune(outfile, 0); + p[0] = '.'; + p[1] = thechar; + p[2] = 0; + } else + outfile = "/dev/null"; + } + p = getenv("INCLUDE"); + if(p) { + setinclude(p); + } else { + if(systemtype(Plan9)) { + sprint(incfile,"/%s/include", thestring); + setinclude(strdup(incfile)); + } + } + + of = mycreat(outfile, 0664); + if(of < 0) { + yyerror("%ca: cannot create %s", thechar, outfile); + errorexit(); + } + Binit(&obuf, of, OWRITE); + + pass = 1; + pinit(file); + for(i=0; itype = itab[i].type; + s->value = itab[i].value; + } + + pathname = allocn(pathname, 0, 100); + if(mygetwd(pathname, 99) == 0) { + pathname = allocn(pathname, 100, 900); + if(mygetwd(pathname, 999) == 0) + strcpy(pathname, "/???"); + } +} + +void +syminit(Sym *s) +{ + + s->type = LNAME; + s->value = 0; +} + +void +cclean(void) +{ + Gen2 g2; + + g2.from = nullgen; + g2.to = nullgen; + outcode(AEND, &g2); + Bflush(&obuf); +} + +void +zname(char *n, int t, int s) +{ + + Bputc(&obuf, ANAME); /* as */ + Bputc(&obuf, ANAME>>8); + Bputc(&obuf, t); /* type */ + Bputc(&obuf, s); /* sym */ + while(*n) { + Bputc(&obuf, *n); + n++; + } + Bputc(&obuf, 0); +} + +void +zaddr(Gen *a, int s) +{ + long l; + int i, t; + char *n; + Ieee e; + + t = 0; + if(a->field) + t |= T_FIELD; + if(a->index != D_NONE || a->displace != 0) + t |= T_INDEX; + if(a->offset != 0) + t |= T_OFFSET; + if(s != 0) + t |= T_SYM; + + if(a->type == D_FCONST) + t |= T_FCONST; + else + if(a->type == D_SCONST) + t |= T_SCONST; + else + if(a->type & ~0xff) + t |= T_TYPE; + Bputc(&obuf, t); + + if(t & T_FIELD) { /* implies field */ + i = a->field; + Bputc(&obuf, i); + Bputc(&obuf, i>>8); + } + if(t & T_INDEX) { /* implies index, scale, displace */ + i = a->index; + Bputc(&obuf, i); + Bputc(&obuf, i>>8); + Bputc(&obuf, a->scale); + l = a->displace; + Bputc(&obuf, l); + Bputc(&obuf, l>>8); + Bputc(&obuf, l>>16); + Bputc(&obuf, l>>24); + } + if(t & T_OFFSET) { /* implies offset */ + l = a->offset; + Bputc(&obuf, l); + Bputc(&obuf, l>>8); + Bputc(&obuf, l>>16); + Bputc(&obuf, l>>24); + } + if(t & T_SYM) /* implies sym */ + Bputc(&obuf, s); + if(t & T_FCONST) { + ieeedtod(&e, a->dval); + l = e.l; + Bputc(&obuf, l); + Bputc(&obuf, l>>8); + Bputc(&obuf, l>>16); + Bputc(&obuf, l>>24); + l = e.h; + Bputc(&obuf, l); + Bputc(&obuf, l>>8); + Bputc(&obuf, l>>16); + Bputc(&obuf, l>>24); + return; + } + if(t & T_SCONST) { + n = a->sval; + for(i=0; itype; + Bputc(&obuf, i); + if(t & T_TYPE) + Bputc(&obuf, i>>8); +} + +void +outcode(int a, Gen2 *g2) +{ + int sf, st, t; + Sym *s; + + if(pass == 1) + goto out; + +jackpot: + sf = 0; + s = g2->from.sym; + while(s != S) { + sf = s->sym; + if(sf < 0 || sf >= NSYM) + sf = 0; + t = g2->from.type & D_MASK; + if(h[sf].type == t) + if(h[sf].sym == s) + break; + zname(s->name, t, sym); + s->sym = sym; + h[sym].sym = s; + h[sym].type = t; + sf = sym; + sym++; + if(sym >= NSYM) + sym = 1; + break; + } + st = 0; + s = g2->to.sym; + while(s != S) { + st = s->sym; + if(st < 0 || st >= NSYM) + st = 0; + t = g2->to.type & D_MASK; + if(h[st].type == t) + if(h[st].sym == s) + break; + zname(s->name, t, sym); + s->sym = sym; + h[sym].sym = s; + h[sym].type = t; + st = sym; + sym++; + if(sym >= NSYM) + sym = 1; + if(st == sf) + goto jackpot; + break; + } + Bputc(&obuf, a); + Bputc(&obuf, a>>8); + Bputc(&obuf, lineno); + Bputc(&obuf, lineno>>8); + Bputc(&obuf, lineno>>16); + Bputc(&obuf, lineno>>24); + zaddr(&g2->from, sf); + zaddr(&g2->to, st); + +out: + if(a != AGLOBL && a != ADATA) + pc++; +} + +void +outhist(void) +{ + Gen g; + Hist *h; + char *p, *q, *op, c; + int n; + + g = nullgen; + c = pathchar(); + for(h = hist; h != H; h = h->link) { + p = h->name; + op = 0; + /* on windows skip drive specifier in pathname */ + if(systemtype(Windows) && p && p[1] == ':'){ + p += 2; + c = *p; + } + if(p && p[0] != c && h->offset == 0 && pathname){ + /* on windows skip drive specifier in pathname */ + if(systemtype(Windows) && pathname[1] == ':') { + op = p; + p = pathname+2; + c = *p; + } else if(pathname[0] == c){ + op = p; + p = pathname; + } + } + while(p) { + q = strchr(p, c); + if(q) { + n = q-p; + if(n == 0){ + n = 1; /* leading "/" */ + *p = '/'; /* don't emit "\" on windows */ + } + q++; + } else { + n = strlen(p); + q = 0; + } + if(n) { + Bputc(&obuf, ANAME); + Bputc(&obuf, ANAME>>8); + Bputc(&obuf, D_FILE); /* type */ + Bputc(&obuf, 1); /* sym */ + Bputc(&obuf, '<'); + Bwrite(&obuf, p, n); + Bputc(&obuf, 0); + } + p = q; + if(p == 0 && op) { + p = op; + op = 0; + } + } + g.offset = h->offset; + + Bputc(&obuf, AHISTORY); + Bputc(&obuf, AHISTORY>>8); + Bputc(&obuf, h->line); + Bputc(&obuf, h->line>>8); + Bputc(&obuf, h->line>>16); + Bputc(&obuf, h->line>>24); + zaddr(&nullgen, 0); + zaddr(&g, 0); + } +} + +#include "../cc/lexbody" +#include "../cc/macbody" +#include "../cc/compat" diff --git a/sys/src/cmd/2a/mkfile b/sys/src/cmd/2a/mkfile new file mode 100755 index 000000000..f5584a7e5 --- /dev/null +++ b/sys/src/cmd/2a/mkfile @@ -0,0 +1,19 @@ +