📄 minimips.md
字号:
%{#define INTTMP 0x0100ff00 /* 8-15, 24 */#define INTVAR 0x00ff0000 /* 16-23 */#define INTRET 0x00000004 /* 2 */#define readsreg(p) \ (generic((p)->op)==INDIR && (p)->kids[0]->op==VREG+P)#define setsrc(d) ((d) && (d)->x.regnode && \ (d)->x.regnode->set == src->x.regnode->set && \ (d)->x.regnode->mask&src->x.regnode->mask)#define relink(a, b) ((b)->x.prev = (a), (a)->x.next = (b))#include "c.h"#define NODEPTR_TYPE Node#define OP_LABEL(p) ((p)->op)#define LEFT_CHILD(p) ((p)->kids[0])#define RIGHT_CHILD(p) ((p)->kids[1])#define STATE_LABEL(p) ((p)->x.state)static void address (Symbol, Symbol, long);static void blkfetch (int, int, int, int);static void blkloop (int, int, int, int, int, int[]);static void blkstore (int, int, int, int);static void defaddress (Symbol);static void defconst (int, int, Value);static void defstring (int, char *);static void defsymbol (Symbol);static void doarg (Node);static void emit2 (Node);static void export (Symbol);static void clobber (Node);static void function (Symbol, Symbol[], Symbol[], int);static void global (Symbol);static void import (Symbol);static void local (Symbol);static void progbeg (int, char **);static void progend (void);static void segment (int);static void space (int);static void target (Node);static int mulops_calls(int op);static int bitcount (unsigned);static Symbol argreg (int, int, int, int, int);static Symbol ireg[32];static Symbol iregw;static int tmpregs[] = { 3, 9, 10, 30 };static Symbol blkreg;static int cseg;%}%start stmt%term CNSTF4=4113%term CNSTI1=1045 %term CNSTI4=4117%term CNSTP4=4119%term CNSTU1=1046 %term CNSTU4=4118%term ARGB=41%term ARGF4=4129%term ARGI4=4133%term ARGP4=4135%term ARGU4=4134%term ASGNB=57%term ASGNF4=4145%term ASGNI1=1077 %term ASGNI4=4149%term ASGNP4=4151%term ASGNU1=1078 %term ASGNU4=4150%term INDIRB=73%term INDIRF4=4161%term INDIRI1=1093 %term INDIRI4=4165%term INDIRP4=4167%term INDIRU1=1094 %term INDIRU4=4166%term CVFF4=4209%term CVFI4=4213%term CVIF4=4225%term CVII1=1157 %term CVII4=4229%term CVIU1=1158 %term CVIU4=4230%term CVPU4=4246%term CVUI1=1205 %term CVUI4=4277%term CVUP4=4279%term CVUU1=1206 %term CVUU4=4278%term NEGF4=4289%term NEGI4=4293%term CALLB=217%term CALLF4=4305%term CALLI4=4309%term CALLP4=4311%term CALLU4=4310%term CALLV=216%term RETF4=4337%term RETI4=4341%term RETP4=4343%term RETU4=4342%term RETV=248%term ADDRGP4=4359%term ADDRFP4=4375%term ADDRLP4=4391%term ADDF4=4401%term ADDI4=4405%term ADDP4=4407%term ADDU4=4406%term SUBF4=4417%term SUBI4=4421%term SUBP4=4423%term SUBU4=4422%term LSHI4=4437%term LSHU4=4438%term MODI4=4453%term MODU4=4454%term RSHI4=4469%term RSHU4=4470%term BANDI4=4485%term BANDU4=4486%term BCOMI4=4501%term BCOMU4=4502%term BORI4=4517%term BORU4=4518%term BXORI4=4533%term BXORU4=4534%term DIVF4=4545%term DIVI4=4549%term DIVU4=4550%term MULF4=4561%term MULI4=4565%term MULU4=4566%term EQF4=4577%term EQI4=4581%term EQU4=4582%term GEF4=4593%term GEI4=4597%term GEU4=4598%term GTF4=4609%term GTI4=4613%term GTU4=4614%term LEF4=4625%term LEI4=4629%term LEU4=4630%term LTF4=4641%term LTI4=4645%term LTU4=4646%term NEF4=4657%term NEI4=4661%term NEU4=4662%term JUMPV=584%term LABELV=600%term LOADB=233%term LOADF4=4321%term LOADF8=8417%term LOADF16=16609%term LOADI1=1253%term LOADI2=2277%term LOADI4=4325%term LOADI8=8421%term LOADP4=4327%term LOADP8=8423%term LOADU1=1254%term LOADU2=2278%term LOADU4=4326%term LOADU8=8422%term VREGP=711%%reg: INDIRI1(VREGP) "# read register\n"reg: INDIRU1(VREGP) "# read register\n"reg: INDIRF4(VREGP) "# read register\n"reg: INDIRI4(VREGP) "# read register\n"reg: INDIRP4(VREGP) "# read register\n"reg: INDIRU4(VREGP) "# read register\n"stmt: ASGNI1(VREGP,reg) "# write register\n"stmt: ASGNU1(VREGP,reg) "# write register\n"stmt: ASGNF4(VREGP,reg) "# write register\n"stmt: ASGNI4(VREGP,reg) "# write register\n"stmt: ASGNP4(VREGP,reg) "# write register\n"stmt: ASGNU4(VREGP,reg) "# write register\n"con: CNSTI1 "%a"con: CNSTU1 "%a"con: CNSTI4 "%a"con: CNSTU4 "%a"con: CNSTP4 "%a"stmt: reg ""acon: con "%0"acon: ADDRGP4 "%a"addr: ADDI4(reg,acon) "%1($%0)"addr: ADDU4(reg,acon) "%1($%0)"addr: ADDP4(reg,acon) "%1($%0)"addr: acon "%0"addr: reg "($%0)"addr: ADDRFP4 "%a+%F($sp)"addr: ADDRLP4 "%a+%F($sp)"reg: addr "\tla $%c,%0\n" 1reg: CNSTI1 "# reg\n" range(a, 0, 0)reg: CNSTI4 "# reg\n" range(a, 0, 0)reg: CNSTU1 "# reg\n" range(a, 0, 0)reg: CNSTU4 "# reg\n" range(a, 0, 0)reg: CNSTP4 "# reg\n" range(a, 0, 0)reg: CNSTF4 "# reg\n" range(a, 0, 0)stmt: ASGNI1(addr,reg) "\tsb $%1,%0\n" 1stmt: ASGNU1(addr,reg) "\tsb $%1,%0\n" 1stmt: ASGNI4(addr,reg) "\tsw $%1,%0\n" 1stmt: ASGNU4(addr,reg) "\tsw $%1,%0\n" 1stmt: ASGNP4(addr,reg) "\tsw $%1,%0\n" 1reg: INDIRI1(addr) "\tlb $%c,%0\n" 1reg: INDIRU1(addr) "\tlb $%c,%0; and $%c,$%c,255\n" 2reg: INDIRI4(addr) "\tlw $%c,%0\n" 1reg: INDIRU4(addr) "\tlw $%c,%0\n" 1reg: INDIRP4(addr) "\tlw $%c,%0\n" 1reg: CVII4(INDIRI1(addr)) "\tlb $%c,%0\n" 1reg: CVUU4(INDIRU1(addr)) "\tlb $%c,%0; and $%c,$%c,255\n" 2 reg: CVUI4(INDIRU1(addr)) "\tlb $%c,%0; and $%c,$%c,255\n" 2 reg: INDIRF4(addr) "\tlw $%c,%0\n" 1stmt: ASGNF4(addr,reg) "\tsw $%1,%0\n" 1reg: DIVI4(reg,reg) "\tjal __div\n" 100reg: DIVU4(reg,reg) "\tjal __divu\n" 100reg: MODI4(reg,reg) "\tjal __mod\n" 100reg: MODU4(reg,reg) "\tjal __modu\n" 100reg: MULI4(reg,reg) "\tjal __mul\n" 100reg: MULU4(reg,reg) "\tjal __mul\n" 100rc: con "%0"rc: reg "$%0"reg: ADDI4(reg,rc) "\taddu $%c,$%0,%1\n" 1reg: ADDP4(reg,rc) "\taddu $%c,$%0,%1\n" 1reg: ADDU4(reg,rc) "\taddu $%c,$%0,%1\n" 1reg: BANDI4(reg,rc) "\tand $%c,$%0,%1\n" 1reg: BORI4(reg,rc) "\tor $%c,$%0,%1\n" 1reg: BXORI4(reg,rc) "\txor $%c,$%0,%1\n" 1reg: BANDU4(reg,rc) "\tand $%c,$%0,%1\n" 1reg: BORU4(reg,rc) "\tor $%c,$%0,%1\n" 1reg: BXORU4(reg,rc) "\txor $%c,$%0,%1\n" 1reg: SUBI4(reg,rc) "\tsubu $%c,$%0,%1\n" 1reg: SUBP4(reg,rc) "\tsubu $%c,$%0,%1\n" 1reg: SUBU4(reg,rc) "\tsubu $%c,$%0,%1\n" 1reg: LSHI4(reg,CNSTI4) "# sll\n" 4reg: LSHU4(reg,CNSTI4) "# sll\n" 4reg: RSHI4(reg,CNSTI4) "# sra\n" 4reg: RSHU4(reg,CNSTI4) "# srl\n" 4reg: LSHI4(reg,reg) "\tjal __sll\n" 100reg: LSHU4(reg,reg) "\tjal __sll\n" 100reg: RSHI4(reg,reg) "\tjal __sra\n" 100reg: RSHU4(reg,reg) "\tjal __srl\n" 100reg: BCOMI4(reg) "\tli $30, -1; xor $%c,$%0,$30\n" 1reg: BCOMU4(reg) "\tli $30, -1; xor $%c,$%0,$30\n" 1reg: NEGI4(reg) "\tnegu $%c,$%0\n" 1reg: LOADI1(reg) "\tmove $%c,$%0\n" move(a)reg: LOADU1(reg) "\tmove $%c,$%0\n" move(a)reg: LOADI4(reg) "\tmove $%c,$%0\n" move(a)reg: LOADP4(reg) "\tmove $%c,$%0\n" move(a)reg: LOADU4(reg) "\tmove $%c,$%0\n" move(a)reg: LOADF4(reg) "\tmove $%c,$%0\n" move(a)reg: ADDF4(reg,reg) "\tjal float32_add\n" 100reg: SUBF4(reg,reg) "\tjal float32_sub\n" 100reg: MULF4(reg,reg) "\tjal float32_mul\n" 100reg: DIVF4(reg,reg) "\tjal float32_div\n" 100reg: NEGF4(reg) "\tjal float32_neg\n" 100reg: CVII4(reg) "\tsb $%0,CVII4_int; lb $%c,CVII4_int\n" 2reg: CVUI4(reg) "\tand $%c,$%0,255\n" 1reg: CVUU4(reg) "\tand $%c,$%0,255\n" 1reg: CVFF4(reg) "\t???" 100reg: CVIF4(reg) "\tjal int32_to_float32\n" 100reg: CVFI4(reg) "\tjal float32_to_int32_round_to_zero\n" 100stmt: LABELV "%a:\n"stmt: JUMPV(acon) "\tb %0\n" 1stmt: JUMPV(reg) "\tj $%0\n" 1stmt: EQI4(reg,reg) "\tbeq $%0,$%1,%a\n" 1stmt: EQU4(reg,reg) "\tbeq $%0,$%1,%a\n" 1stmt: NEI4(reg,reg) "\tbne $%0,$%1,%a\n" 1stmt: NEU4(reg,reg) "\tbne $%0,$%1,%a\n" 1stmt: LTI4(reg,reg) "\tslt $30,$%0,$%1\n\tbne $30,$0,%a\n" 2stmt: LTU4(reg,reg) "\tsltu $30,$%0,$%1\n\tbne $30,$0,%a\n" 2stmt: GTI4(reg,reg) "\tslt $30,$%1,$%0\n\tbne $30,$0,%a\n" 2stmt: GTU4(reg,reg) "\tsltu $30,$%1,$%0\n\tbne $30,$0,%a\n" 2stmt: GEI4(reg,reg) "\tslt $30,$%0,$%1\n\tbeq $30,$0,%a\n" 2stmt: GEU4(reg,reg) "\tsltu $30,$%0,$%1\n\tbeq $30,$0,%a\n" 2stmt: LEI4(reg,reg) "\tslt $30,$%1,$%0\n\tbeq $30,$0,%a\n" 2stmt: LEU4(reg,reg) "\tsltu $30,$%1,$%0\n\tbeq $30,$0,%a\n" 2 stmt: EQF4(reg,reg) "\tbeq $%0,$%1,%a\n" 1stmt: NEF4(reg,reg) "\tbne $%0,$%1,%a\n" 1stmt: LEF4(reg,reg) "\tslt $30,$%1,$%0\n\tbeq $30,$0,%a\n" 2stmt: LTF4(reg,reg) "\tslt $30,$%0,$%1\n\tbne $30,$0,%a\n" 2stmt: GEF4(reg,reg) "\tslt $30,$%0,$%1\n\tbeq $30,$0,%a\n" 2stmt: GTF4(reg,reg) "\tslt $30,$%1,$%0\n\tbne $30,$0,%a\n" 2reg: CALLF4(ar) "\tjal %0\n" 1reg: CALLI4(ar) "\tjal %0\n" 1reg: CALLP4(ar) "\tjal %0\n" 1reg: CALLU4(ar) "\tjal %0\n" 1stmt: CALLV(ar) "\tjal %0\n" 1ar: reg "$%0"ar: CNSTP4 "%a" range(a, 0, 0x0fffffff)ar: ADDRGP4 "%a"magic_addr: CNSTP4 "%a" is_magic_addr(a)reg: ADDI4(reg, ADDI4(reg, INDIRI4(magic_addr))) "\t.word (%c<<11)|(%0<<21)|(%1<<16)|0x30\n"reg: SUBI4(reg, ADDI4(reg, INDIRI4(magic_addr))) "\t.word (%c<<11)|(%0<<21)|(%1<<16)|0x31\n"reg: ADDI4(reg, SUBI4(reg, INDIRI4(magic_addr))) "\t.word (%c<<11)|(%0<<21)|(%1<<16)|0x32\n"reg: SUBI4(reg, SUBI4(reg, INDIRI4(magic_addr))) "\t.word (%c<<11)|(%0<<21)|(%1<<16)|0x33\n"reg: SUBI4(reg, SUBI4(reg, ADDI4(reg, INDIRI4(magic_addr)))) "\t.word (%c<<11)|(%2<<21)|(%2<<16)|0x35\n \t.word (%c<<11)|(%0<<21)|(%1<<16)|0x34\n"stmt: RETF4(reg) "# ret\n" 1stmt: RETI4(reg) "# ret\n" 1stmt: RETU4(reg) "# ret\n" 1stmt: RETP4(reg) "# ret\n" 1stmt: RETV(reg) "# ret\n" 1stmt: ARGF4(reg) "# arg\n" 1stmt: ARGI4(reg) "# arg\n" 1stmt: ARGP4(reg) "# arg\n" 1stmt: ARGU4(reg) "# arg\n" 1stmt: ARGB(INDIRB(reg)) "# argb %0\n" 1stmt: ASGNB(reg,INDIRB(reg)) "# asgnb %0 %1\n" 1%%intis_magic_addr (Node p){ return (int) p->syms[0]->u.c.v.p == 0x12344321 ? 0 : LBURG_MAX;}static voidprogend (void){}static voidprogbeg (int argc, char *argv[]){ int i; union { char c; int i; } u; u.i = 0; u.c = 1; swap = ((int) (u.i == 1)) != IR->little_endian; print ("\t.set reorder\n"); parseflags (argc, argv); for (i = 0; i < 32; i++) ireg[i] = mkreg ("%d", i, 1, IREG); ireg[29]->x.name = "sp"; iregw = mkwildcard (ireg); tmask[IREG] = INTTMP; vmask[IREG] = INTVAR; blkreg = mkreg ("8", 8, 7, IREG);}static Symbolrmap (int opk){ switch (optype (opk)) { case I: case U: case P: case B: case F: return iregw; default: return 0; }}static voidtarget (Node p){ assert (p); switch (specific (p->op)) { case DIV + I: case MOD + I: case MUL + I: case DIV + U: case MOD + U: case MUL + U: case DIV + F: case MOD + F: case MUL + F: case ADD + F: case SUB + F: setreg (p, ireg[2]); rtarget (p, 0, ireg[4]); rtarget (p, 1, ireg[5]); break; case NEG + F: case CVI + F: case CVF + I: setreg (p, ireg[2]); rtarget (p, 0, ireg[4]); break; case LSH + I: case LSH + U: case RSH + I: case RSH + U: if (generic (p->kids[1]->op) != CNST) { setreg (p, ireg[2]); rtarget (p, 0, ireg[4]); rtarget (p, 1, ireg[5]); } break; case CNST + I: case CNST + U: case CNST + P: if (range (p, 0, 0) == 0) { setreg (p, ireg[0]); p->x.registered = 1; } break; case CALL + V: rtarget (p, 0, ireg[25]); break; case CALL + I: case CALL + P: case CALL + U: case CALL + F: rtarget (p, 0, ireg[25]); setreg (p, ireg[2]); break; case RET + I: case RET + U: case RET + P: case RET + F: rtarget (p, 0, ireg[2]); break; case ARG + F: case ARG + I: case ARG + P: case ARG + U: { static int ty0; int ty = optype (p->op); Symbol q; q = argreg (p->x.argno, p->syms[2]->u.c.v.i, ty, opsize (p->op), ty0); if (p->x.argno == 0) ty0 = ty; if (q) rtarget (p, 0, q); break; } case ASGN + B: rtarget (p->kids[1], 0, blkreg); break; }}static voidclobber (Node p){ assert (p); switch (specific (p->op)) { case CALL + I: case CALL + P: case CALL + U: case CALL + F: case ADD + F: case SUB + F: case NEG + F: case DIV + F: case MOD + F: case MUL + F: case DIV + I: case DIV + U: case MOD + I: case MOD + U: case MUL + I: case MUL + U: case CVI + F: case CVF + I: spill (INTTMP, IREG, p); break;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -