| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, 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/code_generator.h" | 5 #include "vm/code_generator.h" |
| 6 | 6 |
| 7 #include "vm/assembler.h" | 7 #include "vm/assembler.h" |
| 8 #include "vm/ast.h" | 8 #include "vm/ast.h" |
| 9 #include "vm/bigint_operations.h" | 9 #include "vm/bigint_operations.h" |
| 10 #include "vm/code_patcher.h" | 10 #include "vm/code_patcher.h" |
| (...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 104 | 104 |
| 105 // Allocate a new object. | 105 // Allocate a new object. |
| 106 // Arg0: class of the object that needs to be allocated. | 106 // Arg0: class of the object that needs to be allocated. |
| 107 // Arg1: type arguments of the object that needs to be allocated. | 107 // Arg1: type arguments of the object that needs to be allocated. |
| 108 // Arg2: type arguments of the instantiator or kNoInstantiator. | 108 // Arg2: type arguments of the instantiator or kNoInstantiator. |
| 109 // Return value: newly allocated object. | 109 // Return value: newly allocated object. |
| 110 DEFINE_RUNTIME_ENTRY(AllocateObject, 3) { | 110 DEFINE_RUNTIME_ENTRY(AllocateObject, 3) { |
| 111 const Class& cls = Class::CheckedHandle(arguments.ArgAt(0)); | 111 const Class& cls = Class::CheckedHandle(arguments.ArgAt(0)); |
| 112 const Instance& instance = Instance::Handle(Instance::New(cls)); | 112 const Instance& instance = Instance::Handle(Instance::New(cls)); |
| 113 arguments.SetReturn(instance); | 113 arguments.SetReturn(instance); |
| 114 if (!cls.HasTypeArguments()) { | 114 if (cls.NumTypeArguments() == 0) { |
| 115 // No type arguments required for a non-parameterized type. | 115 // No type arguments required for a non-parameterized type. |
| 116 ASSERT(Instance::CheckedHandle(arguments.ArgAt(1)).IsNull()); | 116 ASSERT(Instance::CheckedHandle(arguments.ArgAt(1)).IsNull()); |
| 117 return; | 117 return; |
| 118 } | 118 } |
| 119 AbstractTypeArguments& type_arguments = | 119 AbstractTypeArguments& type_arguments = |
| 120 AbstractTypeArguments::CheckedHandle(arguments.ArgAt(1)); | 120 AbstractTypeArguments::CheckedHandle(arguments.ArgAt(1)); |
| 121 // If no instantiator is provided, set the type arguments and return. | 121 // If no instantiator is provided, set the type arguments and return. |
| 122 if (Object::Handle(arguments.ArgAt(2)).IsSmi()) { | 122 if (Object::Handle(arguments.ArgAt(2)).IsSmi()) { |
| 123 ASSERT(Smi::CheckedHandle(arguments.ArgAt(2)).Value() == | 123 ASSERT(Smi::CheckedHandle(arguments.ArgAt(2)).Value() == |
| 124 StubCode::kNoInstantiator); | 124 StubCode::kNoInstantiator); |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 158 // arguments are within the declared bounds or throw a dynamic type error. | 158 // arguments are within the declared bounds or throw a dynamic type error. |
| 159 // Arg0: class of the object that needs to be allocated. | 159 // Arg0: class of the object that needs to be allocated. |
| 160 // Arg1: type arguments of the object that needs to be allocated. | 160 // Arg1: type arguments of the object that needs to be allocated. |
| 161 // Arg2: type arguments of the instantiator or kNoInstantiator. | 161 // Arg2: type arguments of the instantiator or kNoInstantiator. |
| 162 // Return value: newly allocated object. | 162 // Return value: newly allocated object. |
| 163 DEFINE_RUNTIME_ENTRY(AllocateObjectWithBoundsCheck, 3) { | 163 DEFINE_RUNTIME_ENTRY(AllocateObjectWithBoundsCheck, 3) { |
| 164 ASSERT(FLAG_enable_type_checks); | 164 ASSERT(FLAG_enable_type_checks); |
| 165 const Class& cls = Class::CheckedHandle(arguments.ArgAt(0)); | 165 const Class& cls = Class::CheckedHandle(arguments.ArgAt(0)); |
| 166 const Instance& instance = Instance::Handle(Instance::New(cls)); | 166 const Instance& instance = Instance::Handle(Instance::New(cls)); |
| 167 arguments.SetReturn(instance); | 167 arguments.SetReturn(instance); |
| 168 ASSERT(cls.HasTypeArguments()); | 168 ASSERT(cls.NumTypeArguments() > 0); |
| 169 AbstractTypeArguments& type_arguments = | 169 AbstractTypeArguments& type_arguments = |
| 170 AbstractTypeArguments::CheckedHandle(arguments.ArgAt(1)); | 170 AbstractTypeArguments::CheckedHandle(arguments.ArgAt(1)); |
| 171 if (Object::Handle(arguments.ArgAt(2)).IsSmi()) { | 171 if (Object::Handle(arguments.ArgAt(2)).IsSmi()) { |
| 172 ASSERT(Smi::CheckedHandle(arguments.ArgAt(2)).Value() == | 172 ASSERT(Smi::CheckedHandle(arguments.ArgAt(2)).Value() == |
| 173 StubCode::kNoInstantiator); | 173 StubCode::kNoInstantiator); |
| 174 // Unless null (for a raw type), the type argument vector may be longer than | 174 // Unless null (for a raw type), the type argument vector may be longer than |
| 175 // necessary due to a type optimization reusing the type argument vector of | 175 // necessary due to a type optimization reusing the type argument vector of |
| 176 // the instantiator. | 176 // the instantiator. |
| 177 ASSERT(type_arguments.IsNull() || | 177 ASSERT(type_arguments.IsNull() || |
| 178 (type_arguments.IsInstantiated() && | 178 (type_arguments.IsInstantiated() && |
| (...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 365 OS::PrintErr(" -> Function %s\n", function.ToFullyQualifiedCString()); | 365 OS::PrintErr(" -> Function %s\n", function.ToFullyQualifiedCString()); |
| 366 } | 366 } |
| 367 | 367 |
| 368 | 368 |
| 369 // Converts InstantiatedTypeArguments to TypeArguments and stores it | 369 // Converts InstantiatedTypeArguments to TypeArguments and stores it |
| 370 // into the instance. The assembly code can handle only type arguments of | 370 // into the instance. The assembly code can handle only type arguments of |
| 371 // class TypeArguments. Because of the overhead, do it only when needed. | 371 // class TypeArguments. Because of the overhead, do it only when needed. |
| 372 // Return true if type arguments have been replaced, false otherwise. | 372 // Return true if type arguments have been replaced, false otherwise. |
| 373 static bool OptimizeTypeArguments(const Instance& instance) { | 373 static bool OptimizeTypeArguments(const Instance& instance) { |
| 374 const Class& type_class = Class::ZoneHandle(instance.clazz()); | 374 const Class& type_class = Class::ZoneHandle(instance.clazz()); |
| 375 if (!type_class.HasTypeArguments()) { | 375 if (type_class.NumTypeArguments() == 0) { |
| 376 return false; | 376 return false; |
| 377 } | 377 } |
| 378 AbstractTypeArguments& type_arguments = | 378 AbstractTypeArguments& type_arguments = |
| 379 AbstractTypeArguments::Handle(instance.GetTypeArguments()); | 379 AbstractTypeArguments::Handle(instance.GetTypeArguments()); |
| 380 if (type_arguments.IsNull()) { | 380 if (type_arguments.IsNull()) { |
| 381 return false; | 381 return false; |
| 382 } | 382 } |
| 383 bool replaced = false; | 383 bool replaced = false; |
| 384 if (type_arguments.IsInstantiatedTypeArguments()) { | 384 if (type_arguments.IsInstantiatedTypeArguments()) { |
| 385 AbstractTypeArguments& uninstantiated = AbstractTypeArguments::Handle(); | 385 AbstractTypeArguments& uninstantiated = AbstractTypeArguments::Handle(); |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 431 if (new_cache.IsNull()) return; | 431 if (new_cache.IsNull()) return; |
| 432 // Instantiator type arguments may be canonicalized later. | 432 // Instantiator type arguments may be canonicalized later. |
| 433 AbstractTypeArguments& instantiator_type_arguments = | 433 AbstractTypeArguments& instantiator_type_arguments = |
| 434 AbstractTypeArguments::Handle(incoming_instantiator_type_arguments.raw()); | 434 AbstractTypeArguments::Handle(incoming_instantiator_type_arguments.raw()); |
| 435 AbstractTypeArguments& instance_type_arguments = | 435 AbstractTypeArguments& instance_type_arguments = |
| 436 AbstractTypeArguments::Handle(); | 436 AbstractTypeArguments::Handle(); |
| 437 const Class& instance_class = Class::Handle(instance.clazz()); | 437 const Class& instance_class = Class::Handle(instance.clazz()); |
| 438 | 438 |
| 439 // Canonicalize type arguments. | 439 // Canonicalize type arguments. |
| 440 bool type_arguments_replaced = false; | 440 bool type_arguments_replaced = false; |
| 441 if (instance_class.HasTypeArguments()) { | 441 if (instance_class.NumTypeArguments() > 0) { |
| 442 // Canonicalize type arguments. | 442 // Canonicalize type arguments. |
| 443 type_arguments_replaced = OptimizeTypeArguments(instance); | 443 type_arguments_replaced = OptimizeTypeArguments(instance); |
| 444 instance_type_arguments = instance.GetTypeArguments(); | 444 instance_type_arguments = instance.GetTypeArguments(); |
| 445 } | 445 } |
| 446 if (!instantiator.IsNull()) { | 446 if (!instantiator.IsNull()) { |
| 447 if (OptimizeTypeArguments(instantiator)) { | 447 if (OptimizeTypeArguments(instantiator)) { |
| 448 type_arguments_replaced = true; | 448 type_arguments_replaced = true; |
| 449 } | 449 } |
| 450 instantiator_type_arguments = instantiator.GetTypeArguments(); | 450 instantiator_type_arguments = instantiator.GetTypeArguments(); |
| 451 } | 451 } |
| (...skipping 1250 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1702 field.UpdateCid(cid); | 1702 field.UpdateCid(cid); |
| 1703 intptr_t list_length = Field::kNoFixedLength; | 1703 intptr_t list_length = Field::kNoFixedLength; |
| 1704 if ((field.guarded_cid() != kDynamicCid) && | 1704 if ((field.guarded_cid() != kDynamicCid) && |
| 1705 field.is_final() && RawObject::IsBuiltinListClassId(cid)) { | 1705 field.is_final() && RawObject::IsBuiltinListClassId(cid)) { |
| 1706 list_length = GetListLength(value); | 1706 list_length = GetListLength(value); |
| 1707 } | 1707 } |
| 1708 field.UpdateLength(list_length); | 1708 field.UpdateLength(list_length); |
| 1709 } | 1709 } |
| 1710 | 1710 |
| 1711 } // namespace dart | 1711 } // namespace dart |
| OLD | NEW |