1 | // Copyright 2016 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_PARSING_PARSE_INFO_H_ |
6 | #define V8_PARSING_PARSE_INFO_H_ |
7 | |
8 | #include <map> |
9 | #include <memory> |
10 | #include <vector> |
11 | |
12 | #include "include/v8.h" |
13 | #include "src/function-kind.h" |
14 | #include "src/globals.h" |
15 | #include "src/handles.h" |
16 | #include "src/objects/script.h" |
17 | #include "src/parsing/preparse-data.h" |
18 | #include "src/pending-compilation-error-handler.h" |
19 | |
20 | namespace v8 { |
21 | |
22 | class Extension; |
23 | |
24 | namespace internal { |
25 | |
26 | class AccountingAllocator; |
27 | class AstRawString; |
28 | class AstStringConstants; |
29 | class AstValueFactory; |
30 | class CompilerDispatcher; |
31 | class DeclarationScope; |
32 | class FunctionLiteral; |
33 | class RuntimeCallStats; |
34 | class Logger; |
35 | class SourceRangeMap; |
36 | class Utf16CharacterStream; |
37 | class Zone; |
38 | |
39 | // A container for the inputs, configuration options, and outputs of parsing. |
40 | class V8_EXPORT_PRIVATE ParseInfo { |
41 | public: |
42 | explicit ParseInfo(AccountingAllocator* zone_allocator); |
43 | explicit ParseInfo(Isolate*); |
44 | ParseInfo(Isolate*, AccountingAllocator* zone_allocator); |
45 | ParseInfo(Isolate* isolate, Handle<Script> script); |
46 | ParseInfo(Isolate* isolate, Handle<SharedFunctionInfo> shared); |
47 | |
48 | // Creates a new parse info based on parent top-level |outer_parse_info| for |
49 | // function |literal|. |
50 | static std::unique_ptr<ParseInfo> FromParent( |
51 | const ParseInfo* outer_parse_info, AccountingAllocator* zone_allocator, |
52 | const FunctionLiteral* literal, const AstRawString* function_name); |
53 | |
54 | ~ParseInfo(); |
55 | |
56 | Handle<Script> CreateScript(Isolate* isolate, Handle<String> source, |
57 | ScriptOriginOptions origin_options, |
58 | NativesFlag natives = NOT_NATIVES_CODE); |
59 | |
60 | // Either returns the ast-value-factory associcated with this ParseInfo, or |
61 | // creates and returns a new factory if none exists. |
62 | AstValueFactory* GetOrCreateAstValueFactory(); |
63 | |
64 | Zone* zone() const { return zone_.get(); } |
65 | |
66 | // Convenience accessor methods for flags. |
67 | #define FLAG_ACCESSOR(flag, getter, setter) \ |
68 | bool getter() const { return GetFlag(flag); } \ |
69 | void setter() { SetFlag(flag); } \ |
70 | void setter(bool val) { SetFlag(flag, val); } |
71 | |
72 | FLAG_ACCESSOR(kToplevel, is_toplevel, set_toplevel) |
73 | FLAG_ACCESSOR(kEager, is_eager, set_eager) |
74 | FLAG_ACCESSOR(kEval, is_eval, set_eval) |
75 | FLAG_ACCESSOR(kStrictMode, is_strict_mode, set_strict_mode) |
76 | FLAG_ACCESSOR(kModule, is_module, set_module) |
77 | FLAG_ACCESSOR(kAllowLazyParsing, allow_lazy_parsing, set_allow_lazy_parsing) |
78 | FLAG_ACCESSOR(kIsNamedExpression, is_named_expression, |
79 | set_is_named_expression) |
80 | FLAG_ACCESSOR(kLazyCompile, lazy_compile, set_lazy_compile) |
81 | FLAG_ACCESSOR(kCollectTypeProfile, collect_type_profile, |
82 | set_collect_type_profile) |
83 | FLAG_ACCESSOR(kIsAsmWasmBroken, is_asm_wasm_broken, set_asm_wasm_broken) |
84 | FLAG_ACCESSOR(kContainsAsmModule, contains_asm_module, |
85 | set_contains_asm_module) |
86 | FLAG_ACCESSOR(kCoverageEnabled, coverage_enabled, set_coverage_enabled) |
87 | FLAG_ACCESSOR(kBlockCoverageEnabled, block_coverage_enabled, |
88 | set_block_coverage_enabled) |
89 | FLAG_ACCESSOR(kOnBackgroundThread, on_background_thread, |
90 | set_on_background_thread) |
91 | FLAG_ACCESSOR(kWrappedAsFunction, is_wrapped_as_function, |
92 | set_wrapped_as_function) |
93 | FLAG_ACCESSOR(kAllowEvalCache, allow_eval_cache, set_allow_eval_cache) |
94 | FLAG_ACCESSOR(kIsDeclaration, is_declaration, set_declaration) |
95 | FLAG_ACCESSOR(kRequiresInstanceMembersInitializer, |
96 | requires_instance_members_initializer, |
97 | set_requires_instance_members_initializer) |
98 | FLAG_ACCESSOR(kMightAlwaysOpt, might_always_opt, set_might_always_opt) |
99 | FLAG_ACCESSOR(kAllowNativeSyntax, allow_natives_syntax, |
100 | set_allow_natives_syntax) |
101 | FLAG_ACCESSOR(kAllowLazyCompile, allow_lazy_compile, set_allow_lazy_compile) |
102 | FLAG_ACCESSOR(kAllowNativeSyntax, allow_native_syntax, |
103 | set_allow_native_syntax) |
104 | FLAG_ACCESSOR(kAllowHarmonyPublicFields, allow_harmony_public_fields, |
105 | set_allow_harmony_public_fields) |
106 | FLAG_ACCESSOR(kAllowHarmonyStaticFields, allow_harmony_static_fields, |
107 | set_allow_harmony_static_fields) |
108 | FLAG_ACCESSOR(kAllowHarmonyDynamicImport, allow_harmony_dynamic_import, |
109 | set_allow_harmony_dynamic_import) |
110 | FLAG_ACCESSOR(kAllowHarmonyImportMeta, allow_harmony_import_meta, |
111 | set_allow_harmony_import_meta) |
112 | FLAG_ACCESSOR(kAllowHarmonyNumericSeparator, allow_harmony_numeric_separator, |
113 | set_allow_harmony_numeric_separator) |
114 | FLAG_ACCESSOR(kAllowHarmonyPrivateFields, allow_harmony_private_fields, |
115 | set_allow_harmony_private_fields) |
116 | FLAG_ACCESSOR(kAllowHarmonyPrivateMethods, allow_harmony_private_methods, |
117 | set_allow_harmony_private_methods) |
118 | FLAG_ACCESSOR(kIsOneshotIIFE, is_oneshot_iife, set_is_oneshot_iife) |
119 | FLAG_ACCESSOR(kCollectSourcePositions, collect_source_positions, |
120 | set_collect_source_positions) |
121 | #undef FLAG_ACCESSOR |
122 | |
123 | void set_parse_restriction(ParseRestriction restriction) { |
124 | SetFlag(kParseRestriction, restriction != NO_PARSE_RESTRICTION); |
125 | } |
126 | |
127 | ParseRestriction parse_restriction() const { |
128 | return GetFlag(kParseRestriction) ? ONLY_SINGLE_FUNCTION_LITERAL |
129 | : NO_PARSE_RESTRICTION; |
130 | } |
131 | |
132 | Utf16CharacterStream* character_stream() const { |
133 | return character_stream_.get(); |
134 | } |
135 | void set_character_stream( |
136 | std::unique_ptr<Utf16CharacterStream> character_stream); |
137 | void ResetCharacterStream(); |
138 | |
139 | v8::Extension* extension() const { return extension_; } |
140 | void set_extension(v8::Extension* extension) { extension_ = extension; } |
141 | |
142 | void set_consumed_preparse_data(std::unique_ptr<ConsumedPreparseData> data) { |
143 | consumed_preparse_data_.swap(data); |
144 | } |
145 | ConsumedPreparseData* consumed_preparse_data() { |
146 | return consumed_preparse_data_.get(); |
147 | } |
148 | |
149 | DeclarationScope* script_scope() const { return script_scope_; } |
150 | void set_script_scope(DeclarationScope* script_scope) { |
151 | script_scope_ = script_scope; |
152 | } |
153 | |
154 | AstValueFactory* ast_value_factory() const { |
155 | DCHECK(ast_value_factory_.get()); |
156 | return ast_value_factory_.get(); |
157 | } |
158 | |
159 | const AstRawString* function_name() const { return function_name_; } |
160 | void set_function_name(const AstRawString* function_name) { |
161 | function_name_ = function_name; |
162 | } |
163 | |
164 | FunctionLiteral* literal() const { return literal_; } |
165 | void set_literal(FunctionLiteral* literal) { literal_ = literal; } |
166 | |
167 | DeclarationScope* scope() const; |
168 | |
169 | uintptr_t stack_limit() const { return stack_limit_; } |
170 | void set_stack_limit(uintptr_t stack_limit) { stack_limit_ = stack_limit; } |
171 | |
172 | uint64_t hash_seed() const { return hash_seed_; } |
173 | void set_hash_seed(uint64_t hash_seed) { hash_seed_ = hash_seed; } |
174 | |
175 | int start_position() const { return start_position_; } |
176 | void set_start_position(int start_position) { |
177 | start_position_ = start_position; |
178 | } |
179 | |
180 | int end_position() const { return end_position_; } |
181 | void set_end_position(int end_position) { end_position_ = end_position; } |
182 | |
183 | int parameters_end_pos() const { return parameters_end_pos_; } |
184 | void set_parameters_end_pos(int parameters_end_pos) { |
185 | parameters_end_pos_ = parameters_end_pos; |
186 | } |
187 | |
188 | int function_literal_id() const { return function_literal_id_; } |
189 | void set_function_literal_id(int function_literal_id) { |
190 | function_literal_id_ = function_literal_id; |
191 | } |
192 | |
193 | FunctionKind function_kind() const { return function_kind_; } |
194 | void set_function_kind(FunctionKind function_kind) { |
195 | function_kind_ = function_kind; |
196 | } |
197 | |
198 | int max_function_literal_id() const { return max_function_literal_id_; } |
199 | void set_max_function_literal_id(int max_function_literal_id) { |
200 | max_function_literal_id_ = max_function_literal_id; |
201 | } |
202 | |
203 | const AstStringConstants* ast_string_constants() const { |
204 | return ast_string_constants_; |
205 | } |
206 | void set_ast_string_constants( |
207 | const AstStringConstants* ast_string_constants) { |
208 | ast_string_constants_ = ast_string_constants; |
209 | } |
210 | |
211 | RuntimeCallStats* runtime_call_stats() const { return runtime_call_stats_; } |
212 | void set_runtime_call_stats(RuntimeCallStats* runtime_call_stats) { |
213 | runtime_call_stats_ = runtime_call_stats; |
214 | } |
215 | Logger* logger() const { return logger_; } |
216 | void set_logger(Logger* logger) { logger_ = logger; } |
217 | |
218 | void AllocateSourceRangeMap(); |
219 | SourceRangeMap* source_range_map() const { return source_range_map_; } |
220 | void set_source_range_map(SourceRangeMap* source_range_map) { |
221 | source_range_map_ = source_range_map; |
222 | } |
223 | |
224 | PendingCompilationErrorHandler* pending_error_handler() { |
225 | return &pending_error_handler_; |
226 | } |
227 | |
228 | class ParallelTasks { |
229 | public: |
230 | explicit ParallelTasks(CompilerDispatcher* compiler_dispatcher) |
231 | : dispatcher_(compiler_dispatcher) { |
232 | DCHECK(dispatcher_); |
233 | } |
234 | |
235 | void Enqueue(ParseInfo* outer_parse_info, const AstRawString* function_name, |
236 | FunctionLiteral* literal); |
237 | |
238 | using EnqueuedJobsIterator = |
239 | std::forward_list<std::pair<FunctionLiteral*, uintptr_t>>::iterator; |
240 | |
241 | EnqueuedJobsIterator begin() { return enqueued_jobs_.begin(); } |
242 | EnqueuedJobsIterator end() { return enqueued_jobs_.end(); } |
243 | |
244 | CompilerDispatcher* dispatcher() { return dispatcher_; } |
245 | |
246 | private: |
247 | CompilerDispatcher* dispatcher_; |
248 | std::forward_list<std::pair<FunctionLiteral*, uintptr_t>> enqueued_jobs_; |
249 | }; |
250 | |
251 | ParallelTasks* parallel_tasks() { return parallel_tasks_.get(); } |
252 | |
253 | //-------------------------------------------------------------------------- |
254 | // TODO(titzer): these should not be part of ParseInfo. |
255 | //-------------------------------------------------------------------------- |
256 | Handle<Script> script() const { return script_; } |
257 | void set_script(Handle<Script> script); |
258 | |
259 | MaybeHandle<ScopeInfo> maybe_outer_scope_info() const { |
260 | return maybe_outer_scope_info_; |
261 | } |
262 | void set_outer_scope_info(Handle<ScopeInfo> outer_scope_info) { |
263 | maybe_outer_scope_info_ = outer_scope_info; |
264 | } |
265 | |
266 | int script_id() const { return script_id_; } |
267 | //-------------------------------------------------------------------------- |
268 | |
269 | LanguageMode language_mode() const { |
270 | return construct_language_mode(is_strict_mode()); |
271 | } |
272 | void set_language_mode(LanguageMode language_mode) { |
273 | STATIC_ASSERT(LanguageModeSize == 2); |
274 | set_strict_mode(is_strict(language_mode)); |
275 | } |
276 | |
277 | private: |
278 | void SetScriptForToplevelCompile(Isolate* isolate, Handle<Script> script); |
279 | |
280 | // Set function info flags based on those in either FunctionLiteral or |
281 | // SharedFunctionInfo |function| |
282 | template <typename T> |
283 | void SetFunctionInfo(T function); |
284 | |
285 | // Various configuration flags for parsing. |
286 | enum Flag { |
287 | // ---------- Input flags --------------------------- |
288 | kToplevel = 1 << 0, |
289 | kEager = 1 << 1, |
290 | kEval = 1 << 2, |
291 | kStrictMode = 1 << 3, |
292 | kNative = 1 << 4, |
293 | kParseRestriction = 1 << 5, |
294 | kModule = 1 << 6, |
295 | kAllowLazyParsing = 1 << 7, |
296 | kIsNamedExpression = 1 << 8, |
297 | kLazyCompile = 1 << 9, |
298 | kCollectTypeProfile = 1 << 10, |
299 | kCoverageEnabled = 1 << 11, |
300 | kBlockCoverageEnabled = 1 << 12, |
301 | kIsAsmWasmBroken = 1 << 13, |
302 | kOnBackgroundThread = 1 << 14, |
303 | kWrappedAsFunction = 1 << 15, // Implicitly wrapped as function. |
304 | kAllowEvalCache = 1 << 16, |
305 | kIsDeclaration = 1 << 17, |
306 | kRequiresInstanceMembersInitializer = 1 << 18, |
307 | kContainsAsmModule = 1 << 19, |
308 | kMightAlwaysOpt = 1 << 20, |
309 | kAllowLazyCompile = 1 << 21, |
310 | kAllowNativeSyntax = 1 << 22, |
311 | kAllowHarmonyPublicFields = 1 << 23, |
312 | kAllowHarmonyStaticFields = 1 << 24, |
313 | kAllowHarmonyDynamicImport = 1 << 25, |
314 | kAllowHarmonyImportMeta = 1 << 26, |
315 | kAllowHarmonyNumericSeparator = 1 << 27, |
316 | kAllowHarmonyPrivateFields = 1 << 28, |
317 | kAllowHarmonyPrivateMethods = 1 << 29, |
318 | kIsOneshotIIFE = 1 << 30, |
319 | kCollectSourcePositions = 1 << 31, |
320 | }; |
321 | |
322 | //------------- Inputs to parsing and scope analysis ----------------------- |
323 | std::unique_ptr<Zone> zone_; |
324 | unsigned flags_; |
325 | v8::Extension* extension_; |
326 | DeclarationScope* script_scope_; |
327 | uintptr_t stack_limit_; |
328 | uint64_t hash_seed_; |
329 | FunctionKind function_kind_; |
330 | int script_id_; |
331 | int start_position_; |
332 | int end_position_; |
333 | int parameters_end_pos_; |
334 | int function_literal_id_; |
335 | int max_function_literal_id_; |
336 | |
337 | // TODO(titzer): Move handles out of ParseInfo. |
338 | Handle<Script> script_; |
339 | MaybeHandle<ScopeInfo> maybe_outer_scope_info_; |
340 | |
341 | //----------- Inputs+Outputs of parsing and scope analysis ----------------- |
342 | std::unique_ptr<Utf16CharacterStream> character_stream_; |
343 | std::unique_ptr<ConsumedPreparseData> consumed_preparse_data_; |
344 | std::unique_ptr<AstValueFactory> ast_value_factory_; |
345 | const class AstStringConstants* ast_string_constants_; |
346 | const AstRawString* function_name_; |
347 | RuntimeCallStats* runtime_call_stats_; |
348 | Logger* logger_; |
349 | SourceRangeMap* source_range_map_; // Used when block coverage is enabled. |
350 | std::unique_ptr<ParallelTasks> parallel_tasks_; |
351 | |
352 | //----------- Output of parsing and scope analysis ------------------------ |
353 | FunctionLiteral* literal_; |
354 | PendingCompilationErrorHandler pending_error_handler_; |
355 | |
356 | void SetFlag(Flag f) { flags_ |= f; } |
357 | void SetFlag(Flag f, bool v) { flags_ = v ? flags_ | f : flags_ & ~f; } |
358 | bool GetFlag(Flag f) const { return (flags_ & f) != 0; } |
359 | }; |
360 | |
361 | } // namespace internal |
362 | } // namespace v8 |
363 | |
364 | #endif // V8_PARSING_PARSE_INFO_H_ |
365 | |