1 /* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ART_RUNTIME_MIRROR_STRING_H_ 18 #define ART_RUNTIME_MIRROR_STRING_H_ 19 20 #include <gtest/gtest.h> 21 22 #include "gc_root.h" 23 #include "object.h" 24 #include "object_callbacks.h" 25 26 namespace art { 27 28 template<class T> class Handle; 29 struct StringOffsets; 30 class StringPiece; 31 32 namespace mirror { 33 34 // C++ mirror of java.lang.String 35 class MANAGED String FINAL : public Object { 36 public: 37 // Size of java.lang.String.class. 38 static uint32_t ClassSize(); 39 40 // Size of an instance of java.lang.String not including its value array. InstanceSize()41 static constexpr uint32_t InstanceSize() { 42 return sizeof(String); 43 } 44 CountOffset()45 static MemberOffset CountOffset() { 46 return OFFSET_OF_OBJECT_MEMBER(String, count_); 47 } 48 ValueOffset()49 static MemberOffset ValueOffset() { 50 return OFFSET_OF_OBJECT_MEMBER(String, array_); 51 } 52 OffsetOffset()53 static MemberOffset OffsetOffset() { 54 return OFFSET_OF_OBJECT_MEMBER(String, offset_); 55 } 56 57 CharArray* GetCharArray() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 58 GetOffset()59 int32_t GetOffset() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { 60 int32_t result = GetField32(OffsetOffset()); 61 DCHECK_LE(0, result); 62 return result; 63 } 64 65 int32_t GetLength() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 66 67 int32_t GetHashCode() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 68 69 // Computes, stores, and returns the hash code. 70 int32_t ComputeHashCode() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 71 72 int32_t GetUtfLength() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 73 74 uint16_t CharAt(int32_t index) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 75 76 String* Intern() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 77 78 static String* AllocFromUtf16(Thread* self, 79 int32_t utf16_length, 80 const uint16_t* utf16_data_in, 81 int32_t hash_code = 0) 82 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 83 84 static String* AllocFromModifiedUtf8(Thread* self, const char* utf) 85 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 86 87 static String* AllocFromModifiedUtf8(Thread* self, int32_t utf16_length, 88 const char* utf8_data_in) 89 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 90 91 bool Equals(const char* modified_utf8) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 92 93 // TODO: do we need this overload? give it a more intention-revealing name. 94 bool Equals(const StringPiece& modified_utf8) 95 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 96 97 bool Equals(String* that) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 98 99 // Compare UTF-16 code point values not in a locale-sensitive manner 100 int Compare(int32_t utf16_length, const char* utf8_data_in); 101 102 // TODO: do we need this overload? give it a more intention-revealing name. 103 bool Equals(const uint16_t* that_chars, int32_t that_offset, 104 int32_t that_length) 105 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 106 107 // Create a modified UTF-8 encoded std::string from a java/lang/String object. 108 std::string ToModifiedUtf8() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 109 110 int32_t FastIndexOf(int32_t ch, int32_t start) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 111 112 int32_t CompareTo(String* other) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 113 SetOffset(int32_t new_offset)114 void SetOffset(int32_t new_offset) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { 115 // Offset is only used during testing so use non-transactional mode. 116 DCHECK_LE(0, new_offset); 117 SetField32<false>(OFFSET_OF_OBJECT_MEMBER(String, offset_), new_offset); 118 } 119 120 void SetArray(CharArray* new_array) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 121 GetJavaLangString()122 static Class* GetJavaLangString() SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { 123 DCHECK(!java_lang_String_.IsNull()); 124 return java_lang_String_.Read(); 125 } 126 127 static void SetClass(Class* java_lang_String); 128 static void ResetClass(); 129 static void VisitRoots(RootCallback* callback, void* arg) 130 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 131 132 private: SetHashCode(int32_t new_hash_code)133 void SetHashCode(int32_t new_hash_code) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { 134 // Hash code is invariant so use non-transactional mode. Also disable check as we may run inside 135 // a transaction. 136 DCHECK_EQ(0, GetField32(OFFSET_OF_OBJECT_MEMBER(String, hash_code_))); 137 SetField32<false, false>(OFFSET_OF_OBJECT_MEMBER(String, hash_code_), new_hash_code); 138 } 139 SetCount(int32_t new_count)140 void SetCount(int32_t new_count) SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) { 141 // Count is invariant so use non-transactional mode. Also disable check as we may run inside 142 // a transaction. 143 DCHECK_LE(0, new_count); 144 SetField32<false, false>(OFFSET_OF_OBJECT_MEMBER(String, count_), new_count); 145 } 146 147 static String* Alloc(Thread* self, int32_t utf16_length) 148 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 149 150 static String* Alloc(Thread* self, Handle<CharArray> array) 151 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_); 152 153 // Field order required by test "ValidateFieldOrderOfJavaCppUnionClasses". 154 HeapReference<CharArray> array_; 155 156 int32_t count_; 157 158 uint32_t hash_code_; 159 160 int32_t offset_; 161 162 static GcRoot<Class> java_lang_String_; 163 164 friend struct art::StringOffsets; // for verifying offset information 165 166 FRIEND_TEST(ObjectTest, StringLength); // for SetOffset and SetCount 167 DISALLOW_IMPLICIT_CONSTRUCTORS(String); 168 }; 169 170 } // namespace mirror 171 } // namespace art 172 173 #endif // ART_RUNTIME_MIRROR_STRING_H_ 174