| 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/class_finalizer.h" | 5 #include "vm/class_finalizer.h" |
| 6 | 6 |
| 7 #include "vm/code_generator.h" | 7 #include "vm/code_generator.h" |
| 8 #include "vm/flags.h" | 8 #include "vm/flags.h" |
| 9 #include "vm/hash_table.h" | 9 #include "vm/hash_table.h" |
| 10 #include "vm/heap.h" | 10 #include "vm/heap.h" |
| (...skipping 442 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 453 // of the redirection chain. | 453 // of the redirection chain. |
| 454 ResolveRedirectingFactoryTarget(target_class, target, visited_factories); | 454 ResolveRedirectingFactoryTarget(target_class, target, visited_factories); |
| 455 Type& target_type = Type::Handle(target.RedirectionType()); | 455 Type& target_type = Type::Handle(target.RedirectionType()); |
| 456 Function& target_target = Function::Handle(target.RedirectionTarget()); | 456 Function& target_target = Function::Handle(target.RedirectionTarget()); |
| 457 if (target_target.IsNull()) { | 457 if (target_target.IsNull()) { |
| 458 ASSERT(target_type.IsMalformed()); | 458 ASSERT(target_type.IsMalformed()); |
| 459 } else { | 459 } else { |
| 460 // If the target type refers to type parameters, substitute them with the | 460 // If the target type refers to type parameters, substitute them with the |
| 461 // type arguments of the redirection type. | 461 // type arguments of the redirection type. |
| 462 if (!target_type.IsInstantiated()) { | 462 if (!target_type.IsInstantiated()) { |
| 463 // We do not support generic constructors. |
| 464 ASSERT(target_type.IsInstantiated(kFunctions)); |
| 463 const TypeArguments& type_args = TypeArguments::Handle(type.arguments()); | 465 const TypeArguments& type_args = TypeArguments::Handle(type.arguments()); |
| 464 Error& bound_error = Error::Handle(); | 466 Error& bound_error = Error::Handle(); |
| 465 target_type ^= target_type.InstantiateFrom(type_args, &bound_error, NULL, | 467 target_type ^= |
| 466 NULL, Heap::kOld); | 468 target_type.InstantiateFrom(type_args, Object::null_type_arguments(), |
| 469 &bound_error, NULL, NULL, Heap::kOld); |
| 467 if (bound_error.IsNull()) { | 470 if (bound_error.IsNull()) { |
| 468 target_type ^= FinalizeType(cls, target_type); | 471 target_type ^= FinalizeType(cls, target_type); |
| 469 } else { | 472 } else { |
| 470 ASSERT(target_type.IsInstantiated() && type_args.IsInstantiated()); | 473 ASSERT(target_type.IsInstantiated() && type_args.IsInstantiated()); |
| 471 const Script& script = Script::Handle(target_class.script()); | 474 const Script& script = Script::Handle(target_class.script()); |
| 472 FinalizeMalformedType(bound_error, script, target_type, | 475 FinalizeMalformedType(bound_error, script, target_type, |
| 473 "cannot resolve redirecting factory"); | 476 "cannot resolve redirecting factory"); |
| 474 target_target = Function::null(); | 477 target_target = Function::null(); |
| 475 } | 478 } |
| 476 } | 479 } |
| (...skipping 457 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 934 // While finalizing D<T>, the super type arg D<T> (a typeref) gets | 937 // While finalizing D<T>, the super type arg D<T> (a typeref) gets |
| 935 // instantiated from vector [T], yielding itself. | 938 // instantiated from vector [T], yielding itself. |
| 936 // | 939 // |
| 937 if (super_type_arg.IsTypeRef() && super_type_arg.IsBeingFinalized() && | 940 if (super_type_arg.IsTypeRef() && super_type_arg.IsBeingFinalized() && |
| 938 (super_type_arg.arguments() == arguments.raw())) { | 941 (super_type_arg.arguments() == arguments.raw())) { |
| 939 arguments.SetTypeAt(i, super_type_arg); | 942 arguments.SetTypeAt(i, super_type_arg); |
| 940 continue; | 943 continue; |
| 941 } | 944 } |
| 942 Error& error = Error::Handle(); | 945 Error& error = Error::Handle(); |
| 943 super_type_arg = super_type_arg.InstantiateFrom( | 946 super_type_arg = super_type_arg.InstantiateFrom( |
| 944 arguments, &error, instantiation_trail, NULL, Heap::kOld); | 947 arguments, Object::null_type_arguments(), &error, |
| 948 instantiation_trail, NULL, Heap::kOld); |
| 945 if (!error.IsNull()) { | 949 if (!error.IsNull()) { |
| 946 // InstantiateFrom does not report an error if the type is still | 950 // InstantiateFrom does not report an error if the type is still |
| 947 // uninstantiated. Instead, it will return a new BoundedType so | 951 // uninstantiated. Instead, it will return a new BoundedType so |
| 948 // that the check is postponed to run time. | 952 // that the check is postponed to run time. |
| 949 ASSERT(super_type_arg.IsInstantiated()); | 953 ASSERT(super_type_arg.IsInstantiated()); |
| 950 // Keep only the first bound error. | 954 // Keep only the first bound error. |
| 951 if (bound_error->IsNull()) { | 955 if (bound_error->IsNull()) { |
| 952 *bound_error = error.raw(); | 956 *bound_error = error.raw(); |
| 953 } | 957 } |
| 954 } | 958 } |
| (...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1031 type_param.set_bound(declared_bound); | 1035 type_param.set_bound(declared_bound); |
| 1032 } | 1036 } |
| 1033 ASSERT(declared_bound.IsFinalized() || declared_bound.IsBeingFinalized()); | 1037 ASSERT(declared_bound.IsFinalized() || declared_bound.IsBeingFinalized()); |
| 1034 Error& error = Error::Handle(); | 1038 Error& error = Error::Handle(); |
| 1035 // Note that the bound may be malformed, in which case the bound check | 1039 // Note that the bound may be malformed, in which case the bound check |
| 1036 // will return an error and the bound check will be postponed to run time. | 1040 // will return an error and the bound check will be postponed to run time. |
| 1037 if (declared_bound.IsInstantiated()) { | 1041 if (declared_bound.IsInstantiated()) { |
| 1038 instantiated_bound = declared_bound.raw(); | 1042 instantiated_bound = declared_bound.raw(); |
| 1039 } else { | 1043 } else { |
| 1040 instantiated_bound = declared_bound.InstantiateFrom( | 1044 instantiated_bound = declared_bound.InstantiateFrom( |
| 1041 arguments, &error, NULL, NULL, Heap::kOld); | 1045 arguments, Object::null_type_arguments(), &error, NULL, NULL, |
| 1046 Heap::kOld); |
| 1042 } | 1047 } |
| 1043 if (!instantiated_bound.IsFinalized()) { | 1048 if (!instantiated_bound.IsFinalized()) { |
| 1044 // The bound refers to type parameters, creating a cycle; postpone | 1049 // The bound refers to type parameters, creating a cycle; postpone |
| 1045 // bound check to run time, when the bound will be finalized. | 1050 // bound check to run time, when the bound will be finalized. |
| 1046 // The bound may not necessarily be 'IsBeingFinalized' yet, as is the | 1051 // The bound may not necessarily be 'IsBeingFinalized' yet, as is the |
| 1047 // case with a pair of type parameters of the same class referring to | 1052 // case with a pair of type parameters of the same class referring to |
| 1048 // each other via their bounds. | 1053 // each other via their bounds. |
| 1049 type_arg = BoundedType::New(type_arg, instantiated_bound, type_param); | 1054 type_arg = BoundedType::New(type_arg, instantiated_bound, type_param); |
| 1050 arguments.SetTypeAt(offset + i, type_arg); | 1055 arguments.SetTypeAt(offset + i, type_arg); |
| 1051 continue; | 1056 continue; |
| (...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1247 const Type& fun_type = Type::Cast(type); | 1252 const Type& fun_type = Type::Cast(type); |
| 1248 const Class& scope_class = Class::Handle(zone, fun_type.type_class()); | 1253 const Class& scope_class = Class::Handle(zone, fun_type.type_class()); |
| 1249 if (scope_class.IsTypedefClass()) { | 1254 if (scope_class.IsTypedefClass()) { |
| 1250 Function& signature = | 1255 Function& signature = |
| 1251 Function::Handle(zone, scope_class.signature_function()); | 1256 Function::Handle(zone, scope_class.signature_function()); |
| 1252 if (!scope_class.is_type_finalized()) { | 1257 if (!scope_class.is_type_finalized()) { |
| 1253 FinalizeSignature(scope_class, signature); | 1258 FinalizeSignature(scope_class, signature); |
| 1254 } | 1259 } |
| 1255 // If the function type is a generic typedef, instantiate its signature | 1260 // If the function type is a generic typedef, instantiate its signature |
| 1256 // from its type arguments. | 1261 // from its type arguments. |
| 1257 // Example: typedef T F<T>(T x) has uninstantiated signature (T x) => T. | 1262 // Example: typedef F<T> = S Function<S>(T x) has uninstantiated |
| 1258 // The instantiated signature of F(int) becomes (int x) => int. | 1263 // signature (T x) => S. |
| 1264 // The instantiated signature of F(int) becomes (int x) => S. |
| 1259 // Note that after this step, the signature of the function type is not | 1265 // Note that after this step, the signature of the function type is not |
| 1260 // identical to the canonical signature of the typedef class anymore. | 1266 // identical to the canonical signature of the typedef class anymore. |
| 1261 if (scope_class.IsGeneric() && !signature.HasInstantiatedSignature()) { | 1267 if (scope_class.IsGeneric() && !signature.HasInstantiatedSignature()) { |
| 1262 const TypeArguments& type_args = | |
| 1263 TypeArguments::Handle(zone, fun_type.arguments()); | |
| 1264 if (FLAG_trace_type_finalization) { | 1268 if (FLAG_trace_type_finalization) { |
| 1265 THR_Print("Instantiating signature '%s' of typedef '%s'\n", | 1269 THR_Print("Instantiating signature '%s' of typedef '%s'\n", |
| 1266 String::Handle(zone, signature.Signature()).ToCString(), | 1270 String::Handle(zone, signature.Signature()).ToCString(), |
| 1267 String::Handle(zone, fun_type.Name()).ToCString()); | 1271 String::Handle(zone, fun_type.Name()).ToCString()); |
| 1268 } | 1272 } |
| 1269 signature = signature.InstantiateSignatureFrom(type_args, Heap::kOld); | 1273 const TypeArguments& instantiator_type_arguments = |
| 1270 // Note that if type_args contains type parameters, signature is still | 1274 TypeArguments::Handle(zone, fun_type.arguments()); |
| 1271 // uninstantiated here (typedef type parameters were substituted in the | 1275 const TypeArguments& function_type_arguments = |
| 1272 // signature with typedef type arguments). | 1276 TypeArguments::Handle(zone, signature.type_parameters()); |
| 1277 signature = signature.InstantiateSignatureFrom( |
| 1278 instantiator_type_arguments, function_type_arguments, Heap::kOld); |
| 1279 // Note that if instantiator_type_arguments contains type parameters, |
| 1280 // as in F<K>, the signature is still uninstantiated (the typedef type |
| 1281 // parameters were substituted in the signature with typedef type |
| 1282 // arguments). Note also that the function type parameters were not |
| 1283 // modified. |
| 1273 } | 1284 } |
| 1274 fun_type.set_signature(signature); | 1285 fun_type.set_signature(signature); |
| 1275 // The type was already marked as finalized and uninstantiated in | 1286 // The type was already marked as finalized and uninstantiated in |
| 1276 // ExpandAndFinalizeTypeArguments above when its signature was not | 1287 // ExpandAndFinalizeTypeArguments above when its signature was not |
| 1277 // instantiated yet. Check again by calling ResetIsFinalized(). | 1288 // instantiated yet. Check again by calling ResetIsFinalized(). |
| 1278 fun_type.ResetIsFinalized(); | 1289 fun_type.ResetIsFinalized(); |
| 1279 } else { | 1290 } else { |
| 1280 const Function& signature = Function::Handle(zone, fun_type.signature()); | 1291 const Function& signature = Function::Handle(zone, fun_type.signature()); |
| 1281 FinalizeSignature(cls, signature); | 1292 FinalizeSignature(cls, signature); |
| 1282 } | 1293 } |
| (...skipping 265 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1548 Error& error = Error::Handle(zone); | 1559 Error& error = Error::Handle(zone); |
| 1549 if (type.IsMalformedOrMalbounded()) { | 1560 if (type.IsMalformedOrMalbounded()) { |
| 1550 error = type.error(); | 1561 error = type.error(); |
| 1551 } else { | 1562 } else { |
| 1552 ASSERT(type.IsInstantiated()); | 1563 ASSERT(type.IsInstantiated()); |
| 1553 } | 1564 } |
| 1554 const Instance& const_value = Instance::Handle(zone, field.StaticValue()); | 1565 const Instance& const_value = Instance::Handle(zone, field.StaticValue()); |
| 1555 if (!error.IsNull() || | 1566 if (!error.IsNull() || |
| 1556 (!type.IsDynamicType() && | 1567 (!type.IsDynamicType() && |
| 1557 !const_value.IsInstanceOf(type, Object::null_type_arguments(), | 1568 !const_value.IsInstanceOf(type, Object::null_type_arguments(), |
| 1558 &error))) { | 1569 Object::null_type_arguments(), &error))) { |
| 1559 if (Isolate::Current()->error_on_bad_type()) { | 1570 if (Isolate::Current()->error_on_bad_type()) { |
| 1560 const AbstractType& const_value_type = | 1571 const AbstractType& const_value_type = |
| 1561 AbstractType::Handle(zone, const_value.GetType(Heap::kNew)); | 1572 AbstractType::Handle(zone, const_value.GetType(Heap::kNew)); |
| 1562 const String& const_value_type_name = | 1573 const String& const_value_type_name = |
| 1563 String::Handle(zone, const_value_type.UserVisibleName()); | 1574 String::Handle(zone, const_value_type.UserVisibleName()); |
| 1564 const String& type_name = | 1575 const String& type_name = |
| 1565 String::Handle(zone, type.UserVisibleName()); | 1576 String::Handle(zone, type.UserVisibleName()); |
| 1566 ReportErrors(error, cls, field.token_pos(), | 1577 ReportErrors(error, cls, field.token_pos(), |
| 1567 "error initializing static %s field '%s': " | 1578 "error initializing static %s field '%s': " |
| 1568 "type '%s' is not a subtype of type '%s'", | 1579 "type '%s' is not a subtype of type '%s'", |
| (...skipping 306 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1875 for (intptr_t i = 0; i < num_mixin_type_params; i++) { | 1886 for (intptr_t i = 0; i < num_mixin_type_params; i++) { |
| 1876 param ^= mixin_type_args.TypeAt(i); | 1887 param ^= mixin_type_args.TypeAt(i); |
| 1877 param_bound = param.bound(); | 1888 param_bound = param.bound(); |
| 1878 if (!param_bound.IsInstantiated()) { | 1889 if (!param_bound.IsInstantiated()) { |
| 1879 // Make sure the bound is finalized before instantiating it. | 1890 // Make sure the bound is finalized before instantiating it. |
| 1880 if (!param_bound.IsFinalized() && !param_bound.IsBeingFinalized()) { | 1891 if (!param_bound.IsFinalized() && !param_bound.IsBeingFinalized()) { |
| 1881 param_bound = FinalizeType(mixin_app_class, param_bound); | 1892 param_bound = FinalizeType(mixin_app_class, param_bound); |
| 1882 param.set_bound(param_bound); // In case part of recursive type. | 1893 param.set_bound(param_bound); // In case part of recursive type. |
| 1883 } | 1894 } |
| 1884 param_bound = param_bound.InstantiateFrom( | 1895 param_bound = param_bound.InstantiateFrom( |
| 1885 instantiator, &bound_error, NULL, NULL, Heap::kOld); | 1896 instantiator, Object::null_type_arguments(), &bound_error, NULL, |
| 1897 NULL, Heap::kOld); |
| 1886 // The instantiator contains only TypeParameter objects and no | 1898 // The instantiator contains only TypeParameter objects and no |
| 1887 // BoundedType objects, so no bound error may occur. | 1899 // BoundedType objects, so no bound error may occur. |
| 1888 ASSERT(!param_bound.IsBoundedType()); | 1900 ASSERT(!param_bound.IsBoundedType()); |
| 1889 ASSERT(bound_error.IsNull()); | 1901 ASSERT(bound_error.IsNull()); |
| 1890 ASSERT(!param_bound.IsInstantiated()); | 1902 ASSERT(!param_bound.IsInstantiated()); |
| 1891 param.set_bound(param_bound); | 1903 param.set_bound(param_bound); |
| 1892 } | 1904 } |
| 1893 } | 1905 } |
| 1894 } | 1906 } |
| 1895 | 1907 |
| (...skipping 214 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2110 mixin_class_super_type_args.Length() - num_aliased_mixin_type_params; | 2122 mixin_class_super_type_args.Length() - num_aliased_mixin_type_params; |
| 2111 for (intptr_t i = 0; i < num_aliased_mixin_type_params; i++) { | 2123 for (intptr_t i = 0; i < num_aliased_mixin_type_params; i++) { |
| 2112 type = mixin_class_super_type_args.TypeAt(offset + i); | 2124 type = mixin_class_super_type_args.TypeAt(offset + i); |
| 2113 if (!type.IsInstantiated()) { | 2125 if (!type.IsInstantiated()) { |
| 2114 // In the presence of bounds, the bounded type and the upper bound must | 2126 // In the presence of bounds, the bounded type and the upper bound must |
| 2115 // be instantiated separately. Instantiating a BoundedType would wrap | 2127 // be instantiated separately. Instantiating a BoundedType would wrap |
| 2116 // the BoundedType in another BoundedType. | 2128 // the BoundedType in another BoundedType. |
| 2117 if (type.IsBoundedType()) { | 2129 if (type.IsBoundedType()) { |
| 2118 bounded_type = BoundedType::Cast(type).type(); | 2130 bounded_type = BoundedType::Cast(type).type(); |
| 2119 bounded_type = bounded_type.InstantiateFrom( | 2131 bounded_type = bounded_type.InstantiateFrom( |
| 2120 instantiator, &bound_error, NULL, NULL, Heap::kOld); | 2132 instantiator, Object::null_type_arguments(), &bound_error, NULL, |
| 2133 NULL, Heap::kOld); |
| 2121 // The instantiator contains only TypeParameter objects and no | 2134 // The instantiator contains only TypeParameter objects and no |
| 2122 // BoundedType objects, so no bound error may occur. | 2135 // BoundedType objects, so no bound error may occur. |
| 2123 ASSERT(bound_error.IsNull()); | 2136 ASSERT(bound_error.IsNull()); |
| 2124 upper_bound = BoundedType::Cast(type).bound(); | 2137 upper_bound = BoundedType::Cast(type).bound(); |
| 2125 upper_bound = upper_bound.InstantiateFrom(instantiator, &bound_error, | 2138 upper_bound = upper_bound.InstantiateFrom( |
| 2126 NULL, NULL, Heap::kOld); | 2139 instantiator, Object::null_type_arguments(), &bound_error, NULL, |
| 2140 NULL, Heap::kOld); |
| 2127 ASSERT(bound_error.IsNull()); | 2141 ASSERT(bound_error.IsNull()); |
| 2128 type_parameter = BoundedType::Cast(type).type_parameter(); | 2142 type_parameter = BoundedType::Cast(type).type_parameter(); |
| 2129 // The type parameter that declared the bound does not change. | 2143 // The type parameter that declared the bound does not change. |
| 2130 type = BoundedType::New(bounded_type, upper_bound, type_parameter); | 2144 type = BoundedType::New(bounded_type, upper_bound, type_parameter); |
| 2131 } else { | 2145 } else { |
| 2132 type = type.InstantiateFrom(instantiator, &bound_error, NULL, NULL, | 2146 type = |
| 2133 Heap::kOld); | 2147 type.InstantiateFrom(instantiator, Object::null_type_arguments(), |
| 2148 &bound_error, NULL, NULL, Heap::kOld); |
| 2134 ASSERT(bound_error.IsNull()); | 2149 ASSERT(bound_error.IsNull()); |
| 2135 } | 2150 } |
| 2136 } | 2151 } |
| 2137 new_mixin_type_args.SetTypeAt(i, type); | 2152 new_mixin_type_args.SetTypeAt(i, type); |
| 2138 } | 2153 } |
| 2139 } | 2154 } |
| 2140 TypeArguments& new_super_type_args = TypeArguments::Handle(zone); | 2155 TypeArguments& new_super_type_args = TypeArguments::Handle(zone); |
| 2141 if ((num_super_type_params + num_aliased_mixin_type_params) > 0) { | 2156 if ((num_super_type_params + num_aliased_mixin_type_params) > 0) { |
| 2142 new_super_type_args = TypeArguments::New(num_super_type_params + | 2157 new_super_type_args = TypeArguments::New(num_super_type_params + |
| 2143 num_aliased_mixin_type_params); | 2158 num_aliased_mixin_type_params); |
| (...skipping 1609 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3753 ProgramVisitor::VisitFunctions(&function_visitor); | 3768 ProgramVisitor::VisitFunctions(&function_visitor); |
| 3754 | 3769 |
| 3755 class ClearCodeClassVisitor : public ClassVisitor { | 3770 class ClearCodeClassVisitor : public ClassVisitor { |
| 3756 void Visit(const Class& cls) { cls.DisableAllocationStub(); } | 3771 void Visit(const Class& cls) { cls.DisableAllocationStub(); } |
| 3757 }; | 3772 }; |
| 3758 ClearCodeClassVisitor class_visitor; | 3773 ClearCodeClassVisitor class_visitor; |
| 3759 ProgramVisitor::VisitClasses(&class_visitor); | 3774 ProgramVisitor::VisitClasses(&class_visitor); |
| 3760 } | 3775 } |
| 3761 | 3776 |
| 3762 } // namespace dart | 3777 } // namespace dart |
| OLD | NEW |