gcc config
[prop.git] / prop-src / sparc.pC
blobc7b36ed229603bc597ea9903c83e0736059ef217
1 datatype Inst :: rewrite =
2     ADDD(Inst,Inst) | ADDF(Inst,Inst) | ADDI(Inst,Inst) 
3   | ADDP(Inst,Inst) | ADDU(Inst,Inst) 
4   | ADDRFP() | ADDRGP() | ADDRLP()
5   | ARGB(Inst) | ARGD(Inst) | ARGF(Inst) | ARGI(Inst) | ARGP(Inst) 
6   | ASGNB(Inst,Inst) | ASGNC(Inst,Inst) | ASGND(Inst,Inst) 
7   | ASGNF(Inst,Inst) | ASGNI(Inst,Inst) | ASGNP(Inst,Inst) | ASGNS(Inst,Inst) 
8   | BANDU(Inst,Inst) | BCOMU(Inst) | BORU(Inst,Inst) | BXORU(Inst,Inst) 
9   | CALLB(Inst,Inst) | CALLD(Inst) | CALLF(Inst) | CALLI(Inst) | CALLV(Inst) 
10   | CNSTC() | CNSTD() | CNSTF() | CNSTI() | CNSTP() | CNSTS() | CNSTU() 
11   | CVCI(Inst) | CVCU(Inst) | CVDF(Inst) | CVDI(Inst) | CVFD(Inst) 
12   | CVIC(Inst) | CVID(Inst) | CVIS(Inst) | CVIU(Inst) | CVPU(Inst) 
13   | CVSI(Inst) | CVSU(Inst) 
14   | CVUC(Inst) | CVUI(Inst) | CVUP(Inst) | CVUS(Inst) 
15   | DIVD(Inst,Inst) | DIVF(Inst,Inst) | DIVI(Inst,Inst) | DIVU(Inst,Inst) 
16   | EQD(Inst,Inst) | EQF(Inst,Inst) | EQI(Inst,Inst) 
17   | GED(Inst,Inst) | GEF(Inst,Inst) | GEI(Inst,Inst) | GEU(Inst,Inst) 
18   | GTD(Inst,Inst) | GTF(Inst,Inst) | GTI(Inst,Inst) | GTU(Inst,Inst) 
19   | INDIRB(Inst) | INDIRC(Inst) | INDIRD(Inst) | INDIRF(Inst)  
20   | INDIRI(Inst) | INDIRP(Inst) | INDIRS(Inst) 
21   | JUMPV(Inst) | LABELV() 
22   | LED(Inst,Inst) | LEF(Inst,Inst) | LEI(Inst,Inst) | LEU(Inst,Inst) 
23   | LOADB(Inst) | LOADC(Inst) | LOADD(Inst) | LOADF(Inst)  
24   | LOADI(Inst) | LOADP(Inst) | LOADS(Inst) | LOADU(Inst) 
25   | LSHI(Inst,Inst) | LSHU(Inst,Inst) 
26   | LTD(Inst,Inst) | LTF(Inst,Inst) | LTI(Inst,Inst) | LTU(Inst,Inst) 
27   | MODI(Inst,Inst) | MODU(Inst,Inst) 
28   | MULD(Inst,Inst) | MULF(Inst,Inst) | MULI(Inst,Inst) | MULU(Inst,Inst) 
29   | NED(Inst,Inst) | NEF(Inst,Inst) | NEI(Inst,Inst) 
30   | NEGD(Inst) | NEGF(Inst) | NEGI(Inst) 
31   | RETD(Inst) | RETF(Inst) | RETI(Inst) 
32   | RSHI(Inst,Inst) | RSHU(Inst,Inst) 
33   | SUBD(Inst,Inst) | SUBF(Inst,Inst) | SUBI(Inst,Inst) 
34   | SUBP(Inst,Inst) | SUBU(Inst,Inst) 
35   | VREGP() 
38 extern int move(Inst);
39 extern int range(Inst,int,int);
40 extern int imm(Inst);
41 extern int notarget(Inst);
43 void compile (Inst e)
45 rewrite (e) type (Inst) :: treeparser of
46    reg ->   INDIRC(VREGP()):     { "# read register\n"; }
47 |  reg ->   INDIRD(VREGP()):     { "# read register\n"; }
48 |  reg ->   INDIRF(VREGP()):     { "# read register\n"; }
49 |  reg ->   INDIRI(VREGP()):     { "# read register\n"; }
50 |  reg ->   INDIRP(VREGP()):     { "# read register\n"; }
51 |  reg ->   INDIRS(VREGP()):     { "# read register\n"; }
52 |  stmt ->  ASGNC(VREGP(),reg):  { "# write register\n"; }
53 |  stmt ->  ASGND(VREGP(),reg):  { "# write register\n"; }
54 |  stmt ->  ASGNF(VREGP(),reg):  { "# write register\n"; }
55 |  stmt ->  ASGNI(VREGP(),reg):  { "# write register\n"; }
56 |  stmt ->  ASGNP(VREGP(),reg):  { "# write register\n"; }
57 |  stmt ->  ASGNS(VREGP(),reg):  { "# write register\n"; }
58 |  con ->  CNSTC():  { "%a"; }
59 |  con ->  CNSTI():  { "%a"; }
60 |  con ->  CNSTP():  { "%a"; }
61 |  con ->  CNSTS():  { "%a"; }
62 |  con ->  CNSTU():  { "%a"; }
63 |  stmt ->  reg:  { ""; }
64 |  reg ->  CVIU(reg) \ notarget(redex):  { "%0"; }
65 |  reg ->  CVPU(reg) \ notarget(redex):  { "%0"; }
66 |  reg ->  CVUI(reg) \ notarget(redex):  { "%0"; }
67 |  reg ->  CVUP(reg) \ notarget(redex):  { "%0"; }
68 |  reg ->  ADDRGP():  { "set %a,%%%c\n"; }
69 |  stk13 ->  ADDRFP():  { "%a"; }
70 |  stk13 ->  ADDRLP():  { "%a"; }
71 |  reg ->    stk13 \ 1:   { "add %0,%%fp,%%%c\n"; }
72 |  stk ->  ADDRFP() \ 2:  { "set %a,%%%c\n"; }
73 |  stk ->  ADDRLP() \ 2:  { "set %a,%%%c\n"; }
74 |  reg ->  ADDRFP() \ 3:  { "set %a,%%%c\nadd %%%c,%%fp,%%%c\n"; }
75 |  reg ->  ADDRLP() \ 3:  { "set %a,%%%c\nadd %%%c,%%fp,%%%c\n"; }
76 |  con13 ->  CNSTC() \ imm(redex):  { "%a"; }
77 |  con13 ->  CNSTI() \ imm(redex):  { "%a"; }
78 |  con13 ->  CNSTP() \ imm(redex):  { "%a"; }
79 |  con13 ->  CNSTS() \ imm(redex):  { "%a"; }
80 |  con13 ->  CNSTU() \ imm(redex):  { "%a"; }
81 |  base ->  ADDI(reg,con13):  { "%%%0+%1"; }
82 |  base ->  ADDP(reg,con13):  { "%%%0+%1"; }
83 |  base ->  ADDU(reg,con13):  { "%%%0+%1"; }
84 |  base ->  reg:    { "%%%0"; }
85 |  base ->  con13:  { "%0"; }
86 |  base ->  stk13:  { "%%fp+%0"; }
87 |  addr ->  base:           { "%0"; }
88 |  addr ->  ADDI(reg,reg):  { "%%%0+%%%1"; }
89 |  addr ->  ADDP(reg,reg):  { "%%%0+%%%1"; }
90 |  addr ->  ADDU(reg,reg):  { "%%%0+%%%1"; }
91 |  addr ->  stk:            { "%%fp+%%%0"; }
92 |  reg ->   INDIRC(addr) \ 1:     { "ldsb [%0],%%%c\n"; }
93 |  reg ->   INDIRS(addr) \ 1:     { "ldsh [%0],%%%c\n"; }
94 |  reg ->   INDIRI(addr) \ 1:     { "ld [%0],%%%c\n"; }
95 |  reg ->   INDIRP(addr) \ 1:     { "ld [%0],%%%c\n"; }
96 |  reg ->   INDIRF(addr) \ 1:     { "ld [%0],%%f%c\n"; }
97 |  stmt ->  ASGNC(addr,reg) \ 1:  { "stb %%%1,[%0]\n"; }
98 |  stmt ->  ASGNS(addr,reg) \ 1:  { "sth %%%1,[%0]\n"; }
99 |  stmt ->  ASGNI(addr,reg) \ 1:  { "st %%%1,[%0]\n"; }
100 |  stmt ->  ASGNP(addr,reg) \ 1:  { "st %%%1,[%0]\n"; }
101 |  stmt ->  ASGNF(addr,reg) \ 1:  { "st %%f%1,[%0]\n"; }
102 |  addrl ->  ADDRLP() \ imm(redex):           { "%%%fp+%a"; }
103 |  reg ->    INDIRD(addrl) \ 1:    { "ldd [%0],%%f%c\n"; }
104 |  stmt ->   ASGND(addrl,reg) \ 1: { "std %%f%1,[%0]\n"; }
105 |  reg ->   INDIRD(base) \ 2:     { "ld2 [%0],%%f%c\n"; }
106 |  stmt ->  ASGND(base,reg) \ 2:  { "st2 %%f%1,[%0]\n"; }
107 |  spill ->   ADDRLP() \ ! imm(redex):          { "%a"; }
108 |  stmt ->  ASGNC(spill,reg):  { "set %0,%%g1\nstb %%%1,[%%fp+%%g1]\n"; }
109 |  stmt ->  ASGNS(spill,reg):  { "set %0,%%g1\nsth %%%1,[%%fp+%%g1]\n"; }
110 |  stmt ->  ASGNI(spill,reg):  { "set %0,%%g1\nst %%%1,[%%fp+%%g1]\n"; }
111 |  stmt ->  ASGNP(spill,reg):  { "set %0,%%g1\nst %%%1,[%%fp+%%g1]\n"; }
112 |  stmt ->  ASGNF(spill,reg):  { "set %0,%%g1\nst %%f%1,[%%fp+%%g1]\n"; }
113 |  stmt ->  ASGND(spill,reg):  { "set %0,%%g1\nstd %%f%1,[%%fp+%%g1]\n"; }
114 |  reg ->  CVCI(INDIRC(addr)):  { "ldsb [%0],%%%c\n"; }
115 |  reg ->  CVSI(INDIRS(addr)):  { "ldsh [%0],%%%c\n"; }
116 |  reg ->  CVCU(INDIRC(addr)):  { "ldub [%0],%%%c\n"; }
117 |  reg ->  CVSU(INDIRS(addr)):  { "lduh [%0],%%%c\n"; }
118 |  reg ->  CVIC(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
119 |  reg ->  CVIS(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
120 |  reg ->  CVIU(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
121 |  reg ->  CVPU(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
122 |  reg ->  CVUC(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
123 |  reg ->  CVUI(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
124 |  reg ->  CVUP(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
125 |  reg ->  CVUS(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
126 |  reg ->  CVIC(reg) \ notarget(redex):  { "%0"; }
127 |  reg ->  CVIS(reg) \ notarget(redex):  { "%0"; }
128 |  reg ->  CVUC(reg) \ notarget(redex):  { "%0"; }
129 |  reg ->  CVUS(reg) \ notarget(redex):  { "%0"; }
130 |  reg ->  LOADC(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
131 |  reg ->  LOADI(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
132 |  reg ->  LOADP(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
133 |  reg ->  LOADS(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
134 |  reg ->  LOADU(reg) \ move(redex):  { "mov %%%0,%%%c\n"; }
135 |  reg ->  CNSTC() \ range(redex,0,0):  { "# reg\n"; }
136 |  reg ->  CNSTI() \ range(redex,0,0):  { "# reg\n"; }
137 |  reg ->  CNSTP() \ range(redex,0,0):  { "# reg\n"; }
138 |  reg ->  CNSTS() \ range(redex,0,0):  { "# reg\n"; }
139 |  reg ->  CNSTU() \ range(redex,0,0):  { "# reg\n"; }
140 |  reg ->  con \ 1:  { "set %0,%%%c\n"; }
141 |  rc ->  con13:  { "%0"; }
142 |  rc ->  reg:    { "%%%0"; }
143 |  reg ->  ADDI(reg,rc) \ 1:   { "add %%%0,%1,%%%c\n"; }
144 |  reg ->  ADDP(reg,rc) \ 1:   { "add %%%0,%1,%%%c\n"; }
145 |  reg ->  ADDU(reg,rc) \ 1:   { "add %%%0,%1,%%%c\n"; }
146 |  reg ->  BANDU(reg,rc) \ 1:  { "and %%%0,%1,%%%c\n"; }
147 |  reg ->  BORU(reg,rc) \ 1:   { "or %%%0,%1,%%%c\n" ; }
148 |  reg ->  BXORU(reg,rc) \ 1:  { "xor %%%0,%1,%%%c\n"; }
149 |  reg ->  SUBI(reg,rc) \ 1:   { "sub %%%0,%1,%%%c\n"; }
150 |  reg ->  SUBP(reg,rc) \ 1:   { "sub %%%0,%1,%%%c\n"; }
151 |  reg ->  SUBU(reg,rc) \ 1:   { "sub %%%0,%1,%%%c\n"; }
152 |  rc5 ->  CNSTI() \ range(redex,0,31):  { "%a"; }
153 |  rc5 ->  reg:    { "%%%0"; }
154 |  reg ->  LSHI(reg,rc5) \ 1:  { "sll %%%0,%1,%%%c\n"; }
155 |  reg ->  LSHU(reg,rc5) \ 1:  { "sll %%%0,%1,%%%c\n"; }
156 |  reg ->  RSHI(reg,rc5) \ 1:  { "sra %%%0,%1,%%%c\n"; }
157 |  reg ->  RSHU(reg,rc5) \ 1:  { "srl %%%0,%1,%%%c\n"; }
158 |  reg ->  BANDU(reg,BCOMU(rc)) \ 1:  { "andn %%%0,%1,%%%c\n"; }
159 |  reg ->  BORU(reg,BCOMU(rc)) \ 1:   { "orn %%%0,%1,%%%c\n"; }
160 |  reg ->  BXORU(reg,BCOMU(rc)) \ 1:  { "xnor %%%0,%1,%%%c\n"; }
161 |  reg ->  NEGI(reg) \ 1:   { "neg %%%0,%%%c\n"; }
162 |  reg ->  BCOMU(reg) \ 1:  { "not %%%0,%%%c\n"; }
163 |  reg ->  CVCI(reg) \ 2:  { "sll %%%0,24,%%%c; sra %%%c,24,%%%c\n"; }
164 |  reg ->  CVSI(reg) \ 2:  { "sll %%%0,16,%%%c; sra %%%c,16,%%%c\n"; }
165 |  reg ->  CVCU(reg) \ 1:  { "and %%%0,0xff,%%%c\n"; }
166 |  reg ->  CVSU(reg) \ 2:  { "set 0xffff,%%g1; and %%%0,%%g1,%%%c\n"; }
167 |  addrg ->  ADDRGP():        { "%a"; }
168 |  stmt ->   JUMPV(addrg) \ 2:  { "ba %0; nop\n"; }
169 |  stmt ->   JUMPV(addr) \ 2:   { "jmp %0; nop\n"; }
170 |  stmt ->   LABELV():        { "%a:\n"; }
171 |  stmt ->  EQI(reg,rc) \ 3:  { "cmp %%%0,%1; be %a; nop\n"; }
172 |  stmt ->  GEI(reg,rc) \ 3:  { "cmp %%%0,%1; bge %a; nop\n"; }
173 |  stmt ->  GEU(reg,rc) \ 3:  { "cmp %%%0,%1; bgeu %a; nop\n"; }
174 |  stmt ->  GTI(reg,rc) \ 3:  { "cmp %%%0,%1; bg %a; nop\n"; }
175 |  stmt ->  GTU(reg,rc) \ 3:  { "cmp %%%0,%1; bgu %a; nop\n"; }
176 |  stmt ->  LEI(reg,rc) \ 3:  { "cmp %%%0,%1; ble %a; nop\n"; }
177 |  stmt ->  LEU(reg,rc) \ 3:  { "cmp %%%0,%1; bleu %a; nop\n"; }
178 |  stmt ->  LTI(reg,rc) \ 3:  { "cmp %%%0,%1; bl %a; nop\n"; }
179 |  stmt ->  LTU(reg,rc) \ 3:  { "cmp %%%0,%1; blu %a; nop\n"; }
180 |  stmt ->  NEI(reg,rc) \ 3:  { "cmp %%%0,%1; bne %a; nop\n"; }
181 |  call ->  ADDRGP():           { "%a"; }
182 |  call ->  addr:             { "%0"; }
183 |  reg ->   CALLD(call) \ 2:      { "call %0; nop\n"; }
184 |  reg ->   CALLF(call) \ 2:      { "call %0; nop\n"; }
185 |  reg ->   CALLI(call) \ 2:      { "call %0; nop\n"; }
186 |  stmt ->  CALLV(call) \ 2:      { "call %0; nop\n"; }
187 |  stmt ->  CALLB(call,reg) \ 2:  { "call %0; st %%%1,[%%sp+64]\n"; }
188 |  stmt ->  RETD(reg) \ 1:  { "# ret\n"; }
189 |  stmt ->  RETF(reg) \ 1:  { "# ret\n"; }
190 |  stmt ->  RETI(reg) \ 1:  { "# ret\n"; }
191 |  stmt ->  ARGI(reg) \ 1:  { "st %%%0,[%%sp+4*%c+68]\n"; }
192 |  stmt ->  ARGP(reg) \ 1:  { "st %%%0,[%%sp+4*%c+68]\n"; }
193 |  stmt ->  ARGD(reg) \ 1:  { "# ARGD\n"; }
194 |  stmt ->  ARGF(reg) \ 1:  { "# ARGF\n"; }
195 |  reg ->  DIVI(reg,reg) \ 2:  { "call .div,2; nop\n"; }
196 |  reg ->  DIVU(reg,reg) \ 2:  { "call .udiv,2; nop\n"; }
197 |  reg ->  MODI(reg,reg) \ 2:  { "call .rem,2; nop\n"; }
198 |  reg ->  MODU(reg,reg) \ 2:  { "call .urem,2; nop\n"; }
199 |  reg ->  MULI(reg,reg) \ 2:  { "call .mul,2; nop\n"; }
200 |  reg ->  MULU(reg,reg) \ 2:  { "call .umul,2; nop\n"; }
201 |  reg ->  ADDD(reg,reg) \ 1:  { "faddd %%f%0,%%f%1,%%f%c\n"; }
202 |  reg ->  ADDF(reg,reg) \ 1:  { "fadds %%f%0,%%f%1,%%f%c\n"; }
203 |  reg ->  DIVD(reg,reg) \ 1:  { "fdivd %%f%0,%%f%1,%%f%c\n"; }
204 |  reg ->  DIVF(reg,reg) \ 1:  { "fdivs %%f%0,%%f%1,%%f%c\n"; }
205 |  reg ->  MULD(reg,reg) \ 1:  { "fmuld %%f%0,%%f%1,%%f%c\n"; }
206 |  reg ->  MULF(reg,reg) \ 1:  { "fmuls %%f%0,%%f%1,%%f%c\n"; }
207 |  reg ->  SUBD(reg,reg) \ 1:  { "fsubd %%f%0,%%f%1,%%f%c\n"; }
208 |  reg ->  SUBF(reg,reg) \ 1:  { "fsubs %%f%0,%%f%1,%%f%c\n"; }
209 |  reg ->  NEGF(reg) \ 1:   { "fnegs %%f%0,%%f%c\n"; }
210 |  reg ->  LOADF(reg) \ 1:  { "fmovs %%f%0,%%f%c\n"; }
211 |  reg ->  CVDF(reg) \ 1:   { "fdtos %%f%0,%%f%c\n"; }
212 |  reg ->  CVFD(reg) \ 1:   { "fstod %%f%0,%%f%c\n"; }
213 |  reg ->  CVDI(reg) \ 3:  { "fdtoi %%f%0,%%f0; st %%f0,[%%sp+64]; ld [%%sp+64],%%%c\n"; }
214 |  reg ->  CVID(reg) \ 3:  { "st %%%0,[%%sp+64]; ld [%%sp+64],%%f%c; fitod %%f%c,%%f%c\n"; }
215 |  rel ->  EQD(reg,reg):  { "fcmped %%f%0,%%f%1; nop; fbue"; }
216 |  rel ->  EQF(reg,reg):  { "fcmpes %%f%0,%%f%1; nop; fbue"; }
217 |  rel ->  GED(reg,reg):  { "fcmped %%f%0,%%f%1; nop; fbuge"; }
218 |  rel ->  GEF(reg,reg):  { "fcmpes %%f%0,%%f%1; nop; fbuge"; }
219 |  rel ->  GTD(reg,reg):  { "fcmped %%f%0,%%f%1; nop; fbug"; }
220 |  rel ->  GTF(reg,reg):  { "fcmpes %%f%0,%%f%1; nop; fbug"; }
221 |  rel ->  LED(reg,reg):  { "fcmped %%f%0,%%f%1; nop; fbule"; }
222 |  rel ->  LEF(reg,reg):  { "fcmpes %%f%0,%%f%1; nop; fbule"; }
223 |  rel ->  LTD(reg,reg):  { "fcmped %%f%0,%%f%1; nop; fbul"; }
224 |  rel ->  LTF(reg,reg):  { "fcmpes %%f%0,%%f%1; nop; fbul"; }
225 |  rel ->  NED(reg,reg):  { "fcmped %%f%0,%%f%1; nop; fbne"; }
226 |  rel ->  NEF(reg,reg):  { "fcmpes %%f%0,%%f%1; nop; fbne"; }
227 |  stmt ->  rel \ 4:  { "%0 %a; nop\n"; }
228 |  reg ->   LOADD(reg) \ 2:  { "# LOADD\n"; }
229 |  reg ->   NEGD(reg) \ 2:  { "# NEGD\n"; }
230 |  stmt ->  ASGNB(reg,INDIRB(reg)):  { "# ASGNB\n"; }
231 end rewrite;