MIPS: Shorten .bss string/class loads

This is a follow-up to
https://android-review.googlesource.com/#/c/384033/.

Test: booted MIPS64 (with 2nd arch MIPS32R6) in QEMU
Test: testrunner.py --target --optimizing
Test: same tests as above on CI20
Test: booted MIPS32R2 and MIPS64 in QEMU in configurations:
      ART_USE_READ_BARRIER=false,
      ART_READ_BARRIER_TYPE=TABLELOOKUP

Change-Id: I4cb2f4ded13c0d9fc960c7eac55396f7931c1e38
diff --git a/compiler/linker/mips/relative_patcher_mips.cc b/compiler/linker/mips/relative_patcher_mips.cc
index d99d237..3bec30f 100644
--- a/compiler/linker/mips/relative_patcher_mips.cc
+++ b/compiler/linker/mips/relative_patcher_mips.cc
@@ -49,43 +49,27 @@
                                                    uint32_t target_offset) {
   uint32_t anchor_literal_offset = patch.PcInsnOffset();
   uint32_t literal_offset = patch.LiteralOffset();
-  uint32_t literal_low_offset;
+  bool high_patch = ((*code)[literal_offset + 0] == 0x34) && ((*code)[literal_offset + 1] == 0x12);
 
-  // Perform basic sanity checks and initialize `literal_low_offset` to point
-  // to the instruction containing the 16 least significant bits of the
-  // relative address.
-  if (is_r6) {
-    DCHECK_GE(code->size(), 8u);
-    DCHECK_LE(literal_offset, code->size() - 8u);
-    DCHECK_EQ(literal_offset, anchor_literal_offset);
-    // AUIPC reg, offset_high
-    DCHECK_EQ((*code)[literal_offset + 0], 0x34);
-    DCHECK_EQ((*code)[literal_offset + 1], 0x12);
-    DCHECK_EQ(((*code)[literal_offset + 2] & 0x1F), 0x1E);
-    DCHECK_EQ(((*code)[literal_offset + 3] & 0xFC), 0xEC);
-    // instr reg(s), offset_low
-    DCHECK_EQ((*code)[literal_offset + 4], 0x78);
-    DCHECK_EQ((*code)[literal_offset + 5], 0x56);
-    literal_low_offset = literal_offset + 4;
+  // Perform basic sanity checks.
+  if (high_patch) {
+    if (is_r6) {
+      // auipc reg, offset_high
+      DCHECK_EQ(((*code)[literal_offset + 2] & 0x1F), 0x1E);
+      DCHECK_EQ(((*code)[literal_offset + 3] & 0xFC), 0xEC);
+    } else {
+      // lui reg, offset_high
+      DCHECK_EQ(((*code)[literal_offset + 2] & 0xE0), 0x00);
+      DCHECK_EQ((*code)[literal_offset + 3], 0x3C);
+      // addu reg, reg, reg2
+      DCHECK_EQ((*code)[literal_offset + 4], 0x21);
+      DCHECK_EQ(((*code)[literal_offset + 5] & 0x07), 0x00);
+      DCHECK_EQ(((*code)[literal_offset + 7] & 0xFC), 0x00);
+    }
   } else {
-    DCHECK_GE(code->size(), 16u);
-    DCHECK_LE(literal_offset, code->size() - 12u);
-    DCHECK_GE(literal_offset, 4u);
-    // The NAL instruction does not precede immediately as the PC+0
-    // comes from HMipsComputeBaseMethodAddress.
-    // LUI reg, offset_high
-    DCHECK_EQ((*code)[literal_offset + 0], 0x34);
-    DCHECK_EQ((*code)[literal_offset + 1], 0x12);
-    DCHECK_EQ(((*code)[literal_offset + 2] & 0xE0), 0x00);
-    DCHECK_EQ((*code)[literal_offset + 3], 0x3C);
-    // ADDU reg, reg, reg2
-    DCHECK_EQ((*code)[literal_offset + 4], 0x21);
-    DCHECK_EQ(((*code)[literal_offset + 5] & 0x07), 0x00);
-    DCHECK_EQ(((*code)[literal_offset + 7] & 0xFC), 0x00);
     // instr reg(s), offset_low
-    DCHECK_EQ((*code)[literal_offset + 8], 0x78);
-    DCHECK_EQ((*code)[literal_offset + 9], 0x56);
-    literal_low_offset = literal_offset + 8;
+    CHECK_EQ((*code)[literal_offset + 0], 0x78);
+    CHECK_EQ((*code)[literal_offset + 1], 0x56);
   }
 
   // Apply patch.
@@ -93,12 +77,15 @@
   uint32_t diff = target_offset - anchor_offset;
   diff += (diff & 0x8000) << 1;  // Account for sign extension in "instr reg(s), offset_low".
 
-  // LUI reg, offset_high / AUIPC reg, offset_high
-  (*code)[literal_offset + 0] = static_cast<uint8_t>(diff >> 16);
-  (*code)[literal_offset + 1] = static_cast<uint8_t>(diff >> 24);
-  // instr reg(s), offset_low
-  (*code)[literal_low_offset + 0] = static_cast<uint8_t>(diff >> 0);
-  (*code)[literal_low_offset + 1] = static_cast<uint8_t>(diff >> 8);
+  if (high_patch) {
+    // lui reg, offset_high / auipc reg, offset_high
+    (*code)[literal_offset + 0] = static_cast<uint8_t>(diff >> 16);
+    (*code)[literal_offset + 1] = static_cast<uint8_t>(diff >> 24);
+  } else {
+    // instr reg(s), offset_low
+    (*code)[literal_offset + 0] = static_cast<uint8_t>(diff >> 0);
+    (*code)[literal_offset + 1] = static_cast<uint8_t>(diff >> 8);
+  }
 }
 
 void MipsRelativePatcher::PatchBakerReadBarrierBranch(std::vector<uint8_t>* code ATTRIBUTE_UNUSED,