Line data Source code
1 : // Copyright 2017 the V8 project authors. All rights reserved.
2 : // Use of this source code is governed by a BSD-style license that can be
3 : // found in the LICENSE file.
4 :
5 : #ifndef V8_OBJECTS_SHARED_FUNCTION_INFO_INL_H_
6 : #define V8_OBJECTS_SHARED_FUNCTION_INFO_INL_H_
7 :
8 : #include "src/objects/shared-function-info.h"
9 :
10 : #include "src/ast/ast.h"
11 : #include "src/feedback-vector-inl.h"
12 : #include "src/handles-inl.h"
13 : #include "src/heap/heap-write-barrier-inl.h"
14 : #include "src/objects/debug-objects-inl.h"
15 : #include "src/objects/scope-info.h"
16 : #include "src/objects/templates.h"
17 : #include "src/wasm/wasm-objects-inl.h"
18 :
19 : // Has to be the last include (doesn't have include guards):
20 : #include "src/objects/object-macros.h"
21 :
22 : namespace v8 {
23 : namespace internal {
24 :
25 575728 : OBJECT_CONSTRUCTORS_IMPL(PreparseData, HeapObject)
26 :
27 287898 : CAST_ACCESSOR(PreparseData)
28 676974 : INT_ACCESSORS(PreparseData, data_length, kDataLengthOffset)
29 381409 : INT_ACCESSORS(PreparseData, children_length, kInnerLengthOffset)
30 :
31 : int PreparseData::inner_start_offset() const {
32 : return InnerOffset(data_length());
33 : }
34 :
35 : ObjectSlot PreparseData::inner_data_start() const {
36 : return RawField(inner_start_offset());
37 : }
38 :
39 63198 : void PreparseData::clear_padding() {
40 63198 : int data_end_offset = kDataStartOffset + data_length();
41 63198 : int padding_size = inner_start_offset() - data_end_offset;
42 : DCHECK_LE(0, padding_size);
43 126396 : if (padding_size == 0) return;
44 111978 : memset(reinterpret_cast<void*>(address() + data_end_offset), 0, padding_size);
45 : }
46 :
47 : byte PreparseData::get(int index) const {
48 : DCHECK_LE(0, index);
49 : DCHECK_LT(index, data_length());
50 576048 : int offset = kDataStartOffset + index * kByteSize;
51 576048 : return READ_BYTE_FIELD(*this, offset);
52 : }
53 :
54 : void PreparseData::set(int index, byte value) {
55 : DCHECK_LE(0, index);
56 : DCHECK_LT(index, data_length());
57 : int offset = kDataStartOffset + index * kByteSize;
58 : WRITE_BYTE_FIELD(*this, offset, value);
59 : }
60 :
61 : void PreparseData::copy_in(int index, const byte* buffer, int length) {
62 : DCHECK(index >= 0 && length >= 0 && length <= kMaxInt - index &&
63 : index + length <= this->data_length());
64 63198 : Address dst_addr = FIELD_ADDR(*this, kDataStartOffset + index * kByteSize);
65 63198 : memcpy(reinterpret_cast<void*>(dst_addr), buffer, length);
66 : }
67 :
68 3187 : PreparseData PreparseData::get_child(int index) const {
69 6374 : return PreparseData::cast(get_child_raw(index));
70 : }
71 :
72 3187 : Object PreparseData::get_child_raw(int index) const {
73 : DCHECK_LE(0, index);
74 : DCHECK_LT(index, this->children_length());
75 3187 : int offset = inner_start_offset() + index * kTaggedSize;
76 6374 : return RELAXED_READ_FIELD(*this, offset);
77 : }
78 :
79 6798 : void PreparseData::set_child(int index, PreparseData value,
80 : WriteBarrierMode mode) {
81 : DCHECK_LE(0, index);
82 : DCHECK_LT(index, this->children_length());
83 6798 : int offset = inner_start_offset() + index * kTaggedSize;
84 6798 : RELAXED_WRITE_FIELD(*this, offset, value);
85 20394 : CONDITIONAL_WRITE_BARRIER(*this, offset, value, mode);
86 6798 : }
87 :
88 14312422 : OBJECT_CONSTRUCTORS_IMPL(UncompiledData, HeapObject)
89 24501762 : OBJECT_CONSTRUCTORS_IMPL(UncompiledDataWithoutPreparseData, UncompiledData)
90 298104 : OBJECT_CONSTRUCTORS_IMPL(UncompiledDataWithPreparseData, UncompiledData)
91 7156208 : CAST_ACCESSOR(UncompiledData)
92 14512798 : ACCESSORS(UncompiledData, inferred_name, String, kInferredNameOffset)
93 5020470 : INT32_ACCESSORS(UncompiledData, start_position, kStartPositionOffset)
94 3978977 : INT32_ACCESSORS(UncompiledData, end_position, kEndPositionOffset)
95 3374984 : INT32_ACCESSORS(UncompiledData, function_literal_id, kFunctionLiteralIdOffset)
96 :
97 2177979 : void UncompiledData::clear_padding() {
98 2177979 : if (FIELD_SIZE(kOptionalPaddingOffset) == 0) return;
99 : DCHECK_EQ(4, FIELD_SIZE(kOptionalPaddingOffset));
100 2177979 : memset(reinterpret_cast<void*>(address() + kOptionalPaddingOffset), 0,
101 2177979 : FIELD_SIZE(kOptionalPaddingOffset));
102 : }
103 :
104 12252054 : CAST_ACCESSOR(UncompiledDataWithoutPreparseData)
105 :
106 149052 : CAST_ACCESSOR(UncompiledDataWithPreparseData)
107 405627 : ACCESSORS(UncompiledDataWithPreparseData, preparse_data, PreparseData,
108 : kPreparseDataOffset)
109 :
110 : bool HeapObject::IsUncompiledData() const {
111 119390038 : return IsUncompiledDataWithoutPreparseData() ||
112 : IsUncompiledDataWithPreparseData();
113 : }
114 :
115 348 : OBJECT_CONSTRUCTORS_IMPL(InterpreterData, Struct)
116 :
117 174 : CAST_ACCESSOR(InterpreterData)
118 436 : ACCESSORS(InterpreterData, bytecode_array, BytecodeArray, kBytecodeArrayOffset)
119 331 : ACCESSORS(InterpreterData, interpreter_trampoline, Code,
120 : kInterpreterTrampolineOffset)
121 :
122 718284394 : OBJECT_CONSTRUCTORS_IMPL(SharedFunctionInfo, HeapObject)
123 : NEVER_READ_ONLY_SPACE_IMPL(SharedFunctionInfo)
124 359298287 : CAST_ACCESSOR(SharedFunctionInfo)
125 456574 : DEFINE_DEOPT_ELEMENT_ACCESSORS(SharedFunctionInfo, Object)
126 :
127 100686203 : ACCESSORS(SharedFunctionInfo, name_or_scope_info, Object,
128 : kNameOrScopeInfoOffset)
129 139063972 : ACCESSORS(SharedFunctionInfo, script_or_debug_info, Object,
130 : kScriptOrDebugInfoOffset)
131 :
132 19902298 : UINT16_ACCESSORS(SharedFunctionInfo, length, kLengthOffset)
133 32792086 : UINT16_ACCESSORS(SharedFunctionInfo, internal_formal_parameter_count,
134 : kFormalParameterCountOffset)
135 12435242 : UINT8_ACCESSORS(SharedFunctionInfo, expected_nof_properties,
136 : kExpectedNofPropertiesOffset)
137 21999449 : UINT8_ACCESSORS(SharedFunctionInfo, raw_builtin_function_id,
138 : kBuiltinFunctionIdOffset)
139 13423708 : UINT16_ACCESSORS(SharedFunctionInfo, raw_function_token_offset,
140 : kFunctionTokenOffsetOffset)
141 426612631 : RELAXED_INT32_ACCESSORS(SharedFunctionInfo, flags, kFlagsOffset)
142 :
143 25835734 : bool SharedFunctionInfo::HasSharedName() const {
144 25835734 : Object value = name_or_scope_info();
145 25835735 : if (value->IsScopeInfo()) {
146 3173132 : return ScopeInfo::cast(value)->HasSharedFunctionName();
147 : }
148 22662603 : return value != kNoSharedNameSentinel;
149 : }
150 :
151 9710887 : String SharedFunctionInfo::Name() const {
152 9722264 : if (!HasSharedName()) return GetReadOnlyRoots().empty_string();
153 9699513 : Object value = name_or_scope_info();
154 9699516 : if (value->IsScopeInfo()) {
155 3103465 : if (ScopeInfo::cast(value)->HasFunctionName()) {
156 6206932 : return String::cast(ScopeInfo::cast(value)->FunctionName());
157 : }
158 0 : return GetReadOnlyRoots().empty_string();
159 : }
160 : return String::cast(value);
161 : }
162 :
163 640 : void SharedFunctionInfo::SetName(String name) {
164 640 : Object maybe_scope_info = name_or_scope_info();
165 640 : if (maybe_scope_info->IsScopeInfo()) {
166 5 : ScopeInfo::cast(maybe_scope_info)->SetFunctionName(name);
167 : } else {
168 : DCHECK(maybe_scope_info->IsString() ||
169 : maybe_scope_info == kNoSharedNameSentinel);
170 635 : set_name_or_scope_info(name);
171 : }
172 640 : UpdateFunctionMapIndex();
173 640 : }
174 :
175 3617444 : AbstractCode SharedFunctionInfo::abstract_code() {
176 3617444 : if (HasBytecodeArray()) {
177 5280600 : return AbstractCode::cast(GetBytecodeArray());
178 : } else {
179 1954288 : return AbstractCode::cast(GetCode());
180 : }
181 : }
182 :
183 : Object SharedFunctionInfo::function_data() const {
184 381776016 : return ACQUIRE_READ_FIELD(*this, kFunctionDataOffset);
185 : }
186 :
187 12343302 : void SharedFunctionInfo::set_function_data(Object data, WriteBarrierMode mode) {
188 12343302 : RELEASE_WRITE_FIELD(*this, kFunctionDataOffset, data);
189 28413272 : CONDITIONAL_WRITE_BARRIER(*this, kFunctionDataOffset, data, mode);
190 12343311 : }
191 :
192 1786877 : int SharedFunctionInfo::function_token_position() const {
193 1786877 : int offset = raw_function_token_offset();
194 1786877 : if (offset == kFunctionTokenOutOfRange) {
195 : return kNoSourcePosition;
196 : } else {
197 1786805 : return StartPosition() - offset;
198 : }
199 : }
200 :
201 28880830 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_wrapped,
202 : SharedFunctionInfo::IsWrappedBit)
203 136672746 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, allows_lazy_compilation,
204 : SharedFunctionInfo::AllowLazyCompilationBit)
205 20961632 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, has_duplicate_parameters,
206 : SharedFunctionInfo::HasDuplicateParametersBit)
207 8570536 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_declaration,
208 : SharedFunctionInfo::IsDeclarationBit)
209 :
210 1333342 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, native,
211 : SharedFunctionInfo::IsNativeBit)
212 1417128 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_asm_wasm_broken,
213 : SharedFunctionInfo::IsAsmWasmBrokenBit)
214 8570542 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags,
215 : requires_instance_members_initializer,
216 : SharedFunctionInfo::RequiresInstanceMembersInitializer)
217 :
218 2428954 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, name_should_print_as_anonymous,
219 : SharedFunctionInfo::NameShouldPrintAsAnonymousBit)
220 7153756 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_anonymous_expression,
221 : SharedFunctionInfo::IsAnonymousExpressionBit)
222 32416 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, has_reported_binary_coverage,
223 : SharedFunctionInfo::HasReportedBinaryCoverageBit)
224 :
225 8570536 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_named_expression,
226 : SharedFunctionInfo::IsNamedExpressionBit)
227 35177756 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_toplevel,
228 : SharedFunctionInfo::IsTopLevelBit)
229 4131916 : BIT_FIELD_ACCESSORS(SharedFunctionInfo, flags, is_oneshot_iife,
230 : SharedFunctionInfo::IsOneshotIIFEBit)
231 :
232 2122173 : bool SharedFunctionInfo::optimization_disabled() const {
233 2122173 : return disable_optimization_reason() != BailoutReason::kNoReason;
234 : }
235 :
236 12045 : BailoutReason SharedFunctionInfo::disable_optimization_reason() const {
237 12045 : return DisabledOptimizationReasonBits::decode(flags());
238 : }
239 :
240 29244578 : LanguageMode SharedFunctionInfo::language_mode() const {
241 : STATIC_ASSERT(LanguageModeSize == 2);
242 29244578 : return construct_language_mode(IsStrictBit::decode(flags()));
243 : }
244 :
245 4304739 : void SharedFunctionInfo::set_language_mode(LanguageMode language_mode) {
246 : STATIC_ASSERT(LanguageModeSize == 2);
247 : // We only allow language mode transitions that set the same language mode
248 : // again or go up in the chain:
249 : DCHECK(is_sloppy(this->language_mode()) || is_strict(language_mode));
250 : int hints = flags();
251 : hints = IsStrictBit::update(hints, is_strict(language_mode));
252 : set_flags(hints);
253 4304739 : UpdateFunctionMapIndex();
254 4304739 : }
255 :
256 21910 : FunctionKind SharedFunctionInfo::kind() const {
257 21910 : return FunctionKindBits::decode(flags());
258 : }
259 :
260 8058815 : void SharedFunctionInfo::set_kind(FunctionKind kind) {
261 : int hints = flags();
262 : hints = FunctionKindBits::update(hints, kind);
263 : hints = IsClassConstructorBit::update(hints, IsClassConstructor(kind));
264 : hints = IsDerivedConstructorBit::update(hints, IsDerivedConstructor(kind));
265 : set_flags(hints);
266 8058815 : UpdateFunctionMapIndex();
267 8058816 : }
268 :
269 16419364 : bool SharedFunctionInfo::needs_home_object() const {
270 16419364 : return NeedsHomeObjectBit::decode(flags());
271 : }
272 :
273 3576879 : void SharedFunctionInfo::set_needs_home_object(bool value) {
274 : int hints = flags();
275 : hints = NeedsHomeObjectBit::update(hints, value);
276 : set_flags(hints);
277 3576879 : UpdateFunctionMapIndex();
278 3576879 : }
279 :
280 6911557 : bool SharedFunctionInfo::construct_as_builtin() const {
281 6911557 : return ConstructAsBuiltinBit::decode(flags());
282 : }
283 :
284 8058812 : void SharedFunctionInfo::CalculateConstructAsBuiltin() {
285 : bool uses_builtins_construct_stub = false;
286 8058812 : if (HasBuiltinId()) {
287 4308314 : int id = builtin_id();
288 4308318 : if (id != Builtins::kCompileLazy && id != Builtins::kEmptyFunction) {
289 : uses_builtins_construct_stub = true;
290 : }
291 3750498 : } else if (IsApiFunction()) {
292 : uses_builtins_construct_stub = true;
293 : }
294 :
295 : int f = flags();
296 : f = ConstructAsBuiltinBit::update(f, uses_builtins_construct_stub);
297 : set_flags(f);
298 8058816 : }
299 :
300 20003648 : int SharedFunctionInfo::function_map_index() const {
301 : // Note: Must be kept in sync with the FastNewClosure builtin.
302 : int index =
303 20003648 : Context::FIRST_FUNCTION_MAP_INDEX + FunctionMapIndexBits::decode(flags());
304 : DCHECK_LE(index, Context::LAST_FUNCTION_MAP_INDEX);
305 20003648 : return index;
306 : }
307 :
308 15941298 : void SharedFunctionInfo::set_function_map_index(int index) {
309 : STATIC_ASSERT(Context::LAST_FUNCTION_MAP_INDEX <=
310 : Context::FIRST_FUNCTION_MAP_INDEX + FunctionMapIndexBits::kMax);
311 : DCHECK_LE(Context::FIRST_FUNCTION_MAP_INDEX, index);
312 : DCHECK_LE(index, Context::LAST_FUNCTION_MAP_INDEX);
313 15941298 : index -= Context::FIRST_FUNCTION_MAP_INDEX;
314 : set_flags(FunctionMapIndexBits::update(flags(), index));
315 15941298 : }
316 :
317 8058816 : void SharedFunctionInfo::clear_padding() {
318 8058816 : memset(reinterpret_cast<void*>(this->address() + kSize), 0,
319 8058816 : kAlignedSize - kSize);
320 8058816 : }
321 :
322 15941071 : void SharedFunctionInfo::UpdateFunctionMapIndex() {
323 : int map_index = Context::FunctionMapIndex(
324 31882146 : language_mode(), kind(), HasSharedName(), needs_home_object());
325 15941074 : set_function_map_index(map_index);
326 15941073 : }
327 :
328 : void SharedFunctionInfo::DontAdaptArguments() {
329 : // TODO(leszeks): Revise this DCHECK now that the code field is gone.
330 : DCHECK(!HasWasmExportedFunctionData());
331 : set_internal_formal_parameter_count(kDontAdaptArgumentsSentinel);
332 : }
333 :
334 646541 : bool SharedFunctionInfo::IsInterpreted() const { return HasBytecodeArray(); }
335 :
336 4176502 : ScopeInfo SharedFunctionInfo::scope_info() const {
337 4176502 : Object maybe_scope_info = name_or_scope_info();
338 4176504 : if (maybe_scope_info->IsScopeInfo()) {
339 : return ScopeInfo::cast(maybe_scope_info);
340 : }
341 3576893 : return ScopeInfo::Empty(GetIsolate());
342 : }
343 :
344 2066070 : void SharedFunctionInfo::set_scope_info(ScopeInfo scope_info,
345 : WriteBarrierMode mode) {
346 : // Move the existing name onto the ScopeInfo.
347 2066070 : Object name = name_or_scope_info();
348 2066076 : if (name->IsScopeInfo()) {
349 4369 : name = ScopeInfo::cast(name)->FunctionName();
350 : }
351 : DCHECK(name->IsString() || name == kNoSharedNameSentinel);
352 : // Only set the function name for function scopes.
353 2066076 : scope_info->SetFunctionName(name);
354 2623603 : if (HasInferredName() && inferred_name()->length() != 0) {
355 51837 : scope_info->SetInferredFunctionName(inferred_name());
356 : }
357 2066073 : WRITE_FIELD(*this, kNameOrScopeInfoOffset, scope_info);
358 6198217 : CONDITIONAL_WRITE_BARRIER(*this, kNameOrScopeInfoOffset, scope_info, mode);
359 2066072 : }
360 :
361 222271471 : ACCESSORS(SharedFunctionInfo, raw_outer_scope_info_or_feedback_metadata,
362 : HeapObject, kOuterScopeInfoOrFeedbackMetadataOffset)
363 :
364 : HeapObject SharedFunctionInfo::outer_scope_info() const {
365 : DCHECK(!is_compiled());
366 : DCHECK(!HasFeedbackMetadata());
367 1441848 : return raw_outer_scope_info_or_feedback_metadata();
368 : }
369 :
370 708389 : bool SharedFunctionInfo::HasOuterScopeInfo() const {
371 : ScopeInfo outer_info;
372 708389 : if (!is_compiled()) {
373 1200848 : if (!outer_scope_info()->IsScopeInfo()) return false;
374 : outer_info = ScopeInfo::cast(outer_scope_info());
375 : } else {
376 107967 : if (!scope_info()->HasOuterScopeInfo()) return false;
377 21521 : outer_info = scope_info()->OuterScopeInfo();
378 : }
379 451176 : return outer_info->length() > 0;
380 : }
381 :
382 433291 : ScopeInfo SharedFunctionInfo::GetOuterScopeInfo() const {
383 : DCHECK(HasOuterScopeInfo());
384 433291 : if (!is_compiled()) return ScopeInfo::cast(outer_scope_info());
385 21521 : return scope_info()->OuterScopeInfo();
386 : }
387 :
388 : void SharedFunctionInfo::set_outer_scope_info(HeapObject value,
389 : WriteBarrierMode mode) {
390 : DCHECK(!is_compiled());
391 : DCHECK(raw_outer_scope_info_or_feedback_metadata()->IsTheHole());
392 : DCHECK(value->IsScopeInfo() || value->IsTheHole());
393 2187389 : set_raw_outer_scope_info_or_feedback_metadata(value, mode);
394 : }
395 :
396 3064128 : bool SharedFunctionInfo::HasFeedbackMetadata() const {
397 6128259 : return raw_outer_scope_info_or_feedback_metadata()->IsFeedbackMetadata();
398 : }
399 :
400 53940828 : FeedbackMetadata SharedFunctionInfo::feedback_metadata() const {
401 : DCHECK(HasFeedbackMetadata());
402 107881652 : return FeedbackMetadata::cast(raw_outer_scope_info_or_feedback_metadata());
403 : }
404 :
405 : void SharedFunctionInfo::set_feedback_metadata(FeedbackMetadata value,
406 : WriteBarrierMode mode) {
407 : DCHECK(!HasFeedbackMetadata());
408 : DCHECK(value->IsFeedbackMetadata());
409 2065960 : set_raw_outer_scope_info_or_feedback_metadata(value, mode);
410 : }
411 :
412 116820335 : bool SharedFunctionInfo::is_compiled() const {
413 116820335 : Object data = function_data();
414 232068227 : return data != Smi::FromEnum(Builtins::kCompileLazy) &&
415 116823330 : !data->IsUncompiledData();
416 : }
417 :
418 21604248 : IsCompiledScope SharedFunctionInfo::is_compiled_scope() const {
419 21604253 : return IsCompiledScope(*this, GetIsolate());
420 : }
421 :
422 21604250 : IsCompiledScope::IsCompiledScope(const SharedFunctionInfo shared,
423 : Isolate* isolate)
424 21604250 : : retain_bytecode_(shared->HasBytecodeArray()
425 : ? handle(shared->GetBytecodeArray(), isolate)
426 : : MaybeHandle<BytecodeArray>()),
427 29456584 : is_compiled_(shared->is_compiled()) {
428 : DCHECK_IMPLIES(!retain_bytecode_.is_null(), is_compiled());
429 21604256 : }
430 :
431 : uint16_t SharedFunctionInfo::GetLength() const {
432 : DCHECK(is_compiled());
433 : DCHECK(HasLength());
434 : return length();
435 : }
436 :
437 : bool SharedFunctionInfo::HasLength() const {
438 : return length() != kInvalidLength;
439 : }
440 :
441 63608 : bool SharedFunctionInfo::has_simple_parameters() {
442 127216 : return scope_info()->HasSimpleParameters();
443 : }
444 :
445 32155064 : bool SharedFunctionInfo::IsApiFunction() const {
446 64310130 : return function_data()->IsFunctionTemplateInfo();
447 : }
448 :
449 5022063 : FunctionTemplateInfo SharedFunctionInfo::get_api_func_data() {
450 : DCHECK(IsApiFunction());
451 5022062 : return FunctionTemplateInfo::cast(function_data());
452 : }
453 :
454 49976897 : bool SharedFunctionInfo::HasBytecodeArray() const {
455 175171357 : return function_data()->IsBytecodeArray() ||
456 125194460 : function_data()->IsInterpreterData();
457 : }
458 :
459 18988245 : BytecodeArray SharedFunctionInfo::GetBytecodeArray() const {
460 : DCHECK(HasBytecodeArray());
461 18988245 : if (HasDebugInfo() && GetDebugInfo()->HasInstrumentedBytecodeArray()) {
462 268318 : return GetDebugInfo()->OriginalBytecodeArray();
463 37439870 : } else if (function_data()->IsBytecodeArray()) {
464 : return BytecodeArray::cast(function_data());
465 : } else {
466 : DCHECK(function_data()->IsInterpreterData());
467 87 : return InterpreterData::cast(function_data())->bytecode_array();
468 : }
469 : }
470 :
471 : BytecodeArray SharedFunctionInfo::GetDebugBytecodeArray() const {
472 : DCHECK(HasBytecodeArray());
473 : DCHECK(HasDebugInfo() && GetDebugInfo()->HasInstrumentedBytecodeArray());
474 : if (function_data()->IsBytecodeArray()) {
475 : return BytecodeArray::cast(function_data());
476 : } else {
477 : DCHECK(function_data()->IsInterpreterData());
478 : return InterpreterData::cast(function_data())->bytecode_array();
479 : }
480 : }
481 :
482 21154 : void SharedFunctionInfo::SetDebugBytecodeArray(BytecodeArray bytecode) {
483 : DCHECK(HasBytecodeArray());
484 42308 : if (function_data()->IsBytecodeArray()) {
485 21154 : set_function_data(bytecode);
486 : } else {
487 : DCHECK(function_data()->IsInterpreterData());
488 0 : interpreter_data()->set_bytecode_array(bytecode);
489 : }
490 21154 : }
491 :
492 : void SharedFunctionInfo::set_bytecode_array(BytecodeArray bytecode) {
493 : DCHECK(function_data() == Smi::FromEnum(Builtins::kCompileLazy) ||
494 : HasUncompiledData());
495 2063483 : set_function_data(bytecode);
496 : }
497 :
498 64001615 : bool SharedFunctionInfo::ShouldFlushBytecode() {
499 64001615 : if (!FLAG_flush_bytecode) return false;
500 :
501 : // TODO(rmcilroy): Enable bytecode flushing for resumable functions.
502 64007869 : if (IsResumableFunction(kind()) || !allows_lazy_compilation()) {
503 : return false;
504 : }
505 :
506 : // Get a snapshot of the function data field, and if it is a bytecode array,
507 : // check if it is old. Note, this is done this way since this function can be
508 : // called by the concurrent marker.
509 12115513 : Object data = function_data();
510 12144804 : if (!data->IsBytecodeArray()) return false;
511 :
512 1836023 : if (FLAG_stress_flush_bytecode) return true;
513 :
514 1835567 : BytecodeArray bytecode = BytecodeArray::cast(data);
515 :
516 1835567 : return bytecode->IsOld();
517 : }
518 :
519 : Code SharedFunctionInfo::InterpreterTrampoline() const {
520 : DCHECK(HasInterpreterData());
521 52 : return interpreter_data()->interpreter_trampoline();
522 : }
523 :
524 : bool SharedFunctionInfo::HasInterpreterData() const {
525 : return function_data()->IsInterpreterData();
526 : }
527 :
528 52 : InterpreterData SharedFunctionInfo::interpreter_data() const {
529 : DCHECK(HasInterpreterData());
530 52 : return InterpreterData::cast(function_data());
531 : }
532 :
533 : void SharedFunctionInfo::set_interpreter_data(
534 : InterpreterData interpreter_data) {
535 : DCHECK(FLAG_interpreted_frames_native_stack);
536 35 : set_function_data(interpreter_data);
537 : }
538 :
539 7576261 : bool SharedFunctionInfo::HasAsmWasmData() const {
540 15152524 : return function_data()->IsAsmWasmData();
541 : }
542 :
543 4962 : AsmWasmData SharedFunctionInfo::asm_wasm_data() const {
544 : DCHECK(HasAsmWasmData());
545 4962 : return AsmWasmData::cast(function_data());
546 : }
547 :
548 : void SharedFunctionInfo::set_asm_wasm_data(AsmWasmData data) {
549 : DCHECK(function_data() == Smi::FromEnum(Builtins::kCompileLazy) ||
550 : HasUncompiledData() || HasAsmWasmData());
551 2439 : set_function_data(data);
552 : }
553 :
554 23178867 : bool SharedFunctionInfo::HasBuiltinId() const {
555 46357730 : return function_data()->IsSmi();
556 : }
557 :
558 12520278 : int SharedFunctionInfo::builtin_id() const {
559 : DCHECK(HasBuiltinId());
560 12520278 : int id = Smi::ToInt(function_data());
561 : DCHECK(Builtins::IsBuiltinId(id));
562 12520279 : return id;
563 : }
564 :
565 : void SharedFunctionInfo::set_builtin_id(int builtin_id) {
566 : DCHECK(Builtins::IsBuiltinId(builtin_id));
567 4308320 : set_function_data(Smi::FromInt(builtin_id), SKIP_WRITE_BARRIER);
568 : }
569 :
570 10431089 : bool SharedFunctionInfo::HasUncompiledData() const {
571 20862182 : return function_data()->IsUncompiledData();
572 : }
573 :
574 7046910 : UncompiledData SharedFunctionInfo::uncompiled_data() const {
575 : DCHECK(HasUncompiledData());
576 7046915 : return UncompiledData::cast(function_data());
577 : }
578 :
579 : void SharedFunctionInfo::set_uncompiled_data(UncompiledData uncompiled_data) {
580 : DCHECK(function_data() == Smi::FromEnum(Builtins::kCompileLazy));
581 : DCHECK(uncompiled_data->IsUncompiledData());
582 2068470 : set_function_data(uncompiled_data);
583 : }
584 :
585 727566 : bool SharedFunctionInfo::HasUncompiledDataWithPreparseData() const {
586 1455133 : return function_data()->IsUncompiledDataWithPreparseData();
587 : }
588 :
589 : UncompiledDataWithPreparseData
590 36585 : SharedFunctionInfo::uncompiled_data_with_preparse_data() const {
591 : DCHECK(HasUncompiledDataWithPreparseData());
592 36585 : return UncompiledDataWithPreparseData::cast(function_data());
593 : }
594 :
595 : void SharedFunctionInfo::set_uncompiled_data_with_preparse_data(
596 : UncompiledDataWithPreparseData uncompiled_data_with_preparse_data) {
597 : DCHECK(function_data() == Smi::FromEnum(Builtins::kCompileLazy));
598 : DCHECK(
599 : uncompiled_data_with_preparse_data->IsUncompiledDataWithPreparseData());
600 : set_function_data(uncompiled_data_with_preparse_data);
601 : }
602 :
603 : bool SharedFunctionInfo::HasUncompiledDataWithoutPreparseData() const {
604 : return function_data()->IsUncompiledDataWithoutPreparseData();
605 : }
606 :
607 21 : void SharedFunctionInfo::ClearPreparseData() {
608 : DCHECK(HasUncompiledDataWithPreparseData());
609 21 : UncompiledDataWithPreparseData data = uncompiled_data_with_preparse_data();
610 :
611 : // Trim off the pre-parsed scope data from the uncompiled data by swapping the
612 : // map, leaving only an uncompiled data without pre-parsed scope.
613 : DisallowHeapAllocation no_gc;
614 21 : Heap* heap = GetHeapFromWritableObject(data);
615 :
616 : // Swap the map.
617 : heap->NotifyObjectLayoutChange(data, UncompiledDataWithPreparseData::kSize,
618 21 : no_gc);
619 : STATIC_ASSERT(UncompiledDataWithoutPreparseData::kSize <
620 : UncompiledDataWithPreparseData::kSize);
621 : STATIC_ASSERT(UncompiledDataWithoutPreparseData::kSize ==
622 : UncompiledData::kSize);
623 : data->synchronized_set_map(
624 42 : GetReadOnlyRoots().uncompiled_data_without_preparse_data_map());
625 :
626 : // Fill the remaining space with filler.
627 : heap->CreateFillerObjectAt(
628 : data->address() + UncompiledDataWithoutPreparseData::kSize,
629 : UncompiledDataWithPreparseData::kSize -
630 : UncompiledDataWithoutPreparseData::kSize,
631 21 : ClearRecordedSlots::kNo);
632 :
633 : // Ensure that the clear was successful.
634 : DCHECK(HasUncompiledDataWithoutPreparseData());
635 21 : }
636 :
637 : OBJECT_CONSTRUCTORS_IMPL(SharedFunctionInfoWithID, SharedFunctionInfo)
638 : CAST_ACCESSOR(SharedFunctionInfoWithID)
639 : INT_ACCESSORS(SharedFunctionInfoWithID, unique_id, kUniqueIdOffset)
640 :
641 : // static
642 2177980 : void UncompiledData::Initialize(
643 : UncompiledData data, String inferred_name, int start_position,
644 : int end_position, int function_literal_id,
645 : std::function<void(HeapObject object, ObjectSlot slot, HeapObject target)>
646 : gc_notify_updated_slot) {
647 2177980 : data->set_inferred_name(inferred_name);
648 : gc_notify_updated_slot(
649 2177979 : data, data->RawField(UncompiledData::kInferredNameOffset), inferred_name);
650 : data->set_start_position(start_position);
651 : data->set_end_position(end_position);
652 : data->set_function_literal_id(function_literal_id);
653 2177979 : data->clear_padding();
654 2177980 : }
655 :
656 59187 : void UncompiledDataWithPreparseData::Initialize(
657 : UncompiledDataWithPreparseData data, String inferred_name,
658 : int start_position, int end_position, int function_literal_id,
659 : PreparseData scope_data,
660 : std::function<void(HeapObject object, ObjectSlot slot, HeapObject target)>
661 : gc_notify_updated_slot) {
662 : UncompiledData::Initialize(data, inferred_name, start_position, end_position,
663 118374 : function_literal_id, gc_notify_updated_slot);
664 59187 : data->set_preparse_data(scope_data);
665 : gc_notify_updated_slot(
666 : data, data->RawField(UncompiledDataWithPreparseData::kPreparseDataOffset),
667 59187 : scope_data);
668 59187 : }
669 :
670 : bool UncompiledData::has_function_literal_id() {
671 : return function_literal_id() != FunctionLiteral::kIdTypeInvalid;
672 : }
673 :
674 : bool SharedFunctionInfo::HasWasmExportedFunctionData() const {
675 : return function_data()->IsWasmExportedFunctionData();
676 : }
677 :
678 61212716 : Object SharedFunctionInfo::script() const {
679 61212716 : Object maybe_script = script_or_debug_info();
680 61212720 : if (maybe_script->IsDebugInfo()) {
681 : return DebugInfo::cast(maybe_script)->script();
682 : }
683 58819302 : return maybe_script;
684 : }
685 :
686 3578146 : void SharedFunctionInfo::set_script(Object script) {
687 3578146 : Object maybe_debug_info = script_or_debug_info();
688 3578149 : if (maybe_debug_info->IsDebugInfo()) {
689 83 : DebugInfo::cast(maybe_debug_info)->set_script(script);
690 : } else {
691 3578066 : set_script_or_debug_info(script);
692 : }
693 3578149 : }
694 :
695 29258566 : bool SharedFunctionInfo::HasDebugInfo() const {
696 58517150 : return script_or_debug_info()->IsDebugInfo();
697 : }
698 :
699 2348596 : DebugInfo SharedFunctionInfo::GetDebugInfo() const {
700 : DCHECK(HasDebugInfo());
701 2348596 : return DebugInfo::cast(script_or_debug_info());
702 : }
703 :
704 : void SharedFunctionInfo::SetDebugInfo(DebugInfo debug_info) {
705 : DCHECK(!HasDebugInfo());
706 : DCHECK_EQ(debug_info->script(), script_or_debug_info());
707 28576 : set_script_or_debug_info(debug_info);
708 : }
709 :
710 : bool SharedFunctionInfo::HasBuiltinFunctionId() {
711 6906486 : return builtin_function_id() != BuiltinFunctionId::kInvalidBuiltinFunctionId;
712 : }
713 :
714 : BuiltinFunctionId SharedFunctionInfo::builtin_function_id() {
715 : return static_cast<BuiltinFunctionId>(raw_builtin_function_id());
716 : }
717 :
718 : void SharedFunctionInfo::set_builtin_function_id(BuiltinFunctionId id) {
719 : set_raw_builtin_function_id(static_cast<uint8_t>(id));
720 : }
721 :
722 2066066 : bool SharedFunctionInfo::HasInferredName() {
723 2066066 : Object scope_info = name_or_scope_info();
724 2066072 : if (scope_info->IsScopeInfo()) {
725 4369 : return ScopeInfo::cast(scope_info)->HasInferredFunctionName();
726 : }
727 2061703 : return HasUncompiledData();
728 : }
729 :
730 3370165 : String SharedFunctionInfo::inferred_name() {
731 3370165 : Object maybe_scope_info = name_or_scope_info();
732 3370168 : if (maybe_scope_info->IsScopeInfo()) {
733 1502394 : ScopeInfo scope_info = ScopeInfo::cast(maybe_scope_info);
734 1502394 : if (scope_info->HasInferredFunctionName()) {
735 733486 : Object name = ScopeInfo::cast(maybe_scope_info)->InferredFunctionName();
736 750607 : if (name->IsString()) return String::cast(name);
737 : }
738 1867774 : } else if (HasUncompiledData()) {
739 1204617 : return uncompiled_data()->inferred_name();
740 : }
741 4296862 : return GetReadOnlyRoots().empty_string();
742 : }
743 :
744 12031125 : bool SharedFunctionInfo::IsUserJavaScript() {
745 12031125 : Object script_obj = script();
746 12031129 : if (script_obj->IsUndefined()) return false;
747 9953672 : Script script = Script::cast(script_obj);
748 10061914 : return script->IsUserJavaScript();
749 : }
750 :
751 4576330 : bool SharedFunctionInfo::IsSubjectToDebugging() {
752 4576330 : return IsUserJavaScript() && !HasAsmWasmData();
753 : }
754 :
755 150511 : bool SharedFunctionInfo::CanDiscardCompiled() const {
756 300992 : bool can_decompile = (HasBytecodeArray() || HasAsmWasmData() ||
757 150481 : HasUncompiledDataWithPreparseData());
758 150511 : return can_decompile;
759 : }
760 :
761 : } // namespace internal
762 : } // namespace v8
763 :
764 : #include "src/objects/object-macros-undef.h"
765 :
766 : #endif // V8_OBJECTS_SHARED_FUNCTION_INFO_INL_H_
|