diff options
Diffstat (limited to 'runtime')
-rw-r--r-- | runtime/arch/arm64/instruction_set_features_arm64.cc | 16 | ||||
-rw-r--r-- | runtime/arch/arm64/instruction_set_features_arm64.h | 14 | ||||
-rw-r--r-- | runtime/gc/accounting/mod_union_table_test.cc | 2 | ||||
-rw-r--r-- | runtime/mirror/array-inl.h | 21 |
4 files changed, 32 insertions, 21 deletions
diff --git a/runtime/arch/arm64/instruction_set_features_arm64.cc b/runtime/arch/arm64/instruction_set_features_arm64.cc index a1270dcde9..f8a9f9d6aa 100644 --- a/runtime/arch/arm64/instruction_set_features_arm64.cc +++ b/runtime/arch/arm64/instruction_set_features_arm64.cc @@ -48,19 +48,23 @@ const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromVariant( return nullptr; } } - return new Arm64InstructionSetFeatures(smp, needs_a53_835769_fix); + + // The variants that need a fix for 843419 are the same that need a fix for 835769. + bool needs_a53_843419_fix = needs_a53_835769_fix; + + return new Arm64InstructionSetFeatures(smp, needs_a53_835769_fix, needs_a53_843419_fix); } const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromBitmap(uint32_t bitmap) { bool smp = (bitmap & kSmpBitfield) != 0; bool is_a53 = (bitmap & kA53Bitfield) != 0; - return new Arm64InstructionSetFeatures(smp, is_a53); + return new Arm64InstructionSetFeatures(smp, is_a53, is_a53); } const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromCppDefines() { const bool smp = true; const bool is_a53 = true; // Pessimistically assume all ARM64s are A53s. - return new Arm64InstructionSetFeatures(smp, is_a53); + return new Arm64InstructionSetFeatures(smp, is_a53, is_a53); } const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromCpuInfo() { @@ -85,13 +89,13 @@ const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromCpuInfo() { } else { LOG(ERROR) << "Failed to open /proc/cpuinfo"; } - return new Arm64InstructionSetFeatures(smp, is_a53); + return new Arm64InstructionSetFeatures(smp, is_a53, is_a53); } const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromHwcap() { bool smp = sysconf(_SC_NPROCESSORS_CONF) > 1; const bool is_a53 = true; // Pessimistically assume all ARM64s are A53s. - return new Arm64InstructionSetFeatures(smp, is_a53); + return new Arm64InstructionSetFeatures(smp, is_a53, is_a53); } const Arm64InstructionSetFeatures* Arm64InstructionSetFeatures::FromAssembly() { @@ -140,7 +144,7 @@ const InstructionSetFeatures* Arm64InstructionSetFeatures::AddFeaturesFromSplitS return nullptr; } } - return new Arm64InstructionSetFeatures(smp, is_a53); + return new Arm64InstructionSetFeatures(smp, is_a53, is_a53); } } // namespace art diff --git a/runtime/arch/arm64/instruction_set_features_arm64.h b/runtime/arch/arm64/instruction_set_features_arm64.h index f6bfee7e63..3b3e2c95fe 100644 --- a/runtime/arch/arm64/instruction_set_features_arm64.h +++ b/runtime/arch/arm64/instruction_set_features_arm64.h @@ -61,6 +61,11 @@ class Arm64InstructionSetFeatures FINAL : public InstructionSetFeatures { return fix_cortex_a53_835769_; } + // Generate code addressing Cortex-A53 erratum 843419? + bool NeedFixCortexA53_843419() const { + return fix_cortex_a53_843419_; + } + // TODO: Tune this on a per CPU basis. For now, we pessimistically assume // that all ARM64 CPUs prefer explicit memory barriers over acquire-release. // @@ -79,8 +84,12 @@ class Arm64InstructionSetFeatures FINAL : public InstructionSetFeatures { std::string* error_msg) const OVERRIDE; private: - explicit Arm64InstructionSetFeatures(bool smp, bool needs_a53_835769_fix) - : InstructionSetFeatures(smp), fix_cortex_a53_835769_(needs_a53_835769_fix) { + explicit Arm64InstructionSetFeatures(bool smp, + bool needs_a53_835769_fix, + bool needs_a53_843419_fix) + : InstructionSetFeatures(smp), + fix_cortex_a53_835769_(needs_a53_835769_fix), + fix_cortex_a53_843419_(needs_a53_843419_fix) { } // Bitmap positions for encoding features as a bitmap. @@ -90,6 +99,7 @@ class Arm64InstructionSetFeatures FINAL : public InstructionSetFeatures { }; const bool fix_cortex_a53_835769_; + const bool fix_cortex_a53_843419_; DISALLOW_COPY_AND_ASSIGN(Arm64InstructionSetFeatures); }; diff --git a/runtime/gc/accounting/mod_union_table_test.cc b/runtime/gc/accounting/mod_union_table_test.cc index 77809358e4..94bb3f52cc 100644 --- a/runtime/gc/accounting/mod_union_table_test.cc +++ b/runtime/gc/accounting/mod_union_table_test.cc @@ -47,7 +47,7 @@ class ModUnionTableTest : public CommonRuntimeTest { Thread* self, space::ContinuousMemMapAllocSpace* space, size_t component_count) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { auto* klass = GetObjectArrayClass(self, space); - const size_t size = ComputeArraySize(self, klass, component_count, 2); + const size_t size = mirror::ComputeArraySize(component_count, 2); size_t bytes_allocated = 0, bytes_tl_bulk_allocated; auto* obj = down_cast<mirror::ObjectArray<mirror::Object>*>( space->Alloc(self, size, &bytes_allocated, nullptr, &bytes_tl_bulk_allocated)); diff --git a/runtime/mirror/array-inl.h b/runtime/mirror/array-inl.h index 048d8ba08f..7f04992c5c 100644 --- a/runtime/mirror/array-inl.h +++ b/runtime/mirror/array-inl.h @@ -64,25 +64,20 @@ inline bool Array::CheckIsValidIndex(int32_t index) { return true; } -static inline size_t ComputeArraySize(Thread* self, Class* array_class, int32_t component_count, - size_t component_size_shift) - SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { - DCHECK(array_class != NULL); +static inline size_t ComputeArraySize(int32_t component_count, size_t component_size_shift) { DCHECK_GE(component_count, 0); - DCHECK(array_class->IsArrayClass()); size_t component_size = 1U << component_size_shift; size_t header_size = Array::DataOffset(component_size).SizeValue(); size_t data_size = static_cast<size_t>(component_count) << component_size_shift; size_t size = header_size + data_size; - // Check for size_t overflow and throw OutOfMemoryError if this was - // an unreasonable request. + // Check for size_t overflow if this was an unreasonable request + // but let the caller throw OutOfMemoryError. #ifdef __LP64__ // 64-bit. No overflow as component_count is 32-bit and the maximum // component size is 8. DCHECK_LE((1U << component_size_shift), 8U); - UNUSED(self); #else // 32-bit. DCHECK_NE(header_size, 0U); @@ -90,9 +85,6 @@ static inline size_t ComputeArraySize(Thread* self, Class* array_class, int32_t // The array length limit (exclusive). const size_t length_limit = (0U - header_size) >> component_size_shift; if (UNLIKELY(length_limit <= static_cast<size_t>(component_count))) { - self->ThrowOutOfMemoryError(StringPrintf("%s of length %d would overflow", - PrettyDescriptor(array_class).c_str(), - component_count).c_str()); return 0; // failure } #endif @@ -159,15 +151,20 @@ template <bool kIsInstrumented, bool kFillUsable> inline Array* Array::Alloc(Thread* self, Class* array_class, int32_t component_count, size_t component_size_shift, gc::AllocatorType allocator_type) { DCHECK(allocator_type != gc::kAllocatorTypeLOS); + DCHECK(array_class != nullptr); + DCHECK(array_class->IsArrayClass()); DCHECK_EQ(array_class->GetComponentSizeShift(), component_size_shift); DCHECK_EQ(array_class->GetComponentSize(), (1U << component_size_shift)); - size_t size = ComputeArraySize(self, array_class, component_count, component_size_shift); + size_t size = ComputeArraySize(component_count, component_size_shift); #ifdef __LP64__ // 64-bit. No size_t overflow. DCHECK_NE(size, 0U); #else // 32-bit. if (UNLIKELY(size == 0)) { + self->ThrowOutOfMemoryError(StringPrintf("%s of length %d would overflow", + PrettyDescriptor(array_class).c_str(), + component_count).c_str()); return nullptr; } #endif |