Fix 065 and 066 tests (NULL Method bug). Don't use Method in LLVM method compiler.

Change-Id: I98e4e9b329448b1b72c3b5c9d712ea68dab624bd
diff --git a/src/compiler_llvm/method_compiler.cc b/src/compiler_llvm/method_compiler.cc
index 8932b47..49717fc 100644
--- a/src/compiler_llvm/method_compiler.cc
+++ b/src/compiler_llvm/method_compiler.cc
@@ -19,6 +19,7 @@
 #include "backend_types.h"
 #include "compilation_unit.h"
 #include "compiler.h"
+#include "dex_verifier.h"
 #include "inferred_reg_category_map.h"
 #include "ir_builder.h"
 #include "logging.h"
@@ -55,8 +56,6 @@
     dex_cache_(oat_compilation_unit->dex_cache_),
     code_item_(oat_compilation_unit->code_item_),
     oat_compilation_unit_(oat_compilation_unit),
-    method_(dex_cache_->GetResolvedMethod(oat_compilation_unit->method_idx_)),
-    method_helper_(method_),
     method_idx_(oat_compilation_unit->method_idx_),
     access_flags_(oat_compilation_unit->access_flags_),
     module_(cunit->GetModule()),
@@ -82,7 +81,7 @@
 
   // Get function type
   llvm::FunctionType* func_type =
-    GetFunctionType(method_idx_, method_->IsStatic());
+    GetFunctionType(method_idx_, oat_compilation_unit_->IsStatic());
 
   // Create function
   func_ = llvm::Function::Create(func_type, llvm::Function::ExternalLinkage,
@@ -96,7 +95,7 @@
   arg_iter->setName("method");
   ++arg_iter;
 
-  if (!method_->IsStatic()) {
+  if (!oat_compilation_unit_->IsStatic()) {
     DCHECK_NE(arg_iter, arg_end);
     arg_iter->setName("this");
     ++arg_iter;
@@ -216,7 +215,7 @@
   irb_.CreateCall(irb_.GetRuntime(ThrowStackOverflowException));
 
   // Unwind.
-  char ret_shorty = method_helper_.GetShorty()[0];
+  char ret_shorty = oat_compilation_unit_->GetShorty()[0];
   if (ret_shorty == 'V') {
     irb_.CreateRetVoid();
   } else {
@@ -294,19 +293,19 @@
   llvm::Function::arg_iterator arg_iter(func_->arg_begin());
   llvm::Function::arg_iterator arg_end(func_->arg_end());
 
-  char const* shorty = method_helper_.GetShorty();
-  int32_t shorty_size = method_helper_.GetShortyLength();
-  CHECK_LE(1, shorty_size);
+  uint32_t shorty_size = 0;
+  char const* shorty = oat_compilation_unit_->GetShorty(&shorty_size);
+  CHECK_GE(shorty_size, 1u);
 
   ++arg_iter; // skip method object
 
-  if (!method_->IsStatic()) {
+  if (!oat_compilation_unit_->IsStatic()) {
     EmitStoreDalvikReg(arg_reg, kObject, kAccurate, arg_iter);
     ++arg_iter;
     ++arg_reg;
   }
 
-  for (int32_t i = 1; i < shorty_size; ++i, ++arg_iter) {
+  for (uint32_t i = 1; i < shorty_size; ++i, ++arg_iter) {
     EmitStoreDalvikReg(arg_reg, shorty[i], kAccurate, arg_iter);
 
     ++arg_reg;
@@ -1319,7 +1318,7 @@
   // the return value might be collected since the shadow stack is popped.
 
   // Return!
-  char ret_shorty = method_helper_.GetShorty()[0];
+  char ret_shorty = oat_compilation_unit_->GetShorty()[0];
   llvm::Value* retval = EmitLoadDalvikReg(dec_insn.vA, ret_shorty, kAccurate);
 
   irb_.CreateRet(retval);
@@ -1812,40 +1811,41 @@
     EmitAllocNewArray(dex_pc, dec_insn.vA, dec_insn.vB, true);
 
   if (dec_insn.vA > 0) {
-    llvm::Value* object_addr_int =
-      irb_.CreatePtrToInt(object_addr, irb_.getPtrEquivIntTy());
-
-    // TODO: currently FilledNewArray doesn't support I, J, D and L, [ so computing the component
-    // size using int alignment is safe. This code should determine the width of the FilledNewArray
-    // component.
-    llvm::Value* data_field_offset =
-      irb_.getPtrEquivInt(Array::DataOffset(sizeof(int32_t)).Int32Value());
-
-    llvm::Value* data_field_addr_int =
-      irb_.CreateAdd(object_addr_int, data_field_offset);
-
-    Class* klass = method_->GetDexCacheResolvedTypes()->Get(dec_insn.vB);
+    // Resolve the element type
+    Class* klass = dex_cache_->GetResolvedType(dec_insn.vB);
+    // TODO: Avoid the usage of the dex_cache_.  Try to figure out a better
+    // way to distinguish [I and [L.
     CHECK_NE(klass, static_cast<Class*>(NULL));
-    // Moved this below already: CHECK(!klass->IsPrimitive() || klass->IsPrimitiveInt());
 
-    llvm::Constant* word_size = irb_.getSizeOfPtrEquivIntValue();
+    uint32_t alignment;
+    llvm::Constant* elem_size;
+    llvm::PointerType* field_type;
 
-    llvm::Type* field_type;
+    // NOTE: Currently filled-new-array only supports 'L', '[', and 'I'
+    // as the element, thus we are only checking 2 cases: primitive int and
+    // non-primitive type.
     if (klass->IsPrimitiveInt()) {
+      alignment = sizeof(int32_t);
+      elem_size = irb_.getPtrEquivInt(sizeof(int32_t));
       field_type = irb_.getJIntTy()->getPointerTo();
     } else {
       CHECK(!klass->IsPrimitive());
+      alignment = irb_.getSizeOfPtrEquivInt();
+      elem_size = irb_.getSizeOfPtrEquivIntValue();
       field_type = irb_.getJObjectTy()->getPointerTo();
     }
 
+    llvm::Value* data_field_offset =
+      irb_.getPtrEquivInt(Array::DataOffset(alignment).Int32Value());
+
+    llvm::Value* data_field_addr =
+      irb_.CreatePtrDisp(object_addr, data_field_offset, field_type);
+
     // TODO: Tune this code.  Currently we are generating one instruction for
     // one element which may be very space consuming.  Maybe changing to use
     // memcpy may help; however, since we can't guarantee that the alloca of
     // dalvik register are continuous, we can't perform such optimization yet.
     for (uint32_t i = 0; i < dec_insn.vA; ++i) {
-      llvm::Value* data_field_addr =
-        irb_.CreateIntToPtr(data_field_addr_int, field_type);
-
       int reg_index;
       if (is_range) {
         reg_index = dec_insn.vC + i;
@@ -1862,7 +1862,8 @@
 
       irb_.CreateStore(reg_value, data_field_addr);
 
-      data_field_addr_int = irb_.CreateAdd(data_field_addr_int, word_size);
+      data_field_addr =
+        irb_.CreatePtrDisp(data_field_addr, elem_size, field_type);
     }
   }
 
@@ -2209,7 +2210,12 @@
 
 RegCategory MethodCompiler::GetInferredRegCategory(uint32_t dex_pc,
                                                    uint16_t reg_idx) {
-  InferredRegCategoryMap const* map = method_->GetInferredRegCategoryMap();
+
+  Compiler::MethodReference mref(dex_file_, method_idx_);
+
+  InferredRegCategoryMap const* map =
+    verifier::DexVerifier::GetInferredRegCategoryMap(mref);
+
   CHECK_NE(map, static_cast<InferredRegCategoryMap*>(NULL));
 
   return map->GetRegCategory(dex_pc, reg_idx);
@@ -2361,12 +2367,11 @@
 
 
 void MethodCompiler::PrintUnresolvedFieldWarning(int32_t field_idx) {
-  DexFile const& dex_file = method_helper_.GetDexFile();
-  DexFile::FieldId const& field_id = dex_file.GetFieldId(field_idx);
+  DexFile::FieldId const& field_id = dex_file_->GetFieldId(field_idx);
 
   LOG(WARNING) << "unable to resolve static field " << field_idx << " ("
-               << dex_file.GetFieldName(field_id) << ") in "
-               << dex_file.GetFieldDeclaringClassDescriptor(field_id);
+               << dex_file_->GetFieldName(field_id) << ") in "
+               << dex_file_->GetFieldDeclaringClassDescriptor(field_id);
 }
 
 
@@ -3622,9 +3627,6 @@
   // Verify the generated bitcode
   llvm::verifyFunction(*func_, llvm::PrintMessageAction);
 
-  // Delete the inferred register category map (won't be used anymore)
-  method_->ResetInferredRegCategoryMap();
-
   // Add the memory usage approximation of the compilation unit
   cunit_->AddMemUsageApproximation(code_item_->insns_size_in_code_units_ * 900);
   // NOTE: From statistic, the bitcode size is 4.5 times bigger than the
@@ -3823,7 +3825,7 @@
   EmitPopShadowFrame();
 
   // Emit the code to return default value (zero) for the given return type.
-  char ret_shorty = method_helper_.GetShorty()[0];
+  char ret_shorty = oat_compilation_unit_->GetShorty()[0];
   if (ret_shorty == 'V') {
     irb_.CreateRetVoid();
   } else {
@@ -3947,7 +3949,9 @@
 
 
 void MethodCompiler::EmitUpdateLineNumFromDexPC(uint32_t dex_pc) {
-  EmitUpdateLineNum(dex_file_->GetLineNumFromPC(method_, dex_pc));
+  EmitUpdateLineNum(
+    dex_file_->GetLineNumFromPC(oat_compilation_unit_->IsStatic(),
+                                method_idx_, code_item_, dex_pc));
 }
 
 
diff --git a/src/compiler_llvm/method_compiler.h b/src/compiler_llvm/method_compiler.h
index 74c55f0..7b374af 100644
--- a/src/compiler_llvm/method_compiler.h
+++ b/src/compiler_llvm/method_compiler.h
@@ -447,8 +447,6 @@
   DexFile::CodeItem const* code_item_;
 
   OatCompilationUnit* oat_compilation_unit_;
-  Method* method_;
-  MethodHelper method_helper_;
 
   uint32_t method_idx_;
   uint32_t access_flags_;