summaryrefslogtreecommitdiff
path: root/sys/src/cmd/2a
diff options
context:
space:
mode:
authorTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
committerTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
commite5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch)
treed8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/cmd/2a
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/cmd/2a')
-rwxr-xr-xsys/src/cmd/2a/a.h201
-rwxr-xr-xsys/src/cmd/2a/a.y540
-rwxr-xr-xsys/src/cmd/2a/l.s479
-rwxr-xr-xsys/src/cmd/2a/lex.c936
-rwxr-xr-xsys/src/cmd/2a/mkfile19
5 files changed, 2175 insertions, 0 deletions
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 <u.h>
+#include <libc.h>
+#include <bio.h>
+#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 <lval> LTYPE1 LTYPE2 LTYPE3 LTYPE4 LTYPE5
+%token <lval> LTYPE6 LTYPE7 LTYPE8 LTYPE9 LTYPEA LTYPEB
+%token <lval> LCONST LSP LSB LFP LPC LTOS LAREG LDREG LFREG LWID
+%token <dval> LFCONST
+%token <sval> LSCONST
+%token <sym> LNAME LLAB LVAR
+%type <lval> con expr scale type pointer reg offset
+%type <addr> name areg xreg
+%type <gen> gen rel
+%type <gen2> 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 <ctype.h>
+#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; i<nDlist; i++)
+ dodefine(Dlist[i]);
+ yyparse();
+ if(nerrors) {
+ cclean();
+ return nerrors;
+ }
+
+ pass = 2;
+ outhist();
+ pinit(file);
+ for(i=0; i<nDlist; i++)
+ dodefine(Dlist[i]);
+ yyparse();
+ cclean();
+ return nerrors;
+}
+
+struct
+{
+ char *name;
+ ushort type;
+ ushort value;
+} itab[] =
+{
+ "SP", LSP, D_AUTO,
+ "SB", LSB, D_EXTERN,
+ "FP", LFP, D_PARAM,
+ "PC", LPC, D_BRANCH,
+ "TOS", LTOS, D_TOS,
+ "CCR", LTOS, D_CCR,
+ "SR", LTOS, D_SR,
+ "SFC", LTOS, D_SFC,
+ "DFC", LTOS, D_DFC,
+ "CACR", LTOS, D_CACR,
+ "USP", LTOS, D_USP,
+ "VBR", LTOS, D_VBR,
+ "CAAR", LTOS, D_CAAR,
+ "MSP", LTOS, D_MSP,
+ "ISP", LTOS, D_ISP,
+ "FPCR", LTOS, D_FPCR,
+ "FPSR", LTOS, D_FPSR,
+ "FPIAR", LTOS, D_FPIAR,
+ "TC", LTOS, D_TC,
+ "ITT0", LTOS, D_ITT0,
+ "ITT1", LTOS, D_ITT1,
+ "DTT0", LTOS, D_DTT0,
+ "DTT1", LTOS, D_DTT1,
+ "MMUSR", LTOS, D_MMUSR,
+ "URP", LTOS, D_URP,
+ "SRP", LTOS, D_SRP,
+
+ "R0", LDREG, D_R0+0,
+ "R1", LDREG, D_R0+1,
+ "R2", LDREG, D_R0+2,
+ "R3", LDREG, D_R0+3,
+ "R4", LDREG, D_R0+4,
+ "R5", LDREG, D_R0+5,
+ "R6", LDREG, D_R0+6,
+ "R7", LDREG, D_R0+7,
+
+ ".W", LWID, 0,
+ ".L", LWID, 4,
+
+ "A0", LAREG, D_A0+0,
+ "A1", LAREG, D_A0+1,
+ "A2", LAREG, D_A0+2,
+ "A3", LAREG, D_A0+3,
+ "A4", LAREG, D_A0+4,
+ "A5", LAREG, D_A0+5,
+ "A6", LAREG, D_A0+6,
+ "A7", LAREG, D_A0+7,
+
+ "F0", LFREG, D_F0+0,
+ "F1", LFREG, D_F0+1,
+ "F2", LFREG, D_F0+2,
+ "F3", LFREG, D_F0+3,
+ "F4", LFREG, D_F0+4,
+ "F5", LFREG, D_F0+5,
+ "F6", LFREG, D_F0+6,
+ "F7", LFREG, D_F0+7,
+
+ "ABCD", LTYPE1, AABCD,
+ "ADDB", LTYPE1, AADDB,
+ "ADDL", LTYPE1, AADDL,
+ "ADDW", LTYPE1, AADDW,
+ "ADDXB", LTYPE1, AADDXB,
+ "ADDXL", LTYPE1, AADDXL,
+ "ADDXW", LTYPE1, AADDXW,
+ "ADJSP", LTYPE5, AADJSP,
+ "ANDB", LTYPE1, AANDB,
+ "ANDL", LTYPE1, AANDL,
+ "ANDW", LTYPE1, AANDW,
+ "ASLB", LTYPE1, AASLB,
+ "ASLL", LTYPE1, AASLL,
+ "ASLW", LTYPE1, AASLW,
+ "ASRB", LTYPE1, AASRB,
+ "ASRL", LTYPE1, AASRL,
+ "ASRW", LTYPE1, AASRW,
+ "BCASE", LTYPE7, ABCASE,
+ "BCC", LTYPE6, ABCC,
+ "BCHG", LTYPE1, ABCHG,
+ "BCLR", LTYPE1, ABCLR,
+ "BCS", LTYPE6, ABCS,
+ "BEQ", LTYPE6, ABEQ,
+ "BFCHG", LTYPEA, ABFCHG,
+ "BFCLR", LTYPEA, ABFCLR,
+ "BFEXTS", LTYPEA, ABFEXTS,
+ "BFEXTU", LTYPEA, ABFEXTU,
+ "BFFFO", LTYPEA, ABFFFO,
+ "BFINS", LTYPEA, ABFINS,
+ "BFSET", LTYPEA, ABFSET,
+ "BFTST", LTYPEA, ABFTST,
+ "BGE", LTYPE6, ABGE,
+ "BGT", LTYPE6, ABGT,
+ "BHI", LTYPE6, ABHI,
+ "BKPT", LTYPE1, ABKPT,
+ "BLE", LTYPE6, ABLE,
+ "BLS", LTYPE6, ABLS,
+ "BLT", LTYPE6, ABLT,
+ "BMI", LTYPE6, ABMI,
+ "BNE", LTYPE6, ABNE,
+ "BPL", LTYPE6, ABPL,
+ "BRA", LTYPE6, ABRA,
+ "BSET", LTYPE1, ABSET,
+ "BSR", LTYPE3, ABSR,
+ "BTST", LTYPE1, ABTST,
+ "BVC", LTYPE6, ABVC,
+ "BVS", LTYPE6, ABVS,
+ "CALLM", LTYPE1, ACALLM,
+ "CAS2B", LTYPE1, ACAS2B,
+ "CAS2L", LTYPE1, ACAS2L,
+ "CAS2W", LTYPE1, ACAS2W,
+ "CASB", LTYPE1, ACASB,
+ "CASEW", LTYPE2, ACASEW,
+ "CASL", LTYPE1, ACASL,
+ "CASW", LTYPE1, ACASW,
+ "CHK2B", LTYPE1, ACHK2B,
+ "CHK2L", LTYPE1, ACHK2L,
+ "CHK2W", LTYPE1, ACHK2W,
+ "CHKL", LTYPE1, ACHKL,
+ "CHKW", LTYPE1, ACHKW,
+ "CLRB", LTYPE3, ACLRB,
+ "CLRL", LTYPE3, ACLRL,
+ "CLRW", LTYPE3, ACLRW,
+ "CMP2B", LTYPE1, ACMP2B,
+ "CMP2L", LTYPE1, ACMP2L,
+ "CMP2W", LTYPE1, ACMP2W,
+ "CMPB", LTYPE1, ACMPB,
+ "CMPL", LTYPE1, ACMPL,
+ "CMPW", LTYPE1, ACMPW,
+ "DATA", LTYPE4, ADATA,
+ "DBCC", LTYPE7, ADBCC,
+ "DBCS", LTYPE7, ADBCS,
+ "DBEQ", LTYPE7, ADBEQ,
+ "DBF", LTYPE7, ADBF,
+ "DBGE", LTYPE7, ADBGE,
+ "DBGT", LTYPE7, ADBGT,
+ "DBHI", LTYPE7, ADBHI,
+ "DBLE", LTYPE7, ADBLE,
+ "DBLS", LTYPE7, ADBLS,
+ "DBLT", LTYPE7, ADBLT,
+ "DBMI", LTYPE7, ADBMI,
+ "DBNE", LTYPE7, ADBNE,
+ "DBPL", LTYPE7, ADBPL,
+ "DBT", LTYPE7, ADBT,
+ "DBVC", LTYPE7, ADBVC,
+ "DBVS", LTYPE7, ADBVS,
+ "DIVSL", LTYPE1, ADIVSL,
+ "DIVSW", LTYPE1, ADIVSW,
+ "DIVUL", LTYPE1, ADIVUL,
+ "DIVUW", LTYPE1, ADIVUW,
+ "END", LTYPE2, AEND,
+ "EORB", LTYPE1, AEORB,
+ "EORL", LTYPE1, AEORL,
+ "EORW", LTYPE1, AEORW,
+ "EXG", LTYPE1, AEXG,
+ "EXTBL", LTYPE3, AEXTBL,
+ "EXTBW", LTYPE3, AEXTBW,
+ "EXTWL", LTYPE3, AEXTWL,
+ "FABSB", LTYPE1, AFABSB,
+ "FABSD", LTYPE1, AFABSD,
+ "FABSF", LTYPE1, AFABSF,
+ "FABSL", LTYPE1, AFABSL,
+ "FABSW", LTYPE1, AFABSW,
+ "FACOSB", LTYPE1, AFACOSB,
+ "FACOSD", LTYPE1, AFACOSD,
+ "FACOSF", LTYPE1, AFACOSF,
+ "FACOSL", LTYPE1, AFACOSL,
+ "FACOSW", LTYPE1, AFACOSW,
+ "FADDB", LTYPE1, AFADDB,
+ "FADDD", LTYPE1, AFADDD,
+ "FADDF", LTYPE1, AFADDF,
+ "FADDL", LTYPE1, AFADDL,
+ "FADDW", LTYPE1, AFADDW,
+ "FASINB", LTYPE1, AFASINB,
+ "FASIND", LTYPE1, AFASIND,
+ "FASINF", LTYPE1, AFASINF,
+ "FASINL", LTYPE1, AFASINL,
+ "FASINW", LTYPE1, AFASINW,
+ "FATANB", LTYPE1, AFATANB,
+ "FATAND", LTYPE1, AFATAND,
+ "FATANF", LTYPE1, AFATANF,
+ "FATANHB", LTYPE1, AFATANHB,
+ "FATANHD", LTYPE1, AFATANHD,
+ "FATANHF", LTYPE1, AFATANHF,
+ "FATANHL", LTYPE1, AFATANHL,
+ "FATANHW", LTYPE1, AFATANHW,
+ "FATANL", LTYPE1, AFATANL,
+ "FATANW", LTYPE1, AFATANW,
+ "FBEQ", LTYPE6, AFBEQ,
+ "FBF", LTYPE6, AFBF,
+ "FBGE", LTYPE6, AFBGE,
+ "FBGT", LTYPE6, AFBGT,
+ "FBLE", LTYPE6, AFBLE,
+ "FBLT", LTYPE6, AFBLT,
+ "FBNE", LTYPE6, AFBNE,
+ "FBT", LTYPE6, AFBT,
+ "FCMPB", LTYPE1, AFCMPB,
+ "FCMPD", LTYPE1, AFCMPD,
+ "FCMPF", LTYPE1, AFCMPF,
+ "FCMPL", LTYPE1, AFCMPL,
+ "FCMPW", LTYPE1, AFCMPW,
+ "FCOSB", LTYPE1, AFCOSB,
+ "FCOSD", LTYPE1, AFCOSD,
+ "FCOSF", LTYPE1, AFCOSF,
+ "FCOSHB", LTYPE1, AFCOSHB,
+ "FCOSHD", LTYPE1, AFCOSHD,
+ "FCOSHF", LTYPE1, AFCOSHF,
+ "FCOSHL", LTYPE1, AFCOSHL,
+ "FCOSHW", LTYPE1, AFCOSHW,
+ "FCOSL", LTYPE1, AFCOSL,
+ "FCOSW", LTYPE1, AFCOSW,
+ "FDBEQ", LTYPE7, AFDBEQ,
+ "FDBF", LTYPE7, AFDBF,
+ "FDBGE", LTYPE7, AFDBGE,
+ "FDBGT", LTYPE7, AFDBGT,
+ "FDBLE", LTYPE7, AFDBLE,
+ "FDBLT", LTYPE7, AFDBLT,
+ "FDBNE", LTYPE7, AFDBNE,
+ "FDBT", LTYPE7, AFDBT,
+ "FDIVB", LTYPE1, AFDIVB,
+ "FDIVD", LTYPE1, AFDIVD,
+ "FDIVF", LTYPE1, AFDIVF,
+ "FDIVL", LTYPE1, AFDIVL,
+ "FDIVW", LTYPE1, AFDIVW,
+ "FETOXB", LTYPE1, AFETOXB,
+ "FETOXD", LTYPE1, AFETOXD,
+ "FETOXF", LTYPE1, AFETOXF,
+ "FETOXL", LTYPE1, AFETOXL,
+ "FETOXM1B", LTYPE1, AFETOXM1B,
+ "FETOXM1D", LTYPE1, AFETOXM1D,
+ "FETOXM1F", LTYPE1, AFETOXM1F,
+ "FETOXM1L", LTYPE1, AFETOXM1L,
+ "FETOXM1W", LTYPE1, AFETOXM1W,
+ "FETOXW", LTYPE1, AFETOXW,
+ "FGETEXPB", LTYPE1, AFGETEXPB,
+ "FGETEXPD", LTYPE1, AFGETEXPD,
+ "FGETEXPF", LTYPE1, AFGETEXPF,
+ "FGETEXPL", LTYPE1, AFGETEXPL,
+ "FGETEXPW", LTYPE1, AFGETEXPW,
+ "FGETMANB", LTYPE1, AFGETMANB,
+ "FGETMAND", LTYPE1, AFGETMAND,
+ "FGETMANF", LTYPE1, AFGETMANF,
+ "FGETMANL", LTYPE1, AFGETMANL,
+ "FGETMANW", LTYPE1, AFGETMANW,
+ "FINTB", LTYPE1, AFINTB,
+ "FINTD", LTYPE1, AFINTD,
+ "FINTF", LTYPE1, AFINTF,
+ "FINTL", LTYPE1, AFINTL,
+ "FINTRZB", LTYPE1, AFINTRZB,
+ "FINTRZD", LTYPE1, AFINTRZD,
+ "FINTRZF", LTYPE1, AFINTRZF,
+ "FINTRZL", LTYPE1, AFINTRZL,
+ "FINTRZW", LTYPE1, AFINTRZW,
+ "FINTW", LTYPE1, AFINTW,
+ "FLOG10B", LTYPE1, AFLOG10B,
+ "FLOG10D", LTYPE1, AFLOG10D,
+ "FLOG10F", LTYPE1, AFLOG10F,
+ "FLOG10L", LTYPE1, AFLOG10L,
+ "FLOG10W", LTYPE1, AFLOG10W,
+ "FLOG2B", LTYPE1, AFLOG2B,
+ "FLOG2D", LTYPE1, AFLOG2D,
+ "FLOG2F", LTYPE1, AFLOG2F,
+ "FLOG2L", LTYPE1, AFLOG2L,
+ "FLOG2W", LTYPE1, AFLOG2W,
+ "FLOGNB", LTYPE1, AFLOGNB,
+ "FLOGND", LTYPE1, AFLOGND,
+ "FLOGNF", LTYPE1, AFLOGNF,
+ "FLOGNL", LTYPE1, AFLOGNL,
+ "FLOGNP1B", LTYPE1, AFLOGNP1B,
+ "FLOGNP1D", LTYPE1, AFLOGNP1D,
+ "FLOGNP1F", LTYPE1, AFLOGNP1F,
+ "FLOGNP1L", LTYPE1, AFLOGNP1L,
+ "FLOGNP1W", LTYPE1, AFLOGNP1W,
+ "FLOGNW", LTYPE1, AFLOGNW,
+ "FMODB", LTYPE1, AFMODB,
+ "FMODD", LTYPE1, AFMODD,
+ "FMODF", LTYPE1, AFMODF,
+ "FMODL", LTYPE1, AFMODL,
+ "FMODW", LTYPE1, AFMODW,
+ "FMOVEB", LTYPE1, AFMOVEB,
+ "FMOVED", LTYPE1, AFMOVED,
+ "FMOVEF", LTYPE1, AFMOVEF,
+ "FMOVEL", LTYPE1, AFMOVEL,
+ "FMOVEW", LTYPE1, AFMOVEW,
+ "FMULB", LTYPE1, AFMULB,
+ "FMULD", LTYPE1, AFMULD,
+ "FMULF", LTYPE1, AFMULF,
+ "FMULL", LTYPE1, AFMULL,
+ "FMULW", LTYPE1, AFMULW,
+ "FNEGB", LTYPE8, AFNEGB,
+ "FNEGD", LTYPE8, AFNEGD,
+ "FNEGF", LTYPE8, AFNEGF,
+ "FNEGL", LTYPE8, AFNEGL,
+ "FNEGW", LTYPE8, AFNEGW,
+ "FREMB", LTYPE1, AFREMB,
+ "FREMD", LTYPE1, AFREMD,
+ "FREMF", LTYPE1, AFREMF,
+ "FREML", LTYPE1, AFREML,
+ "FREMW", LTYPE1, AFREMW,
+ "FSCALEB", LTYPE1, AFSCALEB,
+ "FSCALED", LTYPE1, AFSCALED,
+ "FSCALEF", LTYPE1, AFSCALEF,
+ "FSCALEL", LTYPE1, AFSCALEL,
+ "FSCALEW", LTYPE1, AFSCALEW,
+ "FSEQ", LTYPE1, AFSEQ,
+ "FSF", LTYPE1, AFSF,
+ "FSGE", LTYPE1, AFSGE,
+ "FSGT", LTYPE1, AFSGT,
+ "FSINB", LTYPE1, AFSINB,
+ "FSIND", LTYPE1, AFSIND,
+ "FSINF", LTYPE1, AFSINF,
+ "FSINHB", LTYPE1, AFSINHB,
+ "FSINHD", LTYPE1, AFSINHD,
+ "FSINHF", LTYPE1, AFSINHF,
+ "FSINHL", LTYPE1, AFSINHL,
+ "FSINHW", LTYPE1, AFSINHW,
+ "FSINL", LTYPE1, AFSINL,
+ "FSINW", LTYPE1, AFSINW,
+ "FSLE", LTYPE1, AFSLE,
+ "FSLT", LTYPE1, AFSLT,
+ "FSNE", LTYPE1, AFSNE,
+ "FSQRTB", LTYPE1, AFSQRTB,
+ "FSQRTD", LTYPE1, AFSQRTD,
+ "FSQRTF", LTYPE1, AFSQRTF,
+ "FSQRTL", LTYPE1, AFSQRTL,
+ "FSQRTW", LTYPE1, AFSQRTW,
+ "FST", LTYPE1, AFST,
+ "FSUBB", LTYPE1, AFSUBB,
+ "FSUBD", LTYPE1, AFSUBD,
+ "FSUBF", LTYPE1, AFSUBF,
+ "FSUBL", LTYPE1, AFSUBL,
+ "FSUBW", LTYPE1, AFSUBW,
+ "FTANB", LTYPE1, AFTANB,
+ "FTAND", LTYPE1, AFTAND,
+ "FTANF", LTYPE1, AFTANF,
+ "FTANHB", LTYPE1, AFTANHB,
+ "FTANHD", LTYPE1, AFTANHD,
+ "FTANHF", LTYPE1, AFTANHF,
+ "FTANHL", LTYPE1, AFTANHL,
+ "FTANHW", LTYPE1, AFTANHW,
+ "FTANL", LTYPE1, AFTANL,
+ "FTANW", LTYPE1, AFTANW,
+ "FTENTOXB", LTYPE1, AFTENTOXB,
+ "FTENTOXD", LTYPE1, AFTENTOXD,
+ "FTENTOXF", LTYPE1, AFTENTOXF,
+ "FTENTOXL", LTYPE1, AFTENTOXL,
+ "FTENTOXW", LTYPE1, AFTENTOXW,
+ "FTSTB", LTYPE1, AFTSTB,
+ "FTSTD", LTYPE1, AFTSTD,
+ "FTSTF", LTYPE1, AFTSTF,
+ "FTSTL", LTYPE1, AFTSTL,
+ "FTSTW", LTYPE1, AFTSTW,
+ "FTWOTOXB", LTYPE1, AFTWOTOXB,
+ "FTWOTOXD", LTYPE1, AFTWOTOXD,
+ "FTWOTOXF", LTYPE1, AFTWOTOXF,
+ "FTWOTOXL", LTYPE1, AFTWOTOXL,
+ "FTWOTOXW", LTYPE1, AFTWOTOXW,
+ "FMOVEM", LTYPE1, AFMOVEM,
+ "FMOVEMC", LTYPE1, AFMOVEMC,
+ "FRESTORE", LTYPE3, AFRESTORE,
+ "FSAVE", LTYPE3, AFSAVE,
+ "GLOBL", LTYPE1, AGLOBL,
+ "GOK", LTYPE2, AGOK,
+ "HISTORY", LTYPE2, AHISTORY,
+ "ILLEG", LTYPE2, AILLEG,
+ "INSTR", LTYPE3, AINSTR,
+ "JMP", LTYPE3, AJMP,
+ "JSR", LTYPE3, AJSR,
+ "LEA", LTYPE1, ALEA,
+ "LINKL", LTYPE1, ALINKL,
+ "LINKW", LTYPE1, ALINKW,
+ "LOCATE", LTYPE1, ALOCATE,
+ "LONG", LTYPE3, ALONG,
+ "LSLB", LTYPE1, ALSLB,
+ "LSLL", LTYPE1, ALSLL,
+ "LSLW", LTYPE1, ALSLW,
+ "LSRB", LTYPE1, ALSRB,
+ "LSRL", LTYPE1, ALSRL,
+ "LSRW", LTYPE1, ALSRW,
+ "MOVB", LTYPE1, AMOVB,
+ "MOVEM", LTYPE1, AMOVEM,
+ "MOVEPL", LTYPE1, AMOVEPL,
+ "MOVEPW", LTYPE1, AMOVEPW,
+ "MOVESB", LTYPE1, AMOVESB,
+ "MOVESL", LTYPE1, AMOVESL,
+ "MOVESW", LTYPE1, AMOVESW,
+ "MOVL", LTYPE1, AMOVL,
+ "MOVW", LTYPE1, AMOVW,
+ "MULSL", LTYPE1, AMULSL,
+ "MULSW", LTYPE1, AMULSW,
+ "MULUL", LTYPE1, AMULUL,
+ "MULUW", LTYPE1, AMULUW,
+ "NAME", LTYPE1, ANAME,
+ "NBCD", LTYPE3, ANBCD,
+ "NEGB", LTYPE3, ANEGB,
+ "NEGL", LTYPE3, ANEGL,
+ "NEGW", LTYPE3, ANEGW,
+ "NEGXB", LTYPE3, ANEGXB,
+ "NEGXL", LTYPE3, ANEGXL,
+ "NEGXW", LTYPE3, ANEGXW,
+ "NOP", LTYPE9, ANOP,
+ "NOTB", LTYPE3, ANOTB,
+ "NOTL", LTYPE3, ANOTL,
+ "NOTW", LTYPE3, ANOTW,
+ "ORB", LTYPE1, AORB,
+ "ORL", LTYPE1, AORL,
+ "ORW", LTYPE1, AORW,
+ "PACK", LTYPE1, APACK,
+ "PEA", LTYPE3, APEA,
+ "RESET", LTYPE2, ARESET,
+ "ROTLB", LTYPE1, AROTLB,
+ "ROTLL", LTYPE1, AROTLL,
+ "ROTLW", LTYPE1, AROTLW,
+ "ROTRB", LTYPE1, AROTRB,
+ "ROTRL", LTYPE1, AROTRL,
+ "ROTRW", LTYPE1, AROTRW,
+ "ROXLB", LTYPE1, AROXLB,
+ "ROXLL", LTYPE1, AROXLL,
+ "ROXLW", LTYPE1, AROXLW,
+ "ROXRB", LTYPE1, AROXRB,
+ "ROXRL", LTYPE1, AROXRL,
+ "ROXRW", LTYPE1, AROXRW,
+ "RTD", LTYPE3, ARTD,
+ "RTE", LTYPE2, ARTE,
+ "RTM", LTYPE3, ARTM,
+ "RTR", LTYPE2, ARTR,
+ "RTS", LTYPE2, ARTS,
+ "SBCD", LTYPE1, ASBCD,
+ "SCC", LTYPE3, ASCC,
+ "SCS", LTYPE3, ASCS,
+ "SEQ", LTYPE3, ASEQ,
+ "SF", LTYPE3, ASF,
+ "SGE", LTYPE3, ASGE,
+ "SGT", LTYPE3, ASGT,
+ "SHI", LTYPE3, ASHI,
+ "SLE", LTYPE3, ASLE,
+ "SLS", LTYPE3, ASLS,
+ "SLT", LTYPE3, ASLT,
+ "SMI", LTYPE3, ASMI,
+ "SNE", LTYPE3, ASNE,
+ "SPL", LTYPE3, ASPL,
+ "ST", LTYPE3, AST,
+ "STOP", LTYPE3, ASTOP,
+ "SUBB", LTYPE1, ASUBB,
+ "SUBL", LTYPE1, ASUBL,
+ "SUBW", LTYPE1, ASUBW,
+ "SUBXB", LTYPE1, ASUBXB,
+ "SUBXL", LTYPE1, ASUBXL,
+ "SUBXW", LTYPE1, ASUBXW,
+ "SVC", LTYPE2, ASVC,
+ "SVS", LTYPE2, ASVS,
+ "SWAP", LTYPE3, ASWAP,
+ "SYS", LTYPE2, ASYS,
+ "TAS", LTYPE3, ATAS,
+ "TEXT", LTYPEB, ATEXT,
+ "TRAP", LTYPE3, ATRAP,
+ "TRAPCC", LTYPE2, ATRAPCC,
+ "TRAPCS", LTYPE2, ATRAPCS,
+ "TRAPEQ", LTYPE2, ATRAPEQ,
+ "TRAPF", LTYPE2, ATRAPF,
+ "TRAPGE", LTYPE2, ATRAPGE,
+ "TRAPGT", LTYPE2, ATRAPGT,
+ "TRAPHI", LTYPE2, ATRAPHI,
+ "TRAPLE", LTYPE2, ATRAPLE,
+ "TRAPLS", LTYPE2, ATRAPLS,
+ "TRAPLT", LTYPE2, ATRAPLT,
+ "TRAPMI", LTYPE2, ATRAPMI,
+ "TRAPNE", LTYPE2, ATRAPNE,
+ "TRAPPL", LTYPE2, ATRAPPL,
+ "TRAPT", LTYPE2, ATRAPT,
+ "TRAPV", LTYPE2, ATRAPV,
+ "TRAPVC", LTYPE2, ATRAPVC,
+ "TRAPVS", LTYPE2, ATRAPVS,
+ "TSTB", LTYPE3, ATSTB,
+ "TSTL", LTYPE3, ATSTL,
+ "TSTW", LTYPE3, ATSTW,
+ "UNLK", LTYPE3, AUNLK,
+ "UNPK", LTYPE1, AUNPK,
+ "WORD", LTYPE3, AWORD,
+
+ 0
+};
+
+void
+cinit(void)
+{
+ Sym *s;
+ int i;
+
+ nullgen.sym = S;
+ nullgen.offset = 0;
+ nullgen.type = D_NONE;
+ if(FPCHIP)
+ nullgen.dval = 0;
+ for(i=0; i<sizeof(nullgen.sval); i++)
+ nullgen.sval[i] = 0;
+ nullgen.displace = 0;
+ nullgen.type = D_NONE;
+ nullgen.index = D_NONE;
+ nullgen.scale = 0;
+ nullgen.field = 0;
+
+ nerrors = 0;
+ iostack = I;
+ iofree = I;
+ peekc = IGN;
+ nhunk = 0;
+ for(i=0; i<NHASH; i++)
+ hash[i] = S;
+ for(i=0; itab[i].name; i++) {
+ s = slookup(itab[i].name);
+ s->type = 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; i<NSNAME; i++) {
+ Bputc(&obuf, *n);
+ n++;
+ }
+ return;
+ }
+ i = a->type;
+ 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 @@
+</$objtype/mkfile
+
+TARG=2a
+OFILES=\
+ y.tab.$O\
+ lex.$O\
+
+HFILES=\
+ ../2c/2.out.h\
+ y.tab.h\
+ a.h\
+
+YFILES=a.y
+
+BIN=/$objtype/bin
+< /sys/src/cmd/mkone
+YFLAGS=-D1 -d
+
+lex.$O: ../cc/macbody ../cc/lexbody ../cc/compat