Merge "Fix unquickening in the presence of duplicate methods."
diff --git a/compiler/optimizing/loop_optimization.cc b/compiler/optimizing/loop_optimization.cc
index 5a95abd..da2acd1 100644
--- a/compiler/optimizing/loop_optimization.cc
+++ b/compiler/optimizing/loop_optimization.cc
@@ -1001,8 +1001,9 @@
vector = new (global_allocator_) HVecStore(
global_allocator_, org->InputAt(0), opa, opb, type, vector_length_);
} else {
+ bool is_string_char_at = org->AsArrayGet()->IsStringCharAt();
vector = new (global_allocator_) HVecLoad(
- global_allocator_, org->InputAt(0), opa, type, vector_length_);
+ global_allocator_, org->InputAt(0), opa, type, vector_length_, is_string_char_at);
}
} else {
// Scalar store or load.
@@ -1010,7 +1011,9 @@
if (opb != nullptr) {
vector = new (global_allocator_) HArraySet(org->InputAt(0), opa, opb, type, kNoDexPc);
} else {
- vector = new (global_allocator_) HArrayGet(org->InputAt(0), opa, type, kNoDexPc);
+ bool is_string_char_at = org->AsArrayGet()->IsStringCharAt();
+ vector = new (global_allocator_) HArrayGet(
+ org->InputAt(0), opa, type, kNoDexPc, is_string_char_at);
}
}
vector_map_->Put(org, vector);
diff --git a/compiler/optimizing/nodes_vector.h b/compiler/optimizing/nodes_vector.h
index fb9dfb7..c9d6ff8 100644
--- a/compiler/optimizing/nodes_vector.h
+++ b/compiler/optimizing/nodes_vector.h
@@ -98,7 +98,7 @@
DECLARE_ABSTRACT_INSTRUCTION(VecOperation);
- private:
+ protected:
// Additional packed bits.
static constexpr size_t kFieldType = HInstruction::kNumberOfGenericPackedBits;
static constexpr size_t kFieldTypeSize =
@@ -107,6 +107,7 @@
static_assert(kNumberOfVectorOpPackedBits <= kMaxNumberOfPackedBits, "Too many packed fields.");
using TypeField = BitField<Primitive::Type, kFieldType, kFieldTypeSize>;
+ private:
const size_t vector_length_;
DISALLOW_COPY_AND_ASSIGN(HVecOperation);
@@ -348,22 +349,25 @@
bool is_unsigned,
bool is_rounded,
uint32_t dex_pc = kNoDexPc)
- : HVecBinaryOperation(arena, left, right, packed_type, vector_length, dex_pc),
- is_unsigned_(is_unsigned),
- is_rounded_(is_rounded) {
+ : HVecBinaryOperation(arena, left, right, packed_type, vector_length, dex_pc) {
DCHECK(left->IsVecOperation() && right->IsVecOperation());
DCHECK_EQ(left->AsVecOperation()->GetPackedType(), packed_type);
DCHECK_EQ(right->AsVecOperation()->GetPackedType(), packed_type);
+ SetPackedFlag<kFieldHAddIsUnsigned>(is_unsigned);
+ SetPackedFlag<kFieldHAddIsRounded>(is_rounded);
}
- bool IsUnsigned() const { return is_unsigned_; }
- bool IsRounded() const { return is_rounded_; }
+ bool IsUnsigned() const { return GetPackedFlag<kFieldHAddIsUnsigned>(); }
+ bool IsRounded() const { return GetPackedFlag<kFieldHAddIsRounded>(); }
DECLARE_INSTRUCTION(VecHalvingAdd);
private:
- bool is_unsigned_;
- bool is_rounded_;
+ // Additional packed bits.
+ static constexpr size_t kFieldHAddIsUnsigned = HVecOperation::kNumberOfVectorOpPackedBits;
+ static constexpr size_t kFieldHAddIsRounded = kFieldHAddIsUnsigned + 1;
+ static constexpr size_t kNumberOfHAddPackedBits = kFieldHAddIsRounded + 1;
+ static_assert(kNumberOfHAddPackedBits <= kMaxNumberOfPackedBits, "Too many packed fields.");
DISALLOW_COPY_AND_ASSIGN(HVecHalvingAdd);
};
@@ -687,6 +691,7 @@
HInstruction* index,
Primitive::Type packed_type,
size_t vector_length,
+ bool is_string_char_at,
uint32_t dex_pc = kNoDexPc)
: HVecMemoryOperation(arena,
packed_type,
@@ -696,9 +701,18 @@
dex_pc) {
SetRawInputAt(0, base);
SetRawInputAt(1, index);
+ SetPackedFlag<kFieldIsStringCharAt>(is_string_char_at);
}
DECLARE_INSTRUCTION(VecLoad);
+
+ bool IsStringCharAt() const { return GetPackedFlag<kFieldIsStringCharAt>(); }
+
private:
+ // Additional packed bits.
+ static constexpr size_t kFieldIsStringCharAt = HVecOperation::kNumberOfVectorOpPackedBits;
+ static constexpr size_t kNumberOfVecLoadPackedBits = kFieldIsStringCharAt + 1;
+ static_assert(kNumberOfVecLoadPackedBits <= kMaxNumberOfPackedBits, "Too many packed fields.");
+
DISALLOW_COPY_AND_ASSIGN(HVecLoad);
};
diff --git a/compiler/utils/mips64/assembler_mips64.cc b/compiler/utils/mips64/assembler_mips64.cc
index 57223b5..f4afb33 100644
--- a/compiler/utils/mips64/assembler_mips64.cc
+++ b/compiler/utils/mips64/assembler_mips64.cc
@@ -1356,6 +1356,106 @@
EmitMsa3R(0x7, 0x3, wt, ws, wd, 0x12);
}
+void Mips64Assembler::Add_aB(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x0, 0x0, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Add_aH(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x0, 0x1, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Add_aW(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x0, 0x2, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Add_aD(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x0, 0x3, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_sB(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x4, 0x0, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_sH(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x4, 0x1, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_sW(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x4, 0x2, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_sD(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x4, 0x3, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_uB(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x5, 0x0, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_uH(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x5, 0x1, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_uW(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x5, 0x2, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Ave_uD(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x5, 0x3, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_sB(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x6, 0x0, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_sH(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x6, 0x1, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_sW(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x6, 0x2, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_sD(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x6, 0x3, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_uB(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x7, 0x0, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_uH(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x7, 0x1, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_uW(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x7, 0x2, wt, ws, wd, 0x10);
+}
+
+void Mips64Assembler::Aver_uD(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
+ CHECK(HasMsa());
+ EmitMsa3R(0x7, 0x3, wt, ws, wd, 0x10);
+}
+
void Mips64Assembler::FaddW(VectorRegister wd, VectorRegister ws, VectorRegister wt) {
CHECK(HasMsa());
EmitMsa3R(0x0, 0x0, wt, ws, wd, 0x1b);
diff --git a/compiler/utils/mips64/assembler_mips64.h b/compiler/utils/mips64/assembler_mips64.h
index 666c693..6ac3361 100644
--- a/compiler/utils/mips64/assembler_mips64.h
+++ b/compiler/utils/mips64/assembler_mips64.h
@@ -682,6 +682,26 @@
void Mod_uH(VectorRegister wd, VectorRegister ws, VectorRegister wt);
void Mod_uW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
void Mod_uD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Add_aB(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Add_aH(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Add_aW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Add_aD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_sB(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_sH(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_sW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_sD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_uB(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_uH(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_uW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Ave_uD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_sB(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_sH(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_sW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_sD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_uB(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_uH(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_uW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
+ void Aver_uD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
void FaddW(VectorRegister wd, VectorRegister ws, VectorRegister wt);
void FaddD(VectorRegister wd, VectorRegister ws, VectorRegister wt);
diff --git a/compiler/utils/mips64/assembler_mips64_test.cc b/compiler/utils/mips64/assembler_mips64_test.cc
index f2e3b16..084ce6f 100644
--- a/compiler/utils/mips64/assembler_mips64_test.cc
+++ b/compiler/utils/mips64/assembler_mips64_test.cc
@@ -2668,6 +2668,106 @@
"mod_u.d");
}
+TEST_F(AssemblerMIPS64Test, Add_aB) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Add_aB, "add_a.b ${reg1}, ${reg2}, ${reg3}"),
+ "add_a.b");
+}
+
+TEST_F(AssemblerMIPS64Test, Add_aH) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Add_aH, "add_a.h ${reg1}, ${reg2}, ${reg3}"),
+ "add_a.h");
+}
+
+TEST_F(AssemblerMIPS64Test, Add_aW) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Add_aW, "add_a.w ${reg1}, ${reg2}, ${reg3}"),
+ "add_a.w");
+}
+
+TEST_F(AssemblerMIPS64Test, Add_aD) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Add_aD, "add_a.d ${reg1}, ${reg2}, ${reg3}"),
+ "add_a.d");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_sB) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_sB, "ave_s.b ${reg1}, ${reg2}, ${reg3}"),
+ "ave_s.b");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_sH) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_sH, "ave_s.h ${reg1}, ${reg2}, ${reg3}"),
+ "ave_s.h");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_sW) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_sW, "ave_s.w ${reg1}, ${reg2}, ${reg3}"),
+ "ave_s.w");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_sD) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_sD, "ave_s.d ${reg1}, ${reg2}, ${reg3}"),
+ "ave_s.d");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_uB) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_uB, "ave_u.b ${reg1}, ${reg2}, ${reg3}"),
+ "ave_u.b");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_uH) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_uH, "ave_u.h ${reg1}, ${reg2}, ${reg3}"),
+ "ave_u.h");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_uW) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_uW, "ave_u.w ${reg1}, ${reg2}, ${reg3}"),
+ "ave_u.w");
+}
+
+TEST_F(AssemblerMIPS64Test, Ave_uD) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Ave_uD, "ave_u.d ${reg1}, ${reg2}, ${reg3}"),
+ "ave_u.d");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_sB) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_sB, "aver_s.b ${reg1}, ${reg2}, ${reg3}"),
+ "aver_s.b");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_sH) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_sH, "aver_s.h ${reg1}, ${reg2}, ${reg3}"),
+ "aver_s.h");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_sW) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_sW, "aver_s.w ${reg1}, ${reg2}, ${reg3}"),
+ "aver_s.w");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_sD) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_sD, "aver_s.d ${reg1}, ${reg2}, ${reg3}"),
+ "aver_s.d");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_uB) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_uB, "aver_u.b ${reg1}, ${reg2}, ${reg3}"),
+ "aver_u.b");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_uH) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_uH, "aver_u.h ${reg1}, ${reg2}, ${reg3}"),
+ "aver_u.h");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_uW) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_uW, "aver_u.w ${reg1}, ${reg2}, ${reg3}"),
+ "aver_u.w");
+}
+
+TEST_F(AssemblerMIPS64Test, Aver_uD) {
+ DriverStr(RepeatVVV(&mips64::Mips64Assembler::Aver_uD, "aver_u.d ${reg1}, ${reg2}, ${reg3}"),
+ "aver_u.d");
+}
+
TEST_F(AssemblerMIPS64Test, FaddW) {
DriverStr(RepeatVVV(&mips64::Mips64Assembler::FaddW, "fadd.w ${reg1}, ${reg2}, ${reg3}"),
"fadd.w");
diff --git a/dex2oat/dex2oat_test.cc b/dex2oat/dex2oat_test.cc
index a267766..d546072 100644
--- a/dex2oat/dex2oat_test.cc
+++ b/dex2oat/dex2oat_test.cc
@@ -884,6 +884,7 @@
};
TEST_F(Dex2oatReturnCodeTest, TestCreateRuntime) {
+ TEST_DISABLED_FOR_MEMORY_TOOL(); // b/19100793
int status = RunTest({ "--boot-image=/this/does/not/exist/yolo.oat" });
EXPECT_EQ(static_cast<int>(dex2oat::ReturnCode::kCreateRuntime), WEXITSTATUS(status)) << output_;
}
diff --git a/dexlayout/Android.bp b/dexlayout/Android.bp
index 4b65c52..a2116cd 100644
--- a/dexlayout/Android.bp
+++ b/dexlayout/Android.bp
@@ -49,6 +49,7 @@
shared_libs: [
"libart",
"libart-dexlayout",
+ "libbase",
],
}
diff --git a/dexlayout/dex_ir.cc b/dexlayout/dex_ir.cc
index 3f715cf..f1c6f67 100644
--- a/dexlayout/dex_ir.cc
+++ b/dexlayout/dex_ir.cc
@@ -451,8 +451,8 @@
}
uint8_t visibility = annotation->visibility_;
const uint8_t* annotation_data = annotation->annotation_;
- EncodedValue* encoded_value =
- ReadEncodedValue(&annotation_data, DexFile::kDexAnnotationAnnotation, 0);
+ std::unique_ptr<EncodedValue> encoded_value(
+ ReadEncodedValue(&annotation_data, DexFile::kDexAnnotationAnnotation, 0));
// TODO: Calculate the size of the annotation.
AnnotationItem* annotation_item =
new AnnotationItem(visibility, encoded_value->ReleaseEncodedAnnotation());
diff --git a/dexlayout/dexlayout_main.cc b/dexlayout/dexlayout_main.cc
index 38faf96..3c627ea 100644
--- a/dexlayout/dexlayout_main.cc
+++ b/dexlayout/dexlayout_main.cc
@@ -170,14 +170,14 @@
}
// Open profile file.
- ProfileCompilationInfo* profile_info = nullptr;
+ std::unique_ptr<ProfileCompilationInfo> profile_info;
if (options.profile_file_name_) {
int profile_fd = open(options.profile_file_name_, O_RDONLY);
if (profile_fd < 0) {
fprintf(stderr, "Can't open %s\n", options.profile_file_name_);
return 1;
}
- profile_info = new ProfileCompilationInfo();
+ profile_info.reset(new ProfileCompilationInfo());
if (!profile_info->Load(profile_fd)) {
fprintf(stderr, "Can't read profile info from %s\n", options.profile_file_name_);
return 1;
@@ -185,13 +185,19 @@
}
// Create DexLayout instance.
- DexLayout dex_layout(options, profile_info, out_file);
+ DexLayout dex_layout(options, profile_info.get(), out_file);
// Process all files supplied on command line.
int result = 0;
while (optind < argc) {
result |= dex_layout.ProcessFile(argv[optind++]);
} // while
+
+ if (options.output_file_name_) {
+ CHECK(out_file != nullptr && out_file != stdout);
+ fclose(out_file);
+ }
+
return result != 0;
}
diff --git a/dexoptanalyzer/dexoptanalyzer.cc b/dexoptanalyzer/dexoptanalyzer.cc
index 965e407..9a2eb7f 100644
--- a/dexoptanalyzer/dexoptanalyzer.cc
+++ b/dexoptanalyzer/dexoptanalyzer.cc
@@ -216,6 +216,8 @@
if (!CreateRuntime()) {
return kErrorCannotCreateRuntime;
}
+ std::unique_ptr<Runtime> runtime(Runtime::Current());
+
OatFileAssistant oat_file_assistant(dex_file_.c_str(), isa_, /*load_executable*/ false);
// Always treat elements of the bootclasspath as up-to-date.
// TODO(calin): this check should be in OatFileAssistant.
diff --git a/disassembler/disassembler_mips.cc b/disassembler/disassembler_mips.cc
index eb57d33..3c60bf4 100644
--- a/disassembler/disassembler_mips.cc
+++ b/disassembler/disassembler_mips.cc
@@ -433,6 +433,11 @@
{ kMsaMask | (0x7 << 23), kMsa | (0x5 << 23) | 0x12, "div_u", "Vkmn" },
{ kMsaMask | (0x7 << 23), kMsa | (0x6 << 23) | 0x12, "mod_s", "Vkmn" },
{ kMsaMask | (0x7 << 23), kMsa | (0x7 << 23) | 0x12, "mod_u", "Vkmn" },
+ { kMsaMask | (0x7 << 23), kMsa | (0x0 << 23) | 0x10, "add_a", "Vkmn" },
+ { kMsaMask | (0x7 << 23), kMsa | (0x4 << 23) | 0x10, "ave_s", "Vkmn" },
+ { kMsaMask | (0x7 << 23), kMsa | (0x5 << 23) | 0x10, "ave_u", "Vkmn" },
+ { kMsaMask | (0x7 << 23), kMsa | (0x6 << 23) | 0x10, "aver_s", "Vkmn" },
+ { kMsaMask | (0x7 << 23), kMsa | (0x7 << 23) | 0x10, "aver_u", "Vkmn" },
{ kMsaMask | (0xf << 22), kMsa | (0x0 << 22) | 0x1b, "fadd", "Ukmn" },
{ kMsaMask | (0xf << 22), kMsa | (0x1 << 22) | 0x1b, "fsub", "Ukmn" },
{ kMsaMask | (0xf << 22), kMsa | (0x2 << 22) | 0x1b, "fmul", "Ukmn" },
diff --git a/oatdump/oatdump.cc b/oatdump/oatdump.cc
index 878d0f2..f07e0f9 100644
--- a/oatdump/oatdump.cc
+++ b/oatdump/oatdump.cc
@@ -125,9 +125,12 @@
std::unique_ptr<const InstructionSetFeatures> features = InstructionSetFeatures::FromBitmap(
isa, oat_file_->GetOatHeader().GetInstructionSetFeaturesBitmap());
- File* elf_file = OS::CreateEmptyFile(output_name_.c_str());
+ std::unique_ptr<File> elf_file(OS::CreateEmptyFile(output_name_.c_str()));
+ if (elf_file == nullptr) {
+ return false;
+ }
std::unique_ptr<BufferedOutputStream> output_stream(
- MakeUnique<BufferedOutputStream>(MakeUnique<FileOutputStream>(elf_file)));
+ MakeUnique<BufferedOutputStream>(MakeUnique<FileOutputStream>(elf_file.get())));
builder_.reset(new ElfBuilder<ElfTypes>(isa, features.get(), output_stream.get()));
builder_->Start();
@@ -182,7 +185,17 @@
builder_->End();
- return builder_->Good();
+ bool ret_value = builder_->Good();
+
+ builder_.reset();
+ output_stream.reset();
+
+ if (elf_file->FlushCloseOrErase() != 0) {
+ return false;
+ }
+ elf_file.reset();
+
+ return ret_value;
}
void Walk() {
@@ -2842,14 +2855,14 @@
static int SymbolizeOat(const char* oat_filename, std::string& output_name, bool no_bits) {
std::string error_msg;
- OatFile* oat_file = OatFile::Open(oat_filename,
- oat_filename,
- nullptr,
- nullptr,
- false,
- /*low_4gb*/false,
- nullptr,
- &error_msg);
+ std::unique_ptr<OatFile> oat_file(OatFile::Open(oat_filename,
+ oat_filename,
+ nullptr,
+ nullptr,
+ false,
+ /*low_4gb*/false,
+ nullptr,
+ &error_msg));
if (oat_file == nullptr) {
fprintf(stderr, "Failed to open oat file from '%s': %s\n", oat_filename, error_msg.c_str());
return EXIT_FAILURE;
@@ -2859,10 +2872,10 @@
// Try to produce an ELF file of the same type. This is finicky, as we have used 32-bit ELF
// files for 64-bit code in the past.
if (Is64BitInstructionSet(oat_file->GetOatHeader().GetInstructionSet())) {
- OatSymbolizer<ElfTypes64> oat_symbolizer(oat_file, output_name, no_bits);
+ OatSymbolizer<ElfTypes64> oat_symbolizer(oat_file.get(), output_name, no_bits);
result = oat_symbolizer.Symbolize();
} else {
- OatSymbolizer<ElfTypes32> oat_symbolizer(oat_file, output_name, no_bits);
+ OatSymbolizer<ElfTypes32> oat_symbolizer(oat_file.get(), output_name, no_bits);
result = oat_symbolizer.Symbolize();
}
if (!result) {
diff --git a/patchoat/patchoat.cc b/patchoat/patchoat.cc
index fbb0978..e750ede 100644
--- a/patchoat/patchoat.cc
+++ b/patchoat/patchoat.cc
@@ -30,6 +30,7 @@
#include "art_field-inl.h"
#include "art_method-inl.h"
#include "base/dumpable.h"
+#include "base/memory_tool.h"
#include "base/scoped_flock.h"
#include "base/stringpiece.h"
#include "base/unix_file/fd_file.h"
@@ -142,6 +143,8 @@
LOG(ERROR) << "Unable to initialize runtime";
return false;
}
+ std::unique_ptr<Runtime> runtime(Runtime::Current());
+
// Runtime::Create acquired the mutator_lock_ that is normally given away when we Runtime::Start,
// give it away now and then switch to a more manageable ScopedObjectAccess.
Thread::Current()->TransitionFromRunnableToSuspended(kNative);
@@ -286,6 +289,13 @@
return false;
}
}
+
+ if (!kIsDebugBuild && !(RUNNING_ON_MEMORY_TOOL && kMemoryToolDetectsLeaks)) {
+ // We want to just exit on non-debug builds, not bringing the runtime down
+ // in an orderly fashion. So release the following fields.
+ runtime.release();
+ }
+
return true;
}
diff --git a/runtime/arch/arm/quick_entrypoints_arm.S b/runtime/arch/arm/quick_entrypoints_arm.S
index 029de46..a277edf 100644
--- a/runtime/arch/arm/quick_entrypoints_arm.S
+++ b/runtime/arch/arm/quick_entrypoints_arm.S
@@ -872,7 +872,7 @@
POISON_HEAP_REF r2
str r2, [r3, r1, lsl #2]
ldr r3, [r9, #THREAD_CARD_TABLE_OFFSET]
- lsr r0, r0, #7
+ lsr r0, r0, #CARD_TABLE_CARD_SHIFT
strb r3, [r3, r0]
blx lr
.Ldo_aput_null:
@@ -900,7 +900,7 @@
POISON_HEAP_REF r2
str r2, [r3, r1, lsl #2]
ldr r3, [r9, #THREAD_CARD_TABLE_OFFSET]
- lsr r0, r0, #7
+ lsr r0, r0, #CARD_TABLE_CARD_SHIFT
strb r3, [r3, r0]
blx lr
.Lthrow_array_store_exception:
diff --git a/runtime/arch/arm64/quick_entrypoints_arm64.S b/runtime/arch/arm64/quick_entrypoints_arm64.S
index d043962..c555126 100644
--- a/runtime/arch/arm64/quick_entrypoints_arm64.S
+++ b/runtime/arch/arm64/quick_entrypoints_arm64.S
@@ -1416,7 +1416,7 @@
POISON_HEAP_REF w2
str w2, [x3, x1, lsl #2] // Heap reference = 32b
ldr x3, [xSELF, #THREAD_CARD_TABLE_OFFSET]
- lsr x0, x0, #7
+ lsr x0, x0, #CARD_TABLE_CARD_SHIFT
strb w3, [x3, x0]
ret
.Ldo_aput_null:
@@ -1447,7 +1447,7 @@
POISON_HEAP_REF w2
str w2, [x3, x1, lsl #2] // Heap reference = 32b
ldr x3, [xSELF, #THREAD_CARD_TABLE_OFFSET]
- lsr x0, x0, #7
+ lsr x0, x0, #CARD_TABLE_CARD_SHIFT
strb w3, [x3, x0]
ret
.cfi_restore_state // Reset unwind info so following code unwinds.
diff --git a/runtime/arch/mips/quick_entrypoints_mips.S b/runtime/arch/mips/quick_entrypoints_mips.S
index 722a679..61a3a04 100644
--- a/runtime/arch/mips/quick_entrypoints_mips.S
+++ b/runtime/arch/mips/quick_entrypoints_mips.S
@@ -1406,7 +1406,7 @@
POISON_HEAP_REF $a2
sw $a2, MIRROR_OBJECT_ARRAY_DATA_OFFSET($t0)
lw $t0, THREAD_CARD_TABLE_OFFSET(rSELF)
- srl $t1, $a0, 7
+ srl $t1, $a0, CARD_TABLE_CARD_SHIFT
add $t1, $t1, $t0
sb $t0, ($t1)
jalr $zero, $ra
diff --git a/runtime/arch/mips64/quick_entrypoints_mips64.S b/runtime/arch/mips64/quick_entrypoints_mips64.S
index 9402232..24caa0e 100644
--- a/runtime/arch/mips64/quick_entrypoints_mips64.S
+++ b/runtime/arch/mips64/quick_entrypoints_mips64.S
@@ -1374,7 +1374,7 @@
POISON_HEAP_REF $a2
sw $a2, MIRROR_OBJECT_ARRAY_DATA_OFFSET($t0)
ld $t0, THREAD_CARD_TABLE_OFFSET(rSELF)
- dsrl $t1, $a0, 7
+ dsrl $t1, $a0, CARD_TABLE_CARD_SHIFT
daddu $t1, $t1, $t0
sb $t0, ($t1)
jalr $zero, $ra
diff --git a/runtime/arch/x86/quick_entrypoints_x86.S b/runtime/arch/x86/quick_entrypoints_x86.S
index 6c0bcc9..3694c3e 100644
--- a/runtime/arch/x86/quick_entrypoints_x86.S
+++ b/runtime/arch/x86/quick_entrypoints_x86.S
@@ -1526,7 +1526,7 @@
POISON_HEAP_REF edx
movl %edx, MIRROR_OBJECT_ARRAY_DATA_OFFSET(%eax, %ecx, 4)
movl %fs:THREAD_CARD_TABLE_OFFSET, %edx
- shrl LITERAL(7), %eax
+ shrl LITERAL(CARD_TABLE_CARD_SHIFT), %eax
movb %dl, (%edx, %eax)
ret
.Ldo_aput_null:
@@ -1567,7 +1567,7 @@
POISON_HEAP_REF edx
movl %edx, MIRROR_OBJECT_ARRAY_DATA_OFFSET(%eax, %ecx, 4) // do the aput
movl %fs:THREAD_CARD_TABLE_OFFSET, %edx
- shrl LITERAL(7), %eax
+ shrl LITERAL(CARD_TABLE_CARD_SHIFT), %eax
movb %dl, (%edx, %eax)
ret
CFI_ADJUST_CFA_OFFSET(12) // 3 POP after the jz for unwinding.
diff --git a/runtime/arch/x86_64/quick_entrypoints_x86_64.S b/runtime/arch/x86_64/quick_entrypoints_x86_64.S
index 8e2acab..ad7c2b3 100644
--- a/runtime/arch/x86_64/quick_entrypoints_x86_64.S
+++ b/runtime/arch/x86_64/quick_entrypoints_x86_64.S
@@ -1504,8 +1504,8 @@
movl %edx, MIRROR_OBJECT_ARRAY_DATA_OFFSET(%edi, %esi, 4)
// movq %rdx, MIRROR_OBJECT_ARRAY_DATA_OFFSET(%rdi, %rsi, 4)
movq %gs:THREAD_CARD_TABLE_OFFSET, %rdx
- shrl LITERAL(7), %edi
-// shrl LITERAL(7), %rdi
+ shrl LITERAL(CARD_TABLE_CARD_SHIFT), %edi
+// shrl LITERAL(CARD_TABLE_CARD_SHIFT), %rdi
movb %dl, (%rdx, %rdi) // Note: this assumes that top 32b of %rdi are zero
ret
.Ldo_aput_null:
@@ -1545,8 +1545,8 @@
movl %edx, MIRROR_OBJECT_ARRAY_DATA_OFFSET(%edi, %esi, 4)
// movq %rdx, MIRROR_OBJECT_ARRAY_DATA_OFFSET(%rdi, %rsi, 4)
movq %gs:THREAD_CARD_TABLE_OFFSET, %rdx
- shrl LITERAL(7), %edi
-// shrl LITERAL(7), %rdi
+ shrl LITERAL(CARD_TABLE_CARD_SHIFT), %edi
+// shrl LITERAL(CARD_TABLE_CARD_SHIFT), %rdi
movb %dl, (%rdx, %rdi) // Note: this assumes that top 32b of %rdi are zero
// movb %dl, (%rdx, %rdi)
ret
diff --git a/runtime/gc/heap.cc b/runtime/gc/heap.cc
index 7da7221..bd4f99b 100644
--- a/runtime/gc/heap.cc
+++ b/runtime/gc/heap.cc
@@ -3517,7 +3517,13 @@
// is not the heap task daemon thread, it's considered as a
// blocking GC (i.e., blocking itself).
running_collection_is_blocking_ = true;
- VLOG(gc) << "Starting a blocking GC " << cause;
+ // Don't log fake "GC" types that are only used for debugger or hidden APIs. If we log these,
+ // it results in log spam. kGcCauseExplicit is already logged in LogGC, so avoid it here too.
+ if (cause == kGcCauseForAlloc ||
+ cause == kGcCauseForNativeAlloc ||
+ cause == kGcCauseDisableMovingGc) {
+ VLOG(gc) << "Starting a blocking GC " << cause;
+ }
}
return last_gc_type;
}
diff --git a/runtime/generated/asm_support_gen.h b/runtime/generated/asm_support_gen.h
index af57397..4af5625 100644
--- a/runtime/generated/asm_support_gen.h
+++ b/runtime/generated/asm_support_gen.h
@@ -78,6 +78,8 @@
DEFINE_CHECK_EQ(static_cast<int32_t>(STRING_DEX_CACHE_HASH_BITS), (static_cast<int32_t>(art::LeastSignificantBit(art::mirror::DexCache::kDexCacheStringCacheSize))))
#define STRING_DEX_CACHE_ELEMENT_SIZE 8
DEFINE_CHECK_EQ(static_cast<int32_t>(STRING_DEX_CACHE_ELEMENT_SIZE), (static_cast<int32_t>(sizeof(art::mirror::StringDexCachePair))))
+#define CARD_TABLE_CARD_SHIFT 0x7
+DEFINE_CHECK_EQ(static_cast<size_t>(CARD_TABLE_CARD_SHIFT), (static_cast<size_t>(art::gc::accounting::CardTable::kCardShift)))
#define MIN_LARGE_OBJECT_THRESHOLD 0x3000
DEFINE_CHECK_EQ(static_cast<size_t>(MIN_LARGE_OBJECT_THRESHOLD), (static_cast<size_t>(art::gc::Heap::kMinLargeObjectThreshold)))
#define LOCK_WORD_STATE_SHIFT 30
diff --git a/runtime/interpreter/unstarted_runtime.cc b/runtime/interpreter/unstarted_runtime.cc
index 70be30c..96934bc 100644
--- a/runtime/interpreter/unstarted_runtime.cc
+++ b/runtime/interpreter/unstarted_runtime.cc
@@ -568,7 +568,7 @@
// Copy in content.
memcpy(h_array->GetData(), mem_map->Begin(), map_size);
// Be proactive releasing memory.
- mem_map.release();
+ mem_map.reset();
// Create a ByteArrayInputStream.
Handle<mirror::Class> h_class(hs.NewHandle(
diff --git a/test/etc/run-test-jar b/test/etc/run-test-jar
index f725b89..df822e7 100755
--- a/test/etc/run-test-jar
+++ b/test/etc/run-test-jar
@@ -603,10 +603,10 @@
# Use -k 1m to SIGKILL it a minute later if it hasn't ended.
dex2oat_cmdline="timeout -k 1m -s SIGRTMIN+2 1m ${dex2oat_cmdline}"
fi
- if [ "$TEST_VDEX" = "y" ]; then
+ if [ "$PROFILE" = "y" ] || [ "$RANDOM_PROFILE" = "y" ]; then
+ vdex_cmdline="${dex2oat_cmdline} ${VDEX_FILTER} --input-vdex=$DEX_LOCATION/oat/$ISA/$TEST_NAME.vdex --output-vdex=$DEX_LOCATION/oat/$ISA/$TEST_NAME.vdex"
+ elif [ "$TEST_VDEX" = "y" ]; then
vdex_cmdline="${dex2oat_cmdline} ${VDEX_FILTER} --input-vdex=$DEX_LOCATION/oat/$ISA/$TEST_NAME.vdex"
- elif [ "$PROFILE" = "y" ] || [ "$RANDOM_PROFILE" = "y" ]; then
- vdex_cmdline="${dex2oat_cmdline} --input-vdex=$DEX_LOCATION/oat/$ISA/$TEST_NAME.vdex --output-vdex=$DEX_LOCATION/oat/$ISA/$TEST_NAME.vdex"
fi
fi
diff --git a/test/knownfailures.json b/test/knownfailures.json
index c7ad5bf..f7fb357 100644
--- a/test/knownfailures.json
+++ b/test/knownfailures.json
@@ -667,12 +667,6 @@
"bug": "b/37636792"
},
{
- "tests": "648-many-direct-methods",
- "variant": "optimizing",
- "description": "Test disabled with AOT because of dex2oatd timeouts.",
- "bug": "b/33650497"
- },
- {
"tests": [
"536-checker-needs-access-check",
"537-checker-inline-and-unverified",
diff --git a/tools/cpp-define-generator/constant_card_table.def b/tools/cpp-define-generator/constant_card_table.def
new file mode 100644
index 0000000..ae3e8f3
--- /dev/null
+++ b/tools/cpp-define-generator/constant_card_table.def
@@ -0,0 +1,25 @@
+/*
+ * Copyright (C) 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+// Export heap values.
+
+#if defined(DEFINE_INCLUDE_DEPENDENCIES)
+#include "gc/accounting/card_table.h"
+#endif
+
+// Size of references to the heap on the stack.
+DEFINE_EXPR(CARD_TABLE_CARD_SHIFT, size_t, art::gc::accounting::CardTable::kCardShift)
+
diff --git a/tools/cpp-define-generator/offsets_all.def b/tools/cpp-define-generator/offsets_all.def
index 13371a1..b8947de 100644
--- a/tools/cpp-define-generator/offsets_all.def
+++ b/tools/cpp-define-generator/offsets_all.def
@@ -49,6 +49,7 @@
// TODO: MIRROR_STRING offsets (depends on header size)
#include "offset_dexcache.def"
#include "constant_dexcache.def"
+#include "constant_card_table.def"
#include "constant_heap.def"
#include "constant_lockword.def"
#include "constant_globals.def"