ObjPtr<>-ify String allocations, fix stale refs.
ObjPtr<>-ify String allocation functions and related code
and remove some unnecessary calls to ObjPtr<>::Ptr(). Fix
stale reference uses in reference_table_test and stub_test.
Test: m test-art-host-gtest
Test: testrunner.py --host --optimizing
Bug: 31113334
Change-Id: I42927fb8b7240e5132188f73318b2ccb218748fd
diff --git a/runtime/mirror/class-inl.h b/runtime/mirror/class-inl.h
index 22597dd..220d66b 100644
--- a/runtime/mirror/class-inl.h
+++ b/runtime/mirror/class-inl.h
@@ -731,7 +731,7 @@
template<VerifyObjectFlags kVerifyFlags,
ReadBarrierOption kReadBarrierOption>
-inline String* Class::GetName() {
+inline ObjPtr<String> Class::GetName() {
return GetFieldObject<String, kVerifyFlags, kReadBarrierOption>(
OFFSET_OF_OBJECT_MEMBER(Class, name_));
}
diff --git a/runtime/mirror/class.cc b/runtime/mirror/class.cc
index 239105f..74b22c4 100644
--- a/runtime/mirror/class.cc
+++ b/runtime/mirror/class.cc
@@ -252,8 +252,8 @@
// Class.getName: keywords for primitive types, regular "[I" form for primitive arrays (so "int"
// but "[I"), and arrays of reference types written between "L" and ";" but with dots rather than
// slashes (so "java.lang.String" but "[Ljava.lang.String;"). Madness.
-String* Class::ComputeName(Handle<Class> h_this) {
- String* name = h_this->GetName();
+ObjPtr<String> Class::ComputeName(Handle<Class> h_this) {
+ ObjPtr<String> name = h_this->GetName();
if (name != nullptr) {
return name;
}
diff --git a/runtime/mirror/class.h b/runtime/mirror/class.h
index e8a7c1e..6ae3c79 100644
--- a/runtime/mirror/class.h
+++ b/runtime/mirror/class.h
@@ -340,10 +340,10 @@
template<VerifyObjectFlags kVerifyFlags = kDefaultVerifyFlags,
ReadBarrierOption kReadBarrierOption = kWithReadBarrier>
- String* GetName() REQUIRES_SHARED(Locks::mutator_lock_); // Returns the cached name.
+ ObjPtr<String> GetName() REQUIRES_SHARED(Locks::mutator_lock_); // Returns the cached name.
void SetName(ObjPtr<String> name) REQUIRES_SHARED(Locks::mutator_lock_); // Sets the cached name.
// Computes the name, then sets the cached value.
- static String* ComputeName(Handle<Class> h_this) REQUIRES_SHARED(Locks::mutator_lock_)
+ static ObjPtr<String> ComputeName(Handle<Class> h_this) REQUIRES_SHARED(Locks::mutator_lock_)
REQUIRES(!Roles::uninterruptible_);
template<VerifyObjectFlags kVerifyFlags = kDefaultVerifyFlags>
diff --git a/runtime/mirror/string-alloc-inl.h b/runtime/mirror/string-alloc-inl.h
index 4c4e2af..4330235 100644
--- a/runtime/mirror/string-alloc-inl.h
+++ b/runtime/mirror/string-alloc-inl.h
@@ -25,6 +25,7 @@
#include "class.h"
#include "class_root.h"
#include "gc/heap-inl.h"
+#include "obj_ptr.h"
#include "runtime.h"
#include "runtime_globals.h"
#include "thread.h"
@@ -154,10 +155,10 @@
};
template <bool kIsInstrumented, typename PreFenceVisitor>
-inline String* String::Alloc(Thread* self,
- int32_t utf16_length_with_flag,
- gc::AllocatorType allocator_type,
- const PreFenceVisitor& pre_fence_visitor) {
+inline ObjPtr<String> String::Alloc(Thread* self,
+ int32_t utf16_length_with_flag,
+ gc::AllocatorType allocator_type,
+ const PreFenceVisitor& pre_fence_visitor) {
constexpr size_t header_size = sizeof(String);
const bool compressible = kUseStringCompression && String::IsCompressed(utf16_length_with_flag);
const size_t block_size = (compressible) ? sizeof(uint8_t) : sizeof(uint16_t);
@@ -189,67 +190,64 @@
}
gc::Heap* heap = runtime->GetHeap();
- return down_cast<String*>(
+ return ObjPtr<String>::DownCast(MakeObjPtr(
heap->AllocObjectWithAllocator<kIsInstrumented, true>(self,
string_class,
alloc_size,
allocator_type,
- pre_fence_visitor));
+ pre_fence_visitor)));
}
template <bool kIsInstrumented>
-inline String* String::AllocEmptyString(Thread* self, gc::AllocatorType allocator_type) {
+inline ObjPtr<String> String::AllocEmptyString(Thread* self, gc::AllocatorType allocator_type) {
const int32_t length_with_flag = String::GetFlaggedCount(0, /* compressible= */ true);
SetStringCountVisitor visitor(length_with_flag);
return Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
}
template <bool kIsInstrumented>
-inline String* String::AllocFromByteArray(Thread* self,
- int32_t byte_length,
- Handle<ByteArray> array,
- int32_t offset,
- int32_t high_byte,
- gc::AllocatorType allocator_type) {
+inline ObjPtr<String> String::AllocFromByteArray(Thread* self,
+ int32_t byte_length,
+ Handle<ByteArray> array,
+ int32_t offset,
+ int32_t high_byte,
+ gc::AllocatorType allocator_type) {
const uint8_t* const src = reinterpret_cast<uint8_t*>(array->GetData()) + offset;
high_byte &= 0xff; // Extract the relevant bits before determining `compressible`.
const bool compressible =
kUseStringCompression && String::AllASCII<uint8_t>(src, byte_length) && (high_byte == 0);
const int32_t length_with_flag = String::GetFlaggedCount(byte_length, compressible);
SetStringCountAndBytesVisitor visitor(length_with_flag, array, offset, high_byte << 8);
- String* string = Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
- return string;
+ return Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
}
template <bool kIsInstrumented>
-inline String* String::AllocFromCharArray(Thread* self,
- int32_t count,
- Handle<CharArray> array,
- int32_t offset,
- gc::AllocatorType allocator_type) {
+inline ObjPtr<String> String::AllocFromCharArray(Thread* self,
+ int32_t count,
+ Handle<CharArray> array,
+ int32_t offset,
+ gc::AllocatorType allocator_type) {
// It is a caller error to have a count less than the actual array's size.
DCHECK_GE(array->GetLength(), count);
const bool compressible = kUseStringCompression &&
String::AllASCII<uint16_t>(array->GetData() + offset, count);
const int32_t length_with_flag = String::GetFlaggedCount(count, compressible);
SetStringCountAndValueVisitorFromCharArray visitor(length_with_flag, array, offset);
- String* new_string = Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
- return new_string;
+ return Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
}
template <bool kIsInstrumented>
-inline String* String::AllocFromString(Thread* self,
- int32_t string_length,
- Handle<String> string,
- int32_t offset,
- gc::AllocatorType allocator_type) {
+inline ObjPtr<String> String::AllocFromString(Thread* self,
+ int32_t string_length,
+ Handle<String> string,
+ int32_t offset,
+ gc::AllocatorType allocator_type) {
const bool compressible = kUseStringCompression &&
((string->IsCompressed()) ? true : String::AllASCII<uint16_t>(string->GetValue() + offset,
string_length));
const int32_t length_with_flag = String::GetFlaggedCount(string_length, compressible);
SetStringCountAndValueVisitorFromString visitor(length_with_flag, string, offset);
- String* new_string = Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
- return new_string;
+ return Alloc<kIsInstrumented>(self, length_with_flag, allocator_type, visitor);
}
} // namespace mirror
diff --git a/runtime/mirror/string.cc b/runtime/mirror/string.cc
index bf99c37..1881c57 100644
--- a/runtime/mirror/string.cc
+++ b/runtime/mirror/string.cc
@@ -119,7 +119,9 @@
return string;
}
-String* String::AllocFromStrings(Thread* self, Handle<String> string, Handle<String> string2) {
+ObjPtr<String> String::AllocFromStrings(Thread* self,
+ Handle<String> string,
+ Handle<String> string2) {
int32_t length = string->GetLength();
int32_t length2 = string2->GetLength();
gc::AllocatorType allocator_type = Runtime::Current()->GetHeap()->GetCurrentAllocator();
@@ -153,10 +155,12 @@
memcpy(new_value + length, string2->GetValue(), length2 * sizeof(uint16_t));
}
}
- return new_string.Ptr();
+ return new_string;
}
-String* String::AllocFromUtf16(Thread* self, int32_t utf16_length, const uint16_t* utf16_data_in) {
+ObjPtr<String> String::AllocFromUtf16(Thread* self,
+ int32_t utf16_length,
+ const uint16_t* utf16_data_in) {
CHECK(utf16_data_in != nullptr || utf16_length == 0);
gc::AllocatorType allocator_type = Runtime::Current()->GetHeap()->GetCurrentAllocator();
const bool compressible = kUseStringCompression &&
@@ -175,26 +179,26 @@
uint16_t* array = string->GetValue();
memcpy(array, utf16_data_in, utf16_length * sizeof(uint16_t));
}
- return string.Ptr();
+ return string;
}
-String* String::AllocFromModifiedUtf8(Thread* self, const char* utf) {
+ObjPtr<String> String::AllocFromModifiedUtf8(Thread* self, const char* utf) {
DCHECK(utf != nullptr);
size_t byte_count = strlen(utf);
size_t char_count = CountModifiedUtf8Chars(utf, byte_count);
return AllocFromModifiedUtf8(self, char_count, utf, byte_count);
}
-String* String::AllocFromModifiedUtf8(Thread* self,
- int32_t utf16_length,
- const char* utf8_data_in) {
+ObjPtr<String> String::AllocFromModifiedUtf8(Thread* self,
+ int32_t utf16_length,
+ const char* utf8_data_in) {
return AllocFromModifiedUtf8(self, utf16_length, utf8_data_in, strlen(utf8_data_in));
}
-String* String::AllocFromModifiedUtf8(Thread* self,
- int32_t utf16_length,
- const char* utf8_data_in,
- int32_t utf8_length) {
+ObjPtr<String> String::AllocFromModifiedUtf8(Thread* self,
+ int32_t utf16_length,
+ const char* utf8_data_in,
+ int32_t utf8_length) {
gc::AllocatorType allocator_type = Runtime::Current()->GetHeap()->GetCurrentAllocator();
const bool compressible = kUseStringCompression && (utf16_length == utf8_length);
const int32_t utf16_length_with_flag = String::GetFlaggedCount(utf16_length, compressible);
@@ -209,7 +213,7 @@
uint16_t* utf16_data_out = string->GetValue();
ConvertModifiedUtf8ToUtf16(utf16_data_out, utf16_length, utf8_data_in, utf8_length);
}
- return string.Ptr();
+ return string;
}
bool String::Equals(ObjPtr<String> that) {
@@ -319,7 +323,7 @@
return count_diff;
}
-CharArray* String::ToCharArray(Thread* self) {
+ObjPtr<CharArray> String::ToCharArray(Thread* self) {
StackHandleScope<1> hs(self);
Handle<String> string(hs.NewHandle(this));
ObjPtr<CharArray> result = CharArray::Alloc(self, GetLength());
@@ -335,7 +339,7 @@
} else {
self->AssertPendingOOMException();
}
- return result.Ptr();
+ return result;
}
void String::GetChars(int32_t start, int32_t end, Handle<CharArray> array, int32_t index) {
diff --git a/runtime/mirror/string.h b/runtime/mirror/string.h
index 4a7f4ae..c98aa6b 100644
--- a/runtime/mirror/string.h
+++ b/runtime/mirror/string.h
@@ -26,6 +26,7 @@
namespace art {
template<class T> class Handle;
+template<class MirrorType> class ObjPtr;
struct StringOffsets;
class StubTest_ReadBarrierForRoot_Test;
@@ -114,43 +115,57 @@
ObjPtr<String> Intern() REQUIRES_SHARED(Locks::mutator_lock_);
template <bool kIsInstrumented>
- ALWAYS_INLINE static String* AllocFromByteArray(Thread* self, int32_t byte_length,
- Handle<ByteArray> array, int32_t offset,
- int32_t high_byte,
- gc::AllocatorType allocator_type)
+ ALWAYS_INLINE static ObjPtr<String> AllocFromByteArray(Thread* self,
+ int32_t byte_length,
+ Handle<ByteArray> array,
+ int32_t offset,
+ int32_t high_byte,
+ gc::AllocatorType allocator_type)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
template <bool kIsInstrumented>
- ALWAYS_INLINE static String* AllocFromCharArray(Thread* self, int32_t count,
- Handle<CharArray> array, int32_t offset,
- gc::AllocatorType allocator_type)
+ ALWAYS_INLINE static ObjPtr<String> AllocFromCharArray(Thread* self,
+ int32_t count,
+ Handle<CharArray> array,
+ int32_t offset,
+ gc::AllocatorType allocator_type)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
template <bool kIsInstrumented>
- ALWAYS_INLINE static String* AllocFromString(Thread* self, int32_t string_length,
- Handle<String> string, int32_t offset,
- gc::AllocatorType allocator_type)
+ ALWAYS_INLINE static ObjPtr<String> AllocFromString(Thread* self,
+ int32_t string_length,
+ Handle<String> string,
+ int32_t offset,
+ gc::AllocatorType allocator_type)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
template <bool kIsInstrumented>
- ALWAYS_INLINE static String* AllocEmptyString(Thread* self,
- gc::AllocatorType allocator_type)
+ ALWAYS_INLINE static ObjPtr<String> AllocEmptyString(Thread* self,
+ gc::AllocatorType allocator_type)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
- static String* AllocFromStrings(Thread* self, Handle<String> string, Handle<String> string2)
+ static ObjPtr<String> AllocFromStrings(Thread* self,
+ Handle<String> string,
+ Handle<String> string2)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
- static String* AllocFromUtf16(Thread* self, int32_t utf16_length, const uint16_t* utf16_data_in)
+ static ObjPtr<String> AllocFromUtf16(Thread* self,
+ int32_t utf16_length,
+ const uint16_t* utf16_data_in)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
- static String* AllocFromModifiedUtf8(Thread* self, const char* utf)
+ static ObjPtr<String> AllocFromModifiedUtf8(Thread* self, const char* utf)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
- static String* AllocFromModifiedUtf8(Thread* self, int32_t utf16_length,
- const char* utf8_data_in, int32_t utf8_length)
+ static ObjPtr<String> AllocFromModifiedUtf8(Thread* self,
+ int32_t utf16_length,
+ const char* utf8_data_in,
+ int32_t utf8_length)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
- static String* AllocFromModifiedUtf8(Thread* self, int32_t utf16_length, const char* utf8_data_in)
+ static ObjPtr<String> AllocFromModifiedUtf8(Thread* self,
+ int32_t utf16_length,
+ const char* utf8_data_in)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
bool Equals(const char* modified_utf8) REQUIRES_SHARED(Locks::mutator_lock_);
@@ -168,7 +183,7 @@
int32_t CompareTo(ObjPtr<String> other) REQUIRES_SHARED(Locks::mutator_lock_);
- CharArray* ToCharArray(Thread* self) REQUIRES_SHARED(Locks::mutator_lock_)
+ ObjPtr<CharArray> ToCharArray(Thread* self) REQUIRES_SHARED(Locks::mutator_lock_)
REQUIRES(!Roles::uninterruptible_);
void GetChars(int32_t start, int32_t end, Handle<CharArray> array, int32_t index)
@@ -234,9 +249,10 @@
}
template <bool kIsInstrumented, typename PreFenceVisitor>
- ALWAYS_INLINE static String* Alloc(Thread* self, int32_t utf16_length_with_flag,
- gc::AllocatorType allocator_type,
- const PreFenceVisitor& pre_fence_visitor)
+ ALWAYS_INLINE static ObjPtr<String> Alloc(Thread* self,
+ int32_t utf16_length_with_flag,
+ gc::AllocatorType allocator_type,
+ const PreFenceVisitor& pre_fence_visitor)
REQUIRES_SHARED(Locks::mutator_lock_) REQUIRES(!Roles::uninterruptible_);
// Field order required by test "ValidateFieldOrderOfJavaCppUnionClasses".
diff --git a/runtime/mirror/var_handle_test.cc b/runtime/mirror/var_handle_test.cc
index a349e34..3382066 100644
--- a/runtime/mirror/var_handle_test.cc
+++ b/runtime/mirror/var_handle_test.cc
@@ -52,7 +52,7 @@
if (art_field->IsStatic()) {
InitializeVarHandle(fvh.Get(), var_type, access_modes_bit_mask);
} else {
- Handle<Class> declaring_type = hs.NewHandle(art_field->GetDeclaringClass().Ptr());
+ Handle<Class> declaring_type = hs.NewHandle(art_field->GetDeclaringClass());
InitializeVarHandle(fvh.Get(),
var_type,
declaring_type,