Fix null check elimination

The existing null check elimination mechanism suffered from the same
limitation as the SSA renaming: it took shortcuts that were valid in
a trace compilation world, but not in a method compilation world.

This CL replaces the old mechanism, and additionally takes advantage
of some the fact that "this" is always non-null, as are objects returned
from OP_NEW_* (thanks Ian!).

Two test cases added.  The one for ensuring that unnecessary null checks
are elminated requires manual inspection.  The other - that we don't
eliminate a necessary null check - is disabled until exceptions are working.

Change-Id: I2a9b72741f56617bf609e4d7c20244796c988f28
diff --git a/src/compiler/codegen/arm/Thumb2/Gen.cc b/src/compiler/codegen/arm/Thumb2/Gen.cc
index cd3a64a..c54a0a8 100644
--- a/src/compiler/codegen/arm/Thumb2/Gen.cc
+++ b/src/compiler/codegen/arm/Thumb2/Gen.cc
@@ -450,7 +450,7 @@
     loadWordDisp(cUnit, r0, art::Field::OffsetOffset().Int32Value(), r0);
 }
 
-static void genIGetX(CompilationUnit* cUnit, MIR* mir, OpSize size,
+static void genIGet(CompilationUnit* cUnit, MIR* mir, OpSize size,
                      RegLocation rlDest, RegLocation rlObj)
 {
     Field* fieldPtr = cUnit->method->GetDeclaringClass()->GetDexCache()->
@@ -485,7 +485,7 @@
     }
 }
 
-static void genIPutX(CompilationUnit* cUnit, MIR* mir, OpSize size,
+static void genIPut(CompilationUnit* cUnit, MIR* mir, OpSize size,
                     RegLocation rlSrc, RegLocation rlObj, bool isObject)
 {
     Field* fieldPtr = cUnit->method->GetDeclaringClass()->GetDexCache()->
@@ -521,7 +521,7 @@
     }
 }
 
-static void genIGetWideX(CompilationUnit* cUnit, MIR* mir, RegLocation rlDest,
+static void genIGetWide(CompilationUnit* cUnit, MIR* mir, RegLocation rlDest,
                         RegLocation rlObj)
 {
     Field* fieldPtr = cUnit->method->GetDeclaringClass()->GetDexCache()->
@@ -564,7 +564,7 @@
     }
 }
 
-static void genIPutWideX(CompilationUnit* cUnit, MIR* mir, RegLocation rlSrc,
+static void genIPutWide(CompilationUnit* cUnit, MIR* mir, RegLocation rlSrc,
                         RegLocation rlObj)
 {
     Field* fieldPtr = cUnit->method->GetDeclaringClass()->GetDexCache()->
@@ -886,8 +886,6 @@
     for (int i = 0; i < numFPTemps; i++) {
         oatMarkTemp(cUnit, fpTemps[i]);
     }
-    pool->nullCheckedRegs =
-        oatAllocBitVector(cUnit->numSSARegs, false);
 }
 
 /*
@@ -1267,11 +1265,7 @@
     loadValueDirectFixed(cUnit, rlSrc, r0);
 
     /* null array object? */
-    ArmLIR*  pcrLabel = NULL;
-
-    if (!(mir->OptimizationFlags & MIR_IGNORE_NULL_CHECK)) {
-        pcrLabel = genNullCheck(cUnit, rlArray.sRegLow, r1, mir);
-    }
+    genNullCheck(cUnit, rlArray.sRegLow, r1, mir);
     loadWordDisp(cUnit, rSELF,
                  OFFSETOF_MEMBER(Thread, pCanPutArrayElementFromCode), rLR);
     /* Get the array's clazz */
@@ -1295,7 +1289,7 @@
         genRegCopy(cUnit, regPtr, rlArray.lowReg);
     }
 
-    if (!(mir->OptimizationFlags & MIR_IGNORE_RANGE_CHECK)) {
+    if (!(mir->optimizationFlags & MIR_IGNORE_RANGE_CHECK)) {
         int regLen = oatAllocTemp(cUnit);
         //NOTE: max live temps(4) here.
         /* Get len */
@@ -1331,15 +1325,11 @@
     int regPtr;
 
     /* null object? */
-    ArmLIR*  pcrLabel = NULL;
-
-    if (!(mir->OptimizationFlags & MIR_IGNORE_NULL_CHECK)) {
-        pcrLabel = genNullCheck(cUnit, rlArray.sRegLow, rlArray.lowReg, mir);
-    }
+    genNullCheck(cUnit, rlArray.sRegLow, rlArray.lowReg, mir);
 
     regPtr = oatAllocTemp(cUnit);
 
-    if (!(mir->OptimizationFlags & MIR_IGNORE_RANGE_CHECK)) {
+    if (!(mir->optimizationFlags & MIR_IGNORE_RANGE_CHECK)) {
         int regLen = oatAllocTemp(cUnit);
         /* Get len */
         loadWordDisp(cUnit, rlArray.lowReg, lenOffset, regLen);
@@ -1405,13 +1395,9 @@
     }
 
     /* null object? */
-    ArmLIR*  pcrLabel = NULL;
+    genNullCheck(cUnit, rlArray.sRegLow, rlArray.lowReg, mir);
 
-    if (!(mir->OptimizationFlags & MIR_IGNORE_NULL_CHECK)) {
-        pcrLabel = genNullCheck(cUnit, rlArray.sRegLow, rlArray.lowReg, mir);
-    }
-
-    if (!(mir->OptimizationFlags & MIR_IGNORE_RANGE_CHECK)) {
+    if (!(mir->optimizationFlags & MIR_IGNORE_RANGE_CHECK)) {
         int regLen = oatAllocTemp(cUnit);
         //NOTE: max live temps(4) here.
         /* Get len */