Simple debugging support for portable path.

Change-Id: Ibdc33b8d7f644c091fdb3ba3ce2ba45804bc4078
diff --git a/src/compiler_llvm/gbc_expander.cc b/src/compiler_llvm/gbc_expander.cc
index 18cef41..c094397 100644
--- a/src/compiler_llvm/gbc_expander.cc
+++ b/src/compiler_llvm/gbc_expander.cc
@@ -60,7 +60,6 @@
  private:
   llvm::AllocaInst* shadow_frame_;
   llvm::Value* old_shadow_frame_;
-  uint16_t num_shadow_frame_refs_;
 
  private:
   art::Compiler* compiler_;
@@ -217,10 +216,12 @@
 
   llvm::Value* Expand_DivRem(llvm::CallInst& call_inst, bool is_div, JType op_jty);
 
-  void Expand_AllocaShadowFrame(llvm::Value* num_entry_value);
+  void Expand_AllocaShadowFrame(llvm::Value* num_entry_value, llvm::Value* num_vregs_value);
 
   void Expand_SetShadowFrameEntry(llvm::Value* obj, llvm::Value* entry_idx);
 
+  void Expand_SetVReg(llvm::Value* entry_idx, llvm::Value* obj);
+
   void Expand_PopShadowFrame();
 
   void Expand_UpdateDexPC(llvm::Value* dex_pc_value);
@@ -326,7 +327,7 @@
   GBCExpanderPass(const IntrinsicHelper& intrinsic_helper, IRBuilder& irb)
       : llvm::FunctionPass(ID), intrinsic_helper_(intrinsic_helper), irb_(irb),
         context_(irb.getContext()), rtb_(irb.Runtime()),
-        shadow_frame_(NULL), old_shadow_frame_(NULL), num_shadow_frame_refs_(0),
+        shadow_frame_(NULL), old_shadow_frame_(NULL),
         compiler_(NULL), dex_file_(NULL), code_item_(NULL),
         oat_compilation_unit_(NULL), method_idx_(-1u), func_(NULL),
         changed_(false)
@@ -336,7 +337,7 @@
                   art::Compiler* compiler, art::OatCompilationUnit* oat_compilation_unit)
       : llvm::FunctionPass(ID), intrinsic_helper_(intrinsic_helper), irb_(irb),
         context_(irb.getContext()), rtb_(irb.Runtime()),
-        shadow_frame_(NULL), old_shadow_frame_(NULL), num_shadow_frame_refs_(0),
+        shadow_frame_(NULL), old_shadow_frame_(NULL),
         compiler_(compiler),
         dex_file_(oat_compilation_unit->GetDexFile()),
         code_item_(oat_compilation_unit->GetCodeItem()),
@@ -366,7 +367,6 @@
   // Setup rewrite context
   shadow_frame_ = NULL;
   old_shadow_frame_ = NULL;
-  num_shadow_frame_refs_ = 0;
   func_ = &func;
   changed_ = false; // Assume unchanged
 
@@ -1092,14 +1092,17 @@
   return result;
 }
 
-void GBCExpanderPass::Expand_AllocaShadowFrame(llvm::Value* num_entry_value) {
+void GBCExpanderPass::Expand_AllocaShadowFrame(llvm::Value* num_entry_value,
+                                               llvm::Value* num_vregs_value) {
   // Most of the codes refer to MethodCompiler::EmitPrologueAllocShadowFrame and
   // MethodCompiler::EmitPushShadowFrame
-  num_shadow_frame_refs_ =
+  uint16_t num_shadow_frame_refs =
     llvm::cast<llvm::ConstantInt>(num_entry_value)->getZExtValue();
+  uint16_t num_vregs =
+    llvm::cast<llvm::ConstantInt>(num_vregs_value)->getZExtValue();
 
   llvm::StructType* shadow_frame_type =
-    irb_.getShadowFrameTy(num_shadow_frame_refs_);
+    irb_.getShadowFrameTy(num_shadow_frame_refs, num_vregs);
 
   shadow_frame_ = irb_.CreateAlloca(shadow_frame_type);
 
@@ -1126,14 +1129,15 @@
 
   llvm::Value* result = rtb_.EmitPushShadowFrame(shadow_frame_upcast,
                                                  method_object_addr,
-                                                 num_shadow_frame_refs_,
-                                                 0);
+                                                 num_shadow_frame_refs,
+                                                 num_vregs);
 
   irb_.CreateStore(result, old_shadow_frame_, kTBAARegister);
 
   return;
 }
 
+// TODO: We will remove ShadowFrameEntry later, so I just copy/paste from ShadowFrameEntry.
 void GBCExpanderPass::Expand_SetShadowFrameEntry(llvm::Value* obj,
                                                  llvm::Value* entry_idx) {
   DCHECK(shadow_frame_ != NULL);
@@ -1154,6 +1158,24 @@
   return;
 }
 
+void GBCExpanderPass::Expand_SetVReg(llvm::Value* entry_idx,
+                                     llvm::Value* value) {
+  DCHECK(shadow_frame_ != NULL);
+
+  llvm::Value* gep_index[] = {
+    irb_.getInt32(0), // No pointer displacement
+    irb_.getInt32(2), // VRegs
+    entry_idx // Pointer field
+  };
+
+  llvm::Value* vreg_addr = irb_.CreateGEP(shadow_frame_, gep_index);
+
+  irb_.CreateStore(value,
+                   irb_.CreateBitCast(vreg_addr, value->getType()->getPointerTo()),
+                   kTBAAShadowFrame);
+  return;
+}
+
 void GBCExpanderPass::Expand_PopShadowFrame() {
 #if defined(ART_USE_PORTABLE_COMPILER)
   if (old_shadow_frame_ == NULL) {
@@ -3455,7 +3477,8 @@
 
     //==- Shadow Frame -----------------------------------------------------==//
     case IntrinsicHelper::AllocaShadowFrame: {
-      Expand_AllocaShadowFrame(call_inst.getArgOperand(0));
+      Expand_AllocaShadowFrame(call_inst.getArgOperand(0),
+                               call_inst.getArgOperand(1));
       return NULL;
     }
     case IntrinsicHelper::SetShadowFrameEntry: {
@@ -3463,6 +3486,11 @@
                                  call_inst.getArgOperand(1));
       return NULL;
     }
+    case IntrinsicHelper::SetVReg: {
+      Expand_SetVReg(call_inst.getArgOperand(0),
+                     call_inst.getArgOperand(1));
+      return NULL;
+    }
     case IntrinsicHelper::PopShadowFrame: {
       Expand_PopShadowFrame();
       return NULL;