Complete MIPS code generation support

With this CL code generation for MIPS is complete (though untested on
actual hardware).  Core and the boot classpath compile without issue.

The primary thrust here was to support expanding of short branch
sequences to long form during assembly if the displacement field overflowed.
That led to a general cleanup of creation on LIR nodes outside of the
normal flow.

Also introduced is a README to describe the state of MIPS support, as well
as memory barrier handling.

Change-Id: I251a2ef8d74bc7183406dce9493464be24a9d7f7
diff --git a/src/compiler/codegen/arm/Thumb2/Factory.cc b/src/compiler/codegen/arm/Thumb2/Factory.cc
index 03a69d5..b6df8e3 100644
--- a/src/compiler/codegen/arm/Thumb2/Factory.cc
+++ b/src/compiler/codegen/arm/Thumb2/Factory.cc
@@ -68,14 +68,8 @@
     if (dataTarget == NULL) {
         dataTarget = addWordData(cUnit, &cUnit->literalList, value);
     }
-    LIR* loadPcRel = (LIR* ) oatNew(cUnit, sizeof(LIR), true,
-                                          kAllocLIR);
-    loadPcRel->dalvikOffset = cUnit->currentDalvikOffset;
-    loadPcRel->opcode = kThumb2Vldrs;
-    loadPcRel->target = (LIR* ) dataTarget;
-    loadPcRel->operands[0] = rDest;
-    loadPcRel->operands[1] = r15pc;
-    setupResourceMasks(loadPcRel);
+    LIR* loadPcRel = rawLIR(cUnit, cUnit->currentDalvikOffset, kThumb2Vldrs,
+                            rDest, r15pc, 0, 0, dataTarget);
     setMemRefType(loadPcRel, true, kLiteral);
     loadPcRel->aliasInfo = (intptr_t)dataTarget;
     oatAppendLIR(cUnit, (LIR* ) loadPcRel);
@@ -177,13 +171,8 @@
     if (dataTarget == NULL) {
         dataTarget = addWordData(cUnit, &cUnit->literalList, value);
     }
-    LIR* loadPcRel = (LIR* ) oatNew(cUnit, sizeof(LIR), true,
-                                          kAllocLIR);
-    loadPcRel->opcode = kThumb2LdrPcRel12;
-    loadPcRel->target = (LIR* ) dataTarget;
-    loadPcRel->dalvikOffset = cUnit->currentDalvikOffset;
-    loadPcRel->operands[0] = rDest;
-    setupResourceMasks(loadPcRel);
+    LIR* loadPcRel = rawLIR(cUnit, cUnit->currentDalvikOffset,
+                            kThumb2LdrPcRel12, rDest, 0, 0, 0, dataTarget);
     setMemRefType(loadPcRel, true, kLiteral);
     loadPcRel->aliasInfo = (intptr_t)dataTarget;
     res = loadPcRel;
@@ -643,14 +632,9 @@
                 dataTarget = addWideData(cUnit, &cUnit->literalList, valLo,
                                          valHi);
             }
-            LIR* loadPcRel = (LIR* ) oatNew(cUnit, sizeof(LIR), true,
-                                                  kAllocLIR);
-            loadPcRel->dalvikOffset = cUnit->currentDalvikOffset;
-            loadPcRel->opcode = kThumb2Vldrd;
-            loadPcRel->target = (LIR* ) dataTarget;
-            loadPcRel->operands[0] = S2D(rDestLo, rDestHi);
-            loadPcRel->operands[1] = r15pc;
-            setupResourceMasks(loadPcRel);
+            LIR* loadPcRel = rawLIR(cUnit, cUnit->currentDalvikOffset,
+                                    kThumb2Vldrd, S2D(rDestLo, rDestHi),
+                                    r15pc, 0, 0, dataTarget);
             setMemRefType(loadPcRel, true, kLiteral);
             loadPcRel->aliasInfo = (intptr_t)dataTarget;
             oatAppendLIR(cUnit, (LIR* ) loadPcRel);
@@ -1042,28 +1026,22 @@
 
 LIR* fpRegCopy(CompilationUnit* cUnit, int rDest, int rSrc)
 {
-    LIR* res = (LIR* ) oatNew(cUnit, sizeof(LIR), true, kAllocLIR);
-    res->dalvikOffset = cUnit->currentDalvikOffset;
-    res->operands[0] = rDest;
-    res->operands[1] = rSrc;
+    int opcode;
+    DCHECK_EQ(DOUBLEREG(rDest), DOUBLEREG(rSrc));
+    if (DOUBLEREG(rDest)) {
+        opcode = kThumb2Vmovd;
+    } else {
+        if (SINGLEREG(rDest)) {
+            opcode = SINGLEREG(rSrc) ? kThumb2Vmovs : kThumb2Fmsr;
+        } else {
+            DCHECK(SINGLEREG(rSrc));
+            opcode = kThumb2Fmrs;
+        }
+    }
+    LIR* res = rawLIR(cUnit, cUnit->currentDalvikOffset, opcode, rDest, rSrc);
     if (rDest == rSrc) {
         res->flags.isNop = true;
-    } else {
-        DCHECK_EQ(DOUBLEREG(rDest), DOUBLEREG(rSrc));
-        if (DOUBLEREG(rDest)) {
-            res->opcode = kThumb2Vmovd;
-        } else {
-            if (SINGLEREG(rDest)) {
-                res->opcode = SINGLEREG(rSrc) ? kThumb2Vmovs : kThumb2Fmsr;
-            } else {
-                DCHECK(SINGLEREG(rSrc));
-                res->opcode = kThumb2Fmrs;
-            }
-        }
-        res->operands[0] = rDest;
-        res->operands[1] = rSrc;
     }
-    setupResourceMasks(res);
     return res;
 }