Merge "Improve performance of invokevirtual/invokeinterface with embedded imt/vtable"
diff --git a/compiler/dex/frontend.cc b/compiler/dex/frontend.cc
index 711743d..d097500 100644
--- a/compiler/dex/frontend.cc
+++ b/compiler/dex/frontend.cc
@@ -96,7 +96,6 @@
~0U,
// 2 = kArm64. TODO(Arm64): enable optimizations once backend is mature enough.
(1 << kLoadStoreElimination) |
- (1 << kLoadHoisting) |
0,
// 3 = kThumb2.
0,
diff --git a/compiler/dex/quick/arm64/target_arm64.cc b/compiler/dex/quick/arm64/target_arm64.cc
index ef9dbdd..be3cd8e 100644
--- a/compiler/dex/quick/arm64/target_arm64.cc
+++ b/compiler/dex/quick/arm64/target_arm64.cc
@@ -158,7 +158,6 @@
}
ResourceMask Arm64Mir2Lir::GetPCUseDefEncoding() const {
- LOG(FATAL) << "Unexpected call to GetPCUseDefEncoding for Arm64";
return kEncodeNone;
}
diff --git a/compiler/dex/quick/local_optimizations.cc b/compiler/dex/quick/local_optimizations.cc
index b97ff2a..2893157 100644
--- a/compiler/dex/quick/local_optimizations.cc
+++ b/compiler/dex/quick/local_optimizations.cc
@@ -121,20 +121,22 @@
}
ResourceMask stop_def_reg_mask = this_lir->u.m.def_mask->Without(kEncodeMem);
- ResourceMask stop_use_reg_mask;
- if (cu_->instruction_set == kX86 || cu_->instruction_set == kX86_64) {
+
+ /*
+ * Add pc to the resource mask to prevent this instruction
+ * from sinking past branch instructions. Also take out the memory
+ * region bits since stop_mask is used to check data/control
+ * dependencies.
+ *
+ * Note: on x86(-64) and Arm64 we use the IsBranch bit, as the PC is not exposed.
+ */
+ ResourceMask pc_encoding = GetPCUseDefEncoding();
+ if (pc_encoding == kEncodeNone) {
// TODO: Stop the abuse of kIsBranch as a bit specification for ResourceMask.
- stop_use_reg_mask = ResourceMask::Bit(kIsBranch).Union(*this_lir->u.m.use_mask).Without(
- kEncodeMem);
- } else {
- /*
- * Add pc to the resource mask to prevent this instruction
- * from sinking past branch instructions. Also take out the memory
- * region bits since stop_mask is used to check data/control
- * dependencies.
- */
- stop_use_reg_mask = GetPCUseDefEncoding().Union(*this_lir->u.m.use_mask).Without(kEncodeMem);
+ pc_encoding = ResourceMask::Bit(kIsBranch);
}
+ ResourceMask stop_use_reg_mask = pc_encoding.Union(*this_lir->u.m.use_mask).
+ Without(kEncodeMem);
for (check_lir = NEXT_LIR(this_lir); check_lir != tail_lir; check_lir = NEXT_LIR(check_lir)) {
/*
@@ -310,16 +312,17 @@
ResourceMask stop_use_all_mask = *this_lir->u.m.use_mask;
- if (cu_->instruction_set != kX86 && cu_->instruction_set != kX86_64) {
- /*
- * Branches for null/range checks are marked with the true resource
- * bits, and loads to Dalvik registers, constant pools, and non-alias
- * locations are safe to be hoisted. So only mark the heap references
- * conservatively here.
- */
- if (stop_use_all_mask.HasBit(ResourceMask::kHeapRef)) {
- stop_use_all_mask.SetBits(GetPCUseDefEncoding());
- }
+ /*
+ * Branches for null/range checks are marked with the true resource
+ * bits, and loads to Dalvik registers, constant pools, and non-alias
+ * locations are safe to be hoisted. So only mark the heap references
+ * conservatively here.
+ *
+ * Note: on x86(-64) and Arm64 this will add kEncodeNone.
+ * TODO: Sanity check. LoadStoreElimination uses kBranchBit to fake a PC.
+ */
+ if (stop_use_all_mask.HasBit(ResourceMask::kHeapRef)) {
+ stop_use_all_mask.SetBits(GetPCUseDefEncoding());
}
/* Similar as above, but just check for pure register dependency */
diff --git a/compiler/dex/quick/mir_to_lir.h b/compiler/dex/quick/mir_to_lir.h
index 87509b6..d1e83c2 100644
--- a/compiler/dex/quick/mir_to_lir.h
+++ b/compiler/dex/quick/mir_to_lir.h
@@ -1263,6 +1263,9 @@
virtual const char* GetTargetInstFmt(int opcode) = 0;
virtual const char* GetTargetInstName(int opcode) = 0;
virtual std::string BuildInsnString(const char* fmt, LIR* lir, unsigned char* base_addr) = 0;
+
+ // Note: This may return kEncodeNone on architectures that do not expose a PC. The caller must
+ // take care of this.
virtual ResourceMask GetPCUseDefEncoding() const = 0;
virtual uint64_t GetTargetInstFlags(int opcode) = 0;
virtual size_t GetInsnSize(LIR* lir) = 0;
diff --git a/compiler/dex/quick/resource_mask.h b/compiler/dex/quick/resource_mask.h
index 12ce98a..436cdb5 100644
--- a/compiler/dex/quick/resource_mask.h
+++ b/compiler/dex/quick/resource_mask.h
@@ -63,6 +63,11 @@
ResourceMask(const ResourceMask& other) = default;
ResourceMask& operator=(const ResourceMask& other) = default;
+ // Comparable by content.
+ bool operator==(const ResourceMask& other) {
+ return masks_[0] == other.masks_[0] && masks_[1] == other.masks_[1];
+ }
+
static constexpr ResourceMask RawMask(uint64_t mask1, uint64_t mask2) {
return ResourceMask(mask1, mask2);
}
diff --git a/compiler/dex/quick/x86/target_x86.cc b/compiler/dex/quick/x86/target_x86.cc
index 4310525..0083128 100755
--- a/compiler/dex/quick/x86/target_x86.cc
+++ b/compiler/dex/quick/x86/target_x86.cc
@@ -246,11 +246,6 @@
}
ResourceMask X86Mir2Lir::GetPCUseDefEncoding() const {
- /*
- * FIXME: might make sense to use a virtual resource encoding bit for pc. Might be
- * able to clean up some of the x86/Arm_Mips differences
- */
- LOG(FATAL) << "Unexpected call to GetPCUseDefEncoding for x86";
return kEncodeNone;
}