| OLD | NEW |
| 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/object.h" | 5 #include "vm/object.h" |
| 6 | 6 |
| 7 #include "vm/assembler.h" | 7 #include "vm/assembler.h" |
| 8 #include "vm/assert.h" | 8 #include "vm/assert.h" |
| 9 #include "vm/bigint_operations.h" | 9 #include "vm/bigint_operations.h" |
| 10 #include "vm/bootstrap.h" | 10 #include "vm/bootstrap.h" |
| (...skipping 754 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 765 result.set_handle_vtable(fake.vtable()); | 765 result.set_handle_vtable(fake.vtable()); |
| 766 result.set_instance_size(FakeObject::InstanceSize()); | 766 result.set_instance_size(FakeObject::InstanceSize()); |
| 767 result.set_next_field_offset(FakeObject::InstanceSize()); | 767 result.set_next_field_offset(FakeObject::InstanceSize()); |
| 768 result.set_instance_kind(FakeObject::kInstanceKind); | 768 result.set_instance_kind(FakeObject::kInstanceKind); |
| 769 result.raw_ptr()->is_const_ = false; | 769 result.raw_ptr()->is_const_ = false; |
| 770 result.raw_ptr()->is_interface_ = false; | 770 result.raw_ptr()->is_interface_ = false; |
| 771 // VM backed classes are almost ready: run checks and resolve class | 771 // VM backed classes are almost ready: run checks and resolve class |
| 772 // references, but do not recompute size. | 772 // references, but do not recompute size. |
| 773 result.raw_ptr()->class_state_ = RawClass::kPreFinalized; | 773 result.raw_ptr()->class_state_ = RawClass::kPreFinalized; |
| 774 result.raw_ptr()->type_arguments_instance_field_offset_ = kNoTypeArguments; | 774 result.raw_ptr()->type_arguments_instance_field_offset_ = kNoTypeArguments; |
| 775 result.raw_ptr()->num_constants_ = 0; | |
| 776 result.raw_ptr()->num_canonical_types_ = 0; | |
| 777 result.raw_ptr()->num_native_fields_ = 0; | 775 result.raw_ptr()->num_native_fields_ = 0; |
| 778 result.InitEmptyFields(); | 776 result.InitEmptyFields(); |
| 779 return result.raw(); | 777 return result.raw(); |
| 780 } | 778 } |
| 781 | 779 |
| 782 | 780 |
| 783 // Initialize class fields of type Array with empty array. | 781 // Initialize class fields of type Array with empty array. |
| 784 void Class::InitEmptyFields() { | 782 void Class::InitEmptyFields() { |
| 785 const Array& empty_array = Array::Handle(Array::Empty()); | 783 const Array& empty_array = Array::Handle(Array::Empty()); |
| 786 if (empty_array.IsNull()) { | 784 if (empty_array.IsNull()) { |
| (...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1003 result.set_handle_vtable(fake.vtable()); | 1001 result.set_handle_vtable(fake.vtable()); |
| 1004 result.set_instance_size(FakeInstance::InstanceSize()); | 1002 result.set_instance_size(FakeInstance::InstanceSize()); |
| 1005 result.set_next_field_offset(FakeInstance::InstanceSize()); | 1003 result.set_next_field_offset(FakeInstance::InstanceSize()); |
| 1006 result.set_instance_kind(FakeInstance::kInstanceKind); | 1004 result.set_instance_kind(FakeInstance::kInstanceKind); |
| 1007 result.set_name(name); | 1005 result.set_name(name); |
| 1008 result.set_script(script); | 1006 result.set_script(script); |
| 1009 result.raw_ptr()->is_const_ = false; | 1007 result.raw_ptr()->is_const_ = false; |
| 1010 result.raw_ptr()->is_interface_ = false; | 1008 result.raw_ptr()->is_interface_ = false; |
| 1011 result.raw_ptr()->class_state_ = RawClass::kAllocated; | 1009 result.raw_ptr()->class_state_ = RawClass::kAllocated; |
| 1012 result.raw_ptr()->type_arguments_instance_field_offset_ = kNoTypeArguments; | 1010 result.raw_ptr()->type_arguments_instance_field_offset_ = kNoTypeArguments; |
| 1013 result.raw_ptr()->num_constants_ = 0; | |
| 1014 result.raw_ptr()->num_canonical_types_ = 0; | |
| 1015 result.raw_ptr()->num_native_fields_ = 0; | 1011 result.raw_ptr()->num_native_fields_ = 0; |
| 1016 result.InitEmptyFields(); | 1012 result.InitEmptyFields(); |
| 1017 return result.raw(); | 1013 return result.raw(); |
| 1018 } | 1014 } |
| 1019 | 1015 |
| 1020 | 1016 |
| 1021 RawClass* Class::New(const String& name, const Script& script) { | 1017 RawClass* Class::New(const String& name, const Script& script) { |
| 1022 Class& result = Class::Handle(New<Instance>(name, script)); | 1018 Class& result = Class::Handle(New<Instance>(name, script)); |
| 1023 return result.raw(); | 1019 return result.raw(); |
| 1024 } | 1020 } |
| (...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1195 RawArray* Class::constants() const { | 1191 RawArray* Class::constants() const { |
| 1196 return raw_ptr()->constants_; | 1192 return raw_ptr()->constants_; |
| 1197 } | 1193 } |
| 1198 | 1194 |
| 1199 void Class::set_constants(const Array& value) const { | 1195 void Class::set_constants(const Array& value) const { |
| 1200 ASSERT(!value.IsNull()); | 1196 ASSERT(!value.IsNull()); |
| 1201 StorePointer(&raw_ptr()->constants_, value.raw()); | 1197 StorePointer(&raw_ptr()->constants_, value.raw()); |
| 1202 } | 1198 } |
| 1203 | 1199 |
| 1204 | 1200 |
| 1205 intptr_t Class::num_constants() const { | |
| 1206 return raw_ptr()->num_constants_; | |
| 1207 } | |
| 1208 | |
| 1209 | |
| 1210 void Class::set_num_constants(intptr_t value) const { | |
| 1211 raw_ptr()->num_constants_ = value; | |
| 1212 } | |
| 1213 | |
| 1214 | |
| 1215 RawArray* Class::canonical_types() const { | 1201 RawArray* Class::canonical_types() const { |
| 1216 return raw_ptr()->canonical_types_; | 1202 return raw_ptr()->canonical_types_; |
| 1217 } | 1203 } |
| 1218 | 1204 |
| 1219 void Class::set_canonical_types(const Array& value) const { | 1205 void Class::set_canonical_types(const Array& value) const { |
| 1220 ASSERT(!value.IsNull()); | 1206 ASSERT(!value.IsNull()); |
| 1221 StorePointer(&raw_ptr()->canonical_types_, value.raw()); | 1207 StorePointer(&raw_ptr()->canonical_types_, value.raw()); |
| 1222 } | 1208 } |
| 1223 | 1209 |
| 1224 | 1210 |
| 1225 intptr_t Class::num_canonical_types() const { | |
| 1226 return raw_ptr()->num_canonical_types_; | |
| 1227 } | |
| 1228 | |
| 1229 | |
| 1230 void Class::set_num_canonical_types(intptr_t value) const { | |
| 1231 raw_ptr()->num_canonical_types_ = value; | |
| 1232 } | |
| 1233 | |
| 1234 | |
| 1235 void Class::set_allocation_stub(const Code& value) const { | 1211 void Class::set_allocation_stub(const Code& value) const { |
| 1236 ASSERT(!value.IsNull()); | 1212 ASSERT(!value.IsNull()); |
| 1237 ASSERT(raw_ptr()->allocation_stub_ == Code::null()); | 1213 ASSERT(raw_ptr()->allocation_stub_ == Code::null()); |
| 1238 StorePointer(&raw_ptr()->allocation_stub_, value.raw()); | 1214 StorePointer(&raw_ptr()->allocation_stub_, value.raw()); |
| 1239 } | 1215 } |
| 1240 | 1216 |
| 1241 | 1217 |
| 1242 bool Class::IsObjectClass() const { | 1218 bool Class::IsObjectClass() const { |
| 1243 return raw() == Type::Handle(Type::ObjectType()).type_class(); | 1219 return raw() == Type::Handle(Type::ObjectType()).type_class(); |
| 1244 } | 1220 } |
| (...skipping 810 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2055 RawType* ParameterizedType::Canonicalize() const { | 2031 RawType* ParameterizedType::Canonicalize() const { |
| 2056 const Class& cls = Class::Handle(type_class()); | 2032 const Class& cls = Class::Handle(type_class()); |
| 2057 Array& canonical_types = Array::Handle(cls.canonical_types()); | 2033 Array& canonical_types = Array::Handle(cls.canonical_types()); |
| 2058 if (canonical_types.IsNull()) { | 2034 if (canonical_types.IsNull()) { |
| 2059 // Types defined in the VM isolate are canonicalized via the object store. | 2035 // Types defined in the VM isolate are canonicalized via the object store. |
| 2060 // TODO(regis): Should we add null_class_, void_class_, dynamic_class_ to | 2036 // TODO(regis): Should we add null_class_, void_class_, dynamic_class_ to |
| 2061 // the object store, remove all types from the object store, and replace | 2037 // the object store, remove all types from the object store, and replace |
| 2062 // the test above by an assert? | 2038 // the test above by an assert? |
| 2063 return this->raw(); | 2039 return this->raw(); |
| 2064 } | 2040 } |
| 2065 const intptr_t num_canonical_types = cls.num_canonical_types(); | 2041 const intptr_t canonical_types_len = canonical_types.Length(); |
| 2066 ASSERT(canonical_types.Length() >= num_canonical_types); | |
| 2067 // Linear search to see whether this type is already present in the | 2042 // Linear search to see whether this type is already present in the |
| 2068 // list of canonicalized types. | 2043 // list of canonicalized types. |
| 2069 Type& type = Type::Handle(); | 2044 Type& type = Type::Handle(); |
| 2070 for (int i = 0; i < num_canonical_types; i++) { | 2045 intptr_t index = 0; |
| 2071 type ^= canonical_types.At(i); | 2046 while (index < canonical_types_len) { |
| 2072 ASSERT(!type.IsNull()); | 2047 type ^= canonical_types.At(index); |
| 2048 if (type.IsNull()) { |
| 2049 break; |
| 2050 } |
| 2073 if (this->Equals(type)) { | 2051 if (this->Equals(type)) { |
| 2074 return type.raw(); | 2052 return type.raw(); |
| 2075 } | 2053 } |
| 2054 index++; |
| 2076 } | 2055 } |
| 2077 // The type needs to be added to the list. Grow the list if it is full. | 2056 // The type needs to be added to the list. Grow the list if it is full. |
| 2078 if (canonical_types.Length() == num_canonical_types) { | 2057 if (index == canonical_types_len) { |
| 2079 const intptr_t kLengthIncrement = 2; // Raw and parameterized. | 2058 const intptr_t kLengthIncrement = 2; // Raw and parameterized. |
| 2080 const intptr_t new_length = canonical_types.Length() + kLengthIncrement; | 2059 const intptr_t new_length = canonical_types.Length() + kLengthIncrement; |
| 2081 const Array& new_canonical_types = | 2060 const Array& new_canonical_types = |
| 2082 Array::Handle(Array::Grow(canonical_types, new_length, Heap::kOld)); | 2061 Array::Handle(Array::Grow(canonical_types, new_length, Heap::kOld)); |
| 2083 cls.set_canonical_types(new_canonical_types); | 2062 cls.set_canonical_types(new_canonical_types); |
| 2084 new_canonical_types.SetAt(num_canonical_types, *this); | 2063 new_canonical_types.SetAt(index, *this); |
| 2085 } else { | 2064 } else { |
| 2086 canonical_types.SetAt(num_canonical_types, *this); | 2065 canonical_types.SetAt(index, *this); |
| 2087 } | 2066 } |
| 2088 cls.set_num_canonical_types(num_canonical_types + 1); | |
| 2089 return this->raw(); | 2067 return this->raw(); |
| 2090 } | 2068 } |
| 2091 | 2069 |
| 2092 | 2070 |
| 2093 void ParameterizedType::set_type_class(const Object& value) const { | 2071 void ParameterizedType::set_type_class(const Object& value) const { |
| 2094 ASSERT(!value.IsNull() && (value.IsClass() || value.IsUnresolvedClass())); | 2072 ASSERT(!value.IsNull() && (value.IsClass() || value.IsUnresolvedClass())); |
| 2095 StorePointer(&raw_ptr()->type_class_, value.raw()); | 2073 StorePointer(&raw_ptr()->type_class_, value.raw()); |
| 2096 } | 2074 } |
| 2097 | 2075 |
| 2098 | 2076 |
| (...skipping 2704 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 4803 (*reinterpret_cast<RawObject**>(other_addr + offset))) { | 4781 (*reinterpret_cast<RawObject**>(other_addr + offset))) { |
| 4804 return false; | 4782 return false; |
| 4805 } | 4783 } |
| 4806 } | 4784 } |
| 4807 } | 4785 } |
| 4808 return true; | 4786 return true; |
| 4809 } | 4787 } |
| 4810 | 4788 |
| 4811 | 4789 |
| 4812 RawInstance* Instance::Canonicalize() const { | 4790 RawInstance* Instance::Canonicalize() const { |
| 4791 ASSERT(!IsNull()); |
| 4813 const Class& cls = Class::Handle(this->clazz()); | 4792 const Class& cls = Class::Handle(this->clazz()); |
| 4814 Array& constants = Array::Handle(cls.constants()); | 4793 Array& constants = Array::Handle(cls.constants()); |
| 4815 const intptr_t num_constants = cls.num_constants(); | 4794 const intptr_t constants_len = constants.Length(); |
| 4816 ASSERT(constants.Length() >= num_constants); | |
| 4817 // Linear search to see whether this value is already present in the | 4795 // Linear search to see whether this value is already present in the |
| 4818 // list of canonicalized constants. | 4796 // list of canonicalized constants. |
| 4819 Instance& norm_value = Instance::Handle(); | 4797 Instance& norm_value = Instance::Handle(); |
| 4820 for (int i = 0; i < num_constants; i++) { | 4798 intptr_t index = 0; |
| 4821 norm_value ^= constants.At(i); | 4799 while (index < constants_len) { |
| 4822 ASSERT(!norm_value.IsNull()); | 4800 norm_value ^= constants.At(index); |
| 4801 if (norm_value.IsNull()) { |
| 4802 break; |
| 4803 } |
| 4823 if (this->Equals(norm_value)) { | 4804 if (this->Equals(norm_value)) { |
| 4824 return norm_value.raw(); | 4805 return norm_value.raw(); |
| 4825 } | 4806 } |
| 4807 index++; |
| 4826 } | 4808 } |
| 4827 // The value needs to be added to the list. Grow the list if | 4809 // The value needs to be added to the list. Grow the list if |
| 4828 // it is full. | 4810 // it is full. |
| 4829 if (constants.Length() == num_constants) { | 4811 if (index == constants_len) { |
| 4830 const intptr_t kInitialConstLength = 4; | 4812 const intptr_t kInitialConstLength = 4; |
| 4831 const intptr_t old_length = constants.Length(); | 4813 const intptr_t old_length = constants.Length(); |
| 4832 const intptr_t new_length = | 4814 const intptr_t new_length = |
| 4833 (old_length == 0) ? kInitialConstLength : old_length * 2; | 4815 (old_length == 0) ? kInitialConstLength : old_length * 2; |
| 4834 const Array& new_constants = | 4816 const Array& new_constants = |
| 4835 Array::Handle(Array::Grow(constants, new_length, Heap::kOld)); | 4817 Array::Handle(Array::Grow(constants, new_length, Heap::kOld)); |
| 4836 cls.set_constants(new_constants); | 4818 cls.set_constants(new_constants); |
| 4837 new_constants.SetAt(num_constants, *this); | 4819 new_constants.SetAt(index, *this); |
| 4838 } else { | 4820 } else { |
| 4839 constants.SetAt(num_constants, *this); | 4821 constants.SetAt(index, *this); |
| 4840 } | 4822 } |
| 4841 cls.set_num_constants(num_constants + 1); | |
| 4842 return this->raw(); | 4823 return this->raw(); |
| 4843 } | 4824 } |
| 4844 | 4825 |
| 4845 | 4826 |
| 4846 RawType* Instance::GetType() const { | 4827 RawType* Instance::GetType() const { |
| 4847 if (IsNull()) { | 4828 if (IsNull()) { |
| 4848 return Type::NullType(); | 4829 return Type::NullType(); |
| 4849 } | 4830 } |
| 4850 const Class& cls = Class::Handle(clazz()); | 4831 const Class& cls = Class::Handle(clazz()); |
| 4851 TypeArguments& type_arguments = TypeArguments::Handle(); | 4832 TypeArguments& type_arguments = TypeArguments::Handle(); |
| (...skipping 2106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6958 const String& str = String::Handle(pattern()); | 6939 const String& str = String::Handle(pattern()); |
| 6959 const char* format = "JSRegExp: pattern=%s flags=%s"; | 6940 const char* format = "JSRegExp: pattern=%s flags=%s"; |
| 6960 intptr_t len = OS::SNPrint(NULL, 0, format, str.ToCString(), Flags()); | 6941 intptr_t len = OS::SNPrint(NULL, 0, format, str.ToCString(), Flags()); |
| 6961 char* chars = reinterpret_cast<char*>( | 6942 char* chars = reinterpret_cast<char*>( |
| 6962 Isolate::Current()->current_zone()->Allocate(len + 1)); | 6943 Isolate::Current()->current_zone()->Allocate(len + 1)); |
| 6963 OS::SNPrint(chars, (len + 1), format, str.ToCString(), Flags()); | 6944 OS::SNPrint(chars, (len + 1), format, str.ToCString(), Flags()); |
| 6964 return chars; | 6945 return chars; |
| 6965 } | 6946 } |
| 6966 | 6947 |
| 6967 } // namespace dart | 6948 } // namespace dart |
| OLD | NEW |