Compress the Dex register maps built by the optimizing compiler.

- Replace the current list-based (fixed-size) Dex register
  encoding in stack maps emitted by the optimizing compiler
  with another list-based variable-size Dex register
  encoding compressing short locations on 1 byte (3 bits for
  the location kind, 5 bits for the value); other (large)
  values remain encoded on 5 bytes.
- In addition, use slot offsets instead of byte offsets to
  encode the location of Dex registers placed in stack
  slots at small offsets, as it enables more values to use
  the short (1-byte wide) encoding instead of the large
  (5-byte wide) one.
- Rename art::DexRegisterMap::LocationKind as
  art::DexRegisterLocation::Kind, turn it into a
  strongly-typed enum based on a uint8_t, and extend it to
  support new kinds (kInStackLargeOffset and
  kConstantLargeValue).
- Move art::DexRegisterEntry from
  compiler/optimizing/stack_map_stream.h to
  runtime/stack_map.h and rename it as
  art::DexRegisterLocation.
- Adjust art::StackMapStream,
  art::CodeGenerator::RecordPcInfo,
  art::CheckReferenceMapVisitor::CheckOptimizedMethod,
  art::StackVisitor::GetVRegFromOptimizedCode, and
  art::StackVisitor::SetVRegFromOptimizedCode.
- Implement unaligned memory accesses in art::MemoryRegion.
- Use them to manipulate data in Dex register maps.
- Adjust oatdump to support the new Dex register encoding.
- Update compiler/optimizing/stack_map_test.cc.

Change-Id: Icefaa2e2b36b3c80bb1b882fe7ea2f77ba85c505
diff --git a/compiler/optimizing/code_generator.cc b/compiler/optimizing/code_generator.cc
index ed3f949..7d256ae 100644
--- a/compiler/optimizing/code_generator.cc
+++ b/compiler/optimizing/code_generator.cc
@@ -610,7 +610,7 @@
   for (size_t i = 0; i < environment_size; ++i) {
     HInstruction* current = environment->GetInstructionAt(i);
     if (current == nullptr) {
-      stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kNone, 0);
+      stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kNone, 0);
       continue;
     }
 
@@ -620,37 +620,43 @@
         DCHECK_EQ(current, location.GetConstant());
         if (current->IsLongConstant()) {
           int64_t value = current->AsLongConstant()->GetValue();
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, Low32Bits(value));
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, High32Bits(value));
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant,
+                                                Low32Bits(value));
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant,
+                                                High32Bits(value));
           ++i;
           DCHECK_LT(i, environment_size);
         } else if (current->IsDoubleConstant()) {
           int64_t value = bit_cast<double, int64_t>(current->AsDoubleConstant()->GetValue());
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, Low32Bits(value));
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, High32Bits(value));
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant,
+                                                Low32Bits(value));
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant,
+                                                High32Bits(value));
           ++i;
           DCHECK_LT(i, environment_size);
         } else if (current->IsIntConstant()) {
           int32_t value = current->AsIntConstant()->GetValue();
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, value);
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant, value);
         } else if (current->IsNullConstant()) {
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, 0);
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant, 0);
         } else {
           DCHECK(current->IsFloatConstant());
           int32_t value = bit_cast<float, int32_t>(current->AsFloatConstant()->GetValue());
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kConstant, value);
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant, value);
         }
         break;
       }
 
       case Location::kStackSlot: {
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInStack, location.GetStackIndex());
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInStack,
+                                              location.GetStackIndex());
         break;
       }
 
       case Location::kDoubleStackSlot: {
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInStack, location.GetStackIndex());
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInStack,
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInStack,
+                                              location.GetStackIndex());
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInStack,
                                               location.GetHighStackIndex(kVRegSize));
         ++i;
         DCHECK_LT(i, environment_size);
@@ -659,9 +665,9 @@
 
       case Location::kRegister : {
         int id = location.reg();
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInRegister, id);
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInRegister, id);
         if (current->GetType() == Primitive::kPrimLong) {
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInRegister, id);
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInRegister, id);
           ++i;
           DCHECK_LT(i, environment_size);
         }
@@ -670,9 +676,9 @@
 
       case Location::kFpuRegister : {
         int id = location.reg();
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInFpuRegister, id);
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInFpuRegister, id);
         if (current->GetType() == Primitive::kPrimDouble) {
-          stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInFpuRegister, id);
+          stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInFpuRegister, id);
           ++i;
           DCHECK_LT(i, environment_size);
         }
@@ -680,16 +686,20 @@
       }
 
       case Location::kFpuRegisterPair : {
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInFpuRegister, location.low());
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInFpuRegister, location.high());
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInFpuRegister,
+                                              location.low());
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInFpuRegister,
+                                              location.high());
         ++i;
         DCHECK_LT(i, environment_size);
         break;
       }
 
       case Location::kRegisterPair : {
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInRegister, location.low());
-        stack_map_stream_.AddDexRegisterEntry(DexRegisterMap::kInRegister, location.high());
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInRegister,
+                                              location.low());
+        stack_map_stream_.AddDexRegisterEntry(DexRegisterLocation::Kind::kInRegister,
+                                              location.high());
         ++i;
         DCHECK_LT(i, environment_size);
         break;
diff --git a/compiler/optimizing/stack_map_stream.h b/compiler/optimizing/stack_map_stream.h
index 5283d5d..79bebd2 100644
--- a/compiler/optimizing/stack_map_stream.h
+++ b/compiler/optimizing/stack_map_stream.h
@@ -56,11 +56,6 @@
     size_t inline_infos_start_index;
   };
 
-  struct DexRegisterEntry {
-    DexRegisterMap::LocationKind kind;
-    int32_t value;
-  };
-
   struct InlineInfoEntry {
     uint32_t method_index;
   };
@@ -90,11 +85,11 @@
     }
   }
 
-  void AddDexRegisterEntry(DexRegisterMap::LocationKind kind, int32_t value) {
-    DexRegisterEntry entry;
-    entry.kind = kind;
-    entry.value = value;
-    dex_register_maps_.Add(entry);
+  void AddDexRegisterEntry(DexRegisterLocation::Kind kind, int32_t value) {
+    // Ensure we only use non-compressed location kind at this stage.
+    DCHECK(DexRegisterLocation::IsShortLocationKind(kind))
+        << DexRegisterLocation::PrettyDescriptor(kind);
+    dex_register_maps_.Add(DexRegisterLocation(kind, value));
   }
 
   void AddInlineInfoEntry(uint32_t method_index) {
@@ -106,7 +101,7 @@
   size_t ComputeNeededSize() const {
     return CodeInfo::kFixedSize
         + ComputeStackMapSize()
-        + ComputeDexRegisterMapSize()
+        + ComputeDexRegisterMapsSize()
         + ComputeInlineInfoSize();
   }
 
@@ -114,27 +109,44 @@
     return stack_maps_.Size() * StackMap::ComputeAlignedStackMapSize(stack_mask_max_);
   }
 
-  size_t ComputeDexRegisterMapSize() const {
-    // We currently encode all dex register information per stack map.
-    return stack_maps_.Size() * DexRegisterMap::kFixedSize
-      // For each dex register entry.
-      + (dex_register_maps_.Size() * DexRegisterMap::SingleEntrySize());
+  // Compute the size of the Dex register map of `entry`.
+  size_t ComputeDexRegisterMapSize(const StackMapEntry& entry) const {
+    size_t size = DexRegisterMap::kFixedSize;
+    for (size_t j = 0; j < entry.num_dex_registers; ++j) {
+      DexRegisterLocation dex_register_location =
+          dex_register_maps_.Get(entry.dex_register_maps_start_index + j);
+      size += DexRegisterMap::EntrySize(dex_register_location);
+    }
+    return size;
   }
 
+  // Compute the size of all the Dex register maps.
+  size_t ComputeDexRegisterMapsSize() const {
+    size_t size = stack_maps_.Size() * DexRegisterMap::kFixedSize;
+    // The size of each register location depends on the type of
+    // the entry.
+    for (size_t i = 0, e = dex_register_maps_.Size(); i < e; ++i) {
+      DexRegisterLocation entry = dex_register_maps_.Get(i);
+      size += DexRegisterMap::EntrySize(entry);
+    }
+    return size;
+  }
+
+  // Compute the size of all the inline information pieces.
   size_t ComputeInlineInfoSize() const {
     return inline_infos_.Size() * InlineInfo::SingleEntrySize()
       // For encoding the depth.
       + (number_of_stack_maps_with_inline_info_ * InlineInfo::kFixedSize);
   }
 
-  size_t ComputeInlineInfoStart() const {
-    return ComputeDexRegisterMapStart() + ComputeDexRegisterMapSize();
-  }
-
   size_t ComputeDexRegisterMapStart() const {
     return CodeInfo::kFixedSize + ComputeStackMapSize();
   }
 
+  size_t ComputeInlineInfoStart() const {
+    return ComputeDexRegisterMapStart() + ComputeDexRegisterMapsSize();
+  }
+
   void FillIn(MemoryRegion region) {
     CodeInfo code_info(region);
     code_info.SetOverallSize(region.size());
@@ -144,7 +156,7 @@
 
     MemoryRegion dex_register_maps_region = region.Subregion(
       ComputeDexRegisterMapStart(),
-      ComputeDexRegisterMapSize());
+      ComputeDexRegisterMapsSize());
 
     MemoryRegion inline_infos_region = region.Subregion(
       ComputeInlineInfoStart(),
@@ -167,20 +179,25 @@
       }
 
       if (entry.num_dex_registers != 0) {
-        // Set the register map.
-        MemoryRegion register_region = dex_register_maps_region.Subregion(
-            next_dex_register_map_offset,
-            DexRegisterMap::kFixedSize
-            + entry.num_dex_registers * DexRegisterMap::SingleEntrySize());
+        // Set the Dex register map.
+        MemoryRegion register_region =
+            dex_register_maps_region.Subregion(
+                next_dex_register_map_offset,
+                ComputeDexRegisterMapSize(entry));
         next_dex_register_map_offset += register_region.size();
         DexRegisterMap dex_register_map(register_region);
         stack_map.SetDexRegisterMapOffset(register_region.start() - memory_start);
 
+        // Offset in `dex_register_map` where to store the next register entry.
+        size_t offset = DexRegisterMap::kFixedSize;
         for (size_t j = 0; j < entry.num_dex_registers; ++j) {
-          DexRegisterEntry register_entry =
-              dex_register_maps_.Get(j + entry.dex_register_maps_start_index);
-          dex_register_map.SetRegisterInfo(j, register_entry.kind, register_entry.value);
+          DexRegisterLocation dex_register_location =
+              dex_register_maps_.Get(entry.dex_register_maps_start_index + j);
+          dex_register_map.SetRegisterInfo(offset, dex_register_location);
+          offset += DexRegisterMap::EntrySize(dex_register_location);
         }
+        // Ensure we reached the end of the Dex registers region.
+        DCHECK_EQ(offset, register_region.size());
       } else {
         stack_map.SetDexRegisterMapOffset(StackMap::kNoDexRegisterMap);
       }
@@ -208,7 +225,7 @@
 
  private:
   GrowableArray<StackMapEntry> stack_maps_;
-  GrowableArray<DexRegisterEntry> dex_register_maps_;
+  GrowableArray<DexRegisterLocation> dex_register_maps_;
   GrowableArray<InlineInfoEntry> inline_infos_;
   int stack_mask_max_;
   size_t number_of_stack_maps_with_inline_info_;
diff --git a/compiler/optimizing/stack_map_test.cc b/compiler/optimizing/stack_map_test.cc
index 5b02510..3a5f806 100644
--- a/compiler/optimizing/stack_map_test.cc
+++ b/compiler/optimizing/stack_map_test.cc
@@ -22,7 +22,7 @@
 
 namespace art {
 
-bool SameBits(MemoryRegion region, const BitVector& bit_vector) {
+static bool SameBits(MemoryRegion region, const BitVector& bit_vector) {
   for (size_t i = 0; i < region.size_in_bits(); ++i) {
     if (region.LoadBit(i) != bit_vector.IsBitSet(i)) {
       return false;
@@ -31,9 +31,9 @@
   return true;
 }
 
-size_t ComputeDexRegisterMapSize(size_t number_of_dex_registers) {
-  return DexRegisterMap::kFixedSize
-      + number_of_dex_registers * DexRegisterMap::SingleEntrySize();
+static size_t ComputeDexRegisterMapSize(const DexRegisterMap& dex_registers,
+                                        size_t number_of_dex_registers) {
+  return dex_registers.FindLocationOffset(number_of_dex_registers);
 }
 
 TEST(StackMapTest, Test1) {
@@ -44,8 +44,8 @@
   ArenaBitVector sp_mask(&arena, 0, false);
   size_t number_of_dex_registers = 2;
   stream.AddStackMapEntry(0, 64, 0x3, &sp_mask, number_of_dex_registers, 0);
-  stream.AddDexRegisterEntry(DexRegisterMap::kInStack, 0);
-  stream.AddDexRegisterEntry(DexRegisterMap::kConstant, -2);
+  stream.AddDexRegisterEntry(DexRegisterLocation::Kind::kInStack, 0);
+  stream.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant, -2);
 
   size_t size = stream.ComputeNeededSize();
   void* memory = arena.Alloc(size, kArenaAllocMisc);
@@ -67,14 +67,17 @@
   ASSERT_TRUE(SameBits(stack_mask, sp_mask));
 
   ASSERT_TRUE(stack_map.HasDexRegisterMap());
-  DexRegisterMap dex_registers =
-      code_info.GetDexRegisterMapOf(stack_map, number_of_dex_registers);
-  ASSERT_EQ(16u, dex_registers.Size());
-  ASSERT_EQ(16u, ComputeDexRegisterMapSize(number_of_dex_registers));
-  ASSERT_EQ(DexRegisterMap::kInStack, dex_registers.GetLocationKind(0));
-  ASSERT_EQ(DexRegisterMap::kConstant, dex_registers.GetLocationKind(1));
-  ASSERT_EQ(0, dex_registers.GetValue(0));
-  ASSERT_EQ(-2, dex_registers.GetValue(1));
+  DexRegisterMap dex_registers = code_info.GetDexRegisterMapOf(stack_map, number_of_dex_registers);
+  ASSERT_EQ(6u, dex_registers.Size());
+  ASSERT_EQ(6u, ComputeDexRegisterMapSize(dex_registers, number_of_dex_registers));
+  DexRegisterLocation location0 = dex_registers.GetLocationKindAndValue(0);
+  DexRegisterLocation location1 = dex_registers.GetLocationKindAndValue(1);
+  ASSERT_EQ(DexRegisterLocation::Kind::kInStack, location0.GetKind());
+  ASSERT_EQ(DexRegisterLocation::Kind::kConstant, location1.GetKind());
+  ASSERT_EQ(DexRegisterLocation::Kind::kInStack, location0.GetInternalKind());
+  ASSERT_EQ(DexRegisterLocation::Kind::kConstantLargeValue, location1.GetInternalKind());
+  ASSERT_EQ(0, location0.GetValue());
+  ASSERT_EQ(-2, location1.GetValue());
 
   ASSERT_FALSE(stack_map.HasInlineInfo());
 }
@@ -89,8 +92,8 @@
   sp_mask1.SetBit(4);
   size_t number_of_dex_registers = 2;
   stream.AddStackMapEntry(0, 64, 0x3, &sp_mask1, number_of_dex_registers, 2);
-  stream.AddDexRegisterEntry(DexRegisterMap::kInStack, 0);
-  stream.AddDexRegisterEntry(DexRegisterMap::kConstant, -2);
+  stream.AddDexRegisterEntry(DexRegisterLocation::Kind::kInStack, 0);
+  stream.AddDexRegisterEntry(DexRegisterLocation::Kind::kConstant, -2);
   stream.AddInlineInfoEntry(42);
   stream.AddInlineInfoEntry(82);
 
@@ -98,8 +101,8 @@
   sp_mask2.SetBit(3);
   sp_mask1.SetBit(8);
   stream.AddStackMapEntry(1, 128, 0xFF, &sp_mask2, number_of_dex_registers, 0);
-  stream.AddDexRegisterEntry(DexRegisterMap::kInRegister, 18);
-  stream.AddDexRegisterEntry(DexRegisterMap::kInFpuRegister, 3);
+  stream.AddDexRegisterEntry(DexRegisterLocation::Kind::kInRegister, 18);
+  stream.AddDexRegisterEntry(DexRegisterLocation::Kind::kInFpuRegister, 3);
 
   size_t size = stream.ComputeNeededSize();
   void* memory = arena.Alloc(size, kArenaAllocMisc);
@@ -111,54 +114,66 @@
   ASSERT_EQ(2u, code_info.GetNumberOfStackMaps());
 
   // First stack map.
-  StackMap stack_map = code_info.GetStackMapAt(0);
-  ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForDexPc(0)));
-  ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForNativePcOffset(64)));
-  ASSERT_EQ(0u, stack_map.GetDexPc());
-  ASSERT_EQ(64u, stack_map.GetNativePcOffset());
-  ASSERT_EQ(0x3u, stack_map.GetRegisterMask());
+  {
+    StackMap stack_map = code_info.GetStackMapAt(0);
+    ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForDexPc(0)));
+    ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForNativePcOffset(64)));
+    ASSERT_EQ(0u, stack_map.GetDexPc());
+    ASSERT_EQ(64u, stack_map.GetNativePcOffset());
+    ASSERT_EQ(0x3u, stack_map.GetRegisterMask());
 
-  MemoryRegion stack_mask = stack_map.GetStackMask();
-  ASSERT_TRUE(SameBits(stack_mask, sp_mask1));
+    MemoryRegion stack_mask = stack_map.GetStackMask();
+    ASSERT_TRUE(SameBits(stack_mask, sp_mask1));
 
-  ASSERT_TRUE(stack_map.HasDexRegisterMap());
-  DexRegisterMap dex_registers =
-      code_info.GetDexRegisterMapOf(stack_map, number_of_dex_registers);
-  ASSERT_EQ(16u, dex_registers.Size());
-  ASSERT_EQ(16u, ComputeDexRegisterMapSize(number_of_dex_registers));
-  ASSERT_EQ(DexRegisterMap::kInStack, dex_registers.GetLocationKind(0));
-  ASSERT_EQ(DexRegisterMap::kConstant, dex_registers.GetLocationKind(1));
-  ASSERT_EQ(0, dex_registers.GetValue(0));
-  ASSERT_EQ(-2, dex_registers.GetValue(1));
+    ASSERT_TRUE(stack_map.HasDexRegisterMap());
+    DexRegisterMap dex_registers =
+        code_info.GetDexRegisterMapOf(stack_map, number_of_dex_registers);
+    ASSERT_EQ(6u, dex_registers.Size());
+    ASSERT_EQ(6u, ComputeDexRegisterMapSize(dex_registers, number_of_dex_registers));
+    DexRegisterLocation location0 = dex_registers.GetLocationKindAndValue(0);
+    DexRegisterLocation location1 = dex_registers.GetLocationKindAndValue(1);
+    ASSERT_EQ(DexRegisterLocation::Kind::kInStack, location0.GetKind());
+    ASSERT_EQ(DexRegisterLocation::Kind::kConstant, location1.GetKind());
+    ASSERT_EQ(DexRegisterLocation::Kind::kInStack, location0.GetInternalKind());
+    ASSERT_EQ(DexRegisterLocation::Kind::kConstantLargeValue, location1.GetInternalKind());
+    ASSERT_EQ(0, location0.GetValue());
+    ASSERT_EQ(-2, location1.GetValue());
 
-  ASSERT_TRUE(stack_map.HasInlineInfo());
-  InlineInfo inline_info = code_info.GetInlineInfoOf(stack_map);
-  ASSERT_EQ(2u, inline_info.GetDepth());
-  ASSERT_EQ(42u, inline_info.GetMethodReferenceIndexAtDepth(0));
-  ASSERT_EQ(82u, inline_info.GetMethodReferenceIndexAtDepth(1));
+    ASSERT_TRUE(stack_map.HasInlineInfo());
+    InlineInfo inline_info = code_info.GetInlineInfoOf(stack_map);
+    ASSERT_EQ(2u, inline_info.GetDepth());
+    ASSERT_EQ(42u, inline_info.GetMethodReferenceIndexAtDepth(0));
+    ASSERT_EQ(82u, inline_info.GetMethodReferenceIndexAtDepth(1));
+  }
 
   // Second stack map.
-  stack_map = code_info.GetStackMapAt(1);
-  ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForDexPc(1u)));
-  ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForNativePcOffset(128u)));
-  ASSERT_EQ(1u, stack_map.GetDexPc());
-  ASSERT_EQ(128u, stack_map.GetNativePcOffset());
-  ASSERT_EQ(0xFFu, stack_map.GetRegisterMask());
+  {
+    StackMap stack_map = code_info.GetStackMapAt(1);
+    ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForDexPc(1u)));
+    ASSERT_TRUE(stack_map.Equals(code_info.GetStackMapForNativePcOffset(128u)));
+    ASSERT_EQ(1u, stack_map.GetDexPc());
+    ASSERT_EQ(128u, stack_map.GetNativePcOffset());
+    ASSERT_EQ(0xFFu, stack_map.GetRegisterMask());
 
-  stack_mask = stack_map.GetStackMask();
-  ASSERT_TRUE(SameBits(stack_mask, sp_mask2));
+    MemoryRegion stack_mask = stack_map.GetStackMask();
+    ASSERT_TRUE(SameBits(stack_mask, sp_mask2));
 
-  ASSERT_TRUE(stack_map.HasDexRegisterMap());
-  dex_registers =
-      code_info.GetDexRegisterMapOf(stack_map, number_of_dex_registers);
-  ASSERT_EQ(16u, dex_registers.Size());
-  ASSERT_EQ(16u, ComputeDexRegisterMapSize(number_of_dex_registers));
-  ASSERT_EQ(DexRegisterMap::kInRegister, dex_registers.GetLocationKind(0));
-  ASSERT_EQ(DexRegisterMap::kInFpuRegister, dex_registers.GetLocationKind(1));
-  ASSERT_EQ(18, dex_registers.GetValue(0));
-  ASSERT_EQ(3, dex_registers.GetValue(1));
+    ASSERT_TRUE(stack_map.HasDexRegisterMap());
+    DexRegisterMap dex_registers =
+        code_info.GetDexRegisterMapOf(stack_map, number_of_dex_registers);
+    ASSERT_EQ(2u, dex_registers.Size());
+    ASSERT_EQ(2u, ComputeDexRegisterMapSize(dex_registers, number_of_dex_registers));
+    DexRegisterLocation location0 = dex_registers.GetLocationKindAndValue(0);
+    DexRegisterLocation location1 = dex_registers.GetLocationKindAndValue(1);
+    ASSERT_EQ(DexRegisterLocation::Kind::kInRegister, location0.GetKind());
+    ASSERT_EQ(DexRegisterLocation::Kind::kInFpuRegister, location1.GetKind());
+    ASSERT_EQ(DexRegisterLocation::Kind::kInRegister, location0.GetInternalKind());
+    ASSERT_EQ(DexRegisterLocation::Kind::kInFpuRegister, location1.GetInternalKind());
+    ASSERT_EQ(18, location0.GetValue());
+    ASSERT_EQ(3, location1.GetValue());
 
-  ASSERT_FALSE(stack_map.HasInlineInfo());
+    ASSERT_FALSE(stack_map.HasInlineInfo());
+  }
 }
 
 }  // namespace art