1 // CodeGen.spec, created Tue Jul 6 12:12:41 1999 by pnkfelix 2 // Copyright (C) 1999 Felix S. Klock II <pnkfelix@mit.edu> 3 // Licensed under the terms of the GNU GPL; see COPYING for details. 4 package harpoon.Backend.StrongARM; 5 6 import harpoon.Backend.Maps.NameMap; 7 import harpoon.ClassFile.HClass; 8 import harpoon.ClassFile.HCodeElement; 9 import harpoon.ClassFile.HMethod; 10 import harpoon.IR.Assem.Instr; 11 import harpoon.IR.Assem.InstrEdge; 12 import harpoon.IR.Assem.InstrMEM; 13 import harpoon.IR.Assem.InstrJUMP; 14 import harpoon.IR.Assem.InstrMOVE; 15 import harpoon.IR.Assem.InstrCALL; 16 import harpoon.IR.Assem.InstrLABEL; 17 import harpoon.IR.Assem.InstrDIRECTIVE; 18 import harpoon.IR.Assem.InstrFactory; 19 import harpoon.IR.Tree.TreeDerivation; 20 import harpoon.IR.Tree.Bop; 21 import harpoon.IR.Tree.Uop; 22 import harpoon.IR.Tree.Type; 23 import harpoon.IR.Tree.TEMP; 24 import harpoon.IR.Tree.Typed; 25 import harpoon.IR.Tree.PreciselyTyped; 26 import harpoon.IR.Tree.ExpList; 27 import harpoon.Temp.TempList; 28 import harpoon.Temp.Temp; 29 import harpoon.Temp.LabelList; 30 import harpoon.Temp.Label; 31 32 import harpoon.IR.Tree.BINOP; 33 import harpoon.IR.Tree.CALL; 34 import harpoon.IR.Tree.INVOCATION; 35 import harpoon.IR.Tree.CJUMP; 36 import harpoon.IR.Tree.CONST; 37 import harpoon.IR.Tree.EXPR; 38 import harpoon.IR.Tree.JUMP; 39 import harpoon.IR.Tree.LABEL; 40 import harpoon.IR.Tree.MEM; 41 import harpoon.IR.Tree.MOVE; 42 import harpoon.IR.Tree.NAME; 43 import harpoon.IR.Tree.NATIVECALL; 44 import harpoon.IR.Tree.OPER; 45 import harpoon.IR.Tree.RETURN; 46 import harpoon.IR.Tree.TEMP; 47 import harpoon.IR.Tree.UNOP; 48 import harpoon.IR.Tree.SEQ; 49 50 import java.util.ArrayList; 51 import java.util.Arrays; 52 import java.util.Collections; 53 import java.util.Comparator; 54 import java.util.List; 55 import java.util.Set; 56 import java.util.HashSet; 57 import java.util.Map; 58 import java.util.HashMap; 59 import java.util.Iterator; 60 61 import net.cscott.jutil.Util; 62 /** 63 * <code>StrongARM.CodeGen</code> is a code-generator for the ARM architecture. 64 * 65 * @see "Jaggar, <U>ARM Architecture Reference Manual</U>" 66 * @author Felix S. Klock II <pnkfelix@mit.edu> 67 * @version $Id: CodeGen.spec,v 1.6 2004/02/08 01:57:59 cananian Exp $ 68 */ 69 // NOTE THAT the StrongARM actually manipulates the DOUBLE type in quasi- 70 // big-endian (45670123) order. To keep things simple, the 'low' temp in 71 // a two-word temp representing a double represents the MSB, and the 'high' 72 // temp the LSB. This makes sure that the parameter-passing order is 73 // correct, even if we don't know whether a given two-word-temp is LONG or 74 // double. See the CONST rules for some more oddity related to this quirk. 75 76 public class CodeGen extends harpoon.Backend.Generic.MaxMunchCG { 77 // InstrFactory to generate Instrs from 78 private InstrFactory instrFactory; 79 80 81 final RegFileInfo regfile; 82 private Temp r0, r1, r2, r3, r4, r5, r6, FP, IP, SP, LR, PC; 83 Comparator regComp; 84 85 // whether to generate stabs debugging information in output (-g flag) 86 private static final boolean stabsDebugging=true; 87 88 // NameMap for calling C functions. 89 NameMap nameMap; 90 91 // whether to generate a.out-style or elf-style segment directives 92 private final boolean is_elf; 93 // whether to use soft-float or hard-float calling convention. 94 private final boolean soft_float = false; // skiffs use hard-float 95 96 public CodeGen(Frame frame, boolean is_elf) { 97 super(frame); 98 last = null; 99 this.regfile = (RegFileInfo) frame.getRegFileInfo(); 100 this.nameMap = frame.getRuntime().getNameMap(); 101 this.is_elf = is_elf; 102 r0 = regfile.reg[0]; 103 r1 = regfile.reg[1]; 104 r2 = regfile.reg[2]; 105 r3 = regfile.reg[3]; 106 r4 = regfile.reg[4]; 107 r5 = regfile.reg[5]; 108 r6 = regfile.reg[6]; 109 FP = regfile.FP; // reg 11 110 IP = regfile.reg[12]; 111 SP = regfile.SP; // reg 13 112 LR = regfile.LR; // reg 14 113 PC = regfile.PC; // reg 15 114 // allow sorting of registers so that stm and ldm work correctly. 115 final Map regToNum = new HashMap(); 116 for (int i=0; i<regfile.reg.length; i++) 117 regToNum.put(regfile.reg[i], new Integer(i)); 118 regComp = new Comparator() { 119 public int compare(Object o1, Object o2) { 120 assert regToNum.keySet().contains(o1) : /* o1+ */" not in regToNum's keys"; 121 assert regToNum.keySet().contains(o2) : /* o2+ */" not in regToNum's keys"; 122 return ((Integer)regToNum.get(o1)).intValue() - 123 ((Integer)regToNum.get(o2)).intValue(); 124 } 125 }; 126 } 127 128 129 /** The main Instr layer; nothing below this line should call 130 emit(Instr) directly, unless they are constructing extensions 131 of Instr. 132 */ 133 private Instr emit(HCodeElement root, String assem, 134 Temp[] dst, Temp[] src, 135 boolean canFallThrough, List<Label> targets) { 136 return emit(new Instr( instrFactory, root, assem, 137 dst, src, canFallThrough, targets)); 138 } 139 140 /** Secondary emit layer; for primary usage by the other emit 141 methods. 142 */ 143 private Instr emit2(HCodeElement root, String assem, 144 Temp[] dst, Temp[] src) { 145 return emit(root, assem, dst, src, true, null); 146 } 147 148 /** Single dest Single source Emit Helper. */ 149 private Instr emit( HCodeElement root, String assem, 150 Temp dst, Temp src) { 151 return emit2(root, assem, new Temp[]{ dst }, new Temp[]{ src }); 152 } 153 154 155 /** Single dest Two source Emit Helper. */ 156 private Instr emit( HCodeElement root, String assem, 157 Temp dst, Temp src1, Temp src2) { 158 return emit2(root, assem, new Temp[]{ dst }, 159 new Temp[]{ src1, src2 }); 160 } 161 162 /** Null dest Null source Emit Helper. */ 163 private Instr emit( HCodeElement root, String assem ) { 164 return emit2(root, assem, null, null); 165 } 166 167 /** Single dest Single source emit InstrMOVE helper */ 168 private Instr emitMOVE( HCodeElement root, String assem, 169 Temp dst, Temp src) { 170 return emit(new InstrMOVE( instrFactory, root, assem+" @move", 171 new Temp[]{ dst }, 172 new Temp[]{ src })); 173 } 174 175 /* Branching instruction emit helper. 176 Instructions emitted using this *can* fall through. 177 */ 178 private Instr emit( HCodeElement root, String assem, 179 Temp[] dst, Temp[] src, Label[] targets ) { 180 return emit(new Instr( instrFactory, root, assem, 181 dst, src, true, Arrays.asList(targets))); 182 } 183 184 /* Branching instruction emit helper. 185 Instructions emitted using this *cannot* fall through. 186 */ 187 private Instr emitNoFall( HCodeElement root, String assem, 188 Temp[] dst, Temp[] src, Label[] targets ) { 189 return emit(new Instr( instrFactory, root, assem, 190 dst, src, false, Arrays.asList(targets))); 191 } 192 193 /* Call instruction emit helper. 194 Instructions emitted using this *cannot* fall through. 195 */ 196 private Instr emitCallNoFall( HCodeElement root, String assem, 197 Temp[] dst, Temp[] src, Label[] targets ) { 198 List<Label> tlist = (targets==null?null:Arrays.asList(targets)); 199 return emit(new InstrCALL( instrFactory, root, assem, 200 dst, src, false, tlist)); 201 } 202 203 private Instr emitNativeCall( HCodeElement root, String assem, 204 Temp[] dst, Temp[] src, 205 boolean canFall, Label[] targets) { 206 List<Label> tlist = (targets==null?null:Arrays.asList(targets)); 207 return emit(new InstrCALL( instrFactory, root, assem, 208 dst, src, canFall, tlist)); 209 } 210 211 /* InstrJUMP emit helper; automatically adds entry to 212 label->branches map. */ 213 private Instr emitJUMP( HCodeElement root, String assem, Label l ) { 214 Instr j = emit( new InstrJUMP( instrFactory, root, assem, l )); 215 return j; 216 } 217 218 /* InstrLABEL emit helper. */ 219 private Instr emitLABEL( HCodeElement root, String assem, Label l ) { 220 return emit( new InstrLABEL( instrFactory, root, assem, l )); 221 } 222 /* InstrLABEL emit helper. */ 223 private Instr emitNoFallLABEL( HCodeElement root, String assem, Label l ) { 224 return emit( InstrLABEL.makeNoFall( instrFactory, root, assem, l )); 225 } 226 227 /* InstrDIRECTIVE emit helper. */ 228 private Instr emitDIRECTIVE( HCodeElement root, String assem ) { 229 return emit( new InstrDIRECTIVE( instrFactory, root, assem )); 230 } 231 /* InstrDIRECTIVE emit helper. */ 232 private Instr emitNoFallDIRECTIVE( HCodeElement root, String assem ) { 233 return emit( InstrDIRECTIVE.makeNoFall( instrFactory, root, assem )); 234 } 235 236 // helper for predicate clauses 237 private boolean is12BitOffset(long val) { 238 // addressing mode two takes a 12 bit unsigned offset, with 239 // an additional bit in the instruction word indicating whether 240 // to add or subtract this offset. This means that there 241 // are two representations for zero offset: +0 and -0. 242 long absval = (val<0)?-val:val; 243 return (absval&(~0xFFF))==0; 244 } 245 private boolean is12BitOffset(Number n) { 246 if (n instanceof Double || n instanceof Float) return false; 247 else return is12BitOffset(n.longValue()); 248 } 249 // helper for operand2 shifts 250 private boolean is5BitShift(long val) { 251 return (val>=0) && (val<=31); 252 } 253 private boolean is5BitShift(Number n) { 254 if (n instanceof Double || n instanceof Float) return false; 255 else return is5BitShift(n.longValue()); 256 } 257 private boolean isShiftOp(int op) { 258 switch (op) { 259 case Bop.SHL: case Bop.SHR: case Bop.USHR: return true; 260 default: return false; 261 } 262 } 263 private String shiftOp2Str(int op) { 264 switch (op) { 265 case Bop.SHL: return "lsl"; 266 case Bop.SHR: return "asr"; 267 case Bop.USHR: return "lsr"; 268 default: throw new Error("Illegal shift operation"); 269 } 270 } 271 // helper for comparison operations 272 private boolean isCmpOp(int op) { 273 switch (op) { 274 case Bop.CMPEQ: case Bop.CMPNE: 275 case Bop.CMPGT: case Bop.CMPGE: 276 case Bop.CMPLT: case Bop.CMPLE: return true; 277 default: return false; 278 } 279 } 280 private String cmpOp2Str(int op) { 281 switch (op) { 282 case Bop.CMPEQ: return "eq"; 283 case Bop.CMPNE: return "ne"; 284 case Bop.CMPGT: return "gt"; 285 case Bop.CMPGE: return "ge"; 286 case Bop.CMPLE: return "le"; 287 case Bop.CMPLT: return "lt"; 288 default: throw new Error("Illegal compare operation"); 289 } 290 } 291 // variants for unsigned compares, which we need for the low word of 292 // long integer comparisons. 293 private String cmpOp2StrUNSIGNED(int op) { 294 switch (op) { 295 case Bop.CMPEQ: return "eq"; 296 case Bop.CMPNE: return "ne"; 297 case Bop.CMPGT: return "hi"; 298 case Bop.CMPGE: return "hs"; 299 case Bop.CMPLE: return "ls"; 300 case Bop.CMPLT: return "lo"; 301 default: throw new Error("Illegal compare operation"); 302 } 303 } 304 private String cmpOp2Func(int op) { 305 switch (op) { 306 case Bop.CMPEQ: return "__ne"; 307 case Bop.CMPNE: return "__ne"; 308 case Bop.CMPGT: return "__gt"; 309 case Bop.CMPGE: return "__lt"; 310 case Bop.CMPLE: return "__gt"; 311 case Bop.CMPLT: return "__lt"; 312 default: throw new Error("Illegal compare operation"); 313 } 314 } 315 private boolean cmpOpFuncInverted(int op) { 316 switch (op) { 317 case Bop.CMPEQ: return true; 318 case Bop.CMPNE: return false; 319 case Bop.CMPGT: return false; 320 case Bop.CMPGE: return true; 321 case Bop.CMPLE: return true; 322 case Bop.CMPLT: return false; 323 default: throw new Error("Illegal compare operation"); 324 } 325 } 326 // helper for operand2 immediates 327 private boolean isOpd2Imm(Number n) { 328 if (!(n instanceof Integer)) return false; 329 else return isOpd2Imm(n.intValue()); 330 } 331 private boolean isOpd2Imm(int val) { 332 return (steps(val)<=1); 333 } 334 private int negate(Number n) { 335 return -((Integer)n).intValue(); 336 } 337 // helper for outputting constants 338 private String loadConst32(String reg, int val, String humanReadable) { 339 StringBuffer sb=new StringBuffer(); 340 String MOV="mov ", ADD="add "; 341 // sometimes it is easier to load the complement of the number. 342 boolean invert = (steps(~val) < steps(val)); 343 if (invert) { val=~val; MOV="mvn "; ADD="sub "; } 344 // continue until there are no more bits to load... 345 boolean first=true; 346 while (val!=0) { 347 // get next eight-bit chunk (shift amount has to be even) 348 int eight = val & (0xFF << ((Util.ffs(val)-1) & ~1)); 349 if (first) { 350 first=false; 351 sb.append(MOV+reg+", #"+eight+ 352 " @ loading constant "+humanReadable); 353 } else 354 sb.append("\n"+ADD+reg+", "+reg+", #"+eight); 355 // zero out the eight bit chunk we just loaded, and continue. 356 val ^= eight; 357 } 358 if (first) return MOV+reg+", #0 @ loading constant "+humanReadable; 359 else return sb.toString(); 360 } 361 /* returns the number of instructions it will take to load the 362 * specified constant. */ 363 private int steps(int v) { 364 int r=0; 365 for ( ; v!=0; r++) 366 v &= ~(0xFF << ((Util.ffs(v)-1) & ~1)); 367 return r; 368 } 369 // helpers for floating-point return values. 370 /* The StrongARM contains a curious mix of calling conventions in its 371 * floating point libraries: functions in libgcc.a (the standard 372 * gcc "helper" library) use the hard-float calling convention, which 373 * puts floating-point return values in floating-point registers. C 374 * native code on skiff/netwinder does also. *However*, the libfloat 375 * floating point library uses integer registers throughout -- BUT 376 * OMITS those functions included in libgcc. So some functions use 377 * hard-float conventions, and some don't. And we still leave open 378 * the option (by setting the soft_float flag) of building code for 379 * a system which uses -msoft-float throughout. These two helper 380 * functions Do The Right Thing for floating-point return values using 381 * the 'native' (ie, same as libgcc) calling convention. */ 382 private void emitMoveFromNativeFloatRetVal(HCodeElement ROOT, Temp dst) { 383 declare(dst, HClass.Float); 384 // native call returns a float. 385 if (soft_float) { // system built with -msoft-float throughout. 386 // float retval passed in int register r0. 387 emitMOVE( ROOT, "mov `d0, `s0", dst, r0 ); 388 } else { 389 // float retval passed in float register f0. 390 declare ( SP, HClass.Void ); 391 emit( ROOT, "stfs f0, [sp, #-4]!", SP, SP); 392 emit2(ROOT, "ldr `d0, [sp], #4",new Temp[]{dst,SP},new Temp[]{SP}); 393 } 394 } 395 private void emitMoveFromNativeDoubleRetVal(HCodeElement ROOT, Temp dst) { 396 // native call returns a double. 397 declare(dst, HClass.Double); 398 if (soft_float) { // system built with -msoft-float throughout. 399 // double retval passed in int registers r0,r1 400 // not certain an emitMOVE is legal with the l/h modifiers 401 emit( ROOT, "mov `d0l, `s0", dst, r0 ); 402 emit( ROOT, "mov `d0h, `s0", dst, r1 ); 403 } else { 404 // double retval passed in float register f0. 405 declare ( SP, HClass.Void ); 406 emit( ROOT, "stfd f0, [sp, #-8]!", SP, SP); 407 emit2(ROOT,"ldr `d0l, [sp], #4",new Temp[]{dst,SP},new Temp[]{SP}); 408 emit2(ROOT,"ldr `d0h, [sp], #4",new Temp[]{dst,SP},new Temp[]{SP}); 409 } 410 } 411 412 /** simple tuple class to wrap some bits of info about the call prologue */ 413 private class CallState { 414 /** number of parameter bytes pushed on to the stack. */ 415 final int stackOffset; 416 /** set of registers used by parameters to the call. */ 417 final List callUses; 418 CallState(int stackOffset, List callUses) { 419 this.stackOffset=stackOffset; this.callUses=callUses; 420 } 421 /** Append a stack-offset instruction to the actual call. 422 * We delay the stack-offset to the point where it is 423 * atomic with the call, so that the register allocator 424 * can't insert spill code between the stack adjustment 425 * and the call. (the spill code would fail horribly in 426 * that case, because the stack pointer won't be where it 427 * expects it to be.) */ 428 String prependSPOffset(String asmString) { 429 // optimize for common case. 430 // CSA: THIS ROUTINE NO LONGER NEEDED. we offset from FP now. 431 if (true || stackOffset==0) return asmString; 432 declare( SP, HClass.Void ); 433 return "sub sp, sp, #"+stackOffset+"\n\t"+asmString; 434 } 435 } 436 437 /** Declare Void types for r0, r1, r2, r3, IP, LR in prep for a call. */ 438 private void declareCALL() { 439 declare(r0, HClass.Void); 440 declare(r1, HClass.Void); 441 declare(r2, HClass.Void); 442 declare(r3, HClass.Void); 443 declare(IP, HClass.Void); 444 declare(LR, HClass.Void); 445 declare(PC, HClass.Void); 446 } 447 private boolean isDoubleWord(Typed ty) { 448 switch (ty.type()) { 449 case Type.LONG: case Type.DOUBLE: return true; 450 default: return false; 451 } 452 } 453 /** Helper for setting up registers/memory with the strongARM standard 454 * calling convention. Returns the stack offset necessary, 455 * along with a set of registers used by the parameters. */ 456 private CallState emitCallPrologue(INVOCATION ROOT, 457 TempList tlist, 458 TreeDerivation td) { 459 ExpList elist = ROOT.getArgs(); 460 /** OUTPUT ARGUMENT ASSIGNMENTS IN REVERSE ORDER **/ 461 List callUses = new ArrayList(6); 462 int stackOffset = 0; 463 // reverse list and count # of words required 464 TempList treverse=null; 465 ExpList ereverse=null; 466 int index=0; 467 for(TempList tl=tlist; tl!=null; tl=tl.tail, elist=elist.tail) { 468 treverse=new TempList(tl.head, treverse); 469 ereverse=new ExpList(elist.head, ereverse); 470 index+=isDoubleWord(elist.head) ? 2 : 1; 471 } 472 // add all registers up to and including r3 to callUses list. 473 for (int i=0; i<index && i<4; i++) 474 callUses.add(frame.getRegFileInfo().getRegister(i)); 475 index--; // so index points to 'register #' of last argument. 476 477 elist=ereverse; 478 for (TempList tl = treverse; tl != null; tl=tl.tail, elist=elist.tail) { 479 Temp temp = tl.head; 480 if (isDoubleWord(elist.head)) { 481 // arg takes up two words 482 switch(index) { 483 case 0: throw new Error("Not enough space!"); 484 case 1: case 2: case 3: // put in registers 485 // not certain an emitMOVE is legal with the l/h modifiers 486 Temp rfirst = frame.getRegFileInfo().getRegister(index--); 487 declare(rfirst, HClass.Void); 488 Temp rsecnd = frame.getRegFileInfo().getRegister(index--); 489 declare(rsecnd, HClass.Void); 490 emit( ROOT, "mov `d0, `s0h", rfirst, temp ); 491 emit( ROOT, "mov `d0, `s0l", rsecnd, temp ); 492 break; 493 case 4: // spread between regs and stack 494 stackOffset += 4; index--; 495 declare( SP, HClass.Void ); 496 emit(new InstrMEM( instrFactory, ROOT, 497 "str `s0h, [`s1, #-4]!", 498 new Temp[] { SP }, 499 new Temp[]{ temp, SP })); 500 // not certain an emitMOVE is legal with the l/h modifiers 501 Temp rthird = frame.getRegFileInfo().getRegister(index--); 502 declare( rthird, HClass.Void ); 503 emit( ROOT, "mov `d0, `s0l", rthird, temp ); 504 break; 505 default: // start putting args in memory 506 stackOffset += 4; index--; 507 declare( SP, HClass.Void ); 508 emit(new InstrMEM( instrFactory, ROOT, 509 "str `s0h, [`s1, #-4]!", 510 new Temp[]{ SP }, 511 new Temp[]{ temp, SP })); 512 stackOffset += 4; index--; 513 declare( SP, HClass.Void ); 514 emit(new InstrMEM( instrFactory, ROOT, 515 "str `s0l, [`s1, #-4]!", 516 new Temp[]{ SP }, 517 new Temp[]{ temp, SP })); 518 break; 519 } 520 } else { 521 // arg is one word 522 if (index < 4) { 523 Temp reg = frame.getRegFileInfo().getRegister(index--); 524 declare( reg, td, elist.head ); 525 emitMOVE( ROOT, "mov `d0, `s0", reg, temp); 526 } else { 527 stackOffset += 4; index--; 528 declare( SP, HClass.Void ); 529 emit(new InstrMEM( 530 instrFactory, ROOT, 531 "str `s0, [`s1, #-4]!", 532 new Temp[]{ SP }, 533 new Temp[]{ temp, SP })); 534 } 535 } 536 } 537 assert index==-1; 538 declareCALL(); 539 if (ROOT.getRetval()!=null) declare( r0, td, ROOT.getRetval() ); 540 return new CallState(stackOffset, callUses); 541 } 542 /** Make a handler stub. */ 543 private void emitHandlerStub(INVOCATION ROOT, Temp retex, Label handler) { 544 declare( retex, frame.getLinker().forName("java.lang.Throwable")); 545 emitMOVE ( ROOT, "mov `d0, `s0", retex, r0 ); 546 emitJUMP ( ROOT, "b "+handler, handler); 547 } 548 /** Emit a fixup table entry */ 549 private void emitCallFixup(INVOCATION ROOT, Label retaddr, Label handler) { 550 // this '1f' and '1:' business is taking advantage of a GNU 551 // Assembly feature to avoid polluting the global name space with 552 // local labels 553 // these may need to be included in the previous instr to preserve 554 // ordering semantics, but for now this way they indent properly 555 emitDIRECTIVE( ROOT, !is_elf?".text 10":".section .flex.fixup"); 556 emitDIRECTIVE( ROOT, "\t.word "+retaddr+", "+handler+" @ (retaddr, handler)"); 557 emitDIRECTIVE( ROOT, !is_elf?".text 0":".section .flex.code"); 558 } 559 /** Finish up a CALL or NATIVECALL. */ 560 private void emitCallEpilogue(INVOCATION ROOT, boolean isNative, 561 Temp retval, HClass type, 562 CallState cs) { 563 // this will break if stackOffset > 255 (ie >63 args) 564 assert cs.stackOffset < 256 : "Update the spec file to handle large SP offsets"; 565 if (cs.stackOffset!=0) { // optimize for common case. 566 declare ( SP, HClass.Void ); 567 emit( ROOT, "add `d0, `s0, #" + cs.stackOffset, SP , SP ); 568 } 569 if (ROOT.getRetval()==null) { 570 // this is a void method. don't bother to emit move. 571 } else if (isNative && ROOT.getRetval().type()==Type.FLOAT) { 572 emitMoveFromNativeFloatRetVal(ROOT, retval); 573 } else if (isNative && ROOT.getRetval().type()==Type.DOUBLE) { 574 emitMoveFromNativeDoubleRetVal(ROOT, retval); 575 } else if (ROOT.getRetval().isDoubleWord()) { 576 // not certain an emitMOVE is legal with the l/h modifiers 577 declare(retval, type); 578 emit( ROOT, "mov `d0l, `s0", retval, r0 ); 579 emit( ROOT, "mov `d0h, `s0", retval, r1 ); 580 } else { 581 declare(retval, type); 582 emitMOVE( ROOT, "mov `d0, `s0", retval, r0 ); 583 } 584 } 585 // make a string "safe". This is made necessary by obfuscators. 586 private static String safe(String s) { 587 char[] ca = s.toCharArray(); 588 for (int i=0; i<ca.length; i++) 589 if (Character.isISOControl(ca[i])) ca[i]='#'; 590 return new String(ca); 591 } 592 593 // Mandated by CodeGen generic class: perform entry/exit 594 public Instr procFixup(HMethod hm, Instr instr, 595 int stackspace, Set usedRegisters) { 596 InstrFactory inf = instrFactory; // convenient abbreviation. 597 Label methodlabel = nameMap.label(hm); 598 // make list of callee-save registers we gotta save. 599 StringBuffer reglist = new StringBuffer(); 600 601 Temp[] usedRegArray = 602 (Temp[]) usedRegisters.toArray(new Temp[usedRegisters.size()]); 603 Collections.sort(Arrays.asList(usedRegArray), regComp); 604 int nregs=0; 605 for (int i=0; i<usedRegArray.length; i++) { 606 Temp rX = usedRegArray[i]; 607 assert regfile.isRegister(rX); 608 if (rX.equals(r0)||rX.equals(r1)||rX.equals(r2)||rX.equals(r3)) 609 continue; // caller save registers. 610 if (rX.equals(LR)||rX.equals(PC)||rX.equals(FP)||rX.equals(SP)|| 611 rX.equals(IP)) continue; // always saved. 612 reglist.append(rX.toString()); 613 reglist.append(", "); 614 nregs++; 615 } 616 // find method entry/exit stubs 617 Instr last=instr; 618 for (Instr il = instr; il!=null; il=il.getNext()) { 619 if (il instanceof InstrENTRY) { // entry stub. 620 Instr in1 = new InstrDIRECTIVE(inf, il, ".balign 4"); 621 Instr in2 = new InstrDIRECTIVE(inf, il, ".global " + 622 methodlabel.name); 623 Instr in2a= new InstrDIRECTIVE(inf, il, ".type " + 624 methodlabel.name+",#function"); 625 Instr in2b= new InstrDIRECTIVE(inf, il, ".set .fpoffset, "+ 626 (-4*(4+nregs))); 627 Instr in3 = new InstrLABEL(inf, il, methodlabel.name+":", 628 methodlabel); 629 Instr in4 = new Instr(inf, il, "mov ip, sp", null, null); 630 Instr in5 = new Instr(inf, il, 631 "stmfd sp!, {"+reglist+"fp,ip,lr,pc}", 632 null, null); 633 Instr in6 = new Instr(inf, il, "sub fp, ip, #4", null, null); 634 635 String assem; 636 if (harpoon.Backend.StrongARM. 637 Code.isValidConst(stackspace*4)) { 638 assem = "sub sp, sp, #"+(stackspace*4); 639 } else { 640 assem=""; 641 int op2 = stackspace *4; 642 while(op2 != 0) { 643 // FSK: trusting CSA's code from CodeGen here... 644 int eight = op2 & (0xFF << ((Util.ffs(op2)-1) & ~1)); 645 assem += "sub sp, sp, #"+eight; 646 op2 ^= eight; 647 if (op2!=0) assem += "\n"; 648 } 649 } 650 Instr in7 = new Instr(inf, il, assem, null, null); 651 in7.layout(il, il.getNext()); 652 in6.layout(il, in7); 653 in5.layout(il, in6); 654 in4.layout(il, in5); 655 in3.layout(il, in4); 656 in2b.layout(il,in3); 657 in2a.layout(il,in2b); 658 in2.layout(il, in2a); 659 in1.layout(il, in2); 660 if (il==instr) instr=in1; // fixup root if necessary. 661 if (stackspace==0) in7.remove(); // optimize 662 il.remove(); il=in1; 663 } 664 if (il instanceof InstrEXIT) { // exit stub 665 Instr in1 = new Instr(inf, il, 666 "ldmea fp, {"+reglist+"fp, sp, pc}", 667 null, null); 668 in1.layout(il.getPrev(), il); 669 il.remove(); il=in1; 670 } 671 last=il; 672 } 673 // add a size directive to the end of the function to let gdb 674 // know how long it is. 675 if (last!=null) { // best be safe. 676 Instr in1 = new InstrDIRECTIVE(inf, last, "\t.size " + 677 methodlabel.name + ", . - " + 678 methodlabel.name); 679 in1.layout(last, last.getNext()); 680 last=in1; 681 } 682 // stabs debugging information: 683 if (stabsDebugging && !hm.getDeclaringClass().isArray()) { 684 int lineno=-1; 685 for (Instr il = instr; il!=null; il=il.getNext()) 686 if (il.getLineNumber()!=lineno) { 687 lineno = il.getLineNumber(); 688 Instr in1 = new InstrDIRECTIVE(inf, il, // line number 689 "\t.stabd 68,0,"+lineno); 690 in1.layout(il.getPrev(), il); 691 if (il==instr) instr=in1; 692 } 693 Instr in1 = new InstrDIRECTIVE(inf, instr, // source path 694 "\t.stabs \""+ 695 hm.getDeclaringClass().getPackage() 696 .replace('.','/')+"/"+ 697 "\",100,0,0,"+methodlabel.name); 698 Instr in2 = new InstrDIRECTIVE(inf, instr, // source file name 699 "\t.stabs \""+ 700 safe(instr.getSourceFile())+ 701 "\",100,0,0,"+methodlabel.name); 702 Instr in3 = new InstrDIRECTIVE(inf, instr, // define void type 703 "\t.stabs \"void:t19=19\",128,0,0,0" 704 ); 705 Instr in4 = new InstrDIRECTIVE(inf, instr, // mark as function 706 "\t.stabs \""+ 707 methodlabel.name.substring(1)+":F19" 708 +"\",36,0,"+(nregs*4)+","+ 709 methodlabel.name); 710 in1.layout(instr.getPrev(), instr); 711 in2.layout(in1, instr); 712 in3.layout(in2, instr); 713 instr = in1; 714 in4.layout(last, last.getNext()); 715 last = in4; 716 } 717 return instr; 718 } 719 720 // now define our little InstrENTRY and InstrEXIT sub-types. 721 private class InstrENTRY extends Instr { 722 public InstrENTRY(InstrFactory inf, HCodeElement src) { 723 // defines SP, FP, and PC providing reaching defs for 724 // InstrEXIT uses. 725 super(inf, src, "@ --method entry point--", 726 new Temp[] { SP, FP, PC }, null); 727 } 728 } 729 private class InstrEXIT extends Instr { 730 public InstrEXIT(InstrFactory inf, HCodeElement hce) { 731 // uses SP, FP, and PC making them live in whole 732 // procedure (so register allocator doesn't stomp 733 // on them!) 734 super(inf, hce, "@ --method exit point--", null, 735 new Temp[]{ SP, FP, PC }, false, null); 736 } 737 } 738 739 private static boolean __CommExp__isCommutative(int op) { 740 switch(op) { 741 case harpoon.IR.Tree.Bop.CMPGT: 742 case harpoon.IR.Tree.Bop.CMPGE: 743 case harpoon.IR.Tree.Bop.CMPLE: 744 case harpoon.IR.Tree.Bop.CMPLT: return true; 745 default: return harpoon.IR.Tree.Bop.isCommutative(op); 746 } 747 } 748 private static int __CommExp__swapCmpOp(int op) { 749 switch(op) { 750 case harpoon.IR.Tree.Bop.CMPGT:return harpoon.IR.Tree.Bop.CMPLT; 751 case harpoon.IR.Tree.Bop.CMPGE:return harpoon.IR.Tree.Bop.CMPLE; 752 case harpoon.IR.Tree.Bop.CMPLE:return harpoon.IR.Tree.Bop.CMPGE; 753 case harpoon.IR.Tree.Bop.CMPLT:return harpoon.IR.Tree.Bop.CMPGT; 754 default: return op; 755 } 756 } 757 758 759 /** Generates assembly code from a <code>harpoon.IR.Tree.Code</code>. 760 <BR> <B>modifies:</B> <code>this</code> 761 <BR> <B>effects:</B> 762 Scans <code>tree</code> to find a tiling of 763 Instruction Patterns, calling auxillary methods 764 and data structures as defined in the .spec file. 765 Generates an associated <code>Derivation</code> 766 object as the second element of the returned 767 <code>List</code>. 768 @param tree Set of abstract <code>Tree</code> instructions 769 that form the body of the procedure being compiled. 770 */ 771 public final java.util.List cgg_genCode(final harpoon.IR.Tree.Code code, final harpoon.IR.Assem.InstrFactory inf) { 772 _methodPrologue_(inf); 773 774 // *** METHOD PROLOGUE *** 775 this.instrFactory = inf; // XXX this should probably move to superclass 776 777 final class CggVisitor extends harpoon.IR.Tree.TreeVisitor { 778 harpoon.Temp.Temp munchExp(harpoon.IR.Tree.Exp expArg) { 779 boolean _matched_ = false; 780 clearDecl(); // reset temp type mappings 781 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),k)),j)) */ 782 if (true 783 // check expression type 784 && expArg instanceof harpoon.IR.Tree.MEM 785 // check operand types 786 && ( 787 expArg.type() == Type.FLOAT || 788 expArg.type() == Type.POINTER || 789 ( expArg.type() == Type.INT && ! 790 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 791 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 792 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 793 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 794 false) : ( 795 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 796 false) ) ) || 797 false ) 798 // end check operand types 799 // check child 800 // check expression type 801 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 802 // check opcode 803 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 804 // check operand types 805 && ( 806 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 807 false ) 808 // end check operand types 809 // check left child 810 // check expression type 811 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.UNOP 812 // check opcode 813 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).op == harpoon.IR.Tree.Uop.NEG 814 // check operand types 815 && ( 816 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.DOUBLE || 817 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.FLOAT || 818 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.LONG || 819 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.POINTER || 820 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.INT && ! 821 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 822 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).isSmall())) || 823 false ) 824 // end check operand types 825 // check child 826 // check expression type 827 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.BINOP 828 // check operand types 829 && ( 830 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.DOUBLE || 831 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.FLOAT || 832 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.LONG || 833 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.POINTER || 834 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.INT && ! 835 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 836 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).isSmall())) || 837 false ) 838 // end check operand types 839 // check left child 840 // check expression type 841 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft() instanceof harpoon.IR.Tree.CONST 842 // check operand types 843 && ( 844 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft().type() == Type.POINTER || 845 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft().type() == Type.INT && ! 846 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 847 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft()).isSmall())) || 848 false ) 849 // end check operand types 850 // check right child 851 // no check needed for ExpId children 852 // check right child 853 // no check needed for ExpId children 854 ){ 855 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).op; 856 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft()).value; 857 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 858 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 859 860 if (_matched_) { // action code! degree: 5 861 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight()); 862 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 863 864 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 865 clearDecl(); 866 declare(i, code.getTreeDerivation(), ROOT); 867 868 String suffix=""; 869 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 870 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 871 emit(new InstrMEM(instrFactory, ROOT, 872 "ldr"+suffix+" `d0, [`s0, -`s1, " + 873 shiftOp2Str(shiftop)+" #"+c+"]", 874 new Temp[]{ i }, new Temp[]{ j, k })); 875 return i; 876 } 877 } 878 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,j,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),k)))) */ 879 if (true 880 // check expression type 881 && expArg instanceof harpoon.IR.Tree.MEM 882 // check operand types 883 && ( 884 expArg.type() == Type.FLOAT || 885 expArg.type() == Type.POINTER || 886 ( expArg.type() == Type.INT && ! 887 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 888 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 889 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 890 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 891 false) : ( 892 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 893 false) ) ) || 894 false ) 895 // end check operand types 896 // check child 897 // check expression type 898 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 899 // check opcode 900 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 901 // check operand types 902 && ( 903 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 904 false ) 905 // end check operand types 906 // check left child 907 // no check needed for ExpId children 908 // check right child 909 // check expression type 910 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.UNOP 911 // check opcode 912 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).op == harpoon.IR.Tree.Uop.NEG 913 // check operand types 914 && ( 915 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.DOUBLE || 916 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.FLOAT || 917 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.LONG || 918 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.POINTER || 919 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.INT && ! 920 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 921 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).isSmall())) || 922 false ) 923 // end check operand types 924 // check child 925 // check expression type 926 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.BINOP 927 // check operand types 928 && ( 929 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.DOUBLE || 930 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.FLOAT || 931 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.LONG || 932 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.POINTER || 933 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.INT && ! 934 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 935 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).isSmall())) || 936 false ) 937 // end check operand types 938 // check left child 939 // check expression type 940 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft() instanceof harpoon.IR.Tree.CONST 941 // check operand types 942 && ( 943 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft().type() == Type.POINTER || 944 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft().type() == Type.INT && ! 945 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 946 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft()).isSmall())) || 947 false ) 948 // end check operand types 949 // check right child 950 // no check needed for ExpId children 951 ){ 952 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).op; 953 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft()).value; 954 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 955 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 956 957 if (_matched_) { // action code! degree: 5 958 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 959 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight()); 960 961 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 962 clearDecl(); 963 declare(i, code.getTreeDerivation(), ROOT); 964 965 String suffix=""; 966 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 967 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 968 emit(new InstrMEM(instrFactory, ROOT, 969 "ldr"+suffix+" `d0, [`s0, -`s1, " + 970 shiftOp2Str(shiftop)+" #"+c+"]", 971 new Temp[]{ i }, new Temp[]{ j, k })); 972 return i; 973 } 974 } 975 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,k,CONST<i,p>(c))),j)) */ 976 if (true 977 // check expression type 978 && expArg instanceof harpoon.IR.Tree.MEM 979 // check operand types 980 && ( 981 expArg.type() == Type.FLOAT || 982 expArg.type() == Type.POINTER || 983 ( expArg.type() == Type.INT && ! 984 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 985 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 986 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 987 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 988 false) : ( 989 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 990 false) ) ) || 991 false ) 992 // end check operand types 993 // check child 994 // check expression type 995 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 996 // check opcode 997 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 998 // check operand types 999 && ( 1000 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 1001 false ) 1002 // end check operand types 1003 // check left child 1004 // check expression type 1005 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.UNOP 1006 // check opcode 1007 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).op == harpoon.IR.Tree.Uop.NEG 1008 // check operand types 1009 && ( 1010 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.DOUBLE || 1011 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.FLOAT || 1012 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.LONG || 1013 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.POINTER || 1014 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.INT && ! 1015 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1016 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).isSmall())) || 1017 false ) 1018 // end check operand types 1019 // check child 1020 // check expression type 1021 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.BINOP 1022 // check operand types 1023 && ( 1024 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.DOUBLE || 1025 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.FLOAT || 1026 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.LONG || 1027 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.POINTER || 1028 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand().type() == Type.INT && ! 1029 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 1030 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).isSmall())) || 1031 false ) 1032 // end check operand types 1033 // check left child 1034 // no check needed for ExpId children 1035 // check right child 1036 // check expression type 1037 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight() instanceof harpoon.IR.Tree.CONST 1038 // check operand types 1039 && ( 1040 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight().type() == Type.POINTER || 1041 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight().type() == Type.INT && ! 1042 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1043 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight()).isSmall())) || 1044 false ) 1045 // end check operand types 1046 // check right child 1047 // no check needed for ExpId children 1048 ){ 1049 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).op; 1050 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getRight()).value; 1051 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 1052 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1053 1054 if (_matched_) { // action code! degree: 5 1055 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()).getLeft()); 1056 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 1057 1058 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1059 clearDecl(); 1060 declare(i, code.getTreeDerivation(), ROOT); 1061 1062 String suffix=""; 1063 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 1064 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 1065 emit(new InstrMEM(instrFactory, ROOT, 1066 "ldr"+suffix+" `d0, [`s0, -`s1, " + 1067 shiftOp2Str(shiftop)+" #"+c+"]", 1068 new Temp[]{ i }, new Temp[]{ j, k })); 1069 return i; 1070 } 1071 } 1072 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,j,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,k,CONST<i,p>(c))))) */ 1073 if (true 1074 // check expression type 1075 && expArg instanceof harpoon.IR.Tree.MEM 1076 // check operand types 1077 && ( 1078 expArg.type() == Type.FLOAT || 1079 expArg.type() == Type.POINTER || 1080 ( expArg.type() == Type.INT && ! 1081 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1082 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1083 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 1084 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 1085 false) : ( 1086 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 1087 false) ) ) || 1088 false ) 1089 // end check operand types 1090 // check child 1091 // check expression type 1092 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 1093 // check opcode 1094 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 1095 // check operand types 1096 && ( 1097 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 1098 false ) 1099 // end check operand types 1100 // check left child 1101 // no check needed for ExpId children 1102 // check right child 1103 // check expression type 1104 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.UNOP 1105 // check opcode 1106 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).op == harpoon.IR.Tree.Uop.NEG 1107 // check operand types 1108 && ( 1109 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.DOUBLE || 1110 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.FLOAT || 1111 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.LONG || 1112 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.POINTER || 1113 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.INT && ! 1114 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1115 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).isSmall())) || 1116 false ) 1117 // end check operand types 1118 // check child 1119 // check expression type 1120 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.BINOP 1121 // check operand types 1122 && ( 1123 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.DOUBLE || 1124 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.FLOAT || 1125 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.LONG || 1126 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.POINTER || 1127 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand().type() == Type.INT && ! 1128 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 1129 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).isSmall())) || 1130 false ) 1131 // end check operand types 1132 // check left child 1133 // no check needed for ExpId children 1134 // check right child 1135 // check expression type 1136 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight() instanceof harpoon.IR.Tree.CONST 1137 // check operand types 1138 && ( 1139 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight().type() == Type.POINTER || 1140 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight().type() == Type.INT && ! 1141 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1142 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight()).isSmall())) || 1143 false ) 1144 // end check operand types 1145 ){ 1146 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).op; 1147 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getRight()).value; 1148 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 1149 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1150 1151 if (_matched_) { // action code! degree: 5 1152 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 1153 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()).getLeft()); 1154 1155 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1156 clearDecl(); 1157 declare(i, code.getTreeDerivation(), ROOT); 1158 1159 String suffix=""; 1160 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 1161 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 1162 emit(new InstrMEM(instrFactory, ROOT, 1163 "ldr"+suffix+" `d0, [`s0, -`s1, " + 1164 shiftOp2Str(shiftop)+" #"+c+"]", 1165 new Temp[]{ i }, new Temp[]{ j, k })); 1166 return i; 1167 } 1168 } 1169 /* BINOP<i,p>(ADD,j,UNOP<i,p>(NEG,BINOP<i,p>(shiftop,CONST<i,p>(c),k))) */ 1170 if (true 1171 // check expression type 1172 && expArg instanceof harpoon.IR.Tree.BINOP 1173 // check opcode 1174 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1175 // check operand types 1176 && ( 1177 expArg.type() == Type.POINTER || 1178 ( expArg.type() == Type.INT && ! 1179 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1180 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1181 false ) 1182 // end check operand types 1183 // check left child 1184 // no check needed for ExpId children 1185 // check right child 1186 // check expression type 1187 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.UNOP 1188 // check opcode 1189 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Uop.NEG 1190 // check operand types 1191 && ( 1192 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1193 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1194 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1195 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1196 false ) 1197 // end check operand types 1198 // check child 1199 // check expression type 1200 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand() instanceof harpoon.IR.Tree.BINOP 1201 // check operand types 1202 && ( 1203 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand().type() == Type.POINTER || 1204 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand().type() == Type.INT && ! 1205 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 1206 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).isSmall())) || 1207 false ) 1208 // end check operand types 1209 // check left child 1210 // check expression type 1211 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft() instanceof harpoon.IR.Tree.CONST 1212 // check operand types 1213 && ( 1214 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft().type() == Type.POINTER || 1215 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft().type() == Type.INT && ! 1216 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1217 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft()).isSmall())) || 1218 false ) 1219 // end check operand types 1220 // check right child 1221 // no check needed for ExpId children 1222 ){ 1223 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).op; 1224 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft()).value; 1225 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1226 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 1227 1228 if (_matched_) { // action code! degree: 4 1229 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 1230 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight()); 1231 1232 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1233 clearDecl(); 1234 declare(i, code.getTreeDerivation(), ROOT); 1235 1236 emit( ROOT, "sub `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k); 1237 return i; 1238 } 1239 } 1240 /* BINOP<i,p>(ADD,j,UNOP<i,p>(NEG,BINOP<i,p>(shiftop,k,CONST<i,p>(c)))) */ 1241 if (true 1242 // check expression type 1243 && expArg instanceof harpoon.IR.Tree.BINOP 1244 // check opcode 1245 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1246 // check operand types 1247 && ( 1248 expArg.type() == Type.POINTER || 1249 ( expArg.type() == Type.INT && ! 1250 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1251 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1252 false ) 1253 // end check operand types 1254 // check left child 1255 // no check needed for ExpId children 1256 // check right child 1257 // check expression type 1258 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.UNOP 1259 // check opcode 1260 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Uop.NEG 1261 // check operand types 1262 && ( 1263 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1264 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1265 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1266 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1267 false ) 1268 // end check operand types 1269 // check child 1270 // check expression type 1271 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand() instanceof harpoon.IR.Tree.BINOP 1272 // check operand types 1273 && ( 1274 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand().type() == Type.POINTER || 1275 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand().type() == Type.INT && ! 1276 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 1277 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).isSmall())) || 1278 false ) 1279 // end check operand types 1280 // check left child 1281 // no check needed for ExpId children 1282 // check right child 1283 // check expression type 1284 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight() instanceof harpoon.IR.Tree.CONST 1285 // check operand types 1286 && ( 1287 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight().type() == Type.POINTER || 1288 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight().type() == Type.INT && ! 1289 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1290 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight()).isSmall())) || 1291 false ) 1292 // end check operand types 1293 ){ 1294 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).op; 1295 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getRight()).value; 1296 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1297 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1298 1299 if (_matched_) { // action code! degree: 4 1300 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 1301 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()).getLeft()); 1302 1303 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1304 clearDecl(); 1305 declare(i, code.getTreeDerivation(), ROOT); 1306 1307 emit( ROOT, "sub `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k); 1308 return i; 1309 } 1310 } 1311 /* BINOP<i,p>(ADD,UNOP<i,p>(NEG,j),BINOP<i,p>(shiftop,CONST<i,p>(c),k)) */ 1312 if (true 1313 // check expression type 1314 && expArg instanceof harpoon.IR.Tree.BINOP 1315 // check opcode 1316 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1317 // check operand types 1318 && ( 1319 expArg.type() == Type.POINTER || 1320 ( expArg.type() == Type.INT && ! 1321 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1322 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1323 false ) 1324 // end check operand types 1325 // check left child 1326 // check expression type 1327 && ((harpoon.IR.Tree.BINOP)expArg).getLeft() instanceof harpoon.IR.Tree.UNOP 1328 // check opcode 1329 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getLeft()).op == harpoon.IR.Tree.Uop.NEG 1330 // check operand types 1331 && ( 1332 ((harpoon.IR.Tree.BINOP)expArg).getLeft().type() == Type.POINTER || 1333 ( ((harpoon.IR.Tree.BINOP)expArg).getLeft().type() == Type.INT && ! 1334 (((harpoon.IR.Tree.BINOP)expArg).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1335 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getLeft()).isSmall())) || 1336 false ) 1337 // end check operand types 1338 // check child 1339 // no check needed for ExpId children 1340 // check right child 1341 // check expression type 1342 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 1343 // check operand types 1344 && ( 1345 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1346 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1347 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1348 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1349 false ) 1350 // end check operand types 1351 // check left child 1352 // check expression type 1353 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 1354 // check operand types 1355 && ( 1356 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.POINTER || 1357 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.INT && ! 1358 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1359 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).isSmall())) || 1360 false ) 1361 // end check operand types 1362 // check right child 1363 // no check needed for ExpId children 1364 ){ 1365 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 1366 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).value; 1367 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1368 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 1369 1370 if (_matched_) { // action code! degree: 4 1371 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getLeft()).getOperand()); 1372 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()); 1373 1374 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1375 clearDecl(); 1376 declare(i, code.getTreeDerivation(), ROOT); 1377 1378 emit( ROOT, "rsb `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k); 1379 return i; 1380 } 1381 } 1382 /* BINOP<i,p>(ADD,UNOP<i,p>(NEG,j),BINOP<i,p>(shiftop,k,CONST<i,p>(c))) */ 1383 if (true 1384 // check expression type 1385 && expArg instanceof harpoon.IR.Tree.BINOP 1386 // check opcode 1387 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1388 // check operand types 1389 && ( 1390 expArg.type() == Type.POINTER || 1391 ( expArg.type() == Type.INT && ! 1392 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1393 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1394 false ) 1395 // end check operand types 1396 // check left child 1397 // check expression type 1398 && ((harpoon.IR.Tree.BINOP)expArg).getLeft() instanceof harpoon.IR.Tree.UNOP 1399 // check opcode 1400 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getLeft()).op == harpoon.IR.Tree.Uop.NEG 1401 // check operand types 1402 && ( 1403 ((harpoon.IR.Tree.BINOP)expArg).getLeft().type() == Type.POINTER || 1404 ( ((harpoon.IR.Tree.BINOP)expArg).getLeft().type() == Type.INT && ! 1405 (((harpoon.IR.Tree.BINOP)expArg).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1406 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getLeft()).isSmall())) || 1407 false ) 1408 // end check operand types 1409 // check child 1410 // no check needed for ExpId children 1411 // check right child 1412 // check expression type 1413 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 1414 // check operand types 1415 && ( 1416 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1417 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1418 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1419 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1420 false ) 1421 // end check operand types 1422 // check left child 1423 // no check needed for ExpId children 1424 // check right child 1425 // check expression type 1426 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 1427 // check operand types 1428 && ( 1429 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.POINTER || 1430 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.INT && ! 1431 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1432 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).isSmall())) || 1433 false ) 1434 // end check operand types 1435 ){ 1436 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 1437 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).value; 1438 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1439 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1440 1441 if (_matched_) { // action code! degree: 4 1442 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getLeft()).getOperand()); 1443 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()); 1444 1445 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1446 clearDecl(); 1447 declare(i, code.getTreeDerivation(), ROOT); 1448 1449 emit( ROOT, "rsb `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k); 1450 return i; 1451 } 1452 } 1453 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),k),j)) */ 1454 if (true 1455 // check expression type 1456 && expArg instanceof harpoon.IR.Tree.MEM 1457 // check operand types 1458 && ( 1459 expArg.type() == Type.FLOAT || 1460 expArg.type() == Type.POINTER || 1461 ( expArg.type() == Type.INT && ! 1462 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1463 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1464 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 1465 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 1466 false) : ( 1467 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 1468 false) ) ) || 1469 false ) 1470 // end check operand types 1471 // check child 1472 // check expression type 1473 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 1474 // check opcode 1475 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 1476 // check operand types 1477 && ( 1478 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 1479 false ) 1480 // end check operand types 1481 // check left child 1482 // check expression type 1483 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.BINOP 1484 // check operand types 1485 && ( 1486 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.DOUBLE || 1487 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.FLOAT || 1488 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.LONG || 1489 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.POINTER || 1490 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.INT && ! 1491 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1492 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).isSmall())) || 1493 false ) 1494 // end check operand types 1495 // check left child 1496 // check expression type 1497 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft() instanceof harpoon.IR.Tree.CONST 1498 // check operand types 1499 && ( 1500 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft().type() == Type.POINTER || 1501 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft().type() == Type.INT && ! 1502 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1503 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft()).isSmall())) || 1504 false ) 1505 // end check operand types 1506 // check right child 1507 // no check needed for ExpId children 1508 // check right child 1509 // no check needed for ExpId children 1510 ){ 1511 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).op; 1512 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft()).value; 1513 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 1514 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 1515 1516 if (_matched_) { // action code! degree: 4 1517 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight()); 1518 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 1519 1520 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1521 clearDecl(); 1522 declare(i, code.getTreeDerivation(), ROOT); 1523 1524 String suffix=""; 1525 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 1526 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 1527 emit(new InstrMEM(instrFactory, ROOT, 1528 "ldr"+suffix+" `d0, [`s0, `s1, " + 1529 shiftOp2Str(shiftop)+" #"+c+"]", 1530 new Temp[]{ i }, new Temp[]{ j, k })); 1531 return i; 1532 } 1533 } 1534 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,j,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),k))) */ 1535 if (true 1536 // check expression type 1537 && expArg instanceof harpoon.IR.Tree.MEM 1538 // check operand types 1539 && ( 1540 expArg.type() == Type.FLOAT || 1541 expArg.type() == Type.POINTER || 1542 ( expArg.type() == Type.INT && ! 1543 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1544 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1545 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 1546 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 1547 false) : ( 1548 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 1549 false) ) ) || 1550 false ) 1551 // end check operand types 1552 // check child 1553 // check expression type 1554 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 1555 // check opcode 1556 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 1557 // check operand types 1558 && ( 1559 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 1560 false ) 1561 // end check operand types 1562 // check left child 1563 // no check needed for ExpId children 1564 // check right child 1565 // check expression type 1566 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.BINOP 1567 // check operand types 1568 && ( 1569 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.DOUBLE || 1570 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.FLOAT || 1571 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.LONG || 1572 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.POINTER || 1573 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.INT && ! 1574 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1575 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).isSmall())) || 1576 false ) 1577 // end check operand types 1578 // check left child 1579 // check expression type 1580 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 1581 // check operand types 1582 && ( 1583 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft().type() == Type.POINTER || 1584 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft().type() == Type.INT && ! 1585 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1586 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft()).isSmall())) || 1587 false ) 1588 // end check operand types 1589 // check right child 1590 // no check needed for ExpId children 1591 ){ 1592 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).op; 1593 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft()).value; 1594 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 1595 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 1596 1597 if (_matched_) { // action code! degree: 4 1598 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 1599 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight()); 1600 1601 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1602 clearDecl(); 1603 declare(i, code.getTreeDerivation(), ROOT); 1604 1605 String suffix=""; 1606 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 1607 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 1608 emit(new InstrMEM(instrFactory, ROOT, 1609 "ldr"+suffix+" `d0, [`s0, `s1, " + 1610 shiftOp2Str(shiftop)+" #"+c+"]", 1611 new Temp[]{ i }, new Temp[]{ j, k })); 1612 return i; 1613 } 1614 } 1615 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,BINOP<i,l,f,d,p>(shiftop,k,CONST<i,p>(c)),j)) */ 1616 if (true 1617 // check expression type 1618 && expArg instanceof harpoon.IR.Tree.MEM 1619 // check operand types 1620 && ( 1621 expArg.type() == Type.FLOAT || 1622 expArg.type() == Type.POINTER || 1623 ( expArg.type() == Type.INT && ! 1624 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1625 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1626 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 1627 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 1628 false) : ( 1629 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 1630 false) ) ) || 1631 false ) 1632 // end check operand types 1633 // check child 1634 // check expression type 1635 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 1636 // check opcode 1637 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 1638 // check operand types 1639 && ( 1640 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 1641 false ) 1642 // end check operand types 1643 // check left child 1644 // check expression type 1645 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.BINOP 1646 // check operand types 1647 && ( 1648 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.DOUBLE || 1649 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.FLOAT || 1650 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.LONG || 1651 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.POINTER || 1652 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.INT && ! 1653 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1654 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).isSmall())) || 1655 false ) 1656 // end check operand types 1657 // check left child 1658 // no check needed for ExpId children 1659 // check right child 1660 // check expression type 1661 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight() instanceof harpoon.IR.Tree.CONST 1662 // check operand types 1663 && ( 1664 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight().type() == Type.POINTER || 1665 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight().type() == Type.INT && ! 1666 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1667 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight()).isSmall())) || 1668 false ) 1669 // end check operand types 1670 // check right child 1671 // no check needed for ExpId children 1672 ){ 1673 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).op; 1674 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getRight()).value; 1675 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 1676 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1677 1678 if (_matched_) { // action code! degree: 4 1679 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getLeft()); 1680 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 1681 1682 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1683 clearDecl(); 1684 declare(i, code.getTreeDerivation(), ROOT); 1685 1686 String suffix=""; 1687 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 1688 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 1689 emit(new InstrMEM(instrFactory, ROOT, 1690 "ldr"+suffix+" `d0, [`s0, `s1, " + 1691 shiftOp2Str(shiftop)+" #"+c+"]", 1692 new Temp[]{ i }, new Temp[]{ j, k })); 1693 return i; 1694 } 1695 } 1696 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,j,BINOP<i,l,f,d,p>(shiftop,k,CONST<i,p>(c)))) */ 1697 if (true 1698 // check expression type 1699 && expArg instanceof harpoon.IR.Tree.MEM 1700 // check operand types 1701 && ( 1702 expArg.type() == Type.FLOAT || 1703 expArg.type() == Type.POINTER || 1704 ( expArg.type() == Type.INT && ! 1705 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1706 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1707 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 1708 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 1709 false) : ( 1710 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 1711 false) ) ) || 1712 false ) 1713 // end check operand types 1714 // check child 1715 // check expression type 1716 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 1717 // check opcode 1718 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 1719 // check operand types 1720 && ( 1721 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 1722 false ) 1723 // end check operand types 1724 // check left child 1725 // no check needed for ExpId children 1726 // check right child 1727 // check expression type 1728 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.BINOP 1729 // check operand types 1730 && ( 1731 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.DOUBLE || 1732 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.FLOAT || 1733 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.LONG || 1734 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.POINTER || 1735 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.INT && ! 1736 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1737 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).isSmall())) || 1738 false ) 1739 // end check operand types 1740 // check left child 1741 // no check needed for ExpId children 1742 // check right child 1743 // check expression type 1744 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 1745 // check operand types 1746 && ( 1747 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight().type() == Type.POINTER || 1748 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight().type() == Type.INT && ! 1749 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1750 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight()).isSmall())) || 1751 false ) 1752 // end check operand types 1753 ){ 1754 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).op; 1755 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getRight()).value; 1756 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 1757 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1758 1759 if (_matched_) { // action code! degree: 4 1760 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 1761 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getLeft()); 1762 1763 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1764 clearDecl(); 1765 declare(i, code.getTreeDerivation(), ROOT); 1766 1767 String suffix=""; 1768 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 1769 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 1770 emit(new InstrMEM(instrFactory, ROOT, 1771 "ldr"+suffix+" `d0, [`s0, `s1, " + 1772 shiftOp2Str(shiftop)+" #"+c+"]", 1773 new Temp[]{ i }, new Temp[]{ j, k })); 1774 return i; 1775 } 1776 } 1777 /* BINOP<i,p>(ADD,j,BINOP<i,p>(shiftop,CONST<i,p>(c),k)) */ 1778 if (true 1779 // check expression type 1780 && expArg instanceof harpoon.IR.Tree.BINOP 1781 // check opcode 1782 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1783 // check operand types 1784 && ( 1785 expArg.type() == Type.POINTER || 1786 ( expArg.type() == Type.INT && ! 1787 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1788 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1789 false ) 1790 // end check operand types 1791 // check left child 1792 // no check needed for ExpId children 1793 // check right child 1794 // check expression type 1795 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 1796 // check operand types 1797 && ( 1798 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1799 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1800 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1801 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1802 false ) 1803 // end check operand types 1804 // check left child 1805 // check expression type 1806 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 1807 // check operand types 1808 && ( 1809 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.POINTER || 1810 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.INT && ! 1811 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1812 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).isSmall())) || 1813 false ) 1814 // end check operand types 1815 // check right child 1816 // no check needed for ExpId children 1817 ){ 1818 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 1819 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).value; 1820 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1821 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 1822 1823 if (_matched_) { // action code! degree: 3 1824 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 1825 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()); 1826 1827 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1828 clearDecl(); 1829 declare(i, code.getTreeDerivation(), ROOT); 1830 1831 emit( ROOT, "add `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k); 1832 return i; 1833 } 1834 } 1835 /* BINOP<i,p>(ADD,j,BINOP<i,p>(shiftop,k,CONST<i,p>(c))) */ 1836 if (true 1837 // check expression type 1838 && expArg instanceof harpoon.IR.Tree.BINOP 1839 // check opcode 1840 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1841 // check operand types 1842 && ( 1843 expArg.type() == Type.POINTER || 1844 ( expArg.type() == Type.INT && ! 1845 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1846 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1847 false ) 1848 // end check operand types 1849 // check left child 1850 // no check needed for ExpId children 1851 // check right child 1852 // check expression type 1853 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 1854 // check operand types 1855 && ( 1856 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1857 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1858 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1859 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1860 false ) 1861 // end check operand types 1862 // check left child 1863 // no check needed for ExpId children 1864 // check right child 1865 // check expression type 1866 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 1867 // check operand types 1868 && ( 1869 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.POINTER || 1870 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.INT && ! 1871 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1872 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).isSmall())) || 1873 false ) 1874 // end check operand types 1875 ){ 1876 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 1877 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).value; 1878 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1879 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 1880 1881 if (_matched_) { // action code! degree: 3 1882 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 1883 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()); 1884 1885 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1886 clearDecl(); 1887 declare(i, code.getTreeDerivation(), ROOT); 1888 1889 emit( ROOT, "add `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k); 1890 return i; 1891 } 1892 } 1893 /* BINOP<i,p>(ADD,UNOP<i,p>(NEG,j),CONST<i,p>(c)) */ 1894 if (true 1895 // check expression type 1896 && expArg instanceof harpoon.IR.Tree.BINOP 1897 // check opcode 1898 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 1899 // check operand types 1900 && ( 1901 expArg.type() == Type.POINTER || 1902 ( expArg.type() == Type.INT && ! 1903 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1904 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1905 false ) 1906 // end check operand types 1907 // check left child 1908 // check expression type 1909 && ((harpoon.IR.Tree.BINOP)expArg).getLeft() instanceof harpoon.IR.Tree.UNOP 1910 // check opcode 1911 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getLeft()).op == harpoon.IR.Tree.Uop.NEG 1912 // check operand types 1913 && ( 1914 ((harpoon.IR.Tree.BINOP)expArg).getLeft().type() == Type.POINTER || 1915 ( ((harpoon.IR.Tree.BINOP)expArg).getLeft().type() == Type.INT && ! 1916 (((harpoon.IR.Tree.BINOP)expArg).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1917 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getLeft()).isSmall())) || 1918 false ) 1919 // end check operand types 1920 // check child 1921 // no check needed for ExpId children 1922 // check right child 1923 // check expression type 1924 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 1925 // check operand types 1926 && ( 1927 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1928 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1929 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1930 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1931 false ) 1932 // end check operand types 1933 ){ 1934 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 1935 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1936 _matched_ = true&& ( isOpd2Imm(c) ); 1937 1938 if (_matched_) { // action code! degree: 3 1939 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getLeft()).getOperand()); 1940 1941 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 1942 clearDecl(); 1943 declare(i, code.getTreeDerivation(), ROOT); 1944 1945 emit( ROOT, "rsb `d0, `s0, #"+c, i, j); 1946 return i; 1947 } 1948 } 1949 /* BINOP<i,p>(AND,j,BINOP<i,p>(shiftop,CONST<i,p>(c),k)) */ 1950 if (true 1951 // check expression type 1952 && expArg instanceof harpoon.IR.Tree.BINOP 1953 // check opcode 1954 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.AND 1955 // check operand types 1956 && ( 1957 expArg.type() == Type.POINTER || 1958 ( expArg.type() == Type.INT && ! 1959 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 1960 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 1961 false ) 1962 // end check operand types 1963 // check left child 1964 // no check needed for ExpId children 1965 // check right child 1966 // check expression type 1967 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 1968 // check operand types 1969 && ( 1970 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 1971 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 1972 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 1973 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 1974 false ) 1975 // end check operand types 1976 // check left child 1977 // check expression type 1978 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 1979 // check operand types 1980 && ( 1981 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.POINTER || 1982 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.INT && ! 1983 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 1984 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).isSmall())) || 1985 false ) 1986 // end check operand types 1987 // check right child 1988 // no check needed for ExpId children 1989 ){ 1990 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 1991 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).value; 1992 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 1993 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 1994 1995 if (_matched_) { // action code! degree: 3 1996 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 1997 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()); 1998 1999 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2000 clearDecl(); 2001 declare(i, code.getTreeDerivation(), ROOT); 2002 2003 emit( ROOT, "and `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k ); 2004 return i; 2005 } 2006 } 2007 /* BINOP<i,p>(AND,j,BINOP<i,p>(shiftop,k,CONST<i,p>(c))) */ 2008 if (true 2009 // check expression type 2010 && expArg instanceof harpoon.IR.Tree.BINOP 2011 // check opcode 2012 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.AND 2013 // check operand types 2014 && ( 2015 expArg.type() == Type.POINTER || 2016 ( expArg.type() == Type.INT && ! 2017 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2018 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2019 false ) 2020 // end check operand types 2021 // check left child 2022 // no check needed for ExpId children 2023 // check right child 2024 // check expression type 2025 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 2026 // check operand types 2027 && ( 2028 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2029 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2030 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2031 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2032 false ) 2033 // end check operand types 2034 // check left child 2035 // no check needed for ExpId children 2036 // check right child 2037 // check expression type 2038 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 2039 // check operand types 2040 && ( 2041 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.POINTER || 2042 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.INT && ! 2043 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2044 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).isSmall())) || 2045 false ) 2046 // end check operand types 2047 ){ 2048 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 2049 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).value; 2050 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2051 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 2052 2053 if (_matched_) { // action code! degree: 3 2054 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2055 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()); 2056 2057 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2058 clearDecl(); 2059 declare(i, code.getTreeDerivation(), ROOT); 2060 2061 emit( ROOT, "and `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k ); 2062 return i; 2063 } 2064 } 2065 /* BINOP<i,p>(OR,j,BINOP<i,p>(shiftop,CONST<i,p>(c),k)) */ 2066 if (true 2067 // check expression type 2068 && expArg instanceof harpoon.IR.Tree.BINOP 2069 // check opcode 2070 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.OR 2071 // check operand types 2072 && ( 2073 expArg.type() == Type.POINTER || 2074 ( expArg.type() == Type.INT && ! 2075 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2076 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2077 false ) 2078 // end check operand types 2079 // check left child 2080 // no check needed for ExpId children 2081 // check right child 2082 // check expression type 2083 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 2084 // check operand types 2085 && ( 2086 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2087 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2088 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2089 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2090 false ) 2091 // end check operand types 2092 // check left child 2093 // check expression type 2094 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 2095 // check operand types 2096 && ( 2097 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.POINTER || 2098 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.INT && ! 2099 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 2100 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).isSmall())) || 2101 false ) 2102 // end check operand types 2103 // check right child 2104 // no check needed for ExpId children 2105 ){ 2106 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 2107 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).value; 2108 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2109 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 2110 2111 if (_matched_) { // action code! degree: 3 2112 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2113 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()); 2114 2115 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2116 clearDecl(); 2117 declare(i, code.getTreeDerivation(), ROOT); 2118 2119 emit( ROOT, "orr `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k ); 2120 return i; 2121 } 2122 } 2123 /* BINOP<i,p>(OR,j,BINOP<i,p>(shiftop,k,CONST<i,p>(c))) */ 2124 if (true 2125 // check expression type 2126 && expArg instanceof harpoon.IR.Tree.BINOP 2127 // check opcode 2128 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.OR 2129 // check operand types 2130 && ( 2131 expArg.type() == Type.POINTER || 2132 ( expArg.type() == Type.INT && ! 2133 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2134 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2135 false ) 2136 // end check operand types 2137 // check left child 2138 // no check needed for ExpId children 2139 // check right child 2140 // check expression type 2141 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 2142 // check operand types 2143 && ( 2144 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2145 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2146 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2147 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2148 false ) 2149 // end check operand types 2150 // check left child 2151 // no check needed for ExpId children 2152 // check right child 2153 // check expression type 2154 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 2155 // check operand types 2156 && ( 2157 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.POINTER || 2158 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.INT && ! 2159 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2160 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).isSmall())) || 2161 false ) 2162 // end check operand types 2163 ){ 2164 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 2165 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).value; 2166 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2167 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 2168 2169 if (_matched_) { // action code! degree: 3 2170 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2171 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()); 2172 2173 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2174 clearDecl(); 2175 declare(i, code.getTreeDerivation(), ROOT); 2176 2177 emit( ROOT, "orr `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k ); 2178 return i; 2179 } 2180 } 2181 /* BINOP<i,p>(XOR,j,BINOP<i,p>(shiftop,CONST<i,p>(c),k)) */ 2182 if (true 2183 // check expression type 2184 && expArg instanceof harpoon.IR.Tree.BINOP 2185 // check opcode 2186 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.XOR 2187 // check operand types 2188 && ( 2189 expArg.type() == Type.POINTER || 2190 ( expArg.type() == Type.INT && ! 2191 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2192 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2193 false ) 2194 // end check operand types 2195 // check left child 2196 // no check needed for ExpId children 2197 // check right child 2198 // check expression type 2199 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 2200 // check operand types 2201 && ( 2202 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2203 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2204 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2205 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2206 false ) 2207 // end check operand types 2208 // check left child 2209 // check expression type 2210 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 2211 // check operand types 2212 && ( 2213 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.POINTER || 2214 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft().type() == Type.INT && ! 2215 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 2216 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).isSmall())) || 2217 false ) 2218 // end check operand types 2219 // check right child 2220 // no check needed for ExpId children 2221 ){ 2222 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 2223 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()).value; 2224 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2225 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 2226 2227 if (_matched_) { // action code! degree: 3 2228 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2229 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()); 2230 2231 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2232 clearDecl(); 2233 declare(i, code.getTreeDerivation(), ROOT); 2234 2235 emit( ROOT, "eor `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k ); 2236 return i; 2237 } 2238 } 2239 /* BINOP<i,p>(XOR,j,BINOP<i,p>(shiftop,k,CONST<i,p>(c))) */ 2240 if (true 2241 // check expression type 2242 && expArg instanceof harpoon.IR.Tree.BINOP 2243 // check opcode 2244 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.XOR 2245 // check operand types 2246 && ( 2247 expArg.type() == Type.POINTER || 2248 ( expArg.type() == Type.INT && ! 2249 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2250 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2251 false ) 2252 // end check operand types 2253 // check left child 2254 // no check needed for ExpId children 2255 // check right child 2256 // check expression type 2257 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 2258 // check operand types 2259 && ( 2260 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2261 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2262 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2263 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2264 false ) 2265 // end check operand types 2266 // check left child 2267 // no check needed for ExpId children 2268 // check right child 2269 // check expression type 2270 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 2271 // check operand types 2272 && ( 2273 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.POINTER || 2274 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight().type() == Type.INT && ! 2275 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2276 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).isSmall())) || 2277 false ) 2278 // end check operand types 2279 ){ 2280 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)expArg).getRight()).op; 2281 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()).value; 2282 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2283 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 2284 2285 if (_matched_) { // action code! degree: 3 2286 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2287 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()); 2288 2289 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2290 clearDecl(); 2291 declare(i, code.getTreeDerivation(), ROOT); 2292 2293 emit( ROOT, "eor `d0, `s0, `s1, "+shiftOp2Str(shiftop)+" #"+c, i, j, k ); 2294 return i; 2295 } 2296 } 2297 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,UNOP<i,l,f,d,p>(NEG,k),j)) */ 2298 if (true 2299 // check expression type 2300 && expArg instanceof harpoon.IR.Tree.MEM 2301 // check operand types 2302 && ( 2303 expArg.type() == Type.FLOAT || 2304 expArg.type() == Type.POINTER || 2305 ( expArg.type() == Type.INT && ! 2306 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2307 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2308 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 2309 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 2310 false) : ( 2311 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 2312 false) ) ) || 2313 false ) 2314 // end check operand types 2315 // check child 2316 // check expression type 2317 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 2318 // check opcode 2319 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 2320 // check operand types 2321 && ( 2322 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 2323 false ) 2324 // end check operand types 2325 // check left child 2326 // check expression type 2327 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.UNOP 2328 // check opcode 2329 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).op == harpoon.IR.Tree.Uop.NEG 2330 // check operand types 2331 && ( 2332 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.DOUBLE || 2333 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.FLOAT || 2334 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.LONG || 2335 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.POINTER || 2336 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.INT && ! 2337 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 2338 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).isSmall())) || 2339 false ) 2340 // end check operand types 2341 // check child 2342 // no check needed for ExpId children 2343 // check right child 2344 // no check needed for ExpId children 2345 ){ 2346 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 2347 _matched_ = true; 2348 2349 if (_matched_) { // action code! degree: 3 2350 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).getOperand()); 2351 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 2352 2353 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2354 clearDecl(); 2355 declare(i, code.getTreeDerivation(), ROOT); 2356 // addressing mode 2 2357 2358 String suffix=""; 2359 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 2360 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 2361 emit(new InstrMEM(instrFactory, ROOT, 2362 "ldr"+suffix+" `d0, [`s0, -`s1]", 2363 new Temp[]{ i }, new Temp[]{ j, k })); 2364 return i; 2365 } 2366 } 2367 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,j,UNOP<i,l,f,d,p>(NEG,k))) */ 2368 if (true 2369 // check expression type 2370 && expArg instanceof harpoon.IR.Tree.MEM 2371 // check operand types 2372 && ( 2373 expArg.type() == Type.FLOAT || 2374 expArg.type() == Type.POINTER || 2375 ( expArg.type() == Type.INT && ! 2376 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2377 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2378 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 2379 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 2380 false) : ( 2381 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 2382 false) ) ) || 2383 false ) 2384 // end check operand types 2385 // check child 2386 // check expression type 2387 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 2388 // check opcode 2389 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 2390 // check operand types 2391 && ( 2392 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 2393 false ) 2394 // end check operand types 2395 // check left child 2396 // no check needed for ExpId children 2397 // check right child 2398 // check expression type 2399 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.UNOP 2400 // check opcode 2401 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).op == harpoon.IR.Tree.Uop.NEG 2402 // check operand types 2403 && ( 2404 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.DOUBLE || 2405 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.FLOAT || 2406 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.LONG || 2407 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.POINTER || 2408 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.INT && ! 2409 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2410 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).isSmall())) || 2411 false ) 2412 // end check operand types 2413 // check child 2414 // no check needed for ExpId children 2415 ){ 2416 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 2417 _matched_ = true; 2418 2419 if (_matched_) { // action code! degree: 3 2420 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 2421 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).getOperand()); 2422 2423 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2424 clearDecl(); 2425 declare(i, code.getTreeDerivation(), ROOT); 2426 // addressing mode 2 2427 2428 String suffix=""; 2429 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 2430 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 2431 emit(new InstrMEM(instrFactory, ROOT, 2432 "ldr"+suffix+" `d0, [`s0, -`s1]", 2433 new Temp[]{ i }, new Temp[]{ j, k })); 2434 return i; 2435 } 2436 } 2437 /* MEM<i,f,p,u:8>(BINOP<i,l,f,d,p>(ADD,CONST<i,p>(c),j)) */ 2438 if (true 2439 // check expression type 2440 && expArg instanceof harpoon.IR.Tree.MEM 2441 // check operand types 2442 && ( 2443 expArg.type() == Type.FLOAT || 2444 expArg.type() == Type.POINTER || 2445 ( expArg.type() == Type.INT && ! 2446 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2447 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2448 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 2449 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 2450 false) : ( 2451 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 2452 false) ) ) || 2453 false ) 2454 // end check operand types 2455 // check child 2456 // check expression type 2457 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 2458 // check opcode 2459 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 2460 // check operand types 2461 && ( 2462 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.DOUBLE || 2463 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.FLOAT || 2464 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.LONG || 2465 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 2466 ( ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.INT && ! 2467 (((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.PreciselyTyped && 2468 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MEM)expArg).getExp()).isSmall())) || 2469 false ) 2470 // end check operand types 2471 // check left child 2472 // check expression type 2473 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.CONST 2474 // check operand types 2475 && ( 2476 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.POINTER || 2477 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft().type() == Type.INT && ! 2478 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 2479 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).isSmall())) || 2480 false ) 2481 // end check operand types 2482 // check right child 2483 // no check needed for ExpId children 2484 ){ 2485 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()).value; 2486 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 2487 _matched_ = true&& ( is12BitOffset(c) ); 2488 2489 if (_matched_) { // action code! degree: 3 2490 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 2491 2492 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2493 clearDecl(); 2494 declare(i, code.getTreeDerivation(), ROOT); 2495 2496 2497 String suffix=""; 2498 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 2499 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 2500 emit(new InstrMEM(instrFactory, ROOT, 2501 "ldr"+suffix+" `d0, [`s0, #"+c+"]", 2502 new Temp[]{ i }, new Temp[]{ j })); 2503 return i; 2504 } 2505 } 2506 /* MEM<i,f,p,u:8>(BINOP<i,l,f,d,p>(ADD,j,CONST<i,p>(c))) */ 2507 if (true 2508 // check expression type 2509 && expArg instanceof harpoon.IR.Tree.MEM 2510 // check operand types 2511 && ( 2512 expArg.type() == Type.FLOAT || 2513 expArg.type() == Type.POINTER || 2514 ( expArg.type() == Type.INT && ! 2515 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2516 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2517 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 2518 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 2519 false) : ( 2520 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 2521 false) ) ) || 2522 false ) 2523 // end check operand types 2524 // check child 2525 // check expression type 2526 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 2527 // check opcode 2528 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 2529 // check operand types 2530 && ( 2531 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.DOUBLE || 2532 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.FLOAT || 2533 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.LONG || 2534 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 2535 ( ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.INT && ! 2536 (((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.PreciselyTyped && 2537 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MEM)expArg).getExp()).isSmall())) || 2538 false ) 2539 // end check operand types 2540 // check left child 2541 // no check needed for ExpId children 2542 // check right child 2543 // check expression type 2544 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.CONST 2545 // check operand types 2546 && ( 2547 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.POINTER || 2548 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight().type() == Type.INT && ! 2549 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2550 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).isSmall())) || 2551 false ) 2552 // end check operand types 2553 ){ 2554 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()).value; 2555 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 2556 _matched_ = true&& ( is12BitOffset(c) ); 2557 2558 if (_matched_) { // action code! degree: 3 2559 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 2560 2561 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2562 clearDecl(); 2563 declare(i, code.getTreeDerivation(), ROOT); 2564 2565 2566 String suffix=""; 2567 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 2568 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 2569 emit(new InstrMEM(instrFactory, ROOT, 2570 "ldr"+suffix+" `d0, [`s0, #"+c+"]", 2571 new Temp[]{ i }, new Temp[]{ j })); 2572 return i; 2573 } 2574 } 2575 /* UNOP<i,l,f,d,p>(NOT,BINOP<i,p>(shiftop,CONST<i,p>(c),j)) */ 2576 if (true 2577 // check expression type 2578 && expArg instanceof harpoon.IR.Tree.UNOP 2579 // check opcode 2580 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NOT 2581 // check operand types 2582 && ( 2583 expArg.type() == Type.DOUBLE || 2584 expArg.type() == Type.FLOAT || 2585 expArg.type() == Type.LONG || 2586 expArg.type() == Type.POINTER || 2587 ( expArg.type() == Type.INT && ! 2588 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2589 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2590 false ) 2591 // end check operand types 2592 // check child 2593 // check expression type 2594 && ((harpoon.IR.Tree.UNOP)expArg).getOperand() instanceof harpoon.IR.Tree.BINOP 2595 // check operand types 2596 && ( 2597 ((harpoon.IR.Tree.UNOP)expArg).getOperand().type() == Type.POINTER || 2598 ( ((harpoon.IR.Tree.UNOP)expArg).getOperand().type() == Type.INT && ! 2599 (((harpoon.IR.Tree.UNOP)expArg).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 2600 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)expArg).getOperand()).isSmall())) || 2601 false ) 2602 // end check operand types 2603 // check left child 2604 // check expression type 2605 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft() instanceof harpoon.IR.Tree.CONST 2606 // check operand types 2607 && ( 2608 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft().type() == Type.POINTER || 2609 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft().type() == Type.INT && ! 2610 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 2611 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft()).isSmall())) || 2612 false ) 2613 // end check operand types 2614 // check right child 2615 // no check needed for ExpId children 2616 ){ 2617 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)expArg).getOperand()).op; 2618 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft()).value; 2619 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 2620 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( ROOT.operandType()==Type.INT && isShiftOp(shiftop)&& is5BitShift(c) )); 2621 2622 if (_matched_) { // action code! degree: 3 2623 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight()); 2624 2625 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2626 clearDecl(); 2627 declare(i, code.getTreeDerivation(), ROOT); 2628 2629 emit( ROOT, "mvn `d0, `s0, "+shiftOp2Str(shiftop)+" #"+c, i, j ); 2630 return i; 2631 } 2632 } 2633 /* UNOP<i,l,f,d,p>(NOT,BINOP<i,p>(shiftop,j,CONST<i,p>(c))) */ 2634 if (true 2635 // check expression type 2636 && expArg instanceof harpoon.IR.Tree.UNOP 2637 // check opcode 2638 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NOT 2639 // check operand types 2640 && ( 2641 expArg.type() == Type.DOUBLE || 2642 expArg.type() == Type.FLOAT || 2643 expArg.type() == Type.LONG || 2644 expArg.type() == Type.POINTER || 2645 ( expArg.type() == Type.INT && ! 2646 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2647 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2648 false ) 2649 // end check operand types 2650 // check child 2651 // check expression type 2652 && ((harpoon.IR.Tree.UNOP)expArg).getOperand() instanceof harpoon.IR.Tree.BINOP 2653 // check operand types 2654 && ( 2655 ((harpoon.IR.Tree.UNOP)expArg).getOperand().type() == Type.POINTER || 2656 ( ((harpoon.IR.Tree.UNOP)expArg).getOperand().type() == Type.INT && ! 2657 (((harpoon.IR.Tree.UNOP)expArg).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 2658 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)expArg).getOperand()).isSmall())) || 2659 false ) 2660 // end check operand types 2661 // check left child 2662 // no check needed for ExpId children 2663 // check right child 2664 // check expression type 2665 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight() instanceof harpoon.IR.Tree.CONST 2666 // check operand types 2667 && ( 2668 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight().type() == Type.POINTER || 2669 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight().type() == Type.INT && ! 2670 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2671 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight()).isSmall())) || 2672 false ) 2673 // end check operand types 2674 ){ 2675 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)expArg).getOperand()).op; 2676 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getRight()).value; 2677 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 2678 _matched_ = true&& ( ROOT.operandType()==Type.INT && isShiftOp(shiftop)&& is5BitShift(c) ); 2679 2680 if (_matched_) { // action code! degree: 3 2681 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)expArg).getOperand()).getLeft()); 2682 2683 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2684 clearDecl(); 2685 declare(i, code.getTreeDerivation(), ROOT); 2686 2687 emit( ROOT, "mvn `d0, `s0, "+shiftOp2Str(shiftop)+" #"+c, i, j ); 2688 return i; 2689 } 2690 } 2691 /* BINOP<i,p>(ADD,j,CONST<i,p>(c)) */ 2692 if (true 2693 // check expression type 2694 && expArg instanceof harpoon.IR.Tree.BINOP 2695 // check opcode 2696 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 2697 // check operand types 2698 && ( 2699 expArg.type() == Type.POINTER || 2700 ( expArg.type() == Type.INT && ! 2701 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2702 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2703 false ) 2704 // end check operand types 2705 // check left child 2706 // no check needed for ExpId children 2707 // check right child 2708 // check expression type 2709 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 2710 // check operand types 2711 && ( 2712 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2713 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2714 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2715 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2716 false ) 2717 // end check operand types 2718 ){ 2719 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 2720 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2721 _matched_ = true&& ( isOpd2Imm(c) ); 2722 2723 if (_matched_) { // action code! degree: 2 2724 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2725 2726 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2727 clearDecl(); 2728 declare(i, code.getTreeDerivation(), ROOT); 2729 2730 emit( ROOT, "add `d0, `s0, #"+c, i, j); 2731 return i; 2732 } 2733 } 2734 /* BINOP<i,p>(ADD,j,UNOP<i,p>(NEG,k)) */ 2735 if (true 2736 // check expression type 2737 && expArg instanceof harpoon.IR.Tree.BINOP 2738 // check opcode 2739 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 2740 // check operand types 2741 && ( 2742 expArg.type() == Type.POINTER || 2743 ( expArg.type() == Type.INT && ! 2744 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2745 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2746 false ) 2747 // end check operand types 2748 // check left child 2749 // no check needed for ExpId children 2750 // check right child 2751 // check expression type 2752 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.UNOP 2753 // check opcode 2754 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Uop.NEG 2755 // check operand types 2756 && ( 2757 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 2758 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2759 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2760 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2761 false ) 2762 // end check operand types 2763 // check child 2764 // no check needed for ExpId children 2765 ){ 2766 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2767 _matched_ = true; 2768 2769 if (_matched_) { // action code! degree: 2 2770 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2771 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()); 2772 2773 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2774 clearDecl(); 2775 declare(i, code.getTreeDerivation(), ROOT); 2776 2777 emit( ROOT, "sub `d0, `s0, `s1", i, j, k); 2778 return i; 2779 } 2780 } 2781 /* BINOP<i,p>(ADD,j,CONST<i>(c)) */ 2782 if (true 2783 // check expression type 2784 && expArg instanceof harpoon.IR.Tree.BINOP 2785 // check opcode 2786 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 2787 // check operand types 2788 && ( 2789 expArg.type() == Type.POINTER || 2790 ( expArg.type() == Type.INT && ! 2791 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2792 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2793 false ) 2794 // end check operand types 2795 // check left child 2796 // no check needed for ExpId children 2797 // check right child 2798 // check expression type 2799 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 2800 // check operand types 2801 && ( 2802 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 2803 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 2804 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 2805 false ) 2806 // end check operand types 2807 ){ 2808 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 2809 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2810 _matched_ = true&& ( isOpd2Imm(negate(c)) ); 2811 2812 if (_matched_) { // action code! degree: 2 2813 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2814 2815 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2816 clearDecl(); 2817 declare(i, code.getTreeDerivation(), ROOT); 2818 2819 emit( ROOT, "sub `d0, `s0, #"+negate(c), i, j); 2820 return i; 2821 } 2822 } 2823 /* BINOP<l>(ADD,j,UNOP<l>(NEG,k)) */ 2824 if (true 2825 // check expression type 2826 && expArg instanceof harpoon.IR.Tree.BINOP 2827 // check opcode 2828 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 2829 // check operand types 2830 && ( 2831 expArg.type() == Type.LONG || 2832 false ) 2833 // end check operand types 2834 // check left child 2835 // no check needed for ExpId children 2836 // check right child 2837 // check expression type 2838 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.UNOP 2839 // check opcode 2840 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Uop.NEG 2841 // check operand types 2842 && ( 2843 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.LONG || 2844 false ) 2845 // end check operand types 2846 // check child 2847 // no check needed for ExpId children 2848 ){ 2849 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2850 _matched_ = true; 2851 2852 if (_matched_) { // action code! degree: 2 2853 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2854 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()); 2855 2856 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2857 clearDecl(); 2858 declare(i, code.getTreeDerivation(), ROOT); 2859 2860 2861 emit( ROOT, "subs `d0l, `s0l, `s1l\n"+ 2862 "sbc `d0h, `s0h, `s1h", i, j, k ); 2863 // make sure d0l isn't assigned same reg as `s0h or `s1h 2864 emit2( ROOT, "@ dummy use of `s0l `s0h `s1l `s1h", null, new Temp[]{j,k}); 2865 return i; 2866 } 2867 } 2868 /* BINOP<f>(ADD,j,UNOP<l>(NEG,k)) */ 2869 if (true 2870 // check expression type 2871 && expArg instanceof harpoon.IR.Tree.BINOP 2872 // check opcode 2873 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 2874 // check operand types 2875 && ( 2876 expArg.type() == Type.FLOAT || 2877 false ) 2878 // end check operand types 2879 // check left child 2880 // no check needed for ExpId children 2881 // check right child 2882 // check expression type 2883 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.UNOP 2884 // check opcode 2885 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Uop.NEG 2886 // check operand types 2887 && ( 2888 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.LONG || 2889 false ) 2890 // end check operand types 2891 // check child 2892 // no check needed for ExpId children 2893 ){ 2894 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2895 _matched_ = true; 2896 2897 if (_matched_) { // action code! degree: 2 2898 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2899 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()); 2900 2901 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2902 clearDecl(); 2903 declare(i, code.getTreeDerivation(), ROOT); 2904 2905 /* call auxillary fp routines */ 2906 declare( r1, HClass.Float ); 2907 declare( r0, HClass.Float ); 2908 2909 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 2910 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 2911 declareCALL(); 2912 declare( r0, HClass.Float ); // retval from call. 2913 emit2( ROOT, "bl "+nameMap.c_function_name("__subsf3"), 2914 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 2915 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 2916 return i; 2917 } 2918 } 2919 /* BINOP<d>(ADD,j,UNOP<l>(NEG,k)) */ 2920 if (true 2921 // check expression type 2922 && expArg instanceof harpoon.IR.Tree.BINOP 2923 // check opcode 2924 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 2925 // check operand types 2926 && ( 2927 expArg.type() == Type.DOUBLE || 2928 false ) 2929 // end check operand types 2930 // check left child 2931 // no check needed for ExpId children 2932 // check right child 2933 // check expression type 2934 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.UNOP 2935 // check opcode 2936 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Uop.NEG 2937 // check operand types 2938 && ( 2939 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.LONG || 2940 false ) 2941 // end check operand types 2942 // check child 2943 // no check needed for ExpId children 2944 ){ 2945 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 2946 _matched_ = true; 2947 2948 if (_matched_) { // action code! degree: 2 2949 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 2950 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getOperand()); 2951 2952 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 2953 clearDecl(); 2954 declare(i, code.getTreeDerivation(), ROOT); 2955 2956 /* call auxillary fp routines */ 2957 declare( r3, HClass.Void ); 2958 declare( r2, HClass.Void ); 2959 declare( r1, HClass.Void ); 2960 declare( r0, HClass.Void ); 2961 2962 // not certain an emitMOVE is legal with the l/h modifiers 2963 emit( ROOT, "mov `d0, `s0l", r2, k ); 2964 emit( ROOT, "mov `d0, `s0h", r3, k ); 2965 emit( ROOT, "mov `d0, `s0l", r0, j ); 2966 emit( ROOT, "mov `d0, `s0h", r1, j ); 2967 declareCALL(); 2968 declare( r0, HClass.Void ); // retval from call. 2969 declare( r1, HClass.Void ); // retval from call. 2970 emit2(ROOT, "bl "+nameMap.c_function_name("__subdf3"), 2971 // uses & stomps on these registers: 2972 new Temp[]{r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 2973 emit( ROOT, "mov `d0l, `s0", i, r0 ); 2974 emit( ROOT, "mov `d0h, `s0", i, r1 ); 2975 return i; 2976 } 2977 } 2978 /* BINOP<i,p>(AND,j,CONST<i,p>(c)) */ 2979 if (true 2980 // check expression type 2981 && expArg instanceof harpoon.IR.Tree.BINOP 2982 // check opcode 2983 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.AND 2984 // check operand types 2985 && ( 2986 expArg.type() == Type.POINTER || 2987 ( expArg.type() == Type.INT && ! 2988 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 2989 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 2990 false ) 2991 // end check operand types 2992 // check left child 2993 // no check needed for ExpId children 2994 // check right child 2995 // check expression type 2996 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 2997 // check operand types 2998 && ( 2999 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 3000 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 3001 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 3002 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 3003 false ) 3004 // end check operand types 3005 ){ 3006 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 3007 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3008 _matched_ = true&& ( isOpd2Imm(c) ); 3009 3010 if (_matched_) { // action code! degree: 2 3011 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3012 3013 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3014 clearDecl(); 3015 declare(i, code.getTreeDerivation(), ROOT); 3016 3017 emit( ROOT, "and `d0, `s0, #"+c, i, j ); 3018 return i; 3019 } 3020 } 3021 /* BINOP<i,l,f,d,p>(cmpop,j,CONST<i,p>(c)) */ 3022 if (true 3023 // check expression type 3024 && expArg instanceof harpoon.IR.Tree.BINOP 3025 // check operand types 3026 && ( 3027 expArg.type() == Type.DOUBLE || 3028 expArg.type() == Type.FLOAT || 3029 expArg.type() == Type.LONG || 3030 expArg.type() == Type.POINTER || 3031 ( expArg.type() == Type.INT && ! 3032 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3033 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3034 false ) 3035 // end check operand types 3036 // check left child 3037 // no check needed for ExpId children 3038 // check right child 3039 // check expression type 3040 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 3041 // check operand types 3042 && ( 3043 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 3044 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 3045 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 3046 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 3047 false ) 3048 // end check operand types 3049 ){ 3050 int cmpop = ((harpoon.IR.Tree.BINOP) expArg).op; 3051 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 3052 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3053 _matched_ = true&& ( (ROOT.operandType()==Type.POINTER || ROOT.operandType()==Type.INT) 3054 && isCmpOp(cmpop) && (c==null || isOpd2Imm(c)) ); 3055 3056 if (_matched_) { // action code! degree: 2 3057 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3058 3059 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3060 clearDecl(); 3061 declare(i, code.getTreeDerivation(), ROOT); 3062 3063 // don't move these into seperate Instrs; there's an implicit 3064 // dependency on the condition register so we don't want to risk 3065 // reordering them 3066 emit( ROOT, "cmp `s0, #"+(c==null?"0 @ null":c.toString())+"\n"+ 3067 "mov"+cmpOp2Str(cmpop)+" `d0, #1\n"+ 3068 "mov"+cmpOp2Str(Bop.invert(cmpop))+" `d0, #0", i, j ); 3069 return i; 3070 } 3071 } 3072 /* BINOP<i,p>(OR,j,CONST<i,p>(c)) */ 3073 if (true 3074 // check expression type 3075 && expArg instanceof harpoon.IR.Tree.BINOP 3076 // check opcode 3077 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.OR 3078 // check operand types 3079 && ( 3080 expArg.type() == Type.POINTER || 3081 ( expArg.type() == Type.INT && ! 3082 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3083 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3084 false ) 3085 // end check operand types 3086 // check left child 3087 // no check needed for ExpId children 3088 // check right child 3089 // check expression type 3090 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 3091 // check operand types 3092 && ( 3093 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 3094 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 3095 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 3096 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 3097 false ) 3098 // end check operand types 3099 ){ 3100 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 3101 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3102 _matched_ = true&& ( isOpd2Imm(c) ); 3103 3104 if (_matched_) { // action code! degree: 2 3105 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3106 3107 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3108 clearDecl(); 3109 declare(i, code.getTreeDerivation(), ROOT); 3110 3111 emit( ROOT, "orr `d0, `s0, #"+c, i, j ); 3112 return i; 3113 } 3114 } 3115 /* BINOP<i,p>(shiftop,j,CONST<i,l,f,d,p>(c)) */ 3116 if (true 3117 // check expression type 3118 && expArg instanceof harpoon.IR.Tree.BINOP 3119 // check operand types 3120 && ( 3121 expArg.type() == Type.POINTER || 3122 ( expArg.type() == Type.INT && ! 3123 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3124 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3125 false ) 3126 // end check operand types 3127 // check left child 3128 // no check needed for ExpId children 3129 // check right child 3130 // check expression type 3131 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 3132 // check operand types 3133 && ( 3134 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.DOUBLE || 3135 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.FLOAT || 3136 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.LONG || 3137 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 3138 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 3139 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 3140 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 3141 false ) 3142 // end check operand types 3143 ){ 3144 int shiftop = ((harpoon.IR.Tree.BINOP) expArg).op; 3145 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 3146 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3147 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 3148 3149 if (_matched_) { // action code! degree: 2 3150 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3151 3152 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3153 clearDecl(); 3154 declare(i, code.getTreeDerivation(), ROOT); 3155 3156 emit( ROOT, "mov `d0, `s0, "+shiftOp2Str(shiftop)+" #"+c, i, j); 3157 return i; 3158 } 3159 } 3160 /* BINOP<i,p>(XOR,j,CONST<i,p>(c)) */ 3161 if (true 3162 // check expression type 3163 && expArg instanceof harpoon.IR.Tree.BINOP 3164 // check opcode 3165 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.XOR 3166 // check operand types 3167 && ( 3168 expArg.type() == Type.POINTER || 3169 ( expArg.type() == Type.INT && ! 3170 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3171 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3172 false ) 3173 // end check operand types 3174 // check left child 3175 // no check needed for ExpId children 3176 // check right child 3177 // check expression type 3178 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.CONST 3179 // check operand types 3180 && ( 3181 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 3182 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 3183 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 3184 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 3185 false ) 3186 // end check operand types 3187 ){ 3188 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)expArg).getRight()).value; 3189 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3190 _matched_ = true&& ( isOpd2Imm(c) ); 3191 3192 if (_matched_) { // action code! degree: 2 3193 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3194 3195 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3196 clearDecl(); 3197 declare(i, code.getTreeDerivation(), ROOT); 3198 3199 emit( ROOT, "eor `d0, `s0, #"+c, i, j ); 3200 return i; 3201 } 3202 } 3203 /* BINOP<i,p>(ADD,l,BINOP<i,p>(MUL,j,k)) */ 3204 if (true 3205 // check expression type 3206 && expArg instanceof harpoon.IR.Tree.BINOP 3207 // check opcode 3208 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 3209 // check operand types 3210 && ( 3211 expArg.type() == Type.POINTER || 3212 ( expArg.type() == Type.INT && ! 3213 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3214 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3215 false ) 3216 // end check operand types 3217 // check left child 3218 // no check needed for ExpId children 3219 // check right child 3220 // check expression type 3221 && ((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.BINOP 3222 // check opcode 3223 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).op == harpoon.IR.Tree.Bop.MUL 3224 // check operand types 3225 && ( 3226 ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.POINTER || 3227 ( ((harpoon.IR.Tree.BINOP)expArg).getRight().type() == Type.INT && ! 3228 (((harpoon.IR.Tree.BINOP)expArg).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 3229 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)expArg).getRight()).isSmall())) || 3230 false ) 3231 // end check operand types 3232 // check left child 3233 // no check needed for ExpId children 3234 // check right child 3235 // no check needed for ExpId children 3236 ){ 3237 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3238 _matched_ = true; 3239 3240 if (_matched_) { // action code! degree: 2 3241 harpoon.Temp.Temp l = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3242 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getLeft()); 3243 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)expArg).getRight()).getRight()); 3244 3245 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3246 clearDecl(); 3247 declare(i, code.getTreeDerivation(), ROOT); 3248 3249 3250 emit(new Instr( instrFactory, ROOT, "mla `d0, `s0, `s1, `s2", 3251 new Temp[] { i }, new Temp[] { j, k, l } )); 3252 // `d0 and `s0 can't be same register on ARM, so we insert a 3253 // dummy use of `s0 following the mul to keep it live. 3254 emit(new Instr( instrFactory, ROOT, "@ dummy", 3255 null, new Temp[] { j })); 3256 return i; 3257 } 3258 } 3259 /* MEM<i,f,p,u:8>(BINOP<p>(ADD,j,k)) */ 3260 if (true 3261 // check expression type 3262 && expArg instanceof harpoon.IR.Tree.MEM 3263 // check operand types 3264 && ( 3265 expArg.type() == Type.FLOAT || 3266 expArg.type() == Type.POINTER || 3267 ( expArg.type() == Type.INT && ! 3268 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3269 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3270 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 3271 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 3272 false) : ( 3273 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 3274 false) ) ) || 3275 false ) 3276 // end check operand types 3277 // check child 3278 // check expression type 3279 && ((harpoon.IR.Tree.MEM)expArg).getExp() instanceof harpoon.IR.Tree.BINOP 3280 // check opcode 3281 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).op == harpoon.IR.Tree.Bop.ADD 3282 // check operand types 3283 && ( 3284 ((harpoon.IR.Tree.MEM)expArg).getExp().type() == Type.POINTER || 3285 false ) 3286 // end check operand types 3287 // check left child 3288 // no check needed for ExpId children 3289 // check right child 3290 // no check needed for ExpId children 3291 ){ 3292 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 3293 _matched_ = true; 3294 3295 if (_matched_) { // action code! degree: 2 3296 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getLeft()); 3297 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)expArg).getExp()).getRight()); 3298 3299 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3300 clearDecl(); 3301 declare(i, code.getTreeDerivation(), ROOT); 3302 // addressing mode 2 3303 3304 String suffix=""; 3305 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 3306 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 3307 emit(new InstrMEM(instrFactory, ROOT, 3308 "ldr"+suffix+" `d0, [`s0, `s1]", 3309 new Temp[]{ i }, new Temp[]{ j, k })); 3310 return i; 3311 } 3312 } 3313 /* BINOP<i,p>(ADD,j,k) */ 3314 if (true 3315 // check expression type 3316 && expArg instanceof harpoon.IR.Tree.BINOP 3317 // check opcode 3318 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 3319 // check operand types 3320 && ( 3321 expArg.type() == Type.POINTER || 3322 ( expArg.type() == Type.INT && ! 3323 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3324 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3325 false ) 3326 // end check operand types 3327 // check left child 3328 // no check needed for ExpId children 3329 // check right child 3330 // no check needed for ExpId children 3331 ){ 3332 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3333 _matched_ = true; 3334 3335 if (_matched_) { // action code! degree: 1 3336 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3337 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3338 3339 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3340 clearDecl(); 3341 declare(i, code.getTreeDerivation(), ROOT); 3342 3343 emit( ROOT, "add `d0, `s0, `s1", i, j, k); 3344 return i; 3345 } 3346 } 3347 /* BINOP<l>(ADD,j,k) */ 3348 if (true 3349 // check expression type 3350 && expArg instanceof harpoon.IR.Tree.BINOP 3351 // check opcode 3352 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 3353 // check operand types 3354 && ( 3355 expArg.type() == Type.LONG || 3356 false ) 3357 // end check operand types 3358 // check left child 3359 // no check needed for ExpId children 3360 // check right child 3361 // no check needed for ExpId children 3362 ){ 3363 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3364 _matched_ = true; 3365 3366 if (_matched_) { // action code! degree: 1 3367 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3368 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3369 3370 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3371 clearDecl(); 3372 declare(i, code.getTreeDerivation(), ROOT); 3373 3374 3375 emit( ROOT, "adds `d0l, `s0l, `s1l\n"+ 3376 "adc `d0h, `s0h, `s1h", i, j, k ); 3377 // make sure d0l isn't assigned same reg as `s0h or `s1h 3378 emit2( ROOT, "@ dummy use of `s0l `s0h `s1l `s1h", null, new Temp[]{j,k}); 3379 return i; 3380 } 3381 } 3382 /* BINOP<f>(ADD,j,k) */ 3383 if (true 3384 // check expression type 3385 && expArg instanceof harpoon.IR.Tree.BINOP 3386 // check opcode 3387 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 3388 // check operand types 3389 && ( 3390 expArg.type() == Type.FLOAT || 3391 false ) 3392 // end check operand types 3393 // check left child 3394 // no check needed for ExpId children 3395 // check right child 3396 // no check needed for ExpId children 3397 ){ 3398 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3399 _matched_ = true; 3400 3401 if (_matched_) { // action code! degree: 1 3402 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3403 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3404 3405 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3406 clearDecl(); 3407 declare(i, code.getTreeDerivation(), ROOT); 3408 3409 /* call auxillary fp routines */ 3410 declare(r1, HClass.Float); 3411 declare(r0, HClass.Float); 3412 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 3413 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 3414 declareCALL(); 3415 declare(r0, HClass.Float); // retval from call. 3416 emit2( ROOT, "bl "+nameMap.c_function_name("__addsf3"), 3417 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 3418 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 3419 return i; 3420 } 3421 } 3422 /* BINOP<d>(ADD,j,k) */ 3423 if (true 3424 // check expression type 3425 && expArg instanceof harpoon.IR.Tree.BINOP 3426 // check opcode 3427 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.ADD 3428 // check operand types 3429 && ( 3430 expArg.type() == Type.DOUBLE || 3431 false ) 3432 // end check operand types 3433 // check left child 3434 // no check needed for ExpId children 3435 // check right child 3436 // no check needed for ExpId children 3437 ){ 3438 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3439 _matched_ = true; 3440 3441 if (_matched_) { // action code! degree: 1 3442 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3443 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3444 3445 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3446 clearDecl(); 3447 declare(i, code.getTreeDerivation(), ROOT); 3448 3449 /* call auxillary fp routines */ 3450 declare( r3, HClass.Void ); 3451 declare( r2, HClass.Void ); 3452 declare( r1, HClass.Void ); 3453 declare( r0, HClass.Void ); 3454 // not certain an emitMOVE is legal with the l/h modifiers 3455 emit( ROOT, "mov `d0, `s0l", r2, k ); 3456 emit( ROOT, "mov `d0, `s0h", r3, k ); 3457 emit( ROOT, "mov `d0, `s0l", r0, j ); 3458 emit( ROOT, "mov `d0, `s0h", r1, j ); 3459 declareCALL(); 3460 declare(r0, HClass.Void); // retval from call. 3461 declare(r1, HClass.Void); // retval from call. 3462 emit2(ROOT, "bl "+nameMap.c_function_name("__adddf3"), 3463 // uses & stomps on these registers: 3464 new Temp[]{r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 3465 emit( ROOT, "mov `d0l, `s0", i, r0 ); 3466 emit( ROOT, "mov `d0h, `s0", i, r1 ); 3467 return i; 3468 } 3469 } 3470 /* BINOP<i,p>(AND,j,k) */ 3471 if (true 3472 // check expression type 3473 && expArg instanceof harpoon.IR.Tree.BINOP 3474 // check opcode 3475 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.AND 3476 // check operand types 3477 && ( 3478 expArg.type() == Type.POINTER || 3479 ( expArg.type() == Type.INT && ! 3480 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3481 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3482 false ) 3483 // end check operand types 3484 // check left child 3485 // no check needed for ExpId children 3486 // check right child 3487 // no check needed for ExpId children 3488 ){ 3489 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3490 _matched_ = true; 3491 3492 if (_matched_) { // action code! degree: 1 3493 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3494 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3495 3496 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3497 clearDecl(); 3498 declare(i, code.getTreeDerivation(), ROOT); 3499 3500 emit( ROOT, "and `d0, `s0, `s1", i, j, k ); 3501 return i; 3502 } 3503 } 3504 /* BINOP<l>(AND,j,k) */ 3505 if (true 3506 // check expression type 3507 && expArg instanceof harpoon.IR.Tree.BINOP 3508 // check opcode 3509 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.AND 3510 // check operand types 3511 && ( 3512 expArg.type() == Type.LONG || 3513 false ) 3514 // end check operand types 3515 // check left child 3516 // no check needed for ExpId children 3517 // check right child 3518 // no check needed for ExpId children 3519 ){ 3520 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3521 _matched_ = true; 3522 3523 if (_matched_) { // action code! degree: 1 3524 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3525 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3526 3527 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3528 clearDecl(); 3529 declare(i, code.getTreeDerivation(), ROOT); 3530 3531 3532 emit( ROOT, "and `d0l, `s0l, `s1l", i, j, k ); 3533 emit( ROOT, "and `d0h, `s0h, `s1h", i, j, k ); 3534 return i; 3535 } 3536 } 3537 /* BINOP<i,l,f,d,p>(cmpop,j,k) */ 3538 if (true 3539 // check expression type 3540 && expArg instanceof harpoon.IR.Tree.BINOP 3541 // check operand types 3542 && ( 3543 expArg.type() == Type.DOUBLE || 3544 expArg.type() == Type.FLOAT || 3545 expArg.type() == Type.LONG || 3546 expArg.type() == Type.POINTER || 3547 ( expArg.type() == Type.INT && ! 3548 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3549 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3550 false ) 3551 // end check operand types 3552 // check left child 3553 // no check needed for ExpId children 3554 // check right child 3555 // no check needed for ExpId children 3556 ){ 3557 int cmpop = ((harpoon.IR.Tree.BINOP) expArg).op; 3558 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3559 _matched_ = true&& ( (ROOT.operandType()==Type.POINTER || ROOT.operandType()==Type.INT) 3560 && isCmpOp(cmpop) ); 3561 3562 if (_matched_) { // action code! degree: 1 3563 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3564 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3565 3566 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3567 clearDecl(); 3568 declare(i, code.getTreeDerivation(), ROOT); 3569 3570 // don't move these into seperate Instrs; there's an implicit 3571 // dependency on the condition register so we don't want to risk 3572 // reordering them 3573 emit( ROOT, "cmp `s0, `s1\n"+ 3574 "mov"+cmpOp2Str(cmpop)+" `d0, #1\n"+ 3575 "mov"+cmpOp2Str(Bop.invert(cmpop))+" `d0, #0", i, j, k ); 3576 return i; 3577 } 3578 } 3579 /* BINOP<i,l,f,d,p>(cmpop,j,k) */ 3580 if (true 3581 // check expression type 3582 && expArg instanceof harpoon.IR.Tree.BINOP 3583 // check operand types 3584 && ( 3585 expArg.type() == Type.DOUBLE || 3586 expArg.type() == Type.FLOAT || 3587 expArg.type() == Type.LONG || 3588 expArg.type() == Type.POINTER || 3589 ( expArg.type() == Type.INT && ! 3590 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3591 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3592 false ) 3593 // end check operand types 3594 // check left child 3595 // no check needed for ExpId children 3596 // check right child 3597 // no check needed for ExpId children 3598 ){ 3599 int cmpop = ((harpoon.IR.Tree.BINOP) expArg).op; 3600 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3601 _matched_ = true&& ( ROOT.operandType()==Type.LONG && isCmpOp(cmpop) && 3602 (cmpop == Bop.CMPEQ || cmpop == Bop.CMPNE) ); 3603 3604 if (_matched_) { // action code! degree: 1 3605 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3606 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3607 3608 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3609 clearDecl(); 3610 declare(i, code.getTreeDerivation(), ROOT); 3611 3612 emit( ROOT, "cmp `s0h, `s1h\n"+ 3613 "cmpeq `s0l, `s1l\n"+ 3614 "mov `d0, #0\n"+ 3615 "mov"+cmpOp2Str(cmpop)+" `d0, #1", i, j, k); 3616 return i; 3617 } 3618 } 3619 /* BINOP<i,l,f,d,p>(cmpop,j,k) */ 3620 if (true 3621 // check expression type 3622 && expArg instanceof harpoon.IR.Tree.BINOP 3623 // check operand types 3624 && ( 3625 expArg.type() == Type.DOUBLE || 3626 expArg.type() == Type.FLOAT || 3627 expArg.type() == Type.LONG || 3628 expArg.type() == Type.POINTER || 3629 ( expArg.type() == Type.INT && ! 3630 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3631 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3632 false ) 3633 // end check operand types 3634 // check left child 3635 // no check needed for ExpId children 3636 // check right child 3637 // no check needed for ExpId children 3638 ){ 3639 int cmpop = ((harpoon.IR.Tree.BINOP) expArg).op; 3640 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3641 _matched_ = true&& ( ROOT.operandType()==Type.LONG && isCmpOp(cmpop) && 3642 (cmpop != Bop.CMPEQ && cmpop != Bop.CMPNE) ); 3643 3644 if (_matched_) { // action code! degree: 1 3645 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3646 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3647 3648 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3649 clearDecl(); 3650 declare(i, code.getTreeDerivation(), ROOT); 3651 3652 //ARGH: EVIL! We'd like to do conditional moves, but the first 3653 //comparison should be *signed* and the second should be 3654 //*unsigned*. Felix and I can't figure out how to do this 3655 // appropriately using only conditional moves, sigh. So we jump. 3656 3657 // don't move these into seperate Instrs; there's an implicit 3658 // dependency on the condition register so we don't want to risk 3659 // reordering them 3660 3661 int cmpopNE = cmpop; // strip the 'equality' test for the high word 3662 if (cmpop==Bop.CMPGE) cmpopNE=Bop.CMPGT; 3663 if (cmpop==Bop.CMPLE) cmpopNE=Bop.CMPLT; 3664 emit( ROOT, "mov `d0, #0\n"+ 3665 "cmp `s0h, `s1h\n"+ 3666 "mov"+cmpOp2Str(cmpopNE)+" `d0, #1\n"+ 3667 "bne 1f\n"+ 3668 "cmp `s0l, `s1l\n"+ 3669 "mov"+cmpOp2StrUNSIGNED(cmpop)+" `d0, #1\n"+ 3670 "1:", i, j, k); 3671 // dummy use of `s0 and `s1 following the comparison to keep them live 3672 // (otherwise the regalloc could allocate d0 over part of s0 or s1) 3673 emit(new Instr( instrFactory, ROOT, "@ dummy use of `s0h `s0l `s1h `s1l", 3674 null, new Temp[] { j, k })); 3675 return i; 3676 } 3677 } 3678 /* BINOP<i,l,f,d,p>(cmpop,j,k) */ 3679 if (true 3680 // check expression type 3681 && expArg instanceof harpoon.IR.Tree.BINOP 3682 // check operand types 3683 && ( 3684 expArg.type() == Type.DOUBLE || 3685 expArg.type() == Type.FLOAT || 3686 expArg.type() == Type.LONG || 3687 expArg.type() == Type.POINTER || 3688 ( expArg.type() == Type.INT && ! 3689 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3690 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3691 false ) 3692 // end check operand types 3693 // check left child 3694 // no check needed for ExpId children 3695 // check right child 3696 // no check needed for ExpId children 3697 ){ 3698 int cmpop = ((harpoon.IR.Tree.BINOP) expArg).op; 3699 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3700 _matched_ = true&& ( ROOT.operandType()==Type.FLOAT && isCmpOp(cmpop) ); 3701 3702 if (_matched_) { // action code! degree: 1 3703 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3704 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3705 3706 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3707 clearDecl(); 3708 declare(i, code.getTreeDerivation(), ROOT); 3709 3710 declare( r1, HClass.Float ); 3711 declare( r0, HClass.Float ); 3712 emitMOVE( ROOT, "mov `d0, `s0", r0, j); 3713 emitMOVE( ROOT, "mov `d0, `s0", r1, k); 3714 // --- some of these comparison functions are broken! -- 3715 // cmpOp2Func might return a non-broken but *inverted* 3716 // comparison function; we'll fixup the inverted value below. 3717 declareCALL(); 3718 declare( r0, HClass.Int ); // retval from call. 3719 emit2( ROOT, "bl "+nameMap.c_function_name(cmpOp2Func(cmpop)+"sf2"), 3720 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0, r1} ); 3721 // don't move these into seperate Instrs; there's an implicit 3722 // dependency on the condition register so we don't want to risk 3723 // reordering them 3724 // --- in addition to converting to a one-bit boolean value, 3725 // we fixup the possibly inverted test here -- 3726 int t=cmpOpFuncInverted(cmpop) ? 0 : 1, f = (t==0) ? 1 : 0; 3727 emit( ROOT, "cmp `s0, #0\n"+ 3728 "moveq `d0, #"+f+"\n"+ 3729 "movne `d0, #"+t, i, r0 ); 3730 return i; 3731 } 3732 } 3733 /* BINOP<i,l,f,d,p>(cmpop,j,k) */ 3734 if (true 3735 // check expression type 3736 && expArg instanceof harpoon.IR.Tree.BINOP 3737 // check operand types 3738 && ( 3739 expArg.type() == Type.DOUBLE || 3740 expArg.type() == Type.FLOAT || 3741 expArg.type() == Type.LONG || 3742 expArg.type() == Type.POINTER || 3743 ( expArg.type() == Type.INT && ! 3744 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3745 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3746 false ) 3747 // end check operand types 3748 // check left child 3749 // no check needed for ExpId children 3750 // check right child 3751 // no check needed for ExpId children 3752 ){ 3753 int cmpop = ((harpoon.IR.Tree.BINOP) expArg).op; 3754 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3755 _matched_ = true&& ( ROOT.operandType()==Type.DOUBLE && isCmpOp(cmpop) ); 3756 3757 if (_matched_) { // action code! degree: 1 3758 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3759 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3760 3761 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3762 clearDecl(); 3763 declare(i, code.getTreeDerivation(), ROOT); 3764 3765 declare( r3, HClass.Void ); 3766 declare( r2, HClass.Void ); 3767 declare( r1, HClass.Void ); 3768 declare( r0, HClass.Void ); 3769 3770 emit ( ROOT, "mov `d0, `s0l", r0, j); 3771 emit ( ROOT, "mov `d0, `s0h", r1, j); 3772 emit ( ROOT, "mov `d0, `s0l", r2, k); 3773 emit ( ROOT, "mov `d0, `s0h", r3, k); 3774 // --- some of these comparison functions are broken! -- 3775 // cmpOp2Func might return a non-broken but *inverted* 3776 // comparison function; we'll fixup the inverted value below. 3777 declareCALL(); 3778 declare( r0, HClass.Int ); // retval from call. 3779 emit2( ROOT, "bl "+nameMap.c_function_name(cmpOp2Func(cmpop)+"df2"), 3780 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0, r1, r2, r3} ); 3781 // don't move these into seperate Instrs; there's an implicit 3782 // dependency on the condition register so we don't want to risk 3783 // reordering them 3784 // --- in addition to converting to a one-bit boolean value, 3785 // we fixup the possibly inverted test here -- 3786 int t=cmpOpFuncInverted(cmpop) ? 0 : 1, f = (t==0) ? 1 : 0; 3787 emit( ROOT, "cmp `s0, #0\n"+ 3788 "moveq `d0, #"+f+"\n"+ 3789 "movne `d0, #"+t, i, r0 ); 3790 return i; 3791 } 3792 } 3793 /* BINOP<i,p>(OR,j,k) */ 3794 if (true 3795 // check expression type 3796 && expArg instanceof harpoon.IR.Tree.BINOP 3797 // check opcode 3798 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.OR 3799 // check operand types 3800 && ( 3801 expArg.type() == Type.POINTER || 3802 ( expArg.type() == Type.INT && ! 3803 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3804 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3805 false ) 3806 // end check operand types 3807 // check left child 3808 // no check needed for ExpId children 3809 // check right child 3810 // no check needed for ExpId children 3811 ){ 3812 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3813 _matched_ = true; 3814 3815 if (_matched_) { // action code! degree: 1 3816 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3817 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3818 3819 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3820 clearDecl(); 3821 declare(i, code.getTreeDerivation(), ROOT); 3822 3823 emit( ROOT, "orr `d0, `s0, `s1", i, j, k ); 3824 return i; 3825 } 3826 } 3827 /* BINOP<l>(OR,j,k) */ 3828 if (true 3829 // check expression type 3830 && expArg instanceof harpoon.IR.Tree.BINOP 3831 // check opcode 3832 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.OR 3833 // check operand types 3834 && ( 3835 expArg.type() == Type.LONG || 3836 false ) 3837 // end check operand types 3838 // check left child 3839 // no check needed for ExpId children 3840 // check right child 3841 // no check needed for ExpId children 3842 ){ 3843 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3844 _matched_ = true; 3845 3846 if (_matched_) { // action code! degree: 1 3847 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3848 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3849 3850 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3851 clearDecl(); 3852 declare(i, code.getTreeDerivation(), ROOT); 3853 3854 3855 emit( ROOT, "orr `d0l, `s0l, `s1l", i, j, k ); 3856 emit( ROOT, "orr `d0h, `s0h, `s1h", i, j, k ); 3857 return i; 3858 } 3859 } 3860 /* BINOP<i,p>(shiftop,j,k) */ 3861 if (true 3862 // check expression type 3863 && expArg instanceof harpoon.IR.Tree.BINOP 3864 // check operand types 3865 && ( 3866 expArg.type() == Type.POINTER || 3867 ( expArg.type() == Type.INT && ! 3868 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 3869 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 3870 false ) 3871 // end check operand types 3872 // check left child 3873 // no check needed for ExpId children 3874 // check right child 3875 // no check needed for ExpId children 3876 ){ 3877 int shiftop = ((harpoon.IR.Tree.BINOP) expArg).op; 3878 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3879 _matched_ = true&& ( isShiftOp(shiftop) ); 3880 3881 if (_matched_) { // action code! degree: 1 3882 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3883 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3884 3885 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3886 clearDecl(); 3887 declare(i, code.getTreeDerivation(), ROOT); 3888 Temp extra = frame.getTempBuilder().makeTemp(new Typed() { 3889 public int type() { return harpoon.IR.Tree.Type.INT; } 3890 public boolean isFloatingPoint() { return false; } 3891 public boolean isDoubleWord() { return false; } 3892 }, inf.tempFactory() ); 3893 declare(extra, HClass.Int); 3894 3895 // java lang spec says shift should occur according to 3896 // 'least significant five bits' of k; StrongARM uses 3897 // least significant *byte*... w/ result 0 if k>31. 3898 emit( ROOT, "and `d0, `s0, #31 @ mask shift", extra, k ); 3899 emit( ROOT, "mov `d0, `s0, "+shiftOp2Str(shiftop)+" `s1", i, j, extra ); 3900 return i; 3901 } 3902 } 3903 /* BINOP<l>(SHL,j,k) */ 3904 if (true 3905 // check expression type 3906 && expArg instanceof harpoon.IR.Tree.BINOP 3907 // check opcode 3908 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.SHL 3909 // check operand types 3910 && ( 3911 expArg.type() == Type.LONG || 3912 false ) 3913 // end check operand types 3914 // check left child 3915 // no check needed for ExpId children 3916 // check right child 3917 // no check needed for ExpId children 3918 ){ 3919 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3920 _matched_ = true; 3921 3922 if (_matched_) { // action code! degree: 1 3923 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3924 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3925 3926 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3927 clearDecl(); 3928 declare(i, code.getTreeDerivation(), ROOT); 3929 3930 declare( r2, HClass.Int ); 3931 declare( r1, HClass.Void ); 3932 declare( r0, HClass.Void ); 3933 3934 emit( ROOT, "mov `d0, `s0l", r0, j ); 3935 emit( ROOT, "mov `d0, `s0h", r1, j ); 3936 emit( ROOT, "and `d0, `s0, #63 @ mask shift ", r2, k ); 3937 declareCALL(); 3938 declare( r0, HClass.Void ); // retval from call. 3939 declare( r1, HClass.Void ); // retval from call. 3940 emit2(ROOT, "bl "+nameMap.c_function_name("__ashldi3"), 3941 new Temp[]{r0,r1,r2,r3,IP,LR},new Temp[]{r0,r1,r2}); 3942 emit( ROOT, "mov `d0l, `s0", i, r0 ); 3943 emit( ROOT, "mov `d0h, `s0", i, r1 ); 3944 return i; 3945 } 3946 } 3947 /* BINOP<l>(SHR,j,k) */ 3948 if (true 3949 // check expression type 3950 && expArg instanceof harpoon.IR.Tree.BINOP 3951 // check opcode 3952 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.SHR 3953 // check operand types 3954 && ( 3955 expArg.type() == Type.LONG || 3956 false ) 3957 // end check operand types 3958 // check left child 3959 // no check needed for ExpId children 3960 // check right child 3961 // no check needed for ExpId children 3962 ){ 3963 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 3964 _matched_ = true; 3965 3966 if (_matched_) { // action code! degree: 1 3967 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 3968 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 3969 3970 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 3971 clearDecl(); 3972 declare(i, code.getTreeDerivation(), ROOT); 3973 3974 declare( r2, HClass.Int ); 3975 declare( r1, HClass.Void ); 3976 declare( r0, HClass.Void ); 3977 3978 emit( ROOT, "mov `d0, `s0l", r0, j ); 3979 emit( ROOT, "mov `d0, `s0h", r1, j ); 3980 emit( ROOT, "and `d0, `s0, #63 @ mask shift ", r2, k ); 3981 declareCALL(); 3982 declare( r0, HClass.Void ); // retval from call. 3983 declare( r1, HClass.Void ); // retval from call. 3984 emit2(ROOT, "bl "+nameMap.c_function_name("__ashrdi3"), 3985 new Temp[]{r0,r1,r2,r3,IP,LR},new Temp[]{r0,r1,r2}); 3986 emit( ROOT, "mov `d0l, `s0", i, r0 ); 3987 emit( ROOT, "mov `d0h, `s0", i, r1 ); 3988 return i; 3989 } 3990 } 3991 /* BINOP<l>(USHR,j,k) */ 3992 if (true 3993 // check expression type 3994 && expArg instanceof harpoon.IR.Tree.BINOP 3995 // check opcode 3996 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.USHR 3997 // check operand types 3998 && ( 3999 expArg.type() == Type.LONG || 4000 false ) 4001 // end check operand types 4002 // check left child 4003 // no check needed for ExpId children 4004 // check right child 4005 // no check needed for ExpId children 4006 ){ 4007 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4008 _matched_ = true; 4009 4010 if (_matched_) { // action code! degree: 1 4011 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4012 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4013 4014 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4015 clearDecl(); 4016 declare(i, code.getTreeDerivation(), ROOT); 4017 4018 declare( r2, HClass.Int ); 4019 declare( r1, HClass.Void ); 4020 declare( r0, HClass.Void ); 4021 4022 emit( ROOT, "mov `d0, `s0l", r0, j ); 4023 emit( ROOT, "mov `d0, `s0h", r1, j ); 4024 emit( ROOT, "and `d0, `s0, #63 @ mask shift ", r2, k ); 4025 declareCALL(); 4026 declare( r0, HClass.Void ); // retval from call. 4027 declare( r1, HClass.Void ); // retval from call. 4028 emit2(ROOT, "bl "+nameMap.c_function_name("__lshrdi3"), 4029 new Temp[]{r0,r1,r2,r3,IP,LR},new Temp[]{r0,r1,r2}); 4030 emit( ROOT, "mov `d0l, `s0", i, r0 ); 4031 emit( ROOT, "mov `d0h, `s0", i, r1 ); 4032 return i; 4033 } 4034 } 4035 /* BINOP<i,p>(XOR,j,k) */ 4036 if (true 4037 // check expression type 4038 && expArg instanceof harpoon.IR.Tree.BINOP 4039 // check opcode 4040 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.XOR 4041 // check operand types 4042 && ( 4043 expArg.type() == Type.POINTER || 4044 ( expArg.type() == Type.INT && ! 4045 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4046 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4047 false ) 4048 // end check operand types 4049 // check left child 4050 // no check needed for ExpId children 4051 // check right child 4052 // no check needed for ExpId children 4053 ){ 4054 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4055 _matched_ = true; 4056 4057 if (_matched_) { // action code! degree: 1 4058 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4059 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4060 4061 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4062 clearDecl(); 4063 declare(i, code.getTreeDerivation(), ROOT); 4064 4065 emit( ROOT, "eor `d0, `s0, `s1", i, j, k ); 4066 return i; 4067 } 4068 } 4069 /* BINOP<l>(XOR,j,k) */ 4070 if (true 4071 // check expression type 4072 && expArg instanceof harpoon.IR.Tree.BINOP 4073 // check opcode 4074 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.XOR 4075 // check operand types 4076 && ( 4077 expArg.type() == Type.LONG || 4078 false ) 4079 // end check operand types 4080 // check left child 4081 // no check needed for ExpId children 4082 // check right child 4083 // no check needed for ExpId children 4084 ){ 4085 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4086 _matched_ = true; 4087 4088 if (_matched_) { // action code! degree: 1 4089 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4090 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4091 4092 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4093 clearDecl(); 4094 declare(i, code.getTreeDerivation(), ROOT); 4095 4096 4097 emit( ROOT, "eor `d0l, `s0l, `s1l", i, j, k ); 4098 emit( ROOT, "eor `d0h, `s0h, `s1h", i, j, k ); 4099 return i; 4100 } 4101 } 4102 /* CONST<l,d>(c) */ 4103 if (true 4104 // check expression type 4105 && expArg instanceof harpoon.IR.Tree.CONST 4106 // check operand types 4107 && ( 4108 expArg.type() == Type.DOUBLE || 4109 expArg.type() == Type.LONG || 4110 false ) 4111 // end check operand types 4112 ){ 4113 Number c = ((harpoon.IR.Tree.CONST) expArg).value; 4114 harpoon.IR.Tree.CONST ROOT = (harpoon.IR.Tree.CONST) expArg; 4115 _matched_ = true; 4116 4117 if (_matched_) { // action code! degree: 1 4118 4119 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4120 clearDecl(); 4121 declare(i, code.getTreeDerivation(), ROOT); 4122 4123 4124 long val = (ROOT.type()==Type.LONG) ? ROOT.value.longValue() 4125 : Double.doubleToLongBits(ROOT.value.doubleValue()); 4126 // DOUBLEs are stored "backwards" on StrongARM. No, I have no clue 4127 // why. They just are. 4128 String lomod = (ROOT.type()==Type.LONG) ? "l" : "h"; 4129 String himod = (ROOT.type()==Type.LONG) ? "h" : "l"; 4130 emit(new Instr( instrFactory, ROOT, 4131 loadConst32("`d0"+lomod, (int)val, "lo("+ROOT.value+")"), 4132 new Temp[]{ i }, null)); 4133 val>>>=32; 4134 emit(new Instr( instrFactory, ROOT, 4135 loadConst32("`d0"+himod, (int)val, "hi("+ROOT.value+")"), 4136 new Temp[]{ i }, null)); 4137 return i; 4138 } 4139 } 4140 /* CONST<i,f>(c) */ 4141 if (true 4142 // check expression type 4143 && expArg instanceof harpoon.IR.Tree.CONST 4144 // check operand types 4145 && ( 4146 expArg.type() == Type.FLOAT || 4147 ( expArg.type() == Type.INT && ! 4148 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4149 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4150 false ) 4151 // end check operand types 4152 ){ 4153 Number c = ((harpoon.IR.Tree.CONST) expArg).value; 4154 harpoon.IR.Tree.CONST ROOT = (harpoon.IR.Tree.CONST) expArg; 4155 _matched_ = true; 4156 4157 if (_matched_) { // action code! degree: 1 4158 4159 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4160 clearDecl(); 4161 declare(i, code.getTreeDerivation(), ROOT); 4162 4163 4164 int val = (ROOT.type()==Type.INT) ? ROOT.value.intValue() 4165 : Float.floatToIntBits(ROOT.value.floatValue()); 4166 emit(new Instr( instrFactory, ROOT, 4167 loadConst32("`d0", val, ROOT.value.toString()), 4168 new Temp[]{ i }, null)); 4169 return i; 4170 } 4171 } 4172 /* CONST<p>(c) */ 4173 if (true 4174 // check expression type 4175 && expArg instanceof harpoon.IR.Tree.CONST 4176 // check operand types 4177 && ( 4178 expArg.type() == Type.POINTER || 4179 false ) 4180 // end check operand types 4181 ){ 4182 Number c = ((harpoon.IR.Tree.CONST) expArg).value; 4183 harpoon.IR.Tree.CONST ROOT = (harpoon.IR.Tree.CONST) expArg; 4184 _matched_ = true; 4185 4186 if (_matched_) { // action code! degree: 1 4187 4188 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4189 clearDecl(); 4190 declare(i, code.getTreeDerivation(), ROOT); 4191 4192 // the only CONST of type Pointer we should see is NULL 4193 assert c==null; 4194 emit(new Instr( instrFactory, ROOT, 4195 "mov `d0, #0 @ null", new Temp[]{ i }, null)); 4196 return i; 4197 } 4198 } 4199 /* BINOP<i,p>(MUL,j,k) */ 4200 if (true 4201 // check expression type 4202 && expArg instanceof harpoon.IR.Tree.BINOP 4203 // check opcode 4204 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.MUL 4205 // check operand types 4206 && ( 4207 expArg.type() == Type.POINTER || 4208 ( expArg.type() == Type.INT && ! 4209 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4210 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4211 false ) 4212 // end check operand types 4213 // check left child 4214 // no check needed for ExpId children 4215 // check right child 4216 // no check needed for ExpId children 4217 ){ 4218 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4219 _matched_ = true; 4220 4221 if (_matched_) { // action code! degree: 1 4222 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4223 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4224 4225 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4226 clearDecl(); 4227 declare(i, code.getTreeDerivation(), ROOT); 4228 4229 4230 emit( ROOT, "mul `d0, `s0, `s1", i, j, k ); 4231 // `d0 and `s0 can't be same register on ARM, so we insert a 4232 // dummy use of `s0 following the mul to keep it live. 4233 emit(new Instr( instrFactory, ROOT, "@ dummy", 4234 null, new Temp[] { j })); 4235 return i; 4236 } 4237 } 4238 /* BINOP<l>(MUL,j,k) */ 4239 if (true 4240 // check expression type 4241 && expArg instanceof harpoon.IR.Tree.BINOP 4242 // check opcode 4243 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.MUL 4244 // check operand types 4245 && ( 4246 expArg.type() == Type.LONG || 4247 false ) 4248 // end check operand types 4249 // check left child 4250 // no check needed for ExpId children 4251 // check right child 4252 // no check needed for ExpId children 4253 ){ 4254 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4255 _matched_ = true; 4256 4257 if (_matched_) { // action code! degree: 1 4258 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4259 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4260 4261 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4262 clearDecl(); 4263 declare(i, code.getTreeDerivation(), ROOT); 4264 4265 // TODO: use the SMULL instruction instead 4266 declare( r3, HClass.Void ); 4267 declare( r2, HClass.Void ); 4268 declare( r1, HClass.Void ); 4269 declare( r0, HClass.Void ); 4270 4271 emit( ROOT, "mov `d0, `s0l", r2, k ); 4272 emit( ROOT, "mov `d0, `s0h", r3, k ); 4273 emit( ROOT, "mov `d0, `s0l", r0, j ); 4274 emit( ROOT, "mov `d0, `s0h", r1, j ); 4275 declareCALL(); 4276 declare( r0, HClass.Void ); // retval from call. 4277 declare( r1, HClass.Void ); // retval from call. 4278 emit2(ROOT, "bl "+nameMap.c_function_name("__muldi3"), 4279 // uses & stomps on these registers: 4280 new Temp[]{r0,r1,r2,r3,IP,LR}, new Temp[]{r0,r1,r2,r3}); 4281 emit( ROOT, "mov `d0l, `s0", i, r0 ); 4282 emit( ROOT, "mov `d0h, `s0", i, r1 ); 4283 return i; 4284 } 4285 } 4286 /* BINOP<f>(MUL,j,k) */ 4287 if (true 4288 // check expression type 4289 && expArg instanceof harpoon.IR.Tree.BINOP 4290 // check opcode 4291 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.MUL 4292 // check operand types 4293 && ( 4294 expArg.type() == Type.FLOAT || 4295 false ) 4296 // end check operand types 4297 // check left child 4298 // no check needed for ExpId children 4299 // check right child 4300 // no check needed for ExpId children 4301 ){ 4302 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4303 _matched_ = true; 4304 4305 if (_matched_) { // action code! degree: 1 4306 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4307 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4308 4309 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4310 clearDecl(); 4311 declare(i, code.getTreeDerivation(), ROOT); 4312 4313 declare( r1, HClass.Float ); 4314 declare( r0, HClass.Float ); 4315 4316 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 4317 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 4318 declareCALL(); 4319 declare( r0, HClass.Float ); // retval from call. 4320 emit2( ROOT, "bl "+nameMap.c_function_name("__mulsf3"), 4321 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1}); 4322 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 4323 return i; 4324 } 4325 } 4326 /* BINOP<d>(MUL,j,k) */ 4327 if (true 4328 // check expression type 4329 && expArg instanceof harpoon.IR.Tree.BINOP 4330 // check opcode 4331 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.MUL 4332 // check operand types 4333 && ( 4334 expArg.type() == Type.DOUBLE || 4335 false ) 4336 // end check operand types 4337 // check left child 4338 // no check needed for ExpId children 4339 // check right child 4340 // no check needed for ExpId children 4341 ){ 4342 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4343 _matched_ = true; 4344 4345 if (_matched_) { // action code! degree: 1 4346 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4347 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4348 4349 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4350 clearDecl(); 4351 declare(i, code.getTreeDerivation(), ROOT); 4352 4353 declare( r3, HClass.Void ); 4354 declare( r2, HClass.Void ); 4355 declare( r1, HClass.Void ); 4356 declare( r0, HClass.Void ); 4357 4358 emit( ROOT, "mov `d0, `s0l", r2, k ); 4359 emit( ROOT, "mov `d0, `s0h", r3, k ); 4360 emit( ROOT, "mov `d0, `s0l", r0, j ); 4361 emit( ROOT, "mov `d0, `s0h", r1, j ); 4362 declareCALL(); 4363 declare( r0, HClass.Void ); // retval from call. 4364 declare( r1, HClass.Void ); // retval from call. 4365 emit2(ROOT, "bl "+nameMap.c_function_name("__muldf3"), 4366 // uses & stomps on these registers: 4367 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 4368 emit( ROOT, "mov `d0l, `s0", i, r0 ); 4369 emit( ROOT, "mov `d0h, `s0", i, r1 ); 4370 return i; 4371 } 4372 } 4373 /* BINOP<i,p>(DIV,j,k) */ 4374 if (true 4375 // check expression type 4376 && expArg instanceof harpoon.IR.Tree.BINOP 4377 // check opcode 4378 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.DIV 4379 // check operand types 4380 && ( 4381 expArg.type() == Type.POINTER || 4382 ( expArg.type() == Type.INT && ! 4383 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4384 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4385 false ) 4386 // end check operand types 4387 // check left child 4388 // no check needed for ExpId children 4389 // check right child 4390 // no check needed for ExpId children 4391 ){ 4392 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4393 _matched_ = true; 4394 4395 if (_matched_) { // action code! degree: 1 4396 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4397 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4398 4399 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4400 clearDecl(); 4401 declare(i, code.getTreeDerivation(), ROOT); 4402 4403 4404 declare( r1, code.getTreeDerivation(), ROOT.getRight()); 4405 declare( r0, code.getTreeDerivation(), ROOT.getLeft()); 4406 4407 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 4408 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 4409 declareCALL(); 4410 declare( r0, HClass.Int ); // retval from call. 4411 emit2( ROOT, "bl "+nameMap.c_function_name("__divsi3"), 4412 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1}); 4413 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 4414 return i; 4415 } 4416 } 4417 /* BINOP<l>(DIV,j,k) */ 4418 if (true 4419 // check expression type 4420 && expArg instanceof harpoon.IR.Tree.BINOP 4421 // check opcode 4422 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.DIV 4423 // check operand types 4424 && ( 4425 expArg.type() == Type.LONG || 4426 false ) 4427 // end check operand types 4428 // check left child 4429 // no check needed for ExpId children 4430 // check right child 4431 // no check needed for ExpId children 4432 ){ 4433 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4434 _matched_ = true; 4435 4436 if (_matched_) { // action code! degree: 1 4437 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4438 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4439 4440 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4441 clearDecl(); 4442 declare(i, code.getTreeDerivation(), ROOT); 4443 4444 4445 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 4446 declare( r2, HClass.Void ); declare( r3, HClass.Void ); 4447 emit( ROOT, "mov `d0, `s0l", r2, k ); 4448 emit( ROOT, "mov `d0, `s0h", r3, k ); 4449 emit( ROOT, "mov `d0, `s0l", r0, j ); 4450 emit( ROOT, "mov `d0, `s0h", r1, j ); 4451 declareCALL(); 4452 declare( r0, HClass.Void ); // retval from call. 4453 declare( r1, HClass.Void ); // retval from call. 4454 emit2(ROOT, "bl "+nameMap.c_function_name("__divdi3"), 4455 // uses and stomps on these registers: 4456 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 4457 emit( ROOT, "mov `d0l, `s0", i, r0 ); 4458 emit( ROOT, "mov `d0h, `s0", i, r1 ); 4459 return i; 4460 } 4461 } 4462 /* BINOP<f>(DIV,j,k) */ 4463 if (true 4464 // check expression type 4465 && expArg instanceof harpoon.IR.Tree.BINOP 4466 // check opcode 4467 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.DIV 4468 // check operand types 4469 && ( 4470 expArg.type() == Type.FLOAT || 4471 false ) 4472 // end check operand types 4473 // check left child 4474 // no check needed for ExpId children 4475 // check right child 4476 // no check needed for ExpId children 4477 ){ 4478 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4479 _matched_ = true; 4480 4481 if (_matched_) { // action code! degree: 1 4482 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4483 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4484 4485 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4486 clearDecl(); 4487 declare(i, code.getTreeDerivation(), ROOT); 4488 4489 4490 declare( r0, HClass.Float ); declare( r1, HClass.Float ); 4491 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 4492 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 4493 declareCALL(); 4494 declare( r0, HClass.Float ); // retval from call. 4495 emit2( ROOT, "bl "+nameMap.c_function_name("__divsf3"), 4496 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1}); 4497 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 4498 return i; 4499 } 4500 } 4501 /* BINOP<d>(DIV,j,k) */ 4502 if (true 4503 // check expression type 4504 && expArg instanceof harpoon.IR.Tree.BINOP 4505 // check opcode 4506 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.DIV 4507 // check operand types 4508 && ( 4509 expArg.type() == Type.DOUBLE || 4510 false ) 4511 // end check operand types 4512 // check left child 4513 // no check needed for ExpId children 4514 // check right child 4515 // no check needed for ExpId children 4516 ){ 4517 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4518 _matched_ = true; 4519 4520 if (_matched_) { // action code! degree: 1 4521 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4522 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4523 4524 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4525 clearDecl(); 4526 declare(i, code.getTreeDerivation(), ROOT); 4527 4528 4529 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 4530 declare( r2, HClass.Void ); declare( r3, HClass.Void ); 4531 emit( ROOT, "mov `d0, `s0l", r2, k ); 4532 emit( ROOT, "mov `d0, `s0h", r3, k ); 4533 emit( ROOT, "mov `d0, `s0l", r0, j ); 4534 emit( ROOT, "mov `d0, `s0h", r1, j ); 4535 declareCALL(); 4536 declare( r0, HClass.Void ); // retval from call. 4537 declare( r1, HClass.Void ); // retval from call. 4538 emit2(ROOT, "bl "+nameMap.c_function_name("__divdf3"), 4539 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 4540 emit( ROOT, "mov `d0l, `s0", i, r0 ); 4541 emit( ROOT, "mov `d0h, `s0", i, r1 ); 4542 return i; 4543 } 4544 } 4545 /* BINOP<i>(REM,j,k) */ 4546 if (true 4547 // check expression type 4548 && expArg instanceof harpoon.IR.Tree.BINOP 4549 // check opcode 4550 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.REM 4551 // check operand types 4552 && ( 4553 ( expArg.type() == Type.INT && ! 4554 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4555 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4556 false ) 4557 // end check operand types 4558 // check left child 4559 // no check needed for ExpId children 4560 // check right child 4561 // no check needed for ExpId children 4562 ){ 4563 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4564 _matched_ = true; 4565 4566 if (_matched_) { // action code! degree: 1 4567 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4568 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4569 4570 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4571 clearDecl(); 4572 declare(i, code.getTreeDerivation(), ROOT); 4573 4574 declare( r1, code.getTreeDerivation(), ROOT.getRight()); 4575 declare( r0, code.getTreeDerivation(), ROOT.getLeft()); 4576 4577 // ___mod has been verified to be consistent w/ the def of % in the JLS 4578 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 4579 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 4580 declareCALL(); 4581 declare( r0, HClass.Int ); // retval from call. 4582 emit2( ROOT, "bl "+nameMap.c_function_name("__modsi3"), 4583 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1}); 4584 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 4585 return i; 4586 } 4587 } 4588 /* BINOP<l>(REM,j,k) */ 4589 if (true 4590 // check expression type 4591 && expArg instanceof harpoon.IR.Tree.BINOP 4592 // check opcode 4593 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.REM 4594 // check operand types 4595 && ( 4596 expArg.type() == Type.LONG || 4597 false ) 4598 // end check operand types 4599 // check left child 4600 // no check needed for ExpId children 4601 // check right child 4602 // no check needed for ExpId children 4603 ){ 4604 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4605 _matched_ = true; 4606 4607 if (_matched_) { // action code! degree: 1 4608 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4609 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4610 4611 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4612 clearDecl(); 4613 declare(i, code.getTreeDerivation(), ROOT); 4614 4615 // ___mod has been verified to be consistent w/ the def of % in the JLS 4616 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 4617 declare( r2, HClass.Void ); declare( r3, HClass.Void ); 4618 emit( ROOT, "mov `d0, `s0l", r2, k ); 4619 emit( ROOT, "mov `d0, `s0h", r3, k ); 4620 emit( ROOT, "mov `d0, `s0l", r0, j ); 4621 emit( ROOT, "mov `d0, `s0h", r1, j ); 4622 declareCALL(); 4623 declare( r0, HClass.Void ); // retval from call. 4624 declare( r1, HClass.Void ); // retval from call. 4625 emit2(ROOT, "bl "+nameMap.c_function_name("__moddi3"), 4626 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 4627 emit( ROOT, "mov `d0l, `s0", i, r0 ); 4628 emit( ROOT, "mov `d0h, `s0", i, r1 ); 4629 return i; 4630 } 4631 } 4632 /* BINOP<f>(REM,j,k) */ 4633 if (true 4634 // check expression type 4635 && expArg instanceof harpoon.IR.Tree.BINOP 4636 // check opcode 4637 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.REM 4638 // check operand types 4639 && ( 4640 expArg.type() == Type.FLOAT || 4641 false ) 4642 // end check operand types 4643 // check left child 4644 // no check needed for ExpId children 4645 // check right child 4646 // no check needed for ExpId children 4647 ){ 4648 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4649 _matched_ = true; 4650 4651 if (_matched_) { // action code! degree: 1 4652 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4653 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4654 4655 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4656 clearDecl(); 4657 declare(i, code.getTreeDerivation(), ROOT); 4658 4659 // XXX: verify that fmodf is consistent with definition of % in JLS 4660 declare( r0, HClass.Float ); declare( r1, HClass.Float ); 4661 emitMOVE( ROOT, "mov `d0, `s0", r1, k ); 4662 emitMOVE( ROOT, "mov `d0, `s0", r0, j ); 4663 declareCALL(); 4664 declare( r0, HClass.Float ); // retval from call. 4665 emit2( ROOT, "bl "+nameMap.c_function_name("fmodf"), 4666 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1}); 4667 emitMoveFromNativeFloatRetVal(ROOT, i); 4668 return i; 4669 } 4670 } 4671 /* BINOP<d>(REM,j,k) */ 4672 if (true 4673 // check expression type 4674 && expArg instanceof harpoon.IR.Tree.BINOP 4675 // check opcode 4676 && ((harpoon.IR.Tree.BINOP)expArg).op == harpoon.IR.Tree.Bop.REM 4677 // check operand types 4678 && ( 4679 expArg.type() == Type.DOUBLE || 4680 false ) 4681 // end check operand types 4682 // check left child 4683 // no check needed for ExpId children 4684 // check right child 4685 // no check needed for ExpId children 4686 ){ 4687 harpoon.IR.Tree.BINOP ROOT = (harpoon.IR.Tree.BINOP) expArg; 4688 _matched_ = true; 4689 4690 if (_matched_) { // action code! degree: 1 4691 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)expArg).getLeft()); 4692 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)expArg).getRight()); 4693 4694 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4695 clearDecl(); 4696 declare(i, code.getTreeDerivation(), ROOT); 4697 4698 // XXX: verify that fmod is consistent with definition of % in JLS 4699 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 4700 declare( r2, HClass.Void ); declare( r3, HClass.Void ); 4701 emit( ROOT, "mov `d0, `s0l", r2, k ); 4702 emit( ROOT, "mov `d0, `s0h", r3, k ); 4703 emit( ROOT, "mov `d0, `s0l", r0, j ); 4704 emit( ROOT, "mov `d0, `s0h", r1, j ); 4705 declareCALL(); 4706 declare( r0, HClass.Void ); // retval from call. 4707 declare( r1, HClass.Void ); // retval from call. 4708 emit2(ROOT, "bl "+nameMap.c_function_name("fmod"), 4709 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1,r2,r3}); 4710 emitMoveFromNativeDoubleRetVal(ROOT, i); 4711 return i; 4712 } 4713 } 4714 /* MEM<s:8>(e) */ 4715 if (true 4716 // check expression type 4717 && expArg instanceof harpoon.IR.Tree.MEM 4718 // check operand types 4719 && ( 4720 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 4721 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 4722 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 4723 false) : ( 4724 false) ) ) || 4725 false ) 4726 // end check operand types 4727 // check child 4728 // no check needed for ExpId children 4729 ){ 4730 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 4731 _matched_ = true; 4732 4733 if (_matched_) { // action code! degree: 1 4734 harpoon.Temp.Temp e = munchExp(((harpoon.IR.Tree.MEM)expArg).getExp()); 4735 4736 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4737 clearDecl(); 4738 declare(i, code.getTreeDerivation(), ROOT); 4739 /* hack. ARMv4 has a special instr for this. */ 4740 4741 emit(new InstrMEM(instrFactory, ROOT, "ldrb `d0, [`s0] @ load signed byte", 4742 new Temp[]{ i }, new Temp[]{ e })); 4743 emit( ROOT, "mov `d0, `s0, asl #24", i, i); 4744 emit( ROOT, "mov `d0, `s0, asr #24", i, i); 4745 return i; 4746 } 4747 } 4748 /* MEM<u:16,s:16>(e) */ 4749 if (true 4750 // check expression type 4751 && expArg instanceof harpoon.IR.Tree.MEM 4752 // check operand types 4753 && ( 4754 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 4755 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 4756 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==16 || 4757 false) : ( 4758 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==16 || 4759 false) ) ) || 4760 false ) 4761 // end check operand types 4762 // check child 4763 // no check needed for ExpId children 4764 ){ 4765 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 4766 _matched_ = true; 4767 4768 if (_matched_) { // action code! degree: 1 4769 harpoon.Temp.Temp e = munchExp(((harpoon.IR.Tree.MEM)expArg).getExp()); 4770 4771 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4772 clearDecl(); 4773 declare(i, code.getTreeDerivation(), ROOT); 4774 /* hack. ARMv4 has a special instr for this. */ 4775 4776 emit(new InstrMEM(instrFactory, ROOT, "ldr `d0, [`s0] @ load halfword", 4777 new Temp[]{ i }, new Temp[]{ e })); 4778 emit( ROOT, "mov `d0, `s0, asl #16", i, i); 4779 if (ROOT.signed()) 4780 emit( ROOT, "mov `d0, `s0, asr #16", i, i); 4781 else 4782 emit( ROOT, "mov `d0, `s0, lsr #16", i, i); 4783 return i; 4784 } 4785 } 4786 /* MEM<i,f,p,u:8>(e) */ 4787 if (true 4788 // check expression type 4789 && expArg instanceof harpoon.IR.Tree.MEM 4790 // check operand types 4791 && ( 4792 expArg.type() == Type.FLOAT || 4793 expArg.type() == Type.POINTER || 4794 ( expArg.type() == Type.INT && ! 4795 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4796 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4797 (((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall() && ( 4798 ((harpoon.IR.Tree.PreciselyTyped)expArg).signed() ? ( 4799 false) : ( 4800 ((harpoon.IR.Tree.PreciselyTyped)expArg).bitwidth()==8 || 4801 false) ) ) || 4802 false ) 4803 // end check operand types 4804 // check child 4805 // no check needed for ExpId children 4806 ){ 4807 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 4808 _matched_ = true; 4809 4810 if (_matched_) { // action code! degree: 1 4811 harpoon.Temp.Temp e = munchExp(((harpoon.IR.Tree.MEM)expArg).getExp()); 4812 4813 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4814 clearDecl(); 4815 declare(i, code.getTreeDerivation(), ROOT); 4816 // addressing mode 2 4817 4818 String suffix=""; 4819 if (ROOT.isSmall() && ROOT.signed()) suffix+="s"; 4820 if (ROOT.isSmall() && ROOT.bitwidth()==8) suffix+="b"; 4821 emit(new InstrMEM(instrFactory, ROOT, 4822 "ldr"+suffix+" `d0, [`s0]", 4823 new Temp[]{ i }, new Temp[]{ e })); 4824 return i; 4825 } 4826 } 4827 /* MEM<l,d>(e) */ 4828 if (true 4829 // check expression type 4830 && expArg instanceof harpoon.IR.Tree.MEM 4831 // check operand types 4832 && ( 4833 expArg.type() == Type.DOUBLE || 4834 expArg.type() == Type.LONG || 4835 false ) 4836 // end check operand types 4837 // check child 4838 // no check needed for ExpId children 4839 ){ 4840 harpoon.IR.Tree.MEM ROOT = (harpoon.IR.Tree.MEM) expArg; 4841 _matched_ = true; 4842 4843 if (_matched_) { // action code! degree: 1 4844 harpoon.Temp.Temp e = munchExp(((harpoon.IR.Tree.MEM)expArg).getExp()); 4845 4846 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4847 clearDecl(); 4848 declare(i, code.getTreeDerivation(), ROOT); 4849 4850 4851 emit(new InstrMEM(instrFactory, ROOT, 4852 "ldr `d0l, [`s0]", 4853 new Temp[]{ i }, new Temp[]{ e })); 4854 emit(new InstrMEM(instrFactory, ROOT, 4855 "ldr `d0h, [`s0, #4]", 4856 new Temp[]{ i }, new Temp[]{ e })); 4857 return i; 4858 } 4859 } 4860 /* NAME(id) */ 4861 if (true 4862 // check expression type 4863 && expArg instanceof harpoon.IR.Tree.NAME 4864 ){ 4865 harpoon.Temp.Label id = ((harpoon.IR.Tree.NAME)expArg).label; 4866 harpoon.IR.Tree.NAME ROOT = (harpoon.IR.Tree.NAME) expArg; 4867 _matched_ = true; 4868 4869 if (_matched_) { // action code! degree: 1 4870 4871 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4872 clearDecl(); 4873 declare(i, code.getTreeDerivation(), ROOT); 4874 4875 // produces a pointer 4876 4877 Label target = new Label(); // new Label("2"+id); 4878 Instr i2 = new Instr(instrFactory, ROOT, 4879 "ldr `d0, 1f\n" + "b 2f", 4880 new Temp[]{ i }, null, false, 4881 Arrays.asList(new Label[]{ target })) { 4882 public boolean hasModifiableTargets() { 4883 return false; 4884 }}; 4885 4886 emit(i2); 4887 4888 assert i2.succC().size() == 1 : "linear control flow"; 4889 4890 // these may need to be included in the previous instr to preserve 4891 // ordering semantics, but for now this way they indent properly 4892 emitNoFallLABEL( ROOT, "1:", new Label()); 4893 emitNoFallDIRECTIVE( ROOT, "\t.word " + id); 4894 // FSK: changed above to NoFall emits so that this is not treated 4895 // as the start of a new basic block. 4896 i2 = emitLABEL( ROOT, "2:", target); 4897 4898 assert i2.predC().size() == 1 : "> one predecessor " /* + i2.predC() */; 4899 4900 return i; 4901 } 4902 } 4903 /* TEMP<i,l,f,d,p>(t) */ 4904 if (true 4905 // check expression type 4906 && expArg instanceof harpoon.IR.Tree.TEMP 4907 // check operand types 4908 && ( 4909 expArg.type() == Type.DOUBLE || 4910 expArg.type() == Type.FLOAT || 4911 expArg.type() == Type.LONG || 4912 expArg.type() == Type.POINTER || 4913 ( expArg.type() == Type.INT && ! 4914 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4915 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4916 false ) 4917 // end check operand types 4918 ){ 4919 harpoon.Temp.Temp t = makeTemp((harpoon.IR.Tree.TEMP)expArg, inf.tempFactory()); 4920 harpoon.IR.Tree.TEMP ROOT = (harpoon.IR.Tree.TEMP) expArg; 4921 _matched_ = true; 4922 4923 if (_matched_) { // action code! degree: 1 4924 4925 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4926 clearDecl(); 4927 declare(i, code.getTreeDerivation(), ROOT); 4928 i=t; /* this case is basically handled entirely by the CGG */ return i; 4929 } 4930 } 4931 /* UNOP<i,l,f,d,p>(I2B,arg) */ 4932 if (true 4933 // check expression type 4934 && expArg instanceof harpoon.IR.Tree.UNOP 4935 // check opcode 4936 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.I2B 4937 // check operand types 4938 && ( 4939 expArg.type() == Type.DOUBLE || 4940 expArg.type() == Type.FLOAT || 4941 expArg.type() == Type.LONG || 4942 expArg.type() == Type.POINTER || 4943 ( expArg.type() == Type.INT && ! 4944 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4945 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4946 false ) 4947 // end check operand types 4948 // check child 4949 // no check needed for ExpId children 4950 ){ 4951 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 4952 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 4953 4954 if (_matched_) { // action code! degree: 1 4955 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 4956 4957 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4958 clearDecl(); 4959 declare(i, code.getTreeDerivation(), ROOT); 4960 4961 4962 emit( ROOT, "mov `d0, `s0, asl #24", i, arg); 4963 emit( ROOT, "mov `d0, `s0, asr #24", i, i); 4964 return i; 4965 } 4966 } 4967 /* UNOP<i,l,f,d,p>(I2C,arg) */ 4968 if (true 4969 // check expression type 4970 && expArg instanceof harpoon.IR.Tree.UNOP 4971 // check opcode 4972 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.I2C 4973 // check operand types 4974 && ( 4975 expArg.type() == Type.DOUBLE || 4976 expArg.type() == Type.FLOAT || 4977 expArg.type() == Type.LONG || 4978 expArg.type() == Type.POINTER || 4979 ( expArg.type() == Type.INT && ! 4980 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 4981 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 4982 false ) 4983 // end check operand types 4984 // check child 4985 // no check needed for ExpId children 4986 ){ 4987 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 4988 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 4989 4990 if (_matched_) { // action code! degree: 1 4991 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 4992 4993 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 4994 clearDecl(); 4995 declare(i, code.getTreeDerivation(), ROOT); 4996 4997 4998 emit( ROOT, "mov `d0, `s0, asl #16", i, arg); 4999 emit( ROOT, "mov `d0, `s0, lsr #16", i, i); 5000 return i; 5001 } 5002 } 5003 /* UNOP<i,l,f,d,p>(I2S,arg) */ 5004 if (true 5005 // check expression type 5006 && expArg instanceof harpoon.IR.Tree.UNOP 5007 // check opcode 5008 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.I2S 5009 // check operand types 5010 && ( 5011 expArg.type() == Type.DOUBLE || 5012 expArg.type() == Type.FLOAT || 5013 expArg.type() == Type.LONG || 5014 expArg.type() == Type.POINTER || 5015 ( expArg.type() == Type.INT && ! 5016 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5017 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5018 false ) 5019 // end check operand types 5020 // check child 5021 // no check needed for ExpId children 5022 ){ 5023 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5024 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 5025 5026 if (_matched_) { // action code! degree: 1 5027 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5028 5029 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5030 clearDecl(); 5031 declare(i, code.getTreeDerivation(), ROOT); 5032 5033 5034 emit( ROOT, "mov `d0, `s0, asl #16", i, arg); 5035 emit( ROOT, "mov `d0, `s0, asr #16", i, i); 5036 return i; 5037 } 5038 } 5039 /* UNOP<i,l,f,d,p>(_2D,arg) */ 5040 if (true 5041 // check expression type 5042 && expArg instanceof harpoon.IR.Tree.UNOP 5043 // check opcode 5044 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2D 5045 // check operand types 5046 && ( 5047 expArg.type() == Type.DOUBLE || 5048 expArg.type() == Type.FLOAT || 5049 expArg.type() == Type.LONG || 5050 expArg.type() == Type.POINTER || 5051 ( expArg.type() == Type.INT && ! 5052 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5053 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5054 false ) 5055 // end check operand types 5056 // check child 5057 // no check needed for ExpId children 5058 ){ 5059 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5060 _matched_ = true&& ( ROOT.operandType()==Type.LONG ); 5061 5062 if (_matched_) { // action code! degree: 1 5063 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5064 5065 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5066 clearDecl(); 5067 declare(i, code.getTreeDerivation(), ROOT); 5068 5069 5070 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5071 emit( ROOT, "mov `d0, `s0l", r0, arg ); 5072 emit( ROOT, "mov `d0, `s0h", r1, arg ); 5073 declareCALL(); declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5074 emit2(ROOT, "bl "+nameMap.c_function_name("__floatdidf"), 5075 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 5076 emitMoveFromNativeDoubleRetVal(ROOT, i);//func in libgcc.a, hence fp retval 5077 return i; 5078 } 5079 } 5080 /* UNOP<i,l,f,d,p>(_2D,arg) */ 5081 if (true 5082 // check expression type 5083 && expArg instanceof harpoon.IR.Tree.UNOP 5084 // check opcode 5085 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2D 5086 // check operand types 5087 && ( 5088 expArg.type() == Type.DOUBLE || 5089 expArg.type() == Type.FLOAT || 5090 expArg.type() == Type.LONG || 5091 expArg.type() == Type.POINTER || 5092 ( expArg.type() == Type.INT && ! 5093 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5094 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5095 false ) 5096 // end check operand types 5097 // check child 5098 // no check needed for ExpId children 5099 ){ 5100 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5101 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 5102 5103 if (_matched_) { // action code! degree: 1 5104 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5105 5106 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5107 clearDecl(); 5108 declare(i, code.getTreeDerivation(), ROOT); 5109 5110 5111 declare( r0, HClass.Int ); 5112 emitMOVE( ROOT, "mov `d0, `s0", r0, arg ); 5113 declareCALL(); declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5114 emit2(ROOT, "bl "+nameMap.c_function_name("__floatsidf"), 5115 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0} ); 5116 emit( ROOT, "mov `d0l, `s0", i, r0 ); 5117 emit( ROOT, "mov `d0h, `s0", i, r1 ); 5118 return i; 5119 } 5120 } 5121 /* UNOP<i,l,f,d,p>(_2D,arg) */ 5122 if (true 5123 // check expression type 5124 && expArg instanceof harpoon.IR.Tree.UNOP 5125 // check opcode 5126 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2D 5127 // check operand types 5128 && ( 5129 expArg.type() == Type.DOUBLE || 5130 expArg.type() == Type.FLOAT || 5131 expArg.type() == Type.LONG || 5132 expArg.type() == Type.POINTER || 5133 ( expArg.type() == Type.INT && ! 5134 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5135 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5136 false ) 5137 // end check operand types 5138 // check child 5139 // no check needed for ExpId children 5140 ){ 5141 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5142 _matched_ = true&& ( ROOT.operandType()==Type.FLOAT ); 5143 5144 if (_matched_) { // action code! degree: 1 5145 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5146 5147 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5148 clearDecl(); 5149 declare(i, code.getTreeDerivation(), ROOT); 5150 5151 5152 declare( r0, HClass.Float ); 5153 emitMOVE( ROOT, "mov `d0, `s0", r0, arg ); 5154 declareCALL(); declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5155 emit2(ROOT, "bl "+nameMap.c_function_name("__extendsfdf2"), 5156 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0} ); 5157 emit( ROOT, "mov `d0l, `s0", i, r0 ); 5158 emit( ROOT, "mov `d0h, `s0", i, r1 ); 5159 5160 return i; 5161 } 5162 } 5163 /* UNOP<i,l,f,d,p>(_2F,arg) */ 5164 if (true 5165 // check expression type 5166 && expArg instanceof harpoon.IR.Tree.UNOP 5167 // check opcode 5168 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2F 5169 // check operand types 5170 && ( 5171 expArg.type() == Type.DOUBLE || 5172 expArg.type() == Type.FLOAT || 5173 expArg.type() == Type.LONG || 5174 expArg.type() == Type.POINTER || 5175 ( expArg.type() == Type.INT && ! 5176 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5177 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5178 false ) 5179 // end check operand types 5180 // check child 5181 // no check needed for ExpId children 5182 ){ 5183 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5184 _matched_ = true&& ( ROOT.operandType()==Type.LONG ); 5185 5186 if (_matched_) { // action code! degree: 1 5187 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5188 5189 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5190 clearDecl(); 5191 declare(i, code.getTreeDerivation(), ROOT); 5192 5193 5194 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5195 emit( ROOT, "mov `d0, `s0l", r0, arg ); 5196 emit( ROOT, "mov `d0, `s0h", r1, arg ); 5197 declareCALL(); declare( r0, HClass.Float ); 5198 emit2(ROOT, "bl "+nameMap.c_function_name("__floatdisf"), 5199 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 5200 emitMoveFromNativeFloatRetVal(ROOT, i);//func in libgcc.a, hence fp retval 5201 return i; 5202 } 5203 } 5204 /* UNOP<i,l,f,d,p>(_2F,arg) */ 5205 if (true 5206 // check expression type 5207 && expArg instanceof harpoon.IR.Tree.UNOP 5208 // check opcode 5209 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2F 5210 // check operand types 5211 && ( 5212 expArg.type() == Type.DOUBLE || 5213 expArg.type() == Type.FLOAT || 5214 expArg.type() == Type.LONG || 5215 expArg.type() == Type.POINTER || 5216 ( expArg.type() == Type.INT && ! 5217 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5218 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5219 false ) 5220 // end check operand types 5221 // check child 5222 // no check needed for ExpId children 5223 ){ 5224 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5225 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 5226 5227 if (_matched_) { // action code! degree: 1 5228 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5229 5230 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5231 clearDecl(); 5232 declare(i, code.getTreeDerivation(), ROOT); 5233 5234 5235 declare( r0, HClass.Int ); 5236 emitMOVE( ROOT, "mov `d0, `s0", r0, arg ); 5237 declareCALL(); declare( r0, HClass.Float ); 5238 emit2( ROOT, "bl "+nameMap.c_function_name("__floatsisf"), 5239 new Temp[] {r0,r1,r2,r3,IP,LR},new Temp[] {r0} ); 5240 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 5241 return i; 5242 } 5243 } 5244 /* UNOP<i,l,f,d,p>(_2F,arg) */ 5245 if (true 5246 // check expression type 5247 && expArg instanceof harpoon.IR.Tree.UNOP 5248 // check opcode 5249 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2F 5250 // check operand types 5251 && ( 5252 expArg.type() == Type.DOUBLE || 5253 expArg.type() == Type.FLOAT || 5254 expArg.type() == Type.LONG || 5255 expArg.type() == Type.POINTER || 5256 ( expArg.type() == Type.INT && ! 5257 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5258 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5259 false ) 5260 // end check operand types 5261 // check child 5262 // no check needed for ExpId children 5263 ){ 5264 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5265 _matched_ = true&& ( ROOT.operandType()==Type.DOUBLE ); 5266 5267 if (_matched_) { // action code! degree: 1 5268 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5269 5270 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5271 clearDecl(); 5272 declare(i, code.getTreeDerivation(), ROOT); 5273 5274 5275 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5276 emit( ROOT, "mov `d0, `s0l", r0, arg ); 5277 emit( ROOT, "mov `d0, `s0h", r1, arg ); 5278 declareCALL(); declare( r0, HClass.Float ); 5279 emit2(ROOT, "bl "+nameMap.c_function_name("__truncdfsf2"), 5280 new Temp[] {r0,r1,r2,r3,IP,LR},new Temp[] {r0,r1} ); 5281 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 5282 return i; 5283 } 5284 } 5285 /* UNOP<i,l,f,d,p>(_2I,arg) */ 5286 if (true 5287 // check expression type 5288 && expArg instanceof harpoon.IR.Tree.UNOP 5289 // check opcode 5290 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2I 5291 // check operand types 5292 && ( 5293 expArg.type() == Type.DOUBLE || 5294 expArg.type() == Type.FLOAT || 5295 expArg.type() == Type.LONG || 5296 expArg.type() == Type.POINTER || 5297 ( expArg.type() == Type.INT && ! 5298 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5299 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5300 false ) 5301 // end check operand types 5302 // check child 5303 // no check needed for ExpId children 5304 ){ 5305 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5306 _matched_ = true&& ( ROOT.operandType()==Type.LONG ); 5307 5308 if (_matched_) { // action code! degree: 1 5309 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5310 5311 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5312 clearDecl(); 5313 declare(i, code.getTreeDerivation(), ROOT); 5314 5315 5316 emit( ROOT, "mov `d0, `s0l", i, arg ); 5317 return i; 5318 } 5319 } 5320 /* UNOP<i,l,f,d,p>(_2I,arg) */ 5321 if (true 5322 // check expression type 5323 && expArg instanceof harpoon.IR.Tree.UNOP 5324 // check opcode 5325 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2I 5326 // check operand types 5327 && ( 5328 expArg.type() == Type.DOUBLE || 5329 expArg.type() == Type.FLOAT || 5330 expArg.type() == Type.LONG || 5331 expArg.type() == Type.POINTER || 5332 ( expArg.type() == Type.INT && ! 5333 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5334 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5335 false ) 5336 // end check operand types 5337 // check child 5338 // no check needed for ExpId children 5339 ){ 5340 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5341 _matched_ = true&& ( ROOT.operandType()==Type.POINTER ); 5342 5343 if (_matched_) { // action code! degree: 1 5344 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5345 5346 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5347 clearDecl(); 5348 declare(i, code.getTreeDerivation(), ROOT); 5349 5350 5351 emitMOVE( ROOT, "mov `d0, `s0", i, arg ); 5352 return i; 5353 } 5354 } 5355 /* UNOP<i,l,f,d,p>(_2I,arg) */ 5356 if (true 5357 // check expression type 5358 && expArg instanceof harpoon.IR.Tree.UNOP 5359 // check opcode 5360 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2I 5361 // check operand types 5362 && ( 5363 expArg.type() == Type.DOUBLE || 5364 expArg.type() == Type.FLOAT || 5365 expArg.type() == Type.LONG || 5366 expArg.type() == Type.POINTER || 5367 ( expArg.type() == Type.INT && ! 5368 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5369 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5370 false ) 5371 // end check operand types 5372 // check child 5373 // no check needed for ExpId children 5374 ){ 5375 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5376 _matched_ = true&& ( ROOT.operandType()==Type.FLOAT ); 5377 5378 if (_matched_) { // action code! degree: 1 5379 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5380 5381 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5382 clearDecl(); 5383 declare(i, code.getTreeDerivation(), ROOT); 5384 5385 5386 declare( r0, HClass.Float ); 5387 emitMOVE( ROOT, "mov `d0, `s0", r0, arg ); 5388 declareCALL(); declare( r0, HClass.Int ); 5389 emit2( ROOT, "bl "+nameMap.c_function_name("__fixsfsi"), 5390 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0} ); 5391 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 5392 return i; 5393 } 5394 } 5395 /* UNOP<i,l,f,d,p>(_2I,arg) */ 5396 if (true 5397 // check expression type 5398 && expArg instanceof harpoon.IR.Tree.UNOP 5399 // check opcode 5400 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2I 5401 // check operand types 5402 && ( 5403 expArg.type() == Type.DOUBLE || 5404 expArg.type() == Type.FLOAT || 5405 expArg.type() == Type.LONG || 5406 expArg.type() == Type.POINTER || 5407 ( expArg.type() == Type.INT && ! 5408 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5409 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5410 false ) 5411 // end check operand types 5412 // check child 5413 // no check needed for ExpId children 5414 ){ 5415 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5416 _matched_ = true&& ( ROOT.operandType()==Type.DOUBLE ); 5417 5418 if (_matched_) { // action code! degree: 1 5419 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5420 5421 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5422 clearDecl(); 5423 declare(i, code.getTreeDerivation(), ROOT); 5424 5425 5426 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5427 emit( ROOT, "mov `d0, `s0l", r0, arg ); 5428 emit( ROOT, "mov `d0, `s0h", r1, arg ); 5429 declareCALL(); declare( r0, HClass.Int ); 5430 emit2(ROOT, "bl "+nameMap.c_function_name("__fixdfsi"), 5431 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 5432 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 5433 return i; 5434 } 5435 } 5436 /* UNOP<i,l,f,d,p>(_2L,arg) */ 5437 if (true 5438 // check expression type 5439 && expArg instanceof harpoon.IR.Tree.UNOP 5440 // check opcode 5441 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2L 5442 // check operand types 5443 && ( 5444 expArg.type() == Type.DOUBLE || 5445 expArg.type() == Type.FLOAT || 5446 expArg.type() == Type.LONG || 5447 expArg.type() == Type.POINTER || 5448 ( expArg.type() == Type.INT && ! 5449 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5450 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5451 false ) 5452 // end check operand types 5453 // check child 5454 // no check needed for ExpId children 5455 ){ 5456 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5457 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 5458 5459 if (_matched_) { // action code! degree: 1 5460 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5461 5462 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5463 clearDecl(); 5464 declare(i, code.getTreeDerivation(), ROOT); 5465 5466 5467 emit( ROOT, "mov `d0l, `s0", i, arg ); 5468 emit( ROOT, "mov `d0h, `s0l, asr #31", i, i ); 5469 return i; 5470 } 5471 } 5472 /* UNOP<i,l,f,d,p>(_2L,arg) */ 5473 if (true 5474 // check expression type 5475 && expArg instanceof harpoon.IR.Tree.UNOP 5476 // check opcode 5477 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2L 5478 // check operand types 5479 && ( 5480 expArg.type() == Type.DOUBLE || 5481 expArg.type() == Type.FLOAT || 5482 expArg.type() == Type.LONG || 5483 expArg.type() == Type.POINTER || 5484 ( expArg.type() == Type.INT && ! 5485 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5486 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5487 false ) 5488 // end check operand types 5489 // check child 5490 // no check needed for ExpId children 5491 ){ 5492 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5493 _matched_ = true&& ( ROOT.operandType()==Type.FLOAT ); 5494 5495 if (_matched_) { // action code! degree: 1 5496 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5497 5498 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5499 clearDecl(); 5500 declare(i, code.getTreeDerivation(), ROOT); 5501 5502 5503 declare( r0, HClass.Float ); 5504 emitMOVE( ROOT, "mov `d0, `s0", r0, arg ); 5505 declareCALL(); declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5506 emit2(ROOT, "bl "+nameMap.c_function_name("__fixsfdi"), 5507 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0} ); 5508 emit( ROOT, "mov `d0l, `s0", i, r0 ); 5509 emit( ROOT, "mov `d0h, `s0", i, r1 ); 5510 return i; 5511 } 5512 } 5513 /* UNOP<i,l,f,d,p>(_2L,arg) */ 5514 if (true 5515 // check expression type 5516 && expArg instanceof harpoon.IR.Tree.UNOP 5517 // check opcode 5518 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop._2L 5519 // check operand types 5520 && ( 5521 expArg.type() == Type.DOUBLE || 5522 expArg.type() == Type.FLOAT || 5523 expArg.type() == Type.LONG || 5524 expArg.type() == Type.POINTER || 5525 ( expArg.type() == Type.INT && ! 5526 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5527 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5528 false ) 5529 // end check operand types 5530 // check child 5531 // no check needed for ExpId children 5532 ){ 5533 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5534 _matched_ = true&& ( ROOT.operandType()==Type.DOUBLE ); 5535 5536 if (_matched_) { // action code! degree: 1 5537 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5538 5539 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5540 clearDecl(); 5541 declare(i, code.getTreeDerivation(), ROOT); 5542 5543 5544 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5545 emit( ROOT, "mov `d0, `s0l", r0, arg ); 5546 emit( ROOT, "mov `d0, `s0h", r1, arg ); 5547 declareCALL(); declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5548 emit2(ROOT, "bl "+nameMap.c_function_name("__fixdfdi"), 5549 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 5550 emit( ROOT, "mov `d0l, `s0", i, r0 ); 5551 emit( ROOT, "mov `d0h, `s0", i, r1 ); 5552 return i; 5553 } 5554 } 5555 /* UNOP<i,l,f,d,p>(NEG,arg) */ 5556 if (true 5557 // check expression type 5558 && expArg instanceof harpoon.IR.Tree.UNOP 5559 // check opcode 5560 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NEG 5561 // check operand types 5562 && ( 5563 expArg.type() == Type.DOUBLE || 5564 expArg.type() == Type.FLOAT || 5565 expArg.type() == Type.LONG || 5566 expArg.type() == Type.POINTER || 5567 ( expArg.type() == Type.INT && ! 5568 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5569 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5570 false ) 5571 // end check operand types 5572 // check child 5573 // no check needed for ExpId children 5574 ){ 5575 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5576 _matched_ = true&& ( ROOT.operandType()==Type.INT || ROOT.operandType()==Type.POINTER ); 5577 5578 if (_matched_) { // action code! degree: 1 5579 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5580 5581 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5582 clearDecl(); 5583 declare(i, code.getTreeDerivation(), ROOT); 5584 5585 5586 emit( ROOT, "rsb `d0, `s0, #0", i, arg ); 5587 return i; 5588 } 5589 } 5590 /* UNOP<i,l,f,d,p>(NEG,arg) */ 5591 if (true 5592 // check expression type 5593 && expArg instanceof harpoon.IR.Tree.UNOP 5594 // check opcode 5595 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NEG 5596 // check operand types 5597 && ( 5598 expArg.type() == Type.DOUBLE || 5599 expArg.type() == Type.FLOAT || 5600 expArg.type() == Type.LONG || 5601 expArg.type() == Type.POINTER || 5602 ( expArg.type() == Type.INT && ! 5603 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5604 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5605 false ) 5606 // end check operand types 5607 // check child 5608 // no check needed for ExpId children 5609 ){ 5610 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5611 _matched_ = true&& ( ROOT.operandType()==Type.LONG ); 5612 5613 if (_matched_) { // action code! degree: 1 5614 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5615 5616 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5617 clearDecl(); 5618 declare(i, code.getTreeDerivation(), ROOT); 5619 5620 5621 // uses condition codes, so keep together 5622 emit( ROOT, "rsbs `d0l, `s0l, #0\n" + 5623 "rsc `d0h, `s0h, #0", i, arg ); 5624 // make sure d0l isn't assigned same reg as `s0h 5625 emit2( ROOT, "@ dummy use of `s0l `s0h", null, new Temp[]{arg}); 5626 return i; 5627 } 5628 } 5629 /* UNOP<i,l,f,d,p>(NEG,arg) */ 5630 if (true 5631 // check expression type 5632 && expArg instanceof harpoon.IR.Tree.UNOP 5633 // check opcode 5634 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NEG 5635 // check operand types 5636 && ( 5637 expArg.type() == Type.DOUBLE || 5638 expArg.type() == Type.FLOAT || 5639 expArg.type() == Type.LONG || 5640 expArg.type() == Type.POINTER || 5641 ( expArg.type() == Type.INT && ! 5642 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5643 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5644 false ) 5645 // end check operand types 5646 // check child 5647 // no check needed for ExpId children 5648 ){ 5649 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5650 _matched_ = true&& ( ROOT.operandType()==Type.FLOAT ); 5651 5652 if (_matched_) { // action code! degree: 1 5653 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5654 5655 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5656 clearDecl(); 5657 declare(i, code.getTreeDerivation(), ROOT); 5658 5659 5660 declare( r0, HClass.Float ); 5661 emitMOVE( ROOT, "mov `d0, `s0", r0, arg ); 5662 declareCALL(); declare( r0, HClass.Float ); 5663 emit2( ROOT, "bl "+nameMap.c_function_name("__negsf2"), 5664 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0} ); 5665 emitMOVE( ROOT, "mov `d0, `s0", i, r0 ); 5666 return i; 5667 } 5668 } 5669 /* UNOP<i,l,f,d,p>(NEG,arg) */ 5670 if (true 5671 // check expression type 5672 && expArg instanceof harpoon.IR.Tree.UNOP 5673 // check opcode 5674 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NEG 5675 // check operand types 5676 && ( 5677 expArg.type() == Type.DOUBLE || 5678 expArg.type() == Type.FLOAT || 5679 expArg.type() == Type.LONG || 5680 expArg.type() == Type.POINTER || 5681 ( expArg.type() == Type.INT && ! 5682 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5683 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5684 false ) 5685 // end check operand types 5686 // check child 5687 // no check needed for ExpId children 5688 ){ 5689 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5690 _matched_ = true&& ( ROOT.operandType()==Type.DOUBLE ); 5691 5692 if (_matched_) { // action code! degree: 1 5693 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5694 5695 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5696 clearDecl(); 5697 declare(i, code.getTreeDerivation(), ROOT); 5698 5699 5700 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5701 emit( ROOT, "mov `d0, `s0l", r0, arg ); 5702 emit( ROOT, "mov `d0, `s0h", r1, arg ); 5703 declareCALL(); declare( r0, HClass.Void ); declare( r1, HClass.Void ); 5704 emit2(ROOT, "bl "+nameMap.c_function_name("__negdf2"), 5705 new Temp[] {r0,r1,r2,r3,IP,LR}, new Temp[] {r0,r1} ); 5706 emit( ROOT, "mov `d0l, `s0", i, r0 ); 5707 emit( ROOT, "mov `d0h, `s0", i, r1 ); 5708 return i; 5709 } 5710 } 5711 /* UNOP<i,l,f,d,p>(NOT,arg) */ 5712 if (true 5713 // check expression type 5714 && expArg instanceof harpoon.IR.Tree.UNOP 5715 // check opcode 5716 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NOT 5717 // check operand types 5718 && ( 5719 expArg.type() == Type.DOUBLE || 5720 expArg.type() == Type.FLOAT || 5721 expArg.type() == Type.LONG || 5722 expArg.type() == Type.POINTER || 5723 ( expArg.type() == Type.INT && ! 5724 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5725 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5726 false ) 5727 // end check operand types 5728 // check child 5729 // no check needed for ExpId children 5730 ){ 5731 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5732 _matched_ = true&& ( ROOT.operandType()==Type.INT ); 5733 5734 if (_matched_) { // action code! degree: 1 5735 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5736 5737 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5738 clearDecl(); 5739 declare(i, code.getTreeDerivation(), ROOT); 5740 5741 emit( ROOT, "mvn `d0, `s0", i, arg ); 5742 return i; 5743 } 5744 } 5745 /* UNOP<i,l,f,d,p>(NOT,arg) */ 5746 if (true 5747 // check expression type 5748 && expArg instanceof harpoon.IR.Tree.UNOP 5749 // check opcode 5750 && ((harpoon.IR.Tree.UNOP)expArg).op == harpoon.IR.Tree.Uop.NOT 5751 // check operand types 5752 && ( 5753 expArg.type() == Type.DOUBLE || 5754 expArg.type() == Type.FLOAT || 5755 expArg.type() == Type.LONG || 5756 expArg.type() == Type.POINTER || 5757 ( expArg.type() == Type.INT && ! 5758 (expArg instanceof harpoon.IR.Tree.PreciselyTyped && 5759 ((harpoon.IR.Tree.PreciselyTyped)expArg).isSmall())) || 5760 false ) 5761 // end check operand types 5762 // check child 5763 // no check needed for ExpId children 5764 ){ 5765 harpoon.IR.Tree.UNOP ROOT = (harpoon.IR.Tree.UNOP) expArg; 5766 _matched_ = true&& ( ROOT.operandType()==Type.LONG ); 5767 5768 if (_matched_) { // action code! degree: 1 5769 harpoon.Temp.Temp arg = munchExp(((harpoon.IR.Tree.UNOP)expArg).getOperand()); 5770 5771 Temp i = frame.getTempBuilder().makeTemp( ROOT , inf.tempFactory()); 5772 clearDecl(); 5773 declare(i, code.getTreeDerivation(), ROOT); 5774 5775 5776 emit( ROOT, "mvn `d0l, `s0l", i, arg ); 5777 emit( ROOT, "mvn `d0h, `s0h", i, arg ); 5778 return i; 5779 } 5780 } 5781 assert false : "Uh oh...\nmaximal munch didn't match anything...SPEC file\nis not complete enough for this program\nDied on "+prettyPrint(expArg)+" in " + prettyPrint(globalStmArg); 5782 return null; // doesn't matter, we're dead if we didn't match... 5783 } // end munchExp 5784 harpoon.IR.Tree.Stm globalStmArg=null; 5785 void munchStm(harpoon.IR.Tree.Stm stmArg) { 5786 globalStmArg = stmArg; 5787 boolean _matched_ = false; 5788 clearDecl(); // reset temp type mappings 5789 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),d2)),d1)),src) */ 5790 if (true 5791 // check statement type 5792 && stmArg instanceof harpoon.IR.Tree.MOVE 5793 // check operand types 5794 && ( 5795 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 5796 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 5797 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 5798 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 5799 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 5800 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 5801 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 5802 false ) 5803 // end check operand types 5804 && (true 5805 // no check needed for ExpId children 5806 ) 5807 && (true 5808 // check expression type 5809 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 5810 // check operand types 5811 && ( 5812 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 5813 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 5814 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 5815 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 5816 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 5817 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 5818 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 5819 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 5820 false) : ( 5821 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 5822 false) ) ) || 5823 false ) 5824 // end check operand types 5825 // check child 5826 // check expression type 5827 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 5828 // check opcode 5829 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 5830 // check operand types 5831 && ( 5832 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 5833 false ) 5834 // end check operand types 5835 // check left child 5836 // check expression type 5837 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.UNOP 5838 // check opcode 5839 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).op == harpoon.IR.Tree.Uop.NEG 5840 // check operand types 5841 && ( 5842 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.DOUBLE || 5843 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.FLOAT || 5844 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.LONG || 5845 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.POINTER || 5846 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.INT && ! 5847 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 5848 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).isSmall())) || 5849 false ) 5850 // end check operand types 5851 // check child 5852 // check expression type 5853 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.BINOP 5854 // check operand types 5855 && ( 5856 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.DOUBLE || 5857 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.FLOAT || 5858 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.LONG || 5859 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.POINTER || 5860 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.INT && ! 5861 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 5862 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).isSmall())) || 5863 false ) 5864 // end check operand types 5865 // check left child 5866 // check expression type 5867 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft() instanceof harpoon.IR.Tree.CONST 5868 // check operand types 5869 && ( 5870 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft().type() == Type.POINTER || 5871 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft().type() == Type.INT && ! 5872 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 5873 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft()).isSmall())) || 5874 false ) 5875 // end check operand types 5876 // check right child 5877 // no check needed for ExpId children 5878 // check right child 5879 // no check needed for ExpId children 5880 ) 5881 ){ 5882 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).op; 5883 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft()).value; 5884 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 5885 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 5886 5887 if (_matched_) { // action code! : degree 6 5888 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 5889 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight()); 5890 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 5891 5892 5893 String suffix=""; 5894 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 5895 suffix+="b"; 5896 emit(new InstrMEM(instrFactory, ROOT, 5897 "str"+suffix+" `s0, [`s1, -`s2, " + 5898 shiftOp2Str(shiftop)+" #"+c+"]", 5899 null, new Temp[]{ src, d1, d2 })); 5900 return; } 5901 } 5902 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d1,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),d2)))),src) */ 5903 if (true 5904 // check statement type 5905 && stmArg instanceof harpoon.IR.Tree.MOVE 5906 // check operand types 5907 && ( 5908 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 5909 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 5910 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 5911 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 5912 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 5913 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 5914 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 5915 false ) 5916 // end check operand types 5917 && (true 5918 // no check needed for ExpId children 5919 ) 5920 && (true 5921 // check expression type 5922 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 5923 // check operand types 5924 && ( 5925 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 5926 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 5927 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 5928 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 5929 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 5930 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 5931 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 5932 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 5933 false) : ( 5934 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 5935 false) ) ) || 5936 false ) 5937 // end check operand types 5938 // check child 5939 // check expression type 5940 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 5941 // check opcode 5942 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 5943 // check operand types 5944 && ( 5945 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 5946 false ) 5947 // end check operand types 5948 // check left child 5949 // no check needed for ExpId children 5950 // check right child 5951 // check expression type 5952 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.UNOP 5953 // check opcode 5954 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).op == harpoon.IR.Tree.Uop.NEG 5955 // check operand types 5956 && ( 5957 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.DOUBLE || 5958 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.FLOAT || 5959 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.LONG || 5960 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.POINTER || 5961 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.INT && ! 5962 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 5963 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).isSmall())) || 5964 false ) 5965 // end check operand types 5966 // check child 5967 // check expression type 5968 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.BINOP 5969 // check operand types 5970 && ( 5971 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.DOUBLE || 5972 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.FLOAT || 5973 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.LONG || 5974 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.POINTER || 5975 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.INT && ! 5976 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 5977 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).isSmall())) || 5978 false ) 5979 // end check operand types 5980 // check left child 5981 // check expression type 5982 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft() instanceof harpoon.IR.Tree.CONST 5983 // check operand types 5984 && ( 5985 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft().type() == Type.POINTER || 5986 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft().type() == Type.INT && ! 5987 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 5988 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft()).isSmall())) || 5989 false ) 5990 // end check operand types 5991 // check right child 5992 // no check needed for ExpId children 5993 ) 5994 ){ 5995 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).op; 5996 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft()).value; 5997 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 5998 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 5999 6000 if (_matched_) { // action code! : degree 6 6001 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6002 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 6003 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight()); 6004 6005 6006 String suffix=""; 6007 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6008 suffix+="b"; 6009 emit(new InstrMEM(instrFactory, ROOT, 6010 "str"+suffix+" `s0, [`s1, -`s2, " + 6011 shiftOp2Str(shiftop)+" #"+c+"]", 6012 null, new Temp[]{ src, d1, d2 })); 6013 return; } 6014 } 6015 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,d2,CONST<i,p>(c))),d1)),src) */ 6016 if (true 6017 // check statement type 6018 && stmArg instanceof harpoon.IR.Tree.MOVE 6019 // check operand types 6020 && ( 6021 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6022 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6023 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6024 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6025 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6026 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6027 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6028 false ) 6029 // end check operand types 6030 && (true 6031 // no check needed for ExpId children 6032 ) 6033 && (true 6034 // check expression type 6035 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6036 // check operand types 6037 && ( 6038 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6039 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6040 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6041 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6042 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6043 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6044 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6045 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6046 false) : ( 6047 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6048 false) ) ) || 6049 false ) 6050 // end check operand types 6051 // check child 6052 // check expression type 6053 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6054 // check opcode 6055 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6056 // check operand types 6057 && ( 6058 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6059 false ) 6060 // end check operand types 6061 // check left child 6062 // check expression type 6063 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.UNOP 6064 // check opcode 6065 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).op == harpoon.IR.Tree.Uop.NEG 6066 // check operand types 6067 && ( 6068 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.DOUBLE || 6069 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.FLOAT || 6070 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.LONG || 6071 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.POINTER || 6072 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.INT && ! 6073 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6074 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).isSmall())) || 6075 false ) 6076 // end check operand types 6077 // check child 6078 // check expression type 6079 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.BINOP 6080 // check operand types 6081 && ( 6082 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.DOUBLE || 6083 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.FLOAT || 6084 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.LONG || 6085 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.POINTER || 6086 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand().type() == Type.INT && ! 6087 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 6088 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).isSmall())) || 6089 false ) 6090 // end check operand types 6091 // check left child 6092 // no check needed for ExpId children 6093 // check right child 6094 // check expression type 6095 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight() instanceof harpoon.IR.Tree.CONST 6096 // check operand types 6097 && ( 6098 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight().type() == Type.POINTER || 6099 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight().type() == Type.INT && ! 6100 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6101 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight()).isSmall())) || 6102 false ) 6103 // end check operand types 6104 // check right child 6105 // no check needed for ExpId children 6106 ) 6107 ){ 6108 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).op; 6109 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getRight()).value; 6110 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6111 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 6112 6113 if (_matched_) { // action code! : degree 6 6114 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6115 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()).getLeft()); 6116 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 6117 6118 6119 String suffix=""; 6120 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6121 suffix+="b"; 6122 emit(new InstrMEM(instrFactory, ROOT, 6123 "str"+suffix+" `s0, [`s1, -`s2, " + 6124 shiftOp2Str(shiftop)+" #"+c+"]", 6125 null, new Temp[]{ src, d1, d2 })); 6126 return; } 6127 } 6128 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d1,UNOP<i,l,f,d,p>(NEG,BINOP<i,l,f,d,p>(shiftop,d2,CONST<i,p>(c))))),src) */ 6129 if (true 6130 // check statement type 6131 && stmArg instanceof harpoon.IR.Tree.MOVE 6132 // check operand types 6133 && ( 6134 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6135 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6136 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6137 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6138 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6139 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6140 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6141 false ) 6142 // end check operand types 6143 && (true 6144 // no check needed for ExpId children 6145 ) 6146 && (true 6147 // check expression type 6148 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6149 // check operand types 6150 && ( 6151 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6152 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6153 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6154 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6155 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6156 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6157 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6158 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6159 false) : ( 6160 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6161 false) ) ) || 6162 false ) 6163 // end check operand types 6164 // check child 6165 // check expression type 6166 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6167 // check opcode 6168 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6169 // check operand types 6170 && ( 6171 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6172 false ) 6173 // end check operand types 6174 // check left child 6175 // no check needed for ExpId children 6176 // check right child 6177 // check expression type 6178 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.UNOP 6179 // check opcode 6180 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).op == harpoon.IR.Tree.Uop.NEG 6181 // check operand types 6182 && ( 6183 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.DOUBLE || 6184 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.FLOAT || 6185 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.LONG || 6186 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.POINTER || 6187 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.INT && ! 6188 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6189 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).isSmall())) || 6190 false ) 6191 // end check operand types 6192 // check child 6193 // check expression type 6194 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.BINOP 6195 // check operand types 6196 && ( 6197 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.DOUBLE || 6198 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.FLOAT || 6199 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.LONG || 6200 ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.POINTER || 6201 ( ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand().type() == Type.INT && ! 6202 (((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand() instanceof harpoon.IR.Tree.PreciselyTyped && 6203 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).isSmall())) || 6204 false ) 6205 // end check operand types 6206 // check left child 6207 // no check needed for ExpId children 6208 // check right child 6209 // check expression type 6210 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight() instanceof harpoon.IR.Tree.CONST 6211 // check operand types 6212 && ( 6213 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight().type() == Type.POINTER || 6214 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight().type() == Type.INT && ! 6215 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6216 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight()).isSmall())) || 6217 false ) 6218 // end check operand types 6219 ) 6220 ){ 6221 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).op; 6222 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getRight()).value; 6223 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6224 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 6225 6226 if (_matched_) { // action code! : degree 6 6227 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6228 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 6229 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()).getLeft()); 6230 6231 6232 String suffix=""; 6233 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6234 suffix+="b"; 6235 emit(new InstrMEM(instrFactory, ROOT, 6236 "str"+suffix+" `s0, [`s1, -`s2, " + 6237 shiftOp2Str(shiftop)+" #"+c+"]", 6238 null, new Temp[]{ src, d1, d2 })); 6239 return; } 6240 } 6241 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),d2),d1)),src) */ 6242 if (true 6243 // check statement type 6244 && stmArg instanceof harpoon.IR.Tree.MOVE 6245 // check operand types 6246 && ( 6247 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6248 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6249 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6250 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6251 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6252 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6253 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6254 false ) 6255 // end check operand types 6256 && (true 6257 // no check needed for ExpId children 6258 ) 6259 && (true 6260 // check expression type 6261 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6262 // check operand types 6263 && ( 6264 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6265 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6266 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6267 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6268 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6269 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6270 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6271 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6272 false) : ( 6273 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6274 false) ) ) || 6275 false ) 6276 // end check operand types 6277 // check child 6278 // check expression type 6279 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6280 // check opcode 6281 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6282 // check operand types 6283 && ( 6284 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6285 false ) 6286 // end check operand types 6287 // check left child 6288 // check expression type 6289 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.BINOP 6290 // check operand types 6291 && ( 6292 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.DOUBLE || 6293 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.FLOAT || 6294 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.LONG || 6295 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.POINTER || 6296 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.INT && ! 6297 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6298 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).isSmall())) || 6299 false ) 6300 // end check operand types 6301 // check left child 6302 // check expression type 6303 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft() instanceof harpoon.IR.Tree.CONST 6304 // check operand types 6305 && ( 6306 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft().type() == Type.POINTER || 6307 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft().type() == Type.INT && ! 6308 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6309 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft()).isSmall())) || 6310 false ) 6311 // end check operand types 6312 // check right child 6313 // no check needed for ExpId children 6314 // check right child 6315 // no check needed for ExpId children 6316 ) 6317 ){ 6318 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).op; 6319 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft()).value; 6320 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6321 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 6322 6323 if (_matched_) { // action code! : degree 5 6324 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6325 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight()); 6326 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 6327 6328 6329 String suffix=""; 6330 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6331 suffix+="b"; 6332 emit(new InstrMEM(instrFactory, ROOT, 6333 "str"+suffix+" `s0, [`s1, `s2, " + 6334 shiftOp2Str(shiftop)+" #"+c+"]", 6335 null, new Temp[]{ src, d1, d2 })); 6336 return; } 6337 } 6338 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d1,BINOP<i,l,f,d,p>(shiftop,CONST<i,p>(c),d2))),src) */ 6339 if (true 6340 // check statement type 6341 && stmArg instanceof harpoon.IR.Tree.MOVE 6342 // check operand types 6343 && ( 6344 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6345 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6346 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6347 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6348 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6349 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6350 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6351 false ) 6352 // end check operand types 6353 && (true 6354 // no check needed for ExpId children 6355 ) 6356 && (true 6357 // check expression type 6358 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6359 // check operand types 6360 && ( 6361 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6362 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6363 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6364 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6365 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6366 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6367 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6368 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6369 false) : ( 6370 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6371 false) ) ) || 6372 false ) 6373 // end check operand types 6374 // check child 6375 // check expression type 6376 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6377 // check opcode 6378 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6379 // check operand types 6380 && ( 6381 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6382 false ) 6383 // end check operand types 6384 // check left child 6385 // no check needed for ExpId children 6386 // check right child 6387 // check expression type 6388 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.BINOP 6389 // check operand types 6390 && ( 6391 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.DOUBLE || 6392 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.FLOAT || 6393 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.LONG || 6394 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.POINTER || 6395 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.INT && ! 6396 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6397 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).isSmall())) || 6398 false ) 6399 // end check operand types 6400 // check left child 6401 // check expression type 6402 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft() instanceof harpoon.IR.Tree.CONST 6403 // check operand types 6404 && ( 6405 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft().type() == Type.POINTER || 6406 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft().type() == Type.INT && ! 6407 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6408 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft()).isSmall())) || 6409 false ) 6410 // end check operand types 6411 // check right child 6412 // no check needed for ExpId children 6413 ) 6414 ){ 6415 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).op; 6416 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft()).value; 6417 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6418 _matched_ = true&& ((__CommExp__isCommutative(shiftop=__CommExp__swapCmpOp(shiftop))) && ( isShiftOp(shiftop) && is5BitShift(c) )); 6419 6420 if (_matched_) { // action code! : degree 5 6421 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6422 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 6423 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight()); 6424 6425 6426 String suffix=""; 6427 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6428 suffix+="b"; 6429 emit(new InstrMEM(instrFactory, ROOT, 6430 "str"+suffix+" `s0, [`s1, `s2, " + 6431 shiftOp2Str(shiftop)+" #"+c+"]", 6432 null, new Temp[]{ src, d1, d2 })); 6433 return; } 6434 } 6435 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,BINOP<i,l,f,d,p>(shiftop,d2,CONST<i,p>(c)),d1)),src) */ 6436 if (true 6437 // check statement type 6438 && stmArg instanceof harpoon.IR.Tree.MOVE 6439 // check operand types 6440 && ( 6441 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6442 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6443 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6444 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6445 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6446 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6447 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6448 false ) 6449 // end check operand types 6450 && (true 6451 // no check needed for ExpId children 6452 ) 6453 && (true 6454 // check expression type 6455 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6456 // check operand types 6457 && ( 6458 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6459 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6460 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6461 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6462 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6463 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6464 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6465 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6466 false) : ( 6467 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6468 false) ) ) || 6469 false ) 6470 // end check operand types 6471 // check child 6472 // check expression type 6473 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6474 // check opcode 6475 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6476 // check operand types 6477 && ( 6478 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6479 false ) 6480 // end check operand types 6481 // check left child 6482 // check expression type 6483 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.BINOP 6484 // check operand types 6485 && ( 6486 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.DOUBLE || 6487 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.FLOAT || 6488 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.LONG || 6489 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.POINTER || 6490 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.INT && ! 6491 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6492 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).isSmall())) || 6493 false ) 6494 // end check operand types 6495 // check left child 6496 // no check needed for ExpId children 6497 // check right child 6498 // check expression type 6499 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight() instanceof harpoon.IR.Tree.CONST 6500 // check operand types 6501 && ( 6502 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight().type() == Type.POINTER || 6503 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight().type() == Type.INT && ! 6504 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6505 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight()).isSmall())) || 6506 false ) 6507 // end check operand types 6508 // check right child 6509 // no check needed for ExpId children 6510 ) 6511 ){ 6512 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).op; 6513 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getRight()).value; 6514 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6515 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 6516 6517 if (_matched_) { // action code! : degree 5 6518 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6519 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getLeft()); 6520 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 6521 6522 6523 String suffix=""; 6524 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6525 suffix+="b"; 6526 emit(new InstrMEM(instrFactory, ROOT, 6527 "str"+suffix+" `s0, [`s1, `s2, " + 6528 shiftOp2Str(shiftop)+" #"+c+"]", 6529 null, new Temp[]{ src, d1, d2 })); 6530 return; } 6531 } 6532 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d1,BINOP<i,l,f,d,p>(shiftop,d2,CONST<i,p>(c)))),src) */ 6533 if (true 6534 // check statement type 6535 && stmArg instanceof harpoon.IR.Tree.MOVE 6536 // check operand types 6537 && ( 6538 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6539 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6540 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6541 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6542 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6543 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6544 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6545 false ) 6546 // end check operand types 6547 && (true 6548 // no check needed for ExpId children 6549 ) 6550 && (true 6551 // check expression type 6552 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6553 // check operand types 6554 && ( 6555 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6556 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6557 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6558 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6559 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6560 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6561 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6562 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6563 false) : ( 6564 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6565 false) ) ) || 6566 false ) 6567 // end check operand types 6568 // check child 6569 // check expression type 6570 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6571 // check opcode 6572 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6573 // check operand types 6574 && ( 6575 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6576 false ) 6577 // end check operand types 6578 // check left child 6579 // no check needed for ExpId children 6580 // check right child 6581 // check expression type 6582 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.BINOP 6583 // check operand types 6584 && ( 6585 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.DOUBLE || 6586 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.FLOAT || 6587 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.LONG || 6588 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.POINTER || 6589 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.INT && ! 6590 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6591 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).isSmall())) || 6592 false ) 6593 // end check operand types 6594 // check left child 6595 // no check needed for ExpId children 6596 // check right child 6597 // check expression type 6598 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight() instanceof harpoon.IR.Tree.CONST 6599 // check operand types 6600 && ( 6601 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight().type() == Type.POINTER || 6602 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight().type() == Type.INT && ! 6603 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6604 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight()).isSmall())) || 6605 false ) 6606 // end check operand types 6607 ) 6608 ){ 6609 int shiftop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).op; 6610 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getRight()).value; 6611 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6612 _matched_ = true&& ( isShiftOp(shiftop) && is5BitShift(c) ); 6613 6614 if (_matched_) { // action code! : degree 5 6615 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6616 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 6617 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getLeft()); 6618 6619 6620 String suffix=""; 6621 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6622 suffix+="b"; 6623 emit(new InstrMEM(instrFactory, ROOT, 6624 "str"+suffix+" `s0, [`s1, `s2, " + 6625 shiftOp2Str(shiftop)+" #"+c+"]", 6626 null, new Temp[]{ src, d1, d2 })); 6627 return; } 6628 } 6629 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,UNOP<i,l,f,d,p>(NEG,d2),d1)),src) */ 6630 if (true 6631 // check statement type 6632 && stmArg instanceof harpoon.IR.Tree.MOVE 6633 // check operand types 6634 && ( 6635 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6636 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6637 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6638 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6639 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6640 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6641 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6642 false ) 6643 // end check operand types 6644 && (true 6645 // no check needed for ExpId children 6646 ) 6647 && (true 6648 // check expression type 6649 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6650 // check operand types 6651 && ( 6652 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6653 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6654 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6655 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6656 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6657 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6658 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6659 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6660 false) : ( 6661 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6662 false) ) ) || 6663 false ) 6664 // end check operand types 6665 // check child 6666 // check expression type 6667 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6668 // check opcode 6669 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6670 // check operand types 6671 && ( 6672 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6673 false ) 6674 // end check operand types 6675 // check left child 6676 // check expression type 6677 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.UNOP 6678 // check opcode 6679 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).op == harpoon.IR.Tree.Uop.NEG 6680 // check operand types 6681 && ( 6682 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.DOUBLE || 6683 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.FLOAT || 6684 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.LONG || 6685 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.POINTER || 6686 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.INT && ! 6687 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6688 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).isSmall())) || 6689 false ) 6690 // end check operand types 6691 // check child 6692 // no check needed for ExpId children 6693 // check right child 6694 // no check needed for ExpId children 6695 ) 6696 ){ 6697 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6698 _matched_ = true; 6699 6700 if (_matched_) { // action code! : degree 4 6701 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6702 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).getOperand()); 6703 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 6704 6705 6706 String suffix=""; 6707 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6708 suffix+="b"; 6709 emit(new InstrMEM(instrFactory, ROOT, 6710 "str"+suffix+" `s0, [`s1, -`s2]", 6711 null, new Temp[]{ src, d1, d2 })); 6712 return; } 6713 } 6714 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d1,UNOP<i,l,f,d,p>(NEG,d2))),src) */ 6715 if (true 6716 // check statement type 6717 && stmArg instanceof harpoon.IR.Tree.MOVE 6718 // check operand types 6719 && ( 6720 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6721 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6722 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6723 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6724 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6725 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6726 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6727 false ) 6728 // end check operand types 6729 && (true 6730 // no check needed for ExpId children 6731 ) 6732 && (true 6733 // check expression type 6734 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6735 // check operand types 6736 && ( 6737 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6738 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6739 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6740 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6741 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6742 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6743 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6744 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6745 false) : ( 6746 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6747 false) ) ) || 6748 false ) 6749 // end check operand types 6750 // check child 6751 // check expression type 6752 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6753 // check opcode 6754 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6755 // check operand types 6756 && ( 6757 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6758 false ) 6759 // end check operand types 6760 // check left child 6761 // no check needed for ExpId children 6762 // check right child 6763 // check expression type 6764 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.UNOP 6765 // check opcode 6766 && ((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).op == harpoon.IR.Tree.Uop.NEG 6767 // check operand types 6768 && ( 6769 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.DOUBLE || 6770 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.FLOAT || 6771 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.LONG || 6772 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.POINTER || 6773 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.INT && ! 6774 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6775 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).isSmall())) || 6776 false ) 6777 // end check operand types 6778 // check child 6779 // no check needed for ExpId children 6780 ) 6781 ){ 6782 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6783 _matched_ = true; 6784 6785 if (_matched_) { // action code! : degree 4 6786 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6787 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 6788 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.UNOP)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).getOperand()); 6789 6790 6791 String suffix=""; 6792 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6793 suffix+="b"; 6794 emit(new InstrMEM(instrFactory, ROOT, 6795 "str"+suffix+" `s0, [`s1, -`s2]", 6796 null, new Temp[]{ src, d1, d2 })); 6797 return; } 6798 } 6799 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,CONST<i,p>(c),d)),src) */ 6800 if (true 6801 // check statement type 6802 && stmArg instanceof harpoon.IR.Tree.MOVE 6803 // check operand types 6804 && ( 6805 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6806 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6807 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6808 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6809 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6810 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6811 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6812 false ) 6813 // end check operand types 6814 && (true 6815 // no check needed for ExpId children 6816 ) 6817 && (true 6818 // check expression type 6819 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6820 // check operand types 6821 && ( 6822 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6823 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6824 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6825 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6826 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6827 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6828 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6829 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6830 false) : ( 6831 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6832 false) ) ) || 6833 false ) 6834 // end check operand types 6835 // check child 6836 // check expression type 6837 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6838 // check opcode 6839 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6840 // check operand types 6841 && ( 6842 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6843 false ) 6844 // end check operand types 6845 // check left child 6846 // check expression type 6847 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.CONST 6848 // check operand types 6849 && ( 6850 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.POINTER || 6851 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft().type() == Type.INT && ! 6852 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 6853 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).isSmall())) || 6854 false ) 6855 // end check operand types 6856 // check right child 6857 // no check needed for ExpId children 6858 ) 6859 ){ 6860 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()).value; 6861 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6862 _matched_ = true&& ( is12BitOffset(c) ); 6863 6864 if (_matched_) { // action code! : degree 4 6865 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6866 harpoon.Temp.Temp d = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 6867 6868 6869 String suffix=""; 6870 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6871 suffix+="b"; 6872 emit(new InstrMEM(instrFactory, ROOT, 6873 "str"+suffix+" `s0, [`s1, #"+c+"]", 6874 null, new Temp[]{ src, d })); 6875 return; } 6876 } 6877 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d,CONST<i,p>(c))),src) */ 6878 if (true 6879 // check statement type 6880 && stmArg instanceof harpoon.IR.Tree.MOVE 6881 // check operand types 6882 && ( 6883 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6884 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6885 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6886 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6887 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6888 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6889 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6890 false ) 6891 // end check operand types 6892 && (true 6893 // no check needed for ExpId children 6894 ) 6895 && (true 6896 // check expression type 6897 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 6898 // check operand types 6899 && ( 6900 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6901 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6902 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6903 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6904 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6905 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 6906 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 6907 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6908 false) : ( 6909 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 6910 false) ) ) || 6911 false ) 6912 // end check operand types 6913 // check child 6914 // check expression type 6915 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 6916 // check opcode 6917 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 6918 // check operand types 6919 && ( 6920 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 6921 false ) 6922 // end check operand types 6923 // check left child 6924 // no check needed for ExpId children 6925 // check right child 6926 // check expression type 6927 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.CONST 6928 // check operand types 6929 && ( 6930 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.POINTER || 6931 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight().type() == Type.INT && ! 6932 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 6933 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).isSmall())) || 6934 false ) 6935 // end check operand types 6936 ) 6937 ){ 6938 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()).value; 6939 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6940 _matched_ = true&& ( is12BitOffset(c) ); 6941 6942 if (_matched_) { // action code! : degree 4 6943 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 6944 harpoon.Temp.Temp d = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 6945 6946 6947 String suffix=""; 6948 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 6949 suffix+="b"; 6950 emit(new InstrMEM(instrFactory, ROOT, 6951 "str"+suffix+" `s0, [`s1, #"+c+"]", 6952 null, new Temp[]{ src, d })); 6953 return; } 6954 } 6955 /* MOVE<i,l,f,d,p>(TEMP<i,l,f,d,p>(dst),CONST<l,d>(c)) */ 6956 if (true 6957 // check statement type 6958 && stmArg instanceof harpoon.IR.Tree.MOVE 6959 // check operand types 6960 && ( 6961 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 6962 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 6963 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 6964 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 6965 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 6966 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 6967 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 6968 false ) 6969 // end check operand types 6970 && (true 6971 // check expression type 6972 && ((harpoon.IR.Tree.MOVE) stmArg).getSrc() instanceof harpoon.IR.Tree.CONST 6973 // check operand types 6974 && ( 6975 ((harpoon.IR.Tree.MOVE) stmArg).getSrc().type() == Type.DOUBLE || 6976 ((harpoon.IR.Tree.MOVE) stmArg).getSrc().type() == Type.LONG || 6977 false ) 6978 // end check operand types 6979 ) 6980 && (true 6981 // check expression type 6982 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.TEMP 6983 // check operand types 6984 && ( 6985 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.DOUBLE || 6986 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 6987 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.LONG || 6988 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 6989 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 6990 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 6991 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 6992 false ) 6993 // end check operand types 6994 ) 6995 ){ 6996 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.MOVE) stmArg).getSrc()).value; 6997 harpoon.Temp.Temp dst = makeTemp((harpoon.IR.Tree.TEMP)((harpoon.IR.Tree.MOVE) stmArg).getDst(), inf.tempFactory()); 6998 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 6999 _matched_ = true; 7000 7001 if (_matched_) { // action code! : degree 3 7002 7003 7004 CONST cROOT = (CONST) ROOT.getSrc(); 7005 long val = (cROOT.type()==Type.LONG) ? cROOT.value.longValue() 7006 : Double.doubleToLongBits(cROOT.value.doubleValue()); 7007 // DOUBLEs are stored "backwards" on StrongARM. No, I have no clue 7008 // why. They just are. 7009 String lomod = (ROOT.type()==Type.LONG) ? "l" : "h"; 7010 String himod = (ROOT.type()==Type.LONG) ? "h" : "l"; 7011 declare( dst, code.getTreeDerivation(), ROOT.getSrc() ); 7012 7013 emit(new Instr( instrFactory, ROOT, 7014 loadConst32("`d0"+lomod, (int)val, "lo("+cROOT.value+")"), 7015 new Temp[]{ dst }, null)); 7016 val>>>=32; 7017 emit(new Instr( instrFactory, ROOT, 7018 loadConst32("`d0"+himod, (int)val, "hi("+cROOT.value+")"), 7019 new Temp[]{ dst }, null)); 7020 return; } 7021 } 7022 /* MOVE<i,l,f,d,p>(TEMP<i,l,f,d,p>(dst),CONST<i,f>(c)) */ 7023 if (true 7024 // check statement type 7025 && stmArg instanceof harpoon.IR.Tree.MOVE 7026 // check operand types 7027 && ( 7028 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7029 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7030 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7031 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7032 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7033 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7034 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7035 false ) 7036 // end check operand types 7037 && (true 7038 // check expression type 7039 && ((harpoon.IR.Tree.MOVE) stmArg).getSrc() instanceof harpoon.IR.Tree.CONST 7040 // check operand types 7041 && ( 7042 ((harpoon.IR.Tree.MOVE) stmArg).getSrc().type() == Type.FLOAT || 7043 ( ((harpoon.IR.Tree.MOVE) stmArg).getSrc().type() == Type.INT && ! 7044 (((harpoon.IR.Tree.MOVE) stmArg).getSrc() instanceof harpoon.IR.Tree.PreciselyTyped && 7045 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getSrc()).isSmall())) || 7046 false ) 7047 // end check operand types 7048 ) 7049 && (true 7050 // check expression type 7051 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.TEMP 7052 // check operand types 7053 && ( 7054 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.DOUBLE || 7055 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 7056 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.LONG || 7057 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 7058 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 7059 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 7060 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 7061 false ) 7062 // end check operand types 7063 ) 7064 ){ 7065 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.MOVE) stmArg).getSrc()).value; 7066 harpoon.Temp.Temp dst = makeTemp((harpoon.IR.Tree.TEMP)((harpoon.IR.Tree.MOVE) stmArg).getDst(), inf.tempFactory()); 7067 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7068 _matched_ = true; 7069 7070 if (_matched_) { // action code! : degree 3 7071 7072 7073 CONST cROOT = (CONST) ROOT.getSrc(); 7074 int val = (cROOT.type()==Type.INT) ? cROOT.value.intValue() 7075 : Float.floatToIntBits(cROOT.value.floatValue()); 7076 declare( dst, code.getTreeDerivation(), ROOT.getSrc()); 7077 emit(new Instr( instrFactory, ROOT, 7078 loadConst32("`d0", val, cROOT.value.toString()), 7079 new Temp[]{ dst }, null)); 7080 return; } 7081 } 7082 /* MOVE<i,l,f,d,p>(TEMP<i,l,f,d,p>(dst),CONST<p>(c)) */ 7083 if (true 7084 // check statement type 7085 && stmArg instanceof harpoon.IR.Tree.MOVE 7086 // check operand types 7087 && ( 7088 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7089 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7090 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7091 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7092 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7093 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7094 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7095 false ) 7096 // end check operand types 7097 && (true 7098 // check expression type 7099 && ((harpoon.IR.Tree.MOVE) stmArg).getSrc() instanceof harpoon.IR.Tree.CONST 7100 // check operand types 7101 && ( 7102 ((harpoon.IR.Tree.MOVE) stmArg).getSrc().type() == Type.POINTER || 7103 false ) 7104 // end check operand types 7105 ) 7106 && (true 7107 // check expression type 7108 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.TEMP 7109 // check operand types 7110 && ( 7111 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.DOUBLE || 7112 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 7113 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.LONG || 7114 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 7115 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 7116 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 7117 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 7118 false ) 7119 // end check operand types 7120 ) 7121 ){ 7122 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.MOVE) stmArg).getSrc()).value; 7123 harpoon.Temp.Temp dst = makeTemp((harpoon.IR.Tree.TEMP)((harpoon.IR.Tree.MOVE) stmArg).getDst(), inf.tempFactory()); 7124 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7125 _matched_ = true; 7126 7127 if (_matched_) { // action code! : degree 3 7128 7129 7130 // the only CONST of type Pointer we should see is NULL 7131 declare( dst, code.getTreeDerivation(), ROOT.getSrc()); 7132 emit(new Instr( instrFactory, ROOT, 7133 "mov `d0, #0 @ null", new Temp[]{ dst }, null)); 7134 return; } 7135 } 7136 /* CJUMP(BINOP<i,l,f,d,p>(cmpop,CONST<i,p>(c),j),iftrue,iffalse) */ 7137 if (true 7138 // check statement type 7139 && (stmArg instanceof harpoon.IR.Tree.CJUMP) 7140 && (true 7141 // check expression type 7142 && ((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.BINOP 7143 // check operand types 7144 && ( 7145 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.DOUBLE || 7146 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.FLOAT || 7147 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.LONG || 7148 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.POINTER || 7149 ( ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.INT && ! 7150 (((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.PreciselyTyped && 7151 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).isSmall())) || 7152 false ) 7153 // end check operand types 7154 // check left child 7155 // check expression type 7156 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft() instanceof harpoon.IR.Tree.CONST 7157 // check operand types 7158 && ( 7159 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft().type() == Type.POINTER || 7160 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft().type() == Type.INT && ! 7161 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 7162 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()).isSmall())) || 7163 false ) 7164 // end check operand types 7165 // check right child 7166 // no check needed for ExpId children 7167 ) 7168 ){ 7169 int cmpop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.CJUMP) stmArg).getTest()).op; 7170 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()).value; 7171 harpoon.Temp.Label iffalse = ((harpoon.IR.Tree.CJUMP)stmArg).iffalse; 7172 harpoon.Temp.Label iftrue = ((harpoon.IR.Tree.CJUMP)stmArg).iftrue; 7173 harpoon.IR.Tree.CJUMP ROOT = (harpoon.IR.Tree.CJUMP) stmArg; 7174 _matched_ = true&& ((__CommExp__isCommutative(cmpop=__CommExp__swapCmpOp(cmpop))) && ( isCmpOp(cmpop) && (c==null || isOpd2Imm(c)) )); 7175 7176 if (_matched_) { // action code! : degree 3 7177 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()); 7178 7179 // this is a frequent special case. 7180 emit( ROOT, "cmp `s0, #"+(c==null?"0 @ null":c.toString())+"\n" + 7181 "b"+cmpOp2Str(cmpop)+" `L0", 7182 null, new Temp[] { j }, new Label[] { iftrue }); 7183 emitJUMP( ROOT, "b `L0", iffalse ); 7184 return; } 7185 } 7186 /* CJUMP(BINOP<i,l,f,d,p>(cmpop,j,CONST<i,p>(c)),iftrue,iffalse) */ 7187 if (true 7188 // check statement type 7189 && (stmArg instanceof harpoon.IR.Tree.CJUMP) 7190 && (true 7191 // check expression type 7192 && ((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.BINOP 7193 // check operand types 7194 && ( 7195 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.DOUBLE || 7196 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.FLOAT || 7197 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.LONG || 7198 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.POINTER || 7199 ( ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.INT && ! 7200 (((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.PreciselyTyped && 7201 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).isSmall())) || 7202 false ) 7203 // end check operand types 7204 // check left child 7205 // no check needed for ExpId children 7206 // check right child 7207 // check expression type 7208 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight() instanceof harpoon.IR.Tree.CONST 7209 // check operand types 7210 && ( 7211 ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight().type() == Type.POINTER || 7212 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight().type() == Type.INT && ! 7213 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 7214 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()).isSmall())) || 7215 false ) 7216 // end check operand types 7217 ) 7218 ){ 7219 int cmpop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.CJUMP) stmArg).getTest()).op; 7220 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()).value; 7221 harpoon.Temp.Label iffalse = ((harpoon.IR.Tree.CJUMP)stmArg).iffalse; 7222 harpoon.Temp.Label iftrue = ((harpoon.IR.Tree.CJUMP)stmArg).iftrue; 7223 harpoon.IR.Tree.CJUMP ROOT = (harpoon.IR.Tree.CJUMP) stmArg; 7224 _matched_ = true&& ( isCmpOp(cmpop) && (c==null || isOpd2Imm(c)) ); 7225 7226 if (_matched_) { // action code! : degree 3 7227 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()); 7228 7229 // this is a frequent special case. 7230 emit( ROOT, "cmp `s0, #"+(c==null?"0 @ null":c.toString())+"\n" + 7231 "b"+cmpOp2Str(cmpop)+" `L0", 7232 null, new Temp[] { j }, new Label[] { iftrue }); 7233 emitJUMP( ROOT, "b `L0", iffalse ); 7234 return; } 7235 } 7236 /* CJUMP(BINOP<i,l,f,d,p>(cmpop,CONST<i>(c),j),iftrue,iffalse) */ 7237 if (true 7238 // check statement type 7239 && (stmArg instanceof harpoon.IR.Tree.CJUMP) 7240 && (true 7241 // check expression type 7242 && ((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.BINOP 7243 // check operand types 7244 && ( 7245 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.DOUBLE || 7246 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.FLOAT || 7247 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.LONG || 7248 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.POINTER || 7249 ( ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.INT && ! 7250 (((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.PreciselyTyped && 7251 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).isSmall())) || 7252 false ) 7253 // end check operand types 7254 // check left child 7255 // check expression type 7256 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft() instanceof harpoon.IR.Tree.CONST 7257 // check operand types 7258 && ( 7259 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft().type() == Type.INT && ! 7260 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft() instanceof harpoon.IR.Tree.PreciselyTyped && 7261 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()).isSmall())) || 7262 false ) 7263 // end check operand types 7264 // check right child 7265 // no check needed for ExpId children 7266 ) 7267 ){ 7268 int cmpop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.CJUMP) stmArg).getTest()).op; 7269 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()).value; 7270 harpoon.Temp.Label iffalse = ((harpoon.IR.Tree.CJUMP)stmArg).iffalse; 7271 harpoon.Temp.Label iftrue = ((harpoon.IR.Tree.CJUMP)stmArg).iftrue; 7272 harpoon.IR.Tree.CJUMP ROOT = (harpoon.IR.Tree.CJUMP) stmArg; 7273 _matched_ = true&& ((__CommExp__isCommutative(cmpop=__CommExp__swapCmpOp(cmpop))) && ( isCmpOp(cmpop) && isOpd2Imm(negate(c)) )); 7274 7275 if (_matched_) { // action code! : degree 3 7276 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()); 7277 7278 // this is a frequent special case. 7279 emit( ROOT, "cmn `s0, #"+negate(c)+"\n" + 7280 "b"+cmpOp2Str(cmpop)+" `L0", 7281 null, new Temp[] { j }, new Label[] { iftrue }); 7282 emitJUMP( ROOT, "b `L0", iffalse ); 7283 return; } 7284 } 7285 /* CJUMP(BINOP<i,l,f,d,p>(cmpop,j,CONST<i>(c)),iftrue,iffalse) */ 7286 if (true 7287 // check statement type 7288 && (stmArg instanceof harpoon.IR.Tree.CJUMP) 7289 && (true 7290 // check expression type 7291 && ((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.BINOP 7292 // check operand types 7293 && ( 7294 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.DOUBLE || 7295 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.FLOAT || 7296 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.LONG || 7297 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.POINTER || 7298 ( ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.INT && ! 7299 (((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.PreciselyTyped && 7300 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).isSmall())) || 7301 false ) 7302 // end check operand types 7303 // check left child 7304 // no check needed for ExpId children 7305 // check right child 7306 // check expression type 7307 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight() instanceof harpoon.IR.Tree.CONST 7308 // check operand types 7309 && ( 7310 ( ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight().type() == Type.INT && ! 7311 (((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight() instanceof harpoon.IR.Tree.PreciselyTyped && 7312 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()).isSmall())) || 7313 false ) 7314 // end check operand types 7315 ) 7316 ){ 7317 int cmpop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.CJUMP) stmArg).getTest()).op; 7318 Number c = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()).value; 7319 harpoon.Temp.Label iffalse = ((harpoon.IR.Tree.CJUMP)stmArg).iffalse; 7320 harpoon.Temp.Label iftrue = ((harpoon.IR.Tree.CJUMP)stmArg).iftrue; 7321 harpoon.IR.Tree.CJUMP ROOT = (harpoon.IR.Tree.CJUMP) stmArg; 7322 _matched_ = true&& ( isCmpOp(cmpop) && isOpd2Imm(negate(c)) ); 7323 7324 if (_matched_) { // action code! : degree 3 7325 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()); 7326 7327 // this is a frequent special case. 7328 emit( ROOT, "cmn `s0, #"+negate(c)+"\n" + 7329 "b"+cmpOp2Str(cmpop)+" `L0", 7330 null, new Temp[] { j }, new Label[] { iftrue }); 7331 emitJUMP( ROOT, "b `L0", iffalse ); 7332 return; } 7333 } 7334 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(BINOP<p>(ADD,d1,d2)),src) */ 7335 if (true 7336 // check statement type 7337 && stmArg instanceof harpoon.IR.Tree.MOVE 7338 // check operand types 7339 && ( 7340 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7341 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7342 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7343 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7344 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7345 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7346 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7347 false ) 7348 // end check operand types 7349 && (true 7350 // no check needed for ExpId children 7351 ) 7352 && (true 7353 // check expression type 7354 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 7355 // check operand types 7356 && ( 7357 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 7358 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 7359 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 7360 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 7361 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 7362 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 7363 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 7364 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 7365 false) : ( 7366 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 7367 false) ) ) || 7368 false ) 7369 // end check operand types 7370 // check child 7371 // check expression type 7372 && ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp() instanceof harpoon.IR.Tree.BINOP 7373 // check opcode 7374 && ((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).op == harpoon.IR.Tree.Bop.ADD 7375 // check operand types 7376 && ( 7377 ((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp().type() == Type.POINTER || 7378 false ) 7379 // end check operand types 7380 // check left child 7381 // no check needed for ExpId children 7382 // check right child 7383 // no check needed for ExpId children 7384 ) 7385 ){ 7386 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7387 _matched_ = true; 7388 7389 if (_matched_) { // action code! : degree 3 7390 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 7391 harpoon.Temp.Temp d1 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getLeft()); 7392 harpoon.Temp.Temp d2 = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()).getRight()); 7393 7394 7395 String suffix=""; 7396 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 7397 suffix+="b"; 7398 emit(new InstrMEM(instrFactory, ROOT, 7399 "str"+suffix+" `s0, [`s1, `s2]", 7400 null, new Temp[]{ src, d1, d2 })); 7401 return; } 7402 } 7403 /* CJUMP(BINOP<i,l,f,d,p>(cmpop,j,k),iftrue,iffalse) */ 7404 if (true 7405 // check statement type 7406 && (stmArg instanceof harpoon.IR.Tree.CJUMP) 7407 && (true 7408 // check expression type 7409 && ((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.BINOP 7410 // check operand types 7411 && ( 7412 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.DOUBLE || 7413 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.FLOAT || 7414 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.LONG || 7415 ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.POINTER || 7416 ( ((harpoon.IR.Tree.CJUMP) stmArg).getTest().type() == Type.INT && ! 7417 (((harpoon.IR.Tree.CJUMP) stmArg).getTest() instanceof harpoon.IR.Tree.PreciselyTyped && 7418 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).isSmall())) || 7419 false ) 7420 // end check operand types 7421 // check left child 7422 // no check needed for ExpId children 7423 // check right child 7424 // no check needed for ExpId children 7425 ) 7426 ){ 7427 int cmpop = ((harpoon.IR.Tree.BINOP) ((harpoon.IR.Tree.CJUMP) stmArg).getTest()).op; 7428 harpoon.Temp.Label iffalse = ((harpoon.IR.Tree.CJUMP)stmArg).iffalse; 7429 harpoon.Temp.Label iftrue = ((harpoon.IR.Tree.CJUMP)stmArg).iftrue; 7430 harpoon.IR.Tree.CJUMP ROOT = (harpoon.IR.Tree.CJUMP) stmArg; 7431 _matched_ = true&& ( isCmpOp(cmpop) && 7432 ( ((BINOP) ROOT.getTest()).operandType()==Type.POINTER || 7433 ((BINOP) ROOT.getTest()).operandType()==Type.INT ) ); 7434 7435 if (_matched_) { // action code! : degree 2 7436 harpoon.Temp.Temp j = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getLeft()); 7437 harpoon.Temp.Temp k = munchExp(((harpoon.IR.Tree.BINOP)((harpoon.IR.Tree.CJUMP) stmArg).getTest()).getRight()); 7438 7439 7440 emit( ROOT, "cmp `s0, `s1\n" + 7441 "b"+cmpOp2Str(cmpop)+" `L0", 7442 null, new Temp[] { j , k }, new Label[] { iftrue }); 7443 emitJUMP( ROOT, "b `L0", iffalse ); 7444 return; } 7445 } 7446 /* JUMP(NAME(id)) */ 7447 if (true 7448 // check statement type 7449 && stmArg instanceof harpoon.IR.Tree.JUMP 7450 && (true 7451 // check expression type 7452 && ((harpoon.IR.Tree.JUMP)stmArg).getExp() instanceof harpoon.IR.Tree.NAME 7453 ) 7454 ){ 7455 harpoon.Temp.Label id = ((harpoon.IR.Tree.NAME)((harpoon.IR.Tree.JUMP)stmArg).getExp()).label; 7456 harpoon.IR.Tree.JUMP ROOT = (harpoon.IR.Tree.JUMP) stmArg; 7457 _matched_ = true; 7458 7459 if (_matched_) { // action code! : degree 2 7460 7461 // direct jump 7462 emitJUMP( ROOT, "b `L0", id ); 7463 return; } 7464 } 7465 /* MOVE<i,f,p>(TEMP<i,l,f,d,p>(dst),src) */ 7466 if (true 7467 // check statement type 7468 && stmArg instanceof harpoon.IR.Tree.MOVE 7469 // check operand types 7470 && ( 7471 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7472 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7473 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7474 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7475 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7476 false ) 7477 // end check operand types 7478 && (true 7479 // no check needed for ExpId children 7480 ) 7481 && (true 7482 // check expression type 7483 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.TEMP 7484 // check operand types 7485 && ( 7486 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.DOUBLE || 7487 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 7488 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.LONG || 7489 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 7490 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 7491 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 7492 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 7493 false ) 7494 // end check operand types 7495 ) 7496 ){ 7497 harpoon.Temp.Temp dst = makeTemp((harpoon.IR.Tree.TEMP)((harpoon.IR.Tree.MOVE) stmArg).getDst(), inf.tempFactory()); 7498 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7499 _matched_ = true; 7500 7501 if (_matched_) { // action code! : degree 2 7502 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 7503 7504 7505 declare( dst, code.getTreeDerivation(), ROOT.getSrc()); 7506 emitMOVE( ROOT, "mov `d0, `s0", dst, src ); 7507 return; } 7508 } 7509 /* MOVE<l,d>(TEMP<i,l,f,d,p>(dst),src) */ 7510 if (true 7511 // check statement type 7512 && stmArg instanceof harpoon.IR.Tree.MOVE 7513 // check operand types 7514 && ( 7515 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7516 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7517 false ) 7518 // end check operand types 7519 && (true 7520 // no check needed for ExpId children 7521 ) 7522 && (true 7523 // check expression type 7524 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.TEMP 7525 // check operand types 7526 && ( 7527 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.DOUBLE || 7528 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 7529 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.LONG || 7530 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 7531 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 7532 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 7533 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 7534 false ) 7535 // end check operand types 7536 ) 7537 ){ 7538 harpoon.Temp.Temp dst = makeTemp((harpoon.IR.Tree.TEMP)((harpoon.IR.Tree.MOVE) stmArg).getDst(), inf.tempFactory()); 7539 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7540 _matched_ = true; 7541 7542 if (_matched_) { // action code! : degree 2 7543 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 7544 7545 7546 assert dst instanceof TwoWordTemp : "normal Temp" /* +": "+dst */ 7547 // + harpoon.IR.Tree.Print.print(ROOT) 7548 ; 7549 7550 assert src instanceof TwoWordTemp : "normal Temp" /* +": "+src */ 7551 // + harpoon.IR.Tree.Print.print(ROOT) 7552 ; 7553 7554 declare( dst, code.getTreeDerivation(), ROOT.getSrc() ); 7555 7556 if (true) { 7557 // old way 7558 emit( ROOT, "mov `d0l, `s0l", dst, src ); 7559 emit( ROOT, "mov `d0h, `s0h", dst, src ); 7560 } else { 7561 // new way 7562 emitMOVE( ROOT, "mov `d0l, `s0l\n"+ 7563 "mov `d0h, `s0h", dst, src ); 7564 emit2( ROOT, "@ dummy use of `s0l `s0h", null, new Temp[]{src}); 7565 } 7566 return; } 7567 } 7568 /* MOVE<i,l,f,d,p>(MEM<u:16,s:16>(d),src) */ 7569 if (true 7570 // check statement type 7571 && stmArg instanceof harpoon.IR.Tree.MOVE 7572 // check operand types 7573 && ( 7574 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7575 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7576 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7577 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7578 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7579 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7580 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7581 false ) 7582 // end check operand types 7583 && (true 7584 // no check needed for ExpId children 7585 ) 7586 && (true 7587 // check expression type 7588 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 7589 // check operand types 7590 && ( 7591 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 7592 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 7593 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==16 || 7594 false) : ( 7595 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==16 || 7596 false) ) ) || 7597 false ) 7598 // end check operand types 7599 // check child 7600 // no check needed for ExpId children 7601 ) 7602 ){ 7603 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7604 _matched_ = true; 7605 7606 if (_matched_) { // action code! : degree 2 7607 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 7608 harpoon.Temp.Temp d = munchExp(((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()); 7609 7610 /* hack. ARMv4 has a special instr for this. */ 7611 emit(new InstrMEM(instrFactory, ROOT, 7612 "strb `s0, [`s1, #0] @ store halfword lo", 7613 null, new Temp[]{ src, d })); 7614 // should use 'extra' register instead of re-using src register? 7615 declare ( src, code.getTreeDerivation(), ROOT.getSrc() ); 7616 emit( ROOT, "mov `d0, `s0, ror #8", src, src ); 7617 emit(new InstrMEM(instrFactory, ROOT, 7618 "strb `s0, [`s1, #1] @ store halfword hi", 7619 null, new Temp[]{ src, d })); 7620 emit( ROOT, "mov `d0, `s0, ror #24", src, src ); 7621 return; } 7622 } 7623 /* MOVE<i,l,f,d,p>(MEM<i,f,p,u:8,s:8>(d),src) */ 7624 if (true 7625 // check statement type 7626 && stmArg instanceof harpoon.IR.Tree.MOVE 7627 // check operand types 7628 && ( 7629 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7630 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7631 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7632 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7633 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7634 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7635 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7636 false ) 7637 // end check operand types 7638 && (true 7639 // no check needed for ExpId children 7640 ) 7641 && (true 7642 // check expression type 7643 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 7644 // check operand types 7645 && ( 7646 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.FLOAT || 7647 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.POINTER || 7648 ( ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.INT && ! 7649 (((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.PreciselyTyped && 7650 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall())) || 7651 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).isSmall() && ( 7652 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).signed() ? ( 7653 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 7654 false) : ( 7655 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE) stmArg).getDst()).bitwidth()==8 || 7656 false) ) ) || 7657 false ) 7658 // end check operand types 7659 // check child 7660 // no check needed for ExpId children 7661 ) 7662 ){ 7663 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7664 _matched_ = true; 7665 7666 if (_matched_) { // action code! : degree 2 7667 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 7668 harpoon.Temp.Temp d = munchExp(((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()); 7669 7670 // addressing mode 2 7671 String suffix=""; 7672 if (((MEM)ROOT.getDst()).isSmall() && ((MEM)ROOT.getDst()).bitwidth()==8) 7673 suffix+="b"; 7674 emit(new InstrMEM(instrFactory, ROOT, 7675 "str"+suffix+" `s0, [`s1]", 7676 null, new Temp[]{ src, d })); 7677 return; } 7678 } 7679 /* MOVE<i,l,f,d,p>(MEM<l,d>(dst),src) */ 7680 if (true 7681 // check statement type 7682 && stmArg instanceof harpoon.IR.Tree.MOVE 7683 // check operand types 7684 && ( 7685 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.DOUBLE || 7686 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.FLOAT || 7687 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.LONG || 7688 ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.POINTER || 7689 ( ((harpoon.IR.Tree.MOVE)stmArg).type() == Type.INT && ! 7690 (((harpoon.IR.Tree.MOVE)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 7691 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.MOVE)stmArg)).isSmall())) || 7692 false ) 7693 // end check operand types 7694 && (true 7695 // no check needed for ExpId children 7696 ) 7697 && (true 7698 // check expression type 7699 && ((harpoon.IR.Tree.MOVE) stmArg).getDst() instanceof harpoon.IR.Tree.MEM 7700 // check operand types 7701 && ( 7702 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.DOUBLE || 7703 ((harpoon.IR.Tree.MOVE) stmArg).getDst().type() == Type.LONG || 7704 false ) 7705 // end check operand types 7706 // check child 7707 // no check needed for ExpId children 7708 ) 7709 ){ 7710 harpoon.IR.Tree.MOVE ROOT = (harpoon.IR.Tree.MOVE) stmArg; 7711 _matched_ = true; 7712 7713 if (_matched_) { // action code! : degree 2 7714 harpoon.Temp.Temp src = munchExp(((harpoon.IR.Tree.MOVE) stmArg).getSrc()); 7715 harpoon.Temp.Temp dst = munchExp(((harpoon.IR.Tree.MEM)((harpoon.IR.Tree.MOVE) stmArg).getDst()).getExp()); 7716 7717 7718 emit(new InstrMEM(instrFactory, ROOT, "str `s0l, [`s1]", 7719 null, new Temp[]{ src, dst })); 7720 emit(new InstrMEM(instrFactory, ROOT, "str `s0h, [`s1, #4]", 7721 null, new Temp[]{ src, dst })); 7722 return; } 7723 } 7724 /* CALL(retval,retex,NAME(funcLabel),arglist,handler) */ 7725 if (true 7726 // check statement type 7727 && stmArg instanceof harpoon.IR.Tree.CALL 7728 && (true 7729 // check expression type 7730 && ((harpoon.IR.Tree.CALL) stmArg).getFunc() instanceof harpoon.IR.Tree.NAME 7731 ) 7732 ){ 7733 harpoon.Temp.Label funcLabel = ((harpoon.IR.Tree.NAME)((harpoon.IR.Tree.CALL) stmArg).getFunc()).label; 7734 harpoon.Temp.Label handler = ((harpoon.IR.Tree.CALL)stmArg).getHandler().label; 7735 harpoon.IR.Tree.CALL ROOT = (harpoon.IR.Tree.CALL) stmArg; 7736 _matched_ = true; 7737 7738 if (_matched_) { // action code! : degree 2 7739 harpoon.Temp.Temp retval = (((harpoon.IR.Tree.CALL)stmArg).getRetval()==null) ? null : munchExp(((harpoon.IR.Tree.CALL)stmArg).getRetval()); 7740 harpoon.Temp.Temp retex = munchExp(((harpoon.IR.Tree.CALL)stmArg).getRetex()); 7741 /* munch argument ExpList into a TempList */ 7742 harpoon.Temp.TempList arglist = new harpoon.Temp.TempList(null, null); 7743 { harpoon.Temp.TempList tl=arglist; 7744 for (harpoon.IR.Tree.ExpList el = ((harpoon.IR.Tree.CALL)stmArg).getArgs(); el!=null; el=el.tail, tl=tl.tail) 7745 tl.tail = new harpoon.Temp.TempList(munchExp(el.head), null); 7746 } 7747 arglist = arglist.tail; 7748 7749 7750 CallState cs = emitCallPrologue(ROOT, arglist, code.getTreeDerivation()); 7751 Label rlabel = new Label(), elabel = new Label(); 7752 // do the call. bl has a 24-bit offset field, which should be plenty. 7753 // note that r0-r3, LR and IP are clobbered by the call. 7754 declare( LR, HClass.Void ); 7755 emit2( ROOT, "adr `d0, "+rlabel, new Temp[] { LR }, null ); 7756 7757 declare( r0, HClass.Void ); declare( r1, HClass.Void ); 7758 declare( r2, HClass.Void ); declare( r3, HClass.Void ); 7759 declare( PC, HClass.Void ); declare( IP, HClass.Void ); 7760 7761 emitCallNoFall( ROOT, cs.prependSPOffset("b "+funcLabel + 7762 " @ clobbers r0-r3, LR, IP"), 7763 new Temp[] { r0,r1,r2,r3,IP,LR }, 7764 (Temp[]) cs.callUses.toArray(new Temp[cs.callUses.size()]), 7765 new Label[] { rlabel, elabel } ); 7766 // make handler stub. 7767 emitLABEL( ROOT, elabel+":", elabel); 7768 emitHandlerStub(ROOT, retex, handler); 7769 // normal return 7770 emitLABEL( ROOT, rlabel+":", rlabel); 7771 emitCallEpilogue(ROOT, false, retval, 7772 ((ROOT.getRetval()==null)?null: 7773 code.getTreeDerivation().typeMap(ROOT.getRetval())), cs); 7774 // emit fixup table. 7775 emitCallFixup(ROOT, rlabel, elabel); 7776 return; } 7777 } 7778 /* NATIVECALL(retval,NAME(funcLabel),arglist) */ 7779 if (true 7780 // check statement type 7781 && stmArg instanceof harpoon.IR.Tree.NATIVECALL 7782 && (true 7783 // check expression type 7784 && ((harpoon.IR.Tree.NATIVECALL) stmArg).getFunc() instanceof harpoon.IR.Tree.NAME 7785 ) 7786 ){ 7787 harpoon.Temp.Label funcLabel = ((harpoon.IR.Tree.NAME)((harpoon.IR.Tree.NATIVECALL) stmArg).getFunc()).label; 7788 harpoon.IR.Tree.NATIVECALL ROOT = (harpoon.IR.Tree.NATIVECALL) stmArg; 7789 _matched_ = true; 7790 7791 if (_matched_) { // action code! : degree 2 7792 harpoon.Temp.Temp retval = (((harpoon.IR.Tree.NATIVECALL)stmArg).getRetval()==null) ? null : munchExp(((harpoon.IR.Tree.NATIVECALL)stmArg).getRetval()); 7793 /* munch argument ExpList into a TempList */ 7794 harpoon.Temp.TempList arglist = new harpoon.Temp.TempList(null, null); 7795 { harpoon.Temp.TempList tl=arglist; 7796 for (harpoon.IR.Tree.ExpList el = ((harpoon.IR.Tree.NATIVECALL)stmArg).getArgs(); el!=null; el=el.tail, tl=tl.tail) 7797 tl.tail = new harpoon.Temp.TempList(munchExp(el.head), null); 7798 } 7799 arglist = arglist.tail; 7800 7801 7802 CallState cs = emitCallPrologue(ROOT, arglist, code.getTreeDerivation()); 7803 // do the call. bl has a 24-bit offset field, which should be plenty. 7804 // note that r0-r3, LR and IP are clobbered by the call. 7805 emitNativeCall( ROOT, cs.prependSPOffset("bl "+funcLabel + 7806 " @clobbers r0-r3, LR, IP"), 7807 new Temp[] { r0,r1,r2,r3,IP,LR }, 7808 (Temp[]) cs.callUses.toArray(new Temp[cs.callUses.size()]), 7809 true, null ); 7810 // clean up. 7811 emitCallEpilogue(ROOT, true, retval, 7812 ((ROOT.getRetval()==null)?null: 7813 code.getTreeDerivation().typeMap(ROOT.getRetval())), cs); 7814 return; } 7815 } 7816 /* DATUM(CONST<i,f>(exp)) */ 7817 if (true 7818 // check statement type 7819 && stmArg instanceof harpoon.IR.Tree.DATUM 7820 && (true 7821 // check expression type 7822 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 7823 // check operand types 7824 && ( 7825 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.FLOAT || 7826 ( ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.INT && ! 7827 (((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.PreciselyTyped && 7828 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).isSmall())) || 7829 false ) 7830 // end check operand types 7831 ) 7832 ){ 7833 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 7834 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 7835 _matched_ = true; 7836 7837 if (_matched_) { // action code! : degree 2 7838 7839 7840 int i = (ROOT.getData().type()==Type.INT) ? exp.intValue() 7841 : Float.floatToIntBits(exp.floatValue()); 7842 String lo = "0x"+Integer.toHexString(i); 7843 emitDIRECTIVE( ROOT, "\t.word "+lo+" @ "+exp); 7844 return; } 7845 } 7846 /* DATUM(CONST<l,d>(exp)) */ 7847 if (true 7848 // check statement type 7849 && stmArg instanceof harpoon.IR.Tree.DATUM 7850 && (true 7851 // check expression type 7852 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 7853 // check operand types 7854 && ( 7855 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.DOUBLE || 7856 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.LONG || 7857 false ) 7858 // end check operand types 7859 ) 7860 ){ 7861 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 7862 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 7863 _matched_ = true; 7864 7865 if (_matched_) { // action code! : degree 2 7866 7867 7868 long l = (ROOT.getData().type()==Type.LONG) ? exp.longValue() 7869 : Double.doubleToLongBits(exp.doubleValue()); 7870 String lo = "0x"+Integer.toHexString((int)l); 7871 String hi = "0x"+Integer.toHexString((int)(l>>32)); 7872 // doubles are stored in reverse order on the StrongARM. No, I don't 7873 // know why. I suspect the StrongARM library designers were on *crack*! 7874 if (ROOT.getData().type()==Type.LONG) 7875 emitDIRECTIVE( ROOT, "\t.word "+lo+" @ lo("+exp+")"); 7876 emitDIRECTIVE( ROOT, "\t.word "+hi+" @ hi("+exp+")"); 7877 if (ROOT.getData().type()==Type.DOUBLE) 7878 emitDIRECTIVE( ROOT, "\t.word "+lo+" @ lo("+exp+")"); 7879 return; } 7880 } 7881 /* DATUM(CONST<p>(exp)) */ 7882 if (true 7883 // check statement type 7884 && stmArg instanceof harpoon.IR.Tree.DATUM 7885 && (true 7886 // check expression type 7887 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 7888 // check operand types 7889 && ( 7890 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.POINTER || 7891 false ) 7892 // end check operand types 7893 ) 7894 ){ 7895 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 7896 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 7897 _matched_ = true; 7898 7899 if (_matched_) { // action code! : degree 2 7900 7901 7902 emitDIRECTIVE( ROOT, "\t.word 0 @ null pointer constant"); 7903 return; } 7904 } 7905 /* DATUM(CONST<u:8,s:8>(exp)) */ 7906 if (true 7907 // check statement type 7908 && stmArg instanceof harpoon.IR.Tree.DATUM 7909 && (true 7910 // check expression type 7911 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 7912 // check operand types 7913 && ( 7914 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).isSmall() && ( 7915 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).signed() ? ( 7916 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==8 || 7917 false) : ( 7918 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==8 || 7919 false) ) ) || 7920 false ) 7921 // end check operand types 7922 ) 7923 ){ 7924 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 7925 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 7926 _matched_ = true; 7927 7928 if (_matched_) { // action code! : degree 2 7929 7930 7931 String chardesc = (exp.intValue()>=32 && exp.intValue()<127 7932 && exp.intValue()!=96 /* backquotes cause problems */ 7933 && exp.intValue()!=34 /* so do double quotes */) ? 7934 ("\t@ char "+((char)exp.intValue())) : ""; 7935 emitDIRECTIVE( ROOT, "\t.byte "+exp+chardesc); 7936 return; } 7937 } 7938 /* DATUM(CONST<u:16,s:16>(exp)) */ 7939 if (true 7940 // check statement type 7941 && stmArg instanceof harpoon.IR.Tree.DATUM 7942 && (true 7943 // check expression type 7944 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 7945 // check operand types 7946 && ( 7947 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).isSmall() && ( 7948 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).signed() ? ( 7949 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==16 || 7950 false) : ( 7951 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==16 || 7952 false) ) ) || 7953 false ) 7954 // end check operand types 7955 ) 7956 ){ 7957 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 7958 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 7959 _matched_ = true; 7960 7961 if (_matched_) { // action code! : degree 2 7962 7963 7964 String chardesc = (exp.intValue()>=32 && exp.intValue()<127 7965 && exp.intValue()!=96 /* backquotes cause problems */ 7966 && exp.intValue()!=34 /* so do double quotes */) ? 7967 ("\t@ char "+((char)exp.intValue())) : ""; 7968 emitDIRECTIVE( ROOT, "\t.short "+exp+chardesc); 7969 return; } 7970 } 7971 /* DATUM(NAME(l)) */ 7972 if (true 7973 // check statement type 7974 && stmArg instanceof harpoon.IR.Tree.DATUM 7975 && (true 7976 // check expression type 7977 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.NAME 7978 ) 7979 ){ 7980 harpoon.Temp.Label l = ((harpoon.IR.Tree.NAME)((harpoon.IR.Tree.DATUM)stmArg).getData()).label; 7981 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 7982 _matched_ = true; 7983 7984 if (_matched_) { // action code! : degree 2 7985 7986 7987 emitDIRECTIVE( ROOT, "\t.word "+l); 7988 return; } 7989 } 7990 /* METHOD(params) */ 7991 if (true 7992 // check statement type 7993 && stmArg instanceof harpoon.IR.Tree.METHOD 7994 ){ 7995 harpoon.IR.Tree.METHOD ROOT = (harpoon.IR.Tree.METHOD) stmArg; 7996 _matched_ = true; 7997 7998 if (_matched_) { // action code! : degree 1 7999 harpoon.Temp.Temp[] params = new harpoon.Temp.Temp[((harpoon.IR.Tree.METHOD)stmArg).getParamsLength()]; 8000 for (int _i_=0; _i_<params.length; _i_++) 8001 params[_i_] = munchExp(((harpoon.IR.Tree.METHOD)stmArg).getParams(_i_)); 8002 8003 8004 // mark entry point. 8005 declare(PC, HClass.Void); 8006 declare(SP, HClass.Void); 8007 declare(FP, HClass.Void); 8008 emit(new InstrENTRY( instrFactory, ROOT )); 8009 // move arguments to temporaries. 8010 int loc=0; 8011 // skip param[0], which is the explicit 'exceptional return address' 8012 for (int i=1; i<params.length; i++) { 8013 declare(params[i], code.getTreeDerivation(), ROOT.getParams(i)); 8014 if (ROOT.getParams(i).isDoubleWord()) { 8015 if (loc<=2) { // both halves in registers 8016 // ack. emitMOVE isn't working with long/double types. 8017 emit( ROOT, "mov `d0l, `s0", params[i],regfile.reg[loc++]); 8018 emit( ROOT, "mov `d0h, `s0", params[i],regfile.reg[loc++]); 8019 } else if (loc==3) { // one half in register, one on stack 8020 // ack. emitMOVE isn't working with long/double types. 8021 emit( ROOT, "mov `d0l, `s0", params[i],regfile.reg[loc++]); 8022 emit(new InstrMEM( instrFactory, ROOT, 8023 "ldr `d0h, [`s0, #"+(4*(loc++)-12)+"]", 8024 new Temp[] {params[i]}, new Temp[] {FP})); 8025 } else { // both halves on stack. 8026 emit(new InstrMEM( instrFactory, ROOT, 8027 "ldr `d0l, [`s0, #"+(4*(loc++)-12)+"]", 8028 new Temp[] {params[i]}, new Temp[] {FP})); 8029 emit(new InstrMEM( instrFactory, ROOT, 8030 "ldr `d0h, [`s0, #"+(4*(loc++)-12)+"]", 8031 new Temp[] {params[i]}, new Temp[] {FP})); 8032 } 8033 } else { // single word. 8034 if (loc<4) { // in register 8035 emitMOVE( ROOT, "mov `d0, `s0", params[i], regfile.reg[loc++]); 8036 } else { // on stack 8037 emit(new InstrMEM( instrFactory, ROOT, 8038 "ldr `d0, [`s0, #"+(4*(loc++)-12)+"]", 8039 new Temp[] {params[i]}, new Temp[] {FP})); 8040 } 8041 } 8042 } 8043 return; } 8044 } 8045 /* CJUMP(test,iftrue,iffalse) */ 8046 if (true 8047 // check statement type 8048 && (stmArg instanceof harpoon.IR.Tree.CJUMP) 8049 && (true 8050 // no check needed for ExpId children 8051 ) 8052 ){ 8053 harpoon.Temp.Label iffalse = ((harpoon.IR.Tree.CJUMP)stmArg).iffalse; 8054 harpoon.Temp.Label iftrue = ((harpoon.IR.Tree.CJUMP)stmArg).iftrue; 8055 harpoon.IR.Tree.CJUMP ROOT = (harpoon.IR.Tree.CJUMP) stmArg; 8056 _matched_ = true; 8057 8058 if (_matched_) { // action code! : degree 1 8059 harpoon.Temp.Temp test = munchExp(((harpoon.IR.Tree.CJUMP) stmArg).getTest()); 8060 8061 8062 Instr j1 = emit( ROOT, "cmp `s0, #0 \n" + 8063 "beq `L0", 8064 null, new Temp[]{ test }, 8065 new Label[]{ iffalse }); 8066 Instr j2 = emitJUMP( ROOT, "b `L0", iftrue ); 8067 return; } 8068 } 8069 /* EXPR(e) */ 8070 if (true 8071 // check statement type 8072 && stmArg instanceof harpoon.IR.Tree.EXPR 8073 && (true 8074 // no check needed for ExpId children 8075 ) 8076 ){ 8077 harpoon.IR.Tree.EXPR ROOT = (harpoon.IR.Tree.EXPR) stmArg; 8078 _matched_ = true; 8079 8080 if (_matched_) { // action code! : degree 1 8081 harpoon.Temp.Temp e = munchExp(((harpoon.IR.Tree.EXPR)stmArg).getExp()); 8082 8083 8084 /* this is a statement that's just an 8085 expression; just throw away 8086 calculated value */ 8087 return; } 8088 } 8089 /* JUMP(e) */ 8090 if (true 8091 // check statement type 8092 && stmArg instanceof harpoon.IR.Tree.JUMP 8093 && (true 8094 // no check needed for ExpId children 8095 ) 8096 ){ 8097 harpoon.IR.Tree.JUMP ROOT = (harpoon.IR.Tree.JUMP) stmArg; 8098 _matched_ = true; 8099 8100 if (_matched_) { // action code! : degree 1 8101 harpoon.Temp.Temp e = munchExp(((harpoon.IR.Tree.JUMP)stmArg).getExp()); 8102 8103 8104 List<Label> labelList = LabelList.toList( ROOT.targets ); 8105 declare( PC, HClass.Void ); 8106 emit(new Instr( instrFactory, ROOT, 8107 "mov `d0, `s0", 8108 new Temp[]{ PC }, 8109 // fake use of PC so that the register allocator 8110 // doesn't think that PC is not live above this point 8111 new Temp[]{ e, PC }, 8112 false, labelList ) { 8113 public boolean hasModifiableTargets(){ 8114 return false; 8115 } 8116 }); 8117 return; } 8118 } 8119 /* LABEL(id) */ 8120 if (true 8121 // check statement type 8122 && stmArg instanceof harpoon.IR.Tree.LABEL 8123 ){ 8124 String id = ((harpoon.IR.Tree.LABEL)stmArg).label.toString(); 8125 8126 harpoon.IR.Tree.LABEL ROOT = (harpoon.IR.Tree.LABEL) stmArg; 8127 _matched_ = true; 8128 8129 if (_matched_) { // action code! : degree 1 8130 8131 8132 if (ROOT.exported) { 8133 emitLABEL( ROOT, "\t.global "+ROOT.label+"\n"+ 8134 ROOT.label + ":", ROOT.label); 8135 } else { 8136 emitLABEL( ROOT, ROOT.label + ":", ROOT.label); 8137 } 8138 return; } 8139 } 8140 /* RETURN<i,f,p>(val) */ 8141 if (true 8142 // check expression type 8143 && stmArg instanceof harpoon.IR.Tree.RETURN 8144 // check operand types 8145 && ( 8146 ((harpoon.IR.Tree.RETURN)stmArg).type() == Type.FLOAT || 8147 ((harpoon.IR.Tree.RETURN)stmArg).type() == Type.POINTER || 8148 ( ((harpoon.IR.Tree.RETURN)stmArg).type() == Type.INT && ! 8149 (((harpoon.IR.Tree.RETURN)stmArg) instanceof harpoon.IR.Tree.PreciselyTyped && 8150 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.RETURN)stmArg)).isSmall())) || 8151 false ) 8152 // end check operand types 8153 && (true 8154 // no check needed for ExpId children 8155 ) 8156 ){ 8157 harpoon.IR.Tree.RETURN ROOT = (harpoon.IR.Tree.RETURN) stmArg; 8158 _matched_ = true; 8159 8160 if (_matched_) { // action code! : degree 1 8161 harpoon.Temp.Temp val = munchExp(((harpoon.IR.Tree.RETURN) stmArg).getRetval()); 8162 8163 8164 declare( r0, code.getTreeDerivation(), ROOT.getRetval() ); 8165 emitMOVE( ROOT, "mov `d0, `s0", r0, val ); 8166 // mark exit point. 8167 emit(new InstrEXIT( instrFactory, ROOT )); 8168 return; } 8169 } 8170 /* RETURN<l,d>(val) */ 8171 if (true 8172 // check expression type 8173 && stmArg instanceof harpoon.IR.Tree.RETURN 8174 // check operand types 8175 && ( 8176 ((harpoon.IR.Tree.RETURN)stmArg).type() == Type.DOUBLE || 8177 ((harpoon.IR.Tree.RETURN)stmArg).type() == Type.LONG || 8178 false ) 8179 // end check operand types 8180 && (true 8181 // no check needed for ExpId children 8182 ) 8183 ){ 8184 harpoon.IR.Tree.RETURN ROOT = (harpoon.IR.Tree.RETURN) stmArg; 8185 _matched_ = true; 8186 8187 if (_matched_) { // action code! : degree 1 8188 harpoon.Temp.Temp val = munchExp(((harpoon.IR.Tree.RETURN) stmArg).getRetval()); 8189 8190 8191 // these should really be InstrMOVEs! 8192 declare( r0, HClass.Void ); 8193 declare( r1, HClass.Void ); 8194 emit( ROOT, "mov `d0, `s0l", r0, val); 8195 emit( ROOT, "mov `d0, `s0h", r1, val); 8196 // mark exit point. 8197 emit(new InstrEXIT( instrFactory, ROOT )); 8198 return; } 8199 } 8200 /* THROW(val,handler) */ 8201 if (true 8202 // check expression type 8203 && stmArg instanceof harpoon.IR.Tree.THROW 8204 && (true 8205 // no check needed for ExpId children 8206 ) 8207 && (true 8208 // no check needed for ExpId children 8209 ) 8210 ){ 8211 harpoon.IR.Tree.THROW ROOT = (harpoon.IR.Tree.THROW) stmArg; 8212 _matched_ = true; 8213 8214 if (_matched_) { // action code! : degree 1 8215 harpoon.Temp.Temp val = munchExp(((harpoon.IR.Tree.THROW) stmArg).getRetex()); 8216 harpoon.Temp.Temp handler = munchExp(((harpoon.IR.Tree.THROW) stmArg).getHandler()); 8217 8218 8219 // ignore handler, as our runtime does clever things instead. 8220 declare( r0, code.getTreeDerivation(), ROOT.getRetex() ); 8221 emitMOVE( ROOT, "mov `d0, `s0", r0, val ); 8222 declareCALL(); 8223 declare( r0, code.getTreeDerivation(), ROOT.getRetex() ); 8224 emit( ROOT, "bl "+nameMap.c_function_name("_lookup_handler")+ 8225 " @ (only r0 & fp are preserved during lookup)", 8226 new Temp[] { r1, r2, r3, LR }, // clobbers 8227 new Temp[] { FP }, true, null); 8228 // mark exit point. 8229 emit(new InstrEXIT( instrFactory, ROOT )); 8230 return; } 8231 } 8232 /* CALL(retval,retex,func,arglist,handler) */ 8233 if (true 8234 // check statement type 8235 && stmArg instanceof harpoon.IR.Tree.CALL 8236 && (true 8237 // no check needed for ExpId children 8238 ) 8239 ){ 8240 harpoon.Temp.Label handler = ((harpoon.IR.Tree.CALL)stmArg).getHandler().label; 8241 harpoon.IR.Tree.CALL ROOT = (harpoon.IR.Tree.CALL) stmArg; 8242 _matched_ = true; 8243 8244 if (_matched_) { // action code! : degree 1 8245 harpoon.Temp.Temp func = munchExp(((harpoon.IR.Tree.CALL) stmArg).getFunc()); 8246 harpoon.Temp.Temp retval = (((harpoon.IR.Tree.CALL)stmArg).getRetval()==null) ? null : munchExp(((harpoon.IR.Tree.CALL)stmArg).getRetval()); 8247 harpoon.Temp.Temp retex = munchExp(((harpoon.IR.Tree.CALL)stmArg).getRetex()); 8248 /* munch argument ExpList into a TempList */ 8249 harpoon.Temp.TempList arglist = new harpoon.Temp.TempList(null, null); 8250 { harpoon.Temp.TempList tl=arglist; 8251 for (harpoon.IR.Tree.ExpList el = ((harpoon.IR.Tree.CALL)stmArg).getArgs(); el!=null; el=el.tail, tl=tl.tail) 8252 tl.tail = new harpoon.Temp.TempList(munchExp(el.head), null); 8253 } 8254 arglist = arglist.tail; 8255 8256 8257 CallState cs = emitCallPrologue(ROOT, arglist, code.getTreeDerivation()); 8258 Label rlabel = new Label(), elabel = new Label(); 8259 // next two instructions are *not* InstrMOVEs, as they have side-effects 8260 emit2( ROOT, "adr `d0, "+rlabel, new Temp[] { LR }, null ); 8261 // call uses 'func' as `s0 8262 // we add a fake use of PC so that it remains live above the call. 8263 cs.callUses.add(PC); cs.callUses.add(0, func); 8264 // note that r0-r3, LR and IP are clobbered by the call. 8265 emitCallNoFall( ROOT,cs.prependSPOffset("mov `d0, `s0 @ clobbers r0-r3,LR,IP"), 8266 new Temp[]{ PC, r0, r1, r2, r3, IP, LR }, 8267 (Temp[]) cs.callUses.toArray(new Temp[cs.callUses.size()]), 8268 new Label[] { rlabel, elabel } ); 8269 // make handler stub. 8270 emitLABEL( ROOT, elabel+":", elabel); 8271 emitHandlerStub(ROOT, retex, handler); 8272 // normal return 8273 emitLABEL( ROOT, rlabel+":", rlabel); 8274 emitCallEpilogue(ROOT, false, retval, 8275 ((ROOT.getRetval()==null)?null: 8276 code.getTreeDerivation().typeMap(ROOT.getRetval())), cs); 8277 // emit fixup table. 8278 emitCallFixup(ROOT, rlabel, elabel); 8279 return; } 8280 } 8281 /* NATIVECALL(retval,func,arglist) */ 8282 if (true 8283 // check statement type 8284 && stmArg instanceof harpoon.IR.Tree.NATIVECALL 8285 && (true 8286 // no check needed for ExpId children 8287 ) 8288 ){ 8289 harpoon.IR.Tree.NATIVECALL ROOT = (harpoon.IR.Tree.NATIVECALL) stmArg; 8290 _matched_ = true; 8291 8292 if (_matched_) { // action code! : degree 1 8293 harpoon.Temp.Temp func = munchExp(((harpoon.IR.Tree.NATIVECALL) stmArg).getFunc()); 8294 harpoon.Temp.Temp retval = (((harpoon.IR.Tree.NATIVECALL)stmArg).getRetval()==null) ? null : munchExp(((harpoon.IR.Tree.NATIVECALL)stmArg).getRetval()); 8295 /* munch argument ExpList into a TempList */ 8296 harpoon.Temp.TempList arglist = new harpoon.Temp.TempList(null, null); 8297 { harpoon.Temp.TempList tl=arglist; 8298 for (harpoon.IR.Tree.ExpList el = ((harpoon.IR.Tree.NATIVECALL)stmArg).getArgs(); el!=null; el=el.tail, tl=tl.tail) 8299 tl.tail = new harpoon.Temp.TempList(munchExp(el.head), null); 8300 } 8301 arglist = arglist.tail; 8302 8303 8304 CallState cs = emitCallPrologue(ROOT, arglist, code.getTreeDerivation()); 8305 // next two instructions are *not* InstrMOVEs, as they have side-effects 8306 emit( ROOT, "mov `d0, `s0", LR, PC ); 8307 // call uses 'func' as `s0 8308 // we add a fake use of PC so that it remains live above the call. 8309 cs.callUses.add(PC); cs.callUses.add(0, func); 8310 // note that r0-r3, LR and IP are clobbered by the call. 8311 emitNativeCall( ROOT, cs.prependSPOffset("mov `d0, `s0 @ clobbers r0-r3, LR, IP"), 8312 new Temp[]{ PC, r0, r1, r2, r3, IP, LR }, 8313 (Temp[]) cs.callUses.toArray(new Temp[cs.callUses.size()]), 8314 true, null); 8315 // clean up. 8316 emitCallEpilogue(ROOT, true, retval, 8317 ((ROOT.getRetval()==null)?null: 8318 code.getTreeDerivation().typeMap(ROOT.getRetval())), cs); 8319 return; } 8320 } 8321 /* ALIGN(n) */ 8322 if (true 8323 // check statement type 8324 && stmArg instanceof harpoon.IR.Tree.ALIGN 8325 ){ 8326 int n = ((harpoon.IR.Tree.ALIGN)stmArg).alignment; harpoon.IR.Tree.ALIGN ROOT = (harpoon.IR.Tree.ALIGN) stmArg; 8327 _matched_ = true; 8328 8329 if (_matched_) { // action code! : degree 1 8330 8331 8332 emitDIRECTIVE( ROOT, "\t.balign "+n); 8333 return; } 8334 } 8335 /* SEGMENT(CLASS) */ 8336 if (true 8337 // check statement type 8338 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8339 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.CLASS 8340 ){ 8341 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8342 _matched_ = true; 8343 8344 if (_matched_) { // action code! : degree 1 8345 8346 8347 emitDIRECTIVE( ROOT, !is_elf?".data 1":".section .flex.class"); 8348 8349 return; } 8350 } 8351 /* SEGMENT(CODE) */ 8352 if (true 8353 // check statement type 8354 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8355 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.CODE 8356 ){ 8357 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8358 _matched_ = true; 8359 8360 if (_matched_) { // action code! : degree 1 8361 8362 8363 // gas 2.7 does not support naming the code section...not 8364 // sure what to do about this yet... 8365 // emitDIRECTIVE( ROOT, !is_elf?".code 32":".section code"); 8366 emitDIRECTIVE( ROOT, !is_elf?".text 0":".section .flex.code"); 8367 return; } 8368 } 8369 /* SEGMENT(GC) */ 8370 if (true 8371 // check statement type 8372 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8373 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.GC 8374 ){ 8375 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8376 _matched_ = true; 8377 8378 if (_matched_) { // action code! : degree 1 8379 8380 8381 emitDIRECTIVE( ROOT, !is_elf?".data 2":".section .flex.gc"); 8382 return; } 8383 } 8384 /* SEGMENT(INIT_DATA) */ 8385 if (true 8386 // check statement type 8387 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8388 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.INIT_DATA 8389 ){ 8390 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8391 _matched_ = true; 8392 8393 if (_matched_) { // action code! : degree 1 8394 8395 8396 emitDIRECTIVE( ROOT, !is_elf?".data 3":".section .flex.init_data"); 8397 return; } 8398 } 8399 /* SEGMENT(STATIC_OBJECTS) */ 8400 if (true 8401 // check statement type 8402 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8403 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STATIC_OBJECTS 8404 ){ 8405 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8406 _matched_ = true; 8407 8408 if (_matched_) { // action code! : degree 1 8409 8410 8411 emitDIRECTIVE( ROOT, !is_elf?".data 4":".section .flex.static_objects"); 8412 return; } 8413 } 8414 /* SEGMENT(STATIC_PRIMITIVES) */ 8415 if (true 8416 // check statement type 8417 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8418 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STATIC_PRIMITIVES 8419 ){ 8420 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8421 _matched_ = true; 8422 8423 if (_matched_) { // action code! : degree 1 8424 8425 8426 emitDIRECTIVE( ROOT, !is_elf?".data 5":".section .flex.static_primitives"); 8427 return; } 8428 } 8429 /* SEGMENT(STRING_CONSTANTS) */ 8430 if (true 8431 // check statement type 8432 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8433 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STRING_CONSTANTS 8434 ){ 8435 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8436 _matched_ = true; 8437 8438 if (_matched_) { // action code! : degree 1 8439 8440 8441 emitDIRECTIVE( ROOT, !is_elf?".data 6":".section .flex.string_constants"); 8442 return; } 8443 } 8444 /* SEGMENT(STRING_DATA) */ 8445 if (true 8446 // check statement type 8447 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8448 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STRING_DATA 8449 ){ 8450 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8451 _matched_ = true; 8452 8453 if (_matched_) { // action code! : degree 1 8454 8455 8456 emitDIRECTIVE( ROOT, !is_elf?".data 7":".section .flex.string_data"); 8457 return; } 8458 } 8459 /* SEGMENT(REFLECTION_OBJECTS) */ 8460 if (true 8461 // check statement type 8462 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8463 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.REFLECTION_OBJECTS 8464 ){ 8465 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8466 _matched_ = true; 8467 8468 if (_matched_) { // action code! : degree 1 8469 8470 8471 emitDIRECTIVE( ROOT, !is_elf?".data 8":".section .flex.reflection_objects"); 8472 return; } 8473 } 8474 /* SEGMENT(REFLECTION_DATA) */ 8475 if (true 8476 // check statement type 8477 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8478 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.REFLECTION_DATA 8479 ){ 8480 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8481 _matched_ = true; 8482 8483 if (_matched_) { // action code! : degree 1 8484 8485 8486 emitDIRECTIVE( ROOT, !is_elf?".data 9":".section .flex.reflection_data"); 8487 return; } 8488 } 8489 /* SEGMENT(GC_INDEX) */ 8490 if (true 8491 // check statement type 8492 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8493 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.GC_INDEX 8494 ){ 8495 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8496 _matched_ = true; 8497 8498 if (_matched_) { // action code! : degree 1 8499 8500 8501 emitDIRECTIVE( ROOT, !is_elf?".data 10":".section .flex.gc_index"); 8502 return; } 8503 } 8504 /* SEGMENT(TEXT) */ 8505 if (true 8506 // check statement type 8507 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8508 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.TEXT 8509 ){ 8510 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8511 _matched_ = true; 8512 8513 if (_matched_) { // action code! : degree 1 8514 8515 8516 emitDIRECTIVE( ROOT, !is_elf?".text":".section .text"); 8517 return; } 8518 } 8519 /* SEGMENT(ZERO_DATA) */ 8520 if (true 8521 // check statement type 8522 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8523 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.ZERO_DATA 8524 ){ 8525 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8526 _matched_ = true; 8527 8528 if (_matched_) { // action code! : degree 1 8529 8530 8531 // gas 2.7 does not allow BSS subsections...use .comm and .lcomm 8532 // for the variables to be initialized to zero 8533 // emitDIRECTIVE( ROOT, ".bss \t@.section zero"); 8534 emitDIRECTIVE(ROOT, !is_elf?".bss":".section .flex.zero"); 8535 return; } 8536 } 8537 assert _matched_ : "Uh oh...\nmaximal munch didn't match anything...SPEC file\nis not complete enough for this program\nDied on "+prettyPrint(stmArg)+" in " + prettyPrint(globalStmArg); 8538 } // end munchStm 8539 public void visit(harpoon.IR.Tree.Tree treee){ 8540 assert false : "Should never visit generic harpoon.IR.Tree.Treein CggVisitor"; 8541 } // end visit(harpoon.IR.Tree.Tree) 8542 public void visit(harpoon.IR.Tree.Stm treee){ 8543 debug("munching "+treee+" "); 8544 munchStm(treee); 8545 } // end visit(harpoon.IR.Tree.Stm) 8546 public void visit(harpoon.IR.Tree.SEQ treee){ 8547 treee.getLeft().accept(this); 8548 treee.getRight().accept(this); 8549 } 8550 } 8551 CggVisitor visitor = new CggVisitor(); 8552 harpoon.IR.Tree.Tree t = (harpoon.IR.Tree.Tree) code.getRootElement(); 8553 t.accept(visitor); 8554 clearDecl(); // reset temp type mappings 8555 8556 // *** METHOD EPILOGUE *** 8557 8558 8559 assert first != null : "Should always generate some instrs"; 8560 return net.cscott.jutil.Default.pair(first, getDerivation()); 8561 } 8562 /** Generates assembly code from a <code>harpoon.IR.Tree.Data</code>. 8563 <BR> <B>modifies:</B> <code>this</code> 8564 <BR> <B>effects:</B> 8565 Scans <code>tree</code> to define a layout of 8566 Instructions, calling auxillary methods 8567 and data structures as defined in the .Spec file 8568 @param tree Set of abstract <code>Tree</code> instructions 8569 that form the body of the data structure being compiled. 8570 */ 8571 public final harpoon.IR.Assem.Instr cgg_genData(harpoon.IR.Tree.Data code, final harpoon.IR.Assem.InstrFactory inf) { 8572 _methodPrologue_(inf); 8573 8574 // *** METHOD PROLOGUE *** 8575 this.instrFactory = inf; // XXX this should probably move to superclass 8576 8577 final class CggVisitor extends harpoon.IR.Tree.TreeVisitor { 8578 harpoon.Temp.Temp munchExp(harpoon.IR.Tree.Exp expArg) { 8579 boolean _matched_ = false; 8580 clearDecl(); // reset temp type mappings 8581 assert false : "Uh oh...\nmaximal munch didn't match anything...SPEC file\nis not complete enough for this program\nDied on "+prettyPrint(expArg)+" in " + prettyPrint(globalStmArg); 8582 return null; // doesn't matter, we're dead if we didn't match... 8583 } // end munchExp 8584 harpoon.IR.Tree.Stm globalStmArg=null; 8585 void munchStm(harpoon.IR.Tree.Stm stmArg) { 8586 globalStmArg = stmArg; 8587 boolean _matched_ = false; 8588 clearDecl(); // reset temp type mappings 8589 /* DATUM(CONST<i,f>(exp)) */ 8590 if (true 8591 // check statement type 8592 && stmArg instanceof harpoon.IR.Tree.DATUM 8593 && (true 8594 // check expression type 8595 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 8596 // check operand types 8597 && ( 8598 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.FLOAT || 8599 ( ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.INT && ! 8600 (((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.PreciselyTyped && 8601 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).isSmall())) || 8602 false ) 8603 // end check operand types 8604 ) 8605 ){ 8606 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 8607 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 8608 _matched_ = true; 8609 8610 if (_matched_) { // action code! : degree 2 8611 8612 8613 int i = (ROOT.getData().type()==Type.INT) ? exp.intValue() 8614 : Float.floatToIntBits(exp.floatValue()); 8615 String lo = "0x"+Integer.toHexString(i); 8616 emitDIRECTIVE( ROOT, "\t.word "+lo+" @ "+exp); 8617 return; } 8618 } 8619 /* DATUM(CONST<l,d>(exp)) */ 8620 if (true 8621 // check statement type 8622 && stmArg instanceof harpoon.IR.Tree.DATUM 8623 && (true 8624 // check expression type 8625 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 8626 // check operand types 8627 && ( 8628 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.DOUBLE || 8629 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.LONG || 8630 false ) 8631 // end check operand types 8632 ) 8633 ){ 8634 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 8635 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 8636 _matched_ = true; 8637 8638 if (_matched_) { // action code! : degree 2 8639 8640 8641 long l = (ROOT.getData().type()==Type.LONG) ? exp.longValue() 8642 : Double.doubleToLongBits(exp.doubleValue()); 8643 String lo = "0x"+Integer.toHexString((int)l); 8644 String hi = "0x"+Integer.toHexString((int)(l>>32)); 8645 // doubles are stored in reverse order on the StrongARM. No, I don't 8646 // know why. I suspect the StrongARM library designers were on *crack*! 8647 if (ROOT.getData().type()==Type.LONG) 8648 emitDIRECTIVE( ROOT, "\t.word "+lo+" @ lo("+exp+")"); 8649 emitDIRECTIVE( ROOT, "\t.word "+hi+" @ hi("+exp+")"); 8650 if (ROOT.getData().type()==Type.DOUBLE) 8651 emitDIRECTIVE( ROOT, "\t.word "+lo+" @ lo("+exp+")"); 8652 return; } 8653 } 8654 /* DATUM(CONST<p>(exp)) */ 8655 if (true 8656 // check statement type 8657 && stmArg instanceof harpoon.IR.Tree.DATUM 8658 && (true 8659 // check expression type 8660 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 8661 // check operand types 8662 && ( 8663 ((harpoon.IR.Tree.DATUM)stmArg).getData().type() == Type.POINTER || 8664 false ) 8665 // end check operand types 8666 ) 8667 ){ 8668 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 8669 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 8670 _matched_ = true; 8671 8672 if (_matched_) { // action code! : degree 2 8673 8674 8675 emitDIRECTIVE( ROOT, "\t.word 0 @ null pointer constant"); 8676 return; } 8677 } 8678 /* DATUM(CONST<u:8,s:8>(exp)) */ 8679 if (true 8680 // check statement type 8681 && stmArg instanceof harpoon.IR.Tree.DATUM 8682 && (true 8683 // check expression type 8684 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 8685 // check operand types 8686 && ( 8687 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).isSmall() && ( 8688 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).signed() ? ( 8689 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==8 || 8690 false) : ( 8691 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==8 || 8692 false) ) ) || 8693 false ) 8694 // end check operand types 8695 ) 8696 ){ 8697 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 8698 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 8699 _matched_ = true; 8700 8701 if (_matched_) { // action code! : degree 2 8702 8703 8704 String chardesc = (exp.intValue()>=32 && exp.intValue()<127 8705 && exp.intValue()!=96 /* backquotes cause problems */ 8706 && exp.intValue()!=34 /* so do double quotes */) ? 8707 ("\t@ char "+((char)exp.intValue())) : ""; 8708 emitDIRECTIVE( ROOT, "\t.byte "+exp+chardesc); 8709 return; } 8710 } 8711 /* DATUM(CONST<u:16,s:16>(exp)) */ 8712 if (true 8713 // check statement type 8714 && stmArg instanceof harpoon.IR.Tree.DATUM 8715 && (true 8716 // check expression type 8717 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.CONST 8718 // check operand types 8719 && ( 8720 (((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).isSmall() && ( 8721 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).signed() ? ( 8722 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==16 || 8723 false) : ( 8724 ((harpoon.IR.Tree.PreciselyTyped)((harpoon.IR.Tree.DATUM)stmArg).getData()).bitwidth()==16 || 8725 false) ) ) || 8726 false ) 8727 // end check operand types 8728 ) 8729 ){ 8730 Number exp = ((harpoon.IR.Tree.CONST) ((harpoon.IR.Tree.DATUM)stmArg).getData()).value; 8731 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 8732 _matched_ = true; 8733 8734 if (_matched_) { // action code! : degree 2 8735 8736 8737 String chardesc = (exp.intValue()>=32 && exp.intValue()<127 8738 && exp.intValue()!=96 /* backquotes cause problems */ 8739 && exp.intValue()!=34 /* so do double quotes */) ? 8740 ("\t@ char "+((char)exp.intValue())) : ""; 8741 emitDIRECTIVE( ROOT, "\t.short "+exp+chardesc); 8742 return; } 8743 } 8744 /* DATUM(NAME(l)) */ 8745 if (true 8746 // check statement type 8747 && stmArg instanceof harpoon.IR.Tree.DATUM 8748 && (true 8749 // check expression type 8750 && ((harpoon.IR.Tree.DATUM)stmArg).getData() instanceof harpoon.IR.Tree.NAME 8751 ) 8752 ){ 8753 harpoon.Temp.Label l = ((harpoon.IR.Tree.NAME)((harpoon.IR.Tree.DATUM)stmArg).getData()).label; 8754 harpoon.IR.Tree.DATUM ROOT = (harpoon.IR.Tree.DATUM) stmArg; 8755 _matched_ = true; 8756 8757 if (_matched_) { // action code! : degree 2 8758 8759 8760 emitDIRECTIVE( ROOT, "\t.word "+l); 8761 return; } 8762 } 8763 /* LABEL(id) */ 8764 if (true 8765 // check statement type 8766 && stmArg instanceof harpoon.IR.Tree.LABEL 8767 ){ 8768 String id = ((harpoon.IR.Tree.LABEL)stmArg).label.toString(); 8769 8770 harpoon.IR.Tree.LABEL ROOT = (harpoon.IR.Tree.LABEL) stmArg; 8771 _matched_ = true; 8772 8773 if (_matched_) { // action code! : degree 1 8774 8775 8776 if (ROOT.exported) { 8777 emitLABEL( ROOT, "\t.global "+ROOT.label+"\n"+ 8778 ROOT.label + ":", ROOT.label); 8779 } else { 8780 emitLABEL( ROOT, ROOT.label + ":", ROOT.label); 8781 } 8782 return; } 8783 } 8784 /* ALIGN(n) */ 8785 if (true 8786 // check statement type 8787 && stmArg instanceof harpoon.IR.Tree.ALIGN 8788 ){ 8789 int n = ((harpoon.IR.Tree.ALIGN)stmArg).alignment; harpoon.IR.Tree.ALIGN ROOT = (harpoon.IR.Tree.ALIGN) stmArg; 8790 _matched_ = true; 8791 8792 if (_matched_) { // action code! : degree 1 8793 8794 8795 emitDIRECTIVE( ROOT, "\t.balign "+n); 8796 return; } 8797 } 8798 /* SEGMENT(CLASS) */ 8799 if (true 8800 // check statement type 8801 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8802 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.CLASS 8803 ){ 8804 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8805 _matched_ = true; 8806 8807 if (_matched_) { // action code! : degree 1 8808 8809 8810 emitDIRECTIVE( ROOT, !is_elf?".data 1":".section .flex.class"); 8811 8812 return; } 8813 } 8814 /* SEGMENT(CODE) */ 8815 if (true 8816 // check statement type 8817 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8818 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.CODE 8819 ){ 8820 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8821 _matched_ = true; 8822 8823 if (_matched_) { // action code! : degree 1 8824 8825 8826 // gas 2.7 does not support naming the code section...not 8827 // sure what to do about this yet... 8828 // emitDIRECTIVE( ROOT, !is_elf?".code 32":".section code"); 8829 emitDIRECTIVE( ROOT, !is_elf?".text 0":".section .flex.code"); 8830 return; } 8831 } 8832 /* SEGMENT(GC) */ 8833 if (true 8834 // check statement type 8835 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8836 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.GC 8837 ){ 8838 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8839 _matched_ = true; 8840 8841 if (_matched_) { // action code! : degree 1 8842 8843 8844 emitDIRECTIVE( ROOT, !is_elf?".data 2":".section .flex.gc"); 8845 return; } 8846 } 8847 /* SEGMENT(INIT_DATA) */ 8848 if (true 8849 // check statement type 8850 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8851 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.INIT_DATA 8852 ){ 8853 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8854 _matched_ = true; 8855 8856 if (_matched_) { // action code! : degree 1 8857 8858 8859 emitDIRECTIVE( ROOT, !is_elf?".data 3":".section .flex.init_data"); 8860 return; } 8861 } 8862 /* SEGMENT(STATIC_OBJECTS) */ 8863 if (true 8864 // check statement type 8865 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8866 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STATIC_OBJECTS 8867 ){ 8868 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8869 _matched_ = true; 8870 8871 if (_matched_) { // action code! : degree 1 8872 8873 8874 emitDIRECTIVE( ROOT, !is_elf?".data 4":".section .flex.static_objects"); 8875 return; } 8876 } 8877 /* SEGMENT(STATIC_PRIMITIVES) */ 8878 if (true 8879 // check statement type 8880 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8881 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STATIC_PRIMITIVES 8882 ){ 8883 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8884 _matched_ = true; 8885 8886 if (_matched_) { // action code! : degree 1 8887 8888 8889 emitDIRECTIVE( ROOT, !is_elf?".data 5":".section .flex.static_primitives"); 8890 return; } 8891 } 8892 /* SEGMENT(STRING_CONSTANTS) */ 8893 if (true 8894 // check statement type 8895 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8896 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STRING_CONSTANTS 8897 ){ 8898 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8899 _matched_ = true; 8900 8901 if (_matched_) { // action code! : degree 1 8902 8903 8904 emitDIRECTIVE( ROOT, !is_elf?".data 6":".section .flex.string_constants"); 8905 return; } 8906 } 8907 /* SEGMENT(STRING_DATA) */ 8908 if (true 8909 // check statement type 8910 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8911 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.STRING_DATA 8912 ){ 8913 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8914 _matched_ = true; 8915 8916 if (_matched_) { // action code! : degree 1 8917 8918 8919 emitDIRECTIVE( ROOT, !is_elf?".data 7":".section .flex.string_data"); 8920 return; } 8921 } 8922 /* SEGMENT(REFLECTION_OBJECTS) */ 8923 if (true 8924 // check statement type 8925 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8926 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.REFLECTION_OBJECTS 8927 ){ 8928 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8929 _matched_ = true; 8930 8931 if (_matched_) { // action code! : degree 1 8932 8933 8934 emitDIRECTIVE( ROOT, !is_elf?".data 8":".section .flex.reflection_objects"); 8935 return; } 8936 } 8937 /* SEGMENT(REFLECTION_DATA) */ 8938 if (true 8939 // check statement type 8940 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8941 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.REFLECTION_DATA 8942 ){ 8943 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8944 _matched_ = true; 8945 8946 if (_matched_) { // action code! : degree 1 8947 8948 8949 emitDIRECTIVE( ROOT, !is_elf?".data 9":".section .flex.reflection_data"); 8950 return; } 8951 } 8952 /* SEGMENT(GC_INDEX) */ 8953 if (true 8954 // check statement type 8955 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8956 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.GC_INDEX 8957 ){ 8958 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8959 _matched_ = true; 8960 8961 if (_matched_) { // action code! : degree 1 8962 8963 8964 emitDIRECTIVE( ROOT, !is_elf?".data 10":".section .flex.gc_index"); 8965 return; } 8966 } 8967 /* SEGMENT(TEXT) */ 8968 if (true 8969 // check statement type 8970 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8971 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.TEXT 8972 ){ 8973 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8974 _matched_ = true; 8975 8976 if (_matched_) { // action code! : degree 1 8977 8978 8979 emitDIRECTIVE( ROOT, !is_elf?".text":".section .text"); 8980 return; } 8981 } 8982 /* SEGMENT(ZERO_DATA) */ 8983 if (true 8984 // check statement type 8985 && stmArg instanceof harpoon.IR.Tree.SEGMENT 8986 && ((harpoon.IR.Tree.SEGMENT)stmArg).segtype == harpoon.IR.Tree.SEGMENT.ZERO_DATA 8987 ){ 8988 harpoon.IR.Tree.SEGMENT ROOT = (harpoon.IR.Tree.SEGMENT) stmArg; 8989 _matched_ = true; 8990 8991 if (_matched_) { // action code! : degree 1 8992 8993 8994 // gas 2.7 does not allow BSS subsections...use .comm and .lcomm 8995 // for the variables to be initialized to zero 8996 // emitDIRECTIVE( ROOT, ".bss \t@.section zero"); 8997 emitDIRECTIVE(ROOT, !is_elf?".bss":".section .flex.zero"); 8998 return; } 8999 } 9000 assert _matched_ : "Uh oh...\nmaximal munch didn't match anything...SPEC file\nis not complete enough for this program\nDied on "+prettyPrint(stmArg)+" in " + prettyPrint(globalStmArg); 9001 } // end munchStm 9002 public void visit(harpoon.IR.Tree.Tree treee){ 9003 assert false : "Should never visit generic harpoon.IR.Tree.Treein CggVisitor"; 9004 } // end visit(harpoon.IR.Tree.Tree) 9005 public void visit(harpoon.IR.Tree.Stm treee){ 9006 debug("munching "+treee+" "); 9007 munchStm(treee); 9008 } // end visit(harpoon.IR.Tree.Stm) 9009 public void visit(harpoon.IR.Tree.SEQ treee){ 9010 treee.getLeft().accept(this); 9011 treee.getRight().accept(this); 9012 } 9013 } 9014 CggVisitor visitor = new CggVisitor(); 9015 harpoon.IR.Tree.Tree t = (harpoon.IR.Tree.Tree) code.getRootElement(); 9016 t.accept(visitor); 9017 clearDecl(); // reset temp type mappings 9018 9019 // *** METHOD EPILOGUE *** 9020 9021 9022 assert first != null : "Should always generate some instrs"; 9023 return first; 9024 } 9025 }