Flutter Engine
The Flutter Engine
Loading...
Searching...
No Matches
runtime_api.cc
Go to the documentation of this file.
1// Copyright (c) 2019, 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
9#include "vm/object.h"
10
11#if !defined(DART_PRECOMPILED_RUNTIME)
14#include "vm/dart_api_state.h"
15#include "vm/dart_entry.h"
16#include "vm/longjump.h"
17#include "vm/native_arguments.h"
18#include "vm/native_entry.h"
19#include "vm/object_store.h"
20#include "vm/runtime_entry.h"
21#include "vm/symbols.h"
22#include "vm/timeline.h"
23#endif // !defined(DART_PRECOMPILED_RUNTIME)
24
25namespace dart {
26namespace compiler {
27namespace target {
28
30
31bool IsSmi(int64_t v) {
32 return Utils::IsInt(kSmiBits + 1, v);
33}
34
35bool WillAllocateNewOrRememberedObject(intptr_t instance_size) {
37 return dart::IsAllocatableInNewSpace(instance_size);
38}
39
40bool WillAllocateNewOrRememberedContext(intptr_t num_context_variables) {
41 if (!dart::Context::IsValidLength(num_context_variables)) return false;
43 dart::Context::InstanceSize(num_context_variables));
44}
45
50
51} // namespace target
52} // namespace compiler
53} // namespace dart
54
55#if !defined(DART_PRECOMPILED_RUNTIME)
56
57namespace dart {
58namespace compiler {
59
60bool IsSameObject(const Object& a, const Object& b) {
61 if (a.IsInstance() && b.IsInstance()) {
62 return Instance::Cast(a).IsIdenticalTo(Instance::Cast(b));
63 }
64 return a.ptr() == b.ptr();
65}
66
67bool IsEqualType(const AbstractType& a, const AbstractType& b) {
68 return a.Equals(b);
69}
70
72 return type.IsDoubleType();
73}
74
76 return type.IsBoolType();
77}
78
80 return type.IsIntType() || type.IsIntegerImplementationType() ||
81 type.IsSmiType() || type.IsMintType();
82}
83
85 return type.IsSmiType();
86}
87
88#if defined(DEBUG)
89bool IsNotTemporaryScopedHandle(const Object& obj) {
90 return obj.IsNotTemporaryScopedHandle();
91}
92#endif
93
94#define DO(clazz) \
95 bool Is##clazz##Handle(const Object& obj) { \
96 return obj.Is##clazz(); \
97 }
99#undef DO
100
101bool IsInOldSpace(const Object& obj) {
102 return obj.IsSmi() || obj.IsOld();
103}
104
105intptr_t ObjectHash(const Object& obj) {
106 if (obj.IsNull()) {
107 return kNullIdentityHash;
108 }
109 // TypeArguments should be handled before Instance as TypeArguments extends
110 // Instance and TypeArguments::CanonicalizeHash just returns 0.
111 if (obj.IsTypeArguments()) {
112 return TypeArguments::Cast(obj).Hash();
113 }
114 if (obj.IsInstance()) {
115 return Instance::Cast(obj).CanonicalizeHash();
116 }
117 if (obj.IsCode()) {
118 return Code::Cast(obj).Hash();
119 }
120 if (obj.IsFunction()) {
121 return Function::Cast(obj).Hash();
122 }
123 if (obj.IsField()) {
124 return Field::Cast(obj).Hash();
125 }
126 if (obj.IsICData()) {
127 return ICData::Cast(obj).Hash();
128 }
129 // Unlikely.
130 return obj.GetClassId();
131}
132
133const char* ObjectToCString(const Object& obj) {
134 return obj.ToCString();
135}
136
137void SetToNull(Object* obj) {
138 *obj = Object::null();
139}
140
142 return Object::ZoneHandle(zone, Object::null());
143}
144
145Object& NewZoneHandle(Zone* zone, const Object& obj) {
146 return Object::ZoneHandle(zone, obj.ptr());
147}
148
150 return Object::null_object();
151}
152
154 return Object::sentinel();
155}
156
157const Bool& TrueObject() {
158 return dart::Bool::True();
159}
160
162 return dart::Bool::False();
163}
164
166 return Object::empty_type_arguments();
167}
168
170 return dart::Type::dynamic_type();
171}
172
173const Type& ObjectType() {
175}
176
177const Type& VoidType() {
178 return dart::Type::void_type();
179}
180
181const Type& IntType() {
183}
184
186 auto object_store = IsolateGroup::Current()->object_store();
187 return Class::Handle(object_store->growable_object_array_class());
188}
189
190const Class& MintClass() {
191 auto object_store = IsolateGroup::Current()->object_store();
192 return Class::Handle(object_store->mint_class());
193}
194
196 auto object_store = IsolateGroup::Current()->object_store();
197 return Class::Handle(object_store->double_class());
198}
199
201 auto object_store = IsolateGroup::Current()->object_store();
202 return Class::Handle(object_store->float32x4_class());
203}
204
206 auto object_store = IsolateGroup::Current()->object_store();
207 return Class::Handle(object_store->float64x2_class());
208}
209
211 auto object_store = IsolateGroup::Current()->object_store();
212 return Class::Handle(object_store->int32x4_class());
213}
214
216 auto object_store = IsolateGroup::Current()->object_store();
217 return Class::Handle(object_store->closure_class());
218}
219
220const Array& ArgumentsDescriptorBoxed(intptr_t type_args_len,
221 intptr_t num_arguments) {
222 return Array::ZoneHandle(
223 ArgumentsDescriptor::NewBoxed(type_args_len, num_arguments));
224}
225
226bool IsOriginalObject(const Object& object) {
227 if (object.IsICData()) {
228 return ICData::Cast(object).IsOriginal();
229 } else if (object.IsField()) {
230 return Field::Cast(object).IsOriginal();
231 }
232 return true;
233}
234
238
239bool HasIntegerValue(const dart::Object& object, int64_t* value) {
240 if (object.IsInteger()) {
241 *value = Integer::Cast(object).AsInt64Value();
242 return true;
243 }
244 return false;
245}
246
248 return static_cast<int32_t>(IsolateGroup::Current()->random()->NextUInt32());
249}
250
254
256 return (dart::kNewAllocatableSize - target::TypedData::HeaderSize()) /
258}
259
261 const auto& math_lib = dart::Library::Handle(dart::Library::MathLibrary());
262 ASSERT(!math_lib.IsNull());
263 const auto& random_class = dart::Class::Handle(
264 math_lib.LookupClassAllowPrivate(dart::Symbols::_Random()));
265 ASSERT(!random_class.IsNull());
266 const auto& state_field = dart::Field::ZoneHandle(
267 random_class.LookupInstanceFieldAllowPrivate(dart::Symbols::_state()));
268 return state_field;
269}
270
272 const auto& convert_lib =
274 ASSERT(!convert_lib.IsNull());
275 const auto& _utf8decoder_class = dart::Class::Handle(
276 convert_lib.LookupClassAllowPrivate(dart::Symbols::_Utf8Decoder()));
277 ASSERT(!_utf8decoder_class.IsNull());
278 const auto& scan_flags_field = dart::Field::ZoneHandle(
279 _utf8decoder_class.LookupInstanceFieldAllowPrivate(
280 dart::Symbols::_scanFlags()));
281 return scan_flags_field;
282}
283
285 return field.TargetOffset();
286}
287
288#if defined(TARGET_ARCH_IA32)
289uword SymbolsPredefinedAddress() {
290 return reinterpret_cast<uword>(dart::Symbols::PredefinedAddress());
291}
292#endif
293
295 return dart::StubCode::AllocateArray();
296}
297
299 return dart::StubCode::Subtype2TestCache();
300}
301
303 return dart::StubCode::Subtype3TestCache();
304}
305
307 return dart::StubCode::Subtype4TestCache();
308}
309
311 return dart::StubCode::Subtype6TestCache();
312}
313
315 return dart::StubCode::Subtype7TestCache();
316}
317
318#define DEFINE_ALIAS(name) \
319 const RuntimeEntry& k##name##RuntimeEntry(dart::k##name##RuntimeEntry);
321#undef DEFINE_ALIAS
322
323#define DEFINE_ALIAS(type, name, ...) \
324 const RuntimeEntry& k##name##RuntimeEntry(dart::k##name##RuntimeEntry);
326#undef DEFINE_ALIAS
327
329 Thread::Current()->long_jump_base()->Jump(1, Object::branch_offset_error());
330}
331
333 return target::Thread::OffsetFromThread(runtime_entry_);
334}
335
337 return runtime_entry_->is_leaf();
338}
339
341 return runtime_entry_->argument_count();
342}
343
344namespace target {
345
349
351 RELEASE_ASSERT((offset % kCompressedWordSize) == 0);
352 return (offset / kCompressedWordSize) * dart::kCompressedWordSize;
353}
354
355bool SizeFitsInSizeTag(uword instance_size) {
357 TranslateOffsetInWordsToHost(instance_size));
358}
359
370
371word Object::tags_offset() {
372 return 0;
373}
374
375const word UntaggedObject::kCardRememberedBit =
377
378const word UntaggedObject::kCanonicalBit = dart::UntaggedObject::kCanonicalBit;
379
380const word UntaggedObject::kNewBit = dart::UntaggedObject::kNewBit;
381
382const word UntaggedObject::kOldAndNotRememberedBit =
384
385const word UntaggedObject::kNotMarkedBit = dart::UntaggedObject::kNotMarkedBit;
386
387const word UntaggedObject::kImmutableBit = dart::UntaggedObject::kImmutableBit;
388
389const word UntaggedObject::kSizeTagPos = dart::UntaggedObject::kSizeTagPos;
390
391const word UntaggedObject::kSizeTagSize = dart::UntaggedObject::kSizeTagSize;
392
393const word UntaggedObject::kClassIdTagPos =
395
396const word UntaggedObject::kClassIdTagSize =
398
399const word UntaggedObject::kHashTagPos = dart::UntaggedObject::kHashTagPos;
400
401const word UntaggedObject::kHashTagSize = dart::UntaggedObject::kHashTagSize;
402
403const word UntaggedObject::kSizeTagMaxSizeTag =
406
407const word UntaggedObject::kTagBitsSizeTagPos =
409
410const word UntaggedAbstractType::kTypeStateFinalizedInstantiated =
412const word UntaggedAbstractType::kTypeStateShift =
414const word UntaggedAbstractType::kTypeStateBits =
416const word UntaggedAbstractType::kNullabilityMask =
418
419const word UntaggedType::kTypeClassIdShift =
421
422const word UntaggedTypeParameter::kIsFunctionTypeParameterBit =
424
425const word UntaggedObject::kBarrierOverlapShift =
427
428const word UntaggedObject::kGenerationalBarrierMask =
430
431const word UntaggedObject::kIncrementalBarrierMask =
433
434bool IsTypedDataClassId(intptr_t cid) {
436}
437
438const word Class::kNoTypeArguments = dart::Class::kNoTypeArguments;
439
440classid_t Class::GetId(const dart::Class& handle) {
441 return handle.id();
442}
443
448
449static uword GetInstanceSizeImpl(const dart::Class& handle) {
450 switch (handle.id()) {
451 case kMintCid:
452 return Mint::InstanceSize();
453 case kDoubleCid:
454 return Double::InstanceSize();
455 case kInt32x4Cid:
456 return Int32x4::InstanceSize();
457 case kFloat32x4Cid:
458 return Float32x4::InstanceSize();
459 case kFloat64x2Cid:
460 return Float64x2::InstanceSize();
461 case kObjectCid:
462 return Object::InstanceSize();
463 case kInstanceCid:
464 return Instance::InstanceSize();
465 case kGrowableObjectArrayCid:
466 return GrowableObjectArray::InstanceSize();
467 case kClosureCid:
468 return Closure::InstanceSize();
469 case kTypedDataBaseCid:
470 return TypedDataBase::InstanceSize();
471 case kMapCid:
472 return Map::InstanceSize();
473 case kSetCid:
474 return Set::InstanceSize();
475 case kUnhandledExceptionCid:
476 return UnhandledException::InstanceSize();
477 case kWeakPropertyCid:
478 return WeakProperty::InstanceSize();
479 case kWeakReferenceCid:
480 return WeakReference::InstanceSize();
481 case kFinalizerCid:
482 return Finalizer::InstanceSize();
483 case kFinalizerEntryCid:
484 return FinalizerEntry::InstanceSize();
485 case kNativeFinalizerCid:
486 return NativeFinalizer::InstanceSize();
487 case kByteBufferCid:
488 case kByteDataViewCid:
490 case kPointerCid:
491 case kDynamicLibraryCid:
492#define HANDLE_CASE(clazz) case kFfi##clazz##Cid:
494#undef HANDLE_CASE
495#define HANDLE_CASE(clazz) \
496 case kTypedData##clazz##Cid: \
497 case kTypedData##clazz##ViewCid: \
498 case kExternalTypedData##clazz##Cid: \
499 case kUnmodifiableTypedData##clazz##ViewCid:
501#undef HANDLE_CASE
502 return handle.target_instance_size();
503 default:
504 if (handle.id() >= kNumPredefinedCids) {
505 return handle.target_instance_size();
506 }
507 }
508 FATAL("Unsupported class for size translation: %s (id=%" Pd
509 ", kNumPredefinedCids=%" Pd ")\n",
510 handle.ToCString(), handle.id(), kNumPredefinedCids);
511 return -1;
512}
513
514uword Class::GetInstanceSize(const dart::Class& handle) {
515 return Utils::RoundUp(GetInstanceSizeImpl(handle),
517}
518
519// Currently, we only have compressed pointers on the target if we also have
520// compressed pointers on the host, since only 64-bit architectures can have
521// compressed pointers and there is no 32-bit host/64-bit target combination.
522// Thus, we cheat a little here and use the host information about compressed
523// pointers for the target, instead of storing this information in the extracted
524// offsets information.
525bool Class::HasCompressedPointers(const dart::Class& handle) {
526 return handle.HasCompressedPointers();
527}
528
529intptr_t Class::NumTypeArguments(const dart::Class& klass) {
530 return klass.NumTypeArguments();
531}
532
533bool Class::HasTypeArgumentsField(const dart::Class& klass) {
534 return klass.host_type_arguments_field_offset() !=
536}
537
538intptr_t Class::TypeArgumentsFieldOffset(const dart::Class& klass) {
540}
541
542bool Class::TraceAllocation(const dart::Class& klass) {
544}
545
546word Instance::first_field_offset() {
548}
549
550word Instance::native_fields_array_offset() {
552}
553
554word Instance::DataOffsetFor(intptr_t cid) {
556 // Elements start at offset 0 of the external data.
557 return 0;
558 }
560 return TypedData::payload_offset();
561 }
562 switch (cid) {
563 case kArrayCid:
564 case kImmutableArrayCid:
565 return Array::data_offset();
566 case kTypeArgumentsCid:
567 return TypeArguments::types_offset();
568 case kOneByteStringCid:
569 return OneByteString::data_offset();
570 case kTwoByteStringCid:
571 return TwoByteString::data_offset();
572 case kRecordCid:
573 return Record::field_offset(0);
574 default:
576 return Array::data_offset();
577 }
578}
579
580word Instance::ElementSizeFor(intptr_t cid) {
585 }
586 switch (cid) {
587 case kArrayCid:
588 case kImmutableArrayCid:
589 return kCompressedWordSize;
590 case kTypeArgumentsCid:
591 return kCompressedWordSize;
592 case kOneByteStringCid:
594 case kTwoByteStringCid:
596 default:
598 return 0;
599 }
600}
601
602word ICData::CodeIndexFor(word num_args) {
603 return dart::ICData::CodeIndexFor(num_args);
604}
605
606word ICData::CountIndexFor(word num_args) {
607 return dart::ICData::CountIndexFor(num_args);
608}
609
610word ICData::TargetIndexFor(word num_args) {
611 return dart::ICData::TargetIndexFor(num_args);
612}
613
614word ICData::ExactnessIndexFor(word num_args) {
615 return dart::ICData::ExactnessIndexFor(num_args);
616}
617
618word ICData::TestEntryLengthFor(word num_args, bool exactness_check) {
619 return dart::ICData::TestEntryLengthFor(num_args, exactness_check);
620}
621
622word ICData::EntryPointIndexFor(word num_args) {
623 return dart::ICData::EntryPointIndexFor(num_args);
624}
625
626const word MegamorphicCache::kSpreadFactor =
628
629// Currently we have two different axes for offset generation:
630//
631// * Target architecture
632// * DART_PRECOMPILED_RUNTIME (i.e, AOT vs. JIT)
633//
634// TODO(dartbug.com/43646): Add DART_PRECOMPILER as another axis.
635
636#define DEFINE_CONSTANT(Class, Name) const word Class::Name = Class##_##Name;
637
638#define DEFINE_ARRAY_SIZEOF(clazz, name, ElementOffset) \
639 word clazz::name() { \
640 return 0; \
641 } \
642 word clazz::name(intptr_t length) { \
643 return RoundedAllocationSize(clazz::ElementOffset(length)); \
644 }
645
646#define DEFINE_PAYLOAD_SIZEOF(clazz, name, header) \
647 word clazz::name() { \
648 return 0; \
649 } \
650 word clazz::name(word payload_size) { \
651 return RoundedAllocationSize(clazz::header() + payload_size); \
652 }
653
654#if defined(TARGET_ARCH_IA32)
655
656#define DEFINE_FIELD(clazz, name) \
657 word clazz::name() { \
658 return clazz##_##name; \
659 }
660
661#define DEFINE_ARRAY(clazz, name) \
662 word clazz::name(intptr_t index) { \
663 return clazz##_elements_start_offset + index * clazz##_element_size; \
664 }
665
666#define DEFINE_SIZEOF(clazz, name, what) \
667 word clazz::name() { \
668 return clazz##_##name; \
669 }
670
671#define DEFINE_RANGE(Class, Getter, Type, First, Last, Filter) \
672 word Class::Getter(Type index) { \
673 return Class##_##Getter[static_cast<intptr_t>(index) - \
674 static_cast<intptr_t>(First)]; \
675 }
676
684
692
693#else
694
695#define DEFINE_JIT_FIELD(clazz, name) \
696 word clazz::name() { \
697 if (FLAG_precompiled_mode) { \
698 FATAL("Use of JIT-only field %s in precompiled mode", \
699 #clazz "::" #name); \
700 } \
701 return clazz##_##name; \
702 }
703
704#define DEFINE_JIT_ARRAY(clazz, name) \
705 word clazz::name(intptr_t index) { \
706 if (FLAG_precompiled_mode) { \
707 FATAL("Use of JIT-only array %s in precompiled mode", \
708 #clazz "::" #name); \
709 } \
710 return clazz##_elements_start_offset + index * clazz##_element_size; \
711 }
712
713#define DEFINE_JIT_SIZEOF(clazz, name, what) \
714 word clazz::name() { \
715 if (FLAG_precompiled_mode) { \
716 FATAL("Use of JIT-only sizeof %s in precompiled mode", \
717 #clazz "::" #name); \
718 } \
719 return clazz##_##name; \
720 }
721
722#define DEFINE_JIT_RANGE(Class, Getter, Type, First, Last, Filter) \
723 word Class::Getter(Type index) { \
724 if (FLAG_precompiled_mode) { \
725 FATAL("Use of JIT-only range %s in precompiled mode", \
726 #Class "::" #Getter); \
727 } \
728 return Class##_##Getter[static_cast<intptr_t>(index) - \
729 static_cast<intptr_t>(First)]; \
730 }
731
739
740#undef DEFINE_JIT_FIELD
741#undef DEFINE_JIT_ARRAY
742#undef DEFINE_JIT_SIZEOF
743#undef DEFINE_JIT_RANGE
744
745#if defined(DART_PRECOMPILER)
746// The following could check FLAG_precompiled_mode for more safety, but that
747// causes problems for defining things like native Slots, where the definition
748// cannot be based on a runtime flag. Instead, we limit the visibility of these
749// definitions using DART_PRECOMPILER.
750
751#define DEFINE_AOT_FIELD(clazz, name) \
752 word clazz::name() { \
753 return AOT_##clazz##_##name; \
754 }
755
756#define DEFINE_AOT_ARRAY(clazz, name) \
757 word clazz::name(intptr_t index) { \
758 return AOT_##clazz##_elements_start_offset + \
759 index * AOT_##clazz##_element_size; \
760 }
761
762#define DEFINE_AOT_SIZEOF(clazz, name, what) \
763 word clazz::name() { \
764 return AOT_##clazz##_##name; \
765 }
766
767#define DEFINE_AOT_RANGE(Class, Getter, Type, First, Last, Filter) \
768 word Class::Getter(Type index) { \
769 return AOT_##Class##_##Getter[static_cast<intptr_t>(index) - \
770 static_cast<intptr_t>(First)]; \
771 }
772#else
773#define DEFINE_AOT_FIELD(clazz, name) \
774 word clazz::name() { \
775 FATAL("Use of AOT-only field %s outside of the precompiler", \
776 #clazz "::" #name); \
777 }
778
779#define DEFINE_AOT_ARRAY(clazz, name) \
780 word clazz::name(intptr_t index) { \
781 FATAL("Use of AOT-only array %s outside of the precompiler", \
782 #clazz "::" #name); \
783 }
784
785#define DEFINE_AOT_SIZEOF(clazz, name, what) \
786 word clazz::name() { \
787 FATAL("Use of AOT-only sizeof %s outside of the precompiler", \
788 #clazz "::" #name); \
789 }
790
791#define DEFINE_AOT_RANGE(Class, Getter, Type, First, Last, Filter) \
792 word Class::Getter(Type index) { \
793 FATAL("Use of AOT-only range %s outside of the precompiler", \
794 #Class "::" #Getter); \
795 }
796#endif // defined(DART_PRECOMPILER)
797
805
806#undef DEFINE_AOT_FIELD
807#undef DEFINE_AOT_ARRAY
808#undef DEFINE_AOT_SIZEOF
809#undef DEFINE_AOT_RANGE
810
811#define DEFINE_FIELD(clazz, name) \
812 word clazz::name() { \
813 return FLAG_precompiled_mode ? AOT_##clazz##_##name : clazz##_##name; \
814 }
815
816#define DEFINE_ARRAY(clazz, name) \
817 word clazz::name(intptr_t index) { \
818 if (FLAG_precompiled_mode) { \
819 return AOT_##clazz##_elements_start_offset + \
820 index * AOT_##clazz##_element_size; \
821 } else { \
822 return clazz##_elements_start_offset + index * clazz##_element_size; \
823 } \
824 }
825
826#define DEFINE_SIZEOF(clazz, name, what) \
827 word clazz::name() { \
828 return FLAG_precompiled_mode ? AOT_##clazz##_##name : clazz##_##name; \
829 }
830
831#define DEFINE_RANGE(Class, Getter, Type, First, Last, Filter) \
832 word Class::Getter(Type index) { \
833 if (FLAG_precompiled_mode) { \
834 return AOT_##Class##_##Getter[static_cast<intptr_t>(index) - \
835 static_cast<intptr_t>(First)]; \
836 } else { \
837 return Class##_##Getter[static_cast<intptr_t>(index) - \
838 static_cast<intptr_t>(First)]; \
839 } \
840 }
841
849
850#endif
851
852#undef DEFINE_FIELD
853#undef DEFINE_ARRAY
854#undef DEFINE_SIZEOF
855#undef DEFINE_RANGE
856#undef DEFINE_PAYLOAD_SIZEOF
857#undef DEFINE_CONSTANT
858
860
862
863// For InstructionsSections and Instructions, we define these by hand, because
864// they depend on flags or #defines.
865
866// Used for InstructionsSection and Instructions methods, since we don't
867// serialize Instructions objects in bare instructions mode, just payloads.
868DART_FORCE_INLINE static bool BareInstructionsPayloads() {
869 return FLAG_precompiled_mode;
870}
871
872word Instructions::HeaderSize() {
874 ? 0
875 : Utils::RoundUp(UnalignedHeaderSize(), kNonBarePayloadAlignment);
876}
877
878word Instructions::InstanceSize() {
879 return 0;
880}
881
882word Instructions::InstanceSize(word payload_size) {
883 const intptr_t alignment = BareInstructionsPayloads()
884 ? kBarePayloadAlignment
886 return Utils::RoundUp(Instructions::HeaderSize() + payload_size, alignment);
887}
888
889word Thread::stack_overflow_shared_stub_entry_point_offset(bool fpu_regs) {
890 return fpu_regs ? stack_overflow_shared_with_fpu_regs_entry_point_offset()
891 : stack_overflow_shared_without_fpu_regs_entry_point_offset();
892}
893
894uword Thread::full_safepoint_state_unacquired() {
896}
897
898uword Thread::full_safepoint_state_acquired() {
900}
901
902uword Thread::generated_execution_state() {
904}
905
906uword Thread::native_execution_state() {
908}
909
910uword Thread::vm_execution_state() {
912}
913
914uword Thread::vm_tag_dart_id() {
915 return dart::VMTag::kDartTagId;
916}
917
918uword Thread::exit_through_runtime_call() {
920}
921
922uword Thread::exit_through_ffi() {
924}
925
926word Thread::OffsetFromThread(const dart::Object& object) {
927 auto host_offset = dart::Thread::OffsetFromThread(object);
928 return object_null_offset() +
929 TranslateOffsetInWords(host_offset -
930 dart::Thread::object_null_offset());
931}
932
933intptr_t Thread::OffsetFromThread(const dart::RuntimeEntry* runtime_entry) {
934 auto host_offset = dart::Thread::OffsetFromThread(runtime_entry);
935 return AllocateArray_entry_point_offset() +
937 host_offset - dart::Thread::AllocateArray_entry_point_offset());
938}
939
941 intptr_t* offset /* = nullptr */) {
943 if (offset != nullptr) {
944 *offset = Thread::OffsetFromThread(object);
945 }
946 return true;
947 }
948 return false;
949}
950
951static_assert(
953 "Expected that size of Smi on HOST is at least as large as on target.");
954
955bool IsSmi(const dart::Object& a) {
956 return a.IsSmi() && IsSmi(dart::Smi::Cast(a).Value());
957}
958
961 return static_cast<compressed_word>(static_cast<intptr_t>(a.ptr()));
962}
963
964word ToRawSmi(intptr_t value) {
966}
967
970 return static_cast<word>(dart::Smi::Cast(a).Value());
971}
972
973bool IsDouble(const dart::Object& a) {
974 return a.IsDouble();
975}
976
977double DoubleValue(const dart::Object& a) {
979 return dart::Double::Cast(a).value();
980}
981
982#if defined(TARGET_ARCH_IA32)
984 static_assert(kHostWordSize == kWordSize,
985 "Can't embed raw pointers to runtime objects when host and "
986 "target word sizes are different");
987 return code.EntryPoint();
988}
989
990bool CanEmbedAsRawPointerInGeneratedCode(const dart::Object& obj) {
991 return obj.IsSmi() || obj.InVMIsolateHeap();
992}
993
994word ToRawPointer(const dart::Object& a) {
995 static_assert(kHostWordSize == kWordSize,
996 "Can't embed raw pointers to runtime objects when host and "
997 "target word sizes are different");
998 return static_cast<word>(a.ptr());
999}
1000#endif // defined(TARGET_ARCH_IA32)
1001
1002word RegExp::function_offset(classid_t cid, bool sticky) {
1003#if !defined(DART_COMPRESSED_POINTERS)
1005#else
1006 // TODO(rmacnak): TranslateOffsetInWords doesn't account for, say, header
1007 // being 1 word and slots being half words.
1008 return dart::RegExp::function_offset(cid, sticky);
1009#endif
1010}
1011
1012const word Symbols::kNumberOfOneCharCodeSymbols =
1014const word Symbols::kNullCharCodeSymbolOffset =
1016
1017const word String::kHashBits = dart::String::kHashBits;
1018
1019const uint8_t Nullability::kNullable =
1020 static_cast<uint8_t>(dart::Nullability::kNullable);
1021const uint8_t Nullability::kNonNullable =
1022 static_cast<uint8_t>(dart::Nullability::kNonNullable);
1023const uint8_t Nullability::kLegacy =
1024 static_cast<uint8_t>(dart::Nullability::kLegacy);
1025
1026bool Heap::IsAllocatableInNewSpace(intptr_t instance_size) {
1027 return dart::IsAllocatableInNewSpace(instance_size);
1028}
1029
1030word Field::OffsetOf(const dart::Field& field) {
1031 return field.TargetOffset();
1032}
1033
1034word FieldTable::OffsetOf(const dart::Field& field) {
1037}
1038
1042
1046
1047word Instance::NextFieldOffset() {
1049}
1050
1051intptr_t Array::index_at_offset(intptr_t offset_in_bytes) {
1053 TranslateOffsetInWordsToHost(offset_in_bytes));
1054}
1055
1056intptr_t Record::field_index_at_offset(intptr_t offset_in_bytes) {
1058 TranslateOffsetInWordsToHost(offset_in_bytes));
1059}
1060
1061word String::InstanceSize(word payload_size) {
1062 return RoundedAllocationSize(String::InstanceSize() + payload_size);
1063}
1064
1065word LocalVarDescriptors::InstanceSize() {
1066 return 0;
1067}
1068
1069word Integer::NextFieldOffset() {
1070 return TranslateOffsetInWords(dart::Integer::NextFieldOffset());
1071}
1072
1073word Smi::InstanceSize() {
1074 return 0;
1075}
1076
1077word Number::NextFieldOffset() {
1078 return TranslateOffsetInWords(dart::Number::NextFieldOffset());
1079}
1080
1082 const dart::AbstractType& type) {
1083 if (field.is_static() || field.is_late()) {
1084 return;
1085 }
1086
1087 if (type.IsNullable()) {
1088 return;
1089 }
1090
1092 if (type.IsDoubleType()) {
1094 cid = kDoubleCid;
1095 }
1096 } else if (type.IsFloat32x4Type()) {
1098 cid = kFloat32x4Cid;
1099 }
1100 } else if (type.IsFloat64x2Type()) {
1102 cid = kFloat64x2Cid;
1103 }
1104 }
1105
1106 if (cid != kIllegalCid) {
1107 field.set_guarded_cid(cid);
1108 field.set_is_nullable(false);
1109 field.set_is_unboxed(true);
1113 }
1114}
1115
1116} // namespace target
1117} // namespace compiler
1118} // namespace dart
1119
1120#else
1121
1122namespace dart {
1123namespace compiler {
1124namespace target {
1125
1126const word Array::kMaxElements = Array_kMaxElements;
1127const word Context::kMaxElements = Context_kMaxElements;
1128const word Record::kMaxElements = Record_kMaxElements;
1129
1130const word RecordShape::kNumFieldsMask = RecordShape_kNumFieldsMask;
1131const word RecordShape::kMaxNumFields = RecordShape_kMaxNumFields;
1132const word RecordShape::kFieldNamesIndexShift =
1133 RecordShape_kFieldNamesIndexShift;
1134const word RecordShape::kFieldNamesIndexMask = RecordShape_kFieldNamesIndexMask;
1135const word RecordShape::kMaxFieldNamesIndex = RecordShape_kMaxFieldNamesIndex;
1136
1137} // namespace target
1138} // namespace compiler
1139} // namespace dart
1140
1141#endif // !defined(DART_PRECOMPILED_RUNTIME)
#define RELEASE_ASSERT(cond)
Definition assert.h:327
#define CLASS_LIST_FOR_HANDLES(V)
Definition class_id.h:193
#define CLASS_LIST_FFI_TYPE_MARKER(V)
Definition class_id.h:165
#define CLASS_LIST_TYPED_DATA(V)
Definition class_id.h:137
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 intptr_t index_at_offset(intptr_t offset_in_bytes)
Definition object.h:10821
static constexpr bool UseCardMarkingForAllocation(const intptr_t array_length)
Definition object.h:10797
static constexpr bool IsValidLength(intptr_t len)
Definition object.h:10906
static const Bool & False()
Definition object.h:10778
static const Bool & True()
Definition object.h:10776
bool TraceAllocation(IsolateGroup *isolate_group) const
Definition object.cc:4489
intptr_t target_type_arguments_field_offset() const
Definition object.h:1386
intptr_t id() const
Definition object.h:1235
intptr_t target_instance_size() const
Definition object.h:1149
intptr_t NumTypeArguments() const
Definition object.cc:3690
intptr_t host_type_arguments_field_offset() const
Definition object.h:1377
bool HasCompressedPointers() const
Definition object.cc:3007
static constexpr intptr_t kNoTypeArguments
Definition object.h:1376
static uword EntryPointOf(const CodePtr code)
Definition object.h:6838
static bool IsValidLength(intptr_t len)
Definition object.h:7415
static intptr_t InstanceSize()
Definition object.h:7419
static intptr_t FieldOffsetFor(intptr_t field_id)
void set_is_unboxed(bool b) const
Definition object.h:4693
@ kUnknownLengthOffset
Definition object.h:4700
@ kNoFixedLength
Definition object.h:4702
intptr_t TargetOffset() const
Definition object.h:13220
bool is_late() const
Definition object.h:4422
bool is_static() const
Definition object.h:4418
void set_guarded_cid(intptr_t cid) const
Definition object.h:4633
void set_guarded_list_length_in_object_offset(intptr_t offset) const
Definition object.h:4661
intptr_t field_id() const
Definition object.h:13258
void set_is_nullable(bool val) const
Definition object.h:4726
void set_guarded_list_length(intptr_t list_length) const
Definition object.h:4651
static bool SupportsUnboxedDoubles()
static bool SupportsUnboxedSimd128()
@ kOld
Definition heap.h:39
static intptr_t ExactnessIndexFor(intptr_t num_args)
Definition object.h:2735
static intptr_t CodeIndexFor(intptr_t num_args)
Definition object.h:2733
static intptr_t TargetIndexFor(intptr_t num_args)
Definition object.h:2732
static intptr_t CountIndexFor(intptr_t num_args)
Definition object.h:2729
static intptr_t TestEntryLengthFor(intptr_t num_args, bool tracking_exactness)
Definition object.cc:16610
static intptr_t EntryPointIndexFor(intptr_t num_args)
Definition object.h:2730
static intptr_t NextFieldOffset()
Definition object.h:8326
static intptr_t NativeFieldsOffset()
Definition object.h:8328
Random * random()
Definition isolate.h:410
ObjectStore * object_store() const
Definition isolate.h:505
static IsolateGroup * Current()
Definition isolate.h:534
static LibraryPtr ConvertLibrary()
Definition object.cc:14830
static LibraryPtr MathLibrary()
Definition object.cc:14858
DART_NORETURN void Jump(int value, const Error &error)
Definition longjump.cc:22
static constexpr intptr_t kSpreadFactor
Definition object.h:7571
static ObjectPtr null()
Definition object.h:433
intptr_t GetClassId() const
Definition object.h:341
ObjectPtr ptr() const
Definition object.h:332
bool InVMIsolateHeap() const
Definition object.h:395
static bool ShouldHaveImmutabilityBitSet(classid_t class_id)
Definition object.cc:2689
bool IsOld() const
Definition object.h:391
virtual const char * ToCString() const
Definition object.h:366
bool IsNull() const
Definition object.h:363
static Object & Handle()
Definition object.h:407
static Object & ZoneHandle()
Definition object.h:419
static constexpr intptr_t kHashBits
Definition object.h:323
static constexpr intptr_t kBytesPerElement
Definition object.h:10521
uint32_t NextUInt32()
Definition random.cc:73
static intptr_t field_index_at_offset(intptr_t offset_in_bytes)
Definition object.h:11426
static intptr_t function_offset(intptr_t cid, bool sticky)
Definition object.h:12789
intptr_t argument_count() const
bool is_leaf() const
static intptr_t RawValue(intptr_t value)
Definition object.h:10001
static StringPtr New(const char *cstr, Heap::Space space=Heap::kNew)
Definition object.cc:23777
static constexpr int kNumberOfOneCharCodeSymbols
Definition symbols.h:600
static constexpr int kNullCharCodeSymbolOffset
Definition symbols.h:604
static StringPtr * PredefinedAddress()
Definition symbols.h:771
LongJumpScope * long_jump_base() const
static uword full_safepoint_state_unacquired()
Definition thread.h:1047
static intptr_t OffsetFromThread(const Object &object)
Definition thread.cc:1112
static Thread * Current()
Definition thread.h:361
@ kExitThroughRuntimeCall
Definition thread.h:471
@ kExitThroughFfi
Definition thread.h:468
static bool CanLoadFromThread(const Object &object)
Definition thread.cc:1088
static uword full_safepoint_state_acquired()
Definition thread.h:1051
@ kThreadInNative
Definition thread.h:1023
@ kThreadInGenerated
Definition thread.h:1022
static constexpr intptr_t kBytesPerElement
Definition object.h:10662
static TypePtr ObjectType()
Definition object.cc:21878
static TypePtr IntType()
Definition object.cc:21886
intptr_t ElementSizeInBytes() const
Definition object.h:11505
static constexpr intptr_t kNullabilityMask
static constexpr intptr_t kTypeStateBits
static constexpr intptr_t kTypeStateShift
static constexpr intptr_t kMaxSizeTagInUnitsOfAlignment
Definition raw_object.h:196
static constexpr bool SizeFits(intptr_t size)
Definition raw_object.h:213
static constexpr uword encode(intptr_t size)
Definition raw_object.h:201
static constexpr intptr_t kIncrementalBarrierMask
Definition raw_object.h:181
static constexpr intptr_t kGenerationalBarrierMask
Definition raw_object.h:180
static constexpr intptr_t kBarrierOverlapShift
Definition raw_object.h:182
static constexpr intptr_t kIsFunctionTypeParameterBit
static constexpr intptr_t kTypeClassIdShift
static bool IsInt(intptr_t N, T value)
Definition utils.h:298
static constexpr T RoundUp(T x, uintptr_t alignment, uintptr_t offset=0)
Definition utils.h:105
static constexpr bool IsAligned(T x, uintptr_t alignment, uintptr_t offset=0)
Definition utils.h:77
intptr_t argument_count() const
#define DO(type, attrs)
#define UNIMPLEMENTED
#define ASSERT(E)
static bool b
struct MyStruct a[10]
#define FATAL(error)
static const uint8_t buffer[]
uint8_t value
uint32_t * target
size_t length
static word TranslateOffsetInWords(word offset)
uword MakeTagWordForNewSpaceObject(classid_t cid, uword instance_size)
bool WillAllocateNewOrRememberedContext(intptr_t num_context_variables)
static uword GetInstanceSizeImpl(const dart::Class &handle)
static word TranslateOffsetInWordsToHost(word offset)
void UnboxFieldIfSupported(const dart::Field &field, const dart::AbstractType &type)
bool CanLoadFromThread(const dart::Object &object, intptr_t *offset)
bool WillAllocateNewOrRememberedArray(intptr_t length)
bool IsTypedDataClassId(intptr_t cid)
double DoubleValue(const dart::Object &a)
word ToRawSmi(const dart::Object &a)
bool IsDouble(const dart::Object &a)
bool IsSmi(int64_t v)
bool SizeFitsInSizeTag(uword instance_size)
bool WillAllocateNewOrRememberedObject(intptr_t instance_size)
word SmiValue(const dart::Object &a)
static DART_FORCE_INLINE bool BareInstructionsPayloads()
const Type & ObjectType()
void BailoutWithBranchOffsetError()
const Field & LookupConvertUtf8DecoderScanFlagsField()
const Class & Int32x4Class()
Object & NewZoneHandle(Zone *zone)
static constexpr intptr_t kHostWordSize
Definition runtime_api.h:90
const Class & Float64x2Class()
bool IsBoolType(const AbstractType &type)
const Type & VoidType()
word LookupFieldOffsetInBytes(const Field &field)
word TypedDataMaxNewSpaceElements(classid_t cid)
const Class & GrowableObjectArrayClass()
const Type & IntType()
const Class & Float32x4Class()
intptr_t ObjectHash(const Object &obj)
word TypedDataElementSizeInBytes(classid_t cid)
bool IsOriginalObject(const Object &object)
int32_t CreateJitCookie()
void SetToNull(Object *obj)
const String & AllocateString(const char *buffer)
const Array & ArgumentsDescriptorBoxed(intptr_t type_args_len, intptr_t num_arguments)
const Code & StubCodeSubtype2TestCache()
const Bool & TrueObject()
bool IsDoubleType(const AbstractType &type)
const Code & StubCodeSubtype6TestCache()
const Code & StubCodeSubtype7TestCache()
const Code & StubCodeSubtype3TestCache()
bool IsInOldSpace(const Object &obj)
const Object & SentinelObject()
bool IsEqualType(const AbstractType &a, const AbstractType &b)
bool IsSubtypeOfInt(const AbstractType &type)
bool IsSameObject(const Object &a, const Object &b)
const Class & ClosureClass()
const Bool & FalseObject()
const Object & NullObject()
const Class & DoubleClass()
InvalidClass kSmiBits
const Field & LookupMathRandomStateFieldOffset()
const Object & EmptyTypeArguments()
bool IsSmiType(const AbstractType &type)
const char * ObjectToCString(const Object &obj)
const Code & StubCodeAllocateArray()
const Class & MintClass()
const Code & StubCodeSubtype4TestCache()
bool HasIntegerValue(const dart::Object &object, int64_t *value)
const Type & DynamicType()
static constexpr intptr_t kNullIdentityHash
Definition object.h:10763
bool IsTypedDataViewClassId(intptr_t index)
Definition class_id.h:439
bool IsTypedDataClassId(intptr_t index)
Definition class_id.h:433
const intptr_t kSmiBits
Definition globals.h:24
static constexpr intptr_t kPageSize
Definition page.h:27
int32_t classid_t
Definition globals.h:524
bool IsUnmodifiableTypedDataViewClassId(intptr_t index)
Definition class_id.h:453
@ kIllegalCid
Definition class_id.h:214
@ kNumPredefinedCids
Definition class_id.h:257
@ kByteDataViewCid
Definition class_id.h:244
@ kByteBufferCid
Definition class_id.h:247
@ kUnmodifiableByteDataViewCid
Definition class_id.h:245
intptr_t compressed_word
Definition globals.h:45
uintptr_t uword
Definition globals.h:501
intptr_t word
Definition globals.h:500
bool IsAllocatableInNewSpace(intptr_t size)
Definition spaces.h:57
const intptr_t cid
static constexpr intptr_t kCompressedWordSize
Definition globals.h:42
constexpr intptr_t kWordSize
Definition globals.h:509
static constexpr intptr_t kPageMask
Definition page.h:29
static constexpr intptr_t kNewAllocatableSize
Definition spaces.h:54
bool IsExternalTypedDataClassId(intptr_t index)
Definition class_id.h:447
#define Pd
Definition globals.h:408
#define DEFINE_JIT_SIZEOF(clazz, name, what)
#define DEFINE_ARRAY(clazz, name)
#define DEFINE_CONSTANT(Class, Name)
#define DEFINE_ALIAS(name)
#define DEFINE_AOT_FIELD(clazz, name)
#define DEFINE_FIELD(clazz, name)
#define HANDLE_CASE(clazz)
#define DEFINE_JIT_RANGE(Class, Getter, Type, First, Last, Filter)
#define DEFINE_JIT_ARRAY(clazz, name)
#define DEFINE_RANGE(Class, Getter, Type, First, Last, Filter)
#define DEFINE_JIT_FIELD(clazz, name)
#define DEFINE_SIZEOF(clazz, name, what)
#define RUNTIME_ENTRY_LIST(V)
#define LEAF_RUNTIME_ENTRY_LIST(V)
#define JIT_OFFSETS_LIST(FIELD, ARRAY, SIZEOF, ARRAY_SIZEOF, PAYLOAD_SIZEOF, RANGE, CONSTANT)
#define AOT_OFFSETS_LIST(FIELD, ARRAY, SIZEOF, ARRAY_SIZEOF, PAYLOAD_SIZEOF, RANGE, CONSTANT)
#define COMMON_OFFSETS_LIST(FIELD, ARRAY, SIZEOF, ARRAY_SIZEOF, PAYLOAD_SIZEOF, RANGE, CONSTANT)
Point offset
static constexpr intptr_t kObjectAlignment