Flutter Engine
The Flutter Engine
object.cc
Go to the documentation of this 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
3// BSD-style license that can be found in the LICENSE file.
4
6
8#include "vm/code_patcher.h"
9#include "vm/dart_entry.h"
10#include "vm/exceptions.h"
11#include "vm/heap/heap.h"
12#include "vm/native_entry.h"
13#include "vm/object.h"
14#include "vm/object_store.h"
15#include "vm/resolver.h"
16#include "vm/stack_frame.h"
17#include "vm/symbols.h"
18
19namespace dart {
20
21DEFINE_NATIVE_ENTRY(DartAsync_fatal, 0, 1) {
22 // The dart:async library code entered an unrecoverable state.
23 const Instance& instance =
24 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
25 const char* msg = instance.ToCString();
26 OS::PrintErr("Fatal error in dart:async: %s\n", msg);
27 FATAL("%s", msg);
28 return Object::null();
29}
30
31DEFINE_NATIVE_ENTRY(Object_equals, 0, 1) {
32 // Implemented in the flow graph builder.
34 return Object::null();
35}
36
37static intptr_t GetHash(Isolate* isolate, const ObjectPtr obj) {
38#if defined(HASH_IN_OBJECT_HEADER)
39 return Object::GetCachedHash(obj);
40#else
41 Heap* heap = isolate->group()->heap();
42 ASSERT(obj->IsDartInstance());
43 return heap->GetHash(obj);
44#endif
45}
46
47DEFINE_NATIVE_ENTRY(Object_getHash, 0, 1) {
48 // Please note that no handle is created for the argument.
49 // This is safe since the argument is only used in a tail call.
50 // The performance benefit is more than 5% when using hashCode.
51 intptr_t hash = GetHash(isolate, arguments->NativeArgAt(0));
52 if (LIKELY(hash != 0)) {
53 return Smi::New(hash);
54 }
55
56 const Instance& instance =
57 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
58 return instance.IdentityHashCode(arguments->thread());
59}
60
61DEFINE_NATIVE_ENTRY(Object_toString, 0, 1) {
62 const Instance& instance =
63 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
64 if (instance.IsString()) {
65 return instance.ptr();
66 }
67 if (instance.IsAbstractType()) {
68 return AbstractType::Cast(instance).UserVisibleName();
69 }
70 const char* c_str = instance.ToCString();
71 return String::New(c_str);
72}
73
74DEFINE_NATIVE_ENTRY(Object_runtimeType, 0, 1) {
75 const Instance& instance =
76 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
77 if (instance.IsString()) {
78 return Type::StringType();
79 } else if (instance.IsInteger()) {
80 return Type::IntType();
81 } else if (instance.IsDouble()) {
82 return Type::Double();
83 } else if (instance.IsAbstractType()) {
84 return Type::DartTypeType();
85 } else if (IsArrayClassId(instance.GetClassId())) {
86 const auto& cls = Class::Handle(
87 zone, thread->isolate_group()->object_store()->list_class());
88 auto& type_arguments =
89 TypeArguments::Handle(zone, instance.GetTypeArguments());
90 type_arguments = type_arguments.FromInstanceTypeArguments(thread, cls);
91 const auto& type = Type::Handle(
92 zone,
93 Type::New(cls, type_arguments, Nullability::kNonNullable, Heap::kNew));
94 type.SetIsFinalized();
95 return type.Canonicalize(thread);
96 }
97
98 return instance.GetType(Heap::kNew);
99}
100
102 const Instance& left,
103 const Instance& right) {
104 const intptr_t left_cid = left.GetClassId();
105 const intptr_t right_cid = right.GetClassId();
106
107 if (left_cid != right_cid) {
108 if (IsIntegerClassId(left_cid)) {
109 return IsIntegerClassId(right_cid);
110 } else if (IsStringClassId(left_cid)) {
111 return IsStringClassId(right_cid);
112 } else if (IsTypeClassId(left_cid)) {
113 return IsTypeClassId(right_cid);
114 } else if (IsArrayClassId(left_cid)) {
115 if (!IsArrayClassId(right_cid)) {
116 return false;
117 }
118 // Still need to check type arguments.
119 } else {
120 return false;
121 }
122 }
123
124 if (left_cid == kClosureCid) {
125 const auto& left_closure = Closure::Cast(left);
126 const auto& right_closure = Closure::Cast(right);
127 // If all the components that make up the instantiated signature are equal,
128 // then no need to instantiate.
129 if (left_closure.function_type_arguments() ==
130 right_closure.function_type_arguments() &&
131 left_closure.delayed_type_arguments() ==
132 right_closure.delayed_type_arguments() &&
133 left_closure.instantiator_type_arguments() ==
134 right_closure.instantiator_type_arguments()) {
135 const auto& left_fun = Function::Handle(zone, left_closure.function());
136 const auto& right_fun = Function::Handle(zone, right_closure.function());
137 if (left_fun.signature() == right_fun.signature()) {
138 return true;
139 }
140 }
141 const AbstractType& left_type =
142 AbstractType::Handle(zone, left.GetType(Heap::kNew));
143 const AbstractType& right_type =
144 AbstractType::Handle(zone, right.GetType(Heap::kNew));
145 return left_type.IsEquivalent(right_type, TypeEquality::kSyntactical);
146 }
147
148 if (left_cid == kRecordCid) {
149 const auto& left_record = Record::Cast(left);
150 const auto& right_record = Record::Cast(right);
151 if (left_record.shape() != right_record.shape()) {
152 return false;
153 }
154 Instance& left_field = Instance::Handle(zone);
155 Instance& right_field = Instance::Handle(zone);
156 const intptr_t num_fields = left_record.num_fields();
157 for (intptr_t i = 0; i < num_fields; ++i) {
158 left_field ^= left_record.FieldAt(i);
159 right_field ^= right_record.FieldAt(i);
160 if (!HaveSameRuntimeTypeHelper(zone, left_field, right_field)) {
161 return false;
162 }
163 }
164 return true;
165 }
166
167 const Class& cls = Class::Handle(zone, left.clazz());
168 if (!cls.IsGeneric()) {
169 return true;
170 }
171
172 if (left.GetTypeArguments() == right.GetTypeArguments()) {
173 return true;
174 }
175 const TypeArguments& left_type_arguments =
176 TypeArguments::Handle(zone, left.GetTypeArguments());
177 const TypeArguments& right_type_arguments =
178 TypeArguments::Handle(zone, right.GetTypeArguments());
179 const intptr_t num_type_args = cls.NumTypeArguments();
180 const intptr_t num_type_params = cls.NumTypeParameters();
181 return left_type_arguments.IsSubvectorEquivalent(
182 right_type_arguments, num_type_args - num_type_params, num_type_params,
184}
185
186DEFINE_NATIVE_ENTRY(Object_haveSameRuntimeType, 0, 2) {
187 const Instance& left =
188 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
189 const Instance& right =
190 Instance::CheckedHandle(zone, arguments->NativeArgAt(1));
191 return Bool::Get(HaveSameRuntimeTypeHelper(zone, left, right)).ptr();
192}
193
194DEFINE_NATIVE_ENTRY(Object_instanceOf, 0, 4) {
195 const Instance& instance =
196 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
197 const TypeArguments& instantiator_type_arguments =
198 TypeArguments::CheckedHandle(zone, arguments->NativeArgAt(1));
199 const TypeArguments& function_type_arguments =
200 TypeArguments::CheckedHandle(zone, arguments->NativeArgAt(2));
201 const AbstractType& type =
202 AbstractType::CheckedHandle(zone, arguments->NativeArgAt(3));
203 ASSERT(type.IsFinalized());
204 const bool is_instance_of = instance.IsInstanceOf(
205 type, instantiator_type_arguments, function_type_arguments);
206 if (FLAG_trace_type_checks) {
207 LogBlock lb;
208 const char* result_str = is_instance_of ? "true" : "false";
209 THR_Print("Native Object.instanceOf: result %s\n", result_str);
210 const AbstractType& instance_type =
212 THR_Print(" instance type: %s\n", instance_type.NameCString());
213 THR_Print(" test type: %s\n", type.NameCString());
214 }
215 return Bool::Get(is_instance_of).ptr();
216}
217
218DEFINE_NATIVE_ENTRY(Object_simpleInstanceOf, 0, 2) {
219 // This native is only called when the right hand side passes
220 // SimpleInstanceOfType and it is a non-negative test.
221 const Instance& instance =
222 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
223 const AbstractType& type =
224 AbstractType::CheckedHandle(zone, arguments->NativeArgAt(1));
225 ASSERT(type.IsFinalized());
226 ASSERT(type.IsInstantiated());
227 const bool is_instance_of = instance.IsInstanceOf(
228 type, Object::null_type_arguments(), Object::null_type_arguments());
229 return Bool::Get(is_instance_of).ptr();
230}
231
232DEFINE_NATIVE_ENTRY(AbstractType_toString, 0, 1) {
233 const AbstractType& type =
234 AbstractType::CheckedHandle(zone, arguments->NativeArgAt(0));
235 return type.UserVisibleName();
236}
237
238DEFINE_NATIVE_ENTRY(AbstractType_getHashCode, 0, 1) {
239 const AbstractType& type =
240 AbstractType::CheckedHandle(zone, arguments->NativeArgAt(0));
241 intptr_t hash_val = type.Hash();
242 ASSERT(hash_val > 0);
243 ASSERT(Smi::IsValid(hash_val));
244 return Smi::New(hash_val);
245}
246
247DEFINE_NATIVE_ENTRY(AbstractType_equality, 0, 2) {
248 const AbstractType& type =
249 AbstractType::CheckedHandle(zone, arguments->NativeArgAt(0));
250 const Instance& other =
251 Instance::CheckedHandle(zone, arguments->NativeArgAt(1));
252 if (type.ptr() == other.ptr()) {
253 return Bool::True().ptr();
254 }
255 return Bool::Get(type.IsEquivalent(other, TypeEquality::kSyntactical)).ptr();
256}
257
258DEFINE_NATIVE_ENTRY(Type_equality, 0, 2) {
259 const Type& type = Type::CheckedHandle(zone, arguments->NativeArgAt(0));
260 const Instance& other =
261 Instance::CheckedHandle(zone, arguments->NativeArgAt(1));
262 if (type.ptr() == other.ptr()) {
263 return Bool::True().ptr();
264 }
265 return Bool::Get(type.IsEquivalent(other, TypeEquality::kSyntactical)).ptr();
266}
267
268DEFINE_NATIVE_ENTRY(LibraryPrefix_isLoaded, 0, 1) {
269 const LibraryPrefix& prefix =
270 LibraryPrefix::CheckedHandle(zone, arguments->NativeArgAt(0));
271 return Bool::Get(isolate->IsPrefixLoaded(prefix)).ptr();
272}
273
274DEFINE_NATIVE_ENTRY(LibraryPrefix_setLoaded, 0, 1) {
275 const LibraryPrefix& prefix =
276 LibraryPrefix::CheckedHandle(zone, arguments->NativeArgAt(0));
277 isolate->SetPrefixIsLoaded(prefix);
278 return Instance::null();
279}
280
281DEFINE_NATIVE_ENTRY(LibraryPrefix_loadingUnit, 0, 1) {
282 const LibraryPrefix& prefix =
283 LibraryPrefix::CheckedHandle(zone, arguments->NativeArgAt(0));
284 const Library& target = Library::Handle(zone, prefix.GetLibrary(0));
285 const LoadingUnit& unit = LoadingUnit::Handle(zone, target.loading_unit());
286 return Smi::New(unit.IsNull() ? LoadingUnit::kIllegalId : unit.id());
287}
288
289DEFINE_NATIVE_ENTRY(LibraryPrefix_issueLoad, 0, 1) {
290 const Smi& id = Smi::CheckedHandle(zone, arguments->NativeArgAt(0));
291 Array& units =
292 Array::Handle(zone, isolate->group()->object_store()->loading_units());
293 if (units.IsNull()) {
294 // Not actually split.
295 const Library& lib = Library::Handle(zone, Library::CoreLibrary());
296 const String& sel = String::Handle(zone, String::New("_completeLoads"));
297 const Function& func =
299 ASSERT(!func.IsNull());
300 const Array& args = Array::Handle(zone, Array::New(3));
301 args.SetAt(0, id);
302 args.SetAt(1, String::Handle(zone));
303 args.SetAt(2, Bool::Get(false));
304 return DartEntry::InvokeFunction(func, args);
305 }
307 LoadingUnit& unit = LoadingUnit::Handle(zone);
308 unit ^= units.At(id.Value());
309 return unit.IssueLoad();
310}
311
312DEFINE_NATIVE_ENTRY(Internal_unsafeCast, 0, 1) {
313 UNREACHABLE(); // Should be erased at Kernel translation time.
314 return arguments->NativeArgAt(0);
315}
316
317DEFINE_NATIVE_ENTRY(Internal_nativeEffect, 0, 1) {
318 UNREACHABLE();
319}
320
321DEFINE_NATIVE_ENTRY(Internal_collectAllGarbage, 0, 0) {
322 isolate->group()->heap()->CollectAllGarbage(GCReason::kDebugging,
323 /*compact=*/true);
324 return Object::null();
325}
326
327DEFINE_NATIVE_ENTRY(Internal_deoptimizeFunctionsOnStack, 0, 0) {
329 return Object::null();
330}
331
332DEFINE_NATIVE_ENTRY(Internal_allocateObjectInstructionsStart, 0, 0) {
333 auto& stub = Code::Handle(
334 zone, isolate->group()->object_store()->allocate_object_stub());
335 ASSERT(!stub.IsUnknownDartCode());
336 // We return the start offset in the isolate instructions instead of the
337 // full address because that fits into small Smis on 32-bit architectures
338 // or compressed pointer builds.
339 const uword instructions_start =
340 reinterpret_cast<uword>(isolate->source()->snapshot_instructions);
341 return Smi::New(stub.PayloadStart() - instructions_start);
342}
343
344DEFINE_NATIVE_ENTRY(Internal_allocateObjectInstructionsEnd, 0, 0) {
345 auto& stub = Code::Handle(
346 zone, isolate->group()->object_store()->allocate_object_stub());
347 ASSERT(!stub.IsUnknownDartCode());
348 // We return the end offset in the isolate instructions instead of the
349 // full address because that fits into small Smis on 32-bit architectures
350 // or compressed pointer builds.
351 const uword instructions_start =
352 reinterpret_cast<uword>(isolate->source()->snapshot_instructions);
353 return Smi::New((stub.PayloadStart() - instructions_start) + stub.Size());
354}
355
357 const Class& instance_cls,
358 const TypeArguments& instance_type_args,
359 const Class& interface_cls,
360 TypeArguments* interface_type_args) {
361 Thread* thread = Thread::Current();
362 Class& cur_cls = Class::Handle(zone, instance_cls.ptr());
363 // The following code is a specialization of Class::IsSubtypeOf().
364 Array& interfaces = Array::Handle(zone);
365 Type& interface = Type::Handle(zone);
366 Class& cur_interface_cls = Class::Handle(zone);
367 TypeArguments& cur_interface_type_args = TypeArguments::Handle(zone);
368 while (true) {
369 // Additional subtyping rules related to 'FutureOr' are not applied.
370 if (cur_cls.ptr() == interface_cls.ptr()) {
371 *interface_type_args = instance_type_args.ptr();
372 return true;
373 }
374 interfaces = cur_cls.interfaces();
375 for (intptr_t i = 0; i < interfaces.Length(); i++) {
376 interface ^= interfaces.At(i);
377 ASSERT(interface.IsFinalized());
378 cur_interface_cls = interface.type_class();
379 cur_interface_type_args =
380 interface.GetInstanceTypeArguments(thread, /*canonicalize=*/false);
381 if (!cur_interface_type_args.IsNull() &&
382 !cur_interface_type_args.IsInstantiated()) {
383 cur_interface_type_args = cur_interface_type_args.InstantiateFrom(
384 instance_type_args, Object::null_type_arguments(), kNoneFree,
385 Heap::kNew);
386 }
387 if (ExtractInterfaceTypeArgs(zone, cur_interface_cls,
388 cur_interface_type_args, interface_cls,
389 interface_type_args)) {
390 return true;
391 }
392 }
393 cur_cls = cur_cls.SuperClass();
394 if (cur_cls.IsNull()) {
395 return false;
396 }
397 }
398}
399
400// for documentation see pkg/dart_internal/lib/extract_type_arguments.dart
401DEFINE_NATIVE_ENTRY(Internal_extractTypeArguments, 0, 2) {
402 const Instance& instance =
403 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
404 const Instance& extract =
405 Instance::CheckedHandle(zone, arguments->NativeArgAt(1));
406
407 Class& interface_cls = Class::Handle(zone);
408 intptr_t num_type_args = 0;
409 if (arguments->NativeTypeArgCount() >= 1) {
410 const AbstractType& function_type_arg =
411 AbstractType::Handle(zone, arguments->NativeTypeArgAt(0));
412 if (function_type_arg.IsType() &&
413 (Type::Cast(function_type_arg).arguments() == TypeArguments::null())) {
414 interface_cls = function_type_arg.type_class();
415 num_type_args = interface_cls.NumTypeParameters();
416 }
417 }
418 if (num_type_args == 0) {
420 zone,
422 "single function type argument must specify a generic class")));
423 }
424 if (instance.IsNull()) {
426 }
427 // Function 'extract' must be generic and accept the same number of type args,
428 // unless we execute Dart 1.0 code.
429 if (extract.IsNull() || !extract.IsClosure() ||
430 ((num_type_args > 0) && // Dart 1.0 if num_type_args == 0.
431 (Function::Handle(zone, Closure::Cast(extract).function())
432 .NumTypeParameters() != num_type_args))) {
434 zone,
435 String::New("argument 'extract' is not a generic function or not one "
436 "accepting the correct number of type arguments")));
437 }
438 TypeArguments& extracted_type_args = TypeArguments::Handle(zone);
439 if (num_type_args > 0) {
440 // The passed instance must implement interface_cls.
441 TypeArguments& interface_type_args = TypeArguments::Handle(zone);
442 interface_type_args = TypeArguments::New(num_type_args);
443 Class& instance_cls = Class::Handle(zone, instance.clazz());
444 TypeArguments& instance_type_args = TypeArguments::Handle(zone);
445 if (instance_cls.NumTypeArguments() > 0) {
446 instance_type_args = instance.GetTypeArguments();
447 }
448 if (!ExtractInterfaceTypeArgs(zone, instance_cls, instance_type_args,
449 interface_cls, &interface_type_args)) {
451 zone, String::New("type of argument 'instance' is not a subtype of "
452 "the function type argument")));
453 }
454 if (!interface_type_args.IsNull()) {
455 extracted_type_args = TypeArguments::New(num_type_args);
456 const intptr_t offset = interface_cls.NumTypeArguments() - num_type_args;
457 AbstractType& type_arg = AbstractType::Handle(zone);
458 for (intptr_t i = 0; i < num_type_args; i++) {
459 type_arg = interface_type_args.TypeAt(offset + i);
460 extracted_type_args.SetTypeAt(i, type_arg);
461 }
462 extracted_type_args =
463 extracted_type_args.Canonicalize(thread); // Can be null.
464 }
465 }
466 // Call the closure 'extract'.
467 Array& args_desc = Array::Handle(zone);
468 Array& args = Array::Handle(zone);
469 if (extracted_type_args.IsNull()) {
470 args_desc = ArgumentsDescriptor::NewBoxed(0, 1);
471 args = Array::New(1);
472 args.SetAt(0, extract);
473 } else {
474 args_desc = ArgumentsDescriptor::NewBoxed(num_type_args, 1);
475 args = Array::New(2);
476 args.SetAt(0, extracted_type_args);
477 args.SetAt(1, extract);
478 }
479 const Object& result =
480 Object::Handle(zone, DartEntry::InvokeClosure(thread, args, args_desc));
481 if (result.IsError()) {
483 UNREACHABLE();
484 }
485 return result.ptr();
486}
487
488DEFINE_NATIVE_ENTRY(Internal_prependTypeArguments, 0, 4) {
489 const TypeArguments& function_type_arguments =
490 TypeArguments::CheckedHandle(zone, arguments->NativeArgAt(0));
491 const TypeArguments& parent_type_arguments =
492 TypeArguments::CheckedHandle(zone, arguments->NativeArgAt(1));
493 GET_NON_NULL_NATIVE_ARGUMENT(Smi, smi_parent_len, arguments->NativeArgAt(2));
494 GET_NON_NULL_NATIVE_ARGUMENT(Smi, smi_len, arguments->NativeArgAt(3));
495 return function_type_arguments.Prepend(
496 zone, parent_type_arguments, smi_parent_len.Value(), smi_len.Value());
497}
498
499// Check that a set of type arguments satisfy the type parameter bounds on a
500// closure.
501// Arg0: Closure object
502// Arg1: Type arguments to function
503DEFINE_NATIVE_ENTRY(Internal_boundsCheckForPartialInstantiation, 0, 2) {
504 const Closure& closure =
505 Closure::CheckedHandle(zone, arguments->NativeArgAt(0));
506 const Function& target = Function::Handle(zone, closure.function());
507 ASSERT(target.IsGeneric()); // No need to check bounds for non-generics.
508 const TypeParameters& type_params =
509 TypeParameters::Handle(zone, target.type_parameters());
510 if (type_params.IsNull() || type_params.AllDynamicBounds()) {
511 // The function is not generic or the bounds are all dynamic.
512 return Object::null();
513 }
514
515 const TypeArguments& type_args_to_check =
516 TypeArguments::CheckedHandle(zone, arguments->NativeArgAt(1));
517
518 // This should be guaranteed by the front-end.
519 ASSERT(type_args_to_check.IsNull() ||
520 type_params.Length() <= type_args_to_check.Length());
521
522 // The bounds on the closure may need instantiation.
523 const TypeArguments& instantiator_type_args =
524 TypeArguments::Handle(zone, closure.instantiator_type_arguments());
525 const TypeArguments& function_type_args = TypeArguments::Handle(
526 zone,
527 type_args_to_check.Prepend(
528 zone, TypeArguments::Handle(zone, closure.function_type_arguments()),
529 target.NumParentTypeArguments(), target.NumTypeArguments()));
530
531 AbstractType& supertype = AbstractType::Handle(zone);
532 AbstractType& subtype = AbstractType::Handle(zone);
533 for (intptr_t i = 0; i < type_params.Length(); ++i) {
534 supertype = type_params.BoundAt(i);
535 subtype = type_args_to_check.IsNull() ? Object::dynamic_type().ptr()
536 : type_args_to_check.TypeAt(i);
537
538 ASSERT(!subtype.IsNull());
539 ASSERT(!supertype.IsNull());
540
541 // The supertype may not be instantiated.
543 &subtype, &supertype, instantiator_type_args, function_type_args)) {
544 // Throw a dynamic type error.
545 TokenPosition location = TokenPosition::kNoSource;
546 {
549 StackFrame* caller_frame = iterator.NextFrame();
550 ASSERT(caller_frame != nullptr);
551 location = caller_frame->GetTokenPos();
552 }
553 const auto& parameter_name = String::Handle(zone, type_params.NameAt(i));
554 Exceptions::CreateAndThrowTypeError(location, subtype, supertype,
555 parameter_name);
556 UNREACHABLE();
557 }
558 }
559
560 return Object::null();
561}
562
563DEFINE_NATIVE_ENTRY(InvocationMirror_unpackTypeArguments, 0, 2) {
564 const TypeArguments& type_arguments =
565 TypeArguments::CheckedHandle(zone, arguments->NativeArgAt(0));
566 const Smi& num_type_arguments =
567 Smi::CheckedHandle(zone, arguments->NativeArgAt(1));
568 bool all_dynamic = type_arguments.IsNull();
569 const intptr_t len =
570 all_dynamic ? num_type_arguments.Value() : type_arguments.Length();
571 const Array& type_list = Array::Handle(
574 for (intptr_t i = 0; i < len; i++) {
575 if (all_dynamic) {
576 type_list.SetAt(i, Object::dynamic_type());
577 } else {
578 type = type_arguments.TypeAt(i);
579 type_list.SetAt(i, type);
580 }
581 }
582 type_list.MakeImmutable();
583 return type_list.ptr();
584}
585
586DEFINE_NATIVE_ENTRY(NoSuchMethodError_existingMethodSignature, 0, 3) {
587 const Instance& receiver =
588 Instance::CheckedHandle(zone, arguments->NativeArgAt(0));
589 GET_NON_NULL_NATIVE_ARGUMENT(String, method_name, arguments->NativeArgAt(1));
590 GET_NON_NULL_NATIVE_ARGUMENT(Smi, invocation_type, arguments->NativeArgAt(2));
593 InvocationMirror::DecodeType(invocation_type.Value(), &level, &kind);
594
596 if (level == InvocationMirror::Level::kTopLevel) {
597 if (receiver.IsString()) return receiver.ptr();
598 ASSERT(receiver.IsNull());
599 return String::null();
600 }
601 if (receiver.IsType()) {
602 const auto& cls = Class::Handle(zone, Type::Cast(receiver).type_class());
603 const auto& error = Error::Handle(zone, cls.EnsureIsFinalized(thread));
604 if (!error.IsNull()) {
606 UNREACHABLE();
607 }
609 function = cls.LookupConstructor(method_name);
610 if (function.IsNull()) {
611 function = cls.LookupFactory(method_name);
612 }
613 } else {
614 function = cls.LookupStaticFunction(method_name);
615 }
616 } else if (receiver.IsClosure()) {
617 function = Closure::Cast(receiver).function();
618 } else {
619 auto& cls = Class::Handle(zone, receiver.clazz());
621 cls = cls.SuperClass();
622 }
623 function = Resolver::ResolveDynamicAnyArgs(zone, cls, method_name,
624 /*allow_add=*/false);
625 }
626 if (!function.IsNull()) {
627 return function.UserVisibleSignature();
628 }
629 return String::null();
630}
631
632} // namespace dart
T extract(SkSpan< const uint8_t > &data)
static uint32_t hash(const SkShaderBase::GradientInfo &v)
#define UNREACHABLE()
Definition: assert.h:248
GLenum type
virtual bool IsEquivalent(const Instance &other, TypeEquality kind, FunctionTypeMapping *function_type_equivalence=nullptr) const
Definition: object.cc:21184
static bool InstantiateAndTestSubtype(AbstractType *subtype, AbstractType *supertype, const TypeArguments &instantiator_type_args, const TypeArguments &function_type_args)
Definition: object.cc:4287
virtual ClassPtr type_class() const
Definition: object.cc:21042
const char * NameCString() const
Definition: object.cc:21324
static ArrayPtr NewBoxed(intptr_t type_args_len, intptr_t num_arguments, const Array &optional_arguments_names, Heap::Space space=Heap::kOld)
Definition: dart_entry.h:83
static ArrayPtr New(intptr_t len, Heap::Space space=Heap::kNew)
Definition: object.h:10959
void MakeImmutable() const
Definition: object.cc:24837
ObjectPtr At(intptr_t index) const
Definition: object.h:10875
intptr_t Length() const
Definition: object.h:10829
void SetAt(intptr_t index, const Object &value) const
Definition: object.h:10880
static const Bool & Get(bool value)
Definition: object.h:10801
static const Bool & True()
Definition: object.h:10797
intptr_t NumTypeArguments() const
Definition: object.cc:3640
ArrayPtr interfaces() const
Definition: object.h:1447
bool IsGeneric() const
Definition: object.h:1358
ClassPtr SuperClass(ClassTable *class_table=nullptr) const
Definition: object.cc:3665
intptr_t NumTypeParameters(Thread *thread) const
Definition: object.cc:3555
static ObjectPtr InvokeClosure(Thread *thread, const Array &arguments)
Definition: dart_entry.cc:282
static ObjectPtr InvokeFunction(const Function &function, const Array &arguments)
Definition: dart_entry.cc:31
StackFrame * NextFrame()
Definition: stack_frame.h:352
static DART_NORETURN void ThrowArgumentError(const Instance &arg)
Definition: exceptions.cc:1082
static void CreateAndThrowTypeError(TokenPosition location, const AbstractType &src_type, const AbstractType &dst_type, const String &dst_name)
Definition: exceptions.cc:896
static DART_NORETURN void PropagateError(const Error &error)
Definition: exceptions.cc:1003
@ kNew
Definition: heap.h:38
intptr_t GetHash(ObjectPtr raw_obj) const
Definition: heap.h:178
static void DecodeType(int type, Level *level, Kind *kind)
Heap * heap() const
Definition: isolate.h:296
IsolateGroup * group() const
Definition: isolate.h:1037
static LibraryPtr CoreLibrary()
Definition: object.cc:14787
FunctionPtr LookupFunctionAllowPrivate(const String &name) const
Definition: object.cc:14084
intptr_t id() const
Definition: object.h:7985
static constexpr intptr_t kIllegalId
Definition: object.h:7967
ObjectPtr IssueLoad() const
Definition: object.cc:19708
static void static void PrintErr(const char *format,...) PRINTF_ATTRIBUTE(1
bool IsDartInstance() const
static ObjectPtr null()
Definition: object.h:433
ObjectPtr ptr() const
Definition: object.h:332
bool IsNull() const
Definition: object.h:363
static Object & Handle()
Definition: object.h:407
ClassPtr clazz() const
Definition: object.h:13218
static FunctionPtr ResolveDynamicAnyArgs(Zone *zone, const Class &receiver_class, const String &function_name, bool allow_add)
Definition: resolver.cc:185
static SmiPtr New(intptr_t value)
Definition: object.h:10006
intptr_t Value() const
Definition: object.h:9990
static bool IsValid(int64_t value)
Definition: object.h:10026
TokenPosition GetTokenPos() const
Definition: stack_frame.cc:429
static StringPtr New(const char *cstr, Heap::Space space=Heap::kNew)
Definition: object.cc:23698
static Thread * Current()
Definition: thread.h:362
bool IsInstantiated(Genericity genericity=kAny, intptr_t num_free_fun_type_params=kAllFree) const
Definition: object.h:8707
intptr_t Length() const
Definition: object.cc:7294
bool IsSubvectorEquivalent(const TypeArguments &other, intptr_t from_index, intptr_t len, TypeEquality kind, FunctionTypeMapping *function_type_equivalence=nullptr) const
Definition: object.cc:6920
void SetTypeAt(intptr_t index, const AbstractType &value) const
Definition: object.cc:7323
TypeArgumentsPtr InstantiateFrom(const TypeArguments &instantiator_type_arguments, const TypeArguments &function_type_arguments, intptr_t num_free_fun_type_params, Heap::Space space, FunctionTypeMapping *function_type_mapping=nullptr, intptr_t num_parent_type_args_adjustment=0) const
Definition: object.cc:7540
TypeArgumentsPtr Canonicalize(Thread *thread) const
Definition: object.cc:7703
static TypeArgumentsPtr New(intptr_t len, Heap::Space space=Heap::kOld)
Definition: object.cc:7675
AbstractTypePtr TypeAt(intptr_t index) const
Definition: object.cc:7308
TypeArgumentsPtr Prepend(Zone *zone, const TypeArguments &other, intptr_t other_length, intptr_t total_length) const
Definition: object.cc:6800
intptr_t Length() const
Definition: object.cc:6564
StringPtr NameAt(intptr_t index) const
Definition: object.cc:6574
bool AllDynamicBounds() const
Definition: object.cc:6605
AbstractTypePtr BoundAt(intptr_t index) const
Definition: object.cc:6593
static TypePtr IntType()
static TypePtr Double()
static TypePtr StringType()
static TypePtr New(const Class &clazz, const TypeArguments &arguments, Nullability nullability=Nullability::kNonNullable, Heap::Space space=Heap::kOld)
static TypePtr DartTypeType()
Definition: il.h:75
#define THR_Print(format,...)
Definition: log.h:20
#define ASSERT(E)
VkInstance instance
Definition: main.cc:48
#define FATAL(error)
G_BEGIN_DECLS G_MODULE_EXPORT FlValue * args
const uint8_t uint32_t uint32_t GError ** error
GAsyncResult * result
uint32_t * target
Dart_NativeFunction function
Definition: fuchsia.cc:51
Definition: dart_vm.cc:33
static bool HaveSameRuntimeTypeHelper(Zone *zone, const Instance &left, const Instance &right)
Definition: object.cc:101
void DeoptimizeFunctionsOnStack()
bool IsTypeClassId(intptr_t index)
Definition: class_id.h:370
bool IsArrayClassId(intptr_t index)
Definition: class_id.h:358
uintptr_t uword
Definition: globals.h:501
static intptr_t GetHash(Isolate *isolate, const ObjectPtr obj)
Definition: object.cc:37
static bool ExtractInterfaceTypeArgs(Zone *zone, const Class &instance_cls, const TypeArguments &instance_type_args, const Class &interface_cls, TypeArguments *interface_type_args)
Definition: object.cc:356
DEFINE_NATIVE_ENTRY(List_allocate, 0, 2)
Definition: array.cc:13
bool IsIntegerClassId(intptr_t index)
Definition: class_id.h:340
bool IsStringClassId(intptr_t index)
Definition: class_id.h:350
@ kNoneFree
Definition: object.h:2926
std::function< void()> closure
Definition: closure.h:14
#define GET_NON_NULL_NATIVE_ARGUMENT(type, name, value)
Definition: native_entry.h:74
#define LIKELY(cond)
Definition: globals.h:260
SeparatedVector2 offset