1 // Copyright 2012 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 /** \mainpage V8 API Reference Guide
6 *
7 * V8 is Google's open source JavaScript engine.
8 *
9 * This set of documents provides reference material generated from the
10 * V8 header file, include/v8.h.
11 *
12 * For other documentation see https://v8.dev/.
13 */
14
15 #ifndef INCLUDE_V8_H_
16 #define INCLUDE_V8_H_
17
18 #include <stddef.h>
19 #include <stdint.h>
20 #include <stdio.h>
21
22 #include <atomic>
23 #include <memory>
24 #include <string>
25 #include <type_traits>
26 #include <utility>
27 #include <vector>
28
29 #include "cppgc/common.h"
30 #include "v8-internal.h" // NOLINT(build/include_directory)
31 #include "v8-version.h" // NOLINT(build/include_directory)
32 #include "v8config.h" // NOLINT(build/include_directory)
33
34 // We reserve the V8_* prefix for macros defined in V8 public API and
35 // assume there are no name conflicts with the embedder's code.
36
37 /**
38 * The v8 JavaScript engine.
39 */
40 namespace v8 {
41
42 class AccessorSignature;
43 class Array;
44 class ArrayBuffer;
45 class BigInt;
46 class BigIntObject;
47 class Boolean;
48 class BooleanObject;
49 class CFunction;
50 class CallHandlerHelper;
51 class Context;
52 class CppHeap;
53 class CTypeInfo;
54 class Data;
55 class Date;
56 class EscapableHandleScope;
57 class External;
58 class Function;
59 class FunctionTemplate;
60 class HeapProfiler;
61 class ImplementationUtilities;
62 class Int32;
63 class Integer;
64 class Isolate;
65 class Isolate;
66 class MicrotaskQueue;
67 class Name;
68 class Number;
69 class NumberObject;
70 class Object;
71 class ObjectOperationDescriptor;
72 class ObjectTemplate;
73 class Platform;
74 class Primitive;
75 class PrimitiveArray;
76 class Private;
77 class Promise;
78 class PropertyDescriptor;
79 class Proxy;
80 class RawOperationDescriptor;
81 class Script;
82 class SharedArrayBuffer;
83 class Signature;
84 class StackFrame;
85 class StackTrace;
86 class StartupData;
87 class String;
88 class StringObject;
89 class Symbol;
90 class SymbolObject;
91 class TracedReferenceBase;
92 class Uint32;
93 class Utils;
94 class Value;
95 class WasmMemoryObject;
96 class WasmModuleObject;
97 template <class K, class V, class T>
98 class GlobalValueMap;
99 template <class K, class V, class T>
100 class PersistentValueMapBase;
101 template<class T> class NonCopyablePersistentTraits;
102 template <class T, class M = NonCopyablePersistentTraits<T>>
103 class Persistent;
104 template <class T>
105 class BasicTracedReference;
106 template <class T>
107 class Eternal;
108 template <class T>
109 class Global;
110 template <class T>
111 class Local;
112 template <class T>
113 class Maybe;
114 template <class T>
115 class MaybeLocal;
116 template <class T>
117 class TracedGlobal;
118 template <class T>
119 class TracedReference;
120 template<class K, class V, class T> class PersistentValueMap;
121 template<class T, class P> class WeakCallbackObject;
122 template <class T>
123 class PersistentBase;
124 template <class V, class T>
125 class PersistentValueVector;
126 template<typename T> class FunctionCallbackInfo;
127 template<typename T> class PropertyCallbackInfo;
128 template<typename T> class ReturnValue;
129
130 namespace internal {
131 class BasicTracedReferenceExtractor;
132 class ExternalString;
133 class FunctionCallbackArguments;
134 class GlobalHandles;
135 class Heap;
136 class HeapObject;
137 class Isolate;
138 class LocalEmbedderHeapTracer;
139 class MicrotaskQueue;
140 class PropertyCallbackArguments;
141 class ReadOnlyHeap;
142 class ScopedExternalStringLock;
143 class ThreadLocalTop;
144 struct ScriptStreamingData;
145 enum class ArgumentsType;
146 template <ArgumentsType>
147 class Arguments;
148 template <typename T>
149 class CustomArguments;
150
151 namespace wasm {
152 class NativeModule;
153 class StreamingDecoder;
154 } // namespace wasm
155
156 } // namespace internal
157
158 namespace metrics {
159 class Recorder;
160 } // namespace metrics
161
162 namespace debug {
163 class ConsoleCallArguments;
164 } // namespace debug
165
166 // --- Handles ---
167
168 /**
169 * An object reference managed by the v8 garbage collector.
170 *
171 * All objects returned from v8 have to be tracked by the garbage
172 * collector so that it knows that the objects are still alive. Also,
173 * because the garbage collector may move objects, it is unsafe to
174 * point directly to an object. Instead, all objects are stored in
175 * handles which are known by the garbage collector and updated
176 * whenever an object moves. Handles should always be passed by value
177 * (except in cases like out-parameters) and they should never be
178 * allocated on the heap.
179 *
180 * There are two types of handles: local and persistent handles.
181 *
182 * Local handles are light-weight and transient and typically used in
183 * local operations. They are managed by HandleScopes. That means that a
184 * HandleScope must exist on the stack when they are created and that they are
185 * only valid inside of the HandleScope active during their creation.
186 * For passing a local handle to an outer HandleScope, an EscapableHandleScope
187 * and its Escape() method must be used.
188 *
189 * Persistent handles can be used when storing objects across several
190 * independent operations and have to be explicitly deallocated when they're no
191 * longer used.
192 *
193 * It is safe to extract the object stored in the handle by
194 * dereferencing the handle (for instance, to extract the Object* from
195 * a Local<Object>); the value will still be governed by a handle
196 * behind the scenes and the same rules apply to these values as to
197 * their handles.
198 */
199 template <class T>
200 class Local {
201 public:
Local()202 V8_INLINE Local() : val_(nullptr) {}
203 template <class S>
Local(Local<S> that)204 V8_INLINE Local(Local<S> that)
205 : val_(reinterpret_cast<T*>(*that)) {
206 /**
207 * This check fails when trying to convert between incompatible
208 * handles. For example, converting from a Local<String> to a
209 * Local<Number>.
210 */
211 static_assert(std::is_base_of<T, S>::value, "type check");
212 }
213
214 /**
215 * Returns true if the handle is empty.
216 */
IsEmpty()217 V8_INLINE bool IsEmpty() const { return val_ == nullptr; }
218
219 /**
220 * Sets the handle to be empty. IsEmpty() will then return true.
221 */
Clear()222 V8_INLINE void Clear() { val_ = nullptr; }
223
224 V8_INLINE T* operator->() const { return val_; }
225
226 V8_INLINE T* operator*() const { return val_; }
227
228 /**
229 * Checks whether two handles are the same.
230 * Returns true if both are empty, or if the objects to which they refer
231 * are identical.
232 *
233 * If both handles refer to JS objects, this is the same as strict equality.
234 * For primitives, such as numbers or strings, a `false` return value does not
235 * indicate that the values aren't equal in the JavaScript sense.
236 * Use `Value::StrictEquals()` to check primitives for equality.
237 */
238 template <class S>
239 V8_INLINE bool operator==(const Local<S>& that) const {
240 internal::Address* a = reinterpret_cast<internal::Address*>(this->val_);
241 internal::Address* b = reinterpret_cast<internal::Address*>(that.val_);
242 if (a == nullptr) return b == nullptr;
243 if (b == nullptr) return false;
244 return *a == *b;
245 }
246
247 template <class S> V8_INLINE bool operator==(
248 const PersistentBase<S>& that) const {
249 internal::Address* a = reinterpret_cast<internal::Address*>(this->val_);
250 internal::Address* b = reinterpret_cast<internal::Address*>(that.val_);
251 if (a == nullptr) return b == nullptr;
252 if (b == nullptr) return false;
253 return *a == *b;
254 }
255
256 /**
257 * Checks whether two handles are different.
258 * Returns true if only one of the handles is empty, or if
259 * the objects to which they refer are different.
260 *
261 * If both handles refer to JS objects, this is the same as strict
262 * non-equality. For primitives, such as numbers or strings, a `true` return
263 * value does not indicate that the values aren't equal in the JavaScript
264 * sense. Use `Value::StrictEquals()` to check primitives for equality.
265 */
266 template <class S>
267 V8_INLINE bool operator!=(const Local<S>& that) const {
268 return !operator==(that);
269 }
270
271 template <class S> V8_INLINE bool operator!=(
272 const Persistent<S>& that) const {
273 return !operator==(that);
274 }
275
276 /**
277 * Cast a handle to a subclass, e.g. Local<Value> to Local<Object>.
278 * This is only valid if the handle actually refers to a value of the
279 * target type.
280 */
Cast(Local<S> that)281 template <class S> V8_INLINE static Local<T> Cast(Local<S> that) {
282 #ifdef V8_ENABLE_CHECKS
283 // If we're going to perform the type check then we have to check
284 // that the handle isn't empty before doing the checked cast.
285 if (that.IsEmpty()) return Local<T>();
286 #endif
287 return Local<T>(T::Cast(*that));
288 }
289
290 /**
291 * Calling this is equivalent to Local<S>::Cast().
292 * In particular, this is only valid if the handle actually refers to a value
293 * of the target type.
294 */
295 template <class S>
As()296 V8_INLINE Local<S> As() const {
297 return Local<S>::Cast(*this);
298 }
299
300 /**
301 * Create a local handle for the content of another handle.
302 * The referee is kept alive by the local handle even when
303 * the original handle is destroyed/disposed.
304 */
305 V8_INLINE static Local<T> New(Isolate* isolate, Local<T> that);
306 V8_INLINE static Local<T> New(Isolate* isolate,
307 const PersistentBase<T>& that);
308 V8_INLINE static Local<T> New(Isolate* isolate,
309 const BasicTracedReference<T>& that);
310
311 private:
312 friend class TracedReferenceBase;
313 friend class Utils;
314 template<class F> friend class Eternal;
315 template<class F> friend class PersistentBase;
316 template<class F, class M> friend class Persistent;
317 template<class F> friend class Local;
318 template <class F>
319 friend class MaybeLocal;
320 template<class F> friend class FunctionCallbackInfo;
321 template<class F> friend class PropertyCallbackInfo;
322 friend class String;
323 friend class Object;
324 friend class Context;
325 friend class Isolate;
326 friend class Private;
327 template<class F> friend class internal::CustomArguments;
328 friend Local<Primitive> Undefined(Isolate* isolate);
329 friend Local<Primitive> Null(Isolate* isolate);
330 friend Local<Boolean> True(Isolate* isolate);
331 friend Local<Boolean> False(Isolate* isolate);
332 friend class HandleScope;
333 friend class EscapableHandleScope;
334 template <class F1, class F2, class F3>
335 friend class PersistentValueMapBase;
336 template<class F1, class F2> friend class PersistentValueVector;
337 template <class F>
338 friend class ReturnValue;
339 template <class F>
340 friend class Traced;
341 template <class F>
342 friend class TracedGlobal;
343 template <class F>
344 friend class BasicTracedReference;
345 template <class F>
346 friend class TracedReference;
347
Local(T * that)348 explicit V8_INLINE Local(T* that) : val_(that) {}
349 V8_INLINE static Local<T> New(Isolate* isolate, T* that);
350 T* val_;
351 };
352
353
354 #if !defined(V8_IMMINENT_DEPRECATION_WARNINGS)
355 // Handle is an alias for Local for historical reasons.
356 template <class T>
357 using Handle = Local<T>;
358 #endif
359
360
361 /**
362 * A MaybeLocal<> is a wrapper around Local<> that enforces a check whether
363 * the Local<> is empty before it can be used.
364 *
365 * If an API method returns a MaybeLocal<>, the API method can potentially fail
366 * either because an exception is thrown, or because an exception is pending,
367 * e.g. because a previous API call threw an exception that hasn't been caught
368 * yet, or because a TerminateExecution exception was thrown. In that case, an
369 * empty MaybeLocal is returned.
370 */
371 template <class T>
372 class MaybeLocal {
373 public:
MaybeLocal()374 V8_INLINE MaybeLocal() : val_(nullptr) {}
375 template <class S>
MaybeLocal(Local<S> that)376 V8_INLINE MaybeLocal(Local<S> that)
377 : val_(reinterpret_cast<T*>(*that)) {
378 static_assert(std::is_base_of<T, S>::value, "type check");
379 }
380
IsEmpty()381 V8_INLINE bool IsEmpty() const { return val_ == nullptr; }
382
383 /**
384 * Converts this MaybeLocal<> to a Local<>. If this MaybeLocal<> is empty,
385 * |false| is returned and |out| is left untouched.
386 */
387 template <class S>
ToLocal(Local<S> * out)388 V8_WARN_UNUSED_RESULT V8_INLINE bool ToLocal(Local<S>* out) const {
389 out->val_ = IsEmpty() ? nullptr : this->val_;
390 return !IsEmpty();
391 }
392
393 /**
394 * Converts this MaybeLocal<> to a Local<>. If this MaybeLocal<> is empty,
395 * V8 will crash the process.
396 */
397 V8_INLINE Local<T> ToLocalChecked();
398
399 /**
400 * Converts this MaybeLocal<> to a Local<>, using a default value if this
401 * MaybeLocal<> is empty.
402 */
403 template <class S>
FromMaybe(Local<S> default_value)404 V8_INLINE Local<S> FromMaybe(Local<S> default_value) const {
405 return IsEmpty() ? default_value : Local<S>(val_);
406 }
407
408 private:
409 T* val_;
410 };
411
412 /**
413 * Eternal handles are set-once handles that live for the lifetime of the
414 * isolate.
415 */
416 template <class T> class Eternal {
417 public:
Eternal()418 V8_INLINE Eternal() : val_(nullptr) {}
419 template <class S>
Eternal(Isolate * isolate,Local<S> handle)420 V8_INLINE Eternal(Isolate* isolate, Local<S> handle) : val_(nullptr) {
421 Set(isolate, handle);
422 }
423 // Can only be safely called if already set.
424 V8_INLINE Local<T> Get(Isolate* isolate) const;
IsEmpty()425 V8_INLINE bool IsEmpty() const { return val_ == nullptr; }
426 template<class S> V8_INLINE void Set(Isolate* isolate, Local<S> handle);
427
428 private:
429 T* val_;
430 };
431
432
433 static const int kInternalFieldsInWeakCallback = 2;
434 static const int kEmbedderFieldsInWeakCallback = 2;
435
436 template <typename T>
437 class WeakCallbackInfo {
438 public:
439 using Callback = void (*)(const WeakCallbackInfo<T>& data);
440
WeakCallbackInfo(Isolate * isolate,T * parameter,void * embedder_fields[kEmbedderFieldsInWeakCallback],Callback * callback)441 WeakCallbackInfo(Isolate* isolate, T* parameter,
442 void* embedder_fields[kEmbedderFieldsInWeakCallback],
443 Callback* callback)
444 : isolate_(isolate), parameter_(parameter), callback_(callback) {
445 for (int i = 0; i < kEmbedderFieldsInWeakCallback; ++i) {
446 embedder_fields_[i] = embedder_fields[i];
447 }
448 }
449
GetIsolate()450 V8_INLINE Isolate* GetIsolate() const { return isolate_; }
GetParameter()451 V8_INLINE T* GetParameter() const { return parameter_; }
452 V8_INLINE void* GetInternalField(int index) const;
453
454 // When first called, the embedder MUST Reset() the Global which triggered the
455 // callback. The Global itself is unusable for anything else. No v8 other api
456 // calls may be called in the first callback. Should additional work be
457 // required, the embedder must set a second pass callback, which will be
458 // called after all the initial callbacks are processed.
459 // Calling SetSecondPassCallback on the second pass will immediately crash.
SetSecondPassCallback(Callback callback)460 void SetSecondPassCallback(Callback callback) const { *callback_ = callback; }
461
462 private:
463 Isolate* isolate_;
464 T* parameter_;
465 Callback* callback_;
466 void* embedder_fields_[kEmbedderFieldsInWeakCallback];
467 };
468
469
470 // kParameter will pass a void* parameter back to the callback, kInternalFields
471 // will pass the first two internal fields back to the callback, kFinalizer
472 // will pass a void* parameter back, but is invoked before the object is
473 // actually collected, so it can be resurrected. In the last case, it is not
474 // possible to request a second pass callback.
475 enum class WeakCallbackType { kParameter, kInternalFields, kFinalizer };
476
477 /**
478 * An object reference that is independent of any handle scope. Where
479 * a Local handle only lives as long as the HandleScope in which it was
480 * allocated, a PersistentBase handle remains valid until it is explicitly
481 * disposed using Reset().
482 *
483 * A persistent handle contains a reference to a storage cell within
484 * the V8 engine which holds an object value and which is updated by
485 * the garbage collector whenever the object is moved. A new storage
486 * cell can be created using the constructor or PersistentBase::Reset and
487 * existing handles can be disposed using PersistentBase::Reset.
488 *
489 */
490 template <class T> class PersistentBase {
491 public:
492 /**
493 * If non-empty, destroy the underlying storage cell
494 * IsEmpty() will return true after this call.
495 */
496 V8_INLINE void Reset();
497 /**
498 * If non-empty, destroy the underlying storage cell
499 * and create a new one with the contents of other if other is non empty
500 */
501 template <class S>
502 V8_INLINE void Reset(Isolate* isolate, const Local<S>& other);
503
504 /**
505 * If non-empty, destroy the underlying storage cell
506 * and create a new one with the contents of other if other is non empty
507 */
508 template <class S>
509 V8_INLINE void Reset(Isolate* isolate, const PersistentBase<S>& other);
510
IsEmpty()511 V8_INLINE bool IsEmpty() const { return val_ == nullptr; }
Empty()512 V8_INLINE void Empty() { val_ = 0; }
513
Get(Isolate * isolate)514 V8_INLINE Local<T> Get(Isolate* isolate) const {
515 return Local<T>::New(isolate, *this);
516 }
517
518 template <class S>
519 V8_INLINE bool operator==(const PersistentBase<S>& that) const {
520 internal::Address* a = reinterpret_cast<internal::Address*>(this->val_);
521 internal::Address* b = reinterpret_cast<internal::Address*>(that.val_);
522 if (a == nullptr) return b == nullptr;
523 if (b == nullptr) return false;
524 return *a == *b;
525 }
526
527 template <class S>
528 V8_INLINE bool operator==(const Local<S>& that) const {
529 internal::Address* a = reinterpret_cast<internal::Address*>(this->val_);
530 internal::Address* b = reinterpret_cast<internal::Address*>(that.val_);
531 if (a == nullptr) return b == nullptr;
532 if (b == nullptr) return false;
533 return *a == *b;
534 }
535
536 template <class S>
537 V8_INLINE bool operator!=(const PersistentBase<S>& that) const {
538 return !operator==(that);
539 }
540
541 template <class S>
542 V8_INLINE bool operator!=(const Local<S>& that) const {
543 return !operator==(that);
544 }
545
546 /**
547 * Install a finalization callback on this object.
548 * NOTE: There is no guarantee as to *when* or even *if* the callback is
549 * invoked. The invocation is performed solely on a best effort basis.
550 * As always, GC-based finalization should *not* be relied upon for any
551 * critical form of resource management!
552 *
553 * The callback is supposed to reset the handle. No further V8 API may be
554 * called in this callback. In case additional work involving V8 needs to be
555 * done, a second callback can be scheduled using
556 * WeakCallbackInfo<void>::SetSecondPassCallback.
557 */
558 template <typename P>
559 V8_INLINE void SetWeak(P* parameter,
560 typename WeakCallbackInfo<P>::Callback callback,
561 WeakCallbackType type);
562
563 /**
564 * Turns this handle into a weak phantom handle without finalization callback.
565 * The handle will be reset automatically when the garbage collector detects
566 * that the object is no longer reachable.
567 * A related function Isolate::NumberOfPhantomHandleResetsSinceLastCall
568 * returns how many phantom handles were reset by the garbage collector.
569 */
570 V8_INLINE void SetWeak();
571
572 template<typename P>
573 V8_INLINE P* ClearWeak();
574
575 // TODO(dcarney): remove this.
ClearWeak()576 V8_INLINE void ClearWeak() { ClearWeak<void>(); }
577
578 /**
579 * Annotates the strong handle with the given label, which is then used by the
580 * heap snapshot generator as a name of the edge from the root to the handle.
581 * The function does not take ownership of the label and assumes that the
582 * label is valid as long as the handle is valid.
583 */
584 V8_INLINE void AnnotateStrongRetainer(const char* label);
585
586 /** Returns true if the handle's reference is weak. */
587 V8_INLINE bool IsWeak() const;
588
589 /**
590 * Assigns a wrapper class ID to the handle.
591 */
592 V8_INLINE void SetWrapperClassId(uint16_t class_id);
593
594 /**
595 * Returns the class ID previously assigned to this handle or 0 if no class ID
596 * was previously assigned.
597 */
598 V8_INLINE uint16_t WrapperClassId() const;
599
600 PersistentBase(const PersistentBase& other) = delete;
601 void operator=(const PersistentBase&) = delete;
602
603 private:
604 friend class Isolate;
605 friend class Utils;
606 template<class F> friend class Local;
607 template<class F1, class F2> friend class Persistent;
608 template <class F>
609 friend class Global;
610 template<class F> friend class PersistentBase;
611 template<class F> friend class ReturnValue;
612 template <class F1, class F2, class F3>
613 friend class PersistentValueMapBase;
614 template<class F1, class F2> friend class PersistentValueVector;
615 friend class Object;
616
PersistentBase(T * val)617 explicit V8_INLINE PersistentBase(T* val) : val_(val) {}
618 V8_INLINE static T* New(Isolate* isolate, T* that);
619
620 T* val_;
621 };
622
623
624 /**
625 * Default traits for Persistent. This class does not allow
626 * use of the copy constructor or assignment operator.
627 * At present kResetInDestructor is not set, but that will change in a future
628 * version.
629 */
630 template<class T>
631 class NonCopyablePersistentTraits {
632 public:
633 using NonCopyablePersistent = Persistent<T, NonCopyablePersistentTraits<T>>;
634 static const bool kResetInDestructor = false;
635 template<class S, class M>
Copy(const Persistent<S,M> & source,NonCopyablePersistent * dest)636 V8_INLINE static void Copy(const Persistent<S, M>& source,
637 NonCopyablePersistent* dest) {
638 static_assert(sizeof(S) < 0,
639 "NonCopyablePersistentTraits::Copy is not instantiable");
640 }
641 };
642
643
644 /**
645 * Helper class traits to allow copying and assignment of Persistent.
646 * This will clone the contents of storage cell, but not any of the flags, etc.
647 */
648 template<class T>
649 struct CopyablePersistentTraits {
650 using CopyablePersistent = Persistent<T, CopyablePersistentTraits<T>>;
651 static const bool kResetInDestructor = true;
652 template<class S, class M>
CopyCopyablePersistentTraits653 static V8_INLINE void Copy(const Persistent<S, M>& source,
654 CopyablePersistent* dest) {
655 // do nothing, just allow copy
656 }
657 };
658
659
660 /**
661 * A PersistentBase which allows copy and assignment.
662 *
663 * Copy, assignment and destructor behavior is controlled by the traits
664 * class M.
665 *
666 * Note: Persistent class hierarchy is subject to future changes.
667 */
668 template <class T, class M> class Persistent : public PersistentBase<T> {
669 public:
670 /**
671 * A Persistent with no storage cell.
672 */
Persistent()673 V8_INLINE Persistent() : PersistentBase<T>(nullptr) {}
674 /**
675 * Construct a Persistent from a Local.
676 * When the Local is non-empty, a new storage cell is created
677 * pointing to the same object, and no flags are set.
678 */
679 template <class S>
Persistent(Isolate * isolate,Local<S> that)680 V8_INLINE Persistent(Isolate* isolate, Local<S> that)
681 : PersistentBase<T>(PersistentBase<T>::New(isolate, *that)) {
682 static_assert(std::is_base_of<T, S>::value, "type check");
683 }
684 /**
685 * Construct a Persistent from a Persistent.
686 * When the Persistent is non-empty, a new storage cell is created
687 * pointing to the same object, and no flags are set.
688 */
689 template <class S, class M2>
Persistent(Isolate * isolate,const Persistent<S,M2> & that)690 V8_INLINE Persistent(Isolate* isolate, const Persistent<S, M2>& that)
691 : PersistentBase<T>(PersistentBase<T>::New(isolate, *that)) {
692 static_assert(std::is_base_of<T, S>::value, "type check");
693 }
694 /**
695 * The copy constructors and assignment operator create a Persistent
696 * exactly as the Persistent constructor, but the Copy function from the
697 * traits class is called, allowing the setting of flags based on the
698 * copied Persistent.
699 */
Persistent(const Persistent & that)700 V8_INLINE Persistent(const Persistent& that) : PersistentBase<T>(nullptr) {
701 Copy(that);
702 }
703 template <class S, class M2>
Persistent(const Persistent<S,M2> & that)704 V8_INLINE Persistent(const Persistent<S, M2>& that) : PersistentBase<T>(0) {
705 Copy(that);
706 }
707 V8_INLINE Persistent& operator=(const Persistent& that) {
708 Copy(that);
709 return *this;
710 }
711 template <class S, class M2>
712 V8_INLINE Persistent& operator=(const Persistent<S, M2>& that) {
713 Copy(that);
714 return *this;
715 }
716 /**
717 * The destructor will dispose the Persistent based on the
718 * kResetInDestructor flags in the traits class. Since not calling dispose
719 * can result in a memory leak, it is recommended to always set this flag.
720 */
~Persistent()721 V8_INLINE ~Persistent() {
722 if (M::kResetInDestructor) this->Reset();
723 }
724
725 // TODO(dcarney): this is pretty useless, fix or remove
726 template <class S>
Cast(const Persistent<S> & that)727 V8_INLINE static Persistent<T>& Cast(const Persistent<S>& that) {
728 #ifdef V8_ENABLE_CHECKS
729 // If we're going to perform the type check then we have to check
730 // that the handle isn't empty before doing the checked cast.
731 if (!that.IsEmpty()) T::Cast(*that);
732 #endif
733 return reinterpret_cast<Persistent<T>&>(const_cast<Persistent<S>&>(that));
734 }
735
736 // TODO(dcarney): this is pretty useless, fix or remove
737 template <class S>
As()738 V8_INLINE Persistent<S>& As() const {
739 return Persistent<S>::Cast(*this);
740 }
741
742 private:
743 friend class Isolate;
744 friend class Utils;
745 template<class F> friend class Local;
746 template<class F1, class F2> friend class Persistent;
747 template<class F> friend class ReturnValue;
748
Persistent(T * that)749 explicit V8_INLINE Persistent(T* that) : PersistentBase<T>(that) {}
750 V8_INLINE T* operator*() const { return this->val_; }
751 template<class S, class M2>
752 V8_INLINE void Copy(const Persistent<S, M2>& that);
753 };
754
755
756 /**
757 * A PersistentBase which has move semantics.
758 *
759 * Note: Persistent class hierarchy is subject to future changes.
760 */
761 template <class T>
762 class Global : public PersistentBase<T> {
763 public:
764 /**
765 * A Global with no storage cell.
766 */
Global()767 V8_INLINE Global() : PersistentBase<T>(nullptr) {}
768
769 /**
770 * Construct a Global from a Local.
771 * When the Local is non-empty, a new storage cell is created
772 * pointing to the same object, and no flags are set.
773 */
774 template <class S>
Global(Isolate * isolate,Local<S> that)775 V8_INLINE Global(Isolate* isolate, Local<S> that)
776 : PersistentBase<T>(PersistentBase<T>::New(isolate, *that)) {
777 static_assert(std::is_base_of<T, S>::value, "type check");
778 }
779
780 /**
781 * Construct a Global from a PersistentBase.
782 * When the Persistent is non-empty, a new storage cell is created
783 * pointing to the same object, and no flags are set.
784 */
785 template <class S>
Global(Isolate * isolate,const PersistentBase<S> & that)786 V8_INLINE Global(Isolate* isolate, const PersistentBase<S>& that)
787 : PersistentBase<T>(PersistentBase<T>::New(isolate, that.val_)) {
788 static_assert(std::is_base_of<T, S>::value, "type check");
789 }
790
791 /**
792 * Move constructor.
793 */
794 V8_INLINE Global(Global&& other);
795
~Global()796 V8_INLINE ~Global() { this->Reset(); }
797
798 /**
799 * Move via assignment.
800 */
801 template <class S>
802 V8_INLINE Global& operator=(Global<S>&& rhs);
803
804 /**
805 * Pass allows returning uniques from functions, etc.
806 */
Pass()807 Global Pass() { return static_cast<Global&&>(*this); }
808
809 /*
810 * For compatibility with Chromium's base::Bind (base::Passed).
811 */
812 using MoveOnlyTypeForCPP03 = void;
813
814 Global(const Global&) = delete;
815 void operator=(const Global&) = delete;
816
817 private:
818 template <class F>
819 friend class ReturnValue;
820 V8_INLINE T* operator*() const { return this->val_; }
821 };
822
823
824 // UniquePersistent is an alias for Global for historical reason.
825 template <class T>
826 using UniquePersistent = Global<T>;
827
828 /**
829 * Deprecated. Use |TracedReference<T>| instead.
830 */
831 template <typename T>
832 struct TracedGlobalTrait {};
833
834 class TracedReferenceBase {
835 public:
836 /**
837 * Returns true if the reference is empty, i.e., has not been assigned
838 * object.
839 */
IsEmpty()840 bool IsEmpty() const { return val_ == nullptr; }
841
842 /**
843 * If non-empty, destroy the underlying storage cell. |IsEmpty| will return
844 * true after this call.
845 */
846 V8_INLINE void Reset();
847
848 /**
849 * Construct a Local<Value> from this handle.
850 */
851 V8_INLINE v8::Local<v8::Value> Get(v8::Isolate* isolate) const;
852
853 /**
854 * Returns true if this TracedReference is empty, i.e., has not been
855 * assigned an object. This version of IsEmpty is thread-safe.
856 */
IsEmptyThreadSafe()857 bool IsEmptyThreadSafe() const {
858 return this->GetSlotThreadSafe() == nullptr;
859 }
860
861 /**
862 * Assigns a wrapper class ID to the handle.
863 */
864 V8_INLINE void SetWrapperClassId(uint16_t class_id);
865
866 /**
867 * Returns the class ID previously assigned to this handle or 0 if no class ID
868 * was previously assigned.
869 */
870 V8_INLINE uint16_t WrapperClassId() const;
871
872 protected:
873 /**
874 * Update this reference in a thread-safe way.
875 */
SetSlotThreadSafe(void * new_val)876 void SetSlotThreadSafe(void* new_val) {
877 reinterpret_cast<std::atomic<void*>*>(&val_)->store(
878 new_val, std::memory_order_relaxed);
879 }
880
881 /**
882 * Get this reference in a thread-safe way
883 */
GetSlotThreadSafe()884 const void* GetSlotThreadSafe() const {
885 return reinterpret_cast<std::atomic<const void*> const*>(&val_)->load(
886 std::memory_order_relaxed);
887 }
888
889 V8_EXPORT void CheckValue() const;
890
891 // val_ points to a GlobalHandles node.
892 internal::Address* val_ = nullptr;
893
894 friend class internal::BasicTracedReferenceExtractor;
895 template <typename F>
896 friend class Local;
897 template <typename U>
898 friend bool operator==(const TracedReferenceBase&, const Local<U>&);
899 friend bool operator==(const TracedReferenceBase&,
900 const TracedReferenceBase&);
901 };
902
903 /**
904 * A traced handle with copy and move semantics. The handle is to be used
905 * together with |v8::EmbedderHeapTracer| or as part of GarbageCollected objects
906 * (see v8-cppgc.h) and specifies edges from C++ objects to JavaScript.
907 *
908 * The exact semantics are:
909 * - Tracing garbage collections use |v8::EmbedderHeapTracer| or cppgc.
910 * - Non-tracing garbage collections refer to
911 * |v8::EmbedderRootsHandler::IsRoot()| whether the handle should
912 * be treated as root or not.
913 *
914 * Note that the base class cannot be instantiated itself. Choose from
915 * - TracedGlobal
916 * - TracedReference
917 */
918 template <typename T>
919 class BasicTracedReference : public TracedReferenceBase {
920 public:
921 /**
922 * Construct a Local<T> from this handle.
923 */
Get(Isolate * isolate)924 Local<T> Get(Isolate* isolate) const { return Local<T>::New(isolate, *this); }
925
926 template <class S>
As()927 V8_INLINE BasicTracedReference<S>& As() const {
928 return reinterpret_cast<BasicTracedReference<S>&>(
929 const_cast<BasicTracedReference<T>&>(*this));
930 }
931
932 T* operator->() const {
933 #ifdef V8_ENABLE_CHECKS
934 CheckValue();
935 #endif // V8_ENABLE_CHECKS
936 return reinterpret_cast<T*>(val_);
937 }
938 T* operator*() const {
939 #ifdef V8_ENABLE_CHECKS
940 CheckValue();
941 #endif // V8_ENABLE_CHECKS
942 return reinterpret_cast<T*>(val_);
943 }
944
945 private:
946 enum DestructionMode { kWithDestructor, kWithoutDestructor };
947
948 /**
949 * An empty BasicTracedReference without storage cell.
950 */
951 BasicTracedReference() = default;
952
953 V8_INLINE static internal::Address* New(Isolate* isolate, T* that, void* slot,
954 DestructionMode destruction_mode);
955
956 friend class EmbedderHeapTracer;
957 template <typename F>
958 friend class Local;
959 friend class Object;
960 template <typename F>
961 friend class TracedGlobal;
962 template <typename F>
963 friend class TracedReference;
964 template <typename F>
965 friend class BasicTracedReference;
966 template <typename F>
967 friend class ReturnValue;
968 };
969
970 /**
971 * A traced handle with destructor that clears the handle. For more details see
972 * BasicTracedReference.
973 */
974 template <typename T>
975 class TracedGlobal : public BasicTracedReference<T> {
976 public:
977 using BasicTracedReference<T>::Reset;
978
979 /**
980 * Destructor resetting the handle.Is
981 */
~TracedGlobal()982 ~TracedGlobal() { this->Reset(); }
983
984 /**
985 * An empty TracedGlobal without storage cell.
986 */
TracedGlobal()987 TracedGlobal() : BasicTracedReference<T>() {}
988
989 /**
990 * Construct a TracedGlobal from a Local.
991 *
992 * When the Local is non-empty, a new storage cell is created
993 * pointing to the same object.
994 */
995 template <class S>
TracedGlobal(Isolate * isolate,Local<S> that)996 TracedGlobal(Isolate* isolate, Local<S> that) : BasicTracedReference<T>() {
997 this->val_ = this->New(isolate, that.val_, &this->val_,
998 BasicTracedReference<T>::kWithDestructor);
999 static_assert(std::is_base_of<T, S>::value, "type check");
1000 }
1001
1002 /**
1003 * Move constructor initializing TracedGlobal from an existing one.
1004 */
TracedGlobal(TracedGlobal && other)1005 V8_INLINE TracedGlobal(TracedGlobal&& other) {
1006 // Forward to operator=.
1007 *this = std::move(other);
1008 }
1009
1010 /**
1011 * Move constructor initializing TracedGlobal from an existing one.
1012 */
1013 template <typename S>
TracedGlobal(TracedGlobal<S> && other)1014 V8_INLINE TracedGlobal(TracedGlobal<S>&& other) {
1015 // Forward to operator=.
1016 *this = std::move(other);
1017 }
1018
1019 /**
1020 * Copy constructor initializing TracedGlobal from an existing one.
1021 */
TracedGlobal(const TracedGlobal & other)1022 V8_INLINE TracedGlobal(const TracedGlobal& other) {
1023 // Forward to operator=;
1024 *this = other;
1025 }
1026
1027 /**
1028 * Copy constructor initializing TracedGlobal from an existing one.
1029 */
1030 template <typename S>
TracedGlobal(const TracedGlobal<S> & other)1031 V8_INLINE TracedGlobal(const TracedGlobal<S>& other) {
1032 // Forward to operator=;
1033 *this = other;
1034 }
1035
1036 /**
1037 * Move assignment operator initializing TracedGlobal from an existing one.
1038 */
1039 V8_INLINE TracedGlobal& operator=(TracedGlobal&& rhs);
1040
1041 /**
1042 * Move assignment operator initializing TracedGlobal from an existing one.
1043 */
1044 template <class S>
1045 V8_INLINE TracedGlobal& operator=(TracedGlobal<S>&& rhs);
1046
1047 /**
1048 * Copy assignment operator initializing TracedGlobal from an existing one.
1049 *
1050 * Note: Prohibited when |other| has a finalization callback set through
1051 * |SetFinalizationCallback|.
1052 */
1053 V8_INLINE TracedGlobal& operator=(const TracedGlobal& rhs);
1054
1055 /**
1056 * Copy assignment operator initializing TracedGlobal from an existing one.
1057 *
1058 * Note: Prohibited when |other| has a finalization callback set through
1059 * |SetFinalizationCallback|.
1060 */
1061 template <class S>
1062 V8_INLINE TracedGlobal& operator=(const TracedGlobal<S>& rhs);
1063
1064 /**
1065 * If non-empty, destroy the underlying storage cell and create a new one with
1066 * the contents of other if other is non empty
1067 */
1068 template <class S>
1069 V8_INLINE void Reset(Isolate* isolate, const Local<S>& other);
1070
1071 template <class S>
As()1072 V8_INLINE TracedGlobal<S>& As() const {
1073 return reinterpret_cast<TracedGlobal<S>&>(
1074 const_cast<TracedGlobal<T>&>(*this));
1075 }
1076
1077 /**
1078 * Adds a finalization callback to the handle. The type of this callback is
1079 * similar to WeakCallbackType::kInternalFields, i.e., it will pass the
1080 * parameter and the first two internal fields of the object.
1081 *
1082 * The callback is then supposed to reset the handle in the callback. No
1083 * further V8 API may be called in this callback. In case additional work
1084 * involving V8 needs to be done, a second callback can be scheduled using
1085 * WeakCallbackInfo<void>::SetSecondPassCallback.
1086 */
1087 V8_INLINE void SetFinalizationCallback(
1088 void* parameter, WeakCallbackInfo<void>::Callback callback);
1089 };
1090
1091 /**
1092 * A traced handle without destructor that clears the handle. The embedder needs
1093 * to ensure that the handle is not accessed once the V8 object has been
1094 * reclaimed. This can happen when the handle is not passed through the
1095 * EmbedderHeapTracer. For more details see BasicTracedReference.
1096 *
1097 * The reference assumes the embedder has precise knowledge about references at
1098 * all times. In case V8 needs to separately handle on-stack references, the
1099 * embedder is required to set the stack start through
1100 * |EmbedderHeapTracer::SetStackStart|.
1101 */
1102 template <typename T>
1103 class TracedReference : public BasicTracedReference<T> {
1104 public:
1105 using BasicTracedReference<T>::Reset;
1106
1107 /**
1108 * An empty TracedReference without storage cell.
1109 */
TracedReference()1110 TracedReference() : BasicTracedReference<T>() {}
1111
1112 /**
1113 * Construct a TracedReference from a Local.
1114 *
1115 * When the Local is non-empty, a new storage cell is created
1116 * pointing to the same object.
1117 */
1118 template <class S>
TracedReference(Isolate * isolate,Local<S> that)1119 TracedReference(Isolate* isolate, Local<S> that) : BasicTracedReference<T>() {
1120 this->val_ = this->New(isolate, that.val_, &this->val_,
1121 BasicTracedReference<T>::kWithoutDestructor);
1122 static_assert(std::is_base_of<T, S>::value, "type check");
1123 }
1124
1125 /**
1126 * Move constructor initializing TracedReference from an
1127 * existing one.
1128 */
TracedReference(TracedReference && other)1129 V8_INLINE TracedReference(TracedReference&& other) {
1130 // Forward to operator=.
1131 *this = std::move(other);
1132 }
1133
1134 /**
1135 * Move constructor initializing TracedReference from an
1136 * existing one.
1137 */
1138 template <typename S>
TracedReference(TracedReference<S> && other)1139 V8_INLINE TracedReference(TracedReference<S>&& other) {
1140 // Forward to operator=.
1141 *this = std::move(other);
1142 }
1143
1144 /**
1145 * Copy constructor initializing TracedReference from an
1146 * existing one.
1147 */
TracedReference(const TracedReference & other)1148 V8_INLINE TracedReference(const TracedReference& other) {
1149 // Forward to operator=;
1150 *this = other;
1151 }
1152
1153 /**
1154 * Copy constructor initializing TracedReference from an
1155 * existing one.
1156 */
1157 template <typename S>
TracedReference(const TracedReference<S> & other)1158 V8_INLINE TracedReference(const TracedReference<S>& other) {
1159 // Forward to operator=;
1160 *this = other;
1161 }
1162
1163 /**
1164 * Move assignment operator initializing TracedGlobal from an existing one.
1165 */
1166 V8_INLINE TracedReference& operator=(TracedReference&& rhs);
1167
1168 /**
1169 * Move assignment operator initializing TracedGlobal from an existing one.
1170 */
1171 template <class S>
1172 V8_INLINE TracedReference& operator=(TracedReference<S>&& rhs);
1173
1174 /**
1175 * Copy assignment operator initializing TracedGlobal from an existing one.
1176 */
1177 V8_INLINE TracedReference& operator=(const TracedReference& rhs);
1178
1179 /**
1180 * Copy assignment operator initializing TracedGlobal from an existing one.
1181 */
1182 template <class S>
1183 V8_INLINE TracedReference& operator=(const TracedReference<S>& rhs);
1184
1185 /**
1186 * If non-empty, destroy the underlying storage cell and create a new one with
1187 * the contents of other if other is non empty
1188 */
1189 template <class S>
1190 V8_INLINE void Reset(Isolate* isolate, const Local<S>& other);
1191
1192 template <class S>
As()1193 V8_INLINE TracedReference<S>& As() const {
1194 return reinterpret_cast<TracedReference<S>&>(
1195 const_cast<TracedReference<T>&>(*this));
1196 }
1197 };
1198
1199 /**
1200 * A stack-allocated class that governs a number of local handles.
1201 * After a handle scope has been created, all local handles will be
1202 * allocated within that handle scope until either the handle scope is
1203 * deleted or another handle scope is created. If there is already a
1204 * handle scope and a new one is created, all allocations will take
1205 * place in the new handle scope until it is deleted. After that,
1206 * new handles will again be allocated in the original handle scope.
1207 *
1208 * After the handle scope of a local handle has been deleted the
1209 * garbage collector will no longer track the object stored in the
1210 * handle and may deallocate it. The behavior of accessing a handle
1211 * for which the handle scope has been deleted is undefined.
1212 */
1213 class V8_EXPORT V8_NODISCARD HandleScope {
1214 public:
1215 explicit HandleScope(Isolate* isolate);
1216
1217 ~HandleScope();
1218
1219 /**
1220 * Counts the number of allocated handles.
1221 */
1222 static int NumberOfHandles(Isolate* isolate);
1223
GetIsolate()1224 V8_INLINE Isolate* GetIsolate() const {
1225 return reinterpret_cast<Isolate*>(isolate_);
1226 }
1227
1228 HandleScope(const HandleScope&) = delete;
1229 void operator=(const HandleScope&) = delete;
1230
1231 protected:
1232 V8_INLINE HandleScope() = default;
1233
1234 void Initialize(Isolate* isolate);
1235
1236 static internal::Address* CreateHandle(internal::Isolate* isolate,
1237 internal::Address value);
1238
1239 private:
1240 // Declaring operator new and delete as deleted is not spec compliant.
1241 // Therefore declare them private instead to disable dynamic alloc
1242 void* operator new(size_t size);
1243 void* operator new[](size_t size);
1244 void operator delete(void*, size_t);
1245 void operator delete[](void*, size_t);
1246
1247 internal::Isolate* isolate_;
1248 internal::Address* prev_next_;
1249 internal::Address* prev_limit_;
1250
1251 // Local::New uses CreateHandle with an Isolate* parameter.
1252 template<class F> friend class Local;
1253
1254 // Object::GetInternalField and Context::GetEmbedderData use CreateHandle with
1255 // a HeapObject in their shortcuts.
1256 friend class Object;
1257 friend class Context;
1258 };
1259
1260 /**
1261 * A HandleScope which first allocates a handle in the current scope
1262 * which will be later filled with the escape value.
1263 */
1264 class V8_EXPORT V8_NODISCARD EscapableHandleScope : public HandleScope {
1265 public:
1266 explicit EscapableHandleScope(Isolate* isolate);
1267 V8_INLINE ~EscapableHandleScope() = default;
1268
1269 /**
1270 * Pushes the value into the previous scope and returns a handle to it.
1271 * Cannot be called twice.
1272 */
1273 template <class T>
Escape(Local<T> value)1274 V8_INLINE Local<T> Escape(Local<T> value) {
1275 internal::Address* slot =
1276 Escape(reinterpret_cast<internal::Address*>(*value));
1277 return Local<T>(reinterpret_cast<T*>(slot));
1278 }
1279
1280 template <class T>
EscapeMaybe(MaybeLocal<T> value)1281 V8_INLINE MaybeLocal<T> EscapeMaybe(MaybeLocal<T> value) {
1282 return Escape(value.FromMaybe(Local<T>()));
1283 }
1284
1285 EscapableHandleScope(const EscapableHandleScope&) = delete;
1286 void operator=(const EscapableHandleScope&) = delete;
1287
1288 private:
1289 // Declaring operator new and delete as deleted is not spec compliant.
1290 // Therefore declare them private instead to disable dynamic alloc
1291 void* operator new(size_t size);
1292 void* operator new[](size_t size);
1293 void operator delete(void*, size_t);
1294 void operator delete[](void*, size_t);
1295
1296 internal::Address* Escape(internal::Address* escape_value);
1297 internal::Address* escape_slot_;
1298 };
1299
1300 /**
1301 * A SealHandleScope acts like a handle scope in which no handle allocations
1302 * are allowed. It can be useful for debugging handle leaks.
1303 * Handles can be allocated within inner normal HandleScopes.
1304 */
1305 class V8_EXPORT V8_NODISCARD SealHandleScope {
1306 public:
1307 explicit SealHandleScope(Isolate* isolate);
1308 ~SealHandleScope();
1309
1310 SealHandleScope(const SealHandleScope&) = delete;
1311 void operator=(const SealHandleScope&) = delete;
1312
1313 private:
1314 // Declaring operator new and delete as deleted is not spec compliant.
1315 // Therefore declare them private instead to disable dynamic alloc
1316 void* operator new(size_t size);
1317 void* operator new[](size_t size);
1318 void operator delete(void*, size_t);
1319 void operator delete[](void*, size_t);
1320
1321 internal::Isolate* const isolate_;
1322 internal::Address* prev_limit_;
1323 int prev_sealed_level_;
1324 };
1325
1326 // --- Special objects ---
1327
1328 /**
1329 * The superclass of objects that can reside on V8's heap.
1330 */
1331 class V8_EXPORT Data {
1332 public:
1333 /**
1334 * Returns true if this data is a |v8::Value|.
1335 */
1336 bool IsValue() const;
1337
1338 /**
1339 * Returns true if this data is a |v8::Module|.
1340 */
1341 bool IsModule() const;
1342
1343 /**
1344 * Returns true if this data is a |v8::Private|.
1345 */
1346 bool IsPrivate() const;
1347
1348 /**
1349 * Returns true if this data is a |v8::ObjectTemplate|.
1350 */
1351 bool IsObjectTemplate() const;
1352
1353 /**
1354 * Returns true if this data is a |v8::FunctionTemplate|.
1355 */
1356 bool IsFunctionTemplate() const;
1357
1358 /**
1359 * Returns true if this data is a |v8::Context|.
1360 */
1361 bool IsContext() const;
1362
1363 private:
1364 Data();
1365 };
1366
1367 /**
1368 * A container type that holds relevant metadata for module loading.
1369 *
1370 * This is passed back to the embedder as part of
1371 * HostImportModuleDynamicallyCallback for module loading.
1372 */
1373 class V8_EXPORT ScriptOrModule {
1374 public:
1375 /**
1376 * The name that was passed by the embedder as ResourceName to the
1377 * ScriptOrigin. This can be either a v8::String or v8::Undefined.
1378 */
1379 Local<Value> GetResourceName();
1380
1381 /**
1382 * The options that were passed by the embedder as HostDefinedOptions to
1383 * the ScriptOrigin.
1384 */
1385 Local<PrimitiveArray> GetHostDefinedOptions();
1386 };
1387
1388 /**
1389 * An array to hold Primitive values. This is used by the embedder to
1390 * pass host defined options to the ScriptOptions during compilation.
1391 *
1392 * This is passed back to the embedder as part of
1393 * HostImportModuleDynamicallyCallback for module loading.
1394 *
1395 */
1396 class V8_EXPORT PrimitiveArray {
1397 public:
1398 static Local<PrimitiveArray> New(Isolate* isolate, int length);
1399 int Length() const;
1400 void Set(Isolate* isolate, int index, Local<Primitive> item);
1401 Local<Primitive> Get(Isolate* isolate, int index);
1402 };
1403
1404 /**
1405 * The optional attributes of ScriptOrigin.
1406 */
1407 class ScriptOriginOptions {
1408 public:
1409 V8_INLINE ScriptOriginOptions(bool is_shared_cross_origin = false,
1410 bool is_opaque = false, bool is_wasm = false,
1411 bool is_module = false)
1412 : flags_((is_shared_cross_origin ? kIsSharedCrossOrigin : 0) |
1413 (is_wasm ? kIsWasm : 0) | (is_opaque ? kIsOpaque : 0) |
1414 (is_module ? kIsModule : 0)) {}
ScriptOriginOptions(int flags)1415 V8_INLINE ScriptOriginOptions(int flags)
1416 : flags_(flags &
1417 (kIsSharedCrossOrigin | kIsOpaque | kIsWasm | kIsModule)) {}
1418
IsSharedCrossOrigin()1419 bool IsSharedCrossOrigin() const {
1420 return (flags_ & kIsSharedCrossOrigin) != 0;
1421 }
IsOpaque()1422 bool IsOpaque() const { return (flags_ & kIsOpaque) != 0; }
IsWasm()1423 bool IsWasm() const { return (flags_ & kIsWasm) != 0; }
IsModule()1424 bool IsModule() const { return (flags_ & kIsModule) != 0; }
1425
Flags()1426 int Flags() const { return flags_; }
1427
1428 private:
1429 enum {
1430 kIsSharedCrossOrigin = 1,
1431 kIsOpaque = 1 << 1,
1432 kIsWasm = 1 << 2,
1433 kIsModule = 1 << 3
1434 };
1435 const int flags_;
1436 };
1437
1438 /**
1439 * The origin, within a file, of a script.
1440 */
1441 class ScriptOrigin {
1442 public:
1443 #if defined(_MSC_VER) && _MSC_VER >= 1910 /* Disable on VS2015 */
1444 V8_DEPRECATED("Use constructor with primitive C++ types")
1445 #endif
1446 V8_INLINE explicit ScriptOrigin(
1447 Local<Value> resource_name, Local<Integer> resource_line_offset,
1448 Local<Integer> resource_column_offset,
1449 Local<Boolean> resource_is_shared_cross_origin = Local<Boolean>(),
1450 Local<Integer> script_id = Local<Integer>(),
1451 Local<Value> source_map_url = Local<Value>(),
1452 Local<Boolean> resource_is_opaque = Local<Boolean>(),
1453 Local<Boolean> is_wasm = Local<Boolean>(),
1454 Local<Boolean> is_module = Local<Boolean>(),
1455 Local<PrimitiveArray> host_defined_options = Local<PrimitiveArray>());
1456 #if defined(_MSC_VER) && _MSC_VER >= 1910 /* Disable on VS2015 */
1457 V8_DEPRECATED("Use constructor that takes an isolate")
1458 #endif
1459 V8_INLINE explicit ScriptOrigin(
1460 Local<Value> resource_name, int resource_line_offset = 0,
1461 int resource_column_offset = 0,
1462 bool resource_is_shared_cross_origin = false, int script_id = -1,
1463 Local<Value> source_map_url = Local<Value>(),
1464 bool resource_is_opaque = false, bool is_wasm = false,
1465 bool is_module = false,
1466 Local<PrimitiveArray> host_defined_options = Local<PrimitiveArray>());
1467 V8_INLINE explicit ScriptOrigin(
1468 Isolate* isolate, Local<Value> resource_name,
1469 int resource_line_offset = 0, int resource_column_offset = 0,
1470 bool resource_is_shared_cross_origin = false, int script_id = -1,
1471 Local<Value> source_map_url = Local<Value>(),
1472 bool resource_is_opaque = false, bool is_wasm = false,
1473 bool is_module = false,
1474 Local<PrimitiveArray> host_defined_options = Local<PrimitiveArray>());
1475
1476 V8_INLINE Local<Value> ResourceName() const;
1477 V8_DEPRECATED("Use getter with primitvie C++ types.")
1478 V8_INLINE Local<Integer> ResourceLineOffset() const;
1479 V8_DEPRECATED("Use getter with primitvie C++ types.")
1480 V8_INLINE Local<Integer> ResourceColumnOffset() const;
1481 V8_DEPRECATED("Use getter with primitvie C++ types.")
1482 V8_INLINE Local<Integer> ScriptID() const;
1483 V8_INLINE int LineOffset() const;
1484 V8_INLINE int ColumnOffset() const;
1485 V8_INLINE int ScriptId() const;
1486 V8_INLINE Local<Value> SourceMapUrl() const;
1487 V8_INLINE Local<PrimitiveArray> HostDefinedOptions() const;
Options()1488 V8_INLINE ScriptOriginOptions Options() const { return options_; }
1489
1490 private:
1491 Isolate* isolate_;
1492 Local<Value> resource_name_;
1493 int resource_line_offset_;
1494 int resource_column_offset_;
1495 ScriptOriginOptions options_;
1496 int script_id_;
1497 Local<Value> source_map_url_;
1498 Local<PrimitiveArray> host_defined_options_;
1499 };
1500
1501 /**
1502 * A compiled JavaScript script, not yet tied to a Context.
1503 */
1504 class V8_EXPORT UnboundScript {
1505 public:
1506 /**
1507 * Binds the script to the currently entered context.
1508 */
1509 Local<Script> BindToCurrentContext();
1510
1511 int GetId();
1512 Local<Value> GetScriptName();
1513
1514 /**
1515 * Data read from magic sourceURL comments.
1516 */
1517 Local<Value> GetSourceURL();
1518 /**
1519 * Data read from magic sourceMappingURL comments.
1520 */
1521 Local<Value> GetSourceMappingURL();
1522
1523 /**
1524 * Returns zero based line number of the code_pos location in the script.
1525 * -1 will be returned if no information available.
1526 */
1527 int GetLineNumber(int code_pos);
1528
1529 static const int kNoScriptId = 0;
1530 };
1531
1532 /**
1533 * A compiled JavaScript module, not yet tied to a Context.
1534 */
1535 class V8_EXPORT UnboundModuleScript : public Data {
1536 // Only used as a container for code caching.
1537 };
1538
1539 /**
1540 * A location in JavaScript source.
1541 */
1542 class V8_EXPORT Location {
1543 public:
GetLineNumber()1544 int GetLineNumber() { return line_number_; }
GetColumnNumber()1545 int GetColumnNumber() { return column_number_; }
1546
Location(int line_number,int column_number)1547 Location(int line_number, int column_number)
1548 : line_number_(line_number), column_number_(column_number) {}
1549
1550 private:
1551 int line_number_;
1552 int column_number_;
1553 };
1554
1555 /**
1556 * A fixed-sized array with elements of type Data.
1557 */
1558 class V8_EXPORT FixedArray : public Data {
1559 public:
1560 int Length() const;
1561 Local<Data> Get(Local<Context> context, int i) const;
1562 };
1563
1564 class V8_EXPORT ModuleRequest : public Data {
1565 public:
1566 /**
1567 * Returns the module specifier for this ModuleRequest.
1568 */
1569 Local<String> GetSpecifier() const;
1570
1571 /**
1572 * Returns the source code offset of this module request.
1573 * Use Module::SourceOffsetToLocation to convert this to line/column numbers.
1574 */
1575 int GetSourceOffset() const;
1576
1577 /**
1578 * Contains the import assertions for this request in the form:
1579 * [key1, value1, source_offset1, key2, value2, source_offset2, ...].
1580 * The keys and values are of type v8::String, and the source offsets are of
1581 * type Int32. Use Module::SourceOffsetToLocation to convert the source
1582 * offsets to Locations with line/column numbers.
1583 *
1584 * All assertions present in the module request will be supplied in this
1585 * list, regardless of whether they are supported by the host. Per
1586 * https://tc39.es/proposal-import-assertions/#sec-hostgetsupportedimportassertions,
1587 * hosts are expected to ignore assertions that they do not support (as
1588 * opposed to, for example, triggering an error if an unsupported assertion is
1589 * present).
1590 */
1591 Local<FixedArray> GetImportAssertions() const;
1592
1593 V8_INLINE static ModuleRequest* Cast(Data* data);
1594
1595 private:
1596 static void CheckCast(Data* obj);
1597 };
1598
1599 /**
1600 * A compiled JavaScript module.
1601 */
1602 class V8_EXPORT Module : public Data {
1603 public:
1604 /**
1605 * The different states a module can be in.
1606 *
1607 * This corresponds to the states used in ECMAScript except that "evaluated"
1608 * is split into kEvaluated and kErrored, indicating success and failure,
1609 * respectively.
1610 */
1611 enum Status {
1612 kUninstantiated,
1613 kInstantiating,
1614 kInstantiated,
1615 kEvaluating,
1616 kEvaluated,
1617 kErrored
1618 };
1619
1620 /**
1621 * Returns the module's current status.
1622 */
1623 Status GetStatus() const;
1624
1625 /**
1626 * For a module in kErrored status, this returns the corresponding exception.
1627 */
1628 Local<Value> GetException() const;
1629
1630 /**
1631 * Returns the number of modules requested by this module.
1632 */
1633 V8_DEPRECATED("Use Module::GetModuleRequests() and FixedArray::Length().")
1634 int GetModuleRequestsLength() const;
1635
1636 /**
1637 * Returns the ith module specifier in this module.
1638 * i must be < GetModuleRequestsLength() and >= 0.
1639 */
1640 V8_DEPRECATED(
1641 "Use Module::GetModuleRequests() and ModuleRequest::GetSpecifier().")
1642 Local<String> GetModuleRequest(int i) const;
1643
1644 /**
1645 * Returns the source location (line number and column number) of the ith
1646 * module specifier's first occurrence in this module.
1647 */
1648 V8_DEPRECATED(
1649 "Use Module::GetModuleRequests(), ModuleRequest::GetSourceOffset(), and "
1650 "Module::SourceOffsetToLocation().")
1651 Location GetModuleRequestLocation(int i) const;
1652
1653 /**
1654 * Returns the ModuleRequests for this module.
1655 */
1656 Local<FixedArray> GetModuleRequests() const;
1657
1658 /**
1659 * For the given source text offset in this module, returns the corresponding
1660 * Location with line and column numbers.
1661 */
1662 Location SourceOffsetToLocation(int offset) const;
1663
1664 /**
1665 * Returns the identity hash for this object.
1666 */
1667 int GetIdentityHash() const;
1668
1669 using ResolveCallback =
1670 MaybeLocal<Module> (*)(Local<Context> context, Local<String> specifier,
1671 Local<Module> referrer);
1672 using ResolveModuleCallback = MaybeLocal<Module> (*)(
1673 Local<Context> context, Local<String> specifier,
1674 Local<FixedArray> import_assertions, Local<Module> referrer);
1675
1676 /**
1677 * Instantiates the module and its dependencies.
1678 *
1679 * Returns an empty Maybe<bool> if an exception occurred during
1680 * instantiation. (In the case where the callback throws an exception, that
1681 * exception is propagated.)
1682 */
1683 V8_DEPRECATED(
1684 "Use the version of InstantiateModule that takes a ResolveModuleCallback "
1685 "parameter")
1686 V8_WARN_UNUSED_RESULT Maybe<bool> InstantiateModule(Local<Context> context,
1687 ResolveCallback callback);
1688 V8_WARN_UNUSED_RESULT Maybe<bool> InstantiateModule(
1689 Local<Context> context, ResolveModuleCallback callback);
1690
1691 /**
1692 * Evaluates the module and its dependencies.
1693 *
1694 * If status is kInstantiated, run the module's code and return a Promise
1695 * object. On success, set status to kEvaluated and resolve the Promise with
1696 * the completion value; on failure, set status to kErrored and reject the
1697 * Promise with the error.
1698 *
1699 * If IsGraphAsync() is false, the returned Promise is settled.
1700 */
1701 V8_WARN_UNUSED_RESULT MaybeLocal<Value> Evaluate(Local<Context> context);
1702
1703 /**
1704 * Returns the namespace object of this module.
1705 *
1706 * The module's status must be at least kInstantiated.
1707 */
1708 Local<Value> GetModuleNamespace();
1709
1710 /**
1711 * Returns the corresponding context-unbound module script.
1712 *
1713 * The module must be unevaluated, i.e. its status must not be kEvaluating,
1714 * kEvaluated or kErrored.
1715 */
1716 Local<UnboundModuleScript> GetUnboundModuleScript();
1717
1718 /**
1719 * Returns the underlying script's id.
1720 *
1721 * The module must be a SourceTextModule and must not have a kErrored status.
1722 */
1723 int ScriptId();
1724
1725 /**
1726 * Returns whether this module or any of its requested modules is async,
1727 * i.e. contains top-level await.
1728 *
1729 * The module's status must be at least kInstantiated.
1730 */
1731 bool IsGraphAsync() const;
1732
1733 /**
1734 * Returns whether the module is a SourceTextModule.
1735 */
1736 bool IsSourceTextModule() const;
1737
1738 /**
1739 * Returns whether the module is a SyntheticModule.
1740 */
1741 bool IsSyntheticModule() const;
1742
1743 /*
1744 * Callback defined in the embedder. This is responsible for setting
1745 * the module's exported values with calls to SetSyntheticModuleExport().
1746 * The callback must return a resolved Promise to indicate success (where no
1747 * exception was thrown) and return an empy MaybeLocal to indicate falure
1748 * (where an exception was thrown).
1749 */
1750 using SyntheticModuleEvaluationSteps =
1751 MaybeLocal<Value> (*)(Local<Context> context, Local<Module> module);
1752
1753 /**
1754 * Creates a new SyntheticModule with the specified export names, where
1755 * evaluation_steps will be executed upon module evaluation.
1756 * export_names must not contain duplicates.
1757 * module_name is used solely for logging/debugging and doesn't affect module
1758 * behavior.
1759 */
1760 static Local<Module> CreateSyntheticModule(
1761 Isolate* isolate, Local<String> module_name,
1762 const std::vector<Local<String>>& export_names,
1763 SyntheticModuleEvaluationSteps evaluation_steps);
1764
1765 /**
1766 * Set this module's exported value for the name export_name to the specified
1767 * export_value. This method must be called only on Modules created via
1768 * CreateSyntheticModule. An error will be thrown if export_name is not one
1769 * of the export_names that were passed in that CreateSyntheticModule call.
1770 * Returns Just(true) on success, Nothing<bool>() if an error was thrown.
1771 */
1772 V8_WARN_UNUSED_RESULT Maybe<bool> SetSyntheticModuleExport(
1773 Isolate* isolate, Local<String> export_name, Local<Value> export_value);
1774 V8_DEPRECATED(
1775 "Use the preceding SetSyntheticModuleExport with an Isolate parameter, "
1776 "instead of the one that follows. The former will throw a runtime "
1777 "error if called for an export that doesn't exist (as per spec); "
1778 "the latter will crash with a failed CHECK().")
1779 void SetSyntheticModuleExport(Local<String> export_name,
1780 Local<Value> export_value);
1781
1782 V8_INLINE static Module* Cast(Data* data);
1783
1784 private:
1785 static void CheckCast(Data* obj);
1786 };
1787
1788 /**
1789 * A compiled JavaScript script, tied to a Context which was active when the
1790 * script was compiled.
1791 */
1792 class V8_EXPORT Script {
1793 public:
1794 /**
1795 * A shorthand for ScriptCompiler::Compile().
1796 */
1797 static V8_WARN_UNUSED_RESULT MaybeLocal<Script> Compile(
1798 Local<Context> context, Local<String> source,
1799 ScriptOrigin* origin = nullptr);
1800
1801 /**
1802 * Runs the script returning the resulting value. It will be run in the
1803 * context in which it was created (ScriptCompiler::CompileBound or
1804 * UnboundScript::BindToCurrentContext()).
1805 */
1806 V8_WARN_UNUSED_RESULT MaybeLocal<Value> Run(Local<Context> context);
1807
1808 /**
1809 * Returns the corresponding context-unbound script.
1810 */
1811 Local<UnboundScript> GetUnboundScript();
1812 };
1813
1814 enum class ScriptType { kClassic, kModule };
1815
1816 /**
1817 * For compiling scripts.
1818 */
1819 class V8_EXPORT ScriptCompiler {
1820 public:
1821 /**
1822 * Compilation data that the embedder can cache and pass back to speed up
1823 * future compilations. The data is produced if the CompilerOptions passed to
1824 * the compilation functions in ScriptCompiler contains produce_data_to_cache
1825 * = true. The data to cache can then can be retrieved from
1826 * UnboundScript.
1827 */
1828 struct V8_EXPORT CachedData {
1829 enum BufferPolicy {
1830 BufferNotOwned,
1831 BufferOwned
1832 };
1833
CachedDataCachedData1834 CachedData()
1835 : data(nullptr),
1836 length(0),
1837 rejected(false),
1838 buffer_policy(BufferNotOwned) {}
1839
1840 // If buffer_policy is BufferNotOwned, the caller keeps the ownership of
1841 // data and guarantees that it stays alive until the CachedData object is
1842 // destroyed. If the policy is BufferOwned, the given data will be deleted
1843 // (with delete[]) when the CachedData object is destroyed.
1844 CachedData(const uint8_t* data, int length,
1845 BufferPolicy buffer_policy = BufferNotOwned);
1846 ~CachedData();
1847 // TODO(marja): Async compilation; add constructors which take a callback
1848 // which will be called when V8 no longer needs the data.
1849 const uint8_t* data;
1850 int length;
1851 bool rejected;
1852 BufferPolicy buffer_policy;
1853
1854 // Prevent copying.
1855 CachedData(const CachedData&) = delete;
1856 CachedData& operator=(const CachedData&) = delete;
1857 };
1858
1859 /**
1860 * Source code which can be then compiled to a UnboundScript or Script.
1861 */
1862 class Source {
1863 public:
1864 // Source takes ownership of CachedData.
1865 V8_INLINE Source(Local<String> source_string, const ScriptOrigin& origin,
1866 CachedData* cached_data = nullptr);
1867 V8_INLINE explicit Source(Local<String> source_string,
1868 CachedData* cached_data = nullptr);
1869 V8_INLINE ~Source();
1870
1871 // Ownership of the CachedData or its buffers is *not* transferred to the
1872 // caller. The CachedData object is alive as long as the Source object is
1873 // alive.
1874 V8_INLINE const CachedData* GetCachedData() const;
1875
1876 V8_INLINE const ScriptOriginOptions& GetResourceOptions() const;
1877
1878 // Prevent copying.
1879 Source(const Source&) = delete;
1880 Source& operator=(const Source&) = delete;
1881
1882 private:
1883 friend class ScriptCompiler;
1884
1885 Local<String> source_string;
1886
1887 // Origin information
1888 Local<Value> resource_name;
1889 int resource_line_offset;
1890 int resource_column_offset;
1891 ScriptOriginOptions resource_options;
1892 Local<Value> source_map_url;
1893 Local<PrimitiveArray> host_defined_options;
1894
1895 // Cached data from previous compilation (if a kConsume*Cache flag is
1896 // set), or hold newly generated cache data (kProduce*Cache flags) are
1897 // set when calling a compile method.
1898 CachedData* cached_data;
1899 };
1900
1901 /**
1902 * For streaming incomplete script data to V8. The embedder should implement a
1903 * subclass of this class.
1904 */
1905 class V8_EXPORT ExternalSourceStream {
1906 public:
1907 virtual ~ExternalSourceStream() = default;
1908
1909 /**
1910 * V8 calls this to request the next chunk of data from the embedder. This
1911 * function will be called on a background thread, so it's OK to block and
1912 * wait for the data, if the embedder doesn't have data yet. Returns the
1913 * length of the data returned. When the data ends, GetMoreData should
1914 * return 0. Caller takes ownership of the data.
1915 *
1916 * When streaming UTF-8 data, V8 handles multi-byte characters split between
1917 * two data chunks, but doesn't handle multi-byte characters split between
1918 * more than two data chunks. The embedder can avoid this problem by always
1919 * returning at least 2 bytes of data.
1920 *
1921 * When streaming UTF-16 data, V8 does not handle characters split between
1922 * two data chunks. The embedder has to make sure that chunks have an even
1923 * length.
1924 *
1925 * If the embedder wants to cancel the streaming, they should make the next
1926 * GetMoreData call return 0. V8 will interpret it as end of data (and most
1927 * probably, parsing will fail). The streaming task will return as soon as
1928 * V8 has parsed the data it received so far.
1929 */
1930 virtual size_t GetMoreData(const uint8_t** src) = 0;
1931
1932 /**
1933 * V8 calls this method to set a 'bookmark' at the current position in
1934 * the source stream, for the purpose of (maybe) later calling
1935 * ResetToBookmark. If ResetToBookmark is called later, then subsequent
1936 * calls to GetMoreData should return the same data as they did when
1937 * SetBookmark was called earlier.
1938 *
1939 * The embedder may return 'false' to indicate it cannot provide this
1940 * functionality.
1941 */
1942 virtual bool SetBookmark();
1943
1944 /**
1945 * V8 calls this to return to a previously set bookmark.
1946 */
1947 virtual void ResetToBookmark();
1948 };
1949
1950 /**
1951 * Source code which can be streamed into V8 in pieces. It will be parsed
1952 * while streaming and compiled after parsing has completed. StreamedSource
1953 * must be kept alive while the streaming task is run (see ScriptStreamingTask
1954 * below).
1955 */
1956 class V8_EXPORT StreamedSource {
1957 public:
1958 enum Encoding { ONE_BYTE, TWO_BYTE, UTF8, WINDOWS_1252 };
1959
1960 #if defined(_MSC_VER) && _MSC_VER >= 1910 /* Disable on VS2015 */
1961 V8_DEPRECATED(
1962 "This class takes ownership of source_stream, so use the constructor "
1963 "taking a unique_ptr to make these semantics clearer")
1964 #endif
1965 StreamedSource(ExternalSourceStream* source_stream, Encoding encoding);
1966 StreamedSource(std::unique_ptr<ExternalSourceStream> source_stream,
1967 Encoding encoding);
1968 ~StreamedSource();
1969
impl()1970 internal::ScriptStreamingData* impl() const { return impl_.get(); }
1971
1972 // Prevent copying.
1973 StreamedSource(const StreamedSource&) = delete;
1974 StreamedSource& operator=(const StreamedSource&) = delete;
1975
1976 private:
1977 std::unique_ptr<internal::ScriptStreamingData> impl_;
1978 };
1979
1980 /**
1981 * A streaming task which the embedder must run on a background thread to
1982 * stream scripts into V8. Returned by ScriptCompiler::StartStreaming.
1983 */
1984 class V8_EXPORT ScriptStreamingTask final {
1985 public:
1986 void Run();
1987
1988 private:
1989 friend class ScriptCompiler;
1990
ScriptStreamingTask(internal::ScriptStreamingData * data)1991 explicit ScriptStreamingTask(internal::ScriptStreamingData* data)
1992 : data_(data) {}
1993
1994 internal::ScriptStreamingData* data_;
1995 };
1996
1997 enum CompileOptions {
1998 kNoCompileOptions = 0,
1999 kConsumeCodeCache,
2000 kEagerCompile
2001 };
2002
2003 /**
2004 * The reason for which we are not requesting or providing a code cache.
2005 */
2006 enum NoCacheReason {
2007 kNoCacheNoReason = 0,
2008 kNoCacheBecauseCachingDisabled,
2009 kNoCacheBecauseNoResource,
2010 kNoCacheBecauseInlineScript,
2011 kNoCacheBecauseModule,
2012 kNoCacheBecauseStreamingSource,
2013 kNoCacheBecauseInspector,
2014 kNoCacheBecauseScriptTooSmall,
2015 kNoCacheBecauseCacheTooCold,
2016 kNoCacheBecauseV8Extension,
2017 kNoCacheBecauseExtensionModule,
2018 kNoCacheBecausePacScript,
2019 kNoCacheBecauseInDocumentWrite,
2020 kNoCacheBecauseResourceWithNoCacheHandler,
2021 kNoCacheBecauseDeferredProduceCodeCache
2022 };
2023
2024 /**
2025 * Compiles the specified script (context-independent).
2026 * Cached data as part of the source object can be optionally produced to be
2027 * consumed later to speed up compilation of identical source scripts.
2028 *
2029 * Note that when producing cached data, the source must point to NULL for
2030 * cached data. When consuming cached data, the cached data must have been
2031 * produced by the same version of V8, and the embedder needs to ensure the
2032 * cached data is the correct one for the given script.
2033 *
2034 * \param source Script source code.
2035 * \return Compiled script object (context independent; for running it must be
2036 * bound to a context).
2037 */
2038 static V8_WARN_UNUSED_RESULT MaybeLocal<UnboundScript> CompileUnboundScript(
2039 Isolate* isolate, Source* source,
2040 CompileOptions options = kNoCompileOptions,
2041 NoCacheReason no_cache_reason = kNoCacheNoReason);
2042
2043 /**
2044 * Compiles the specified script (bound to current context).
2045 *
2046 * \param source Script source code.
2047 * \param pre_data Pre-parsing data, as obtained by ScriptData::PreCompile()
2048 * using pre_data speeds compilation if it's done multiple times.
2049 * Owned by caller, no references are kept when this function returns.
2050 * \return Compiled script object, bound to the context that was active
2051 * when this function was called. When run it will always use this
2052 * context.
2053 */
2054 static V8_WARN_UNUSED_RESULT MaybeLocal<Script> Compile(
2055 Local<Context> context, Source* source,
2056 CompileOptions options = kNoCompileOptions,
2057 NoCacheReason no_cache_reason = kNoCacheNoReason);
2058
2059 /**
2060 * Returns a task which streams script data into V8, or NULL if the script
2061 * cannot be streamed. The user is responsible for running the task on a
2062 * background thread and deleting it. When ran, the task starts parsing the
2063 * script, and it will request data from the StreamedSource as needed. When
2064 * ScriptStreamingTask::Run exits, all data has been streamed and the script
2065 * can be compiled (see Compile below).
2066 *
2067 * This API allows to start the streaming with as little data as possible, and
2068 * the remaining data (for example, the ScriptOrigin) is passed to Compile.
2069 */
2070 V8_DEPRECATED("Use ScriptCompiler::StartStreaming instead.")
2071 static ScriptStreamingTask* StartStreamingScript(
2072 Isolate* isolate, StreamedSource* source,
2073 CompileOptions options = kNoCompileOptions);
2074 static ScriptStreamingTask* StartStreaming(
2075 Isolate* isolate, StreamedSource* source,
2076 ScriptType type = ScriptType::kClassic);
2077
2078 /**
2079 * Compiles a streamed script (bound to current context).
2080 *
2081 * This can only be called after the streaming has finished
2082 * (ScriptStreamingTask has been run). V8 doesn't construct the source string
2083 * during streaming, so the embedder needs to pass the full source here.
2084 */
2085 static V8_WARN_UNUSED_RESULT MaybeLocal<Script> Compile(
2086 Local<Context> context, StreamedSource* source,
2087 Local<String> full_source_string, const ScriptOrigin& origin);
2088
2089 /**
2090 * Return a version tag for CachedData for the current V8 version & flags.
2091 *
2092 * This value is meant only for determining whether a previously generated
2093 * CachedData instance is still valid; the tag has no other meaing.
2094 *
2095 * Background: The data carried by CachedData may depend on the exact
2096 * V8 version number or current compiler flags. This means that when
2097 * persisting CachedData, the embedder must take care to not pass in
2098 * data from another V8 version, or the same version with different
2099 * features enabled.
2100 *
2101 * The easiest way to do so is to clear the embedder's cache on any
2102 * such change.
2103 *
2104 * Alternatively, this tag can be stored alongside the cached data and
2105 * compared when it is being used.
2106 */
2107 static uint32_t CachedDataVersionTag();
2108
2109 /**
2110 * Compile an ES module, returning a Module that encapsulates
2111 * the compiled code.
2112 *
2113 * Corresponds to the ParseModule abstract operation in the
2114 * ECMAScript specification.
2115 */
2116 static V8_WARN_UNUSED_RESULT MaybeLocal<Module> CompileModule(
2117 Isolate* isolate, Source* source,
2118 CompileOptions options = kNoCompileOptions,
2119 NoCacheReason no_cache_reason = kNoCacheNoReason);
2120
2121 /**
2122 * Compiles a streamed module script.
2123 *
2124 * This can only be called after the streaming has finished
2125 * (ScriptStreamingTask has been run). V8 doesn't construct the source string
2126 * during streaming, so the embedder needs to pass the full source here.
2127 */
2128 static V8_WARN_UNUSED_RESULT MaybeLocal<Module> CompileModule(
2129 Local<Context> context, StreamedSource* v8_source,
2130 Local<String> full_source_string, const ScriptOrigin& origin);
2131
2132 /**
2133 * Compile a function for a given context. This is equivalent to running
2134 *
2135 * with (obj) {
2136 * return function(args) { ... }
2137 * }
2138 *
2139 * It is possible to specify multiple context extensions (obj in the above
2140 * example).
2141 */
2142 static V8_WARN_UNUSED_RESULT MaybeLocal<Function> CompileFunctionInContext(
2143 Local<Context> context, Source* source, size_t arguments_count,
2144 Local<String> arguments[], size_t context_extension_count,
2145 Local<Object> context_extensions[],
2146 CompileOptions options = kNoCompileOptions,
2147 NoCacheReason no_cache_reason = kNoCacheNoReason,
2148 Local<ScriptOrModule>* script_or_module_out = nullptr);
2149
2150 /**
2151 * Creates and returns code cache for the specified unbound_script.
2152 * This will return nullptr if the script cannot be serialized. The
2153 * CachedData returned by this function should be owned by the caller.
2154 */
2155 static CachedData* CreateCodeCache(Local<UnboundScript> unbound_script);
2156
2157 /**
2158 * Creates and returns code cache for the specified unbound_module_script.
2159 * This will return nullptr if the script cannot be serialized. The
2160 * CachedData returned by this function should be owned by the caller.
2161 */
2162 static CachedData* CreateCodeCache(
2163 Local<UnboundModuleScript> unbound_module_script);
2164
2165 /**
2166 * Creates and returns code cache for the specified function that was
2167 * previously produced by CompileFunctionInContext.
2168 * This will return nullptr if the script cannot be serialized. The
2169 * CachedData returned by this function should be owned by the caller.
2170 */
2171 static CachedData* CreateCodeCacheForFunction(Local<Function> function);
2172
2173 private:
2174 static V8_WARN_UNUSED_RESULT MaybeLocal<UnboundScript> CompileUnboundInternal(
2175 Isolate* isolate, Source* source, CompileOptions options,
2176 NoCacheReason no_cache_reason);
2177 };
2178
2179
2180 /**
2181 * An error message.
2182 */
2183 class V8_EXPORT Message {
2184 public:
2185 Local<String> Get() const;
2186
2187 /**
2188 * Return the isolate to which the Message belongs.
2189 */
2190 Isolate* GetIsolate() const;
2191
2192 V8_WARN_UNUSED_RESULT MaybeLocal<String> GetSource(
2193 Local<Context> context) const;
2194 V8_WARN_UNUSED_RESULT MaybeLocal<String> GetSourceLine(
2195 Local<Context> context) const;
2196
2197 /**
2198 * Returns the origin for the script from where the function causing the
2199 * error originates.
2200 */
2201 ScriptOrigin GetScriptOrigin() const;
2202
2203 /**
2204 * Returns the resource name for the script from where the function causing
2205 * the error originates.
2206 */
2207 Local<Value> GetScriptResourceName() const;
2208
2209 /**
2210 * Exception stack trace. By default stack traces are not captured for
2211 * uncaught exceptions. SetCaptureStackTraceForUncaughtExceptions allows
2212 * to change this option.
2213 */
2214 Local<StackTrace> GetStackTrace() const;
2215
2216 /**
2217 * Returns the number, 1-based, of the line where the error occurred.
2218 */
2219 V8_WARN_UNUSED_RESULT Maybe<int> GetLineNumber(Local<Context> context) const;
2220
2221 /**
2222 * Returns the index within the script of the first character where
2223 * the error occurred.
2224 */
2225 int GetStartPosition() const;
2226
2227 /**
2228 * Returns the index within the script of the last character where
2229 * the error occurred.
2230 */
2231 int GetEndPosition() const;
2232
2233 /**
2234 * Returns the Wasm function index where the error occurred. Returns -1 if
2235 * message is not from a Wasm script.
2236 */
2237 int GetWasmFunctionIndex() const;
2238
2239 /**
2240 * Returns the error level of the message.
2241 */
2242 int ErrorLevel() const;
2243
2244 /**
2245 * Returns the index within the line of the first character where
2246 * the error occurred.
2247 */
2248 int GetStartColumn() const;
2249 V8_WARN_UNUSED_RESULT Maybe<int> GetStartColumn(Local<Context> context) const;
2250
2251 /**
2252 * Returns the index within the line of the last character where
2253 * the error occurred.
2254 */
2255 int GetEndColumn() const;
2256 V8_WARN_UNUSED_RESULT Maybe<int> GetEndColumn(Local<Context> context) const;
2257
2258 /**
2259 * Passes on the value set by the embedder when it fed the script from which
2260 * this Message was generated to V8.
2261 */
2262 bool IsSharedCrossOrigin() const;
2263 bool IsOpaque() const;
2264
2265 // TODO(1245381): Print to a string instead of on a FILE.
2266 static void PrintCurrentStackTrace(Isolate* isolate, FILE* out);
2267
2268 static const int kNoLineNumberInfo = 0;
2269 static const int kNoColumnInfo = 0;
2270 static const int kNoScriptIdInfo = 0;
2271 static const int kNoWasmFunctionIndexInfo = -1;
2272 };
2273
2274
2275 /**
2276 * Representation of a JavaScript stack trace. The information collected is a
2277 * snapshot of the execution stack and the information remains valid after
2278 * execution continues.
2279 */
2280 class V8_EXPORT StackTrace {
2281 public:
2282 /**
2283 * Flags that determine what information is placed captured for each
2284 * StackFrame when grabbing the current stack trace.
2285 * Note: these options are deprecated and we always collect all available
2286 * information (kDetailed).
2287 */
2288 enum StackTraceOptions {
2289 kLineNumber = 1,
2290 kColumnOffset = 1 << 1 | kLineNumber,
2291 kScriptName = 1 << 2,
2292 kFunctionName = 1 << 3,
2293 kIsEval = 1 << 4,
2294 kIsConstructor = 1 << 5,
2295 kScriptNameOrSourceURL = 1 << 6,
2296 kScriptId = 1 << 7,
2297 kExposeFramesAcrossSecurityOrigins = 1 << 8,
2298 kOverview = kLineNumber | kColumnOffset | kScriptName | kFunctionName,
2299 kDetailed = kOverview | kIsEval | kIsConstructor | kScriptNameOrSourceURL
2300 };
2301
2302 /**
2303 * Returns a StackFrame at a particular index.
2304 */
2305 Local<StackFrame> GetFrame(Isolate* isolate, uint32_t index) const;
2306
2307 /**
2308 * Returns the number of StackFrames.
2309 */
2310 int GetFrameCount() const;
2311
2312 /**
2313 * Grab a snapshot of the current JavaScript execution stack.
2314 *
2315 * \param frame_limit The maximum number of stack frames we want to capture.
2316 * \param options Enumerates the set of things we will capture for each
2317 * StackFrame.
2318 */
2319 static Local<StackTrace> CurrentStackTrace(
2320 Isolate* isolate, int frame_limit, StackTraceOptions options = kDetailed);
2321 };
2322
2323
2324 /**
2325 * A single JavaScript stack frame.
2326 */
2327 class V8_EXPORT StackFrame {
2328 public:
2329 /**
2330 * Returns the number, 1-based, of the line for the associate function call.
2331 * This method will return Message::kNoLineNumberInfo if it is unable to
2332 * retrieve the line number, or if kLineNumber was not passed as an option
2333 * when capturing the StackTrace.
2334 */
2335 int GetLineNumber() const;
2336
2337 /**
2338 * Returns the 1-based column offset on the line for the associated function
2339 * call.
2340 * This method will return Message::kNoColumnInfo if it is unable to retrieve
2341 * the column number, or if kColumnOffset was not passed as an option when
2342 * capturing the StackTrace.
2343 */
2344 int GetColumn() const;
2345
2346 /**
2347 * Returns the id of the script for the function for this StackFrame.
2348 * This method will return Message::kNoScriptIdInfo if it is unable to
2349 * retrieve the script id, or if kScriptId was not passed as an option when
2350 * capturing the StackTrace.
2351 */
2352 int GetScriptId() const;
2353
2354 /**
2355 * Returns the name of the resource that contains the script for the
2356 * function for this StackFrame.
2357 */
2358 Local<String> GetScriptName() const;
2359
2360 /**
2361 * Returns the name of the resource that contains the script for the
2362 * function for this StackFrame or sourceURL value if the script name
2363 * is undefined and its source ends with //# sourceURL=... string or
2364 * deprecated //@ sourceURL=... string.
2365 */
2366 Local<String> GetScriptNameOrSourceURL() const;
2367
2368 /**
2369 * Returns the source of the script for the function for this StackFrame.
2370 */
2371 Local<String> GetScriptSource() const;
2372
2373 /**
2374 * Returns the source mapping URL (if one is present) of the script for
2375 * the function for this StackFrame.
2376 */
2377 Local<String> GetScriptSourceMappingURL() const;
2378
2379 /**
2380 * Returns the name of the function associated with this stack frame.
2381 */
2382 Local<String> GetFunctionName() const;
2383
2384 /**
2385 * Returns whether or not the associated function is compiled via a call to
2386 * eval().
2387 */
2388 bool IsEval() const;
2389
2390 /**
2391 * Returns whether or not the associated function is called as a
2392 * constructor via "new".
2393 */
2394 bool IsConstructor() const;
2395
2396 /**
2397 * Returns whether or not the associated functions is defined in wasm.
2398 */
2399 bool IsWasm() const;
2400
2401 /**
2402 * Returns whether or not the associated function is defined by the user.
2403 */
2404 bool IsUserJavaScript() const;
2405 };
2406
2407
2408 // A StateTag represents a possible state of the VM.
2409 enum StateTag {
2410 JS,
2411 GC,
2412 PARSER,
2413 BYTECODE_COMPILER,
2414 COMPILER,
2415 OTHER,
2416 EXTERNAL,
2417 ATOMICS_WAIT,
2418 IDLE
2419 };
2420
2421 // Holds the callee saved registers needed for the stack unwinder. It is the
2422 // empty struct if no registers are required. Implemented in
2423 // include/v8-unwinder-state.h.
2424 struct CalleeSavedRegisters;
2425
2426 // A RegisterState represents the current state of registers used
2427 // by the sampling profiler API.
2428 struct V8_EXPORT RegisterState {
2429 RegisterState();
2430 ~RegisterState();
2431 RegisterState(const RegisterState& other);
2432 RegisterState& operator=(const RegisterState& other);
2433
2434 void* pc; // Instruction pointer.
2435 void* sp; // Stack pointer.
2436 void* fp; // Frame pointer.
2437 void* lr; // Link register (or nullptr on platforms without a link register).
2438 // Callee saved registers (or null if no callee saved registers were stored)
2439 std::unique_ptr<CalleeSavedRegisters> callee_saved;
2440 };
2441
2442 // The output structure filled up by GetStackSample API function.
2443 struct SampleInfo {
2444 size_t frames_count; // Number of frames collected.
2445 StateTag vm_state; // Current VM state.
2446 void* external_callback_entry; // External callback address if VM is
2447 // executing an external callback.
2448 void* top_context; // Incumbent native context address.
2449 };
2450
2451 struct MemoryRange {
2452 const void* start = nullptr;
2453 size_t length_in_bytes = 0;
2454 };
2455
2456 struct JSEntryStub {
2457 MemoryRange code;
2458 };
2459
2460 struct JSEntryStubs {
2461 JSEntryStub js_entry_stub;
2462 JSEntryStub js_construct_entry_stub;
2463 JSEntryStub js_run_microtasks_entry_stub;
2464 };
2465
2466 /**
2467 * A JSON Parser and Stringifier.
2468 */
2469 class V8_EXPORT JSON {
2470 public:
2471 /**
2472 * Tries to parse the string |json_string| and returns it as value if
2473 * successful.
2474 *
2475 * \param the context in which to parse and create the value.
2476 * \param json_string The string to parse.
2477 * \return The corresponding value if successfully parsed.
2478 */
2479 static V8_WARN_UNUSED_RESULT MaybeLocal<Value> Parse(
2480 Local<Context> context, Local<String> json_string);
2481
2482 /**
2483 * Tries to stringify the JSON-serializable object |json_object| and returns
2484 * it as string if successful.
2485 *
2486 * \param json_object The JSON-serializable object to stringify.
2487 * \return The corresponding string if successfully stringified.
2488 */
2489 static V8_WARN_UNUSED_RESULT MaybeLocal<String> Stringify(
2490 Local<Context> context, Local<Value> json_object,
2491 Local<String> gap = Local<String>());
2492 };
2493
2494 /**
2495 * Value serialization compatible with the HTML structured clone algorithm.
2496 * The format is backward-compatible (i.e. safe to store to disk).
2497 */
2498 class V8_EXPORT ValueSerializer {
2499 public:
2500 class V8_EXPORT Delegate {
2501 public:
2502 virtual ~Delegate() = default;
2503
2504 /**
2505 * Handles the case where a DataCloneError would be thrown in the structured
2506 * clone spec. Other V8 embedders may throw some other appropriate exception
2507 * type.
2508 */
2509 virtual void ThrowDataCloneError(Local<String> message) = 0;
2510
2511 /**
2512 * The embedder overrides this method to write some kind of host object, if
2513 * possible. If not, a suitable exception should be thrown and
2514 * Nothing<bool>() returned.
2515 */
2516 virtual Maybe<bool> WriteHostObject(Isolate* isolate, Local<Object> object);
2517
2518 /**
2519 * Called when the ValueSerializer is going to serialize a
2520 * SharedArrayBuffer object. The embedder must return an ID for the
2521 * object, using the same ID if this SharedArrayBuffer has already been
2522 * serialized in this buffer. When deserializing, this ID will be passed to
2523 * ValueDeserializer::GetSharedArrayBufferFromId as |clone_id|.
2524 *
2525 * If the object cannot be serialized, an
2526 * exception should be thrown and Nothing<uint32_t>() returned.
2527 */
2528 virtual Maybe<uint32_t> GetSharedArrayBufferId(
2529 Isolate* isolate, Local<SharedArrayBuffer> shared_array_buffer);
2530
2531 virtual Maybe<uint32_t> GetWasmModuleTransferId(
2532 Isolate* isolate, Local<WasmModuleObject> module);
2533 /**
2534 * Allocates memory for the buffer of at least the size provided. The actual
2535 * size (which may be greater or equal) is written to |actual_size|. If no
2536 * buffer has been allocated yet, nullptr will be provided.
2537 *
2538 * If the memory cannot be allocated, nullptr should be returned.
2539 * |actual_size| will be ignored. It is assumed that |old_buffer| is still
2540 * valid in this case and has not been modified.
2541 *
2542 * The default implementation uses the stdlib's `realloc()` function.
2543 */
2544 virtual void* ReallocateBufferMemory(void* old_buffer, size_t size,
2545 size_t* actual_size);
2546
2547 /**
2548 * Frees a buffer allocated with |ReallocateBufferMemory|.
2549 *
2550 * The default implementation uses the stdlib's `free()` function.
2551 */
2552 virtual void FreeBufferMemory(void* buffer);
2553 };
2554
2555 explicit ValueSerializer(Isolate* isolate);
2556 ValueSerializer(Isolate* isolate, Delegate* delegate);
2557 ~ValueSerializer();
2558
2559 /**
2560 * Writes out a header, which includes the format version.
2561 */
2562 void WriteHeader();
2563
2564 /**
2565 * Serializes a JavaScript value into the buffer.
2566 */
2567 V8_WARN_UNUSED_RESULT Maybe<bool> WriteValue(Local<Context> context,
2568 Local<Value> value);
2569
2570 /**
2571 * Returns the stored data (allocated using the delegate's
2572 * ReallocateBufferMemory) and its size. This serializer should not be used
2573 * once the buffer is released. The contents are undefined if a previous write
2574 * has failed. Ownership of the buffer is transferred to the caller.
2575 */
2576 V8_WARN_UNUSED_RESULT std::pair<uint8_t*, size_t> Release();
2577
2578 /**
2579 * Marks an ArrayBuffer as havings its contents transferred out of band.
2580 * Pass the corresponding ArrayBuffer in the deserializing context to
2581 * ValueDeserializer::TransferArrayBuffer.
2582 */
2583 void TransferArrayBuffer(uint32_t transfer_id,
2584 Local<ArrayBuffer> array_buffer);
2585
2586
2587 /**
2588 * Indicate whether to treat ArrayBufferView objects as host objects,
2589 * i.e. pass them to Delegate::WriteHostObject. This should not be
2590 * called when no Delegate was passed.
2591 *
2592 * The default is not to treat ArrayBufferViews as host objects.
2593 */
2594 void SetTreatArrayBufferViewsAsHostObjects(bool mode);
2595
2596 /**
2597 * Write raw data in various common formats to the buffer.
2598 * Note that integer types are written in base-128 varint format, not with a
2599 * binary copy. For use during an override of Delegate::WriteHostObject.
2600 */
2601 void WriteUint32(uint32_t value);
2602 void WriteUint64(uint64_t value);
2603 void WriteDouble(double value);
2604 void WriteRawBytes(const void* source, size_t length);
2605
2606 ValueSerializer(const ValueSerializer&) = delete;
2607 void operator=(const ValueSerializer&) = delete;
2608
2609 private:
2610 struct PrivateData;
2611 PrivateData* private_;
2612 };
2613
2614 /**
2615 * Deserializes values from data written with ValueSerializer, or a compatible
2616 * implementation.
2617 */
2618 class V8_EXPORT ValueDeserializer {
2619 public:
2620 class V8_EXPORT Delegate {
2621 public:
2622 virtual ~Delegate() = default;
2623
2624 /**
2625 * The embedder overrides this method to read some kind of host object, if
2626 * possible. If not, a suitable exception should be thrown and
2627 * MaybeLocal<Object>() returned.
2628 */
2629 virtual MaybeLocal<Object> ReadHostObject(Isolate* isolate);
2630
2631 /**
2632 * Get a WasmModuleObject given a transfer_id previously provided
2633 * by ValueSerializer::GetWasmModuleTransferId
2634 */
2635 virtual MaybeLocal<WasmModuleObject> GetWasmModuleFromId(
2636 Isolate* isolate, uint32_t transfer_id);
2637
2638 /**
2639 * Get a SharedArrayBuffer given a clone_id previously provided
2640 * by ValueSerializer::GetSharedArrayBufferId
2641 */
2642 virtual MaybeLocal<SharedArrayBuffer> GetSharedArrayBufferFromId(
2643 Isolate* isolate, uint32_t clone_id);
2644 };
2645
2646 ValueDeserializer(Isolate* isolate, const uint8_t* data, size_t size);
2647 ValueDeserializer(Isolate* isolate, const uint8_t* data, size_t size,
2648 Delegate* delegate);
2649 ~ValueDeserializer();
2650
2651 /**
2652 * Reads and validates a header (including the format version).
2653 * May, for example, reject an invalid or unsupported wire format.
2654 */
2655 V8_WARN_UNUSED_RESULT Maybe<bool> ReadHeader(Local<Context> context);
2656
2657 /**
2658 * Deserializes a JavaScript value from the buffer.
2659 */
2660 V8_WARN_UNUSED_RESULT MaybeLocal<Value> ReadValue(Local<Context> context);
2661
2662 /**
2663 * Accepts the array buffer corresponding to the one passed previously to
2664 * ValueSerializer::TransferArrayBuffer.
2665 */
2666 void TransferArrayBuffer(uint32_t transfer_id,
2667 Local<ArrayBuffer> array_buffer);
2668
2669 /**
2670 * Similar to TransferArrayBuffer, but for SharedArrayBuffer.
2671 * The id is not necessarily in the same namespace as unshared ArrayBuffer
2672 * objects.
2673 */
2674 void TransferSharedArrayBuffer(uint32_t id,
2675 Local<SharedArrayBuffer> shared_array_buffer);
2676
2677 /**
2678 * Must be called before ReadHeader to enable support for reading the legacy
2679 * wire format (i.e., which predates this being shipped).
2680 *
2681 * Don't use this unless you need to read data written by previous versions of
2682 * blink::ScriptValueSerializer.
2683 */
2684 void SetSupportsLegacyWireFormat(bool supports_legacy_wire_format);
2685
2686 /**
2687 * Reads the underlying wire format version. Likely mostly to be useful to
2688 * legacy code reading old wire format versions. Must be called after
2689 * ReadHeader.
2690 */
2691 uint32_t GetWireFormatVersion() const;
2692
2693 /**
2694 * Reads raw data in various common formats to the buffer.
2695 * Note that integer types are read in base-128 varint format, not with a
2696 * binary copy. For use during an override of Delegate::ReadHostObject.
2697 */
2698 V8_WARN_UNUSED_RESULT bool ReadUint32(uint32_t* value);
2699 V8_WARN_UNUSED_RESULT bool ReadUint64(uint64_t* value);
2700 V8_WARN_UNUSED_RESULT bool ReadDouble(double* value);
2701 V8_WARN_UNUSED_RESULT bool ReadRawBytes(size_t length, const void** data);
2702
2703 ValueDeserializer(const ValueDeserializer&) = delete;
2704 void operator=(const ValueDeserializer&) = delete;
2705
2706 private:
2707 struct PrivateData;
2708 PrivateData* private_;
2709 };
2710
2711
2712 // --- Value ---
2713
2714
2715 /**
2716 * The superclass of all JavaScript values and objects.
2717 */
2718 class V8_EXPORT Value : public Data {
2719 public:
2720 /**
2721 * Returns true if this value is the undefined value. See ECMA-262
2722 * 4.3.10.
2723 *
2724 * This is equivalent to `value === undefined` in JS.
2725 */
2726 V8_INLINE bool IsUndefined() const;
2727
2728 /**
2729 * Returns true if this value is the null value. See ECMA-262
2730 * 4.3.11.
2731 *
2732 * This is equivalent to `value === null` in JS.
2733 */
2734 V8_INLINE bool IsNull() const;
2735
2736 /**
2737 * Returns true if this value is either the null or the undefined value.
2738 * See ECMA-262
2739 * 4.3.11. and 4.3.12
2740 *
2741 * This is equivalent to `value == null` in JS.
2742 */
2743 V8_INLINE bool IsNullOrUndefined() const;
2744
2745 /**
2746 * Returns true if this value is true.
2747 *
2748 * This is not the same as `BooleanValue()`. The latter performs a
2749 * conversion to boolean, i.e. the result of `Boolean(value)` in JS, whereas
2750 * this checks `value === true`.
2751 */
2752 bool IsTrue() const;
2753
2754 /**
2755 * Returns true if this value is false.
2756 *
2757 * This is not the same as `!BooleanValue()`. The latter performs a
2758 * conversion to boolean, i.e. the result of `!Boolean(value)` in JS, whereas
2759 * this checks `value === false`.
2760 */
2761 bool IsFalse() const;
2762
2763 /**
2764 * Returns true if this value is a symbol or a string.
2765 *
2766 * This is equivalent to
2767 * `typeof value === 'string' || typeof value === 'symbol'` in JS.
2768 */
2769 bool IsName() const;
2770
2771 /**
2772 * Returns true if this value is an instance of the String type.
2773 * See ECMA-262 8.4.
2774 *
2775 * This is equivalent to `typeof value === 'string'` in JS.
2776 */
2777 V8_INLINE bool IsString() const;
2778
2779 /**
2780 * Returns true if this value is a symbol.
2781 *
2782 * This is equivalent to `typeof value === 'symbol'` in JS.
2783 */
2784 bool IsSymbol() const;
2785
2786 /**
2787 * Returns true if this value is a function.
2788 *
2789 * This is equivalent to `typeof value === 'function'` in JS.
2790 */
2791 bool IsFunction() const;
2792
2793 /**
2794 * Returns true if this value is an array. Note that it will return false for
2795 * an Proxy for an array.
2796 */
2797 bool IsArray() const;
2798
2799 /**
2800 * Returns true if this value is an object.
2801 */
2802 bool IsObject() const;
2803
2804 /**
2805 * Returns true if this value is a bigint.
2806 *
2807 * This is equivalent to `typeof value === 'bigint'` in JS.
2808 */
2809 bool IsBigInt() const;
2810
2811 /**
2812 * Returns true if this value is boolean.
2813 *
2814 * This is equivalent to `typeof value === 'boolean'` in JS.
2815 */
2816 bool IsBoolean() const;
2817
2818 /**
2819 * Returns true if this value is a number.
2820 *
2821 * This is equivalent to `typeof value === 'number'` in JS.
2822 */
2823 bool IsNumber() const;
2824
2825 /**
2826 * Returns true if this value is an `External` object.
2827 */
2828 bool IsExternal() const;
2829
2830 /**
2831 * Returns true if this value is a 32-bit signed integer.
2832 */
2833 bool IsInt32() const;
2834
2835 /**
2836 * Returns true if this value is a 32-bit unsigned integer.
2837 */
2838 bool IsUint32() const;
2839
2840 /**
2841 * Returns true if this value is a Date.
2842 */
2843 bool IsDate() const;
2844
2845 /**
2846 * Returns true if this value is an Arguments object.
2847 */
2848 bool IsArgumentsObject() const;
2849
2850 /**
2851 * Returns true if this value is a BigInt object.
2852 */
2853 bool IsBigIntObject() const;
2854
2855 /**
2856 * Returns true if this value is a Boolean object.
2857 */
2858 bool IsBooleanObject() const;
2859
2860 /**
2861 * Returns true if this value is a Number object.
2862 */
2863 bool IsNumberObject() const;
2864
2865 /**
2866 * Returns true if this value is a String object.
2867 */
2868 bool IsStringObject() const;
2869
2870 /**
2871 * Returns true if this value is a Symbol object.
2872 */
2873 bool IsSymbolObject() const;
2874
2875 /**
2876 * Returns true if this value is a NativeError.
2877 */
2878 bool IsNativeError() const;
2879
2880 /**
2881 * Returns true if this value is a RegExp.
2882 */
2883 bool IsRegExp() const;
2884
2885 /**
2886 * Returns true if this value is an async function.
2887 */
2888 bool IsAsyncFunction() const;
2889
2890 /**
2891 * Returns true if this value is a Generator function.
2892 */
2893 bool IsGeneratorFunction() const;
2894
2895 /**
2896 * Returns true if this value is a Generator object (iterator).
2897 */
2898 bool IsGeneratorObject() const;
2899
2900 /**
2901 * Returns true if this value is a Promise.
2902 */
2903 bool IsPromise() const;
2904
2905 /**
2906 * Returns true if this value is a Map.
2907 */
2908 bool IsMap() const;
2909
2910 /**
2911 * Returns true if this value is a Set.
2912 */
2913 bool IsSet() const;
2914
2915 /**
2916 * Returns true if this value is a Map Iterator.
2917 */
2918 bool IsMapIterator() const;
2919
2920 /**
2921 * Returns true if this value is a Set Iterator.
2922 */
2923 bool IsSetIterator() const;
2924
2925 /**
2926 * Returns true if this value is a WeakMap.
2927 */
2928 bool IsWeakMap() const;
2929
2930 /**
2931 * Returns true if this value is a WeakSet.
2932 */
2933 bool IsWeakSet() const;
2934
2935 /**
2936 * Returns true if this value is an ArrayBuffer.
2937 */
2938 bool IsArrayBuffer() const;
2939
2940 /**
2941 * Returns true if this value is an ArrayBufferView.
2942 */
2943 bool IsArrayBufferView() const;
2944
2945 /**
2946 * Returns true if this value is one of TypedArrays.
2947 */
2948 bool IsTypedArray() const;
2949
2950 /**
2951 * Returns true if this value is an Uint8Array.
2952 */
2953 bool IsUint8Array() const;
2954
2955 /**
2956 * Returns true if this value is an Uint8ClampedArray.
2957 */
2958 bool IsUint8ClampedArray() const;
2959
2960 /**
2961 * Returns true if this value is an Int8Array.
2962 */
2963 bool IsInt8Array() const;
2964
2965 /**
2966 * Returns true if this value is an Uint16Array.
2967 */
2968 bool IsUint16Array() const;
2969
2970 /**
2971 * Returns true if this value is an Int16Array.
2972 */
2973 bool IsInt16Array() const;
2974
2975 /**
2976 * Returns true if this value is an Uint32Array.
2977 */
2978 bool IsUint32Array() const;
2979
2980 /**
2981 * Returns true if this value is an Int32Array.
2982 */
2983 bool IsInt32Array() const;
2984
2985 /**
2986 * Returns true if this value is a Float32Array.
2987 */
2988 bool IsFloat32Array() const;
2989
2990 /**
2991 * Returns true if this value is a Float64Array.
2992 */
2993 bool IsFloat64Array() const;
2994
2995 /**
2996 * Returns true if this value is a BigInt64Array.
2997 */
2998 bool IsBigInt64Array() const;
2999
3000 /**
3001 * Returns true if this value is a BigUint64Array.
3002 */
3003 bool IsBigUint64Array() const;
3004
3005 /**
3006 * Returns true if this value is a DataView.
3007 */
3008 bool IsDataView() const;
3009
3010 /**
3011 * Returns true if this value is a SharedArrayBuffer.
3012 */
3013 bool IsSharedArrayBuffer() const;
3014
3015 /**
3016 * Returns true if this value is a JavaScript Proxy.
3017 */
3018 bool IsProxy() const;
3019
3020 /**
3021 * Returns true if this value is a WasmMemoryObject.
3022 */
3023 bool IsWasmMemoryObject() const;
3024
3025 /**
3026 * Returns true if this value is a WasmModuleObject.
3027 */
3028 bool IsWasmModuleObject() const;
3029
3030 /**
3031 * Returns true if the value is a Module Namespace Object.
3032 */
3033 bool IsModuleNamespaceObject() const;
3034
3035 /**
3036 * Perform the equivalent of `BigInt(value)` in JS.
3037 */
3038 V8_WARN_UNUSED_RESULT MaybeLocal<BigInt> ToBigInt(
3039 Local<Context> context) const;
3040 /**
3041 * Perform the equivalent of `Number(value)` in JS.
3042 */
3043 V8_WARN_UNUSED_RESULT MaybeLocal<Number> ToNumber(
3044 Local<Context> context) const;
3045 /**
3046 * Perform the equivalent of `String(value)` in JS.
3047 */
3048 V8_WARN_UNUSED_RESULT MaybeLocal<String> ToString(
3049 Local<Context> context) const;
3050 /**
3051 * Provide a string representation of this value usable for debugging.
3052 * This operation has no observable side effects and will succeed
3053 * unless e.g. execution is being terminated.
3054 */
3055 V8_WARN_UNUSED_RESULT MaybeLocal<String> ToDetailString(
3056 Local<Context> context) const;
3057 /**
3058 * Perform the equivalent of `Object(value)` in JS.
3059 */
3060 V8_WARN_UNUSED_RESULT MaybeLocal<Object> ToObject(
3061 Local<Context> context) const;
3062 /**
3063 * Perform the equivalent of `Number(value)` in JS and convert the result
3064 * to an integer. Negative values are rounded up, positive values are rounded
3065 * down. NaN is converted to 0. Infinite values yield undefined results.
3066 */
3067 V8_WARN_UNUSED_RESULT MaybeLocal<Integer> ToInteger(
3068 Local<Context> context) const;
3069 /**
3070 * Perform the equivalent of `Number(value)` in JS and convert the result
3071 * to an unsigned 32-bit integer by performing the steps in
3072 * https://tc39.es/ecma262/#sec-touint32.
3073 */
3074 V8_WARN_UNUSED_RESULT MaybeLocal<Uint32> ToUint32(
3075 Local<Context> context) const;
3076 /**
3077 * Perform the equivalent of `Number(value)` in JS and convert the result
3078 * to a signed 32-bit integer by performing the steps in
3079 * https://tc39.es/ecma262/#sec-toint32.
3080 */
3081 V8_WARN_UNUSED_RESULT MaybeLocal<Int32> ToInt32(Local<Context> context) const;
3082
3083 /**
3084 * Perform the equivalent of `Boolean(value)` in JS. This can never fail.
3085 */
3086 Local<Boolean> ToBoolean(Isolate* isolate) const;
3087
3088 /**
3089 * Attempts to convert a string to an array index.
3090 * Returns an empty handle if the conversion fails.
3091 */
3092 V8_WARN_UNUSED_RESULT MaybeLocal<Uint32> ToArrayIndex(
3093 Local<Context> context) const;
3094
3095 /** Returns the equivalent of `ToBoolean()->Value()`. */
3096 bool BooleanValue(Isolate* isolate) const;
3097
3098 /** Returns the equivalent of `ToNumber()->Value()`. */
3099 V8_WARN_UNUSED_RESULT Maybe<double> NumberValue(Local<Context> context) const;
3100 /** Returns the equivalent of `ToInteger()->Value()`. */
3101 V8_WARN_UNUSED_RESULT Maybe<int64_t> IntegerValue(
3102 Local<Context> context) const;
3103 /** Returns the equivalent of `ToUint32()->Value()`. */
3104 V8_WARN_UNUSED_RESULT Maybe<uint32_t> Uint32Value(
3105 Local<Context> context) const;
3106 /** Returns the equivalent of `ToInt32()->Value()`. */
3107 V8_WARN_UNUSED_RESULT Maybe<int32_t> Int32Value(Local<Context> context) const;
3108
3109 /** JS == */
3110 V8_WARN_UNUSED_RESULT Maybe<bool> Equals(Local<Context> context,
3111 Local<Value> that) const;
3112 bool StrictEquals(Local<Value> that) const;
3113 bool SameValue(Local<Value> that) const;
3114
3115 template <class T> V8_INLINE static Value* Cast(T* value);
3116
3117 Local<String> TypeOf(Isolate*);
3118
3119 Maybe<bool> InstanceOf(Local<Context> context, Local<Object> object);
3120
3121 private:
3122 V8_INLINE bool QuickIsUndefined() const;
3123 V8_INLINE bool QuickIsNull() const;
3124 V8_INLINE bool QuickIsNullOrUndefined() const;
3125 V8_INLINE bool QuickIsString() const;
3126 bool FullIsUndefined() const;
3127 bool FullIsNull() const;
3128 bool FullIsString() const;
3129
3130 static void CheckCast(Data* that);
3131 };
3132
3133
3134 /**
3135 * The superclass of primitive values. See ECMA-262 4.3.2.
3136 */
3137 class V8_EXPORT Primitive : public Value { };
3138
3139
3140 /**
3141 * A primitive boolean value (ECMA-262, 4.3.14). Either the true
3142 * or false value.
3143 */
3144 class V8_EXPORT Boolean : public Primitive {
3145 public:
3146 bool Value() const;
3147 V8_INLINE static Boolean* Cast(v8::Data* data);
3148 V8_INLINE static Local<Boolean> New(Isolate* isolate, bool value);
3149
3150 private:
3151 static void CheckCast(v8::Data* that);
3152 };
3153
3154
3155 /**
3156 * A superclass for symbols and strings.
3157 */
3158 class V8_EXPORT Name : public Primitive {
3159 public:
3160 /**
3161 * Returns the identity hash for this object. The current implementation
3162 * uses an inline property on the object to store the identity hash.
3163 *
3164 * The return value will never be 0. Also, it is not guaranteed to be
3165 * unique.
3166 */
3167 int GetIdentityHash();
3168
3169 V8_INLINE static Name* Cast(Data* data);
3170
3171 private:
3172 static void CheckCast(Data* that);
3173 };
3174
3175 /**
3176 * A flag describing different modes of string creation.
3177 *
3178 * Aside from performance implications there are no differences between the two
3179 * creation modes.
3180 */
3181 enum class NewStringType {
3182 /**
3183 * Create a new string, always allocating new storage memory.
3184 */
3185 kNormal,
3186
3187 /**
3188 * Acts as a hint that the string should be created in the
3189 * old generation heap space and be deduplicated if an identical string
3190 * already exists.
3191 */
3192 kInternalized
3193 };
3194
3195 /**
3196 * A JavaScript string value (ECMA-262, 4.3.17).
3197 */
3198 class V8_EXPORT String : public Name {
3199 public:
3200 static constexpr int kMaxLength =
3201 internal::kApiSystemPointerSize == 4 ? (1 << 28) - 16 : (1 << 29) - 24;
3202
3203 enum Encoding {
3204 UNKNOWN_ENCODING = 0x1,
3205 TWO_BYTE_ENCODING = 0x0,
3206 ONE_BYTE_ENCODING = 0x8
3207 };
3208 /**
3209 * Returns the number of characters (UTF-16 code units) in this string.
3210 */
3211 int Length() const;
3212
3213 /**
3214 * Returns the number of bytes in the UTF-8 encoded
3215 * representation of this string.
3216 */
3217 int Utf8Length(Isolate* isolate) const;
3218
3219 /**
3220 * Returns whether this string is known to contain only one byte data,
3221 * i.e. ISO-8859-1 code points.
3222 * Does not read the string.
3223 * False negatives are possible.
3224 */
3225 bool IsOneByte() const;
3226
3227 /**
3228 * Returns whether this string contain only one byte data,
3229 * i.e. ISO-8859-1 code points.
3230 * Will read the entire string in some cases.
3231 */
3232 bool ContainsOnlyOneByte() const;
3233
3234 /**
3235 * Write the contents of the string to an external buffer.
3236 * If no arguments are given, expects the buffer to be large
3237 * enough to hold the entire string and NULL terminator. Copies
3238 * the contents of the string and the NULL terminator into the
3239 * buffer.
3240 *
3241 * WriteUtf8 will not write partial UTF-8 sequences, preferring to stop
3242 * before the end of the buffer.
3243 *
3244 * Copies up to length characters into the output buffer.
3245 * Only null-terminates if there is enough space in the buffer.
3246 *
3247 * \param buffer The buffer into which the string will be copied.
3248 * \param start The starting position within the string at which
3249 * copying begins.
3250 * \param length The number of characters to copy from the string. For
3251 * WriteUtf8 the number of bytes in the buffer.
3252 * \param nchars_ref The number of characters written, can be NULL.
3253 * \param options Various options that might affect performance of this or
3254 * subsequent operations.
3255 * \return The number of characters copied to the buffer excluding the null
3256 * terminator. For WriteUtf8: The number of bytes copied to the buffer
3257 * including the null terminator (if written).
3258 */
3259 enum WriteOptions {
3260 NO_OPTIONS = 0,
3261 HINT_MANY_WRITES_EXPECTED = 1,
3262 NO_NULL_TERMINATION = 2,
3263 PRESERVE_ONE_BYTE_NULL = 4,
3264 // Used by WriteUtf8 to replace orphan surrogate code units with the
3265 // unicode replacement character. Needs to be set to guarantee valid UTF-8
3266 // output.
3267 REPLACE_INVALID_UTF8 = 8
3268 };
3269
3270 // 16-bit character codes.
3271 int Write(Isolate* isolate, uint16_t* buffer, int start = 0, int length = -1,
3272 int options = NO_OPTIONS) const;
3273 // One byte characters.
3274 int WriteOneByte(Isolate* isolate, uint8_t* buffer, int start = 0,
3275 int length = -1, int options = NO_OPTIONS) const;
3276 // UTF-8 encoded characters.
3277 int WriteUtf8(Isolate* isolate, char* buffer, int length = -1,
3278 int* nchars_ref = nullptr, int options = NO_OPTIONS) const;
3279
3280 /**
3281 * A zero length string.
3282 */
3283 V8_INLINE static Local<String> Empty(Isolate* isolate);
3284
3285 /**
3286 * Returns true if the string is external.
3287 */
3288 bool IsExternal() const;
3289
3290 /**
3291 * Returns true if the string is both external and two-byte.
3292 */
3293 bool IsExternalTwoByte() const;
3294
3295 /**
3296 * Returns true if the string is both external and one-byte.
3297 */
3298 bool IsExternalOneByte() const;
3299
3300 class V8_EXPORT ExternalStringResourceBase {
3301 public:
3302 virtual ~ExternalStringResourceBase() = default;
3303
3304 /**
3305 * If a string is cacheable, the value returned by
3306 * ExternalStringResource::data() may be cached, otherwise it is not
3307 * expected to be stable beyond the current top-level task.
3308 */
IsCacheable()3309 virtual bool IsCacheable() const { return true; }
3310
3311 // Disallow copying and assigning.
3312 ExternalStringResourceBase(const ExternalStringResourceBase&) = delete;
3313 void operator=(const ExternalStringResourceBase&) = delete;
3314
3315 protected:
3316 ExternalStringResourceBase() = default;
3317
3318 /**
3319 * Internally V8 will call this Dispose method when the external string
3320 * resource is no longer needed. The default implementation will use the
3321 * delete operator. This method can be overridden in subclasses to
3322 * control how allocated external string resources are disposed.
3323 */
Dispose()3324 virtual void Dispose() { delete this; }
3325
3326 /**
3327 * For a non-cacheable string, the value returned by
3328 * |ExternalStringResource::data()| has to be stable between |Lock()| and
3329 * |Unlock()|, that is the string must behave as is |IsCacheable()| returned
3330 * true.
3331 *
3332 * These two functions must be thread-safe, and can be called from anywhere.
3333 * They also must handle lock depth, in the sense that each can be called
3334 * several times, from different threads, and unlocking should only happen
3335 * when the balance of Lock() and Unlock() calls is 0.
3336 */
Lock()3337 virtual void Lock() const {}
3338
3339 /**
3340 * Unlocks the string.
3341 */
Unlock()3342 virtual void Unlock() const {}
3343
3344 private:
3345 friend class internal::ExternalString;
3346 friend class v8::String;
3347 friend class internal::ScopedExternalStringLock;
3348 };
3349
3350 /**
3351 * An ExternalStringResource is a wrapper around a two-byte string
3352 * buffer that resides outside V8's heap. Implement an
3353 * ExternalStringResource to manage the life cycle of the underlying
3354 * buffer. Note that the string data must be immutable.
3355 */
3356 class V8_EXPORT ExternalStringResource
3357 : public ExternalStringResourceBase {
3358 public:
3359 /**
3360 * Override the destructor to manage the life cycle of the underlying
3361 * buffer.
3362 */
3363 ~ExternalStringResource() override = default;
3364
3365 /**
3366 * The string data from the underlying buffer. If the resource is cacheable
3367 * then data() must return the same value for all invocations.
3368 */
3369 virtual const uint16_t* data() const = 0;
3370
3371 /**
3372 * The length of the string. That is, the number of two-byte characters.
3373 */
3374 virtual size_t length() const = 0;
3375
3376 /**
3377 * Returns the cached data from the underlying buffer. This method can be
3378 * called only for cacheable resources (i.e. IsCacheable() == true) and only
3379 * after UpdateDataCache() was called.
3380 */
cached_data()3381 const uint16_t* cached_data() const {
3382 CheckCachedDataInvariants();
3383 return cached_data_;
3384 }
3385
3386 /**
3387 * Update {cached_data_} with the data from the underlying buffer. This can
3388 * be called only for cacheable resources.
3389 */
3390 void UpdateDataCache();
3391
3392 protected:
3393 ExternalStringResource() = default;
3394
3395 private:
3396 void CheckCachedDataInvariants() const;
3397
3398 const uint16_t* cached_data_ = nullptr;
3399 };
3400
3401 /**
3402 * An ExternalOneByteStringResource is a wrapper around an one-byte
3403 * string buffer that resides outside V8's heap. Implement an
3404 * ExternalOneByteStringResource to manage the life cycle of the
3405 * underlying buffer. Note that the string data must be immutable
3406 * and that the data must be Latin-1 and not UTF-8, which would require
3407 * special treatment internally in the engine and do not allow efficient
3408 * indexing. Use String::New or convert to 16 bit data for non-Latin1.
3409 */
3410
3411 class V8_EXPORT ExternalOneByteStringResource
3412 : public ExternalStringResourceBase {
3413 public:
3414 /**
3415 * Override the destructor to manage the life cycle of the underlying
3416 * buffer.
3417 */
3418 ~ExternalOneByteStringResource() override = default;
3419
3420 /**
3421 * The string data from the underlying buffer. If the resource is cacheable
3422 * then data() must return the same value for all invocations.
3423 */
3424 virtual const char* data() const = 0;
3425
3426 /** The number of Latin-1 characters in the string.*/
3427 virtual size_t length() const = 0;
3428
3429 /**
3430 * Returns the cached data from the underlying buffer. If the resource is
3431 * uncacheable or if UpdateDataCache() was not called before, it has
3432 * undefined behaviour.
3433 */
cached_data()3434 const char* cached_data() const {
3435 CheckCachedDataInvariants();
3436 return cached_data_;
3437 }
3438
3439 /**
3440 * Update {cached_data_} with the data from the underlying buffer. This can
3441 * be called only for cacheable resources.
3442 */
3443 void UpdateDataCache();
3444
3445 protected:
3446 ExternalOneByteStringResource() = default;
3447
3448 private:
3449 void CheckCachedDataInvariants() const;
3450
3451 const char* cached_data_ = nullptr;
3452 };
3453
3454 /**
3455 * If the string is an external string, return the ExternalStringResourceBase
3456 * regardless of the encoding, otherwise return NULL. The encoding of the
3457 * string is returned in encoding_out.
3458 */
3459 V8_INLINE ExternalStringResourceBase* GetExternalStringResourceBase(
3460 Encoding* encoding_out) const;
3461
3462 /**
3463 * Get the ExternalStringResource for an external string. Returns
3464 * NULL if IsExternal() doesn't return true.
3465 */
3466 V8_INLINE ExternalStringResource* GetExternalStringResource() const;
3467
3468 /**
3469 * Get the ExternalOneByteStringResource for an external one-byte string.
3470 * Returns NULL if IsExternalOneByte() doesn't return true.
3471 */
3472 const ExternalOneByteStringResource* GetExternalOneByteStringResource() const;
3473
3474 V8_INLINE static String* Cast(v8::Data* data);
3475
3476 /**
3477 * Allocates a new string from a UTF-8 literal. This is equivalent to calling
3478 * String::NewFromUtf(isolate, "...").ToLocalChecked(), but without the check
3479 * overhead.
3480 *
3481 * When called on a string literal containing '\0', the inferred length is the
3482 * length of the input array minus 1 (for the final '\0') and not the value
3483 * returned by strlen.
3484 **/
3485 template <int N>
3486 static V8_WARN_UNUSED_RESULT Local<String> NewFromUtf8Literal(
3487 Isolate* isolate, const char (&literal)[N],
3488 NewStringType type = NewStringType::kNormal) {
3489 static_assert(N <= kMaxLength, "String is too long");
3490 return NewFromUtf8Literal(isolate, literal, type, N - 1);
3491 }
3492
3493 /** Allocates a new string from UTF-8 data. Only returns an empty value when
3494 * length > kMaxLength. **/
3495 static V8_WARN_UNUSED_RESULT MaybeLocal<String> NewFromUtf8(
3496 Isolate* isolate, const char* data,
3497 NewStringType type = NewStringType::kNormal, int length = -1);
3498
3499 /** Allocates a new string from Latin-1 data. Only returns an empty value
3500 * when length > kMaxLength. **/
3501 static V8_WARN_UNUSED_RESULT MaybeLocal<String> NewFromOneByte(
3502 Isolate* isolate, const uint8_t* data,
3503 NewStringType type = NewStringType::kNormal, int length = -1);
3504
3505 /** Allocates a new string from UTF-16 data. Only returns an empty value when
3506 * length > kMaxLength. **/
3507 static V8_WARN_UNUSED_RESULT MaybeLocal<String> NewFromTwoByte(
3508 Isolate* isolate, const uint16_t* data,
3509 NewStringType type = NewStringType::kNormal, int length = -1);
3510
3511 /**
3512 * Creates a new string by concatenating the left and the right strings
3513 * passed in as parameters.
3514 */
3515 static Local<String> Concat(Isolate* isolate, Local<String> left,
3516 Local<String> right);
3517
3518 /**
3519 * Creates a new external string using the data defined in the given
3520 * resource. When the external string is no longer live on V8's heap the
3521 * resource will be disposed by calling its Dispose method. The caller of
3522 * this function should not otherwise delete or modify the resource. Neither
3523 * should the underlying buffer be deallocated or modified except through the
3524 * destructor of the external string resource.
3525 */
3526 static V8_WARN_UNUSED_RESULT MaybeLocal<String> NewExternalTwoByte(
3527 Isolate* isolate, ExternalStringResource* resource);
3528
3529 /**
3530 * Associate an external string resource with this string by transforming it
3531 * in place so that existing references to this string in the JavaScript heap
3532 * will use the external string resource. The external string resource's
3533 * character contents need to be equivalent to this string.
3534 * Returns true if the string has been changed to be an external string.
3535 * The string is not modified if the operation fails. See NewExternal for
3536 * information on the lifetime of the resource.
3537 */
3538 bool MakeExternal(ExternalStringResource* resource);
3539
3540 /**
3541 * Creates a new external string using the one-byte data defined in the given
3542 * resource. When the external string is no longer live on V8's heap the
3543 * resource will be disposed by calling its Dispose method. The caller of
3544 * this function should not otherwise delete or modify the resource. Neither
3545 * should the underlying buffer be deallocated or modified except through the
3546 * destructor of the external string resource.
3547 */
3548 static V8_WARN_UNUSED_RESULT MaybeLocal<String> NewExternalOneByte(
3549 Isolate* isolate, ExternalOneByteStringResource* resource);
3550
3551 /**
3552 * Associate an external string resource with this string by transforming it
3553 * in place so that existing references to this string in the JavaScript heap
3554 * will use the external string resource. The external string resource's
3555 * character contents need to be equivalent to this string.
3556 * Returns true if the string has been changed to be an external string.
3557 * The string is not modified if the operation fails. See NewExternal for
3558 * information on the lifetime of the resource.
3559 */
3560 bool MakeExternal(ExternalOneByteStringResource* resource);
3561
3562 /**
3563 * Returns true if this string can be made external.
3564 */
3565 bool CanMakeExternal();
3566
3567 /**
3568 * Returns true if the strings values are equal. Same as JS ==/===.
3569 */
3570 bool StringEquals(Local<String> str);
3571
3572 /**
3573 * Converts an object to a UTF-8-encoded character array. Useful if
3574 * you want to print the object. If conversion to a string fails
3575 * (e.g. due to an exception in the toString() method of the object)
3576 * then the length() method returns 0 and the * operator returns
3577 * NULL.
3578 */
3579 class V8_EXPORT Utf8Value {
3580 public:
3581 Utf8Value(Isolate* isolate, Local<v8::Value> obj);
3582 ~Utf8Value();
3583 char* operator*() { return str_; }
3584 const char* operator*() const { return str_; }
length()3585 int length() const { return length_; }
3586
3587 // Disallow copying and assigning.
3588 Utf8Value(const Utf8Value&) = delete;
3589 void operator=(const Utf8Value&) = delete;
3590
3591 private:
3592 char* str_;
3593 int length_;
3594 };
3595
3596 /**
3597 * Converts an object to a two-byte (UTF-16-encoded) string.
3598 * If conversion to a string fails (eg. due to an exception in the toString()
3599 * method of the object) then the length() method returns 0 and the * operator
3600 * returns NULL.
3601 */
3602 class V8_EXPORT Value {
3603 public:
3604 Value(Isolate* isolate, Local<v8::Value> obj);
3605 ~Value();
3606 uint16_t* operator*() { return str_; }
3607 const uint16_t* operator*() const { return str_; }
length()3608 int length() const { return length_; }
3609
3610 // Disallow copying and assigning.
3611 Value(const Value&) = delete;
3612 void operator=(const Value&) = delete;
3613
3614 private:
3615 uint16_t* str_;
3616 int length_;
3617 };
3618
3619 private:
3620 void VerifyExternalStringResourceBase(ExternalStringResourceBase* v,
3621 Encoding encoding) const;
3622 void VerifyExternalStringResource(ExternalStringResource* val) const;
3623 ExternalStringResource* GetExternalStringResourceSlow() const;
3624 ExternalStringResourceBase* GetExternalStringResourceBaseSlow(
3625 String::Encoding* encoding_out) const;
3626
3627 static Local<v8::String> NewFromUtf8Literal(Isolate* isolate,
3628 const char* literal,
3629 NewStringType type, int length);
3630
3631 static void CheckCast(v8::Data* that);
3632 };
3633
3634 // Zero-length string specialization (templated string size includes
3635 // terminator).
3636 template <>
NewFromUtf8Literal(Isolate * isolate,const char (& literal)[1],NewStringType type)3637 inline V8_WARN_UNUSED_RESULT Local<String> String::NewFromUtf8Literal(
3638 Isolate* isolate, const char (&literal)[1], NewStringType type) {
3639 return String::Empty(isolate);
3640 }
3641
3642 /**
3643 * A JavaScript symbol (ECMA-262 edition 6)
3644 */
3645 class V8_EXPORT Symbol : public Name {
3646 public:
3647 /**
3648 * Returns the description string of the symbol, or undefined if none.
3649 */
3650 Local<Value> Description() const;
3651 Local<Value> Description(Isolate* isolate) const;
3652
3653 V8_DEPRECATED("Use Symbol::Description()")
Name()3654 Local<Value> Name() const { return Description(); }
3655
3656 /**
3657 * Create a symbol. If description is not empty, it will be used as the
3658 * description.
3659 */
3660 static Local<Symbol> New(Isolate* isolate,
3661 Local<String> description = Local<String>());
3662
3663 /**
3664 * Access global symbol registry.
3665 * Note that symbols created this way are never collected, so
3666 * they should only be used for statically fixed properties.
3667 * Also, there is only one global name space for the descriptions used as
3668 * keys.
3669 * To minimize the potential for clashes, use qualified names as keys.
3670 */
3671 static Local<Symbol> For(Isolate* isolate, Local<String> description);
3672
3673 /**
3674 * Retrieve a global symbol. Similar to |For|, but using a separate
3675 * registry that is not accessible by (and cannot clash with) JavaScript code.
3676 */
3677 static Local<Symbol> ForApi(Isolate* isolate, Local<String> description);
3678
3679 // Well-known symbols
3680 static Local<Symbol> GetAsyncIterator(Isolate* isolate);
3681 static Local<Symbol> GetHasInstance(Isolate* isolate);
3682 static Local<Symbol> GetIsConcatSpreadable(Isolate* isolate);
3683 static Local<Symbol> GetIterator(Isolate* isolate);
3684 static Local<Symbol> GetMatch(Isolate* isolate);
3685 static Local<Symbol> GetReplace(Isolate* isolate);
3686 static Local<Symbol> GetSearch(Isolate* isolate);
3687 static Local<Symbol> GetSplit(Isolate* isolate);
3688 static Local<Symbol> GetToPrimitive(Isolate* isolate);
3689 static Local<Symbol> GetToStringTag(Isolate* isolate);
3690 static Local<Symbol> GetUnscopables(Isolate* isolate);
3691
3692 V8_INLINE static Symbol* Cast(Data* data);
3693
3694 private:
3695 Symbol();
3696 static void CheckCast(Data* that);
3697 };
3698
3699
3700 /**
3701 * A private symbol
3702 *
3703 * This is an experimental feature. Use at your own risk.
3704 */
3705 class V8_EXPORT Private : public Data {
3706 public:
3707 /**
3708 * Returns the print name string of the private symbol, or undefined if none.
3709 */
3710 Local<Value> Name() const;
3711
3712 /**
3713 * Create a private symbol. If name is not empty, it will be the description.
3714 */
3715 static Local<Private> New(Isolate* isolate,
3716 Local<String> name = Local<String>());
3717
3718 /**
3719 * Retrieve a global private symbol. If a symbol with this name has not
3720 * been retrieved in the same isolate before, it is created.
3721 * Note that private symbols created this way are never collected, so
3722 * they should only be used for statically fixed properties.
3723 * Also, there is only one global name space for the names used as keys.
3724 * To minimize the potential for clashes, use qualified names as keys,
3725 * e.g., "Class#property".
3726 */
3727 static Local<Private> ForApi(Isolate* isolate, Local<String> name);
3728
3729 V8_INLINE static Private* Cast(Data* data);
3730
3731 private:
3732 Private();
3733
3734 static void CheckCast(Data* that);
3735 };
3736
3737
3738 /**
3739 * A JavaScript number value (ECMA-262, 4.3.20)
3740 */
3741 class V8_EXPORT Number : public Primitive {
3742 public:
3743 double Value() const;
3744 static Local<Number> New(Isolate* isolate, double value);
3745 V8_INLINE static Number* Cast(v8::Data* data);
3746
3747 private:
3748 Number();
3749 static void CheckCast(v8::Data* that);
3750 };
3751
3752
3753 /**
3754 * A JavaScript value representing a signed integer.
3755 */
3756 class V8_EXPORT Integer : public Number {
3757 public:
3758 static Local<Integer> New(Isolate* isolate, int32_t value);
3759 static Local<Integer> NewFromUnsigned(Isolate* isolate, uint32_t value);
3760 int64_t Value() const;
3761 V8_INLINE static Integer* Cast(v8::Data* data);
3762
3763 private:
3764 Integer();
3765 static void CheckCast(v8::Data* that);
3766 };
3767
3768
3769 /**
3770 * A JavaScript value representing a 32-bit signed integer.
3771 */
3772 class V8_EXPORT Int32 : public Integer {
3773 public:
3774 int32_t Value() const;
3775 V8_INLINE static Int32* Cast(v8::Data* data);
3776
3777 private:
3778 Int32();
3779 static void CheckCast(v8::Data* that);
3780 };
3781
3782
3783 /**
3784 * A JavaScript value representing a 32-bit unsigned integer.
3785 */
3786 class V8_EXPORT Uint32 : public Integer {
3787 public:
3788 uint32_t Value() const;
3789 V8_INLINE static Uint32* Cast(v8::Data* data);
3790
3791 private:
3792 Uint32();
3793 static void CheckCast(v8::Data* that);
3794 };
3795
3796 /**
3797 * A JavaScript BigInt value (https://tc39.github.io/proposal-bigint)
3798 */
3799 class V8_EXPORT BigInt : public Primitive {
3800 public:
3801 static Local<BigInt> New(Isolate* isolate, int64_t value);
3802 static Local<BigInt> NewFromUnsigned(Isolate* isolate, uint64_t value);
3803 /**
3804 * Creates a new BigInt object using a specified sign bit and a
3805 * specified list of digits/words.
3806 * The resulting number is calculated as:
3807 *
3808 * (-1)^sign_bit * (words[0] * (2^64)^0 + words[1] * (2^64)^1 + ...)
3809 */
3810 static MaybeLocal<BigInt> NewFromWords(Local<Context> context, int sign_bit,
3811 int word_count, const uint64_t* words);
3812
3813 /**
3814 * Returns the value of this BigInt as an unsigned 64-bit integer.
3815 * If `lossless` is provided, it will reflect whether the return value was
3816 * truncated or wrapped around. In particular, it is set to `false` if this
3817 * BigInt is negative.
3818 */
3819 uint64_t Uint64Value(bool* lossless = nullptr) const;
3820
3821 /**
3822 * Returns the value of this BigInt as a signed 64-bit integer.
3823 * If `lossless` is provided, it will reflect whether this BigInt was
3824 * truncated or not.
3825 */
3826 int64_t Int64Value(bool* lossless = nullptr) const;
3827
3828 /**
3829 * Returns the number of 64-bit words needed to store the result of
3830 * ToWordsArray().
3831 */
3832 int WordCount() const;
3833
3834 /**
3835 * Writes the contents of this BigInt to a specified memory location.
3836 * `sign_bit` must be provided and will be set to 1 if this BigInt is
3837 * negative.
3838 * `*word_count` has to be initialized to the length of the `words` array.
3839 * Upon return, it will be set to the actual number of words that would
3840 * be needed to store this BigInt (i.e. the return value of `WordCount()`).
3841 */
3842 void ToWordsArray(int* sign_bit, int* word_count, uint64_t* words) const;
3843
3844 V8_INLINE static BigInt* Cast(v8::Data* data);
3845
3846 private:
3847 BigInt();
3848 static void CheckCast(v8::Data* that);
3849 };
3850
3851 /**
3852 * PropertyAttribute.
3853 */
3854 enum PropertyAttribute {
3855 /** None. **/
3856 None = 0,
3857 /** ReadOnly, i.e., not writable. **/
3858 ReadOnly = 1 << 0,
3859 /** DontEnum, i.e., not enumerable. **/
3860 DontEnum = 1 << 1,
3861 /** DontDelete, i.e., not configurable. **/
3862 DontDelete = 1 << 2
3863 };
3864
3865 /**
3866 * Accessor[Getter|Setter] are used as callback functions when
3867 * setting|getting a particular property. See Object and ObjectTemplate's
3868 * method SetAccessor.
3869 */
3870 using AccessorGetterCallback =
3871 void (*)(Local<String> property, const PropertyCallbackInfo<Value>& info);
3872 using AccessorNameGetterCallback =
3873 void (*)(Local<Name> property, const PropertyCallbackInfo<Value>& info);
3874
3875 using AccessorSetterCallback = void (*)(Local<String> property,
3876 Local<Value> value,
3877 const PropertyCallbackInfo<void>& info);
3878 using AccessorNameSetterCallback =
3879 void (*)(Local<Name> property, Local<Value> value,
3880 const PropertyCallbackInfo<void>& info);
3881
3882 /**
3883 * Access control specifications.
3884 *
3885 * Some accessors should be accessible across contexts. These
3886 * accessors have an explicit access control parameter which specifies
3887 * the kind of cross-context access that should be allowed.
3888 *
3889 * TODO(dcarney): Remove PROHIBITS_OVERWRITING as it is now unused.
3890 */
3891 enum AccessControl {
3892 DEFAULT = 0,
3893 ALL_CAN_READ = 1,
3894 ALL_CAN_WRITE = 1 << 1,
3895 PROHIBITS_OVERWRITING = 1 << 2
3896 };
3897
3898 /**
3899 * Property filter bits. They can be or'ed to build a composite filter.
3900 */
3901 enum PropertyFilter {
3902 ALL_PROPERTIES = 0,
3903 ONLY_WRITABLE = 1,
3904 ONLY_ENUMERABLE = 2,
3905 ONLY_CONFIGURABLE = 4,
3906 SKIP_STRINGS = 8,
3907 SKIP_SYMBOLS = 16
3908 };
3909
3910 /**
3911 * Options for marking whether callbacks may trigger JS-observable side effects.
3912 * Side-effect-free callbacks are allowlisted during debug evaluation with
3913 * throwOnSideEffect. It applies when calling a Function, FunctionTemplate,
3914 * or an Accessor callback. For Interceptors, please see
3915 * PropertyHandlerFlags's kHasNoSideEffect.
3916 * Callbacks that only cause side effects to the receiver are allowlisted if
3917 * invoked on receiver objects that are created within the same debug-evaluate
3918 * call, as these objects are temporary and the side effect does not escape.
3919 */
3920 enum class SideEffectType {
3921 kHasSideEffect,
3922 kHasNoSideEffect,
3923 kHasSideEffectToReceiver
3924 };
3925
3926 /**
3927 * Keys/Properties filter enums:
3928 *
3929 * KeyCollectionMode limits the range of collected properties. kOwnOnly limits
3930 * the collected properties to the given Object only. kIncludesPrototypes will
3931 * include all keys of the objects's prototype chain as well.
3932 */
3933 enum class KeyCollectionMode { kOwnOnly, kIncludePrototypes };
3934
3935 /**
3936 * kIncludesIndices allows for integer indices to be collected, while
3937 * kSkipIndices will exclude integer indices from being collected.
3938 */
3939 enum class IndexFilter { kIncludeIndices, kSkipIndices };
3940
3941 /**
3942 * kConvertToString will convert integer indices to strings.
3943 * kKeepNumbers will return numbers for integer indices.
3944 */
3945 enum class KeyConversionMode { kConvertToString, kKeepNumbers, kNoNumbers };
3946
3947 /**
3948 * Integrity level for objects.
3949 */
3950 enum class IntegrityLevel { kFrozen, kSealed };
3951
3952 /**
3953 * A JavaScript object (ECMA-262, 4.3.3)
3954 */
3955 class V8_EXPORT Object : public Value {
3956 public:
3957 /**
3958 * Set only return Just(true) or Empty(), so if it should never fail, use
3959 * result.Check().
3960 */
3961 V8_WARN_UNUSED_RESULT Maybe<bool> Set(Local<Context> context,
3962 Local<Value> key, Local<Value> value);
3963
3964 V8_WARN_UNUSED_RESULT Maybe<bool> Set(Local<Context> context, uint32_t index,
3965 Local<Value> value);
3966
3967 // Implements CreateDataProperty (ECMA-262, 7.3.4).
3968 //
3969 // Defines a configurable, writable, enumerable property with the given value
3970 // on the object unless the property already exists and is not configurable
3971 // or the object is not extensible.
3972 //
3973 // Returns true on success.
3974 V8_WARN_UNUSED_RESULT Maybe<bool> CreateDataProperty(Local<Context> context,
3975 Local<Name> key,
3976 Local<Value> value);
3977 V8_WARN_UNUSED_RESULT Maybe<bool> CreateDataProperty(Local<Context> context,
3978 uint32_t index,
3979 Local<Value> value);
3980
3981 // Implements DefineOwnProperty.
3982 //
3983 // In general, CreateDataProperty will be faster, however, does not allow
3984 // for specifying attributes.
3985 //
3986 // Returns true on success.
3987 V8_WARN_UNUSED_RESULT Maybe<bool> DefineOwnProperty(
3988 Local<Context> context, Local<Name> key, Local<Value> value,
3989 PropertyAttribute attributes = None);
3990
3991 // Implements Object.DefineProperty(O, P, Attributes), see Ecma-262 19.1.2.4.
3992 //
3993 // The defineProperty function is used to add an own property or
3994 // update the attributes of an existing own property of an object.
3995 //
3996 // Both data and accessor descriptors can be used.
3997 //
3998 // In general, CreateDataProperty is faster, however, does not allow
3999 // for specifying attributes or an accessor descriptor.
4000 //
4001 // The PropertyDescriptor can change when redefining a property.
4002 //
4003 // Returns true on success.
4004 V8_WARN_UNUSED_RESULT Maybe<bool> DefineProperty(
4005 Local<Context> context, Local<Name> key, PropertyDescriptor& descriptor);
4006
4007 V8_WARN_UNUSED_RESULT MaybeLocal<Value> Get(Local<Context> context,
4008 Local<Value> key);
4009
4010 V8_WARN_UNUSED_RESULT MaybeLocal<Value> Get(Local<Context> context,
4011 uint32_t index);
4012
4013 /**
4014 * Gets the property attributes of a property which can be None or
4015 * any combination of ReadOnly, DontEnum and DontDelete. Returns
4016 * None when the property doesn't exist.
4017 */
4018 V8_WARN_UNUSED_RESULT Maybe<PropertyAttribute> GetPropertyAttributes(
4019 Local<Context> context, Local<Value> key);
4020
4021 /**
4022 * Returns Object.getOwnPropertyDescriptor as per ES2016 section 19.1.2.6.
4023 */
4024 V8_WARN_UNUSED_RESULT MaybeLocal<Value> GetOwnPropertyDescriptor(
4025 Local<Context> context, Local<Name> key);
4026
4027 /**
4028 * Object::Has() calls the abstract operation HasProperty(O, P) described
4029 * in ECMA-262, 7.3.10. Has() returns
4030 * true, if the object has the property, either own or on the prototype chain.
4031 * Interceptors, i.e., PropertyQueryCallbacks, are called if present.
4032 *
4033 * Has() has the same side effects as JavaScript's `variable in object`.
4034 * For example, calling Has() on a revoked proxy will throw an exception.
4035 *
4036 * \note Has() converts the key to a name, which possibly calls back into
4037 * JavaScript.
4038 *
4039 * See also v8::Object::HasOwnProperty() and
4040 * v8::Object::HasRealNamedProperty().
4041 */
4042 V8_WARN_UNUSED_RESULT Maybe<bool> Has(Local<Context> context,
4043 Local<Value> key);
4044
4045 V8_WARN_UNUSED_RESULT Maybe<bool> Delete(Local<Context> context,
4046 Local<Value> key);
4047
4048 V8_WARN_UNUSED_RESULT Maybe<bool> Has(Local<Context> context, uint32_t index);
4049
4050 V8_WARN_UNUSED_RESULT Maybe<bool> Delete(Local<Context> context,
4051 uint32_t index);
4052
4053 /**
4054 * Note: SideEffectType affects the getter only, not the setter.
4055 */
4056 V8_WARN_UNUSED_RESULT Maybe<bool> SetAccessor(
4057 Local<Context> context, Local<Name> name,
4058 AccessorNameGetterCallback getter,
4059 AccessorNameSetterCallback setter = nullptr,
4060 MaybeLocal<Value> data = MaybeLocal<Value>(),
4061 AccessControl settings = DEFAULT, PropertyAttribute attribute = None,
4062 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
4063 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
4064
4065 void SetAccessorProperty(Local<Name> name, Local<Function> getter,
4066 Local<Function> setter = Local<Function>(),
4067 PropertyAttribute attribute = None,
4068 AccessControl settings = DEFAULT);
4069
4070 /**
4071 * Sets a native data property like Template::SetNativeDataProperty, but
4072 * this method sets on this object directly.
4073 */
4074 V8_WARN_UNUSED_RESULT Maybe<bool> SetNativeDataProperty(
4075 Local<Context> context, Local<Name> name,
4076 AccessorNameGetterCallback getter,
4077 AccessorNameSetterCallback setter = nullptr,
4078 Local<Value> data = Local<Value>(), PropertyAttribute attributes = None,
4079 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
4080 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
4081
4082 /**
4083 * Attempts to create a property with the given name which behaves like a data
4084 * property, except that the provided getter is invoked (and provided with the
4085 * data value) to supply its value the first time it is read. After the
4086 * property is accessed once, it is replaced with an ordinary data property.
4087 *
4088 * Analogous to Template::SetLazyDataProperty.
4089 */
4090 V8_WARN_UNUSED_RESULT Maybe<bool> SetLazyDataProperty(
4091 Local<Context> context, Local<Name> name,
4092 AccessorNameGetterCallback getter, Local<Value> data = Local<Value>(),
4093 PropertyAttribute attributes = None,
4094 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
4095 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
4096
4097 /**
4098 * Functionality for private properties.
4099 * This is an experimental feature, use at your own risk.
4100 * Note: Private properties are not inherited. Do not rely on this, since it
4101 * may change.
4102 */
4103 Maybe<bool> HasPrivate(Local<Context> context, Local<Private> key);
4104 Maybe<bool> SetPrivate(Local<Context> context, Local<Private> key,
4105 Local<Value> value);
4106 Maybe<bool> DeletePrivate(Local<Context> context, Local<Private> key);
4107 MaybeLocal<Value> GetPrivate(Local<Context> context, Local<Private> key);
4108
4109 /**
4110 * Returns an array containing the names of the enumerable properties
4111 * of this object, including properties from prototype objects. The
4112 * array returned by this method contains the same values as would
4113 * be enumerated by a for-in statement over this object.
4114 */
4115 V8_WARN_UNUSED_RESULT MaybeLocal<Array> GetPropertyNames(
4116 Local<Context> context);
4117 V8_WARN_UNUSED_RESULT MaybeLocal<Array> GetPropertyNames(
4118 Local<Context> context, KeyCollectionMode mode,
4119 PropertyFilter property_filter, IndexFilter index_filter,
4120 KeyConversionMode key_conversion = KeyConversionMode::kKeepNumbers);
4121
4122 /**
4123 * This function has the same functionality as GetPropertyNames but
4124 * the returned array doesn't contain the names of properties from
4125 * prototype objects.
4126 */
4127 V8_WARN_UNUSED_RESULT MaybeLocal<Array> GetOwnPropertyNames(
4128 Local<Context> context);
4129
4130 /**
4131 * Returns an array containing the names of the filtered properties
4132 * of this object, including properties from prototype objects. The
4133 * array returned by this method contains the same values as would
4134 * be enumerated by a for-in statement over this object.
4135 */
4136 V8_WARN_UNUSED_RESULT MaybeLocal<Array> GetOwnPropertyNames(
4137 Local<Context> context, PropertyFilter filter,
4138 KeyConversionMode key_conversion = KeyConversionMode::kKeepNumbers);
4139
4140 /**
4141 * Get the prototype object. This does not skip objects marked to
4142 * be skipped by __proto__ and it does not consult the security
4143 * handler.
4144 */
4145 Local<Value> GetPrototype();
4146
4147 /**
4148 * Set the prototype object. This does not skip objects marked to
4149 * be skipped by __proto__ and it does not consult the security
4150 * handler.
4151 */
4152 V8_WARN_UNUSED_RESULT Maybe<bool> SetPrototype(Local<Context> context,
4153 Local<Value> prototype);
4154
4155 /**
4156 * Finds an instance of the given function template in the prototype
4157 * chain.
4158 */
4159 Local<Object> FindInstanceInPrototypeChain(Local<FunctionTemplate> tmpl);
4160
4161 /**
4162 * Call builtin Object.prototype.toString on this object.
4163 * This is different from Value::ToString() that may call
4164 * user-defined toString function. This one does not.
4165 */
4166 V8_WARN_UNUSED_RESULT MaybeLocal<String> ObjectProtoToString(
4167 Local<Context> context);
4168
4169 /**
4170 * Returns the name of the function invoked as a constructor for this object.
4171 */
4172 Local<String> GetConstructorName();
4173
4174 /**
4175 * Sets the integrity level of the object.
4176 */
4177 Maybe<bool> SetIntegrityLevel(Local<Context> context, IntegrityLevel level);
4178
4179 /** Gets the number of internal fields for this Object. */
4180 int InternalFieldCount();
4181
4182 /** Same as above, but works for PersistentBase. */
InternalFieldCount(const PersistentBase<Object> & object)4183 V8_INLINE static int InternalFieldCount(
4184 const PersistentBase<Object>& object) {
4185 return object.val_->InternalFieldCount();
4186 }
4187
4188 /** Same as above, but works for BasicTracedReference. */
InternalFieldCount(const BasicTracedReference<Object> & object)4189 V8_INLINE static int InternalFieldCount(
4190 const BasicTracedReference<Object>& object) {
4191 return object->InternalFieldCount();
4192 }
4193
4194 /** Gets the value from an internal field. */
4195 V8_INLINE Local<Value> GetInternalField(int index);
4196
4197 /** Sets the value in an internal field. */
4198 void SetInternalField(int index, Local<Value> value);
4199
4200 /**
4201 * Gets a 2-byte-aligned native pointer from an internal field. This field
4202 * must have been set by SetAlignedPointerInInternalField, everything else
4203 * leads to undefined behavior.
4204 */
4205 V8_INLINE void* GetAlignedPointerFromInternalField(int index);
4206
4207 /** Same as above, but works for PersistentBase. */
GetAlignedPointerFromInternalField(const PersistentBase<Object> & object,int index)4208 V8_INLINE static void* GetAlignedPointerFromInternalField(
4209 const PersistentBase<Object>& object, int index) {
4210 return object.val_->GetAlignedPointerFromInternalField(index);
4211 }
4212
4213 /** Same as above, but works for TracedGlobal. */
GetAlignedPointerFromInternalField(const BasicTracedReference<Object> & object,int index)4214 V8_INLINE static void* GetAlignedPointerFromInternalField(
4215 const BasicTracedReference<Object>& object, int index) {
4216 return object->GetAlignedPointerFromInternalField(index);
4217 }
4218
4219 /**
4220 * Sets a 2-byte-aligned native pointer in an internal field. To retrieve such
4221 * a field, GetAlignedPointerFromInternalField must be used, everything else
4222 * leads to undefined behavior.
4223 */
4224 void SetAlignedPointerInInternalField(int index, void* value);
4225 void SetAlignedPointerInInternalFields(int argc, int indices[],
4226 void* values[]);
4227
4228 /**
4229 * HasOwnProperty() is like JavaScript's Object.prototype.hasOwnProperty().
4230 *
4231 * See also v8::Object::Has() and v8::Object::HasRealNamedProperty().
4232 */
4233 V8_WARN_UNUSED_RESULT Maybe<bool> HasOwnProperty(Local<Context> context,
4234 Local<Name> key);
4235 V8_WARN_UNUSED_RESULT Maybe<bool> HasOwnProperty(Local<Context> context,
4236 uint32_t index);
4237 /**
4238 * Use HasRealNamedProperty() if you want to check if an object has an own
4239 * property without causing side effects, i.e., without calling interceptors.
4240 *
4241 * This function is similar to v8::Object::HasOwnProperty(), but it does not
4242 * call interceptors.
4243 *
4244 * \note Consider using non-masking interceptors, i.e., the interceptors are
4245 * not called if the receiver has the real named property. See
4246 * `v8::PropertyHandlerFlags::kNonMasking`.
4247 *
4248 * See also v8::Object::Has().
4249 */
4250 V8_WARN_UNUSED_RESULT Maybe<bool> HasRealNamedProperty(Local<Context> context,
4251 Local<Name> key);
4252 V8_WARN_UNUSED_RESULT Maybe<bool> HasRealIndexedProperty(
4253 Local<Context> context, uint32_t index);
4254 V8_WARN_UNUSED_RESULT Maybe<bool> HasRealNamedCallbackProperty(
4255 Local<Context> context, Local<Name> key);
4256
4257 /**
4258 * If result.IsEmpty() no real property was located in the prototype chain.
4259 * This means interceptors in the prototype chain are not called.
4260 */
4261 V8_WARN_UNUSED_RESULT MaybeLocal<Value> GetRealNamedPropertyInPrototypeChain(
4262 Local<Context> context, Local<Name> key);
4263
4264 /**
4265 * Gets the property attributes of a real property in the prototype chain,
4266 * which can be None or any combination of ReadOnly, DontEnum and DontDelete.
4267 * Interceptors in the prototype chain are not called.
4268 */
4269 V8_WARN_UNUSED_RESULT Maybe<PropertyAttribute>
4270 GetRealNamedPropertyAttributesInPrototypeChain(Local<Context> context,
4271 Local<Name> key);
4272
4273 /**
4274 * If result.IsEmpty() no real property was located on the object or
4275 * in the prototype chain.
4276 * This means interceptors in the prototype chain are not called.
4277 */
4278 V8_WARN_UNUSED_RESULT MaybeLocal<Value> GetRealNamedProperty(
4279 Local<Context> context, Local<Name> key);
4280
4281 /**
4282 * Gets the property attributes of a real property which can be
4283 * None or any combination of ReadOnly, DontEnum and DontDelete.
4284 * Interceptors in the prototype chain are not called.
4285 */
4286 V8_WARN_UNUSED_RESULT Maybe<PropertyAttribute> GetRealNamedPropertyAttributes(
4287 Local<Context> context, Local<Name> key);
4288
4289 /** Tests for a named lookup interceptor.*/
4290 bool HasNamedLookupInterceptor();
4291
4292 /** Tests for an index lookup interceptor.*/
4293 bool HasIndexedLookupInterceptor();
4294
4295 /**
4296 * Returns the identity hash for this object. The current implementation
4297 * uses a hidden property on the object to store the identity hash.
4298 *
4299 * The return value will never be 0. Also, it is not guaranteed to be
4300 * unique.
4301 */
4302 int GetIdentityHash();
4303
4304 /**
4305 * Clone this object with a fast but shallow copy. Values will point
4306 * to the same values as the original object.
4307 */
4308 // TODO(dcarney): take an isolate and optionally bail out?
4309 Local<Object> Clone();
4310
4311 /**
4312 * Returns the context in which the object was created.
4313 */
4314 // TODO(chromium:1166077): Mark as deprecate once users are updated.
4315 V8_DEPRECATE_SOON("Use MaybeLocal<Context> GetCreationContext()")
4316 Local<Context> CreationContext();
4317 MaybeLocal<Context> GetCreationContext();
4318
4319 /** Same as above, but works for Persistents */
4320 // TODO(chromium:1166077): Mark as deprecate once users are updated.
4321 V8_DEPRECATE_SOON(
4322 "Use MaybeLocal<Context> GetCreationContext(const "
4323 "PersistentBase<Object>& object)")
4324 static Local<Context> CreationContext(const PersistentBase<Object>& object);
GetCreationContext(const PersistentBase<Object> & object)4325 V8_INLINE static MaybeLocal<Context> GetCreationContext(
4326 const PersistentBase<Object>& object) {
4327 return object.val_->GetCreationContext();
4328 }
4329
4330 /**
4331 * Checks whether a callback is set by the
4332 * ObjectTemplate::SetCallAsFunctionHandler method.
4333 * When an Object is callable this method returns true.
4334 */
4335 bool IsCallable();
4336
4337 /**
4338 * True if this object is a constructor.
4339 */
4340 bool IsConstructor();
4341
4342 /**
4343 * True if this object can carry information relevant to the embedder in its
4344 * embedder fields, false otherwise. This is generally true for objects
4345 * constructed through function templates but also holds for other types where
4346 * V8 automatically adds internal fields at compile time, such as e.g.
4347 * v8::ArrayBuffer.
4348 */
4349 bool IsApiWrapper();
4350
4351 /**
4352 * True if this object was created from an object template which was marked
4353 * as undetectable. See v8::ObjectTemplate::MarkAsUndetectable for more
4354 * information.
4355 */
4356 bool IsUndetectable();
4357
4358 /**
4359 * Call an Object as a function if a callback is set by the
4360 * ObjectTemplate::SetCallAsFunctionHandler method.
4361 */
4362 V8_WARN_UNUSED_RESULT MaybeLocal<Value> CallAsFunction(Local<Context> context,
4363 Local<Value> recv,
4364 int argc,
4365 Local<Value> argv[]);
4366
4367 /**
4368 * Call an Object as a constructor if a callback is set by the
4369 * ObjectTemplate::SetCallAsFunctionHandler method.
4370 * Note: This method behaves like the Function::NewInstance method.
4371 */
4372 V8_WARN_UNUSED_RESULT MaybeLocal<Value> CallAsConstructor(
4373 Local<Context> context, int argc, Local<Value> argv[]);
4374
4375 /**
4376 * Return the isolate to which the Object belongs to.
4377 */
4378 Isolate* GetIsolate();
4379
4380 /**
4381 * If this object is a Set, Map, WeakSet or WeakMap, this returns a
4382 * representation of the elements of this object as an array.
4383 * If this object is a SetIterator or MapIterator, this returns all
4384 * elements of the underlying collection, starting at the iterator's current
4385 * position.
4386 * For other types, this will return an empty MaybeLocal<Array> (without
4387 * scheduling an exception).
4388 */
4389 MaybeLocal<Array> PreviewEntries(bool* is_key_value);
4390
4391 static Local<Object> New(Isolate* isolate);
4392
4393 /**
4394 * Creates a JavaScript object with the given properties, and
4395 * a the given prototype_or_null (which can be any JavaScript
4396 * value, and if it's null, the newly created object won't have
4397 * a prototype at all). This is similar to Object.create().
4398 * All properties will be created as enumerable, configurable
4399 * and writable properties.
4400 */
4401 static Local<Object> New(Isolate* isolate, Local<Value> prototype_or_null,
4402 Local<Name>* names, Local<Value>* values,
4403 size_t length);
4404
4405 V8_INLINE static Object* Cast(Value* obj);
4406
4407 /**
4408 * Support for TC39 "dynamic code brand checks" proposal.
4409 *
4410 * This API allows to query whether an object was constructed from a
4411 * "code like" ObjectTemplate.
4412 *
4413 * See also: v8::ObjectTemplate::SetCodeLike
4414 */
4415 bool IsCodeLike(Isolate* isolate);
4416
4417 private:
4418 Object();
4419 static void CheckCast(Value* obj);
4420 Local<Value> SlowGetInternalField(int index);
4421 void* SlowGetAlignedPointerFromInternalField(int index);
4422 };
4423
4424
4425 /**
4426 * An instance of the built-in array constructor (ECMA-262, 15.4.2).
4427 */
4428 class V8_EXPORT Array : public Object {
4429 public:
4430 uint32_t Length() const;
4431
4432 /**
4433 * Creates a JavaScript array with the given length. If the length
4434 * is negative the returned array will have length 0.
4435 */
4436 static Local<Array> New(Isolate* isolate, int length = 0);
4437
4438 /**
4439 * Creates a JavaScript array out of a Local<Value> array in C++
4440 * with a known length.
4441 */
4442 static Local<Array> New(Isolate* isolate, Local<Value>* elements,
4443 size_t length);
4444 V8_INLINE static Array* Cast(Value* obj);
4445
4446 private:
4447 Array();
4448 static void CheckCast(Value* obj);
4449 };
4450
4451
4452 /**
4453 * An instance of the built-in Map constructor (ECMA-262, 6th Edition, 23.1.1).
4454 */
4455 class V8_EXPORT Map : public Object {
4456 public:
4457 size_t Size() const;
4458 void Clear();
4459 V8_WARN_UNUSED_RESULT MaybeLocal<Value> Get(Local<Context> context,
4460 Local<Value> key);
4461 V8_WARN_UNUSED_RESULT MaybeLocal<Map> Set(Local<Context> context,
4462 Local<Value> key,
4463 Local<Value> value);
4464 V8_WARN_UNUSED_RESULT Maybe<bool> Has(Local<Context> context,
4465 Local<Value> key);
4466 V8_WARN_UNUSED_RESULT Maybe<bool> Delete(Local<Context> context,
4467 Local<Value> key);
4468
4469 /**
4470 * Returns an array of length Size() * 2, where index N is the Nth key and
4471 * index N + 1 is the Nth value.
4472 */
4473 Local<Array> AsArray() const;
4474
4475 /**
4476 * Creates a new empty Map.
4477 */
4478 static Local<Map> New(Isolate* isolate);
4479
4480 V8_INLINE static Map* Cast(Value* obj);
4481
4482 private:
4483 Map();
4484 static void CheckCast(Value* obj);
4485 };
4486
4487
4488 /**
4489 * An instance of the built-in Set constructor (ECMA-262, 6th Edition, 23.2.1).
4490 */
4491 class V8_EXPORT Set : public Object {
4492 public:
4493 size_t Size() const;
4494 void Clear();
4495 V8_WARN_UNUSED_RESULT MaybeLocal<Set> Add(Local<Context> context,
4496 Local<Value> key);
4497 V8_WARN_UNUSED_RESULT Maybe<bool> Has(Local<Context> context,
4498 Local<Value> key);
4499 V8_WARN_UNUSED_RESULT Maybe<bool> Delete(Local<Context> context,
4500 Local<Value> key);
4501
4502 /**
4503 * Returns an array of the keys in this Set.
4504 */
4505 Local<Array> AsArray() const;
4506
4507 /**
4508 * Creates a new empty Set.
4509 */
4510 static Local<Set> New(Isolate* isolate);
4511
4512 V8_INLINE static Set* Cast(Value* obj);
4513
4514 private:
4515 Set();
4516 static void CheckCast(Value* obj);
4517 };
4518
4519
4520 template<typename T>
4521 class ReturnValue {
4522 public:
ReturnValue(const ReturnValue<S> & that)4523 template <class S> V8_INLINE ReturnValue(const ReturnValue<S>& that)
4524 : value_(that.value_) {
4525 static_assert(std::is_base_of<T, S>::value, "type check");
4526 }
4527 // Local setters
4528 template <typename S>
4529 V8_INLINE void Set(const Global<S>& handle);
4530 template <typename S>
4531 V8_INLINE void Set(const BasicTracedReference<S>& handle);
4532 template <typename S>
4533 V8_INLINE void Set(const Local<S> handle);
4534 // Fast primitive setters
4535 V8_INLINE void Set(bool value);
4536 V8_INLINE void Set(double i);
4537 V8_INLINE void Set(int32_t i);
4538 V8_INLINE void Set(uint32_t i);
4539 // Fast JS primitive setters
4540 V8_INLINE void SetNull();
4541 V8_INLINE void SetUndefined();
4542 V8_INLINE void SetEmptyString();
4543 // Convenience getter for Isolate
4544 V8_INLINE Isolate* GetIsolate() const;
4545
4546 // Pointer setter: Uncompilable to prevent inadvertent misuse.
4547 template <typename S>
4548 V8_INLINE void Set(S* whatever);
4549
4550 // Getter. Creates a new Local<> so it comes with a certain performance
4551 // hit. If the ReturnValue was not yet set, this will return the undefined
4552 // value.
4553 V8_INLINE Local<Value> Get() const;
4554
4555 private:
4556 template<class F> friend class ReturnValue;
4557 template<class F> friend class FunctionCallbackInfo;
4558 template<class F> friend class PropertyCallbackInfo;
4559 template <class F, class G, class H>
4560 friend class PersistentValueMapBase;
SetInternal(internal::Address value)4561 V8_INLINE void SetInternal(internal::Address value) { *value_ = value; }
4562 V8_INLINE internal::Address GetDefaultValue();
4563 V8_INLINE explicit ReturnValue(internal::Address* slot);
4564 internal::Address* value_;
4565 };
4566
4567
4568 /**
4569 * The argument information given to function call callbacks. This
4570 * class provides access to information about the context of the call,
4571 * including the receiver, the number and values of arguments, and
4572 * the holder of the function.
4573 */
4574 template<typename T>
4575 class FunctionCallbackInfo {
4576 public:
4577 /** The number of available arguments. */
4578 V8_INLINE int Length() const;
4579 /**
4580 * Accessor for the available arguments. Returns `undefined` if the index
4581 * is out of bounds.
4582 */
4583 V8_INLINE Local<Value> operator[](int i) const;
4584 /** Returns the receiver. This corresponds to the "this" value. */
4585 V8_INLINE Local<Object> This() const;
4586 /**
4587 * If the callback was created without a Signature, this is the same
4588 * value as This(). If there is a signature, and the signature didn't match
4589 * This() but one of its hidden prototypes, this will be the respective
4590 * hidden prototype.
4591 *
4592 * Note that this is not the prototype of This() on which the accessor
4593 * referencing this callback was found (which in V8 internally is often
4594 * referred to as holder [sic]).
4595 */
4596 V8_INLINE Local<Object> Holder() const;
4597 /** For construct calls, this returns the "new.target" value. */
4598 V8_INLINE Local<Value> NewTarget() const;
4599 /** Indicates whether this is a regular call or a construct call. */
4600 V8_INLINE bool IsConstructCall() const;
4601 /** The data argument specified when creating the callback. */
4602 V8_INLINE Local<Value> Data() const;
4603 /** The current Isolate. */
4604 V8_INLINE Isolate* GetIsolate() const;
4605 /** The ReturnValue for the call. */
4606 V8_INLINE ReturnValue<T> GetReturnValue() const;
4607 // This shouldn't be public, but the arm compiler needs it.
4608 static const int kArgsLength = 6;
4609
4610 protected:
4611 friend class internal::FunctionCallbackArguments;
4612 friend class internal::CustomArguments<FunctionCallbackInfo>;
4613 friend class debug::ConsoleCallArguments;
4614 static const int kHolderIndex = 0;
4615 static const int kIsolateIndex = 1;
4616 static const int kReturnValueDefaultValueIndex = 2;
4617 static const int kReturnValueIndex = 3;
4618 static const int kDataIndex = 4;
4619 static const int kNewTargetIndex = 5;
4620
4621 V8_INLINE FunctionCallbackInfo(internal::Address* implicit_args,
4622 internal::Address* values, int length);
4623 internal::Address* implicit_args_;
4624 internal::Address* values_;
4625 int length_;
4626 };
4627
4628
4629 /**
4630 * The information passed to a property callback about the context
4631 * of the property access.
4632 */
4633 template<typename T>
4634 class PropertyCallbackInfo {
4635 public:
4636 /**
4637 * \return The isolate of the property access.
4638 */
4639 V8_INLINE Isolate* GetIsolate() const;
4640
4641 /**
4642 * \return The data set in the configuration, i.e., in
4643 * `NamedPropertyHandlerConfiguration` or
4644 * `IndexedPropertyHandlerConfiguration.`
4645 */
4646 V8_INLINE Local<Value> Data() const;
4647
4648 /**
4649 * \return The receiver. In many cases, this is the object on which the
4650 * property access was intercepted. When using
4651 * `Reflect.get`, `Function.prototype.call`, or similar functions, it is the
4652 * object passed in as receiver or thisArg.
4653 *
4654 * \code
4655 * void GetterCallback(Local<Name> name,
4656 * const v8::PropertyCallbackInfo<v8::Value>& info) {
4657 * auto context = info.GetIsolate()->GetCurrentContext();
4658 *
4659 * v8::Local<v8::Value> a_this =
4660 * info.This()
4661 * ->GetRealNamedProperty(context, v8_str("a"))
4662 * .ToLocalChecked();
4663 * v8::Local<v8::Value> a_holder =
4664 * info.Holder()
4665 * ->GetRealNamedProperty(context, v8_str("a"))
4666 * .ToLocalChecked();
4667 *
4668 * CHECK(v8_str("r")->Equals(context, a_this).FromJust());
4669 * CHECK(v8_str("obj")->Equals(context, a_holder).FromJust());
4670 *
4671 * info.GetReturnValue().Set(name);
4672 * }
4673 *
4674 * v8::Local<v8::FunctionTemplate> templ =
4675 * v8::FunctionTemplate::New(isolate);
4676 * templ->InstanceTemplate()->SetHandler(
4677 * v8::NamedPropertyHandlerConfiguration(GetterCallback));
4678 * LocalContext env;
4679 * env->Global()
4680 * ->Set(env.local(), v8_str("obj"), templ->GetFunction(env.local())
4681 * .ToLocalChecked()
4682 * ->NewInstance(env.local())
4683 * .ToLocalChecked())
4684 * .FromJust();
4685 *
4686 * CompileRun("obj.a = 'obj'; var r = {a: 'r'}; Reflect.get(obj, 'x', r)");
4687 * \endcode
4688 */
4689 V8_INLINE Local<Object> This() const;
4690
4691 /**
4692 * \return The object in the prototype chain of the receiver that has the
4693 * interceptor. Suppose you have `x` and its prototype is `y`, and `y`
4694 * has an interceptor. Then `info.This()` is `x` and `info.Holder()` is `y`.
4695 * The Holder() could be a hidden object (the global object, rather
4696 * than the global proxy).
4697 *
4698 * \note For security reasons, do not pass the object back into the runtime.
4699 */
4700 V8_INLINE Local<Object> Holder() const;
4701
4702 /**
4703 * \return The return value of the callback.
4704 * Can be changed by calling Set().
4705 * \code
4706 * info.GetReturnValue().Set(...)
4707 * \endcode
4708 *
4709 */
4710 V8_INLINE ReturnValue<T> GetReturnValue() const;
4711
4712 /**
4713 * \return True if the intercepted function should throw if an error occurs.
4714 * Usually, `true` corresponds to `'use strict'`.
4715 *
4716 * \note Always `false` when intercepting `Reflect.set()`
4717 * independent of the language mode.
4718 */
4719 V8_INLINE bool ShouldThrowOnError() const;
4720
4721 // This shouldn't be public, but the arm compiler needs it.
4722 static const int kArgsLength = 7;
4723
4724 protected:
4725 friend class MacroAssembler;
4726 friend class internal::PropertyCallbackArguments;
4727 friend class internal::CustomArguments<PropertyCallbackInfo>;
4728 static const int kShouldThrowOnErrorIndex = 0;
4729 static const int kHolderIndex = 1;
4730 static const int kIsolateIndex = 2;
4731 static const int kReturnValueDefaultValueIndex = 3;
4732 static const int kReturnValueIndex = 4;
4733 static const int kDataIndex = 5;
4734 static const int kThisIndex = 6;
4735
PropertyCallbackInfo(internal::Address * args)4736 V8_INLINE PropertyCallbackInfo(internal::Address* args) : args_(args) {}
4737 internal::Address* args_;
4738 };
4739
4740 using FunctionCallback = void (*)(const FunctionCallbackInfo<Value>& info);
4741
4742 enum class ConstructorBehavior { kThrow, kAllow };
4743
4744 /**
4745 * A JavaScript function object (ECMA-262, 15.3).
4746 */
4747 class V8_EXPORT Function : public Object {
4748 public:
4749 /**
4750 * Create a function in the current execution context
4751 * for a given FunctionCallback.
4752 */
4753 static MaybeLocal<Function> New(
4754 Local<Context> context, FunctionCallback callback,
4755 Local<Value> data = Local<Value>(), int length = 0,
4756 ConstructorBehavior behavior = ConstructorBehavior::kAllow,
4757 SideEffectType side_effect_type = SideEffectType::kHasSideEffect);
4758
4759 V8_WARN_UNUSED_RESULT MaybeLocal<Object> NewInstance(
4760 Local<Context> context, int argc, Local<Value> argv[]) const;
4761
NewInstance(Local<Context> context)4762 V8_WARN_UNUSED_RESULT MaybeLocal<Object> NewInstance(
4763 Local<Context> context) const {
4764 return NewInstance(context, 0, nullptr);
4765 }
4766
4767 /**
4768 * When side effect checks are enabled, passing kHasNoSideEffect allows the
4769 * constructor to be invoked without throwing. Calls made within the
4770 * constructor are still checked.
4771 */
4772 V8_WARN_UNUSED_RESULT MaybeLocal<Object> NewInstanceWithSideEffectType(
4773 Local<Context> context, int argc, Local<Value> argv[],
4774 SideEffectType side_effect_type = SideEffectType::kHasSideEffect) const;
4775
4776 V8_WARN_UNUSED_RESULT MaybeLocal<Value> Call(Local<Context> context,
4777 Local<Value> recv, int argc,
4778 Local<Value> argv[]);
4779
4780 void SetName(Local<String> name);
4781 Local<Value> GetName() const;
4782
4783 /**
4784 * Name inferred from variable or property assignment of this function.
4785 * Used to facilitate debugging and profiling of JavaScript code written
4786 * in an OO style, where many functions are anonymous but are assigned
4787 * to object properties.
4788 */
4789 Local<Value> GetInferredName() const;
4790
4791 /**
4792 * displayName if it is set, otherwise name if it is configured, otherwise
4793 * function name, otherwise inferred name.
4794 */
4795 Local<Value> GetDebugName() const;
4796
4797 /**
4798 * User-defined name assigned to the "displayName" property of this function.
4799 * Used to facilitate debugging and profiling of JavaScript code.
4800 */
4801 V8_DEPRECATED(
4802 "Use v8::Object::Get() instead to look up \"displayName\". "
4803 "V8 and DevTools no longer use \"displayName\" in stack "
4804 "traces, but the standard \"name\" property. "
4805 "See http://crbug.com/1177685.")
4806 Local<Value> GetDisplayName() const;
4807
4808 /**
4809 * Returns zero based line number of function body and
4810 * kLineOffsetNotFound if no information available.
4811 */
4812 int GetScriptLineNumber() const;
4813 /**
4814 * Returns zero based column number of function body and
4815 * kLineOffsetNotFound if no information available.
4816 */
4817 int GetScriptColumnNumber() const;
4818
4819 /**
4820 * Returns scriptId.
4821 */
4822 int ScriptId() const;
4823
4824 /**
4825 * Returns the original function if this function is bound, else returns
4826 * v8::Undefined.
4827 */
4828 Local<Value> GetBoundFunction() const;
4829
4830 /**
4831 * Calls builtin Function.prototype.toString on this function.
4832 * This is different from Value::ToString() that may call a user-defined
4833 * toString() function, and different than Object::ObjectProtoToString() which
4834 * always serializes "[object Function]".
4835 */
4836 V8_WARN_UNUSED_RESULT MaybeLocal<String> FunctionProtoToString(
4837 Local<Context> context);
4838
4839 ScriptOrigin GetScriptOrigin() const;
4840 V8_INLINE static Function* Cast(Value* obj);
4841 static const int kLineOffsetNotFound;
4842
4843 private:
4844 Function();
4845 static void CheckCast(Value* obj);
4846 };
4847
4848 #ifndef V8_PROMISE_INTERNAL_FIELD_COUNT
4849 // The number of required internal fields can be defined by embedder.
4850 #define V8_PROMISE_INTERNAL_FIELD_COUNT 0
4851 #endif
4852
4853 /**
4854 * An instance of the built-in Promise constructor (ES6 draft).
4855 */
4856 class V8_EXPORT Promise : public Object {
4857 public:
4858 /**
4859 * State of the promise. Each value corresponds to one of the possible values
4860 * of the [[PromiseState]] field.
4861 */
4862 enum PromiseState { kPending, kFulfilled, kRejected };
4863
4864 class V8_EXPORT Resolver : public Object {
4865 public:
4866 /**
4867 * Create a new resolver, along with an associated promise in pending state.
4868 */
4869 static V8_WARN_UNUSED_RESULT MaybeLocal<Resolver> New(
4870 Local<Context> context);
4871
4872 /**
4873 * Extract the associated promise.
4874 */
4875 Local<Promise> GetPromise();
4876
4877 /**
4878 * Resolve/reject the associated promise with a given value.
4879 * Ignored if the promise is no longer pending.
4880 */
4881 V8_WARN_UNUSED_RESULT Maybe<bool> Resolve(Local<Context> context,
4882 Local<Value> value);
4883
4884 V8_WARN_UNUSED_RESULT Maybe<bool> Reject(Local<Context> context,
4885 Local<Value> value);
4886
4887 V8_INLINE static Resolver* Cast(Value* obj);
4888
4889 private:
4890 Resolver();
4891 static void CheckCast(Value* obj);
4892 };
4893
4894 /**
4895 * Register a resolution/rejection handler with a promise.
4896 * The handler is given the respective resolution/rejection value as
4897 * an argument. If the promise is already resolved/rejected, the handler is
4898 * invoked at the end of turn.
4899 */
4900 V8_WARN_UNUSED_RESULT MaybeLocal<Promise> Catch(Local<Context> context,
4901 Local<Function> handler);
4902
4903 V8_WARN_UNUSED_RESULT MaybeLocal<Promise> Then(Local<Context> context,
4904 Local<Function> handler);
4905
4906 V8_WARN_UNUSED_RESULT MaybeLocal<Promise> Then(Local<Context> context,
4907 Local<Function> on_fulfilled,
4908 Local<Function> on_rejected);
4909
4910 /**
4911 * Returns true if the promise has at least one derived promise, and
4912 * therefore resolve/reject handlers (including default handler).
4913 */
4914 bool HasHandler();
4915
4916 /**
4917 * Returns the content of the [[PromiseResult]] field. The Promise must not
4918 * be pending.
4919 */
4920 Local<Value> Result();
4921
4922 /**
4923 * Returns the value of the [[PromiseState]] field.
4924 */
4925 PromiseState State();
4926
4927 /**
4928 * Marks this promise as handled to avoid reporting unhandled rejections.
4929 */
4930 void MarkAsHandled();
4931
4932 /**
4933 * Marks this promise as silent to prevent pausing the debugger when the
4934 * promise is rejected.
4935 */
4936 void MarkAsSilent();
4937
4938 V8_INLINE static Promise* Cast(Value* obj);
4939
4940 static const int kEmbedderFieldCount = V8_PROMISE_INTERNAL_FIELD_COUNT;
4941
4942 private:
4943 Promise();
4944 static void CheckCast(Value* obj);
4945 };
4946
4947 /**
4948 * An instance of a Property Descriptor, see Ecma-262 6.2.4.
4949 *
4950 * Properties in a descriptor are present or absent. If you do not set
4951 * `enumerable`, `configurable`, and `writable`, they are absent. If `value`,
4952 * `get`, or `set` are absent, but you must specify them in the constructor, use
4953 * empty handles.
4954 *
4955 * Accessors `get` and `set` must be callable or undefined if they are present.
4956 *
4957 * \note Only query properties if they are present, i.e., call `x()` only if
4958 * `has_x()` returns true.
4959 *
4960 * \code
4961 * // var desc = {writable: false}
4962 * v8::PropertyDescriptor d(Local<Value>()), false);
4963 * d.value(); // error, value not set
4964 * if (d.has_writable()) {
4965 * d.writable(); // false
4966 * }
4967 *
4968 * // var desc = {value: undefined}
4969 * v8::PropertyDescriptor d(v8::Undefined(isolate));
4970 *
4971 * // var desc = {get: undefined}
4972 * v8::PropertyDescriptor d(v8::Undefined(isolate), Local<Value>()));
4973 * \endcode
4974 */
4975 class V8_EXPORT PropertyDescriptor {
4976 public:
4977 // GenericDescriptor
4978 PropertyDescriptor();
4979
4980 // DataDescriptor
4981 explicit PropertyDescriptor(Local<Value> value);
4982
4983 // DataDescriptor with writable property
4984 PropertyDescriptor(Local<Value> value, bool writable);
4985
4986 // AccessorDescriptor
4987 PropertyDescriptor(Local<Value> get, Local<Value> set);
4988
4989 ~PropertyDescriptor();
4990
4991 Local<Value> value() const;
4992 bool has_value() const;
4993
4994 Local<Value> get() const;
4995 bool has_get() const;
4996 Local<Value> set() const;
4997 bool has_set() const;
4998
4999 void set_enumerable(bool enumerable);
5000 bool enumerable() const;
5001 bool has_enumerable() const;
5002
5003 void set_configurable(bool configurable);
5004 bool configurable() const;
5005 bool has_configurable() const;
5006
5007 bool writable() const;
5008 bool has_writable() const;
5009
5010 struct PrivateData;
get_private()5011 PrivateData* get_private() const { return private_; }
5012
5013 PropertyDescriptor(const PropertyDescriptor&) = delete;
5014 void operator=(const PropertyDescriptor&) = delete;
5015
5016 private:
5017 PrivateData* private_;
5018 };
5019
5020 /**
5021 * An instance of the built-in Proxy constructor (ECMA-262, 6th Edition,
5022 * 26.2.1).
5023 */
5024 class V8_EXPORT Proxy : public Object {
5025 public:
5026 Local<Value> GetTarget();
5027 Local<Value> GetHandler();
5028 bool IsRevoked();
5029 void Revoke();
5030
5031 /**
5032 * Creates a new Proxy for the target object.
5033 */
5034 static MaybeLocal<Proxy> New(Local<Context> context,
5035 Local<Object> local_target,
5036 Local<Object> local_handler);
5037
5038 V8_INLINE static Proxy* Cast(Value* obj);
5039
5040 private:
5041 Proxy();
5042 static void CheckCast(Value* obj);
5043 };
5044
5045 /**
5046 * Points to an unowned continous buffer holding a known number of elements.
5047 *
5048 * This is similar to std::span (under consideration for C++20), but does not
5049 * require advanced C++ support. In the (far) future, this may be replaced with
5050 * or aliased to std::span.
5051 *
5052 * To facilitate future migration, this class exposes a subset of the interface
5053 * implemented by std::span.
5054 */
5055 template <typename T>
5056 class V8_EXPORT MemorySpan {
5057 public:
5058 /** The default constructor creates an empty span. */
5059 constexpr MemorySpan() = default;
5060
MemorySpan(T * data,size_t size)5061 constexpr MemorySpan(T* data, size_t size) : data_(data), size_(size) {}
5062
5063 /** Returns a pointer to the beginning of the buffer. */
data()5064 constexpr T* data() const { return data_; }
5065 /** Returns the number of elements that the buffer holds. */
size()5066 constexpr size_t size() const { return size_; }
5067
5068 private:
5069 T* data_ = nullptr;
5070 size_t size_ = 0;
5071 };
5072
5073 /**
5074 * An owned byte buffer with associated size.
5075 */
5076 struct OwnedBuffer {
5077 std::unique_ptr<const uint8_t[]> buffer;
5078 size_t size = 0;
OwnedBufferOwnedBuffer5079 OwnedBuffer(std::unique_ptr<const uint8_t[]> buffer, size_t size)
5080 : buffer(std::move(buffer)), size(size) {}
5081 OwnedBuffer() = default;
5082 };
5083
5084 // Wrapper around a compiled WebAssembly module, which is potentially shared by
5085 // different WasmModuleObjects.
5086 class V8_EXPORT CompiledWasmModule {
5087 public:
5088 /**
5089 * Serialize the compiled module. The serialized data does not include the
5090 * wire bytes.
5091 */
5092 OwnedBuffer Serialize();
5093
5094 /**
5095 * Get the (wasm-encoded) wire bytes that were used to compile this module.
5096 */
5097 MemorySpan<const uint8_t> GetWireBytesRef();
5098
source_url()5099 const std::string& source_url() const { return source_url_; }
5100
5101 private:
5102 friend class WasmModuleObject;
5103 friend class WasmStreaming;
5104
5105 explicit CompiledWasmModule(std::shared_ptr<internal::wasm::NativeModule>,
5106 const char* source_url, size_t url_length);
5107
5108 const std::shared_ptr<internal::wasm::NativeModule> native_module_;
5109 const std::string source_url_;
5110 };
5111
5112 // An instance of WebAssembly.Memory.
5113 class V8_EXPORT WasmMemoryObject : public Object {
5114 public:
5115 WasmMemoryObject() = delete;
5116
5117 /**
5118 * Returns underlying ArrayBuffer.
5119 */
5120 Local<ArrayBuffer> Buffer();
5121
5122 V8_INLINE static WasmMemoryObject* Cast(Value* obj);
5123
5124 private:
5125 static void CheckCast(Value* object);
5126 };
5127
5128 // An instance of WebAssembly.Module.
5129 class V8_EXPORT WasmModuleObject : public Object {
5130 public:
5131 WasmModuleObject() = delete;
5132
5133 /**
5134 * Efficiently re-create a WasmModuleObject, without recompiling, from
5135 * a CompiledWasmModule.
5136 */
5137 static MaybeLocal<WasmModuleObject> FromCompiledModule(
5138 Isolate* isolate, const CompiledWasmModule&);
5139
5140 /**
5141 * Get the compiled module for this module object. The compiled module can be
5142 * shared by several module objects.
5143 */
5144 CompiledWasmModule GetCompiledModule();
5145
5146 V8_INLINE static WasmModuleObject* Cast(Value* obj);
5147
5148 private:
5149 static void CheckCast(Value* obj);
5150 };
5151
5152 /**
5153 * The V8 interface for WebAssembly streaming compilation. When streaming
5154 * compilation is initiated, V8 passes a {WasmStreaming} object to the embedder
5155 * such that the embedder can pass the input bytes for streaming compilation to
5156 * V8.
5157 */
5158 class V8_EXPORT WasmStreaming final {
5159 public:
5160 class WasmStreamingImpl;
5161
5162 /**
5163 * Client to receive streaming event notifications.
5164 */
5165 class Client {
5166 public:
5167 virtual ~Client() = default;
5168 /**
5169 * Passes the fully compiled module to the client. This can be used to
5170 * implement code caching.
5171 */
5172 virtual void OnModuleCompiled(CompiledWasmModule compiled_module) = 0;
5173 };
5174
5175 explicit WasmStreaming(std::unique_ptr<WasmStreamingImpl> impl);
5176
5177 ~WasmStreaming();
5178
5179 /**
5180 * Pass a new chunk of bytes to WebAssembly streaming compilation.
5181 * The buffer passed into {OnBytesReceived} is owned by the caller.
5182 */
5183 void OnBytesReceived(const uint8_t* bytes, size_t size);
5184
5185 /**
5186 * {Finish} should be called after all received bytes where passed to
5187 * {OnBytesReceived} to tell V8 that there will be no more bytes. {Finish}
5188 * does not have to be called after {Abort} has been called already.
5189 */
5190 void Finish();
5191
5192 /**
5193 * Abort streaming compilation. If {exception} has a value, then the promise
5194 * associated with streaming compilation is rejected with that value. If
5195 * {exception} does not have value, the promise does not get rejected.
5196 */
5197 void Abort(MaybeLocal<Value> exception);
5198
5199 /**
5200 * Passes previously compiled module bytes. This must be called before
5201 * {OnBytesReceived}, {Finish}, or {Abort}. Returns true if the module bytes
5202 * can be used, false otherwise. The buffer passed via {bytes} and {size}
5203 * is owned by the caller. If {SetCompiledModuleBytes} returns true, the
5204 * buffer must remain valid until either {Finish} or {Abort} completes.
5205 */
5206 bool SetCompiledModuleBytes(const uint8_t* bytes, size_t size);
5207
5208 /**
5209 * Sets the client object that will receive streaming event notifications.
5210 * This must be called before {OnBytesReceived}, {Finish}, or {Abort}.
5211 */
5212 void SetClient(std::shared_ptr<Client> client);
5213
5214 /*
5215 * Sets the UTF-8 encoded source URL for the {Script} object. This must be
5216 * called before {Finish}.
5217 */
5218 void SetUrl(const char* url, size_t length);
5219
5220 /**
5221 * Unpacks a {WasmStreaming} object wrapped in a {Managed} for the embedder.
5222 * Since the embedder is on the other side of the API, it cannot unpack the
5223 * {Managed} itself.
5224 */
5225 static std::shared_ptr<WasmStreaming> Unpack(Isolate* isolate,
5226 Local<Value> value);
5227
5228 private:
5229 std::unique_ptr<WasmStreamingImpl> impl_;
5230 };
5231
5232 // TODO(mtrofin): when streaming compilation is done, we can rename this
5233 // to simply WasmModuleObjectBuilder
5234 class V8_EXPORT WasmModuleObjectBuilderStreaming final {
5235 public:
5236 explicit WasmModuleObjectBuilderStreaming(Isolate* isolate);
5237 /**
5238 * The buffer passed into OnBytesReceived is owned by the caller.
5239 */
5240 void OnBytesReceived(const uint8_t*, size_t size);
5241 void Finish();
5242 /**
5243 * Abort streaming compilation. If {exception} has a value, then the promise
5244 * associated with streaming compilation is rejected with that value. If
5245 * {exception} does not have value, the promise does not get rejected.
5246 */
5247 void Abort(MaybeLocal<Value> exception);
5248 Local<Promise> GetPromise();
5249
5250 ~WasmModuleObjectBuilderStreaming() = default;
5251
5252 private:
5253 WasmModuleObjectBuilderStreaming(const WasmModuleObjectBuilderStreaming&) =
5254 delete;
5255 WasmModuleObjectBuilderStreaming(WasmModuleObjectBuilderStreaming&&) =
5256 default;
5257 WasmModuleObjectBuilderStreaming& operator=(
5258 const WasmModuleObjectBuilderStreaming&) = delete;
5259 WasmModuleObjectBuilderStreaming& operator=(
5260 WasmModuleObjectBuilderStreaming&&) = default;
5261 Isolate* isolate_ = nullptr;
5262
5263 #if V8_CC_MSVC
5264 /**
5265 * We don't need the static Copy API, so the default
5266 * NonCopyablePersistentTraits would be sufficient, however,
5267 * MSVC eagerly instantiates the Copy.
5268 * We ensure we don't use Copy, however, by compiling with the
5269 * defaults everywhere else.
5270 */
5271 Persistent<Promise, CopyablePersistentTraits<Promise>> promise_;
5272 #else
5273 Persistent<Promise> promise_;
5274 #endif
5275 std::shared_ptr<internal::wasm::StreamingDecoder> streaming_decoder_;
5276 };
5277
5278 #ifndef V8_ARRAY_BUFFER_INTERNAL_FIELD_COUNT
5279 // The number of required internal fields can be defined by embedder.
5280 #define V8_ARRAY_BUFFER_INTERNAL_FIELD_COUNT 2
5281 #endif
5282
5283
5284 enum class ArrayBufferCreationMode { kInternalized, kExternalized };
5285
5286 /**
5287 * A wrapper around the backing store (i.e. the raw memory) of an array buffer.
5288 * See a document linked in http://crbug.com/v8/9908 for more information.
5289 *
5290 * The allocation and destruction of backing stores is generally managed by
5291 * V8. Clients should always use standard C++ memory ownership types (i.e.
5292 * std::unique_ptr and std::shared_ptr) to manage lifetimes of backing stores
5293 * properly, since V8 internal objects may alias backing stores.
5294 *
5295 * This object does not keep the underlying |ArrayBuffer::Allocator| alive by
5296 * default. Use Isolate::CreateParams::array_buffer_allocator_shared when
5297 * creating the Isolate to make it hold a reference to the allocator itself.
5298 */
5299 class V8_EXPORT BackingStore : public v8::internal::BackingStoreBase {
5300 public:
5301 ~BackingStore();
5302
5303 /**
5304 * Return a pointer to the beginning of the memory block for this backing
5305 * store. The pointer is only valid as long as this backing store object
5306 * lives.
5307 */
5308 void* Data() const;
5309
5310 /**
5311 * The length (in bytes) of this backing store.
5312 */
5313 size_t ByteLength() const;
5314
5315 /**
5316 * Indicates whether the backing store was created for an ArrayBuffer or
5317 * a SharedArrayBuffer.
5318 */
5319 bool IsShared() const;
5320
5321 /**
5322 * Prevent implicit instantiation of operator delete with size_t argument.
5323 * The size_t argument would be incorrect because ptr points to the
5324 * internal BackingStore object.
5325 */
delete(void * ptr)5326 void operator delete(void* ptr) { ::operator delete(ptr); }
5327
5328 /**
5329 * Wrapper around ArrayBuffer::Allocator::Reallocate that preserves IsShared.
5330 * Assumes that the backing_store was allocated by the ArrayBuffer allocator
5331 * of the given isolate.
5332 */
5333 static std::unique_ptr<BackingStore> Reallocate(
5334 v8::Isolate* isolate, std::unique_ptr<BackingStore> backing_store,
5335 size_t byte_length);
5336
5337 /**
5338 * This callback is used only if the memory block for a BackingStore cannot be
5339 * allocated with an ArrayBuffer::Allocator. In such cases the destructor of
5340 * the BackingStore invokes the callback to free the memory block.
5341 */
5342 using DeleterCallback = void (*)(void* data, size_t length,
5343 void* deleter_data);
5344
5345 /**
5346 * If the memory block of a BackingStore is static or is managed manually,
5347 * then this empty deleter along with nullptr deleter_data can be passed to
5348 * ArrayBuffer::NewBackingStore to indicate that.
5349 *
5350 * The manually managed case should be used with caution and only when it
5351 * is guaranteed that the memory block freeing happens after detaching its
5352 * ArrayBuffer.
5353 */
5354 static void EmptyDeleter(void* data, size_t length, void* deleter_data);
5355
5356 private:
5357 /**
5358 * See [Shared]ArrayBuffer::GetBackingStore and
5359 * [Shared]ArrayBuffer::NewBackingStore.
5360 */
5361 BackingStore();
5362 };
5363
5364 #if !defined(V8_IMMINENT_DEPRECATION_WARNINGS)
5365 // Use v8::BackingStore::DeleterCallback instead.
5366 using BackingStoreDeleterCallback = void (*)(void* data, size_t length,
5367 void* deleter_data);
5368
5369 #endif
5370
5371 /**
5372 * An instance of the built-in ArrayBuffer constructor (ES6 draft 15.13.5).
5373 */
5374 class V8_EXPORT ArrayBuffer : public Object {
5375 public:
5376 /**
5377 * A thread-safe allocator that V8 uses to allocate |ArrayBuffer|'s memory.
5378 * The allocator is a global V8 setting. It has to be set via
5379 * Isolate::CreateParams.
5380 *
5381 * Memory allocated through this allocator by V8 is accounted for as external
5382 * memory by V8. Note that V8 keeps track of the memory for all internalized
5383 * |ArrayBuffer|s. Responsibility for tracking external memory (using
5384 * Isolate::AdjustAmountOfExternalAllocatedMemory) is handed over to the
5385 * embedder upon externalization and taken over upon internalization (creating
5386 * an internalized buffer from an existing buffer).
5387 *
5388 * Note that it is unsafe to call back into V8 from any of the allocator
5389 * functions.
5390 */
5391 class V8_EXPORT Allocator {
5392 public:
5393 virtual ~Allocator() = default;
5394
5395 /**
5396 * Allocate |length| bytes. Return nullptr if allocation is not successful.
5397 * Memory should be initialized to zeroes.
5398 */
5399 virtual void* Allocate(size_t length) = 0;
5400
5401 /**
5402 * Allocate |length| bytes. Return nullptr if allocation is not successful.
5403 * Memory does not have to be initialized.
5404 */
5405 virtual void* AllocateUninitialized(size_t length) = 0;
5406
5407 /**
5408 * Free the memory block of size |length|, pointed to by |data|.
5409 * That memory is guaranteed to be previously allocated by |Allocate|.
5410 */
5411 virtual void Free(void* data, size_t length) = 0;
5412
5413 /**
5414 * Reallocate the memory block of size |old_length| to a memory block of
5415 * size |new_length| by expanding, contracting, or copying the existing
5416 * memory block. If |new_length| > |old_length|, then the new part of
5417 * the memory must be initialized to zeros. Return nullptr if reallocation
5418 * is not successful.
5419 *
5420 * The caller guarantees that the memory block was previously allocated
5421 * using Allocate or AllocateUninitialized.
5422 *
5423 * The default implementation allocates a new block and copies data.
5424 */
5425 virtual void* Reallocate(void* data, size_t old_length, size_t new_length);
5426
5427 /**
5428 * ArrayBuffer allocation mode. kNormal is a malloc/free style allocation,
5429 * while kReservation is for larger allocations with the ability to set
5430 * access permissions.
5431 */
5432 enum class AllocationMode { kNormal, kReservation };
5433
5434 /**
5435 * malloc/free based convenience allocator.
5436 *
5437 * Caller takes ownership, i.e. the returned object needs to be freed using
5438 * |delete allocator| once it is no longer in use.
5439 */
5440 static Allocator* NewDefaultAllocator();
5441 };
5442
5443 /**
5444 * The contents of an |ArrayBuffer|. Externalization of |ArrayBuffer|
5445 * returns an instance of this class, populated, with a pointer to data
5446 * and byte length.
5447 *
5448 * The Data pointer of ArrayBuffer::Contents must be freed using the provided
5449 * deleter, which will call ArrayBuffer::Allocator::Free if the buffer
5450 * was allocated with ArraryBuffer::Allocator::Allocate.
5451 */
5452 class V8_EXPORT Contents { // NOLINT
5453 public:
5454 using DeleterCallback = void (*)(void* buffer, size_t length, void* info);
5455
Contents()5456 Contents()
5457 : data_(nullptr),
5458 byte_length_(0),
5459 allocation_base_(nullptr),
5460 allocation_length_(0),
5461 allocation_mode_(Allocator::AllocationMode::kNormal),
5462 deleter_(nullptr),
5463 deleter_data_(nullptr) {}
5464
AllocationBase()5465 void* AllocationBase() const { return allocation_base_; }
AllocationLength()5466 size_t AllocationLength() const { return allocation_length_; }
AllocationMode()5467 Allocator::AllocationMode AllocationMode() const {
5468 return allocation_mode_;
5469 }
5470
Data()5471 void* Data() const { return data_; }
ByteLength()5472 size_t ByteLength() const { return byte_length_; }
Deleter()5473 DeleterCallback Deleter() const { return deleter_; }
DeleterData()5474 void* DeleterData() const { return deleter_data_; }
5475
5476 private:
5477 Contents(void* data, size_t byte_length, void* allocation_base,
5478 size_t allocation_length,
5479 Allocator::AllocationMode allocation_mode, DeleterCallback deleter,
5480 void* deleter_data);
5481
5482 void* data_;
5483 size_t byte_length_;
5484 void* allocation_base_;
5485 size_t allocation_length_;
5486 Allocator::AllocationMode allocation_mode_;
5487 DeleterCallback deleter_;
5488 void* deleter_data_;
5489
5490 friend class ArrayBuffer;
5491 };
5492
5493
5494 /**
5495 * Data length in bytes.
5496 */
5497 size_t ByteLength() const;
5498
5499 /**
5500 * Create a new ArrayBuffer. Allocate |byte_length| bytes.
5501 * Allocated memory will be owned by a created ArrayBuffer and
5502 * will be deallocated when it is garbage-collected,
5503 * unless the object is externalized.
5504 */
5505 static Local<ArrayBuffer> New(Isolate* isolate, size_t byte_length);
5506
5507 /**
5508 * Create a new ArrayBuffer over an existing memory block.
5509 * The created array buffer is by default immediately in externalized state.
5510 * In externalized state, the memory block will not be reclaimed when a
5511 * created ArrayBuffer is garbage-collected.
5512 * In internalized state, the memory block will be released using
5513 * |Allocator::Free| once all ArrayBuffers referencing it are collected by
5514 * the garbage collector.
5515 */
5516 V8_DEPRECATED(
5517 "Use the version that takes a BackingStore. "
5518 "See http://crbug.com/v8/9908.")
5519 static Local<ArrayBuffer> New(
5520 Isolate* isolate, void* data, size_t byte_length,
5521 ArrayBufferCreationMode mode = ArrayBufferCreationMode::kExternalized);
5522
5523 /**
5524 * Create a new ArrayBuffer with an existing backing store.
5525 * The created array keeps a reference to the backing store until the array
5526 * is garbage collected. Note that the IsExternal bit does not affect this
5527 * reference from the array to the backing store.
5528 *
5529 * In future IsExternal bit will be removed. Until then the bit is set as
5530 * follows. If the backing store does not own the underlying buffer, then
5531 * the array is created in externalized state. Otherwise, the array is created
5532 * in internalized state. In the latter case the array can be transitioned
5533 * to the externalized state using Externalize(backing_store).
5534 */
5535 static Local<ArrayBuffer> New(Isolate* isolate,
5536 std::shared_ptr<BackingStore> backing_store);
5537
5538 /**
5539 * Returns a new standalone BackingStore that is allocated using the array
5540 * buffer allocator of the isolate. The result can be later passed to
5541 * ArrayBuffer::New.
5542 *
5543 * If the allocator returns nullptr, then the function may cause GCs in the
5544 * given isolate and re-try the allocation. If GCs do not help, then the
5545 * function will crash with an out-of-memory error.
5546 */
5547 static std::unique_ptr<BackingStore> NewBackingStore(Isolate* isolate,
5548 size_t byte_length);
5549 /**
5550 * Returns a new standalone BackingStore that takes over the ownership of
5551 * the given buffer. The destructor of the BackingStore invokes the given
5552 * deleter callback.
5553 *
5554 * The result can be later passed to ArrayBuffer::New. The raw pointer
5555 * to the buffer must not be passed again to any V8 API function.
5556 */
5557 static std::unique_ptr<BackingStore> NewBackingStore(
5558 void* data, size_t byte_length, v8::BackingStore::DeleterCallback deleter,
5559 void* deleter_data);
5560
5561 /**
5562 * Returns true if ArrayBuffer is externalized, that is, does not
5563 * own its memory block.
5564 */
5565 V8_DEPRECATED(
5566 "With v8::BackingStore externalized ArrayBuffers are "
5567 "the same as ordinary ArrayBuffers. See http://crbug.com/v8/9908.")
5568 bool IsExternal() const;
5569
5570 /**
5571 * Returns true if this ArrayBuffer may be detached.
5572 */
5573 bool IsDetachable() const;
5574
5575 /**
5576 * Detaches this ArrayBuffer and all its views (typed arrays).
5577 * Detaching sets the byte length of the buffer and all typed arrays to zero,
5578 * preventing JavaScript from ever accessing underlying backing store.
5579 * ArrayBuffer should have been externalized and must be detachable.
5580 */
5581 void Detach();
5582
5583 /**
5584 * Make this ArrayBuffer external. The pointer to underlying memory block
5585 * and byte length are returned as |Contents| structure. After ArrayBuffer
5586 * had been externalized, it does no longer own the memory block. The caller
5587 * should take steps to free memory when it is no longer needed.
5588 *
5589 * The Data pointer of ArrayBuffer::Contents must be freed using the provided
5590 * deleter, which will call ArrayBuffer::Allocator::Free if the buffer
5591 * was allocated with ArrayBuffer::Allocator::Allocate.
5592 */
5593 V8_DEPRECATED("Use GetBackingStore or Detach. See http://crbug.com/v8/9908.")
5594 Contents Externalize();
5595
5596 /**
5597 * Marks this ArrayBuffer external given a witness that the embedder
5598 * has fetched the backing store using the new GetBackingStore() function.
5599 *
5600 * With the new lifetime management of backing stores there is no need for
5601 * externalizing, so this function exists only to make the transition easier.
5602 */
5603 V8_DEPRECATED("This will be removed together with IsExternal.")
5604 void Externalize(const std::shared_ptr<BackingStore>& backing_store);
5605
5606 /**
5607 * Get a pointer to the ArrayBuffer's underlying memory block without
5608 * externalizing it. If the ArrayBuffer is not externalized, this pointer
5609 * will become invalid as soon as the ArrayBuffer gets garbage collected.
5610 *
5611 * The embedder should make sure to hold a strong reference to the
5612 * ArrayBuffer while accessing this pointer.
5613 */
5614 V8_DEPRECATED("Use GetBackingStore. See http://crbug.com/v8/9908.")
5615 Contents GetContents();
5616
5617 /**
5618 * Get a shared pointer to the backing store of this array buffer. This
5619 * pointer coordinates the lifetime management of the internal storage
5620 * with any live ArrayBuffers on the heap, even across isolates. The embedder
5621 * should not attempt to manage lifetime of the storage through other means.
5622 *
5623 * This function replaces both Externalize() and GetContents().
5624 */
5625 std::shared_ptr<BackingStore> GetBackingStore();
5626
5627 V8_INLINE static ArrayBuffer* Cast(Value* obj);
5628
5629 static const int kInternalFieldCount = V8_ARRAY_BUFFER_INTERNAL_FIELD_COUNT;
5630 static const int kEmbedderFieldCount = V8_ARRAY_BUFFER_INTERNAL_FIELD_COUNT;
5631
5632 private:
5633 ArrayBuffer();
5634 static void CheckCast(Value* obj);
5635 Contents GetContents(bool externalize);
5636 };
5637
5638
5639 #ifndef V8_ARRAY_BUFFER_VIEW_INTERNAL_FIELD_COUNT
5640 // The number of required internal fields can be defined by embedder.
5641 #define V8_ARRAY_BUFFER_VIEW_INTERNAL_FIELD_COUNT 2
5642 #endif
5643
5644
5645 /**
5646 * A base class for an instance of one of "views" over ArrayBuffer,
5647 * including TypedArrays and DataView (ES6 draft 15.13).
5648 */
5649 class V8_EXPORT ArrayBufferView : public Object {
5650 public:
5651 /**
5652 * Returns underlying ArrayBuffer.
5653 */
5654 Local<ArrayBuffer> Buffer();
5655 /**
5656 * Byte offset in |Buffer|.
5657 */
5658 size_t ByteOffset();
5659 /**
5660 * Size of a view in bytes.
5661 */
5662 size_t ByteLength();
5663
5664 /**
5665 * Copy the contents of the ArrayBufferView's buffer to an embedder defined
5666 * memory without additional overhead that calling ArrayBufferView::Buffer
5667 * might incur.
5668 *
5669 * Will write at most min(|byte_length|, ByteLength) bytes starting at
5670 * ByteOffset of the underlying buffer to the memory starting at |dest|.
5671 * Returns the number of bytes actually written.
5672 */
5673 size_t CopyContents(void* dest, size_t byte_length);
5674
5675 /**
5676 * Returns true if ArrayBufferView's backing ArrayBuffer has already been
5677 * allocated.
5678 */
5679 bool HasBuffer() const;
5680
5681 V8_INLINE static ArrayBufferView* Cast(Value* obj);
5682
5683 static const int kInternalFieldCount =
5684 V8_ARRAY_BUFFER_VIEW_INTERNAL_FIELD_COUNT;
5685 static const int kEmbedderFieldCount =
5686 V8_ARRAY_BUFFER_VIEW_INTERNAL_FIELD_COUNT;
5687
5688 private:
5689 ArrayBufferView();
5690 static void CheckCast(Value* obj);
5691 };
5692
5693
5694 /**
5695 * A base class for an instance of TypedArray series of constructors
5696 * (ES6 draft 15.13.6).
5697 */
5698 class V8_EXPORT TypedArray : public ArrayBufferView {
5699 public:
5700 /*
5701 * The largest typed array size that can be constructed using New.
5702 */
5703 static constexpr size_t kMaxLength =
5704 internal::kApiSystemPointerSize == 4
5705 ? internal::kSmiMaxValue
5706 : static_cast<size_t>(uint64_t{1} << 32);
5707
5708 /**
5709 * Number of elements in this typed array
5710 * (e.g. for Int16Array, |ByteLength|/2).
5711 */
5712 size_t Length();
5713
5714 V8_INLINE static TypedArray* Cast(Value* obj);
5715
5716 private:
5717 TypedArray();
5718 static void CheckCast(Value* obj);
5719 };
5720
5721
5722 /**
5723 * An instance of Uint8Array constructor (ES6 draft 15.13.6).
5724 */
5725 class V8_EXPORT Uint8Array : public TypedArray {
5726 public:
5727 static Local<Uint8Array> New(Local<ArrayBuffer> array_buffer,
5728 size_t byte_offset, size_t length);
5729 static Local<Uint8Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5730 size_t byte_offset, size_t length);
5731 V8_INLINE static Uint8Array* Cast(Value* obj);
5732
5733 private:
5734 Uint8Array();
5735 static void CheckCast(Value* obj);
5736 };
5737
5738
5739 /**
5740 * An instance of Uint8ClampedArray constructor (ES6 draft 15.13.6).
5741 */
5742 class V8_EXPORT Uint8ClampedArray : public TypedArray {
5743 public:
5744 static Local<Uint8ClampedArray> New(Local<ArrayBuffer> array_buffer,
5745 size_t byte_offset, size_t length);
5746 static Local<Uint8ClampedArray> New(
5747 Local<SharedArrayBuffer> shared_array_buffer, size_t byte_offset,
5748 size_t length);
5749 V8_INLINE static Uint8ClampedArray* Cast(Value* obj);
5750
5751 private:
5752 Uint8ClampedArray();
5753 static void CheckCast(Value* obj);
5754 };
5755
5756 /**
5757 * An instance of Int8Array constructor (ES6 draft 15.13.6).
5758 */
5759 class V8_EXPORT Int8Array : public TypedArray {
5760 public:
5761 static Local<Int8Array> New(Local<ArrayBuffer> array_buffer,
5762 size_t byte_offset, size_t length);
5763 static Local<Int8Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5764 size_t byte_offset, size_t length);
5765 V8_INLINE static Int8Array* Cast(Value* obj);
5766
5767 private:
5768 Int8Array();
5769 static void CheckCast(Value* obj);
5770 };
5771
5772
5773 /**
5774 * An instance of Uint16Array constructor (ES6 draft 15.13.6).
5775 */
5776 class V8_EXPORT Uint16Array : public TypedArray {
5777 public:
5778 static Local<Uint16Array> New(Local<ArrayBuffer> array_buffer,
5779 size_t byte_offset, size_t length);
5780 static Local<Uint16Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5781 size_t byte_offset, size_t length);
5782 V8_INLINE static Uint16Array* Cast(Value* obj);
5783
5784 private:
5785 Uint16Array();
5786 static void CheckCast(Value* obj);
5787 };
5788
5789
5790 /**
5791 * An instance of Int16Array constructor (ES6 draft 15.13.6).
5792 */
5793 class V8_EXPORT Int16Array : public TypedArray {
5794 public:
5795 static Local<Int16Array> New(Local<ArrayBuffer> array_buffer,
5796 size_t byte_offset, size_t length);
5797 static Local<Int16Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5798 size_t byte_offset, size_t length);
5799 V8_INLINE static Int16Array* Cast(Value* obj);
5800
5801 private:
5802 Int16Array();
5803 static void CheckCast(Value* obj);
5804 };
5805
5806
5807 /**
5808 * An instance of Uint32Array constructor (ES6 draft 15.13.6).
5809 */
5810 class V8_EXPORT Uint32Array : public TypedArray {
5811 public:
5812 static Local<Uint32Array> New(Local<ArrayBuffer> array_buffer,
5813 size_t byte_offset, size_t length);
5814 static Local<Uint32Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5815 size_t byte_offset, size_t length);
5816 V8_INLINE static Uint32Array* Cast(Value* obj);
5817
5818 private:
5819 Uint32Array();
5820 static void CheckCast(Value* obj);
5821 };
5822
5823
5824 /**
5825 * An instance of Int32Array constructor (ES6 draft 15.13.6).
5826 */
5827 class V8_EXPORT Int32Array : public TypedArray {
5828 public:
5829 static Local<Int32Array> New(Local<ArrayBuffer> array_buffer,
5830 size_t byte_offset, size_t length);
5831 static Local<Int32Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5832 size_t byte_offset, size_t length);
5833 V8_INLINE static Int32Array* Cast(Value* obj);
5834
5835 private:
5836 Int32Array();
5837 static void CheckCast(Value* obj);
5838 };
5839
5840
5841 /**
5842 * An instance of Float32Array constructor (ES6 draft 15.13.6).
5843 */
5844 class V8_EXPORT Float32Array : public TypedArray {
5845 public:
5846 static Local<Float32Array> New(Local<ArrayBuffer> array_buffer,
5847 size_t byte_offset, size_t length);
5848 static Local<Float32Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5849 size_t byte_offset, size_t length);
5850 V8_INLINE static Float32Array* Cast(Value* obj);
5851
5852 private:
5853 Float32Array();
5854 static void CheckCast(Value* obj);
5855 };
5856
5857
5858 /**
5859 * An instance of Float64Array constructor (ES6 draft 15.13.6).
5860 */
5861 class V8_EXPORT Float64Array : public TypedArray {
5862 public:
5863 static Local<Float64Array> New(Local<ArrayBuffer> array_buffer,
5864 size_t byte_offset, size_t length);
5865 static Local<Float64Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5866 size_t byte_offset, size_t length);
5867 V8_INLINE static Float64Array* Cast(Value* obj);
5868
5869 private:
5870 Float64Array();
5871 static void CheckCast(Value* obj);
5872 };
5873
5874 /**
5875 * An instance of BigInt64Array constructor.
5876 */
5877 class V8_EXPORT BigInt64Array : public TypedArray {
5878 public:
5879 static Local<BigInt64Array> New(Local<ArrayBuffer> array_buffer,
5880 size_t byte_offset, size_t length);
5881 static Local<BigInt64Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5882 size_t byte_offset, size_t length);
5883 V8_INLINE static BigInt64Array* Cast(Value* obj);
5884
5885 private:
5886 BigInt64Array();
5887 static void CheckCast(Value* obj);
5888 };
5889
5890 /**
5891 * An instance of BigUint64Array constructor.
5892 */
5893 class V8_EXPORT BigUint64Array : public TypedArray {
5894 public:
5895 static Local<BigUint64Array> New(Local<ArrayBuffer> array_buffer,
5896 size_t byte_offset, size_t length);
5897 static Local<BigUint64Array> New(Local<SharedArrayBuffer> shared_array_buffer,
5898 size_t byte_offset, size_t length);
5899 V8_INLINE static BigUint64Array* Cast(Value* obj);
5900
5901 private:
5902 BigUint64Array();
5903 static void CheckCast(Value* obj);
5904 };
5905
5906 /**
5907 * An instance of DataView constructor (ES6 draft 15.13.7).
5908 */
5909 class V8_EXPORT DataView : public ArrayBufferView {
5910 public:
5911 static Local<DataView> New(Local<ArrayBuffer> array_buffer,
5912 size_t byte_offset, size_t length);
5913 static Local<DataView> New(Local<SharedArrayBuffer> shared_array_buffer,
5914 size_t byte_offset, size_t length);
5915 V8_INLINE static DataView* Cast(Value* obj);
5916
5917 private:
5918 DataView();
5919 static void CheckCast(Value* obj);
5920 };
5921
5922
5923 /**
5924 * An instance of the built-in SharedArrayBuffer constructor.
5925 */
5926 class V8_EXPORT SharedArrayBuffer : public Object {
5927 public:
5928 /**
5929 * The contents of an |SharedArrayBuffer|. Externalization of
5930 * |SharedArrayBuffer| returns an instance of this class, populated, with a
5931 * pointer to data and byte length.
5932 *
5933 * The Data pointer of ArrayBuffer::Contents must be freed using the provided
5934 * deleter, which will call ArrayBuffer::Allocator::Free if the buffer
5935 * was allocated with ArraryBuffer::Allocator::Allocate.
5936 */
5937 class V8_EXPORT Contents { // NOLINT
5938 public:
5939 using Allocator = v8::ArrayBuffer::Allocator;
5940 using DeleterCallback = void (*)(void* buffer, size_t length, void* info);
5941
Contents()5942 Contents()
5943 : data_(nullptr),
5944 byte_length_(0),
5945 allocation_base_(nullptr),
5946 allocation_length_(0),
5947 allocation_mode_(Allocator::AllocationMode::kNormal),
5948 deleter_(nullptr),
5949 deleter_data_(nullptr) {}
5950
AllocationBase()5951 void* AllocationBase() const { return allocation_base_; }
AllocationLength()5952 size_t AllocationLength() const { return allocation_length_; }
AllocationMode()5953 Allocator::AllocationMode AllocationMode() const {
5954 return allocation_mode_;
5955 }
5956
Data()5957 void* Data() const { return data_; }
ByteLength()5958 size_t ByteLength() const { return byte_length_; }
Deleter()5959 DeleterCallback Deleter() const { return deleter_; }
DeleterData()5960 void* DeleterData() const { return deleter_data_; }
5961
5962 private:
5963 Contents(void* data, size_t byte_length, void* allocation_base,
5964 size_t allocation_length,
5965 Allocator::AllocationMode allocation_mode, DeleterCallback deleter,
5966 void* deleter_data);
5967
5968 void* data_;
5969 size_t byte_length_;
5970 void* allocation_base_;
5971 size_t allocation_length_;
5972 Allocator::AllocationMode allocation_mode_;
5973 DeleterCallback deleter_;
5974 void* deleter_data_;
5975
5976 friend class SharedArrayBuffer;
5977 };
5978
5979 /**
5980 * Data length in bytes.
5981 */
5982 size_t ByteLength() const;
5983
5984 /**
5985 * Create a new SharedArrayBuffer. Allocate |byte_length| bytes.
5986 * Allocated memory will be owned by a created SharedArrayBuffer and
5987 * will be deallocated when it is garbage-collected,
5988 * unless the object is externalized.
5989 */
5990 static Local<SharedArrayBuffer> New(Isolate* isolate, size_t byte_length);
5991
5992 /**
5993 * Create a new SharedArrayBuffer over an existing memory block. The created
5994 * array buffer is immediately in externalized state unless otherwise
5995 * specified. The memory block will not be reclaimed when a created
5996 * SharedArrayBuffer is garbage-collected.
5997 */
5998 V8_DEPRECATED(
5999 "Use the version that takes a BackingStore. "
6000 "See http://crbug.com/v8/9908.")
6001 static Local<SharedArrayBuffer> New(
6002 Isolate* isolate, void* data, size_t byte_length,
6003 ArrayBufferCreationMode mode = ArrayBufferCreationMode::kExternalized);
6004
6005 /**
6006 * Create a new SharedArrayBuffer with an existing backing store.
6007 * The created array keeps a reference to the backing store until the array
6008 * is garbage collected. Note that the IsExternal bit does not affect this
6009 * reference from the array to the backing store.
6010 *
6011 * In future IsExternal bit will be removed. Until then the bit is set as
6012 * follows. If the backing store does not own the underlying buffer, then
6013 * the array is created in externalized state. Otherwise, the array is created
6014 * in internalized state. In the latter case the array can be transitioned
6015 * to the externalized state using Externalize(backing_store).
6016 */
6017 static Local<SharedArrayBuffer> New(
6018 Isolate* isolate, std::shared_ptr<BackingStore> backing_store);
6019
6020 /**
6021 * Returns a new standalone BackingStore that is allocated using the array
6022 * buffer allocator of the isolate. The result can be later passed to
6023 * SharedArrayBuffer::New.
6024 *
6025 * If the allocator returns nullptr, then the function may cause GCs in the
6026 * given isolate and re-try the allocation. If GCs do not help, then the
6027 * function will crash with an out-of-memory error.
6028 */
6029 static std::unique_ptr<BackingStore> NewBackingStore(Isolate* isolate,
6030 size_t byte_length);
6031 /**
6032 * Returns a new standalone BackingStore that takes over the ownership of
6033 * the given buffer. The destructor of the BackingStore invokes the given
6034 * deleter callback.
6035 *
6036 * The result can be later passed to SharedArrayBuffer::New. The raw pointer
6037 * to the buffer must not be passed again to any V8 functions.
6038 */
6039 static std::unique_ptr<BackingStore> NewBackingStore(
6040 void* data, size_t byte_length, v8::BackingStore::DeleterCallback deleter,
6041 void* deleter_data);
6042
6043 /**
6044 * Create a new SharedArrayBuffer over an existing memory block. Propagate
6045 * flags to indicate whether the underlying buffer can be grown.
6046 */
6047 V8_DEPRECATED(
6048 "Use the version that takes a BackingStore. "
6049 "See http://crbug.com/v8/9908.")
6050 static Local<SharedArrayBuffer> New(
6051 Isolate* isolate, const SharedArrayBuffer::Contents&,
6052 ArrayBufferCreationMode mode = ArrayBufferCreationMode::kExternalized);
6053
6054 /**
6055 * Returns true if SharedArrayBuffer is externalized, that is, does not
6056 * own its memory block.
6057 */
6058 V8_DEPRECATED(
6059 "With v8::BackingStore externalized SharedArrayBuffers are the same "
6060 "as ordinary SharedArrayBuffers. See http://crbug.com/v8/9908.")
6061 bool IsExternal() const;
6062
6063 /**
6064 * Make this SharedArrayBuffer external. The pointer to underlying memory
6065 * block and byte length are returned as |Contents| structure. After
6066 * SharedArrayBuffer had been externalized, it does no longer own the memory
6067 * block. The caller should take steps to free memory when it is no longer
6068 * needed.
6069 *
6070 * The memory block is guaranteed to be allocated with |Allocator::Allocate|
6071 * by the allocator specified in
6072 * v8::Isolate::CreateParams::array_buffer_allocator.
6073 *
6074 */
6075 V8_DEPRECATED("Use GetBackingStore or Detach. See http://crbug.com/v8/9908.")
6076 Contents Externalize();
6077
6078 /**
6079 * Marks this SharedArrayBuffer external given a witness that the embedder
6080 * has fetched the backing store using the new GetBackingStore() function.
6081 *
6082 * With the new lifetime management of backing stores there is no need for
6083 * externalizing, so this function exists only to make the transition easier.
6084 */
6085 V8_DEPRECATED("This will be removed together with IsExternal.")
6086 void Externalize(const std::shared_ptr<BackingStore>& backing_store);
6087
6088 /**
6089 * Get a pointer to the ArrayBuffer's underlying memory block without
6090 * externalizing it. If the ArrayBuffer is not externalized, this pointer
6091 * will become invalid as soon as the ArrayBuffer became garbage collected.
6092 *
6093 * The embedder should make sure to hold a strong reference to the
6094 * ArrayBuffer while accessing this pointer.
6095 *
6096 * The memory block is guaranteed to be allocated with |Allocator::Allocate|
6097 * by the allocator specified in
6098 * v8::Isolate::CreateParams::array_buffer_allocator.
6099 */
6100 V8_DEPRECATED("Use GetBackingStore. See http://crbug.com/v8/9908.")
6101 Contents GetContents();
6102
6103 /**
6104 * Get a shared pointer to the backing store of this array buffer. This
6105 * pointer coordinates the lifetime management of the internal storage
6106 * with any live ArrayBuffers on the heap, even across isolates. The embedder
6107 * should not attempt to manage lifetime of the storage through other means.
6108 *
6109 * This function replaces both Externalize() and GetContents().
6110 */
6111 std::shared_ptr<BackingStore> GetBackingStore();
6112
6113 V8_INLINE static SharedArrayBuffer* Cast(Value* obj);
6114
6115 static const int kInternalFieldCount = V8_ARRAY_BUFFER_INTERNAL_FIELD_COUNT;
6116
6117 private:
6118 SharedArrayBuffer();
6119 static void CheckCast(Value* obj);
6120 Contents GetContents(bool externalize);
6121 };
6122
6123
6124 /**
6125 * An instance of the built-in Date constructor (ECMA-262, 15.9).
6126 */
6127 class V8_EXPORT Date : public Object {
6128 public:
6129 static V8_WARN_UNUSED_RESULT MaybeLocal<Value> New(Local<Context> context,
6130 double time);
6131
6132 /**
6133 * A specialization of Value::NumberValue that is more efficient
6134 * because we know the structure of this object.
6135 */
6136 double ValueOf() const;
6137
6138 V8_INLINE static Date* Cast(Value* obj);
6139
6140 private:
6141 static void CheckCast(Value* obj);
6142 };
6143
6144
6145 /**
6146 * A Number object (ECMA-262, 4.3.21).
6147 */
6148 class V8_EXPORT NumberObject : public Object {
6149 public:
6150 static Local<Value> New(Isolate* isolate, double value);
6151
6152 double ValueOf() const;
6153
6154 V8_INLINE static NumberObject* Cast(Value* obj);
6155
6156 private:
6157 static void CheckCast(Value* obj);
6158 };
6159
6160 /**
6161 * A BigInt object (https://tc39.github.io/proposal-bigint)
6162 */
6163 class V8_EXPORT BigIntObject : public Object {
6164 public:
6165 static Local<Value> New(Isolate* isolate, int64_t value);
6166
6167 Local<BigInt> ValueOf() const;
6168
6169 V8_INLINE static BigIntObject* Cast(Value* obj);
6170
6171 private:
6172 static void CheckCast(Value* obj);
6173 };
6174
6175 /**
6176 * A Boolean object (ECMA-262, 4.3.15).
6177 */
6178 class V8_EXPORT BooleanObject : public Object {
6179 public:
6180 static Local<Value> New(Isolate* isolate, bool value);
6181
6182 bool ValueOf() const;
6183
6184 V8_INLINE static BooleanObject* Cast(Value* obj);
6185
6186 private:
6187 static void CheckCast(Value* obj);
6188 };
6189
6190
6191 /**
6192 * A String object (ECMA-262, 4.3.18).
6193 */
6194 class V8_EXPORT StringObject : public Object {
6195 public:
6196 static Local<Value> New(Isolate* isolate, Local<String> value);
6197
6198 Local<String> ValueOf() const;
6199
6200 V8_INLINE static StringObject* Cast(Value* obj);
6201
6202 private:
6203 static void CheckCast(Value* obj);
6204 };
6205
6206
6207 /**
6208 * A Symbol object (ECMA-262 edition 6).
6209 */
6210 class V8_EXPORT SymbolObject : public Object {
6211 public:
6212 static Local<Value> New(Isolate* isolate, Local<Symbol> value);
6213
6214 Local<Symbol> ValueOf() const;
6215
6216 V8_INLINE static SymbolObject* Cast(Value* obj);
6217
6218 private:
6219 static void CheckCast(Value* obj);
6220 };
6221
6222
6223 /**
6224 * An instance of the built-in RegExp constructor (ECMA-262, 15.10).
6225 */
6226 class V8_EXPORT RegExp : public Object {
6227 public:
6228 /**
6229 * Regular expression flag bits. They can be or'ed to enable a set
6230 * of flags.
6231 * The kLinear value ('l') is experimental and can only be used with
6232 * --enable-experimental-regexp-engine. RegExps with kLinear flag are
6233 * guaranteed to be executed in asymptotic linear time wrt. the length of
6234 * the subject string.
6235 */
6236 enum Flags {
6237 kNone = 0,
6238 kGlobal = 1 << 0,
6239 kIgnoreCase = 1 << 1,
6240 kMultiline = 1 << 2,
6241 kSticky = 1 << 3,
6242 kUnicode = 1 << 4,
6243 kDotAll = 1 << 5,
6244 kLinear = 1 << 6,
6245 kHasIndices = 1 << 7,
6246 };
6247
6248 static constexpr int kFlagCount = 8;
6249
6250 /**
6251 * Creates a regular expression from the given pattern string and
6252 * the flags bit field. May throw a JavaScript exception as
6253 * described in ECMA-262, 15.10.4.1.
6254 *
6255 * For example,
6256 * RegExp::New(v8::String::New("foo"),
6257 * static_cast<RegExp::Flags>(kGlobal | kMultiline))
6258 * is equivalent to evaluating "/foo/gm".
6259 */
6260 static V8_WARN_UNUSED_RESULT MaybeLocal<RegExp> New(Local<Context> context,
6261 Local<String> pattern,
6262 Flags flags);
6263
6264 /**
6265 * Like New, but additionally specifies a backtrack limit. If the number of
6266 * backtracks done in one Exec call hits the limit, a match failure is
6267 * immediately returned.
6268 */
6269 static V8_WARN_UNUSED_RESULT MaybeLocal<RegExp> NewWithBacktrackLimit(
6270 Local<Context> context, Local<String> pattern, Flags flags,
6271 uint32_t backtrack_limit);
6272
6273 /**
6274 * Executes the current RegExp instance on the given subject string.
6275 * Equivalent to RegExp.prototype.exec as described in
6276 *
6277 * https://tc39.es/ecma262/#sec-regexp.prototype.exec
6278 *
6279 * On success, an Array containing the matched strings is returned. On
6280 * failure, returns Null.
6281 *
6282 * Note: modifies global context state, accessible e.g. through RegExp.input.
6283 */
6284 V8_WARN_UNUSED_RESULT MaybeLocal<Object> Exec(Local<Context> context,
6285 Local<String> subject);
6286
6287 /**
6288 * Returns the value of the source property: a string representing
6289 * the regular expression.
6290 */
6291 Local<String> GetSource() const;
6292
6293 /**
6294 * Returns the flags bit field.
6295 */
6296 Flags GetFlags() const;
6297
6298 V8_INLINE static RegExp* Cast(Value* obj);
6299
6300 private:
6301 static void CheckCast(Value* obj);
6302 };
6303
6304 /**
6305 * A JavaScript value that wraps a C++ void*. This type of value is mainly used
6306 * to associate C++ data structures with JavaScript objects.
6307 */
6308 class V8_EXPORT External : public Value {
6309 public:
6310 static Local<External> New(Isolate* isolate, void* value);
6311 V8_INLINE static External* Cast(Value* obj);
6312 void* Value() const;
6313 private:
6314 static void CheckCast(v8::Value* obj);
6315 };
6316
6317 #define V8_INTRINSICS_LIST(F) \
6318 F(ArrayProto_entries, array_entries_iterator) \
6319 F(ArrayProto_forEach, array_for_each_iterator) \
6320 F(ArrayProto_keys, array_keys_iterator) \
6321 F(ArrayProto_values, array_values_iterator) \
6322 F(AsyncIteratorPrototype, initial_async_iterator_prototype) \
6323 F(ErrorPrototype, initial_error_prototype) \
6324 F(IteratorPrototype, initial_iterator_prototype) \
6325 F(ObjProto_valueOf, object_value_of_function)
6326
6327 enum Intrinsic {
6328 #define V8_DECL_INTRINSIC(name, iname) k##name,
6329 V8_INTRINSICS_LIST(V8_DECL_INTRINSIC)
6330 #undef V8_DECL_INTRINSIC
6331 };
6332
6333
6334 // --- Templates ---
6335
6336
6337 /**
6338 * The superclass of object and function templates.
6339 */
6340 class V8_EXPORT Template : public Data {
6341 public:
6342 /**
6343 * Adds a property to each instance created by this template.
6344 *
6345 * The property must be defined either as a primitive value, or a template.
6346 */
6347 void Set(Local<Name> name, Local<Data> value,
6348 PropertyAttribute attributes = None);
6349 void SetPrivate(Local<Private> name, Local<Data> value,
6350 PropertyAttribute attributes = None);
6351 V8_INLINE void Set(Isolate* isolate, const char* name, Local<Data> value);
6352
6353 void SetAccessorProperty(
6354 Local<Name> name,
6355 Local<FunctionTemplate> getter = Local<FunctionTemplate>(),
6356 Local<FunctionTemplate> setter = Local<FunctionTemplate>(),
6357 PropertyAttribute attribute = None,
6358 AccessControl settings = DEFAULT);
6359
6360 /**
6361 * Whenever the property with the given name is accessed on objects
6362 * created from this Template the getter and setter callbacks
6363 * are called instead of getting and setting the property directly
6364 * on the JavaScript object.
6365 *
6366 * \param name The name of the property for which an accessor is added.
6367 * \param getter The callback to invoke when getting the property.
6368 * \param setter The callback to invoke when setting the property.
6369 * \param data A piece of data that will be passed to the getter and setter
6370 * callbacks whenever they are invoked.
6371 * \param settings Access control settings for the accessor. This is a bit
6372 * field consisting of one of more of
6373 * DEFAULT = 0, ALL_CAN_READ = 1, or ALL_CAN_WRITE = 2.
6374 * The default is to not allow cross-context access.
6375 * ALL_CAN_READ means that all cross-context reads are allowed.
6376 * ALL_CAN_WRITE means that all cross-context writes are allowed.
6377 * The combination ALL_CAN_READ | ALL_CAN_WRITE can be used to allow all
6378 * cross-context access.
6379 * \param attribute The attributes of the property for which an accessor
6380 * is added.
6381 * \param signature The signature describes valid receivers for the accessor
6382 * and is used to perform implicit instance checks against them. If the
6383 * receiver is incompatible (i.e. is not an instance of the constructor as
6384 * defined by FunctionTemplate::HasInstance()), an implicit TypeError is
6385 * thrown and no callback is invoked.
6386 */
6387 void SetNativeDataProperty(
6388 Local<String> name, AccessorGetterCallback getter,
6389 AccessorSetterCallback setter = nullptr,
6390 Local<Value> data = Local<Value>(), PropertyAttribute attribute = None,
6391 Local<AccessorSignature> signature = Local<AccessorSignature>(),
6392 AccessControl settings = DEFAULT,
6393 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
6394 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
6395 void SetNativeDataProperty(
6396 Local<Name> name, AccessorNameGetterCallback getter,
6397 AccessorNameSetterCallback setter = nullptr,
6398 Local<Value> data = Local<Value>(), PropertyAttribute attribute = None,
6399 Local<AccessorSignature> signature = Local<AccessorSignature>(),
6400 AccessControl settings = DEFAULT,
6401 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
6402 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
6403
6404 /**
6405 * Like SetNativeDataProperty, but V8 will replace the native data property
6406 * with a real data property on first access.
6407 */
6408 void SetLazyDataProperty(
6409 Local<Name> name, AccessorNameGetterCallback getter,
6410 Local<Value> data = Local<Value>(), PropertyAttribute attribute = None,
6411 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
6412 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
6413
6414 /**
6415 * During template instantiation, sets the value with the intrinsic property
6416 * from the correct context.
6417 */
6418 void SetIntrinsicDataProperty(Local<Name> name, Intrinsic intrinsic,
6419 PropertyAttribute attribute = None);
6420
6421 private:
6422 Template();
6423
6424 friend class ObjectTemplate;
6425 friend class FunctionTemplate;
6426 };
6427
6428 // TODO(dcarney): Replace GenericNamedPropertyFooCallback with just
6429 // NamedPropertyFooCallback.
6430
6431 /**
6432 * Interceptor for get requests on an object.
6433 *
6434 * Use `info.GetReturnValue().Set()` to set the return value of the
6435 * intercepted get request.
6436 *
6437 * \param property The name of the property for which the request was
6438 * intercepted.
6439 * \param info Information about the intercepted request, such as
6440 * isolate, receiver, return value, or whether running in `'use strict`' mode.
6441 * See `PropertyCallbackInfo`.
6442 *
6443 * \code
6444 * void GetterCallback(
6445 * Local<Name> name,
6446 * const v8::PropertyCallbackInfo<v8::Value>& info) {
6447 * info.GetReturnValue().Set(v8_num(42));
6448 * }
6449 *
6450 * v8::Local<v8::FunctionTemplate> templ =
6451 * v8::FunctionTemplate::New(isolate);
6452 * templ->InstanceTemplate()->SetHandler(
6453 * v8::NamedPropertyHandlerConfiguration(GetterCallback));
6454 * LocalContext env;
6455 * env->Global()
6456 * ->Set(env.local(), v8_str("obj"), templ->GetFunction(env.local())
6457 * .ToLocalChecked()
6458 * ->NewInstance(env.local())
6459 * .ToLocalChecked())
6460 * .FromJust();
6461 * v8::Local<v8::Value> result = CompileRun("obj.a = 17; obj.a");
6462 * CHECK(v8_num(42)->Equals(env.local(), result).FromJust());
6463 * \endcode
6464 *
6465 * See also `ObjectTemplate::SetHandler`.
6466 */
6467 using GenericNamedPropertyGetterCallback =
6468 void (*)(Local<Name> property, const PropertyCallbackInfo<Value>& info);
6469
6470 /**
6471 * Interceptor for set requests on an object.
6472 *
6473 * Use `info.GetReturnValue()` to indicate whether the request was intercepted
6474 * or not. If the setter successfully intercepts the request, i.e., if the
6475 * request should not be further executed, call
6476 * `info.GetReturnValue().Set(value)`. If the setter
6477 * did not intercept the request, i.e., if the request should be handled as
6478 * if no interceptor is present, do not not call `Set()`.
6479 *
6480 * \param property The name of the property for which the request was
6481 * intercepted.
6482 * \param value The value which the property will have if the request
6483 * is not intercepted.
6484 * \param info Information about the intercepted request, such as
6485 * isolate, receiver, return value, or whether running in `'use strict'` mode.
6486 * See `PropertyCallbackInfo`.
6487 *
6488 * See also
6489 * `ObjectTemplate::SetHandler.`
6490 */
6491 using GenericNamedPropertySetterCallback =
6492 void (*)(Local<Name> property, Local<Value> value,
6493 const PropertyCallbackInfo<Value>& info);
6494
6495 /**
6496 * Intercepts all requests that query the attributes of the
6497 * property, e.g., getOwnPropertyDescriptor(), propertyIsEnumerable(), and
6498 * defineProperty().
6499 *
6500 * Use `info.GetReturnValue().Set(value)` to set the property attributes. The
6501 * value is an integer encoding a `v8::PropertyAttribute`.
6502 *
6503 * \param property The name of the property for which the request was
6504 * intercepted.
6505 * \param info Information about the intercepted request, such as
6506 * isolate, receiver, return value, or whether running in `'use strict'` mode.
6507 * See `PropertyCallbackInfo`.
6508 *
6509 * \note Some functions query the property attributes internally, even though
6510 * they do not return the attributes. For example, `hasOwnProperty()` can
6511 * trigger this interceptor depending on the state of the object.
6512 *
6513 * See also
6514 * `ObjectTemplate::SetHandler.`
6515 */
6516 using GenericNamedPropertyQueryCallback =
6517 void (*)(Local<Name> property, const PropertyCallbackInfo<Integer>& info);
6518
6519 /**
6520 * Interceptor for delete requests on an object.
6521 *
6522 * Use `info.GetReturnValue()` to indicate whether the request was intercepted
6523 * or not. If the deleter successfully intercepts the request, i.e., if the
6524 * request should not be further executed, call
6525 * `info.GetReturnValue().Set(value)` with a boolean `value`. The `value` is
6526 * used as the return value of `delete`.
6527 *
6528 * \param property The name of the property for which the request was
6529 * intercepted.
6530 * \param info Information about the intercepted request, such as
6531 * isolate, receiver, return value, or whether running in `'use strict'` mode.
6532 * See `PropertyCallbackInfo`.
6533 *
6534 * \note If you need to mimic the behavior of `delete`, i.e., throw in strict
6535 * mode instead of returning false, use `info.ShouldThrowOnError()` to determine
6536 * if you are in strict mode.
6537 *
6538 * See also `ObjectTemplate::SetHandler.`
6539 */
6540 using GenericNamedPropertyDeleterCallback =
6541 void (*)(Local<Name> property, const PropertyCallbackInfo<Boolean>& info);
6542
6543 /**
6544 * Returns an array containing the names of the properties the named
6545 * property getter intercepts.
6546 *
6547 * Note: The values in the array must be of type v8::Name.
6548 */
6549 using GenericNamedPropertyEnumeratorCallback =
6550 void (*)(const PropertyCallbackInfo<Array>& info);
6551
6552 /**
6553 * Interceptor for defineProperty requests on an object.
6554 *
6555 * Use `info.GetReturnValue()` to indicate whether the request was intercepted
6556 * or not. If the definer successfully intercepts the request, i.e., if the
6557 * request should not be further executed, call
6558 * `info.GetReturnValue().Set(value)`. If the definer
6559 * did not intercept the request, i.e., if the request should be handled as
6560 * if no interceptor is present, do not not call `Set()`.
6561 *
6562 * \param property The name of the property for which the request was
6563 * intercepted.
6564 * \param desc The property descriptor which is used to define the
6565 * property if the request is not intercepted.
6566 * \param info Information about the intercepted request, such as
6567 * isolate, receiver, return value, or whether running in `'use strict'` mode.
6568 * See `PropertyCallbackInfo`.
6569 *
6570 * See also `ObjectTemplate::SetHandler`.
6571 */
6572 using GenericNamedPropertyDefinerCallback =
6573 void (*)(Local<Name> property, const PropertyDescriptor& desc,
6574 const PropertyCallbackInfo<Value>& info);
6575
6576 /**
6577 * Interceptor for getOwnPropertyDescriptor requests on an object.
6578 *
6579 * Use `info.GetReturnValue().Set()` to set the return value of the
6580 * intercepted request. The return value must be an object that
6581 * can be converted to a PropertyDescriptor, e.g., a `v8::value` returned from
6582 * `v8::Object::getOwnPropertyDescriptor`.
6583 *
6584 * \param property The name of the property for which the request was
6585 * intercepted.
6586 * \info Information about the intercepted request, such as
6587 * isolate, receiver, return value, or whether running in `'use strict'` mode.
6588 * See `PropertyCallbackInfo`.
6589 *
6590 * \note If GetOwnPropertyDescriptor is intercepted, it will
6591 * always return true, i.e., indicate that the property was found.
6592 *
6593 * See also `ObjectTemplate::SetHandler`.
6594 */
6595 using GenericNamedPropertyDescriptorCallback =
6596 void (*)(Local<Name> property, const PropertyCallbackInfo<Value>& info);
6597
6598 /**
6599 * See `v8::GenericNamedPropertyGetterCallback`.
6600 */
6601 using IndexedPropertyGetterCallback =
6602 void (*)(uint32_t index, const PropertyCallbackInfo<Value>& info);
6603
6604 /**
6605 * See `v8::GenericNamedPropertySetterCallback`.
6606 */
6607 using IndexedPropertySetterCallback =
6608 void (*)(uint32_t index, Local<Value> value,
6609 const PropertyCallbackInfo<Value>& info);
6610
6611 /**
6612 * See `v8::GenericNamedPropertyQueryCallback`.
6613 */
6614 using IndexedPropertyQueryCallback =
6615 void (*)(uint32_t index, const PropertyCallbackInfo<Integer>& info);
6616
6617 /**
6618 * See `v8::GenericNamedPropertyDeleterCallback`.
6619 */
6620 using IndexedPropertyDeleterCallback =
6621 void (*)(uint32_t index, const PropertyCallbackInfo<Boolean>& info);
6622
6623 /**
6624 * Returns an array containing the indices of the properties the indexed
6625 * property getter intercepts.
6626 *
6627 * Note: The values in the array must be uint32_t.
6628 */
6629 using IndexedPropertyEnumeratorCallback =
6630 void (*)(const PropertyCallbackInfo<Array>& info);
6631
6632 /**
6633 * See `v8::GenericNamedPropertyDefinerCallback`.
6634 */
6635 using IndexedPropertyDefinerCallback =
6636 void (*)(uint32_t index, const PropertyDescriptor& desc,
6637 const PropertyCallbackInfo<Value>& info);
6638
6639 /**
6640 * See `v8::GenericNamedPropertyDescriptorCallback`.
6641 */
6642 using IndexedPropertyDescriptorCallback =
6643 void (*)(uint32_t index, const PropertyCallbackInfo<Value>& info);
6644
6645 /**
6646 * Access type specification.
6647 */
6648 enum AccessType {
6649 ACCESS_GET,
6650 ACCESS_SET,
6651 ACCESS_HAS,
6652 ACCESS_DELETE,
6653 ACCESS_KEYS
6654 };
6655
6656
6657 /**
6658 * Returns true if the given context should be allowed to access the given
6659 * object.
6660 */
6661 using AccessCheckCallback = bool (*)(Local<Context> accessing_context,
6662 Local<Object> accessed_object,
6663 Local<Value> data);
6664
6665 /**
6666 * A FunctionTemplate is used to create functions at runtime. There
6667 * can only be one function created from a FunctionTemplate in a
6668 * context. The lifetime of the created function is equal to the
6669 * lifetime of the context. So in case the embedder needs to create
6670 * temporary functions that can be collected using Scripts is
6671 * preferred.
6672 *
6673 * Any modification of a FunctionTemplate after first instantiation will trigger
6674 * a crash.
6675 *
6676 * A FunctionTemplate can have properties, these properties are added to the
6677 * function object when it is created.
6678 *
6679 * A FunctionTemplate has a corresponding instance template which is
6680 * used to create object instances when the function is used as a
6681 * constructor. Properties added to the instance template are added to
6682 * each object instance.
6683 *
6684 * A FunctionTemplate can have a prototype template. The prototype template
6685 * is used to create the prototype object of the function.
6686 *
6687 * The following example shows how to use a FunctionTemplate:
6688 *
6689 * \code
6690 * v8::Local<v8::FunctionTemplate> t = v8::FunctionTemplate::New(isolate);
6691 * t->Set(isolate, "func_property", v8::Number::New(isolate, 1));
6692 *
6693 * v8::Local<v8::Template> proto_t = t->PrototypeTemplate();
6694 * proto_t->Set(isolate,
6695 * "proto_method",
6696 * v8::FunctionTemplate::New(isolate, InvokeCallback));
6697 * proto_t->Set(isolate, "proto_const", v8::Number::New(isolate, 2));
6698 *
6699 * v8::Local<v8::ObjectTemplate> instance_t = t->InstanceTemplate();
6700 * instance_t->SetAccessor(
6701 String::NewFromUtf8Literal(isolate, "instance_accessor"),
6702 * InstanceAccessorCallback);
6703 * instance_t->SetHandler(
6704 * NamedPropertyHandlerConfiguration(PropertyHandlerCallback));
6705 * instance_t->Set(String::NewFromUtf8Literal(isolate, "instance_property"),
6706 * Number::New(isolate, 3));
6707 *
6708 * v8::Local<v8::Function> function = t->GetFunction();
6709 * v8::Local<v8::Object> instance = function->NewInstance();
6710 * \endcode
6711 *
6712 * Let's use "function" as the JS variable name of the function object
6713 * and "instance" for the instance object created above. The function
6714 * and the instance will have the following properties:
6715 *
6716 * \code
6717 * func_property in function == true;
6718 * function.func_property == 1;
6719 *
6720 * function.prototype.proto_method() invokes 'InvokeCallback'
6721 * function.prototype.proto_const == 2;
6722 *
6723 * instance instanceof function == true;
6724 * instance.instance_accessor calls 'InstanceAccessorCallback'
6725 * instance.instance_property == 3;
6726 * \endcode
6727 *
6728 * A FunctionTemplate can inherit from another one by calling the
6729 * FunctionTemplate::Inherit method. The following graph illustrates
6730 * the semantics of inheritance:
6731 *
6732 * \code
6733 * FunctionTemplate Parent -> Parent() . prototype -> { }
6734 * ^ ^
6735 * | Inherit(Parent) | .__proto__
6736 * | |
6737 * FunctionTemplate Child -> Child() . prototype -> { }
6738 * \endcode
6739 *
6740 * A FunctionTemplate 'Child' inherits from 'Parent', the prototype
6741 * object of the Child() function has __proto__ pointing to the
6742 * Parent() function's prototype object. An instance of the Child
6743 * function has all properties on Parent's instance templates.
6744 *
6745 * Let Parent be the FunctionTemplate initialized in the previous
6746 * section and create a Child FunctionTemplate by:
6747 *
6748 * \code
6749 * Local<FunctionTemplate> parent = t;
6750 * Local<FunctionTemplate> child = FunctionTemplate::New();
6751 * child->Inherit(parent);
6752 *
6753 * Local<Function> child_function = child->GetFunction();
6754 * Local<Object> child_instance = child_function->NewInstance();
6755 * \endcode
6756 *
6757 * The Child function and Child instance will have the following
6758 * properties:
6759 *
6760 * \code
6761 * child_func.prototype.__proto__ == function.prototype;
6762 * child_instance.instance_accessor calls 'InstanceAccessorCallback'
6763 * child_instance.instance_property == 3;
6764 * \endcode
6765 *
6766 * The additional 'c_function' parameter refers to a fast API call, which
6767 * must not trigger GC or JavaScript execution, or call into V8 in other
6768 * ways. For more information how to define them, see
6769 * include/v8-fast-api-calls.h. Please note that this feature is still
6770 * experimental.
6771 */
6772 class V8_EXPORT FunctionTemplate : public Template {
6773 public:
6774 /** Creates a function template.*/
6775 static Local<FunctionTemplate> New(
6776 Isolate* isolate, FunctionCallback callback = nullptr,
6777 Local<Value> data = Local<Value>(),
6778 Local<Signature> signature = Local<Signature>(), int length = 0,
6779 ConstructorBehavior behavior = ConstructorBehavior::kAllow,
6780 SideEffectType side_effect_type = SideEffectType::kHasSideEffect,
6781 const CFunction* c_function = nullptr);
6782
6783 /** Creates a function template for multiple overloaded fast API calls.*/
6784 static Local<FunctionTemplate> NewWithCFunctionOverloads(
6785 Isolate* isolate, FunctionCallback callback = nullptr,
6786 Local<Value> data = Local<Value>(),
6787 Local<Signature> signature = Local<Signature>(), int length = 0,
6788 ConstructorBehavior behavior = ConstructorBehavior::kAllow,
6789 SideEffectType side_effect_type = SideEffectType::kHasSideEffect,
6790 const MemorySpan<const CFunction>& c_function_overloads = {});
6791
6792 /**
6793 * Creates a function template backed/cached by a private property.
6794 */
6795 static Local<FunctionTemplate> NewWithCache(
6796 Isolate* isolate, FunctionCallback callback,
6797 Local<Private> cache_property, Local<Value> data = Local<Value>(),
6798 Local<Signature> signature = Local<Signature>(), int length = 0,
6799 SideEffectType side_effect_type = SideEffectType::kHasSideEffect);
6800
6801 /** Returns the unique function instance in the current execution context.*/
6802 V8_WARN_UNUSED_RESULT MaybeLocal<Function> GetFunction(
6803 Local<Context> context);
6804
6805 /**
6806 * Similar to Context::NewRemoteContext, this creates an instance that
6807 * isn't backed by an actual object.
6808 *
6809 * The InstanceTemplate of this FunctionTemplate must have access checks with
6810 * handlers installed.
6811 */
6812 V8_WARN_UNUSED_RESULT MaybeLocal<Object> NewRemoteInstance();
6813
6814 /**
6815 * Set the call-handler callback for a FunctionTemplate. This
6816 * callback is called whenever the function created from this
6817 * FunctionTemplate is called. The 'c_function' represents a fast
6818 * API call, see the comment above the class declaration.
6819 */
6820 void SetCallHandler(
6821 FunctionCallback callback, Local<Value> data = Local<Value>(),
6822 SideEffectType side_effect_type = SideEffectType::kHasSideEffect,
6823 const CFunction* c_function = nullptr);
6824
6825 /**
6826 * Set the call-handler callback for a FunctionTemplate. This
6827 * callback is called whenever the function created from this
6828 * FunctionTemplate is called. The 'c_function' represents a fast
6829 * API call, see the comment above the class declaration.
6830 */
6831 void SetCallHandlerV8_92(
6832 FunctionCallback callback, Local<Value> data = Local<Value>(),
6833 SideEffectType side_effect_type = SideEffectType::kHasSideEffect,
6834 const MemorySpan<const CFunction>& c_function_overloads = {});
6835
6836 /** Set the predefined length property for the FunctionTemplate. */
6837 void SetLength(int length);
6838
6839 /** Get the InstanceTemplate. */
6840 Local<ObjectTemplate> InstanceTemplate();
6841
6842 /**
6843 * Causes the function template to inherit from a parent function template.
6844 * This means the function's prototype.__proto__ is set to the parent
6845 * function's prototype.
6846 **/
6847 void Inherit(Local<FunctionTemplate> parent);
6848
6849 /**
6850 * A PrototypeTemplate is the template used to create the prototype object
6851 * of the function created by this template.
6852 */
6853 Local<ObjectTemplate> PrototypeTemplate();
6854
6855 /**
6856 * A PrototypeProviderTemplate is another function template whose prototype
6857 * property is used for this template. This is mutually exclusive with setting
6858 * a prototype template indirectly by calling PrototypeTemplate() or using
6859 * Inherit().
6860 **/
6861 void SetPrototypeProviderTemplate(Local<FunctionTemplate> prototype_provider);
6862
6863 /**
6864 * Set the class name of the FunctionTemplate. This is used for
6865 * printing objects created with the function created from the
6866 * FunctionTemplate as its constructor.
6867 */
6868 void SetClassName(Local<String> name);
6869
6870
6871 /**
6872 * When set to true, no access check will be performed on the receiver of a
6873 * function call. Currently defaults to true, but this is subject to change.
6874 */
6875 void SetAcceptAnyReceiver(bool value);
6876
6877 /**
6878 * Sets the ReadOnly flag in the attributes of the 'prototype' property
6879 * of functions created from this FunctionTemplate to true.
6880 */
6881 void ReadOnlyPrototype();
6882
6883 /**
6884 * Removes the prototype property from functions created from this
6885 * FunctionTemplate.
6886 */
6887 void RemovePrototype();
6888
6889 /**
6890 * Returns true if the given object is an instance of this function
6891 * template.
6892 */
6893 bool HasInstance(Local<Value> object);
6894
6895 /**
6896 * Returns true if the given value is an API object that was constructed by an
6897 * instance of this function template (without checking for inheriting
6898 * function templates).
6899 *
6900 * This is an experimental feature and may still change significantly.
6901 */
6902 bool IsLeafTemplateForApiObject(v8::Local<v8::Value> value) const;
6903
6904 V8_INLINE static FunctionTemplate* Cast(Data* data);
6905
6906 private:
6907 FunctionTemplate();
6908
6909 static void CheckCast(Data* that);
6910 friend class Context;
6911 friend class ObjectTemplate;
6912 };
6913
6914 /**
6915 * Configuration flags for v8::NamedPropertyHandlerConfiguration or
6916 * v8::IndexedPropertyHandlerConfiguration.
6917 */
6918 enum class PropertyHandlerFlags {
6919 /**
6920 * None.
6921 */
6922 kNone = 0,
6923
6924 /**
6925 * See ALL_CAN_READ above.
6926 */
6927 kAllCanRead = 1,
6928
6929 /** Will not call into interceptor for properties on the receiver or prototype
6930 * chain, i.e., only call into interceptor for properties that do not exist.
6931 * Currently only valid for named interceptors.
6932 */
6933 kNonMasking = 1 << 1,
6934
6935 /**
6936 * Will not call into interceptor for symbol lookup. Only meaningful for
6937 * named interceptors.
6938 */
6939 kOnlyInterceptStrings = 1 << 2,
6940
6941 /**
6942 * The getter, query, enumerator callbacks do not produce side effects.
6943 */
6944 kHasNoSideEffect = 1 << 3,
6945 };
6946
6947 struct NamedPropertyHandlerConfiguration {
6948 NamedPropertyHandlerConfiguration(
6949 GenericNamedPropertyGetterCallback getter,
6950 GenericNamedPropertySetterCallback setter,
6951 GenericNamedPropertyQueryCallback query,
6952 GenericNamedPropertyDeleterCallback deleter,
6953 GenericNamedPropertyEnumeratorCallback enumerator,
6954 GenericNamedPropertyDefinerCallback definer,
6955 GenericNamedPropertyDescriptorCallback descriptor,
6956 Local<Value> data = Local<Value>(),
6957 PropertyHandlerFlags flags = PropertyHandlerFlags::kNone)
getterNamedPropertyHandlerConfiguration6958 : getter(getter),
6959 setter(setter),
6960 query(query),
6961 deleter(deleter),
6962 enumerator(enumerator),
6963 definer(definer),
6964 descriptor(descriptor),
6965 data(data),
6966 flags(flags) {}
6967
6968 NamedPropertyHandlerConfiguration(
6969 /** Note: getter is required */
6970 GenericNamedPropertyGetterCallback getter = nullptr,
6971 GenericNamedPropertySetterCallback setter = nullptr,
6972 GenericNamedPropertyQueryCallback query = nullptr,
6973 GenericNamedPropertyDeleterCallback deleter = nullptr,
6974 GenericNamedPropertyEnumeratorCallback enumerator = nullptr,
6975 Local<Value> data = Local<Value>(),
6976 PropertyHandlerFlags flags = PropertyHandlerFlags::kNone)
getterNamedPropertyHandlerConfiguration6977 : getter(getter),
6978 setter(setter),
6979 query(query),
6980 deleter(deleter),
6981 enumerator(enumerator),
6982 definer(nullptr),
6983 descriptor(nullptr),
6984 data(data),
6985 flags(flags) {}
6986
6987 NamedPropertyHandlerConfiguration(
6988 GenericNamedPropertyGetterCallback getter,
6989 GenericNamedPropertySetterCallback setter,
6990 GenericNamedPropertyDescriptorCallback descriptor,
6991 GenericNamedPropertyDeleterCallback deleter,
6992 GenericNamedPropertyEnumeratorCallback enumerator,
6993 GenericNamedPropertyDefinerCallback definer,
6994 Local<Value> data = Local<Value>(),
6995 PropertyHandlerFlags flags = PropertyHandlerFlags::kNone)
getterNamedPropertyHandlerConfiguration6996 : getter(getter),
6997 setter(setter),
6998 query(nullptr),
6999 deleter(deleter),
7000 enumerator(enumerator),
7001 definer(definer),
7002 descriptor(descriptor),
7003 data(data),
7004 flags(flags) {}
7005
7006 GenericNamedPropertyGetterCallback getter;
7007 GenericNamedPropertySetterCallback setter;
7008 GenericNamedPropertyQueryCallback query;
7009 GenericNamedPropertyDeleterCallback deleter;
7010 GenericNamedPropertyEnumeratorCallback enumerator;
7011 GenericNamedPropertyDefinerCallback definer;
7012 GenericNamedPropertyDescriptorCallback descriptor;
7013 Local<Value> data;
7014 PropertyHandlerFlags flags;
7015 };
7016
7017
7018 struct IndexedPropertyHandlerConfiguration {
7019 IndexedPropertyHandlerConfiguration(
7020 IndexedPropertyGetterCallback getter,
7021 IndexedPropertySetterCallback setter, IndexedPropertyQueryCallback query,
7022 IndexedPropertyDeleterCallback deleter,
7023 IndexedPropertyEnumeratorCallback enumerator,
7024 IndexedPropertyDefinerCallback definer,
7025 IndexedPropertyDescriptorCallback descriptor,
7026 Local<Value> data = Local<Value>(),
7027 PropertyHandlerFlags flags = PropertyHandlerFlags::kNone)
getterIndexedPropertyHandlerConfiguration7028 : getter(getter),
7029 setter(setter),
7030 query(query),
7031 deleter(deleter),
7032 enumerator(enumerator),
7033 definer(definer),
7034 descriptor(descriptor),
7035 data(data),
7036 flags(flags) {}
7037
7038 IndexedPropertyHandlerConfiguration(
7039 /** Note: getter is required */
7040 IndexedPropertyGetterCallback getter = nullptr,
7041 IndexedPropertySetterCallback setter = nullptr,
7042 IndexedPropertyQueryCallback query = nullptr,
7043 IndexedPropertyDeleterCallback deleter = nullptr,
7044 IndexedPropertyEnumeratorCallback enumerator = nullptr,
7045 Local<Value> data = Local<Value>(),
7046 PropertyHandlerFlags flags = PropertyHandlerFlags::kNone)
getterIndexedPropertyHandlerConfiguration7047 : getter(getter),
7048 setter(setter),
7049 query(query),
7050 deleter(deleter),
7051 enumerator(enumerator),
7052 definer(nullptr),
7053 descriptor(nullptr),
7054 data(data),
7055 flags(flags) {}
7056
7057 IndexedPropertyHandlerConfiguration(
7058 IndexedPropertyGetterCallback getter,
7059 IndexedPropertySetterCallback setter,
7060 IndexedPropertyDescriptorCallback descriptor,
7061 IndexedPropertyDeleterCallback deleter,
7062 IndexedPropertyEnumeratorCallback enumerator,
7063 IndexedPropertyDefinerCallback definer,
7064 Local<Value> data = Local<Value>(),
7065 PropertyHandlerFlags flags = PropertyHandlerFlags::kNone)
getterIndexedPropertyHandlerConfiguration7066 : getter(getter),
7067 setter(setter),
7068 query(nullptr),
7069 deleter(deleter),
7070 enumerator(enumerator),
7071 definer(definer),
7072 descriptor(descriptor),
7073 data(data),
7074 flags(flags) {}
7075
7076 IndexedPropertyGetterCallback getter;
7077 IndexedPropertySetterCallback setter;
7078 IndexedPropertyQueryCallback query;
7079 IndexedPropertyDeleterCallback deleter;
7080 IndexedPropertyEnumeratorCallback enumerator;
7081 IndexedPropertyDefinerCallback definer;
7082 IndexedPropertyDescriptorCallback descriptor;
7083 Local<Value> data;
7084 PropertyHandlerFlags flags;
7085 };
7086
7087
7088 /**
7089 * An ObjectTemplate is used to create objects at runtime.
7090 *
7091 * Properties added to an ObjectTemplate are added to each object
7092 * created from the ObjectTemplate.
7093 */
7094 class V8_EXPORT ObjectTemplate : public Template {
7095 public:
7096 /** Creates an ObjectTemplate. */
7097 static Local<ObjectTemplate> New(
7098 Isolate* isolate,
7099 Local<FunctionTemplate> constructor = Local<FunctionTemplate>());
7100
7101 /** Creates a new instance of this template.*/
7102 V8_WARN_UNUSED_RESULT MaybeLocal<Object> NewInstance(Local<Context> context);
7103
7104 /**
7105 * Sets an accessor on the object template.
7106 *
7107 * Whenever the property with the given name is accessed on objects
7108 * created from this ObjectTemplate the getter and setter callbacks
7109 * are called instead of getting and setting the property directly
7110 * on the JavaScript object.
7111 *
7112 * \param name The name of the property for which an accessor is added.
7113 * \param getter The callback to invoke when getting the property.
7114 * \param setter The callback to invoke when setting the property.
7115 * \param data A piece of data that will be passed to the getter and setter
7116 * callbacks whenever they are invoked.
7117 * \param settings Access control settings for the accessor. This is a bit
7118 * field consisting of one of more of
7119 * DEFAULT = 0, ALL_CAN_READ = 1, or ALL_CAN_WRITE = 2.
7120 * The default is to not allow cross-context access.
7121 * ALL_CAN_READ means that all cross-context reads are allowed.
7122 * ALL_CAN_WRITE means that all cross-context writes are allowed.
7123 * The combination ALL_CAN_READ | ALL_CAN_WRITE can be used to allow all
7124 * cross-context access.
7125 * \param attribute The attributes of the property for which an accessor
7126 * is added.
7127 * \param signature The signature describes valid receivers for the accessor
7128 * and is used to perform implicit instance checks against them. If the
7129 * receiver is incompatible (i.e. is not an instance of the constructor as
7130 * defined by FunctionTemplate::HasInstance()), an implicit TypeError is
7131 * thrown and no callback is invoked.
7132 */
7133 void SetAccessor(
7134 Local<String> name, AccessorGetterCallback getter,
7135 AccessorSetterCallback setter = nullptr,
7136 Local<Value> data = Local<Value>(), AccessControl settings = DEFAULT,
7137 PropertyAttribute attribute = None,
7138 Local<AccessorSignature> signature = Local<AccessorSignature>(),
7139 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
7140 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
7141 void SetAccessor(
7142 Local<Name> name, AccessorNameGetterCallback getter,
7143 AccessorNameSetterCallback setter = nullptr,
7144 Local<Value> data = Local<Value>(), AccessControl settings = DEFAULT,
7145 PropertyAttribute attribute = None,
7146 Local<AccessorSignature> signature = Local<AccessorSignature>(),
7147 SideEffectType getter_side_effect_type = SideEffectType::kHasSideEffect,
7148 SideEffectType setter_side_effect_type = SideEffectType::kHasSideEffect);
7149
7150 /**
7151 * Sets a named property handler on the object template.
7152 *
7153 * Whenever a property whose name is a string or a symbol is accessed on
7154 * objects created from this object template, the provided callback is
7155 * invoked instead of accessing the property directly on the JavaScript
7156 * object.
7157 *
7158 * @param configuration The NamedPropertyHandlerConfiguration that defines the
7159 * callbacks to invoke when accessing a property.
7160 */
7161 void SetHandler(const NamedPropertyHandlerConfiguration& configuration);
7162
7163 /**
7164 * Sets an indexed property handler on the object template.
7165 *
7166 * Whenever an indexed property is accessed on objects created from
7167 * this object template, the provided callback is invoked instead of
7168 * accessing the property directly on the JavaScript object.
7169 *
7170 * \param getter The callback to invoke when getting a property.
7171 * \param setter The callback to invoke when setting a property.
7172 * \param query The callback to invoke to check if an object has a property.
7173 * \param deleter The callback to invoke when deleting a property.
7174 * \param enumerator The callback to invoke to enumerate all the indexed
7175 * properties of an object.
7176 * \param data A piece of data that will be passed to the callbacks
7177 * whenever they are invoked.
7178 */
7179 // TODO(dcarney): deprecate
7180 void SetIndexedPropertyHandler(
7181 IndexedPropertyGetterCallback getter,
7182 IndexedPropertySetterCallback setter = nullptr,
7183 IndexedPropertyQueryCallback query = nullptr,
7184 IndexedPropertyDeleterCallback deleter = nullptr,
7185 IndexedPropertyEnumeratorCallback enumerator = nullptr,
7186 Local<Value> data = Local<Value>()) {
7187 SetHandler(IndexedPropertyHandlerConfiguration(getter, setter, query,
7188 deleter, enumerator, data));
7189 }
7190
7191 /**
7192 * Sets an indexed property handler on the object template.
7193 *
7194 * Whenever an indexed property is accessed on objects created from
7195 * this object template, the provided callback is invoked instead of
7196 * accessing the property directly on the JavaScript object.
7197 *
7198 * @param configuration The IndexedPropertyHandlerConfiguration that defines
7199 * the callbacks to invoke when accessing a property.
7200 */
7201 void SetHandler(const IndexedPropertyHandlerConfiguration& configuration);
7202
7203 /**
7204 * Sets the callback to be used when calling instances created from
7205 * this template as a function. If no callback is set, instances
7206 * behave like normal JavaScript objects that cannot be called as a
7207 * function.
7208 */
7209 void SetCallAsFunctionHandler(FunctionCallback callback,
7210 Local<Value> data = Local<Value>());
7211
7212 /**
7213 * Mark object instances of the template as undetectable.
7214 *
7215 * In many ways, undetectable objects behave as though they are not
7216 * there. They behave like 'undefined' in conditionals and when
7217 * printed. However, properties can be accessed and called as on
7218 * normal objects.
7219 */
7220 void MarkAsUndetectable();
7221
7222 /**
7223 * Sets access check callback on the object template and enables access
7224 * checks.
7225 *
7226 * When accessing properties on instances of this object template,
7227 * the access check callback will be called to determine whether or
7228 * not to allow cross-context access to the properties.
7229 */
7230 void SetAccessCheckCallback(AccessCheckCallback callback,
7231 Local<Value> data = Local<Value>());
7232
7233 /**
7234 * Like SetAccessCheckCallback but invokes an interceptor on failed access
7235 * checks instead of looking up all-can-read properties. You can only use
7236 * either this method or SetAccessCheckCallback, but not both at the same
7237 * time.
7238 */
7239 void SetAccessCheckCallbackAndHandler(
7240 AccessCheckCallback callback,
7241 const NamedPropertyHandlerConfiguration& named_handler,
7242 const IndexedPropertyHandlerConfiguration& indexed_handler,
7243 Local<Value> data = Local<Value>());
7244
7245 /**
7246 * Gets the number of internal fields for objects generated from
7247 * this template.
7248 */
7249 int InternalFieldCount();
7250
7251 /**
7252 * Sets the number of internal fields for objects generated from
7253 * this template.
7254 */
7255 void SetInternalFieldCount(int value);
7256
7257 /**
7258 * Returns true if the object will be an immutable prototype exotic object.
7259 */
7260 bool IsImmutableProto();
7261
7262 /**
7263 * Makes the ObjectTemplate for an immutable prototype exotic object, with an
7264 * immutable __proto__.
7265 */
7266 void SetImmutableProto();
7267
7268 /**
7269 * Support for TC39 "dynamic code brand checks" proposal.
7270 *
7271 * This API allows to mark (& query) objects as "code like", which causes
7272 * them to be treated like Strings in the context of eval and function
7273 * constructor.
7274 *
7275 * Reference: https://github.com/tc39/proposal-dynamic-code-brand-checks
7276 */
7277 void SetCodeLike();
7278 bool IsCodeLike();
7279
7280 V8_INLINE static ObjectTemplate* Cast(Data* data);
7281
7282 private:
7283 ObjectTemplate();
7284 static Local<ObjectTemplate> New(internal::Isolate* isolate,
7285 Local<FunctionTemplate> constructor);
7286 static void CheckCast(Data* that);
7287 friend class FunctionTemplate;
7288 };
7289
7290 /**
7291 * A Signature specifies which receiver is valid for a function.
7292 *
7293 * A receiver matches a given signature if the receiver (or any of its
7294 * hidden prototypes) was created from the signature's FunctionTemplate, or
7295 * from a FunctionTemplate that inherits directly or indirectly from the
7296 * signature's FunctionTemplate.
7297 */
7298 class V8_EXPORT Signature : public Data {
7299 public:
7300 static Local<Signature> New(
7301 Isolate* isolate,
7302 Local<FunctionTemplate> receiver = Local<FunctionTemplate>());
7303
7304 V8_INLINE static Signature* Cast(Data* data);
7305
7306 private:
7307 Signature();
7308
7309 static void CheckCast(Data* that);
7310 };
7311
7312
7313 /**
7314 * An AccessorSignature specifies which receivers are valid parameters
7315 * to an accessor callback.
7316 */
7317 class V8_EXPORT AccessorSignature : public Data {
7318 public:
7319 static Local<AccessorSignature> New(
7320 Isolate* isolate,
7321 Local<FunctionTemplate> receiver = Local<FunctionTemplate>());
7322
7323 V8_INLINE static AccessorSignature* Cast(Data* data);
7324
7325 private:
7326 AccessorSignature();
7327
7328 static void CheckCast(Data* that);
7329 };
7330
7331
7332 // --- Extensions ---
7333
7334 /**
7335 * Ignore
7336 */
7337 class V8_EXPORT Extension {
7338 public:
7339 // Note that the strings passed into this constructor must live as long
7340 // as the Extension itself.
7341 Extension(const char* name, const char* source = nullptr, int dep_count = 0,
7342 const char** deps = nullptr, int source_length = -1);
~Extension()7343 virtual ~Extension() { delete source_; }
GetNativeFunctionTemplate(Isolate * isolate,Local<String> name)7344 virtual Local<FunctionTemplate> GetNativeFunctionTemplate(
7345 Isolate* isolate, Local<String> name) {
7346 return Local<FunctionTemplate>();
7347 }
7348
name()7349 const char* name() const { return name_; }
source_length()7350 size_t source_length() const { return source_length_; }
source()7351 const String::ExternalOneByteStringResource* source() const {
7352 return source_;
7353 }
dependency_count()7354 int dependency_count() const { return dep_count_; }
dependencies()7355 const char** dependencies() const { return deps_; }
set_auto_enable(bool value)7356 void set_auto_enable(bool value) { auto_enable_ = value; }
auto_enable()7357 bool auto_enable() { return auto_enable_; }
7358
7359 // Disallow copying and assigning.
7360 Extension(const Extension&) = delete;
7361 void operator=(const Extension&) = delete;
7362
7363 private:
7364 const char* name_;
7365 size_t source_length_; // expected to initialize before source_
7366 String::ExternalOneByteStringResource* source_;
7367 int dep_count_;
7368 const char** deps_;
7369 bool auto_enable_;
7370 };
7371
7372 void V8_EXPORT RegisterExtension(std::unique_ptr<Extension>);
7373
7374 // --- Statics ---
7375
7376 V8_INLINE Local<Primitive> Undefined(Isolate* isolate);
7377 V8_INLINE Local<Primitive> Null(Isolate* isolate);
7378 V8_INLINE Local<Boolean> True(Isolate* isolate);
7379 V8_INLINE Local<Boolean> False(Isolate* isolate);
7380
7381 /**
7382 * A set of constraints that specifies the limits of the runtime's memory use.
7383 * You must set the heap size before initializing the VM - the size cannot be
7384 * adjusted after the VM is initialized.
7385 *
7386 * If you are using threads then you should hold the V8::Locker lock while
7387 * setting the stack limit and you must set a non-default stack limit separately
7388 * for each thread.
7389 *
7390 * The arguments for set_max_semi_space_size, set_max_old_space_size,
7391 * set_max_executable_size, set_code_range_size specify limits in MB.
7392 *
7393 * The argument for set_max_semi_space_size_in_kb is in KB.
7394 */
7395 class V8_EXPORT ResourceConstraints {
7396 public:
7397 /**
7398 * Configures the constraints with reasonable default values based on the
7399 * provided heap size limit. The heap size includes both the young and
7400 * the old generation.
7401 *
7402 * \param initial_heap_size_in_bytes The initial heap size or zero.
7403 * By default V8 starts with a small heap and dynamically grows it to
7404 * match the set of live objects. This may lead to ineffective
7405 * garbage collections at startup if the live set is large.
7406 * Setting the initial heap size avoids such garbage collections.
7407 * Note that this does not affect young generation garbage collections.
7408 *
7409 * \param maximum_heap_size_in_bytes The hard limit for the heap size.
7410 * When the heap size approaches this limit, V8 will perform series of
7411 * garbage collections and invoke the NearHeapLimitCallback. If the garbage
7412 * collections do not help and the callback does not increase the limit,
7413 * then V8 will crash with V8::FatalProcessOutOfMemory.
7414 */
7415 void ConfigureDefaultsFromHeapSize(size_t initial_heap_size_in_bytes,
7416 size_t maximum_heap_size_in_bytes);
7417
7418 /**
7419 * Configures the constraints with reasonable default values based on the
7420 * capabilities of the current device the VM is running on.
7421 *
7422 * \param physical_memory The total amount of physical memory on the current
7423 * device, in bytes.
7424 * \param virtual_memory_limit The amount of virtual memory on the current
7425 * device, in bytes, or zero, if there is no limit.
7426 */
7427 void ConfigureDefaults(uint64_t physical_memory,
7428 uint64_t virtual_memory_limit);
7429
7430 /**
7431 * The address beyond which the VM's stack may not grow.
7432 */
stack_limit()7433 uint32_t* stack_limit() const { return stack_limit_; }
set_stack_limit(uint32_t * value)7434 void set_stack_limit(uint32_t* value) { stack_limit_ = value; }
7435
7436 /**
7437 * The amount of virtual memory reserved for generated code. This is relevant
7438 * for 64-bit architectures that rely on code range for calls in code.
7439 *
7440 * When V8_COMPRESS_POINTERS_IN_SHARED_CAGE is defined, there is a shared
7441 * process-wide code range that is lazily initialized. This value is used to
7442 * configure that shared code range when the first Isolate is
7443 * created. Subsequent Isolates ignore this value.
7444 */
code_range_size_in_bytes()7445 size_t code_range_size_in_bytes() const { return code_range_size_; }
set_code_range_size_in_bytes(size_t limit)7446 void set_code_range_size_in_bytes(size_t limit) { code_range_size_ = limit; }
7447
7448 /**
7449 * The maximum size of the old generation.
7450 * When the old generation approaches this limit, V8 will perform series of
7451 * garbage collections and invoke the NearHeapLimitCallback.
7452 * If the garbage collections do not help and the callback does not
7453 * increase the limit, then V8 will crash with V8::FatalProcessOutOfMemory.
7454 */
max_old_generation_size_in_bytes()7455 size_t max_old_generation_size_in_bytes() const {
7456 return max_old_generation_size_;
7457 }
set_max_old_generation_size_in_bytes(size_t limit)7458 void set_max_old_generation_size_in_bytes(size_t limit) {
7459 max_old_generation_size_ = limit;
7460 }
7461
7462 /**
7463 * The maximum size of the young generation, which consists of two semi-spaces
7464 * and a large object space. This affects frequency of Scavenge garbage
7465 * collections and should be typically much smaller that the old generation.
7466 */
max_young_generation_size_in_bytes()7467 size_t max_young_generation_size_in_bytes() const {
7468 return max_young_generation_size_;
7469 }
set_max_young_generation_size_in_bytes(size_t limit)7470 void set_max_young_generation_size_in_bytes(size_t limit) {
7471 max_young_generation_size_ = limit;
7472 }
7473
initial_old_generation_size_in_bytes()7474 size_t initial_old_generation_size_in_bytes() const {
7475 return initial_old_generation_size_;
7476 }
set_initial_old_generation_size_in_bytes(size_t initial_size)7477 void set_initial_old_generation_size_in_bytes(size_t initial_size) {
7478 initial_old_generation_size_ = initial_size;
7479 }
7480
initial_young_generation_size_in_bytes()7481 size_t initial_young_generation_size_in_bytes() const {
7482 return initial_young_generation_size_;
7483 }
set_initial_young_generation_size_in_bytes(size_t initial_size)7484 void set_initial_young_generation_size_in_bytes(size_t initial_size) {
7485 initial_young_generation_size_ = initial_size;
7486 }
7487
7488 private:
7489 static constexpr size_t kMB = 1048576u;
7490 size_t code_range_size_ = 0;
7491 size_t max_old_generation_size_ = 0;
7492 size_t max_young_generation_size_ = 0;
7493 size_t initial_old_generation_size_ = 0;
7494 size_t initial_young_generation_size_ = 0;
7495 uint32_t* stack_limit_ = nullptr;
7496 };
7497
7498
7499 // --- Exceptions ---
7500
7501 using FatalErrorCallback = void (*)(const char* location, const char* message);
7502
7503 using OOMErrorCallback = void (*)(const char* location, bool is_heap_oom);
7504
7505 using DcheckErrorCallback = void (*)(const char* file, int line,
7506 const char* message);
7507
7508 using MessageCallback = void (*)(Local<Message> message, Local<Value> data);
7509
7510 // --- Tracing ---
7511
7512 enum LogEventStatus : int { kStart = 0, kEnd = 1, kStamp = 2 };
7513 using LogEventCallback = void (*)(const char* name,
7514 int /* LogEventStatus */ status);
7515
7516 /**
7517 * Create new error objects by calling the corresponding error object
7518 * constructor with the message.
7519 */
7520 class V8_EXPORT Exception {
7521 public:
7522 static Local<Value> RangeError(Local<String> message);
7523 static Local<Value> ReferenceError(Local<String> message);
7524 static Local<Value> SyntaxError(Local<String> message);
7525 static Local<Value> TypeError(Local<String> message);
7526 static Local<Value> WasmCompileError(Local<String> message);
7527 static Local<Value> WasmLinkError(Local<String> message);
7528 static Local<Value> WasmRuntimeError(Local<String> message);
7529 static Local<Value> Error(Local<String> message);
7530
7531 /**
7532 * Creates an error message for the given exception.
7533 * Will try to reconstruct the original stack trace from the exception value,
7534 * or capture the current stack trace if not available.
7535 */
7536 static Local<Message> CreateMessage(Isolate* isolate, Local<Value> exception);
7537
7538 /**
7539 * Returns the original stack trace that was captured at the creation time
7540 * of a given exception, or an empty handle if not available.
7541 */
7542 static Local<StackTrace> GetStackTrace(Local<Value> exception);
7543 };
7544
7545
7546 // --- Counters Callbacks ---
7547
7548 using CounterLookupCallback = int* (*)(const char* name);
7549
7550 using CreateHistogramCallback = void* (*)(const char* name, int min, int max,
7551 size_t buckets);
7552
7553 using AddHistogramSampleCallback = void (*)(void* histogram, int sample);
7554
7555 // --- Crashkeys Callback ---
7556 enum class CrashKeyId {
7557 kIsolateAddress,
7558 kReadonlySpaceFirstPageAddress,
7559 kMapSpaceFirstPageAddress,
7560 kCodeSpaceFirstPageAddress,
7561 kDumpType,
7562 };
7563
7564 using AddCrashKeyCallback = void (*)(CrashKeyId id, const std::string& value);
7565
7566 // --- Enter/Leave Script Callback ---
7567 using BeforeCallEnteredCallback = void (*)(Isolate*);
7568 using CallCompletedCallback = void (*)(Isolate*);
7569
7570 /**
7571 * HostImportModuleDynamicallyCallback is called when we require the
7572 * embedder to load a module. This is used as part of the dynamic
7573 * import syntax.
7574 *
7575 * The referrer contains metadata about the script/module that calls
7576 * import.
7577 *
7578 * The specifier is the name of the module that should be imported.
7579 *
7580 * The embedder must compile, instantiate, evaluate the Module, and
7581 * obtain its namespace object.
7582 *
7583 * The Promise returned from this function is forwarded to userland
7584 * JavaScript. The embedder must resolve this promise with the module
7585 * namespace object. In case of an exception, the embedder must reject
7586 * this promise with the exception. If the promise creation itself
7587 * fails (e.g. due to stack overflow), the embedder must propagate
7588 * that exception by returning an empty MaybeLocal.
7589 */
7590 using HostImportModuleDynamicallyCallback =
7591 MaybeLocal<Promise> (*)(Local<Context> context,
7592 Local<ScriptOrModule> referrer,
7593 Local<String> specifier);
7594
7595 /**
7596 * HostImportModuleDynamicallyWithImportAssertionsCallback is called when we
7597 * require the embedder to load a module. This is used as part of the dynamic
7598 * import syntax.
7599 *
7600 * The referrer contains metadata about the script/module that calls
7601 * import.
7602 *
7603 * The specifier is the name of the module that should be imported.
7604 *
7605 * The import_assertions are import assertions for this request in the form:
7606 * [key1, value1, key2, value2, ...] where the keys and values are of type
7607 * v8::String. Note, unlike the FixedArray passed to ResolveModuleCallback and
7608 * returned from ModuleRequest::GetImportAssertions(), this array does not
7609 * contain the source Locations of the assertions.
7610 *
7611 * The embedder must compile, instantiate, evaluate the Module, and
7612 * obtain its namespace object.
7613 *
7614 * The Promise returned from this function is forwarded to userland
7615 * JavaScript. The embedder must resolve this promise with the module
7616 * namespace object. In case of an exception, the embedder must reject
7617 * this promise with the exception. If the promise creation itself
7618 * fails (e.g. due to stack overflow), the embedder must propagate
7619 * that exception by returning an empty MaybeLocal.
7620 */
7621 using HostImportModuleDynamicallyWithImportAssertionsCallback =
7622 MaybeLocal<Promise> (*)(Local<Context> context,
7623 Local<ScriptOrModule> referrer,
7624 Local<String> specifier,
7625 Local<FixedArray> import_assertions);
7626
7627 /**
7628 * HostInitializeImportMetaObjectCallback is called the first time import.meta
7629 * is accessed for a module. Subsequent access will reuse the same value.
7630 *
7631 * The method combines two implementation-defined abstract operations into one:
7632 * HostGetImportMetaProperties and HostFinalizeImportMeta.
7633 *
7634 * The embedder should use v8::Object::CreateDataProperty to add properties on
7635 * the meta object.
7636 */
7637 using HostInitializeImportMetaObjectCallback = void (*)(Local<Context> context,
7638 Local<Module> module,
7639 Local<Object> meta);
7640
7641 /**
7642 * PrepareStackTraceCallback is called when the stack property of an error is
7643 * first accessed. The return value will be used as the stack value. If this
7644 * callback is registed, the |Error.prepareStackTrace| API will be disabled.
7645 * |sites| is an array of call sites, specified in
7646 * https://v8.dev/docs/stack-trace-api
7647 */
7648 using PrepareStackTraceCallback = MaybeLocal<Value> (*)(Local<Context> context,
7649 Local<Value> error,
7650 Local<Array> sites);
7651
7652 /**
7653 * PromiseHook with type kInit is called when a new promise is
7654 * created. When a new promise is created as part of the chain in the
7655 * case of Promise.then or in the intermediate promises created by
7656 * Promise.{race, all}/AsyncFunctionAwait, we pass the parent promise
7657 * otherwise we pass undefined.
7658 *
7659 * PromiseHook with type kResolve is called at the beginning of
7660 * resolve or reject function defined by CreateResolvingFunctions.
7661 *
7662 * PromiseHook with type kBefore is called at the beginning of the
7663 * PromiseReactionJob.
7664 *
7665 * PromiseHook with type kAfter is called right at the end of the
7666 * PromiseReactionJob.
7667 */
7668 enum class PromiseHookType { kInit, kResolve, kBefore, kAfter };
7669
7670 using PromiseHook = void (*)(PromiseHookType type, Local<Promise> promise,
7671 Local<Value> parent);
7672
7673 // --- Promise Reject Callback ---
7674 enum PromiseRejectEvent {
7675 kPromiseRejectWithNoHandler = 0,
7676 kPromiseHandlerAddedAfterReject = 1,
7677 kPromiseRejectAfterResolved = 2,
7678 kPromiseResolveAfterResolved = 3,
7679 };
7680
7681 class PromiseRejectMessage {
7682 public:
PromiseRejectMessage(Local<Promise> promise,PromiseRejectEvent event,Local<Value> value)7683 PromiseRejectMessage(Local<Promise> promise, PromiseRejectEvent event,
7684 Local<Value> value)
7685 : promise_(promise), event_(event), value_(value) {}
7686
GetPromise()7687 V8_INLINE Local<Promise> GetPromise() const { return promise_; }
GetEvent()7688 V8_INLINE PromiseRejectEvent GetEvent() const { return event_; }
GetValue()7689 V8_INLINE Local<Value> GetValue() const { return value_; }
7690
7691 private:
7692 Local<Promise> promise_;
7693 PromiseRejectEvent event_;
7694 Local<Value> value_;
7695 };
7696
7697 using PromiseRejectCallback = void (*)(PromiseRejectMessage message);
7698
7699 // --- Microtasks Callbacks ---
7700 using MicrotasksCompletedCallbackWithData = void (*)(Isolate*, void*);
7701 using MicrotaskCallback = void (*)(void* data);
7702
7703 /**
7704 * Policy for running microtasks:
7705 * - explicit: microtasks are invoked with the
7706 * Isolate::PerformMicrotaskCheckpoint() method;
7707 * - scoped: microtasks invocation is controlled by MicrotasksScope objects;
7708 * - auto: microtasks are invoked when the script call depth decrements
7709 * to zero.
7710 */
7711 enum class MicrotasksPolicy { kExplicit, kScoped, kAuto };
7712
7713 /**
7714 * Represents the microtask queue, where microtasks are stored and processed.
7715 * https://html.spec.whatwg.org/multipage/webappapis.html#microtask-queue
7716 * https://html.spec.whatwg.org/multipage/webappapis.html#enqueuejob(queuename,-job,-arguments)
7717 * https://html.spec.whatwg.org/multipage/webappapis.html#perform-a-microtask-checkpoint
7718 *
7719 * A MicrotaskQueue instance may be associated to multiple Contexts by passing
7720 * it to Context::New(), and they can be detached by Context::DetachGlobal().
7721 * The embedder must keep the MicrotaskQueue instance alive until all associated
7722 * Contexts are gone or detached.
7723 *
7724 * Use the same instance of MicrotaskQueue for all Contexts that may access each
7725 * other synchronously. E.g. for Web embedding, use the same instance for all
7726 * origins that share the same URL scheme and eTLD+1.
7727 */
7728 class V8_EXPORT MicrotaskQueue {
7729 public:
7730 /**
7731 * Creates an empty MicrotaskQueue instance.
7732 */
7733 static std::unique_ptr<MicrotaskQueue> New(
7734 Isolate* isolate, MicrotasksPolicy policy = MicrotasksPolicy::kAuto);
7735
7736 virtual ~MicrotaskQueue() = default;
7737
7738 /**
7739 * Enqueues the callback to the queue.
7740 */
7741 virtual void EnqueueMicrotask(Isolate* isolate,
7742 Local<Function> microtask) = 0;
7743
7744 /**
7745 * Enqueues the callback to the queue.
7746 */
7747 virtual void EnqueueMicrotask(v8::Isolate* isolate,
7748 MicrotaskCallback callback,
7749 void* data = nullptr) = 0;
7750
7751 /**
7752 * Adds a callback to notify the embedder after microtasks were run. The
7753 * callback is triggered by explicit RunMicrotasks call or automatic
7754 * microtasks execution (see Isolate::SetMicrotasksPolicy).
7755 *
7756 * Callback will trigger even if microtasks were attempted to run,
7757 * but the microtasks queue was empty and no single microtask was actually
7758 * executed.
7759 *
7760 * Executing scripts inside the callback will not re-trigger microtasks and
7761 * the callback.
7762 */
7763 virtual void AddMicrotasksCompletedCallback(
7764 MicrotasksCompletedCallbackWithData callback, void* data = nullptr) = 0;
7765
7766 /**
7767 * Removes callback that was installed by AddMicrotasksCompletedCallback.
7768 */
7769 virtual void RemoveMicrotasksCompletedCallback(
7770 MicrotasksCompletedCallbackWithData callback, void* data = nullptr) = 0;
7771
7772 /**
7773 * Runs microtasks if no microtask is running on this MicrotaskQueue instance.
7774 */
7775 virtual void PerformCheckpoint(Isolate* isolate) = 0;
7776
7777 /**
7778 * Returns true if a microtask is running on this MicrotaskQueue instance.
7779 */
7780 virtual bool IsRunningMicrotasks() const = 0;
7781
7782 /**
7783 * Returns the current depth of nested MicrotasksScope that has
7784 * kRunMicrotasks.
7785 */
7786 virtual int GetMicrotasksScopeDepth() const = 0;
7787
7788 MicrotaskQueue(const MicrotaskQueue&) = delete;
7789 MicrotaskQueue& operator=(const MicrotaskQueue&) = delete;
7790
7791 private:
7792 friend class internal::MicrotaskQueue;
7793 MicrotaskQueue() = default;
7794 };
7795
7796 /**
7797 * This scope is used to control microtasks when MicrotasksPolicy::kScoped
7798 * is used on Isolate. In this mode every non-primitive call to V8 should be
7799 * done inside some MicrotasksScope.
7800 * Microtasks are executed when topmost MicrotasksScope marked as kRunMicrotasks
7801 * exits.
7802 * kDoNotRunMicrotasks should be used to annotate calls not intended to trigger
7803 * microtasks.
7804 */
7805 class V8_EXPORT V8_NODISCARD MicrotasksScope {
7806 public:
7807 enum Type { kRunMicrotasks, kDoNotRunMicrotasks };
7808
7809 MicrotasksScope(Isolate* isolate, Type type);
7810 MicrotasksScope(Isolate* isolate, MicrotaskQueue* microtask_queue, Type type);
7811 ~MicrotasksScope();
7812
7813 /**
7814 * Runs microtasks if no kRunMicrotasks scope is currently active.
7815 */
7816 static void PerformCheckpoint(Isolate* isolate);
7817
7818 /**
7819 * Returns current depth of nested kRunMicrotasks scopes.
7820 */
7821 static int GetCurrentDepth(Isolate* isolate);
7822
7823 /**
7824 * Returns true while microtasks are being executed.
7825 */
7826 static bool IsRunningMicrotasks(Isolate* isolate);
7827
7828 // Prevent copying.
7829 MicrotasksScope(const MicrotasksScope&) = delete;
7830 MicrotasksScope& operator=(const MicrotasksScope&) = delete;
7831
7832 private:
7833 internal::Isolate* const isolate_;
7834 internal::MicrotaskQueue* const microtask_queue_;
7835 bool run_;
7836 };
7837
7838 // --- Failed Access Check Callback ---
7839 using FailedAccessCheckCallback = void (*)(Local<Object> target,
7840 AccessType type, Local<Value> data);
7841
7842 // --- AllowCodeGenerationFromStrings callbacks ---
7843
7844 /**
7845 * Callback to check if code generation from strings is allowed. See
7846 * Context::AllowCodeGenerationFromStrings.
7847 */
7848 using AllowCodeGenerationFromStringsCallback = bool (*)(Local<Context> context,
7849 Local<String> source);
7850
7851 struct ModifyCodeGenerationFromStringsResult {
7852 // If true, proceed with the codegen algorithm. Otherwise, block it.
7853 bool codegen_allowed = false;
7854 // Overwrite the original source with this string, if present.
7855 // Use the original source if empty.
7856 // This field is considered only if codegen_allowed is true.
7857 MaybeLocal<String> modified_source;
7858 };
7859
7860 /**
7861 * Callback to check if codegen is allowed from a source object, and convert
7862 * the source to string if necessary. See: ModifyCodeGenerationFromStrings.
7863 */
7864 using ModifyCodeGenerationFromStringsCallback =
7865 ModifyCodeGenerationFromStringsResult (*)(Local<Context> context,
7866 Local<Value> source);
7867 using ModifyCodeGenerationFromStringsCallback2 =
7868 ModifyCodeGenerationFromStringsResult (*)(Local<Context> context,
7869 Local<Value> source,
7870 bool is_code_like);
7871
7872 // --- WebAssembly compilation callbacks ---
7873 using ExtensionCallback = bool (*)(const FunctionCallbackInfo<Value>&);
7874
7875 using AllowWasmCodeGenerationCallback = bool (*)(Local<Context> context,
7876 Local<String> source);
7877
7878 // --- Callback for APIs defined on v8-supported objects, but implemented
7879 // by the embedder. Example: WebAssembly.{compile|instantiate}Streaming ---
7880 using ApiImplementationCallback = void (*)(const FunctionCallbackInfo<Value>&);
7881
7882 // --- Callback for WebAssembly.compileStreaming ---
7883 using WasmStreamingCallback = void (*)(const FunctionCallbackInfo<Value>&);
7884
7885 // --- Callback for loading source map file for Wasm profiling support
7886 using WasmLoadSourceMapCallback = Local<String> (*)(Isolate* isolate,
7887 const char* name);
7888
7889 // --- Callback for checking if WebAssembly Simd is enabled ---
7890 using WasmSimdEnabledCallback = bool (*)(Local<Context> context);
7891
7892 // --- Callback for checking if WebAssembly exceptions are enabled ---
7893 using WasmExceptionsEnabledCallback = bool (*)(Local<Context> context);
7894
7895 // --- Callback for checking if the SharedArrayBuffer constructor is enabled ---
7896 using SharedArrayBufferConstructorEnabledCallback =
7897 bool (*)(Local<Context> context);
7898
7899 // --- Garbage Collection Callbacks ---
7900
7901 /**
7902 * Applications can register callback functions which will be called before and
7903 * after certain garbage collection operations. Allocations are not allowed in
7904 * the callback functions, you therefore cannot manipulate objects (set or
7905 * delete properties for example) since it is possible such operations will
7906 * result in the allocation of objects.
7907 */
7908 enum GCType {
7909 kGCTypeScavenge = 1 << 0,
7910 kGCTypeMarkSweepCompact = 1 << 1,
7911 kGCTypeIncrementalMarking = 1 << 2,
7912 kGCTypeProcessWeakCallbacks = 1 << 3,
7913 kGCTypeAll = kGCTypeScavenge | kGCTypeMarkSweepCompact |
7914 kGCTypeIncrementalMarking | kGCTypeProcessWeakCallbacks
7915 };
7916
7917 /**
7918 * GCCallbackFlags is used to notify additional information about the GC
7919 * callback.
7920 * - kGCCallbackFlagConstructRetainedObjectInfos: The GC callback is for
7921 * constructing retained object infos.
7922 * - kGCCallbackFlagForced: The GC callback is for a forced GC for testing.
7923 * - kGCCallbackFlagSynchronousPhantomCallbackProcessing: The GC callback
7924 * is called synchronously without getting posted to an idle task.
7925 * - kGCCallbackFlagCollectAllAvailableGarbage: The GC callback is called
7926 * in a phase where V8 is trying to collect all available garbage
7927 * (e.g., handling a low memory notification).
7928 * - kGCCallbackScheduleIdleGarbageCollection: The GC callback is called to
7929 * trigger an idle garbage collection.
7930 */
7931 enum GCCallbackFlags {
7932 kNoGCCallbackFlags = 0,
7933 kGCCallbackFlagConstructRetainedObjectInfos = 1 << 1,
7934 kGCCallbackFlagForced = 1 << 2,
7935 kGCCallbackFlagSynchronousPhantomCallbackProcessing = 1 << 3,
7936 kGCCallbackFlagCollectAllAvailableGarbage = 1 << 4,
7937 kGCCallbackFlagCollectAllExternalMemory = 1 << 5,
7938 kGCCallbackScheduleIdleGarbageCollection = 1 << 6,
7939 };
7940
7941 using GCCallback = void (*)(GCType type, GCCallbackFlags flags);
7942
7943 using InterruptCallback = void (*)(Isolate* isolate, void* data);
7944
7945 /**
7946 * This callback is invoked when the heap size is close to the heap limit and
7947 * V8 is likely to abort with out-of-memory error.
7948 * The callback can extend the heap limit by returning a value that is greater
7949 * than the current_heap_limit. The initial heap limit is the limit that was
7950 * set after heap setup.
7951 */
7952 using NearHeapLimitCallback = size_t (*)(void* data, size_t current_heap_limit,
7953 size_t initial_heap_limit);
7954
7955 /**
7956 * Collection of shared per-process V8 memory information.
7957 *
7958 * Instances of this class can be passed to
7959 * v8::V8::GetSharedMemoryStatistics to get shared memory statistics from V8.
7960 */
7961 class V8_EXPORT SharedMemoryStatistics {
7962 public:
7963 SharedMemoryStatistics();
read_only_space_size()7964 size_t read_only_space_size() { return read_only_space_size_; }
read_only_space_used_size()7965 size_t read_only_space_used_size() { return read_only_space_used_size_; }
read_only_space_physical_size()7966 size_t read_only_space_physical_size() {
7967 return read_only_space_physical_size_;
7968 }
7969
7970 private:
7971 size_t read_only_space_size_;
7972 size_t read_only_space_used_size_;
7973 size_t read_only_space_physical_size_;
7974
7975 friend class V8;
7976 friend class internal::ReadOnlyHeap;
7977 };
7978
7979 /**
7980 * Collection of V8 heap information.
7981 *
7982 * Instances of this class can be passed to v8::Isolate::GetHeapStatistics to
7983 * get heap statistics from V8.
7984 */
7985 class V8_EXPORT HeapStatistics {
7986 public:
7987 HeapStatistics();
total_heap_size()7988 size_t total_heap_size() { return total_heap_size_; }
total_heap_size_executable()7989 size_t total_heap_size_executable() { return total_heap_size_executable_; }
total_physical_size()7990 size_t total_physical_size() { return total_physical_size_; }
total_available_size()7991 size_t total_available_size() { return total_available_size_; }
total_global_handles_size()7992 size_t total_global_handles_size() { return total_global_handles_size_; }
used_global_handles_size()7993 size_t used_global_handles_size() { return used_global_handles_size_; }
used_heap_size()7994 size_t used_heap_size() { return used_heap_size_; }
heap_size_limit()7995 size_t heap_size_limit() { return heap_size_limit_; }
malloced_memory()7996 size_t malloced_memory() { return malloced_memory_; }
external_memory()7997 size_t external_memory() { return external_memory_; }
peak_malloced_memory()7998 size_t peak_malloced_memory() { return peak_malloced_memory_; }
number_of_native_contexts()7999 size_t number_of_native_contexts() { return number_of_native_contexts_; }
number_of_detached_contexts()8000 size_t number_of_detached_contexts() { return number_of_detached_contexts_; }
8001
8002 /**
8003 * Returns a 0/1 boolean, which signifies whether the V8 overwrite heap
8004 * garbage with a bit pattern.
8005 */
does_zap_garbage()8006 size_t does_zap_garbage() { return does_zap_garbage_; }
8007
8008 private:
8009 size_t total_heap_size_;
8010 size_t total_heap_size_executable_;
8011 size_t total_physical_size_;
8012 size_t total_available_size_;
8013 size_t used_heap_size_;
8014 size_t heap_size_limit_;
8015 size_t malloced_memory_;
8016 size_t external_memory_;
8017 size_t peak_malloced_memory_;
8018 bool does_zap_garbage_;
8019 size_t number_of_native_contexts_;
8020 size_t number_of_detached_contexts_;
8021 size_t total_global_handles_size_;
8022 size_t used_global_handles_size_;
8023
8024 friend class V8;
8025 friend class Isolate;
8026 };
8027
8028
8029 class V8_EXPORT HeapSpaceStatistics {
8030 public:
8031 HeapSpaceStatistics();
space_name()8032 const char* space_name() { return space_name_; }
space_size()8033 size_t space_size() { return space_size_; }
space_used_size()8034 size_t space_used_size() { return space_used_size_; }
space_available_size()8035 size_t space_available_size() { return space_available_size_; }
physical_space_size()8036 size_t physical_space_size() { return physical_space_size_; }
8037
8038 private:
8039 const char* space_name_;
8040 size_t space_size_;
8041 size_t space_used_size_;
8042 size_t space_available_size_;
8043 size_t physical_space_size_;
8044
8045 friend class Isolate;
8046 };
8047
8048
8049 class V8_EXPORT HeapObjectStatistics {
8050 public:
8051 HeapObjectStatistics();
object_type()8052 const char* object_type() { return object_type_; }
object_sub_type()8053 const char* object_sub_type() { return object_sub_type_; }
object_count()8054 size_t object_count() { return object_count_; }
object_size()8055 size_t object_size() { return object_size_; }
8056
8057 private:
8058 const char* object_type_;
8059 const char* object_sub_type_;
8060 size_t object_count_;
8061 size_t object_size_;
8062
8063 friend class Isolate;
8064 };
8065
8066 class V8_EXPORT HeapCodeStatistics {
8067 public:
8068 HeapCodeStatistics();
code_and_metadata_size()8069 size_t code_and_metadata_size() { return code_and_metadata_size_; }
bytecode_and_metadata_size()8070 size_t bytecode_and_metadata_size() { return bytecode_and_metadata_size_; }
external_script_source_size()8071 size_t external_script_source_size() { return external_script_source_size_; }
8072
8073 private:
8074 size_t code_and_metadata_size_;
8075 size_t bytecode_and_metadata_size_;
8076 size_t external_script_source_size_;
8077
8078 friend class Isolate;
8079 };
8080
8081 /**
8082 * A JIT code event is issued each time code is added, moved or removed.
8083 *
8084 * \note removal events are not currently issued.
8085 */
8086 struct JitCodeEvent {
8087 enum EventType {
8088 CODE_ADDED,
8089 CODE_MOVED,
8090 CODE_REMOVED,
8091 CODE_ADD_LINE_POS_INFO,
8092 CODE_START_LINE_INFO_RECORDING,
8093 CODE_END_LINE_INFO_RECORDING
8094 };
8095 // Definition of the code position type. The "POSITION" type means the place
8096 // in the source code which are of interest when making stack traces to
8097 // pin-point the source location of a stack frame as close as possible.
8098 // The "STATEMENT_POSITION" means the place at the beginning of each
8099 // statement, and is used to indicate possible break locations.
8100 enum PositionType { POSITION, STATEMENT_POSITION };
8101
8102 // There are two different kinds of JitCodeEvents, one for JIT code generated
8103 // by the optimizing compiler, and one for byte code generated for the
8104 // interpreter. For JIT_CODE events, the |code_start| member of the event
8105 // points to the beginning of jitted assembly code, while for BYTE_CODE
8106 // events, |code_start| points to the first bytecode of the interpreted
8107 // function.
8108 enum CodeType { BYTE_CODE, JIT_CODE };
8109
8110 // Type of event.
8111 EventType type;
8112 CodeType code_type;
8113 // Start of the instructions.
8114 void* code_start;
8115 // Size of the instructions.
8116 size_t code_len;
8117 // Script info for CODE_ADDED event.
8118 Local<UnboundScript> script;
8119 // User-defined data for *_LINE_INFO_* event. It's used to hold the source
8120 // code line information which is returned from the
8121 // CODE_START_LINE_INFO_RECORDING event. And it's passed to subsequent
8122 // CODE_ADD_LINE_POS_INFO and CODE_END_LINE_INFO_RECORDING events.
8123 void* user_data;
8124
8125 struct name_t {
8126 // Name of the object associated with the code, note that the string is not
8127 // zero-terminated.
8128 const char* str;
8129 // Number of chars in str.
8130 size_t len;
8131 };
8132
8133 struct line_info_t {
8134 // PC offset
8135 size_t offset;
8136 // Code position
8137 size_t pos;
8138 // The position type.
8139 PositionType position_type;
8140 };
8141
8142 struct wasm_source_info_t {
8143 // Source file name.
8144 const char* filename;
8145 // Length of filename.
8146 size_t filename_size;
8147 // Line number table, which maps offsets of JITted code to line numbers of
8148 // source file.
8149 const line_info_t* line_number_table;
8150 // Number of entries in the line number table.
8151 size_t line_number_table_size;
8152 };
8153
8154 wasm_source_info_t* wasm_source_info;
8155
8156 union {
8157 // Only valid for CODE_ADDED.
8158 struct name_t name;
8159
8160 // Only valid for CODE_ADD_LINE_POS_INFO
8161 struct line_info_t line_info;
8162
8163 // New location of instructions. Only valid for CODE_MOVED.
8164 void* new_code_start;
8165 };
8166
8167 Isolate* isolate;
8168 };
8169
8170 /**
8171 * Option flags passed to the SetRAILMode function.
8172 * See documentation https://developers.google.com/web/tools/chrome-devtools/
8173 * profile/evaluate-performance/rail
8174 */
8175 enum RAILMode : unsigned {
8176 // Response performance mode: In this mode very low virtual machine latency
8177 // is provided. V8 will try to avoid JavaScript execution interruptions.
8178 // Throughput may be throttled.
8179 PERFORMANCE_RESPONSE,
8180 // Animation performance mode: In this mode low virtual machine latency is
8181 // provided. V8 will try to avoid as many JavaScript execution interruptions
8182 // as possible. Throughput may be throttled. This is the default mode.
8183 PERFORMANCE_ANIMATION,
8184 // Idle performance mode: The embedder is idle. V8 can complete deferred work
8185 // in this mode.
8186 PERFORMANCE_IDLE,
8187 // Load performance mode: In this mode high throughput is provided. V8 may
8188 // turn off latency optimizations.
8189 PERFORMANCE_LOAD
8190 };
8191
8192 /**
8193 * Option flags passed to the SetJitCodeEventHandler function.
8194 */
8195 enum JitCodeEventOptions {
8196 kJitCodeEventDefault = 0,
8197 // Generate callbacks for already existent code.
8198 kJitCodeEventEnumExisting = 1
8199 };
8200
8201
8202 /**
8203 * Callback function passed to SetJitCodeEventHandler.
8204 *
8205 * \param event code add, move or removal event.
8206 */
8207 using JitCodeEventHandler = void (*)(const JitCodeEvent* event);
8208
8209 /**
8210 * Callback function passed to SetUnhandledExceptionCallback.
8211 */
8212 #if defined(V8_OS_WIN)
8213 using UnhandledExceptionCallback =
8214 int (*)(_EXCEPTION_POINTERS* exception_pointers);
8215 #endif
8216
8217 /**
8218 * Interface for iterating through all external resources in the heap.
8219 */
8220 class V8_EXPORT ExternalResourceVisitor {
8221 public:
8222 virtual ~ExternalResourceVisitor() = default;
VisitExternalString(Local<String> string)8223 virtual void VisitExternalString(Local<String> string) {}
8224 };
8225
8226 /**
8227 * Interface for iterating through all the persistent handles in the heap.
8228 */
8229 class V8_EXPORT PersistentHandleVisitor {
8230 public:
8231 virtual ~PersistentHandleVisitor() = default;
VisitPersistentHandle(Persistent<Value> * value,uint16_t class_id)8232 virtual void VisitPersistentHandle(Persistent<Value>* value,
8233 uint16_t class_id) {}
8234 };
8235
8236 /**
8237 * Memory pressure level for the MemoryPressureNotification.
8238 * kNone hints V8 that there is no memory pressure.
8239 * kModerate hints V8 to speed up incremental garbage collection at the cost of
8240 * of higher latency due to garbage collection pauses.
8241 * kCritical hints V8 to free memory as soon as possible. Garbage collection
8242 * pauses at this level will be large.
8243 */
8244 enum class MemoryPressureLevel { kNone, kModerate, kCritical };
8245
8246 /**
8247 * Handler for embedder roots on non-unified heap garbage collections.
8248 */
8249 class V8_EXPORT EmbedderRootsHandler {
8250 public:
8251 virtual ~EmbedderRootsHandler() = default;
8252
8253 /**
8254 * Returns true if the TracedGlobal handle should be considered as root for
8255 * the currently running non-tracing garbage collection and false otherwise.
8256 * The default implementation will keep all TracedGlobal references as roots.
8257 *
8258 * If this returns false, then V8 may decide that the object referred to by
8259 * such a handle is reclaimed. In that case:
8260 * - No action is required if handles are used with destructors, i.e., by just
8261 * using |TracedGlobal|.
8262 * - When run without destructors, i.e., by using |TracedReference|, V8 calls
8263 * |ResetRoot|.
8264 *
8265 * Note that the |handle| is different from the handle that the embedder holds
8266 * for retaining the object. The embedder may use |WrapperClassId()| to
8267 * distinguish cases where it wants handles to be treated as roots from not
8268 * being treated as roots.
8269 */
8270 virtual bool IsRoot(const v8::TracedReference<v8::Value>& handle) = 0;
8271 virtual bool IsRoot(const v8::TracedGlobal<v8::Value>& handle) = 0;
8272
8273 /**
8274 * Used in combination with |IsRoot|. Called by V8 when an
8275 * object that is backed by a handle is reclaimed by a non-tracing garbage
8276 * collection. It is up to the embedder to reset the original handle.
8277 *
8278 * Note that the |handle| is different from the handle that the embedder holds
8279 * for retaining the object. It is up to the embedder to find the original
8280 * handle via the object or class id.
8281 */
8282 virtual void ResetRoot(const v8::TracedReference<v8::Value>& handle) = 0;
8283 };
8284
8285 /**
8286 * Interface for tracing through the embedder heap. During a V8 garbage
8287 * collection, V8 collects hidden fields of all potential wrappers, and at the
8288 * end of its marking phase iterates the collection and asks the embedder to
8289 * trace through its heap and use reporter to report each JavaScript object
8290 * reachable from any of the given wrappers.
8291 */
8292 class V8_EXPORT EmbedderHeapTracer {
8293 public:
8294 using EmbedderStackState = cppgc::EmbedderStackState;
8295
8296 enum TraceFlags : uint64_t {
8297 kNoFlags = 0,
8298 kReduceMemory = 1 << 0,
8299 kForced = 1 << 2,
8300 };
8301
8302 /**
8303 * Interface for iterating through TracedGlobal handles.
8304 */
8305 class V8_EXPORT TracedGlobalHandleVisitor {
8306 public:
8307 virtual ~TracedGlobalHandleVisitor() = default;
VisitTracedGlobalHandle(const TracedGlobal<Value> & handle)8308 virtual void VisitTracedGlobalHandle(const TracedGlobal<Value>& handle) {}
VisitTracedReference(const TracedReference<Value> & handle)8309 virtual void VisitTracedReference(const TracedReference<Value>& handle) {}
8310 };
8311
8312 /**
8313 * Summary of a garbage collection cycle. See |TraceEpilogue| on how the
8314 * summary is reported.
8315 */
8316 struct TraceSummary {
8317 /**
8318 * Time spent managing the retained memory in milliseconds. This can e.g.
8319 * include the time tracing through objects in the embedder.
8320 */
8321 double time = 0.0;
8322
8323 /**
8324 * Memory retained by the embedder through the |EmbedderHeapTracer|
8325 * mechanism in bytes.
8326 */
8327 size_t allocated_size = 0;
8328 };
8329
8330 virtual ~EmbedderHeapTracer() = default;
8331
8332 /**
8333 * Iterates all TracedGlobal handles created for the v8::Isolate the tracer is
8334 * attached to.
8335 */
8336 void IterateTracedGlobalHandles(TracedGlobalHandleVisitor* visitor);
8337
8338 /**
8339 * Called by the embedder to set the start of the stack which is e.g. used by
8340 * V8 to determine whether handles are used from stack or heap.
8341 */
8342 void SetStackStart(void* stack_start);
8343
8344 /**
8345 * Called by the embedder to notify V8 of an empty execution stack.
8346 */
8347 V8_DEPRECATE_SOON(
8348 "This call only optimized internal caches which V8 is able to figure out "
8349 "on its own now.")
8350 void NotifyEmptyEmbedderStack();
8351
8352 /**
8353 * Called by v8 to register internal fields of found wrappers.
8354 *
8355 * The embedder is expected to store them somewhere and trace reachable
8356 * wrappers from them when called through |AdvanceTracing|.
8357 */
8358 virtual void RegisterV8References(
8359 const std::vector<std::pair<void*, void*> >& embedder_fields) = 0;
8360
8361 void RegisterEmbedderReference(const BasicTracedReference<v8::Data>& ref);
8362
8363 /**
8364 * Called at the beginning of a GC cycle.
8365 */
TracePrologue(TraceFlags flags)8366 virtual void TracePrologue(TraceFlags flags) {}
8367
8368 /**
8369 * Called to advance tracing in the embedder.
8370 *
8371 * The embedder is expected to trace its heap starting from wrappers reported
8372 * by RegisterV8References method, and report back all reachable wrappers.
8373 * Furthermore, the embedder is expected to stop tracing by the given
8374 * deadline. A deadline of infinity means that tracing should be finished.
8375 *
8376 * Returns |true| if tracing is done, and false otherwise.
8377 */
8378 virtual bool AdvanceTracing(double deadline_in_ms) = 0;
8379
8380 /*
8381 * Returns true if there no more tracing work to be done (see AdvanceTracing)
8382 * and false otherwise.
8383 */
8384 virtual bool IsTracingDone() = 0;
8385
8386 /**
8387 * Called at the end of a GC cycle.
8388 *
8389 * Note that allocation is *not* allowed within |TraceEpilogue|. Can be
8390 * overriden to fill a |TraceSummary| that is used by V8 to schedule future
8391 * garbage collections.
8392 */
TraceEpilogue(TraceSummary * trace_summary)8393 virtual void TraceEpilogue(TraceSummary* trace_summary) {}
8394
8395 /**
8396 * Called upon entering the final marking pause. No more incremental marking
8397 * steps will follow this call.
8398 */
8399 virtual void EnterFinalPause(EmbedderStackState stack_state) = 0;
8400
8401 /*
8402 * Called by the embedder to request immediate finalization of the currently
8403 * running tracing phase that has been started with TracePrologue and not
8404 * yet finished with TraceEpilogue.
8405 *
8406 * Will be a noop when currently not in tracing.
8407 *
8408 * This is an experimental feature.
8409 */
8410 void FinalizeTracing();
8411
8412 /**
8413 * See documentation on EmbedderRootsHandler.
8414 */
8415 virtual bool IsRootForNonTracingGC(
8416 const v8::TracedReference<v8::Value>& handle);
8417 virtual bool IsRootForNonTracingGC(const v8::TracedGlobal<v8::Value>& handle);
8418
8419 /**
8420 * See documentation on EmbedderRootsHandler.
8421 */
8422 virtual void ResetHandleInNonTracingGC(
8423 const v8::TracedReference<v8::Value>& handle);
8424
8425 /*
8426 * Called by the embedder to immediately perform a full garbage collection.
8427 *
8428 * Should only be used in testing code.
8429 */
8430 void GarbageCollectionForTesting(EmbedderStackState stack_state);
8431
8432 /*
8433 * Called by the embedder to signal newly allocated or freed memory. Not bound
8434 * to tracing phases. Embedders should trade off when increments are reported
8435 * as V8 may consult global heuristics on whether to trigger garbage
8436 * collection on this change.
8437 */
8438 void IncreaseAllocatedSize(size_t bytes);
8439 void DecreaseAllocatedSize(size_t bytes);
8440
8441 /*
8442 * Returns the v8::Isolate this tracer is attached too and |nullptr| if it
8443 * is not attached to any v8::Isolate.
8444 */
isolate()8445 v8::Isolate* isolate() const { return isolate_; }
8446
8447 protected:
8448 v8::Isolate* isolate_ = nullptr;
8449
8450 friend class internal::LocalEmbedderHeapTracer;
8451 };
8452
8453 /**
8454 * Callback and supporting data used in SnapshotCreator to implement embedder
8455 * logic to serialize internal fields.
8456 * Internal fields that directly reference V8 objects are serialized without
8457 * calling this callback. Internal fields that contain aligned pointers are
8458 * serialized by this callback if it returns non-zero result. Otherwise it is
8459 * serialized verbatim.
8460 */
8461 struct SerializeInternalFieldsCallback {
8462 using CallbackFunction = StartupData (*)(Local<Object> holder, int index,
8463 void* data);
8464 SerializeInternalFieldsCallback(CallbackFunction function = nullptr,
8465 void* data_arg = nullptr)
callbackSerializeInternalFieldsCallback8466 : callback(function), data(data_arg) {}
8467 CallbackFunction callback;
8468 void* data;
8469 };
8470 // Note that these fields are called "internal fields" in the API and called
8471 // "embedder fields" within V8.
8472 using SerializeEmbedderFieldsCallback = SerializeInternalFieldsCallback;
8473
8474 /**
8475 * Callback and supporting data used to implement embedder logic to deserialize
8476 * internal fields.
8477 */
8478 struct DeserializeInternalFieldsCallback {
8479 using CallbackFunction = void (*)(Local<Object> holder, int index,
8480 StartupData payload, void* data);
8481 DeserializeInternalFieldsCallback(CallbackFunction function = nullptr,
8482 void* data_arg = nullptr)
callbackDeserializeInternalFieldsCallback8483 : callback(function), data(data_arg) {}
8484 void (*callback)(Local<Object> holder, int index, StartupData payload,
8485 void* data);
8486 void* data;
8487 };
8488 using DeserializeEmbedderFieldsCallback = DeserializeInternalFieldsCallback;
8489
8490 /**
8491 * Controls how the default MeasureMemoryDelegate reports the result of
8492 * the memory measurement to JS. With kSummary only the total size is reported.
8493 * With kDetailed the result includes the size of each native context.
8494 */
8495 enum class MeasureMemoryMode { kSummary, kDetailed };
8496
8497 /**
8498 * Controls how promptly a memory measurement request is executed.
8499 * By default the measurement is folded with the next scheduled GC which may
8500 * happen after a while and is forced after some timeout.
8501 * The kEager mode starts incremental GC right away and is useful for testing.
8502 * The kLazy mode does not force GC.
8503 */
8504 enum class MeasureMemoryExecution { kDefault, kEager, kLazy };
8505
8506 /**
8507 * The delegate is used in Isolate::MeasureMemory API.
8508 *
8509 * It specifies the contexts that need to be measured and gets called when
8510 * the measurement is completed to report the results.
8511 */
8512 class V8_EXPORT MeasureMemoryDelegate {
8513 public:
8514 virtual ~MeasureMemoryDelegate() = default;
8515
8516 /**
8517 * Returns true if the size of the given context needs to be measured.
8518 */
8519 virtual bool ShouldMeasure(Local<Context> context) = 0;
8520
8521 /**
8522 * This function is called when memory measurement finishes.
8523 *
8524 * \param context_sizes_in_bytes a vector of (context, size) pairs that
8525 * includes each context for which ShouldMeasure returned true and that
8526 * was not garbage collected while the memory measurement was in progress.
8527 *
8528 * \param unattributed_size_in_bytes total size of objects that were not
8529 * attributed to any context (i.e. are likely shared objects).
8530 */
8531 virtual void MeasurementComplete(
8532 const std::vector<std::pair<Local<Context>, size_t>>&
8533 context_sizes_in_bytes,
8534 size_t unattributed_size_in_bytes) = 0;
8535
8536 /**
8537 * Returns a default delegate that resolves the given promise when
8538 * the memory measurement completes.
8539 *
8540 * \param isolate the current isolate
8541 * \param context the current context
8542 * \param promise_resolver the promise resolver that is given the
8543 * result of the memory measurement.
8544 * \param mode the detail level of the result.
8545 */
8546 static std::unique_ptr<MeasureMemoryDelegate> Default(
8547 Isolate* isolate, Local<Context> context,
8548 Local<Promise::Resolver> promise_resolver, MeasureMemoryMode mode);
8549 };
8550
8551 /**
8552 * Isolate represents an isolated instance of the V8 engine. V8 isolates have
8553 * completely separate states. Objects from one isolate must not be used in
8554 * other isolates. The embedder can create multiple isolates and use them in
8555 * parallel in multiple threads. An isolate can be entered by at most one
8556 * thread at any given time. The Locker/Unlocker API must be used to
8557 * synchronize.
8558 */
8559 class V8_EXPORT Isolate {
8560 public:
8561 /**
8562 * Initial configuration parameters for a new Isolate.
8563 */
8564 struct V8_EXPORT CreateParams {
8565 CreateParams();
8566 ~CreateParams();
8567
8568 /**
8569 * Allows the host application to provide the address of a function that is
8570 * notified each time code is added, moved or removed.
8571 */
8572 JitCodeEventHandler code_event_handler = nullptr;
8573
8574 /**
8575 * ResourceConstraints to use for the new Isolate.
8576 */
8577 ResourceConstraints constraints;
8578
8579 /**
8580 * Explicitly specify a startup snapshot blob. The embedder owns the blob.
8581 */
8582 StartupData* snapshot_blob = nullptr;
8583
8584 /**
8585 * Enables the host application to provide a mechanism for recording
8586 * statistics counters.
8587 */
8588 CounterLookupCallback counter_lookup_callback = nullptr;
8589
8590 /**
8591 * Enables the host application to provide a mechanism for recording
8592 * histograms. The CreateHistogram function returns a
8593 * histogram which will later be passed to the AddHistogramSample
8594 * function.
8595 */
8596 CreateHistogramCallback create_histogram_callback = nullptr;
8597 AddHistogramSampleCallback add_histogram_sample_callback = nullptr;
8598
8599 /**
8600 * The ArrayBuffer::Allocator to use for allocating and freeing the backing
8601 * store of ArrayBuffers.
8602 *
8603 * If the shared_ptr version is used, the Isolate instance and every
8604 * |BackingStore| allocated using this allocator hold a std::shared_ptr
8605 * to the allocator, in order to facilitate lifetime
8606 * management for the allocator instance.
8607 */
8608 ArrayBuffer::Allocator* array_buffer_allocator = nullptr;
8609 std::shared_ptr<ArrayBuffer::Allocator> array_buffer_allocator_shared;
8610
8611 /**
8612 * Specifies an optional nullptr-terminated array of raw addresses in the
8613 * embedder that V8 can match against during serialization and use for
8614 * deserialization. This array and its content must stay valid for the
8615 * entire lifetime of the isolate.
8616 */
8617 const intptr_t* external_references = nullptr;
8618
8619 /**
8620 * Whether calling Atomics.wait (a function that may block) is allowed in
8621 * this isolate. This can also be configured via SetAllowAtomicsWait.
8622 */
8623 bool allow_atomics_wait = true;
8624
8625 /**
8626 * Termination is postponed when there is no active SafeForTerminationScope.
8627 */
8628 bool only_terminate_in_safe_scope = false;
8629
8630 /**
8631 * The following parameters describe the offsets for addressing type info
8632 * for wrapped API objects and are used by the fast C API
8633 * (for details see v8-fast-api-calls.h).
8634 */
8635 int embedder_wrapper_type_index = -1;
8636 int embedder_wrapper_object_index = -1;
8637
8638 V8_DEPRECATED(
8639 "Setting this has no effect. Embedders should ignore import assertions "
8640 "that they do not use.")
8641 std::vector<std::string> supported_import_assertions;
8642 };
8643
8644 /**
8645 * Stack-allocated class which sets the isolate for all operations
8646 * executed within a local scope.
8647 */
8648 class V8_EXPORT V8_NODISCARD Scope {
8649 public:
Scope(Isolate * isolate)8650 explicit Scope(Isolate* isolate) : isolate_(isolate) {
8651 isolate->Enter();
8652 }
8653
~Scope()8654 ~Scope() { isolate_->Exit(); }
8655
8656 // Prevent copying of Scope objects.
8657 Scope(const Scope&) = delete;
8658 Scope& operator=(const Scope&) = delete;
8659
8660 private:
8661 Isolate* const isolate_;
8662 };
8663
8664 /**
8665 * Assert that no Javascript code is invoked.
8666 */
8667 class V8_EXPORT V8_NODISCARD DisallowJavascriptExecutionScope {
8668 public:
8669 enum OnFailure { CRASH_ON_FAILURE, THROW_ON_FAILURE, DUMP_ON_FAILURE };
8670
8671 DisallowJavascriptExecutionScope(Isolate* isolate, OnFailure on_failure);
8672 ~DisallowJavascriptExecutionScope();
8673
8674 // Prevent copying of Scope objects.
8675 DisallowJavascriptExecutionScope(const DisallowJavascriptExecutionScope&) =
8676 delete;
8677 DisallowJavascriptExecutionScope& operator=(
8678 const DisallowJavascriptExecutionScope&) = delete;
8679
8680 private:
8681 OnFailure on_failure_;
8682 Isolate* isolate_;
8683
8684 bool was_execution_allowed_assert_;
8685 bool was_execution_allowed_throws_;
8686 bool was_execution_allowed_dump_;
8687 };
8688
8689 /**
8690 * Introduce exception to DisallowJavascriptExecutionScope.
8691 */
8692 class V8_EXPORT V8_NODISCARD AllowJavascriptExecutionScope {
8693 public:
8694 explicit AllowJavascriptExecutionScope(Isolate* isolate);
8695 ~AllowJavascriptExecutionScope();
8696
8697 // Prevent copying of Scope objects.
8698 AllowJavascriptExecutionScope(const AllowJavascriptExecutionScope&) =
8699 delete;
8700 AllowJavascriptExecutionScope& operator=(
8701 const AllowJavascriptExecutionScope&) = delete;
8702
8703 private:
8704 Isolate* isolate_;
8705 bool was_execution_allowed_assert_;
8706 bool was_execution_allowed_throws_;
8707 bool was_execution_allowed_dump_;
8708 };
8709
8710 /**
8711 * Do not run microtasks while this scope is active, even if microtasks are
8712 * automatically executed otherwise.
8713 */
8714 class V8_EXPORT V8_NODISCARD SuppressMicrotaskExecutionScope {
8715 public:
8716 explicit SuppressMicrotaskExecutionScope(
8717 Isolate* isolate, MicrotaskQueue* microtask_queue = nullptr);
8718 ~SuppressMicrotaskExecutionScope();
8719
8720 // Prevent copying of Scope objects.
8721 SuppressMicrotaskExecutionScope(const SuppressMicrotaskExecutionScope&) =
8722 delete;
8723 SuppressMicrotaskExecutionScope& operator=(
8724 const SuppressMicrotaskExecutionScope&) = delete;
8725
8726 private:
8727 internal::Isolate* const isolate_;
8728 internal::MicrotaskQueue* const microtask_queue_;
8729 internal::Address previous_stack_height_;
8730
8731 friend class internal::ThreadLocalTop;
8732 };
8733
8734 /**
8735 * This scope allows terminations inside direct V8 API calls and forbid them
8736 * inside any recursive API calls without explicit SafeForTerminationScope.
8737 */
8738 class V8_EXPORT V8_NODISCARD SafeForTerminationScope {
8739 public:
8740 explicit SafeForTerminationScope(v8::Isolate* isolate);
8741 ~SafeForTerminationScope();
8742
8743 // Prevent copying of Scope objects.
8744 SafeForTerminationScope(const SafeForTerminationScope&) = delete;
8745 SafeForTerminationScope& operator=(const SafeForTerminationScope&) = delete;
8746
8747 private:
8748 internal::Isolate* isolate_;
8749 bool prev_value_;
8750 };
8751
8752 /**
8753 * Types of garbage collections that can be requested via
8754 * RequestGarbageCollectionForTesting.
8755 */
8756 enum GarbageCollectionType {
8757 kFullGarbageCollection,
8758 kMinorGarbageCollection
8759 };
8760
8761 /**
8762 * Features reported via the SetUseCounterCallback callback. Do not change
8763 * assigned numbers of existing items; add new features to the end of this
8764 * list.
8765 */
8766 enum UseCounterFeature {
8767 kUseAsm = 0,
8768 kBreakIterator = 1,
8769 kLegacyConst = 2,
8770 kMarkDequeOverflow = 3,
8771 kStoreBufferOverflow = 4,
8772 kSlotsBufferOverflow = 5,
8773 kObjectObserve = 6,
8774 kForcedGC = 7,
8775 kSloppyMode = 8,
8776 kStrictMode = 9,
8777 kStrongMode = 10,
8778 kRegExpPrototypeStickyGetter = 11,
8779 kRegExpPrototypeToString = 12,
8780 kRegExpPrototypeUnicodeGetter = 13,
8781 kIntlV8Parse = 14,
8782 kIntlPattern = 15,
8783 kIntlResolved = 16,
8784 kPromiseChain = 17,
8785 kPromiseAccept = 18,
8786 kPromiseDefer = 19,
8787 kHtmlCommentInExternalScript = 20,
8788 kHtmlComment = 21,
8789 kSloppyModeBlockScopedFunctionRedefinition = 22,
8790 kForInInitializer = 23,
8791 kArrayProtectorDirtied = 24,
8792 kArraySpeciesModified = 25,
8793 kArrayPrototypeConstructorModified = 26,
8794 kArrayInstanceProtoModified = 27,
8795 kArrayInstanceConstructorModified = 28,
8796 kLegacyFunctionDeclaration = 29,
8797 kRegExpPrototypeSourceGetter = 30, // Unused.
8798 kRegExpPrototypeOldFlagGetter = 31, // Unused.
8799 kDecimalWithLeadingZeroInStrictMode = 32,
8800 kLegacyDateParser = 33,
8801 kDefineGetterOrSetterWouldThrow = 34,
8802 kFunctionConstructorReturnedUndefined = 35,
8803 kAssigmentExpressionLHSIsCallInSloppy = 36,
8804 kAssigmentExpressionLHSIsCallInStrict = 37,
8805 kPromiseConstructorReturnedUndefined = 38,
8806 kConstructorNonUndefinedPrimitiveReturn = 39,
8807 kLabeledExpressionStatement = 40,
8808 kLineOrParagraphSeparatorAsLineTerminator = 41,
8809 kIndexAccessor = 42,
8810 kErrorCaptureStackTrace = 43,
8811 kErrorPrepareStackTrace = 44,
8812 kErrorStackTraceLimit = 45,
8813 kWebAssemblyInstantiation = 46,
8814 kDeoptimizerDisableSpeculation = 47,
8815 kArrayPrototypeSortJSArrayModifiedPrototype = 48,
8816 kFunctionTokenOffsetTooLongForToString = 49,
8817 kWasmSharedMemory = 50,
8818 kWasmThreadOpcodes = 51,
8819 kAtomicsNotify = 52, // Unused.
8820 kAtomicsWake = 53, // Unused.
8821 kCollator = 54,
8822 kNumberFormat = 55,
8823 kDateTimeFormat = 56,
8824 kPluralRules = 57,
8825 kRelativeTimeFormat = 58,
8826 kLocale = 59,
8827 kListFormat = 60,
8828 kSegmenter = 61,
8829 kStringLocaleCompare = 62,
8830 kStringToLocaleUpperCase = 63,
8831 kStringToLocaleLowerCase = 64,
8832 kNumberToLocaleString = 65,
8833 kDateToLocaleString = 66,
8834 kDateToLocaleDateString = 67,
8835 kDateToLocaleTimeString = 68,
8836 kAttemptOverrideReadOnlyOnPrototypeSloppy = 69,
8837 kAttemptOverrideReadOnlyOnPrototypeStrict = 70,
8838 kOptimizedFunctionWithOneShotBytecode = 71, // Unused.
8839 kRegExpMatchIsTrueishOnNonJSRegExp = 72,
8840 kRegExpMatchIsFalseishOnJSRegExp = 73,
8841 kDateGetTimezoneOffset = 74, // Unused.
8842 kStringNormalize = 75,
8843 kCallSiteAPIGetFunctionSloppyCall = 76,
8844 kCallSiteAPIGetThisSloppyCall = 77,
8845 kRegExpMatchAllWithNonGlobalRegExp = 78,
8846 kRegExpExecCalledOnSlowRegExp = 79,
8847 kRegExpReplaceCalledOnSlowRegExp = 80,
8848 kDisplayNames = 81,
8849 kSharedArrayBufferConstructed = 82,
8850 kArrayPrototypeHasElements = 83,
8851 kObjectPrototypeHasElements = 84,
8852 kNumberFormatStyleUnit = 85,
8853 kDateTimeFormatRange = 86,
8854 kDateTimeFormatDateTimeStyle = 87,
8855 kBreakIteratorTypeWord = 88,
8856 kBreakIteratorTypeLine = 89,
8857 kInvalidatedArrayBufferDetachingProtector = 90,
8858 kInvalidatedArrayConstructorProtector = 91,
8859 kInvalidatedArrayIteratorLookupChainProtector = 92,
8860 kInvalidatedArraySpeciesLookupChainProtector = 93,
8861 kInvalidatedIsConcatSpreadableLookupChainProtector = 94,
8862 kInvalidatedMapIteratorLookupChainProtector = 95,
8863 kInvalidatedNoElementsProtector = 96,
8864 kInvalidatedPromiseHookProtector = 97,
8865 kInvalidatedPromiseResolveLookupChainProtector = 98,
8866 kInvalidatedPromiseSpeciesLookupChainProtector = 99,
8867 kInvalidatedPromiseThenLookupChainProtector = 100,
8868 kInvalidatedRegExpSpeciesLookupChainProtector = 101,
8869 kInvalidatedSetIteratorLookupChainProtector = 102,
8870 kInvalidatedStringIteratorLookupChainProtector = 103,
8871 kInvalidatedStringLengthOverflowLookupChainProtector = 104,
8872 kInvalidatedTypedArraySpeciesLookupChainProtector = 105,
8873 kWasmSimdOpcodes = 106,
8874 kVarRedeclaredCatchBinding = 107,
8875 kWasmRefTypes = 108,
8876 kWasmBulkMemory = 109, // Unused.
8877 kWasmMultiValue = 110,
8878 kWasmExceptionHandling = 111,
8879 kInvalidatedMegaDOMProtector = 112,
8880
8881 // If you add new values here, you'll also need to update Chromium's:
8882 // web_feature.mojom, use_counter_callback.cc, and enums.xml. V8 changes to
8883 // this list need to be landed first, then changes on the Chromium side.
8884 kUseCounterFeatureCount // This enum value must be last.
8885 };
8886
8887 enum MessageErrorLevel {
8888 kMessageLog = (1 << 0),
8889 kMessageDebug = (1 << 1),
8890 kMessageInfo = (1 << 2),
8891 kMessageError = (1 << 3),
8892 kMessageWarning = (1 << 4),
8893 kMessageAll = kMessageLog | kMessageDebug | kMessageInfo | kMessageError |
8894 kMessageWarning,
8895 };
8896
8897 using UseCounterCallback = void (*)(Isolate* isolate,
8898 UseCounterFeature feature);
8899
8900 /**
8901 * Allocates a new isolate but does not initialize it. Does not change the
8902 * currently entered isolate.
8903 *
8904 * Only Isolate::GetData() and Isolate::SetData(), which access the
8905 * embedder-controlled parts of the isolate, are allowed to be called on the
8906 * uninitialized isolate. To initialize the isolate, call
8907 * Isolate::Initialize().
8908 *
8909 * When an isolate is no longer used its resources should be freed
8910 * by calling Dispose(). Using the delete operator is not allowed.
8911 *
8912 * V8::Initialize() must have run prior to this.
8913 */
8914 static Isolate* Allocate();
8915
8916 /**
8917 * Initialize an Isolate previously allocated by Isolate::Allocate().
8918 */
8919 static void Initialize(Isolate* isolate, const CreateParams& params);
8920
8921 /**
8922 * Creates a new isolate. Does not change the currently entered
8923 * isolate.
8924 *
8925 * When an isolate is no longer used its resources should be freed
8926 * by calling Dispose(). Using the delete operator is not allowed.
8927 *
8928 * V8::Initialize() must have run prior to this.
8929 */
8930 static Isolate* New(const CreateParams& params);
8931
8932 /**
8933 * Returns the entered isolate for the current thread or NULL in
8934 * case there is no current isolate.
8935 *
8936 * This method must not be invoked before V8::Initialize() was invoked.
8937 */
8938 static Isolate* GetCurrent();
8939
8940 /**
8941 * Returns the entered isolate for the current thread or NULL in
8942 * case there is no current isolate.
8943 *
8944 * No checks are performed by this method.
8945 */
8946 static Isolate* TryGetCurrent();
8947
8948 /**
8949 * Clears the set of objects held strongly by the heap. This set of
8950 * objects are originally built when a WeakRef is created or
8951 * successfully dereferenced.
8952 *
8953 * This is invoked automatically after microtasks are run. See
8954 * MicrotasksPolicy for when microtasks are run.
8955 *
8956 * This needs to be manually invoked only if the embedder is manually running
8957 * microtasks via a custom MicrotaskQueue class's PerformCheckpoint. In that
8958 * case, it is the embedder's responsibility to make this call at a time which
8959 * does not interrupt synchronous ECMAScript code execution.
8960 */
8961 void ClearKeptObjects();
8962
8963 /**
8964 * Custom callback used by embedders to help V8 determine if it should abort
8965 * when it throws and no internal handler is predicted to catch the
8966 * exception. If --abort-on-uncaught-exception is used on the command line,
8967 * then V8 will abort if either:
8968 * - no custom callback is set.
8969 * - the custom callback set returns true.
8970 * Otherwise, the custom callback will not be called and V8 will not abort.
8971 */
8972 using AbortOnUncaughtExceptionCallback = bool (*)(Isolate*);
8973 void SetAbortOnUncaughtExceptionCallback(
8974 AbortOnUncaughtExceptionCallback callback);
8975
8976 /**
8977 * This specifies the callback called by the upcoming dynamic
8978 * import() language feature to load modules.
8979 */
8980 V8_DEPRECATED(
8981 "Use the version of SetHostImportModuleDynamicallyCallback that takes a "
8982 "HostImportModuleDynamicallyWithImportAssertionsCallback instead")
8983 void SetHostImportModuleDynamicallyCallback(
8984 HostImportModuleDynamicallyCallback callback);
8985
8986 /**
8987 * This specifies the callback called by the upcoming dynamic
8988 * import() language feature to load modules.
8989 */
8990 void SetHostImportModuleDynamicallyCallback(
8991 HostImportModuleDynamicallyWithImportAssertionsCallback callback);
8992
8993 /**
8994 * This specifies the callback called by the upcoming import.meta
8995 * language feature to retrieve host-defined meta data for a module.
8996 */
8997 void SetHostInitializeImportMetaObjectCallback(
8998 HostInitializeImportMetaObjectCallback callback);
8999
9000 /**
9001 * This specifies the callback called when the stack property of Error
9002 * is accessed.
9003 */
9004 void SetPrepareStackTraceCallback(PrepareStackTraceCallback callback);
9005
9006 /**
9007 * Optional notification that the system is running low on memory.
9008 * V8 uses these notifications to guide heuristics.
9009 * It is allowed to call this function from another thread while
9010 * the isolate is executing long running JavaScript code.
9011 */
9012 void MemoryPressureNotification(MemoryPressureLevel level);
9013
9014 /**
9015 * Drop non-essential caches. Should only be called from testing code.
9016 * The method can potentially block for a long time and does not necessarily
9017 * trigger GC.
9018 */
9019 void ClearCachesForTesting();
9020
9021 /**
9022 * Methods below this point require holding a lock (using Locker) in
9023 * a multi-threaded environment.
9024 */
9025
9026 /**
9027 * Sets this isolate as the entered one for the current thread.
9028 * Saves the previously entered one (if any), so that it can be
9029 * restored when exiting. Re-entering an isolate is allowed.
9030 */
9031 void Enter();
9032
9033 /**
9034 * Exits this isolate by restoring the previously entered one in the
9035 * current thread. The isolate may still stay the same, if it was
9036 * entered more than once.
9037 *
9038 * Requires: this == Isolate::GetCurrent().
9039 */
9040 void Exit();
9041
9042 /**
9043 * Disposes the isolate. The isolate must not be entered by any
9044 * thread to be disposable.
9045 */
9046 void Dispose();
9047
9048 /**
9049 * Dumps activated low-level V8 internal stats. This can be used instead
9050 * of performing a full isolate disposal.
9051 */
9052 void DumpAndResetStats();
9053
9054 /**
9055 * Discards all V8 thread-specific data for the Isolate. Should be used
9056 * if a thread is terminating and it has used an Isolate that will outlive
9057 * the thread -- all thread-specific data for an Isolate is discarded when
9058 * an Isolate is disposed so this call is pointless if an Isolate is about
9059 * to be Disposed.
9060 */
9061 void DiscardThreadSpecificMetadata();
9062
9063 /**
9064 * Associate embedder-specific data with the isolate. |slot| has to be
9065 * between 0 and GetNumberOfDataSlots() - 1.
9066 */
9067 V8_INLINE void SetData(uint32_t slot, void* data);
9068
9069 /**
9070 * Retrieve embedder-specific data from the isolate.
9071 * Returns NULL if SetData has never been called for the given |slot|.
9072 */
9073 V8_INLINE void* GetData(uint32_t slot);
9074
9075 /**
9076 * Returns the maximum number of available embedder data slots. Valid slots
9077 * are in the range of 0 - GetNumberOfDataSlots() - 1.
9078 */
9079 V8_INLINE static uint32_t GetNumberOfDataSlots();
9080
9081 /**
9082 * Return data that was previously attached to the isolate snapshot via
9083 * SnapshotCreator, and removes the reference to it.
9084 * Repeated call with the same index returns an empty MaybeLocal.
9085 */
9086 template <class T>
9087 V8_INLINE MaybeLocal<T> GetDataFromSnapshotOnce(size_t index);
9088
9089 /**
9090 * Get statistics about the heap memory usage.
9091 */
9092 void GetHeapStatistics(HeapStatistics* heap_statistics);
9093
9094 /**
9095 * Returns the number of spaces in the heap.
9096 */
9097 size_t NumberOfHeapSpaces();
9098
9099 /**
9100 * Get the memory usage of a space in the heap.
9101 *
9102 * \param space_statistics The HeapSpaceStatistics object to fill in
9103 * statistics.
9104 * \param index The index of the space to get statistics from, which ranges
9105 * from 0 to NumberOfHeapSpaces() - 1.
9106 * \returns true on success.
9107 */
9108 bool GetHeapSpaceStatistics(HeapSpaceStatistics* space_statistics,
9109 size_t index);
9110
9111 /**
9112 * Returns the number of types of objects tracked in the heap at GC.
9113 */
9114 size_t NumberOfTrackedHeapObjectTypes();
9115
9116 /**
9117 * Get statistics about objects in the heap.
9118 *
9119 * \param object_statistics The HeapObjectStatistics object to fill in
9120 * statistics of objects of given type, which were live in the previous GC.
9121 * \param type_index The index of the type of object to fill details about,
9122 * which ranges from 0 to NumberOfTrackedHeapObjectTypes() - 1.
9123 * \returns true on success.
9124 */
9125 bool GetHeapObjectStatisticsAtLastGC(HeapObjectStatistics* object_statistics,
9126 size_t type_index);
9127
9128 /**
9129 * Get statistics about code and its metadata in the heap.
9130 *
9131 * \param object_statistics The HeapCodeStatistics object to fill in
9132 * statistics of code, bytecode and their metadata.
9133 * \returns true on success.
9134 */
9135 bool GetHeapCodeAndMetadataStatistics(HeapCodeStatistics* object_statistics);
9136
9137 /**
9138 * This API is experimental and may change significantly.
9139 *
9140 * Enqueues a memory measurement request and invokes the delegate with the
9141 * results.
9142 *
9143 * \param delegate the delegate that defines which contexts to measure and
9144 * reports the results.
9145 *
9146 * \param execution promptness executing the memory measurement.
9147 * The kEager value is expected to be used only in tests.
9148 */
9149 bool MeasureMemory(
9150 std::unique_ptr<MeasureMemoryDelegate> delegate,
9151 MeasureMemoryExecution execution = MeasureMemoryExecution::kDefault);
9152
9153 V8_DEPRECATED("Use the version with a delegate")
9154 MaybeLocal<Promise> MeasureMemory(Local<Context> context,
9155 MeasureMemoryMode mode);
9156
9157 /**
9158 * Get a call stack sample from the isolate.
9159 * \param state Execution state.
9160 * \param frames Caller allocated buffer to store stack frames.
9161 * \param frames_limit Maximum number of frames to capture. The buffer must
9162 * be large enough to hold the number of frames.
9163 * \param sample_info The sample info is filled up by the function
9164 * provides number of actual captured stack frames and
9165 * the current VM state.
9166 * \note GetStackSample should only be called when the JS thread is paused or
9167 * interrupted. Otherwise the behavior is undefined.
9168 */
9169 void GetStackSample(const RegisterState& state, void** frames,
9170 size_t frames_limit, SampleInfo* sample_info);
9171
9172 /**
9173 * Adjusts the amount of registered external memory. Used to give V8 an
9174 * indication of the amount of externally allocated memory that is kept alive
9175 * by JavaScript objects. V8 uses this to decide when to perform global
9176 * garbage collections. Registering externally allocated memory will trigger
9177 * global garbage collections more often than it would otherwise in an attempt
9178 * to garbage collect the JavaScript objects that keep the externally
9179 * allocated memory alive.
9180 *
9181 * \param change_in_bytes the change in externally allocated memory that is
9182 * kept alive by JavaScript objects.
9183 * \returns the adjusted value.
9184 */
9185 int64_t AdjustAmountOfExternalAllocatedMemory(int64_t change_in_bytes);
9186
9187 /**
9188 * Returns the number of phantom handles without callbacks that were reset
9189 * by the garbage collector since the last call to this function.
9190 */
9191 size_t NumberOfPhantomHandleResetsSinceLastCall();
9192
9193 /**
9194 * Returns heap profiler for this isolate. Will return NULL until the isolate
9195 * is initialized.
9196 */
9197 HeapProfiler* GetHeapProfiler();
9198
9199 /**
9200 * Tells the VM whether the embedder is idle or not.
9201 */
9202 void SetIdle(bool is_idle);
9203
9204 /** Returns the ArrayBuffer::Allocator used in this isolate. */
9205 ArrayBuffer::Allocator* GetArrayBufferAllocator();
9206
9207 /** Returns true if this isolate has a current context. */
9208 bool InContext();
9209
9210 /**
9211 * Returns the context of the currently running JavaScript, or the context
9212 * on the top of the stack if no JavaScript is running.
9213 */
9214 Local<Context> GetCurrentContext();
9215
9216 /**
9217 * Returns either the last context entered through V8's C++ API, or the
9218 * context of the currently running microtask while processing microtasks.
9219 * If a context is entered while executing a microtask, that context is
9220 * returned.
9221 */
9222 Local<Context> GetEnteredOrMicrotaskContext();
9223
9224 /**
9225 * Returns the Context that corresponds to the Incumbent realm in HTML spec.
9226 * https://html.spec.whatwg.org/multipage/webappapis.html#incumbent
9227 */
9228 Local<Context> GetIncumbentContext();
9229
9230 /**
9231 * Schedules a v8::Exception::Error with the given message.
9232 * See ThrowException for more details. Templatized to provide compile-time
9233 * errors in case of too long strings (see v8::String::NewFromUtf8Literal).
9234 */
9235 template <int N>
ThrowError(const char (& message)[N])9236 Local<Value> ThrowError(const char (&message)[N]) {
9237 return ThrowError(String::NewFromUtf8Literal(this, message));
9238 }
9239 Local<Value> ThrowError(Local<String> message);
9240
9241 /**
9242 * Schedules an exception to be thrown when returning to JavaScript. When an
9243 * exception has been scheduled it is illegal to invoke any JavaScript
9244 * operation; the caller must return immediately and only after the exception
9245 * has been handled does it become legal to invoke JavaScript operations.
9246 */
9247 Local<Value> ThrowException(Local<Value> exception);
9248
9249 using GCCallback = void (*)(Isolate* isolate, GCType type,
9250 GCCallbackFlags flags);
9251 using GCCallbackWithData = void (*)(Isolate* isolate, GCType type,
9252 GCCallbackFlags flags, void* data);
9253
9254 /**
9255 * Enables the host application to receive a notification before a
9256 * garbage collection. Allocations are allowed in the callback function,
9257 * but the callback is not re-entrant: if the allocation inside it will
9258 * trigger the garbage collection, the callback won't be called again.
9259 * It is possible to specify the GCType filter for your callback. But it is
9260 * not possible to register the same callback function two times with
9261 * different GCType filters.
9262 */
9263 void AddGCPrologueCallback(GCCallbackWithData callback, void* data = nullptr,
9264 GCType gc_type_filter = kGCTypeAll);
9265 void AddGCPrologueCallback(GCCallback callback,
9266 GCType gc_type_filter = kGCTypeAll);
9267
9268 /**
9269 * This function removes callback which was installed by
9270 * AddGCPrologueCallback function.
9271 */
9272 void RemoveGCPrologueCallback(GCCallbackWithData, void* data = nullptr);
9273 void RemoveGCPrologueCallback(GCCallback callback);
9274
9275 /**
9276 * Sets the embedder heap tracer for the isolate.
9277 */
9278 void SetEmbedderHeapTracer(EmbedderHeapTracer* tracer);
9279
9280 /*
9281 * Gets the currently active heap tracer for the isolate.
9282 */
9283 EmbedderHeapTracer* GetEmbedderHeapTracer();
9284
9285 /**
9286 * Sets an embedder roots handle that V8 should consider when performing
9287 * non-unified heap garbage collections.
9288 *
9289 * Using only EmbedderHeapTracer automatically sets up a default handler.
9290 * The intended use case is for setting a custom handler after invoking
9291 * `AttachCppHeap()`.
9292 *
9293 * V8 does not take ownership of the handler.
9294 */
9295 void SetEmbedderRootsHandler(EmbedderRootsHandler* handler);
9296
9297 /**
9298 * Attaches a managed C++ heap as an extension to the JavaScript heap. The
9299 * embedder maintains ownership of the CppHeap. At most one C++ heap can be
9300 * attached to V8.
9301 *
9302 * This is an experimental feature and may still change significantly.
9303 */
9304 void AttachCppHeap(CppHeap*);
9305
9306 /**
9307 * Detaches a managed C++ heap if one was attached using `AttachCppHeap()`.
9308 *
9309 * This is an experimental feature and may still change significantly.
9310 */
9311 void DetachCppHeap();
9312
9313 /**
9314 * This is an experimental feature and may still change significantly.
9315
9316 * \returns the C++ heap managed by V8. Only available if such a heap has been
9317 * attached using `AttachCppHeap()`.
9318 */
9319 CppHeap* GetCppHeap() const;
9320
9321 /**
9322 * Use for |AtomicsWaitCallback| to indicate the type of event it receives.
9323 */
9324 enum class AtomicsWaitEvent {
9325 /** Indicates that this call is happening before waiting. */
9326 kStartWait,
9327 /** `Atomics.wait()` finished because of an `Atomics.wake()` call. */
9328 kWokenUp,
9329 /** `Atomics.wait()` finished because it timed out. */
9330 kTimedOut,
9331 /** `Atomics.wait()` was interrupted through |TerminateExecution()|. */
9332 kTerminatedExecution,
9333 /** `Atomics.wait()` was stopped through |AtomicsWaitWakeHandle|. */
9334 kAPIStopped,
9335 /** `Atomics.wait()` did not wait, as the initial condition was not met. */
9336 kNotEqual
9337 };
9338
9339 /**
9340 * Passed to |AtomicsWaitCallback| as a means of stopping an ongoing
9341 * `Atomics.wait` call.
9342 */
9343 class V8_EXPORT AtomicsWaitWakeHandle {
9344 public:
9345 /**
9346 * Stop this `Atomics.wait()` call and call the |AtomicsWaitCallback|
9347 * with |kAPIStopped|.
9348 *
9349 * This function may be called from another thread. The caller has to ensure
9350 * through proper synchronization that it is not called after
9351 * the finishing |AtomicsWaitCallback|.
9352 *
9353 * Note that the ECMAScript specification does not plan for the possibility
9354 * of wakeups that are neither coming from a timeout or an `Atomics.wake()`
9355 * call, so this may invalidate assumptions made by existing code.
9356 * The embedder may accordingly wish to schedule an exception in the
9357 * finishing |AtomicsWaitCallback|.
9358 */
9359 void Wake();
9360 };
9361
9362 /**
9363 * Embedder callback for `Atomics.wait()` that can be added through
9364 * |SetAtomicsWaitCallback|.
9365 *
9366 * This will be called just before starting to wait with the |event| value
9367 * |kStartWait| and after finishing waiting with one of the other
9368 * values of |AtomicsWaitEvent| inside of an `Atomics.wait()` call.
9369 *
9370 * |array_buffer| will refer to the underlying SharedArrayBuffer,
9371 * |offset_in_bytes| to the location of the waited-on memory address inside
9372 * the SharedArrayBuffer.
9373 *
9374 * |value| and |timeout_in_ms| will be the values passed to
9375 * the `Atomics.wait()` call. If no timeout was used, |timeout_in_ms|
9376 * will be `INFINITY`.
9377 *
9378 * In the |kStartWait| callback, |stop_handle| will be an object that
9379 * is only valid until the corresponding finishing callback and that
9380 * can be used to stop the wait process while it is happening.
9381 *
9382 * This callback may schedule exceptions, *unless* |event| is equal to
9383 * |kTerminatedExecution|.
9384 */
9385 using AtomicsWaitCallback = void (*)(AtomicsWaitEvent event,
9386 Local<SharedArrayBuffer> array_buffer,
9387 size_t offset_in_bytes, int64_t value,
9388 double timeout_in_ms,
9389 AtomicsWaitWakeHandle* stop_handle,
9390 void* data);
9391
9392 /**
9393 * Set a new |AtomicsWaitCallback|. This overrides an earlier
9394 * |AtomicsWaitCallback|, if there was any. If |callback| is nullptr,
9395 * this unsets the callback. |data| will be passed to the callback
9396 * as its last parameter.
9397 */
9398 void SetAtomicsWaitCallback(AtomicsWaitCallback callback, void* data);
9399
9400 /**
9401 * Enables the host application to receive a notification after a
9402 * garbage collection. Allocations are allowed in the callback function,
9403 * but the callback is not re-entrant: if the allocation inside it will
9404 * trigger the garbage collection, the callback won't be called again.
9405 * It is possible to specify the GCType filter for your callback. But it is
9406 * not possible to register the same callback function two times with
9407 * different GCType filters.
9408 */
9409 void AddGCEpilogueCallback(GCCallbackWithData callback, void* data = nullptr,
9410 GCType gc_type_filter = kGCTypeAll);
9411 void AddGCEpilogueCallback(GCCallback callback,
9412 GCType gc_type_filter = kGCTypeAll);
9413
9414 /**
9415 * This function removes callback which was installed by
9416 * AddGCEpilogueCallback function.
9417 */
9418 void RemoveGCEpilogueCallback(GCCallbackWithData callback,
9419 void* data = nullptr);
9420 void RemoveGCEpilogueCallback(GCCallback callback);
9421
9422 using GetExternallyAllocatedMemoryInBytesCallback = size_t (*)();
9423
9424 /**
9425 * Set the callback that tells V8 how much memory is currently allocated
9426 * externally of the V8 heap. Ideally this memory is somehow connected to V8
9427 * objects and may get freed-up when the corresponding V8 objects get
9428 * collected by a V8 garbage collection.
9429 */
9430 void SetGetExternallyAllocatedMemoryInBytesCallback(
9431 GetExternallyAllocatedMemoryInBytesCallback callback);
9432
9433 /**
9434 * Forcefully terminate the current thread of JavaScript execution
9435 * in the given isolate.
9436 *
9437 * This method can be used by any thread even if that thread has not
9438 * acquired the V8 lock with a Locker object.
9439 */
9440 void TerminateExecution();
9441
9442 /**
9443 * Is V8 terminating JavaScript execution.
9444 *
9445 * Returns true if JavaScript execution is currently terminating
9446 * because of a call to TerminateExecution. In that case there are
9447 * still JavaScript frames on the stack and the termination
9448 * exception is still active.
9449 */
9450 bool IsExecutionTerminating();
9451
9452 /**
9453 * Resume execution capability in the given isolate, whose execution
9454 * was previously forcefully terminated using TerminateExecution().
9455 *
9456 * When execution is forcefully terminated using TerminateExecution(),
9457 * the isolate can not resume execution until all JavaScript frames
9458 * have propagated the uncatchable exception which is generated. This
9459 * method allows the program embedding the engine to handle the
9460 * termination event and resume execution capability, even if
9461 * JavaScript frames remain on the stack.
9462 *
9463 * This method can be used by any thread even if that thread has not
9464 * acquired the V8 lock with a Locker object.
9465 */
9466 void CancelTerminateExecution();
9467
9468 /**
9469 * Request V8 to interrupt long running JavaScript code and invoke
9470 * the given |callback| passing the given |data| to it. After |callback|
9471 * returns control will be returned to the JavaScript code.
9472 * There may be a number of interrupt requests in flight.
9473 * Can be called from another thread without acquiring a |Locker|.
9474 * Registered |callback| must not reenter interrupted Isolate.
9475 */
9476 void RequestInterrupt(InterruptCallback callback, void* data);
9477
9478 /**
9479 * Returns true if there is ongoing background work within V8 that will
9480 * eventually post a foreground task, like asynchronous WebAssembly
9481 * compilation.
9482 */
9483 bool HasPendingBackgroundTasks();
9484
9485 /**
9486 * Request garbage collection in this Isolate. It is only valid to call this
9487 * function if --expose_gc was specified.
9488 *
9489 * This should only be used for testing purposes and not to enforce a garbage
9490 * collection schedule. It has strong negative impact on the garbage
9491 * collection performance. Use IdleNotificationDeadline() or
9492 * LowMemoryNotification() instead to influence the garbage collection
9493 * schedule.
9494 */
9495 void RequestGarbageCollectionForTesting(GarbageCollectionType type);
9496
9497 /**
9498 * Set the callback to invoke for logging event.
9499 */
9500 void SetEventLogger(LogEventCallback that);
9501
9502 /**
9503 * Adds a callback to notify the host application right before a script
9504 * is about to run. If a script re-enters the runtime during executing, the
9505 * BeforeCallEnteredCallback is invoked for each re-entrance.
9506 * Executing scripts inside the callback will re-trigger the callback.
9507 */
9508 void AddBeforeCallEnteredCallback(BeforeCallEnteredCallback callback);
9509
9510 /**
9511 * Removes callback that was installed by AddBeforeCallEnteredCallback.
9512 */
9513 void RemoveBeforeCallEnteredCallback(BeforeCallEnteredCallback callback);
9514
9515 /**
9516 * Adds a callback to notify the host application when a script finished
9517 * running. If a script re-enters the runtime during executing, the
9518 * CallCompletedCallback is only invoked when the outer-most script
9519 * execution ends. Executing scripts inside the callback do not trigger
9520 * further callbacks.
9521 */
9522 void AddCallCompletedCallback(CallCompletedCallback callback);
9523
9524 /**
9525 * Removes callback that was installed by AddCallCompletedCallback.
9526 */
9527 void RemoveCallCompletedCallback(CallCompletedCallback callback);
9528
9529 /**
9530 * Set the PromiseHook callback for various promise lifecycle
9531 * events.
9532 */
9533 void SetPromiseHook(PromiseHook hook);
9534
9535 /**
9536 * Set callback to notify about promise reject with no handler, or
9537 * revocation of such a previous notification once the handler is added.
9538 */
9539 void SetPromiseRejectCallback(PromiseRejectCallback callback);
9540
9541 /**
9542 * Runs the default MicrotaskQueue until it gets empty and perform other
9543 * microtask checkpoint steps, such as calling ClearKeptObjects. Asserts that
9544 * the MicrotasksPolicy is not kScoped. Any exceptions thrown by microtask
9545 * callbacks are swallowed.
9546 */
9547 void PerformMicrotaskCheckpoint();
9548
9549 /**
9550 * Enqueues the callback to the default MicrotaskQueue
9551 */
9552 void EnqueueMicrotask(Local<Function> microtask);
9553
9554 /**
9555 * Enqueues the callback to the default MicrotaskQueue
9556 */
9557 void EnqueueMicrotask(MicrotaskCallback callback, void* data = nullptr);
9558
9559 /**
9560 * Controls how Microtasks are invoked. See MicrotasksPolicy for details.
9561 */
9562 void SetMicrotasksPolicy(MicrotasksPolicy policy);
9563
9564 /**
9565 * Returns the policy controlling how Microtasks are invoked.
9566 */
9567 MicrotasksPolicy GetMicrotasksPolicy() const;
9568
9569 /**
9570 * Adds a callback to notify the host application after
9571 * microtasks were run on the default MicrotaskQueue. The callback is
9572 * triggered by explicit RunMicrotasks call or automatic microtasks execution
9573 * (see SetMicrotaskPolicy).
9574 *
9575 * Callback will trigger even if microtasks were attempted to run,
9576 * but the microtasks queue was empty and no single microtask was actually
9577 * executed.
9578 *
9579 * Executing scripts inside the callback will not re-trigger microtasks and
9580 * the callback.
9581 */
9582 void AddMicrotasksCompletedCallback(
9583 MicrotasksCompletedCallbackWithData callback, void* data = nullptr);
9584
9585 /**
9586 * Removes callback that was installed by AddMicrotasksCompletedCallback.
9587 */
9588 void RemoveMicrotasksCompletedCallback(
9589 MicrotasksCompletedCallbackWithData callback, void* data = nullptr);
9590
9591 /**
9592 * Sets a callback for counting the number of times a feature of V8 is used.
9593 */
9594 void SetUseCounterCallback(UseCounterCallback callback);
9595
9596 /**
9597 * Enables the host application to provide a mechanism for recording
9598 * statistics counters.
9599 */
9600 void SetCounterFunction(CounterLookupCallback);
9601
9602 /**
9603 * Enables the host application to provide a mechanism for recording
9604 * histograms. The CreateHistogram function returns a
9605 * histogram which will later be passed to the AddHistogramSample
9606 * function.
9607 */
9608 void SetCreateHistogramFunction(CreateHistogramCallback);
9609 void SetAddHistogramSampleFunction(AddHistogramSampleCallback);
9610
9611 /**
9612 * Enables the host application to provide a mechanism for recording
9613 * event based metrics. In order to use this interface
9614 * include/v8-metrics.h
9615 * needs to be included and the recorder needs to be derived from the
9616 * Recorder base class defined there.
9617 * This method can only be called once per isolate and must happen during
9618 * isolate initialization before background threads are spawned.
9619 */
9620 void SetMetricsRecorder(
9621 const std::shared_ptr<metrics::Recorder>& metrics_recorder);
9622
9623 /**
9624 * Enables the host application to provide a mechanism for recording a
9625 * predefined set of data as crash keys to be used in postmortem debugging in
9626 * case of a crash.
9627 */
9628 void SetAddCrashKeyCallback(AddCrashKeyCallback);
9629
9630 /**
9631 * Optional notification that the embedder is idle.
9632 * V8 uses the notification to perform garbage collection.
9633 * This call can be used repeatedly if the embedder remains idle.
9634 * Returns true if the embedder should stop calling IdleNotificationDeadline
9635 * until real work has been done. This indicates that V8 has done
9636 * as much cleanup as it will be able to do.
9637 *
9638 * The deadline_in_seconds argument specifies the deadline V8 has to finish
9639 * garbage collection work. deadline_in_seconds is compared with
9640 * MonotonicallyIncreasingTime() and should be based on the same timebase as
9641 * that function. There is no guarantee that the actual work will be done
9642 * within the time limit.
9643 */
9644 bool IdleNotificationDeadline(double deadline_in_seconds);
9645
9646 /**
9647 * Optional notification that the system is running low on memory.
9648 * V8 uses these notifications to attempt to free memory.
9649 */
9650 void LowMemoryNotification();
9651
9652 /**
9653 * Optional notification that a context has been disposed. V8 uses these
9654 * notifications to guide the GC heuristic and cancel FinalizationRegistry
9655 * cleanup tasks. Returns the number of context disposals - including this one
9656 * - since the last time V8 had a chance to clean up.
9657 *
9658 * The optional parameter |dependant_context| specifies whether the disposed
9659 * context was depending on state from other contexts or not.
9660 */
9661 int ContextDisposedNotification(bool dependant_context = true);
9662
9663 /**
9664 * Optional notification that the isolate switched to the foreground.
9665 * V8 uses these notifications to guide heuristics.
9666 */
9667 void IsolateInForegroundNotification();
9668
9669 /**
9670 * Optional notification that the isolate switched to the background.
9671 * V8 uses these notifications to guide heuristics.
9672 */
9673 void IsolateInBackgroundNotification();
9674
9675 /**
9676 * Optional notification which will enable the memory savings mode.
9677 * V8 uses this notification to guide heuristics which may result in a
9678 * smaller memory footprint at the cost of reduced runtime performance.
9679 */
9680 void EnableMemorySavingsMode();
9681
9682 /**
9683 * Optional notification which will disable the memory savings mode.
9684 */
9685 void DisableMemorySavingsMode();
9686
9687 /**
9688 * Optional notification to tell V8 the current performance requirements
9689 * of the embedder based on RAIL.
9690 * V8 uses these notifications to guide heuristics.
9691 * This is an unfinished experimental feature. Semantics and implementation
9692 * may change frequently.
9693 */
9694 void SetRAILMode(RAILMode rail_mode);
9695
9696 /**
9697 * Update load start time of the RAIL mode
9698 */
9699 void UpdateLoadStartTime();
9700
9701 /**
9702 * Optional notification to tell V8 the current isolate is used for debugging
9703 * and requires higher heap limit.
9704 */
9705 void IncreaseHeapLimitForDebugging();
9706
9707 /**
9708 * Restores the original heap limit after IncreaseHeapLimitForDebugging().
9709 */
9710 void RestoreOriginalHeapLimit();
9711
9712 /**
9713 * Returns true if the heap limit was increased for debugging and the
9714 * original heap limit was not restored yet.
9715 */
9716 bool IsHeapLimitIncreasedForDebugging();
9717
9718 /**
9719 * Allows the host application to provide the address of a function that is
9720 * notified each time code is added, moved or removed.
9721 *
9722 * \param options options for the JIT code event handler.
9723 * \param event_handler the JIT code event handler, which will be invoked
9724 * each time code is added, moved or removed.
9725 * \note \p event_handler won't get notified of existent code.
9726 * \note since code removal notifications are not currently issued, the
9727 * \p event_handler may get notifications of code that overlaps earlier
9728 * code notifications. This happens when code areas are reused, and the
9729 * earlier overlapping code areas should therefore be discarded.
9730 * \note the events passed to \p event_handler and the strings they point to
9731 * are not guaranteed to live past each call. The \p event_handler must
9732 * copy strings and other parameters it needs to keep around.
9733 * \note the set of events declared in JitCodeEvent::EventType is expected to
9734 * grow over time, and the JitCodeEvent structure is expected to accrue
9735 * new members. The \p event_handler function must ignore event codes
9736 * it does not recognize to maintain future compatibility.
9737 * \note Use Isolate::CreateParams to get events for code executed during
9738 * Isolate setup.
9739 */
9740 void SetJitCodeEventHandler(JitCodeEventOptions options,
9741 JitCodeEventHandler event_handler);
9742
9743 /**
9744 * Modifies the stack limit for this Isolate.
9745 *
9746 * \param stack_limit An address beyond which the Vm's stack may not grow.
9747 *
9748 * \note If you are using threads then you should hold the V8::Locker lock
9749 * while setting the stack limit and you must set a non-default stack
9750 * limit separately for each thread.
9751 */
9752 void SetStackLimit(uintptr_t stack_limit);
9753
9754 /**
9755 * Returns a memory range that can potentially contain jitted code. Code for
9756 * V8's 'builtins' will not be in this range if embedded builtins is enabled.
9757 *
9758 * On Win64, embedders are advised to install function table callbacks for
9759 * these ranges, as default SEH won't be able to unwind through jitted code.
9760 * The first page of the code range is reserved for the embedder and is
9761 * committed, writable, and executable, to be used to store unwind data, as
9762 * documented in
9763 * https://docs.microsoft.com/en-us/cpp/build/exception-handling-x64.
9764 *
9765 * Might be empty on other platforms.
9766 *
9767 * https://code.google.com/p/v8/issues/detail?id=3598
9768 */
9769 void GetCodeRange(void** start, size_t* length_in_bytes);
9770
9771 /**
9772 * As GetCodeRange, but for embedded builtins (these live in a distinct
9773 * memory region from other V8 Code objects).
9774 */
9775 void GetEmbeddedCodeRange(const void** start, size_t* length_in_bytes);
9776
9777 /**
9778 * Returns the JSEntryStubs necessary for use with the Unwinder API.
9779 */
9780 JSEntryStubs GetJSEntryStubs();
9781
9782 static constexpr size_t kMinCodePagesBufferSize = 32;
9783
9784 /**
9785 * Copies the code heap pages currently in use by V8 into |code_pages_out|.
9786 * |code_pages_out| must have at least kMinCodePagesBufferSize capacity and
9787 * must be empty.
9788 *
9789 * Signal-safe, does not allocate, does not access the V8 heap.
9790 * No code on the stack can rely on pages that might be missing.
9791 *
9792 * Returns the number of pages available to be copied, which might be greater
9793 * than |capacity|. In this case, only |capacity| pages will be copied into
9794 * |code_pages_out|. The caller should provide a bigger buffer on the next
9795 * call in order to get all available code pages, but this is not required.
9796 */
9797 size_t CopyCodePages(size_t capacity, MemoryRange* code_pages_out);
9798
9799 /** Set the callback to invoke in case of fatal errors. */
9800 void SetFatalErrorHandler(FatalErrorCallback that);
9801
9802 /** Set the callback to invoke in case of OOM errors. */
9803 void SetOOMErrorHandler(OOMErrorCallback that);
9804
9805 /**
9806 * Add a callback to invoke in case the heap size is close to the heap limit.
9807 * If multiple callbacks are added, only the most recently added callback is
9808 * invoked.
9809 */
9810 void AddNearHeapLimitCallback(NearHeapLimitCallback callback, void* data);
9811
9812 /**
9813 * Remove the given callback and restore the heap limit to the
9814 * given limit. If the given limit is zero, then it is ignored.
9815 * If the current heap size is greater than the given limit,
9816 * then the heap limit is restored to the minimal limit that
9817 * is possible for the current heap size.
9818 */
9819 void RemoveNearHeapLimitCallback(NearHeapLimitCallback callback,
9820 size_t heap_limit);
9821
9822 /**
9823 * If the heap limit was changed by the NearHeapLimitCallback, then the
9824 * initial heap limit will be restored once the heap size falls below the
9825 * given threshold percentage of the initial heap limit.
9826 * The threshold percentage is a number in (0.0, 1.0) range.
9827 */
9828 void AutomaticallyRestoreInitialHeapLimit(double threshold_percent = 0.5);
9829
9830 /**
9831 * Set the callback to invoke to check if code generation from
9832 * strings should be allowed.
9833 */
9834 V8_DEPRECATED(
9835 "Use Isolate::SetModifyCodeGenerationFromStringsCallback with "
9836 "ModifyCodeGenerationFromStringsCallback2 instead. See "
9837 "http://crbug.com/1096017 and TC39 Dynamic Code Brand Checks proposal "
9838 "at https://github.com/tc39/proposal-dynamic-code-brand-checks.")
9839 void SetModifyCodeGenerationFromStringsCallback(
9840 ModifyCodeGenerationFromStringsCallback callback);
9841 void SetModifyCodeGenerationFromStringsCallback(
9842 ModifyCodeGenerationFromStringsCallback2 callback);
9843
9844 /**
9845 * Set the callback to invoke to check if wasm code generation should
9846 * be allowed.
9847 */
9848 void SetAllowWasmCodeGenerationCallback(
9849 AllowWasmCodeGenerationCallback callback);
9850
9851 /**
9852 * Embedder over{ride|load} injection points for wasm APIs. The expectation
9853 * is that the embedder sets them at most once.
9854 */
9855 void SetWasmModuleCallback(ExtensionCallback callback);
9856 void SetWasmInstanceCallback(ExtensionCallback callback);
9857
9858 void SetWasmStreamingCallback(WasmStreamingCallback callback);
9859
9860 void SetWasmLoadSourceMapCallback(WasmLoadSourceMapCallback callback);
9861
9862 void SetWasmSimdEnabledCallback(WasmSimdEnabledCallback callback);
9863
9864 void SetWasmExceptionsEnabledCallback(WasmExceptionsEnabledCallback callback);
9865
9866 void SetSharedArrayBufferConstructorEnabledCallback(
9867 SharedArrayBufferConstructorEnabledCallback callback);
9868
9869 /**
9870 * This function can be called by the embedder to signal V8 that the dynamic
9871 * enabling of features has finished. V8 can now set up dynamically added
9872 * features.
9873 */
9874 void InstallConditionalFeatures(Local<Context> context);
9875
9876 /**
9877 * Check if V8 is dead and therefore unusable. This is the case after
9878 * fatal errors such as out-of-memory situations.
9879 */
9880 bool IsDead();
9881
9882 /**
9883 * Adds a message listener (errors only).
9884 *
9885 * The same message listener can be added more than once and in that
9886 * case it will be called more than once for each message.
9887 *
9888 * If data is specified, it will be passed to the callback when it is called.
9889 * Otherwise, the exception object will be passed to the callback instead.
9890 */
9891 bool AddMessageListener(MessageCallback that,
9892 Local<Value> data = Local<Value>());
9893
9894 /**
9895 * Adds a message listener.
9896 *
9897 * The same message listener can be added more than once and in that
9898 * case it will be called more than once for each message.
9899 *
9900 * If data is specified, it will be passed to the callback when it is called.
9901 * Otherwise, the exception object will be passed to the callback instead.
9902 *
9903 * A listener can listen for particular error levels by providing a mask.
9904 */
9905 bool AddMessageListenerWithErrorLevel(MessageCallback that,
9906 int message_levels,
9907 Local<Value> data = Local<Value>());
9908
9909 /**
9910 * Remove all message listeners from the specified callback function.
9911 */
9912 void RemoveMessageListeners(MessageCallback that);
9913
9914 /** Callback function for reporting failed access checks.*/
9915 void SetFailedAccessCheckCallbackFunction(FailedAccessCheckCallback);
9916
9917 /**
9918 * Tells V8 to capture current stack trace when uncaught exception occurs
9919 * and report it to the message listeners. The option is off by default.
9920 */
9921 void SetCaptureStackTraceForUncaughtExceptions(
9922 bool capture, int frame_limit = 10,
9923 StackTrace::StackTraceOptions options = StackTrace::kOverview);
9924
9925 /**
9926 * Iterates through all external resources referenced from current isolate
9927 * heap. GC is not invoked prior to iterating, therefore there is no
9928 * guarantee that visited objects are still alive.
9929 */
9930 void VisitExternalResources(ExternalResourceVisitor* visitor);
9931
9932 /**
9933 * Iterates through all the persistent handles in the current isolate's heap
9934 * that have class_ids.
9935 */
9936 void VisitHandlesWithClassIds(PersistentHandleVisitor* visitor);
9937
9938 /**
9939 * Iterates through all the persistent handles in the current isolate's heap
9940 * that have class_ids and are weak to be marked as inactive if there is no
9941 * pending activity for the handle.
9942 */
9943 void VisitWeakHandles(PersistentHandleVisitor* visitor);
9944
9945 /**
9946 * Check if this isolate is in use.
9947 * True if at least one thread Enter'ed this isolate.
9948 */
9949 bool IsInUse();
9950
9951 /**
9952 * Set whether calling Atomics.wait (a function that may block) is allowed in
9953 * this isolate. This can also be configured via
9954 * CreateParams::allow_atomics_wait.
9955 */
9956 void SetAllowAtomicsWait(bool allow);
9957
9958 /**
9959 * Time zone redetection indicator for
9960 * DateTimeConfigurationChangeNotification.
9961 *
9962 * kSkip indicates V8 that the notification should not trigger redetecting
9963 * host time zone. kRedetect indicates V8 that host time zone should be
9964 * redetected, and used to set the default time zone.
9965 *
9966 * The host time zone detection may require file system access or similar
9967 * operations unlikely to be available inside a sandbox. If v8 is run inside a
9968 * sandbox, the host time zone has to be detected outside the sandbox before
9969 * calling DateTimeConfigurationChangeNotification function.
9970 */
9971 enum class TimeZoneDetection { kSkip, kRedetect };
9972
9973 /**
9974 * Notification that the embedder has changed the time zone, daylight savings
9975 * time or other date / time configuration parameters. V8 keeps a cache of
9976 * various values used for date / time computation. This notification will
9977 * reset those cached values for the current context so that date / time
9978 * configuration changes would be reflected.
9979 *
9980 * This API should not be called more than needed as it will negatively impact
9981 * the performance of date operations.
9982 */
9983 void DateTimeConfigurationChangeNotification(
9984 TimeZoneDetection time_zone_detection = TimeZoneDetection::kSkip);
9985
9986 /**
9987 * Notification that the embedder has changed the locale. V8 keeps a cache of
9988 * various values used for locale computation. This notification will reset
9989 * those cached values for the current context so that locale configuration
9990 * changes would be reflected.
9991 *
9992 * This API should not be called more than needed as it will negatively impact
9993 * the performance of locale operations.
9994 */
9995 void LocaleConfigurationChangeNotification();
9996
9997 Isolate() = delete;
9998 ~Isolate() = delete;
9999 Isolate(const Isolate&) = delete;
10000 Isolate& operator=(const Isolate&) = delete;
10001 // Deleting operator new and delete here is allowed as ctor and dtor is also
10002 // deleted.
10003 void* operator new(size_t size) = delete;
10004 void* operator new[](size_t size) = delete;
10005 void operator delete(void*, size_t) = delete;
10006 void operator delete[](void*, size_t) = delete;
10007
10008 private:
10009 template <class K, class V, class Traits>
10010 friend class PersistentValueMapBase;
10011
10012 internal::Address* GetDataFromSnapshotOnce(size_t index);
10013 void ReportExternalAllocationLimitReached();
10014 };
10015
10016 class V8_EXPORT StartupData {
10017 public:
10018 /**
10019 * Whether the data created can be rehashed and and the hash seed can be
10020 * recomputed when deserialized.
10021 * Only valid for StartupData returned by SnapshotCreator::CreateBlob().
10022 */
10023 bool CanBeRehashed() const;
10024 /**
10025 * Allows embedders to verify whether the data is valid for the current
10026 * V8 instance.
10027 */
10028 bool IsValid() const;
10029
10030 const char* data;
10031 int raw_size;
10032 };
10033
10034 /**
10035 * EntropySource is used as a callback function when v8 needs a source
10036 * of entropy.
10037 */
10038 using EntropySource = bool (*)(unsigned char* buffer, size_t length);
10039
10040 /**
10041 * ReturnAddressLocationResolver is used as a callback function when v8 is
10042 * resolving the location of a return address on the stack. Profilers that
10043 * change the return address on the stack can use this to resolve the stack
10044 * location to wherever the profiler stashed the original return address.
10045 *
10046 * \param return_addr_location A location on stack where a machine
10047 * return address resides.
10048 * \returns Either return_addr_location, or else a pointer to the profiler's
10049 * copy of the original return address.
10050 *
10051 * \note The resolver function must not cause garbage collection.
10052 */
10053 using ReturnAddressLocationResolver =
10054 uintptr_t (*)(uintptr_t return_addr_location);
10055
10056 /**
10057 * Container class for static utility functions.
10058 */
10059 class V8_EXPORT V8 {
10060 public:
10061 /**
10062 * Hand startup data to V8, in case the embedder has chosen to build
10063 * V8 with external startup data.
10064 *
10065 * Note:
10066 * - By default the startup data is linked into the V8 library, in which
10067 * case this function is not meaningful.
10068 * - If this needs to be called, it needs to be called before V8
10069 * tries to make use of its built-ins.
10070 * - To avoid unnecessary copies of data, V8 will point directly into the
10071 * given data blob, so pretty please keep it around until V8 exit.
10072 * - Compression of the startup blob might be useful, but needs to
10073 * handled entirely on the embedders' side.
10074 * - The call will abort if the data is invalid.
10075 */
10076 static void SetSnapshotDataBlob(StartupData* startup_blob);
10077
10078 /** Set the callback to invoke in case of Dcheck failures. */
10079 static void SetDcheckErrorHandler(DcheckErrorCallback that);
10080
10081
10082 /**
10083 * Sets V8 flags from a string.
10084 */
10085 static void SetFlagsFromString(const char* str);
10086 static void SetFlagsFromString(const char* str, size_t length);
10087
10088 /**
10089 * Sets V8 flags from the command line.
10090 */
10091 static void SetFlagsFromCommandLine(int* argc,
10092 char** argv,
10093 bool remove_flags);
10094
10095 /** Get the version string. */
10096 static const char* GetVersion();
10097
10098 /**
10099 * Initializes V8. This function needs to be called before the first Isolate
10100 * is created. It always returns true.
10101 */
Initialize()10102 V8_INLINE static bool Initialize() {
10103 const int kBuildConfiguration =
10104 (internal::PointerCompressionIsEnabled() ? kPointerCompression : 0) |
10105 (internal::SmiValuesAre31Bits() ? k31BitSmis : 0) |
10106 (internal::HeapSandboxIsEnabled() ? kHeapSandbox : 0);
10107 return Initialize(kBuildConfiguration);
10108 }
10109
10110 /**
10111 * Allows the host application to provide a callback which can be used
10112 * as a source of entropy for random number generators.
10113 */
10114 static void SetEntropySource(EntropySource source);
10115
10116 /**
10117 * Allows the host application to provide a callback that allows v8 to
10118 * cooperate with a profiler that rewrites return addresses on stack.
10119 */
10120 static void SetReturnAddressLocationResolver(
10121 ReturnAddressLocationResolver return_address_resolver);
10122
10123 /**
10124 * Releases any resources used by v8 and stops any utility threads
10125 * that may be running. Note that disposing v8 is permanent, it
10126 * cannot be reinitialized.
10127 *
10128 * It should generally not be necessary to dispose v8 before exiting
10129 * a process, this should happen automatically. It is only necessary
10130 * to use if the process needs the resources taken up by v8.
10131 */
10132 static bool Dispose();
10133
10134 /**
10135 * Initialize the ICU library bundled with V8. The embedder should only
10136 * invoke this method when using the bundled ICU. Returns true on success.
10137 *
10138 * If V8 was compiled with the ICU data in an external file, the location
10139 * of the data file has to be provided.
10140 */
10141 static bool InitializeICU(const char* icu_data_file = nullptr);
10142
10143 /**
10144 * Initialize the ICU library bundled with V8. The embedder should only
10145 * invoke this method when using the bundled ICU. If V8 was compiled with
10146 * the ICU data in an external file and when the default location of that
10147 * file should be used, a path to the executable must be provided.
10148 * Returns true on success.
10149 *
10150 * The default is a file called icudtl.dat side-by-side with the executable.
10151 *
10152 * Optionally, the location of the data file can be provided to override the
10153 * default.
10154 */
10155 static bool InitializeICUDefaultLocation(const char* exec_path,
10156 const char* icu_data_file = nullptr);
10157
10158 /**
10159 * Initialize the external startup data. The embedder only needs to
10160 * invoke this method when external startup data was enabled in a build.
10161 *
10162 * If V8 was compiled with the startup data in an external file, then
10163 * V8 needs to be given those external files during startup. There are
10164 * three ways to do this:
10165 * - InitializeExternalStartupData(const char*)
10166 * This will look in the given directory for the file "snapshot_blob.bin".
10167 * - InitializeExternalStartupDataFromFile(const char*)
10168 * As above, but will directly use the given file name.
10169 * - Call SetSnapshotDataBlob.
10170 * This will read the blobs from the given data structure and will
10171 * not perform any file IO.
10172 */
10173 static void InitializeExternalStartupData(const char* directory_path);
10174 static void InitializeExternalStartupDataFromFile(const char* snapshot_blob);
10175
10176 /**
10177 * Sets the v8::Platform to use. This should be invoked before V8 is
10178 * initialized.
10179 */
10180 static void InitializePlatform(Platform* platform);
10181
10182 /**
10183 * Clears all references to the v8::Platform. This should be invoked after
10184 * V8 was disposed.
10185 */
10186 static void ShutdownPlatform();
10187
10188 #if V8_OS_POSIX
10189 /**
10190 * Give the V8 signal handler a chance to handle a fault.
10191 *
10192 * This function determines whether a memory access violation can be recovered
10193 * by V8. If so, it will return true and modify context to return to a code
10194 * fragment that can recover from the fault. Otherwise, TryHandleSignal will
10195 * return false.
10196 *
10197 * The parameters to this function correspond to those passed to a Linux
10198 * signal handler.
10199 *
10200 * \param signal_number The signal number.
10201 *
10202 * \param info A pointer to the siginfo_t structure provided to the signal
10203 * handler.
10204 *
10205 * \param context The third argument passed to the Linux signal handler, which
10206 * points to a ucontext_t structure.
10207 */
10208 V8_DEPRECATED("Use TryHandleWebAssemblyTrapPosix")
10209 static bool TryHandleSignal(int signal_number, void* info, void* context);
10210 #endif // V8_OS_POSIX
10211
10212 /**
10213 * Activate trap-based bounds checking for WebAssembly.
10214 *
10215 * \param use_v8_signal_handler Whether V8 should install its own signal
10216 * handler or rely on the embedder's.
10217 */
10218 static bool EnableWebAssemblyTrapHandler(bool use_v8_signal_handler);
10219
10220 #if defined(V8_OS_WIN)
10221 /**
10222 * On Win64, by default V8 does not emit unwinding data for jitted code,
10223 * which means the OS cannot walk the stack frames and the system Structured
10224 * Exception Handling (SEH) cannot unwind through V8-generated code:
10225 * https://code.google.com/p/v8/issues/detail?id=3598.
10226 *
10227 * This function allows embedders to register a custom exception handler for
10228 * exceptions in V8-generated code.
10229 */
10230 static void SetUnhandledExceptionCallback(
10231 UnhandledExceptionCallback unhandled_exception_callback);
10232 #endif
10233
10234 /**
10235 * Get statistics about the shared memory usage.
10236 */
10237 static void GetSharedMemoryStatistics(SharedMemoryStatistics* statistics);
10238
10239 /**
10240 * Notifies V8 that the process is cross-origin-isolated, which enables
10241 * defining the SharedArrayBuffer function on the global object of Contexts.
10242 */
10243 V8_DEPRECATED(
10244 "Use the command line argument --enable-sharedarraybuffer-per-context "
10245 "together with SetSharedArrayBufferConstructorEnabledCallback")
10246 static void SetIsCrossOriginIsolated();
10247
10248 private:
10249 V8();
10250
10251 enum BuildConfigurationFeatures {
10252 kPointerCompression = 1 << 0,
10253 k31BitSmis = 1 << 1,
10254 kHeapSandbox = 1 << 2,
10255 };
10256
10257 /**
10258 * Checks that the embedder build configuration is compatible with
10259 * the V8 binary and if so initializes V8.
10260 */
10261 static bool Initialize(int build_config);
10262
10263 static internal::Address* GlobalizeReference(internal::Isolate* isolate,
10264 internal::Address* handle);
10265 static internal::Address* GlobalizeTracedReference(internal::Isolate* isolate,
10266 internal::Address* handle,
10267 internal::Address* slot,
10268 bool has_destructor);
10269 static void MoveGlobalReference(internal::Address** from,
10270 internal::Address** to);
10271 static void MoveTracedGlobalReference(internal::Address** from,
10272 internal::Address** to);
10273 static void CopyTracedGlobalReference(const internal::Address* const* from,
10274 internal::Address** to);
10275 static internal::Address* CopyGlobalReference(internal::Address* from);
10276 static void DisposeGlobal(internal::Address* global_handle);
10277 static void DisposeTracedGlobal(internal::Address* global_handle);
10278 static void MakeWeak(internal::Address* location, void* data,
10279 WeakCallbackInfo<void>::Callback weak_callback,
10280 WeakCallbackType type);
10281 static void MakeWeak(internal::Address** location_addr);
10282 static void* ClearWeak(internal::Address* location);
10283 static void SetFinalizationCallbackTraced(
10284 internal::Address* location, void* parameter,
10285 WeakCallbackInfo<void>::Callback callback);
10286 static void AnnotateStrongRetainer(internal::Address* location,
10287 const char* label);
10288 static Value* Eternalize(Isolate* isolate, Value* handle);
10289
10290 template <class K, class V, class T>
10291 friend class PersistentValueMapBase;
10292
10293 static void FromJustIsNothing();
10294 static void ToLocalEmpty();
10295 static void InternalFieldOutOfBounds(int index);
10296 template <class T>
10297 friend class BasicTracedReference;
10298 template <class T>
10299 friend class Global;
10300 template <class T> friend class Local;
10301 template <class T>
10302 friend class MaybeLocal;
10303 template <class T>
10304 friend class Maybe;
10305 template <class T>
10306 friend class TracedGlobal;
10307 friend class TracedReferenceBase;
10308 template <class T>
10309 friend class TracedReference;
10310 template <class T>
10311 friend class WeakCallbackInfo;
10312 template <class T> friend class Eternal;
10313 template <class T> friend class PersistentBase;
10314 template <class T, class M> friend class Persistent;
10315 friend class Context;
10316 };
10317
10318 /**
10319 * Helper class to create a snapshot data blob.
10320 *
10321 * The Isolate used by a SnapshotCreator is owned by it, and will be entered
10322 * and exited by the constructor and destructor, respectively; The destructor
10323 * will also destroy the Isolate. Experimental language features, including
10324 * those available by default, are not available while creating a snapshot.
10325 */
10326 class V8_EXPORT SnapshotCreator {
10327 public:
10328 enum class FunctionCodeHandling { kClear, kKeep };
10329
10330 /**
10331 * Initialize and enter an isolate, and set it up for serialization.
10332 * The isolate is either created from scratch or from an existing snapshot.
10333 * The caller keeps ownership of the argument snapshot.
10334 * \param existing_blob existing snapshot from which to create this one.
10335 * \param external_references a null-terminated array of external references
10336 * that must be equivalent to CreateParams::external_references.
10337 */
10338 SnapshotCreator(Isolate* isolate,
10339 const intptr_t* external_references = nullptr,
10340 StartupData* existing_blob = nullptr);
10341
10342 /**
10343 * Create and enter an isolate, and set it up for serialization.
10344 * The isolate is either created from scratch or from an existing snapshot.
10345 * The caller keeps ownership of the argument snapshot.
10346 * \param existing_blob existing snapshot from which to create this one.
10347 * \param external_references a null-terminated array of external references
10348 * that must be equivalent to CreateParams::external_references.
10349 */
10350 SnapshotCreator(const intptr_t* external_references = nullptr,
10351 StartupData* existing_blob = nullptr);
10352
10353 /**
10354 * Destroy the snapshot creator, and exit and dispose of the Isolate
10355 * associated with it.
10356 */
10357 ~SnapshotCreator();
10358
10359 /**
10360 * \returns the isolate prepared by the snapshot creator.
10361 */
10362 Isolate* GetIsolate();
10363
10364 /**
10365 * Set the default context to be included in the snapshot blob.
10366 * The snapshot will not contain the global proxy, and we expect one or a
10367 * global object template to create one, to be provided upon deserialization.
10368 *
10369 * \param callback optional callback to serialize internal fields.
10370 */
10371 void SetDefaultContext(Local<Context> context,
10372 SerializeInternalFieldsCallback callback =
10373 SerializeInternalFieldsCallback());
10374
10375 /**
10376 * Add additional context to be included in the snapshot blob.
10377 * The snapshot will include the global proxy.
10378 *
10379 * \param callback optional callback to serialize internal fields.
10380 *
10381 * \returns the index of the context in the snapshot blob.
10382 */
10383 size_t AddContext(Local<Context> context,
10384 SerializeInternalFieldsCallback callback =
10385 SerializeInternalFieldsCallback());
10386
10387 /**
10388 * Attach arbitrary V8::Data to the context snapshot, which can be retrieved
10389 * via Context::GetDataFromSnapshot after deserialization. This data does not
10390 * survive when a new snapshot is created from an existing snapshot.
10391 * \returns the index for retrieval.
10392 */
10393 template <class T>
10394 V8_INLINE size_t AddData(Local<Context> context, Local<T> object);
10395
10396 /**
10397 * Attach arbitrary V8::Data to the isolate snapshot, which can be retrieved
10398 * via Isolate::GetDataFromSnapshot after deserialization. This data does not
10399 * survive when a new snapshot is created from an existing snapshot.
10400 * \returns the index for retrieval.
10401 */
10402 template <class T>
10403 V8_INLINE size_t AddData(Local<T> object);
10404
10405 /**
10406 * Created a snapshot data blob.
10407 * This must not be called from within a handle scope.
10408 * \param function_code_handling whether to include compiled function code
10409 * in the snapshot.
10410 * \returns { nullptr, 0 } on failure, and a startup snapshot on success. The
10411 * caller acquires ownership of the data array in the return value.
10412 */
10413 StartupData CreateBlob(FunctionCodeHandling function_code_handling);
10414
10415 // Disallow copying and assigning.
10416 SnapshotCreator(const SnapshotCreator&) = delete;
10417 void operator=(const SnapshotCreator&) = delete;
10418
10419 private:
10420 size_t AddData(Local<Context> context, internal::Address object);
10421 size_t AddData(internal::Address object);
10422
10423 void* data_;
10424 };
10425
10426 /**
10427 * A simple Maybe type, representing an object which may or may not have a
10428 * value, see https://hackage.haskell.org/package/base/docs/Data-Maybe.html.
10429 *
10430 * If an API method returns a Maybe<>, the API method can potentially fail
10431 * either because an exception is thrown, or because an exception is pending,
10432 * e.g. because a previous API call threw an exception that hasn't been caught
10433 * yet, or because a TerminateExecution exception was thrown. In that case, a
10434 * "Nothing" value is returned.
10435 */
10436 template <class T>
10437 class Maybe {
10438 public:
IsNothing()10439 V8_INLINE bool IsNothing() const { return !has_value_; }
IsJust()10440 V8_INLINE bool IsJust() const { return has_value_; }
10441
10442 /**
10443 * An alias for |FromJust|. Will crash if the Maybe<> is nothing.
10444 */
ToChecked()10445 V8_INLINE T ToChecked() const { return FromJust(); }
10446
10447 /**
10448 * Short-hand for ToChecked(), which doesn't return a value. To be used, where
10449 * the actual value of the Maybe is not needed like Object::Set.
10450 */
Check()10451 V8_INLINE void Check() const {
10452 if (V8_UNLIKELY(!IsJust())) V8::FromJustIsNothing();
10453 }
10454
10455 /**
10456 * Converts this Maybe<> to a value of type T. If this Maybe<> is
10457 * nothing (empty), |false| is returned and |out| is left untouched.
10458 */
To(T * out)10459 V8_WARN_UNUSED_RESULT V8_INLINE bool To(T* out) const {
10460 if (V8_LIKELY(IsJust())) *out = value_;
10461 return IsJust();
10462 }
10463
10464 /**
10465 * Converts this Maybe<> to a value of type T. If this Maybe<> is
10466 * nothing (empty), V8 will crash the process.
10467 */
FromJust()10468 V8_INLINE T FromJust() const {
10469 if (V8_UNLIKELY(!IsJust())) V8::FromJustIsNothing();
10470 return value_;
10471 }
10472
10473 /**
10474 * Converts this Maybe<> to a value of type T, using a default value if this
10475 * Maybe<> is nothing (empty).
10476 */
FromMaybe(const T & default_value)10477 V8_INLINE T FromMaybe(const T& default_value) const {
10478 return has_value_ ? value_ : default_value;
10479 }
10480
10481 V8_INLINE bool operator==(const Maybe& other) const {
10482 return (IsJust() == other.IsJust()) &&
10483 (!IsJust() || FromJust() == other.FromJust());
10484 }
10485
10486 V8_INLINE bool operator!=(const Maybe& other) const {
10487 return !operator==(other);
10488 }
10489
10490 private:
Maybe()10491 Maybe() : has_value_(false) {}
Maybe(const T & t)10492 explicit Maybe(const T& t) : has_value_(true), value_(t) {}
10493
10494 bool has_value_;
10495 T value_;
10496
10497 template <class U>
10498 friend Maybe<U> Nothing();
10499 template <class U>
10500 friend Maybe<U> Just(const U& u);
10501 };
10502
10503 template <class T>
Nothing()10504 inline Maybe<T> Nothing() {
10505 return Maybe<T>();
10506 }
10507
10508 template <class T>
Just(const T & t)10509 inline Maybe<T> Just(const T& t) {
10510 return Maybe<T>(t);
10511 }
10512
10513 // A template specialization of Maybe<T> for the case of T = void.
10514 template <>
10515 class Maybe<void> {
10516 public:
IsNothing()10517 V8_INLINE bool IsNothing() const { return !is_valid_; }
IsJust()10518 V8_INLINE bool IsJust() const { return is_valid_; }
10519
10520 V8_INLINE bool operator==(const Maybe& other) const {
10521 return IsJust() == other.IsJust();
10522 }
10523
10524 V8_INLINE bool operator!=(const Maybe& other) const {
10525 return !operator==(other);
10526 }
10527
10528 private:
10529 struct JustTag {};
10530
Maybe()10531 Maybe() : is_valid_(false) {}
Maybe(JustTag)10532 explicit Maybe(JustTag) : is_valid_(true) {}
10533
10534 bool is_valid_;
10535
10536 template <class U>
10537 friend Maybe<U> Nothing();
10538 friend Maybe<void> JustVoid();
10539 };
10540
JustVoid()10541 inline Maybe<void> JustVoid() { return Maybe<void>(Maybe<void>::JustTag()); }
10542
10543 /**
10544 * An external exception handler.
10545 */
10546 class V8_EXPORT TryCatch {
10547 public:
10548 /**
10549 * Creates a new try/catch block and registers it with v8. Note that
10550 * all TryCatch blocks should be stack allocated because the memory
10551 * location itself is compared against JavaScript try/catch blocks.
10552 */
10553 explicit TryCatch(Isolate* isolate);
10554
10555 /**
10556 * Unregisters and deletes this try/catch block.
10557 */
10558 ~TryCatch();
10559
10560 /**
10561 * Returns true if an exception has been caught by this try/catch block.
10562 */
10563 bool HasCaught() const;
10564
10565 /**
10566 * For certain types of exceptions, it makes no sense to continue execution.
10567 *
10568 * If CanContinue returns false, the correct action is to perform any C++
10569 * cleanup needed and then return. If CanContinue returns false and
10570 * HasTerminated returns true, it is possible to call
10571 * CancelTerminateExecution in order to continue calling into the engine.
10572 */
10573 bool CanContinue() const;
10574
10575 /**
10576 * Returns true if an exception has been caught due to script execution
10577 * being terminated.
10578 *
10579 * There is no JavaScript representation of an execution termination
10580 * exception. Such exceptions are thrown when the TerminateExecution
10581 * methods are called to terminate a long-running script.
10582 *
10583 * If such an exception has been thrown, HasTerminated will return true,
10584 * indicating that it is possible to call CancelTerminateExecution in order
10585 * to continue calling into the engine.
10586 */
10587 bool HasTerminated() const;
10588
10589 /**
10590 * Throws the exception caught by this TryCatch in a way that avoids
10591 * it being caught again by this same TryCatch. As with ThrowException
10592 * it is illegal to execute any JavaScript operations after calling
10593 * ReThrow; the caller must return immediately to where the exception
10594 * is caught.
10595 */
10596 Local<Value> ReThrow();
10597
10598 /**
10599 * Returns the exception caught by this try/catch block. If no exception has
10600 * been caught an empty handle is returned.
10601 */
10602 Local<Value> Exception() const;
10603
10604 /**
10605 * Returns the .stack property of an object. If no .stack
10606 * property is present an empty handle is returned.
10607 */
10608 V8_WARN_UNUSED_RESULT static MaybeLocal<Value> StackTrace(
10609 Local<Context> context, Local<Value> exception);
10610
10611 /**
10612 * Returns the .stack property of the thrown object. If no .stack property is
10613 * present or if this try/catch block has not caught an exception, an empty
10614 * handle is returned.
10615 */
10616 V8_WARN_UNUSED_RESULT MaybeLocal<Value> StackTrace(
10617 Local<Context> context) const;
10618
10619 /**
10620 * Returns the message associated with this exception. If there is
10621 * no message associated an empty handle is returned.
10622 */
10623 Local<v8::Message> Message() const;
10624
10625 /**
10626 * Clears any exceptions that may have been caught by this try/catch block.
10627 * After this method has been called, HasCaught() will return false. Cancels
10628 * the scheduled exception if it is caught and ReThrow() is not called before.
10629 *
10630 * It is not necessary to clear a try/catch block before using it again; if
10631 * another exception is thrown the previously caught exception will just be
10632 * overwritten. However, it is often a good idea since it makes it easier
10633 * to determine which operation threw a given exception.
10634 */
10635 void Reset();
10636
10637 /**
10638 * Set verbosity of the external exception handler.
10639 *
10640 * By default, exceptions that are caught by an external exception
10641 * handler are not reported. Call SetVerbose with true on an
10642 * external exception handler to have exceptions caught by the
10643 * handler reported as if they were not caught.
10644 */
10645 void SetVerbose(bool value);
10646
10647 /**
10648 * Returns true if verbosity is enabled.
10649 */
10650 bool IsVerbose() const;
10651
10652 /**
10653 * Set whether or not this TryCatch should capture a Message object
10654 * which holds source information about where the exception
10655 * occurred. True by default.
10656 */
10657 void SetCaptureMessage(bool value);
10658
10659 /**
10660 * There are cases when the raw address of C++ TryCatch object cannot be
10661 * used for comparisons with addresses into the JS stack. The cases are:
10662 * 1) ARM, ARM64 and MIPS simulators which have separate JS stack.
10663 * 2) Address sanitizer allocates local C++ object in the heap when
10664 * UseAfterReturn mode is enabled.
10665 * This method returns address that can be used for comparisons with
10666 * addresses into the JS stack. When neither simulator nor ASAN's
10667 * UseAfterReturn is enabled, then the address returned will be the address
10668 * of the C++ try catch handler itself.
10669 */
JSStackComparableAddress(TryCatch * handler)10670 static void* JSStackComparableAddress(TryCatch* handler) {
10671 if (handler == nullptr) return nullptr;
10672 return handler->js_stack_comparable_address_;
10673 }
10674
10675 TryCatch(const TryCatch&) = delete;
10676 void operator=(const TryCatch&) = delete;
10677
10678 private:
10679 // Declaring operator new and delete as deleted is not spec compliant.
10680 // Therefore declare them private instead to disable dynamic alloc
10681 void* operator new(size_t size);
10682 void* operator new[](size_t size);
10683 void operator delete(void*, size_t);
10684 void operator delete[](void*, size_t);
10685
10686 void ResetInternal();
10687
10688 internal::Isolate* isolate_;
10689 TryCatch* next_;
10690 void* exception_;
10691 void* message_obj_;
10692 void* js_stack_comparable_address_;
10693 bool is_verbose_ : 1;
10694 bool can_continue_ : 1;
10695 bool capture_message_ : 1;
10696 bool rethrow_ : 1;
10697 bool has_terminated_ : 1;
10698
10699 friend class internal::Isolate;
10700 };
10701
10702
10703 // --- Context ---
10704
10705
10706 /**
10707 * A container for extension names.
10708 */
10709 class V8_EXPORT ExtensionConfiguration {
10710 public:
ExtensionConfiguration()10711 ExtensionConfiguration() : name_count_(0), names_(nullptr) {}
ExtensionConfiguration(int name_count,const char * names[])10712 ExtensionConfiguration(int name_count, const char* names[])
10713 : name_count_(name_count), names_(names) { }
10714
begin()10715 const char** begin() const { return &names_[0]; }
end()10716 const char** end() const { return &names_[name_count_]; }
10717
10718 private:
10719 const int name_count_;
10720 const char** names_;
10721 };
10722
10723 /**
10724 * A sandboxed execution context with its own set of built-in objects
10725 * and functions.
10726 */
10727 class V8_EXPORT Context : public Data {
10728 public:
10729 /**
10730 * Returns the global proxy object.
10731 *
10732 * Global proxy object is a thin wrapper whose prototype points to actual
10733 * context's global object with the properties like Object, etc. This is done
10734 * that way for security reasons (for more details see
10735 * https://wiki.mozilla.org/Gecko:SplitWindow).
10736 *
10737 * Please note that changes to global proxy object prototype most probably
10738 * would break VM---v8 expects only global object as a prototype of global
10739 * proxy object.
10740 */
10741 Local<Object> Global();
10742
10743 /**
10744 * Detaches the global object from its context before
10745 * the global object can be reused to create a new context.
10746 */
10747 void DetachGlobal();
10748
10749 /**
10750 * Creates a new context and returns a handle to the newly allocated
10751 * context.
10752 *
10753 * \param isolate The isolate in which to create the context.
10754 *
10755 * \param extensions An optional extension configuration containing
10756 * the extensions to be installed in the newly created context.
10757 *
10758 * \param global_template An optional object template from which the
10759 * global object for the newly created context will be created.
10760 *
10761 * \param global_object An optional global object to be reused for
10762 * the newly created context. This global object must have been
10763 * created by a previous call to Context::New with the same global
10764 * template. The state of the global object will be completely reset
10765 * and only object identify will remain.
10766 */
10767 static Local<Context> New(
10768 Isolate* isolate, ExtensionConfiguration* extensions = nullptr,
10769 MaybeLocal<ObjectTemplate> global_template = MaybeLocal<ObjectTemplate>(),
10770 MaybeLocal<Value> global_object = MaybeLocal<Value>(),
10771 DeserializeInternalFieldsCallback internal_fields_deserializer =
10772 DeserializeInternalFieldsCallback(),
10773 MicrotaskQueue* microtask_queue = nullptr);
10774
10775 /**
10776 * Create a new context from a (non-default) context snapshot. There
10777 * is no way to provide a global object template since we do not create
10778 * a new global object from template, but we can reuse a global object.
10779 *
10780 * \param isolate See v8::Context::New.
10781 *
10782 * \param context_snapshot_index The index of the context snapshot to
10783 * deserialize from. Use v8::Context::New for the default snapshot.
10784 *
10785 * \param embedder_fields_deserializer Optional callback to deserialize
10786 * internal fields. It should match the SerializeInternalFieldCallback used
10787 * to serialize.
10788 *
10789 * \param extensions See v8::Context::New.
10790 *
10791 * \param global_object See v8::Context::New.
10792 */
10793 static MaybeLocal<Context> FromSnapshot(
10794 Isolate* isolate, size_t context_snapshot_index,
10795 DeserializeInternalFieldsCallback embedder_fields_deserializer =
10796 DeserializeInternalFieldsCallback(),
10797 ExtensionConfiguration* extensions = nullptr,
10798 MaybeLocal<Value> global_object = MaybeLocal<Value>(),
10799 MicrotaskQueue* microtask_queue = nullptr);
10800
10801 /**
10802 * Returns an global object that isn't backed by an actual context.
10803 *
10804 * The global template needs to have access checks with handlers installed.
10805 * If an existing global object is passed in, the global object is detached
10806 * from its context.
10807 *
10808 * Note that this is different from a detached context where all accesses to
10809 * the global proxy will fail. Instead, the access check handlers are invoked.
10810 *
10811 * It is also not possible to detach an object returned by this method.
10812 * Instead, the access check handlers need to return nothing to achieve the
10813 * same effect.
10814 *
10815 * It is possible, however, to create a new context from the global object
10816 * returned by this method.
10817 */
10818 static MaybeLocal<Object> NewRemoteContext(
10819 Isolate* isolate, Local<ObjectTemplate> global_template,
10820 MaybeLocal<Value> global_object = MaybeLocal<Value>());
10821
10822 /**
10823 * Sets the security token for the context. To access an object in
10824 * another context, the security tokens must match.
10825 */
10826 void SetSecurityToken(Local<Value> token);
10827
10828 /** Restores the security token to the default value. */
10829 void UseDefaultSecurityToken();
10830
10831 /** Returns the security token of this context.*/
10832 Local<Value> GetSecurityToken();
10833
10834 /**
10835 * Enter this context. After entering a context, all code compiled
10836 * and run is compiled and run in this context. If another context
10837 * is already entered, this old context is saved so it can be
10838 * restored when the new context is exited.
10839 */
10840 void Enter();
10841
10842 /**
10843 * Exit this context. Exiting the current context restores the
10844 * context that was in place when entering the current context.
10845 */
10846 void Exit();
10847
10848 /** Returns the isolate associated with a current context. */
10849 Isolate* GetIsolate();
10850
10851 /** Returns the microtask queue associated with a current context. */
10852 MicrotaskQueue* GetMicrotaskQueue();
10853
10854 /**
10855 * The field at kDebugIdIndex used to be reserved for the inspector.
10856 * It now serves no purpose.
10857 */
10858 enum EmbedderDataFields { kDebugIdIndex = 0 };
10859
10860 /**
10861 * Return the number of fields allocated for embedder data.
10862 */
10863 uint32_t GetNumberOfEmbedderDataFields();
10864
10865 /**
10866 * Gets the embedder data with the given index, which must have been set by a
10867 * previous call to SetEmbedderData with the same index.
10868 */
10869 V8_INLINE Local<Value> GetEmbedderData(int index);
10870
10871 /**
10872 * Gets the binding object used by V8 extras. Extra natives get a reference
10873 * to this object and can use it to "export" functionality by adding
10874 * properties. Extra natives can also "import" functionality by accessing
10875 * properties added by the embedder using the V8 API.
10876 */
10877 Local<Object> GetExtrasBindingObject();
10878
10879 /**
10880 * Sets the embedder data with the given index, growing the data as
10881 * needed. Note that index 0 currently has a special meaning for Chrome's
10882 * debugger.
10883 */
10884 void SetEmbedderData(int index, Local<Value> value);
10885
10886 /**
10887 * Gets a 2-byte-aligned native pointer from the embedder data with the given
10888 * index, which must have been set by a previous call to
10889 * SetAlignedPointerInEmbedderData with the same index. Note that index 0
10890 * currently has a special meaning for Chrome's debugger.
10891 */
10892 V8_INLINE void* GetAlignedPointerFromEmbedderData(int index);
10893
10894 /**
10895 * Sets a 2-byte-aligned native pointer in the embedder data with the given
10896 * index, growing the data as needed. Note that index 0 currently has a
10897 * special meaning for Chrome's debugger.
10898 */
10899 void SetAlignedPointerInEmbedderData(int index, void* value);
10900
10901 /**
10902 * Control whether code generation from strings is allowed. Calling
10903 * this method with false will disable 'eval' and the 'Function'
10904 * constructor for code running in this context. If 'eval' or the
10905 * 'Function' constructor are used an exception will be thrown.
10906 *
10907 * If code generation from strings is not allowed the
10908 * V8::AllowCodeGenerationFromStrings callback will be invoked if
10909 * set before blocking the call to 'eval' or the 'Function'
10910 * constructor. If that callback returns true, the call will be
10911 * allowed, otherwise an exception will be thrown. If no callback is
10912 * set an exception will be thrown.
10913 */
10914 void AllowCodeGenerationFromStrings(bool allow);
10915
10916 /**
10917 * Returns true if code generation from strings is allowed for the context.
10918 * For more details see AllowCodeGenerationFromStrings(bool) documentation.
10919 */
10920 bool IsCodeGenerationFromStringsAllowed();
10921
10922 /**
10923 * Sets the error description for the exception that is thrown when
10924 * code generation from strings is not allowed and 'eval' or the 'Function'
10925 * constructor are called.
10926 */
10927 void SetErrorMessageForCodeGenerationFromStrings(Local<String> message);
10928
10929 /**
10930 * Return data that was previously attached to the context snapshot via
10931 * SnapshotCreator, and removes the reference to it.
10932 * Repeated call with the same index returns an empty MaybeLocal.
10933 */
10934 template <class T>
10935 V8_INLINE MaybeLocal<T> GetDataFromSnapshotOnce(size_t index);
10936
10937 /**
10938 * If callback is set, abort any attempt to execute JavaScript in this
10939 * context, call the specified callback, and throw an exception.
10940 * To unset abort, pass nullptr as callback.
10941 */
10942 using AbortScriptExecutionCallback = void (*)(Isolate* isolate,
10943 Local<Context> context);
10944 void SetAbortScriptExecution(AbortScriptExecutionCallback callback);
10945
10946 /**
10947 * Returns the value that was set or restored by
10948 * SetContinuationPreservedEmbedderData(), if any.
10949 */
10950 Local<Value> GetContinuationPreservedEmbedderData() const;
10951
10952 /**
10953 * Sets a value that will be stored on continuations and reset while the
10954 * continuation runs.
10955 */
10956 void SetContinuationPreservedEmbedderData(Local<Value> context);
10957
10958 /**
10959 * Set or clear hooks to be invoked for promise lifecycle operations.
10960 * To clear a hook, set it to an empty v8::Function. Each function will
10961 * receive the observed promise as the first argument. If a chaining
10962 * operation is used on a promise, the init will additionally receive
10963 * the parent promise as the second argument.
10964 */
10965 void SetPromiseHooks(Local<Function> init_hook,
10966 Local<Function> before_hook,
10967 Local<Function> after_hook,
10968 Local<Function> resolve_hook);
10969
10970 /**
10971 * Stack-allocated class which sets the execution context for all
10972 * operations executed within a local scope.
10973 */
10974 class V8_NODISCARD Scope {
10975 public:
Scope(Local<Context> context)10976 explicit V8_INLINE Scope(Local<Context> context) : context_(context) {
10977 context_->Enter();
10978 }
~Scope()10979 V8_INLINE ~Scope() { context_->Exit(); }
10980
10981 private:
10982 Local<Context> context_;
10983 };
10984
10985 /**
10986 * Stack-allocated class to support the backup incumbent settings object
10987 * stack.
10988 * https://html.spec.whatwg.org/multipage/webappapis.html#backup-incumbent-settings-object-stack
10989 */
10990 class V8_EXPORT V8_NODISCARD BackupIncumbentScope final {
10991 public:
10992 /**
10993 * |backup_incumbent_context| is pushed onto the backup incumbent settings
10994 * object stack.
10995 */
10996 explicit BackupIncumbentScope(Local<Context> backup_incumbent_context);
10997 ~BackupIncumbentScope();
10998
10999 /**
11000 * Returns address that is comparable with JS stack address. Note that JS
11001 * stack may be allocated separately from the native stack. See also
11002 * |TryCatch::JSStackComparableAddress| for details.
11003 */
JSStackComparableAddress()11004 uintptr_t JSStackComparableAddress() const {
11005 return js_stack_comparable_address_;
11006 }
11007
11008 private:
11009 friend class internal::Isolate;
11010
11011 Local<Context> backup_incumbent_context_;
11012 uintptr_t js_stack_comparable_address_ = 0;
11013 const BackupIncumbentScope* prev_ = nullptr;
11014 };
11015
11016 V8_INLINE static Context* Cast(Data* data);
11017
11018 private:
11019 friend class Value;
11020 friend class Script;
11021 friend class Object;
11022 friend class Function;
11023
11024 static void CheckCast(Data* obj);
11025
11026 internal::Address* GetDataFromSnapshotOnce(size_t index);
11027 Local<Value> SlowGetEmbedderData(int index);
11028 void* SlowGetAlignedPointerFromEmbedderData(int index);
11029 };
11030
11031 /**
11032 * Multiple threads in V8 are allowed, but only one thread at a time is allowed
11033 * to use any given V8 isolate, see the comments in the Isolate class. The
11034 * definition of 'using a V8 isolate' includes accessing handles or holding onto
11035 * object pointers obtained from V8 handles while in the particular V8 isolate.
11036 * It is up to the user of V8 to ensure, perhaps with locking, that this
11037 * constraint is not violated. In addition to any other synchronization
11038 * mechanism that may be used, the v8::Locker and v8::Unlocker classes must be
11039 * used to signal thread switches to V8.
11040 *
11041 * v8::Locker is a scoped lock object. While it's active, i.e. between its
11042 * construction and destruction, the current thread is allowed to use the locked
11043 * isolate. V8 guarantees that an isolate can be locked by at most one thread at
11044 * any time. In other words, the scope of a v8::Locker is a critical section.
11045 *
11046 * Sample usage:
11047 * \code
11048 * ...
11049 * {
11050 * v8::Locker locker(isolate);
11051 * v8::Isolate::Scope isolate_scope(isolate);
11052 * ...
11053 * // Code using V8 and isolate goes here.
11054 * ...
11055 * } // Destructor called here
11056 * \endcode
11057 *
11058 * If you wish to stop using V8 in a thread A you can do this either by
11059 * destroying the v8::Locker object as above or by constructing a v8::Unlocker
11060 * object:
11061 *
11062 * \code
11063 * {
11064 * isolate->Exit();
11065 * v8::Unlocker unlocker(isolate);
11066 * ...
11067 * // Code not using V8 goes here while V8 can run in another thread.
11068 * ...
11069 * } // Destructor called here.
11070 * isolate->Enter();
11071 * \endcode
11072 *
11073 * The Unlocker object is intended for use in a long-running callback from V8,
11074 * where you want to release the V8 lock for other threads to use.
11075 *
11076 * The v8::Locker is a recursive lock, i.e. you can lock more than once in a
11077 * given thread. This can be useful if you have code that can be called either
11078 * from code that holds the lock or from code that does not. The Unlocker is
11079 * not recursive so you can not have several Unlockers on the stack at once, and
11080 * you can not use an Unlocker in a thread that is not inside a Locker's scope.
11081 *
11082 * An unlocker will unlock several lockers if it has to and reinstate the
11083 * correct depth of locking on its destruction, e.g.:
11084 *
11085 * \code
11086 * // V8 not locked.
11087 * {
11088 * v8::Locker locker(isolate);
11089 * Isolate::Scope isolate_scope(isolate);
11090 * // V8 locked.
11091 * {
11092 * v8::Locker another_locker(isolate);
11093 * // V8 still locked (2 levels).
11094 * {
11095 * isolate->Exit();
11096 * v8::Unlocker unlocker(isolate);
11097 * // V8 not locked.
11098 * }
11099 * isolate->Enter();
11100 * // V8 locked again (2 levels).
11101 * }
11102 * // V8 still locked (1 level).
11103 * }
11104 * // V8 Now no longer locked.
11105 * \endcode
11106 */
11107 class V8_EXPORT Unlocker {
11108 public:
11109 /**
11110 * Initialize Unlocker for a given Isolate.
11111 */
Unlocker(Isolate * isolate)11112 V8_INLINE explicit Unlocker(Isolate* isolate) { Initialize(isolate); }
11113
11114 ~Unlocker();
11115 private:
11116 void Initialize(Isolate* isolate);
11117
11118 internal::Isolate* isolate_;
11119 };
11120
11121
11122 class V8_EXPORT Locker {
11123 public:
11124 /**
11125 * Initialize Locker for a given Isolate.
11126 */
Locker(Isolate * isolate)11127 V8_INLINE explicit Locker(Isolate* isolate) { Initialize(isolate); }
11128
11129 ~Locker();
11130
11131 /**
11132 * Returns whether or not the locker for a given isolate, is locked by the
11133 * current thread.
11134 */
11135 static bool IsLocked(Isolate* isolate);
11136
11137 /**
11138 * Returns whether v8::Locker is being used by this V8 instance.
11139 */
11140 static bool IsActive();
11141
11142 // Disallow copying and assigning.
11143 Locker(const Locker&) = delete;
11144 void operator=(const Locker&) = delete;
11145
11146 private:
11147 void Initialize(Isolate* isolate);
11148
11149 bool has_lock_;
11150 bool top_level_;
11151 internal::Isolate* isolate_;
11152 };
11153
11154 /**
11155 * Various helpers for skipping over V8 frames in a given stack.
11156 *
11157 * The unwinder API is only supported on the x64, ARM64 and ARM32 architectures.
11158 */
11159 class V8_EXPORT Unwinder {
11160 public:
11161 /**
11162 * Attempt to unwind the stack to the most recent C++ frame. This function is
11163 * signal-safe and does not access any V8 state and thus doesn't require an
11164 * Isolate.
11165 *
11166 * The unwinder needs to know the location of the JS Entry Stub (a piece of
11167 * code that is run when C++ code calls into generated JS code). This is used
11168 * for edge cases where the current frame is being constructed or torn down
11169 * when the stack sample occurs.
11170 *
11171 * The unwinder also needs the virtual memory range of all possible V8 code
11172 * objects. There are two ranges required - the heap code range and the range
11173 * for code embedded in the binary.
11174 *
11175 * Available on x64, ARM64 and ARM32.
11176 *
11177 * \param code_pages A list of all of the ranges in which V8 has allocated
11178 * executable code. The caller should obtain this list by calling
11179 * Isolate::CopyCodePages() during the same interrupt/thread suspension that
11180 * captures the stack.
11181 * \param register_state The current registers. This is an in-out param that
11182 * will be overwritten with the register values after unwinding, on success.
11183 * \param stack_base The resulting stack pointer and frame pointer values are
11184 * bounds-checked against the stack_base and the original stack pointer value
11185 * to ensure that they are valid locations in the given stack. If these values
11186 * or any intermediate frame pointer values used during unwinding are ever out
11187 * of these bounds, unwinding will fail.
11188 *
11189 * \return True on success.
11190 */
11191 static bool TryUnwindV8Frames(const JSEntryStubs& entry_stubs,
11192 size_t code_pages_length,
11193 const MemoryRange* code_pages,
11194 RegisterState* register_state,
11195 const void* stack_base);
11196
11197 /**
11198 * Whether the PC is within the V8 code range represented by code_pages.
11199 *
11200 * If this returns false, then calling UnwindV8Frames() with the same PC
11201 * and unwind_state will always fail. If it returns true, then unwinding may
11202 * (but not necessarily) be successful.
11203 *
11204 * Available on x64, ARM64 and ARM32
11205 */
11206 static bool PCIsInV8(size_t code_pages_length, const MemoryRange* code_pages,
11207 void* pc);
11208 };
11209
11210 // --- Implementation ---
11211
11212 template <class T>
New(Isolate * isolate,Local<T> that)11213 Local<T> Local<T>::New(Isolate* isolate, Local<T> that) {
11214 return New(isolate, that.val_);
11215 }
11216
11217 template <class T>
New(Isolate * isolate,const PersistentBase<T> & that)11218 Local<T> Local<T>::New(Isolate* isolate, const PersistentBase<T>& that) {
11219 return New(isolate, that.val_);
11220 }
11221
11222 template <class T>
New(Isolate * isolate,const BasicTracedReference<T> & that)11223 Local<T> Local<T>::New(Isolate* isolate, const BasicTracedReference<T>& that) {
11224 return New(isolate, *that);
11225 }
11226
11227 template <class T>
New(Isolate * isolate,T * that)11228 Local<T> Local<T>::New(Isolate* isolate, T* that) {
11229 if (that == nullptr) return Local<T>();
11230 T* that_ptr = that;
11231 internal::Address* p = reinterpret_cast<internal::Address*>(that_ptr);
11232 return Local<T>(reinterpret_cast<T*>(HandleScope::CreateHandle(
11233 reinterpret_cast<internal::Isolate*>(isolate), *p)));
11234 }
11235
11236
11237 template<class T>
11238 template<class S>
Set(Isolate * isolate,Local<S> handle)11239 void Eternal<T>::Set(Isolate* isolate, Local<S> handle) {
11240 static_assert(std::is_base_of<T, S>::value, "type check");
11241 val_ = reinterpret_cast<T*>(
11242 V8::Eternalize(isolate, reinterpret_cast<Value*>(*handle)));
11243 }
11244
11245 template <class T>
Get(Isolate * isolate)11246 Local<T> Eternal<T>::Get(Isolate* isolate) const {
11247 // The eternal handle will never go away, so as with the roots, we don't even
11248 // need to open a handle.
11249 return Local<T>(val_);
11250 }
11251
11252
11253 template <class T>
ToLocalChecked()11254 Local<T> MaybeLocal<T>::ToLocalChecked() {
11255 if (V8_UNLIKELY(val_ == nullptr)) V8::ToLocalEmpty();
11256 return Local<T>(val_);
11257 }
11258
11259
11260 template <class T>
GetInternalField(int index)11261 void* WeakCallbackInfo<T>::GetInternalField(int index) const {
11262 #ifdef V8_ENABLE_CHECKS
11263 if (index < 0 || index >= kEmbedderFieldsInWeakCallback) {
11264 V8::InternalFieldOutOfBounds(index);
11265 }
11266 #endif
11267 return embedder_fields_[index];
11268 }
11269
11270
11271 template <class T>
New(Isolate * isolate,T * that)11272 T* PersistentBase<T>::New(Isolate* isolate, T* that) {
11273 if (that == nullptr) return nullptr;
11274 internal::Address* p = reinterpret_cast<internal::Address*>(that);
11275 return reinterpret_cast<T*>(
11276 V8::GlobalizeReference(reinterpret_cast<internal::Isolate*>(isolate),
11277 p));
11278 }
11279
11280
11281 template <class T, class M>
11282 template <class S, class M2>
Copy(const Persistent<S,M2> & that)11283 void Persistent<T, M>::Copy(const Persistent<S, M2>& that) {
11284 static_assert(std::is_base_of<T, S>::value, "type check");
11285 this->Reset();
11286 if (that.IsEmpty()) return;
11287 internal::Address* p = reinterpret_cast<internal::Address*>(that.val_);
11288 this->val_ = reinterpret_cast<T*>(V8::CopyGlobalReference(p));
11289 M::Copy(that, this);
11290 }
11291
11292 template <class T>
IsWeak()11293 bool PersistentBase<T>::IsWeak() const {
11294 using I = internal::Internals;
11295 if (this->IsEmpty()) return false;
11296 return I::GetNodeState(reinterpret_cast<internal::Address*>(this->val_)) ==
11297 I::kNodeStateIsWeakValue;
11298 }
11299
11300
11301 template <class T>
Reset()11302 void PersistentBase<T>::Reset() {
11303 if (this->IsEmpty()) return;
11304 V8::DisposeGlobal(reinterpret_cast<internal::Address*>(this->val_));
11305 val_ = nullptr;
11306 }
11307
11308
11309 template <class T>
11310 template <class S>
Reset(Isolate * isolate,const Local<S> & other)11311 void PersistentBase<T>::Reset(Isolate* isolate, const Local<S>& other) {
11312 static_assert(std::is_base_of<T, S>::value, "type check");
11313 Reset();
11314 if (other.IsEmpty()) return;
11315 this->val_ = New(isolate, other.val_);
11316 }
11317
11318
11319 template <class T>
11320 template <class S>
Reset(Isolate * isolate,const PersistentBase<S> & other)11321 void PersistentBase<T>::Reset(Isolate* isolate,
11322 const PersistentBase<S>& other) {
11323 static_assert(std::is_base_of<T, S>::value, "type check");
11324 Reset();
11325 if (other.IsEmpty()) return;
11326 this->val_ = New(isolate, other.val_);
11327 }
11328
11329
11330 template <class T>
11331 template <typename P>
SetWeak(P * parameter,typename WeakCallbackInfo<P>::Callback callback,WeakCallbackType type)11332 V8_INLINE void PersistentBase<T>::SetWeak(
11333 P* parameter, typename WeakCallbackInfo<P>::Callback callback,
11334 WeakCallbackType type) {
11335 using Callback = WeakCallbackInfo<void>::Callback;
11336 #if (__GNUC__ >= 8) && !defined(__clang__)
11337 #pragma GCC diagnostic push
11338 #pragma GCC diagnostic ignored "-Wcast-function-type"
11339 #endif
11340 V8::MakeWeak(reinterpret_cast<internal::Address*>(this->val_), parameter,
11341 reinterpret_cast<Callback>(callback), type);
11342 #if (__GNUC__ >= 8) && !defined(__clang__)
11343 #pragma GCC diagnostic pop
11344 #endif
11345 }
11346
11347 template <class T>
SetWeak()11348 void PersistentBase<T>::SetWeak() {
11349 V8::MakeWeak(reinterpret_cast<internal::Address**>(&this->val_));
11350 }
11351
11352 template <class T>
11353 template <typename P>
ClearWeak()11354 P* PersistentBase<T>::ClearWeak() {
11355 return reinterpret_cast<P*>(
11356 V8::ClearWeak(reinterpret_cast<internal::Address*>(this->val_)));
11357 }
11358
11359 template <class T>
AnnotateStrongRetainer(const char * label)11360 void PersistentBase<T>::AnnotateStrongRetainer(const char* label) {
11361 V8::AnnotateStrongRetainer(reinterpret_cast<internal::Address*>(this->val_),
11362 label);
11363 }
11364
11365 template <class T>
SetWrapperClassId(uint16_t class_id)11366 void PersistentBase<T>::SetWrapperClassId(uint16_t class_id) {
11367 using I = internal::Internals;
11368 if (this->IsEmpty()) return;
11369 internal::Address* obj = reinterpret_cast<internal::Address*>(this->val_);
11370 uint8_t* addr = reinterpret_cast<uint8_t*>(obj) + I::kNodeClassIdOffset;
11371 *reinterpret_cast<uint16_t*>(addr) = class_id;
11372 }
11373
11374
11375 template <class T>
WrapperClassId()11376 uint16_t PersistentBase<T>::WrapperClassId() const {
11377 using I = internal::Internals;
11378 if (this->IsEmpty()) return 0;
11379 internal::Address* obj = reinterpret_cast<internal::Address*>(this->val_);
11380 uint8_t* addr = reinterpret_cast<uint8_t*>(obj) + I::kNodeClassIdOffset;
11381 return *reinterpret_cast<uint16_t*>(addr);
11382 }
11383
11384 template <class T>
Global(Global && other)11385 Global<T>::Global(Global&& other) : PersistentBase<T>(other.val_) {
11386 if (other.val_ != nullptr) {
11387 V8::MoveGlobalReference(reinterpret_cast<internal::Address**>(&other.val_),
11388 reinterpret_cast<internal::Address**>(&this->val_));
11389 other.val_ = nullptr;
11390 }
11391 }
11392
11393 template <class T>
11394 template <class S>
11395 Global<T>& Global<T>::operator=(Global<S>&& rhs) {
11396 static_assert(std::is_base_of<T, S>::value, "type check");
11397 if (this != &rhs) {
11398 this->Reset();
11399 if (rhs.val_ != nullptr) {
11400 this->val_ = rhs.val_;
11401 V8::MoveGlobalReference(
11402 reinterpret_cast<internal::Address**>(&rhs.val_),
11403 reinterpret_cast<internal::Address**>(&this->val_));
11404 rhs.val_ = nullptr;
11405 }
11406 }
11407 return *this;
11408 }
11409
11410 template <class T>
New(Isolate * isolate,T * that,void * slot,DestructionMode destruction_mode)11411 internal::Address* BasicTracedReference<T>::New(
11412 Isolate* isolate, T* that, void* slot, DestructionMode destruction_mode) {
11413 if (that == nullptr) return nullptr;
11414 internal::Address* p = reinterpret_cast<internal::Address*>(that);
11415 return V8::GlobalizeTracedReference(
11416 reinterpret_cast<internal::Isolate*>(isolate), p,
11417 reinterpret_cast<internal::Address*>(slot),
11418 destruction_mode == kWithDestructor);
11419 }
11420
Reset()11421 void TracedReferenceBase::Reset() {
11422 if (IsEmpty()) return;
11423 V8::DisposeTracedGlobal(reinterpret_cast<internal::Address*>(val_));
11424 SetSlotThreadSafe(nullptr);
11425 }
11426
Get(v8::Isolate * isolate)11427 v8::Local<v8::Value> TracedReferenceBase::Get(v8::Isolate* isolate) const {
11428 if (IsEmpty()) return Local<Value>();
11429 return Local<Value>::New(isolate, reinterpret_cast<Value*>(val_));
11430 }
11431
11432 V8_INLINE bool operator==(const TracedReferenceBase& lhs,
11433 const TracedReferenceBase& rhs) {
11434 v8::internal::Address* a = reinterpret_cast<v8::internal::Address*>(lhs.val_);
11435 v8::internal::Address* b = reinterpret_cast<v8::internal::Address*>(rhs.val_);
11436 if (a == nullptr) return b == nullptr;
11437 if (b == nullptr) return false;
11438 return *a == *b;
11439 }
11440
11441 template <typename U>
11442 V8_INLINE bool operator==(const TracedReferenceBase& lhs,
11443 const v8::Local<U>& rhs) {
11444 v8::internal::Address* a = reinterpret_cast<v8::internal::Address*>(lhs.val_);
11445 v8::internal::Address* b = reinterpret_cast<v8::internal::Address*>(*rhs);
11446 if (a == nullptr) return b == nullptr;
11447 if (b == nullptr) return false;
11448 return *a == *b;
11449 }
11450
11451 template <typename U>
11452 V8_INLINE bool operator==(const v8::Local<U>& lhs,
11453 const TracedReferenceBase& rhs) {
11454 return rhs == lhs;
11455 }
11456
11457 V8_INLINE bool operator!=(const TracedReferenceBase& lhs,
11458 const TracedReferenceBase& rhs) {
11459 return !(lhs == rhs);
11460 }
11461
11462 template <typename U>
11463 V8_INLINE bool operator!=(const TracedReferenceBase& lhs,
11464 const v8::Local<U>& rhs) {
11465 return !(lhs == rhs);
11466 }
11467
11468 template <typename U>
11469 V8_INLINE bool operator!=(const v8::Local<U>& lhs,
11470 const TracedReferenceBase& rhs) {
11471 return !(rhs == lhs);
11472 }
11473
11474 template <class T>
11475 template <class S>
Reset(Isolate * isolate,const Local<S> & other)11476 void TracedGlobal<T>::Reset(Isolate* isolate, const Local<S>& other) {
11477 static_assert(std::is_base_of<T, S>::value, "type check");
11478 Reset();
11479 if (other.IsEmpty()) return;
11480 this->val_ = this->New(isolate, other.val_, &this->val_,
11481 BasicTracedReference<T>::kWithDestructor);
11482 }
11483
11484 template <class T>
11485 template <class S>
11486 TracedGlobal<T>& TracedGlobal<T>::operator=(TracedGlobal<S>&& rhs) {
11487 static_assert(std::is_base_of<T, S>::value, "type check");
11488 *this = std::move(rhs.template As<T>());
11489 return *this;
11490 }
11491
11492 template <class T>
11493 template <class S>
11494 TracedGlobal<T>& TracedGlobal<T>::operator=(const TracedGlobal<S>& rhs) {
11495 static_assert(std::is_base_of<T, S>::value, "type check");
11496 *this = rhs.template As<T>();
11497 return *this;
11498 }
11499
11500 template <class T>
11501 TracedGlobal<T>& TracedGlobal<T>::operator=(TracedGlobal&& rhs) {
11502 if (this != &rhs) {
11503 V8::MoveTracedGlobalReference(
11504 reinterpret_cast<internal::Address**>(&rhs.val_),
11505 reinterpret_cast<internal::Address**>(&this->val_));
11506 }
11507 return *this;
11508 }
11509
11510 template <class T>
11511 TracedGlobal<T>& TracedGlobal<T>::operator=(const TracedGlobal& rhs) {
11512 if (this != &rhs) {
11513 this->Reset();
11514 if (rhs.val_ != nullptr) {
11515 V8::CopyTracedGlobalReference(
11516 reinterpret_cast<const internal::Address* const*>(&rhs.val_),
11517 reinterpret_cast<internal::Address**>(&this->val_));
11518 }
11519 }
11520 return *this;
11521 }
11522
11523 template <class T>
11524 template <class S>
Reset(Isolate * isolate,const Local<S> & other)11525 void TracedReference<T>::Reset(Isolate* isolate, const Local<S>& other) {
11526 static_assert(std::is_base_of<T, S>::value, "type check");
11527 this->Reset();
11528 if (other.IsEmpty()) return;
11529 this->SetSlotThreadSafe(
11530 this->New(isolate, other.val_, &this->val_,
11531 BasicTracedReference<T>::kWithoutDestructor));
11532 }
11533
11534 template <class T>
11535 template <class S>
11536 TracedReference<T>& TracedReference<T>::operator=(TracedReference<S>&& rhs) {
11537 static_assert(std::is_base_of<T, S>::value, "type check");
11538 *this = std::move(rhs.template As<T>());
11539 return *this;
11540 }
11541
11542 template <class T>
11543 template <class S>
11544 TracedReference<T>& TracedReference<T>::operator=(
11545 const TracedReference<S>& rhs) {
11546 static_assert(std::is_base_of<T, S>::value, "type check");
11547 *this = rhs.template As<T>();
11548 return *this;
11549 }
11550
11551 template <class T>
11552 TracedReference<T>& TracedReference<T>::operator=(TracedReference&& rhs) {
11553 if (this != &rhs) {
11554 V8::MoveTracedGlobalReference(
11555 reinterpret_cast<internal::Address**>(&rhs.val_),
11556 reinterpret_cast<internal::Address**>(&this->val_));
11557 }
11558 return *this;
11559 }
11560
11561 template <class T>
11562 TracedReference<T>& TracedReference<T>::operator=(const TracedReference& rhs) {
11563 if (this != &rhs) {
11564 this->Reset();
11565 if (rhs.val_ != nullptr) {
11566 V8::CopyTracedGlobalReference(
11567 reinterpret_cast<const internal::Address* const*>(&rhs.val_),
11568 reinterpret_cast<internal::Address**>(&this->val_));
11569 }
11570 }
11571 return *this;
11572 }
11573
SetWrapperClassId(uint16_t class_id)11574 void TracedReferenceBase::SetWrapperClassId(uint16_t class_id) {
11575 using I = internal::Internals;
11576 if (IsEmpty()) return;
11577 internal::Address* obj = reinterpret_cast<internal::Address*>(val_);
11578 uint8_t* addr = reinterpret_cast<uint8_t*>(obj) + I::kNodeClassIdOffset;
11579 *reinterpret_cast<uint16_t*>(addr) = class_id;
11580 }
11581
WrapperClassId()11582 uint16_t TracedReferenceBase::WrapperClassId() const {
11583 using I = internal::Internals;
11584 if (IsEmpty()) return 0;
11585 internal::Address* obj = reinterpret_cast<internal::Address*>(val_);
11586 uint8_t* addr = reinterpret_cast<uint8_t*>(obj) + I::kNodeClassIdOffset;
11587 return *reinterpret_cast<uint16_t*>(addr);
11588 }
11589
11590 template <class T>
SetFinalizationCallback(void * parameter,typename WeakCallbackInfo<void>::Callback callback)11591 void TracedGlobal<T>::SetFinalizationCallback(
11592 void* parameter, typename WeakCallbackInfo<void>::Callback callback) {
11593 V8::SetFinalizationCallbackTraced(
11594 reinterpret_cast<internal::Address*>(this->val_), parameter, callback);
11595 }
11596
11597 template <typename T>
ReturnValue(internal::Address * slot)11598 ReturnValue<T>::ReturnValue(internal::Address* slot) : value_(slot) {}
11599
11600 template <typename T>
11601 template <typename S>
Set(const Global<S> & handle)11602 void ReturnValue<T>::Set(const Global<S>& handle) {
11603 static_assert(std::is_base_of<T, S>::value, "type check");
11604 if (V8_UNLIKELY(handle.IsEmpty())) {
11605 *value_ = GetDefaultValue();
11606 } else {
11607 *value_ = *reinterpret_cast<internal::Address*>(*handle);
11608 }
11609 }
11610
11611 template <typename T>
11612 template <typename S>
Set(const BasicTracedReference<S> & handle)11613 void ReturnValue<T>::Set(const BasicTracedReference<S>& handle) {
11614 static_assert(std::is_base_of<T, S>::value, "type check");
11615 if (V8_UNLIKELY(handle.IsEmpty())) {
11616 *value_ = GetDefaultValue();
11617 } else {
11618 *value_ = *reinterpret_cast<internal::Address*>(handle.val_);
11619 }
11620 }
11621
11622 template <typename T>
11623 template <typename S>
Set(const Local<S> handle)11624 void ReturnValue<T>::Set(const Local<S> handle) {
11625 static_assert(std::is_void<T>::value || std::is_base_of<T, S>::value,
11626 "type check");
11627 if (V8_UNLIKELY(handle.IsEmpty())) {
11628 *value_ = GetDefaultValue();
11629 } else {
11630 *value_ = *reinterpret_cast<internal::Address*>(*handle);
11631 }
11632 }
11633
11634 template<typename T>
Set(double i)11635 void ReturnValue<T>::Set(double i) {
11636 static_assert(std::is_base_of<T, Number>::value, "type check");
11637 Set(Number::New(GetIsolate(), i));
11638 }
11639
11640 template<typename T>
Set(int32_t i)11641 void ReturnValue<T>::Set(int32_t i) {
11642 static_assert(std::is_base_of<T, Integer>::value, "type check");
11643 using I = internal::Internals;
11644 if (V8_LIKELY(I::IsValidSmi(i))) {
11645 *value_ = I::IntToSmi(i);
11646 return;
11647 }
11648 Set(Integer::New(GetIsolate(), i));
11649 }
11650
11651 template<typename T>
Set(uint32_t i)11652 void ReturnValue<T>::Set(uint32_t i) {
11653 static_assert(std::is_base_of<T, Integer>::value, "type check");
11654 // Can't simply use INT32_MAX here for whatever reason.
11655 bool fits_into_int32_t = (i & (1U << 31)) == 0;
11656 if (V8_LIKELY(fits_into_int32_t)) {
11657 Set(static_cast<int32_t>(i));
11658 return;
11659 }
11660 Set(Integer::NewFromUnsigned(GetIsolate(), i));
11661 }
11662
11663 template<typename T>
Set(bool value)11664 void ReturnValue<T>::Set(bool value) {
11665 static_assert(std::is_base_of<T, Boolean>::value, "type check");
11666 using I = internal::Internals;
11667 int root_index;
11668 if (value) {
11669 root_index = I::kTrueValueRootIndex;
11670 } else {
11671 root_index = I::kFalseValueRootIndex;
11672 }
11673 *value_ = *I::GetRoot(GetIsolate(), root_index);
11674 }
11675
11676 template<typename T>
SetNull()11677 void ReturnValue<T>::SetNull() {
11678 static_assert(std::is_base_of<T, Primitive>::value, "type check");
11679 using I = internal::Internals;
11680 *value_ = *I::GetRoot(GetIsolate(), I::kNullValueRootIndex);
11681 }
11682
11683 template<typename T>
SetUndefined()11684 void ReturnValue<T>::SetUndefined() {
11685 static_assert(std::is_base_of<T, Primitive>::value, "type check");
11686 using I = internal::Internals;
11687 *value_ = *I::GetRoot(GetIsolate(), I::kUndefinedValueRootIndex);
11688 }
11689
11690 template<typename T>
SetEmptyString()11691 void ReturnValue<T>::SetEmptyString() {
11692 static_assert(std::is_base_of<T, String>::value, "type check");
11693 using I = internal::Internals;
11694 *value_ = *I::GetRoot(GetIsolate(), I::kEmptyStringRootIndex);
11695 }
11696
11697 template <typename T>
GetIsolate()11698 Isolate* ReturnValue<T>::GetIsolate() const {
11699 // Isolate is always the pointer below the default value on the stack.
11700 return *reinterpret_cast<Isolate**>(&value_[-2]);
11701 }
11702
11703 template <typename T>
Get()11704 Local<Value> ReturnValue<T>::Get() const {
11705 using I = internal::Internals;
11706 if (*value_ == *I::GetRoot(GetIsolate(), I::kTheHoleValueRootIndex))
11707 return Local<Value>(*Undefined(GetIsolate()));
11708 return Local<Value>::New(GetIsolate(), reinterpret_cast<Value*>(value_));
11709 }
11710
11711 template <typename T>
11712 template <typename S>
Set(S * whatever)11713 void ReturnValue<T>::Set(S* whatever) {
11714 static_assert(sizeof(S) < 0, "incompilable to prevent inadvertent misuse");
11715 }
11716
11717 template <typename T>
GetDefaultValue()11718 internal::Address ReturnValue<T>::GetDefaultValue() {
11719 // Default value is always the pointer below value_ on the stack.
11720 return value_[-1];
11721 }
11722
11723 template <typename T>
FunctionCallbackInfo(internal::Address * implicit_args,internal::Address * values,int length)11724 FunctionCallbackInfo<T>::FunctionCallbackInfo(internal::Address* implicit_args,
11725 internal::Address* values,
11726 int length)
11727 : implicit_args_(implicit_args), values_(values), length_(length) {}
11728
11729 template<typename T>
11730 Local<Value> FunctionCallbackInfo<T>::operator[](int i) const {
11731 // values_ points to the first argument (not the receiver).
11732 if (i < 0 || length_ <= i) return Local<Value>(*Undefined(GetIsolate()));
11733 return Local<Value>(reinterpret_cast<Value*>(values_ + i));
11734 }
11735
11736
11737 template<typename T>
This()11738 Local<Object> FunctionCallbackInfo<T>::This() const {
11739 // values_ points to the first argument (not the receiver).
11740 return Local<Object>(reinterpret_cast<Object*>(values_ - 1));
11741 }
11742
11743
11744 template<typename T>
Holder()11745 Local<Object> FunctionCallbackInfo<T>::Holder() const {
11746 return Local<Object>(reinterpret_cast<Object*>(
11747 &implicit_args_[kHolderIndex]));
11748 }
11749
11750 template <typename T>
NewTarget()11751 Local<Value> FunctionCallbackInfo<T>::NewTarget() const {
11752 return Local<Value>(
11753 reinterpret_cast<Value*>(&implicit_args_[kNewTargetIndex]));
11754 }
11755
11756 template <typename T>
Data()11757 Local<Value> FunctionCallbackInfo<T>::Data() const {
11758 return Local<Value>(reinterpret_cast<Value*>(&implicit_args_[kDataIndex]));
11759 }
11760
11761
11762 template<typename T>
GetIsolate()11763 Isolate* FunctionCallbackInfo<T>::GetIsolate() const {
11764 return *reinterpret_cast<Isolate**>(&implicit_args_[kIsolateIndex]);
11765 }
11766
11767
11768 template<typename T>
GetReturnValue()11769 ReturnValue<T> FunctionCallbackInfo<T>::GetReturnValue() const {
11770 return ReturnValue<T>(&implicit_args_[kReturnValueIndex]);
11771 }
11772
11773
11774 template<typename T>
IsConstructCall()11775 bool FunctionCallbackInfo<T>::IsConstructCall() const {
11776 return !NewTarget()->IsUndefined();
11777 }
11778
11779
11780 template<typename T>
Length()11781 int FunctionCallbackInfo<T>::Length() const {
11782 return length_;
11783 }
11784
ScriptOrigin(Local<Value> resource_name,Local<Integer> line_offset,Local<Integer> column_offset,Local<Boolean> is_shared_cross_origin,Local<Integer> script_id,Local<Value> source_map_url,Local<Boolean> is_opaque,Local<Boolean> is_wasm,Local<Boolean> is_module,Local<PrimitiveArray> host_defined_options)11785 ScriptOrigin::ScriptOrigin(
11786 Local<Value> resource_name, Local<Integer> line_offset,
11787 Local<Integer> column_offset, Local<Boolean> is_shared_cross_origin,
11788 Local<Integer> script_id, Local<Value> source_map_url,
11789 Local<Boolean> is_opaque, Local<Boolean> is_wasm, Local<Boolean> is_module,
11790 Local<PrimitiveArray> host_defined_options)
11791 : ScriptOrigin(
11792 Isolate::GetCurrent(), resource_name,
11793 line_offset.IsEmpty() ? 0 : static_cast<int>(line_offset->Value()),
11794 column_offset.IsEmpty() ? 0
11795 : static_cast<int>(column_offset->Value()),
11796 !is_shared_cross_origin.IsEmpty() && is_shared_cross_origin->IsTrue(),
11797 static_cast<int>(script_id.IsEmpty() ? -1 : script_id->Value()),
11798 source_map_url, !is_opaque.IsEmpty() && is_opaque->IsTrue(),
11799 !is_wasm.IsEmpty() && is_wasm->IsTrue(),
11800 !is_module.IsEmpty() && is_module->IsTrue(), host_defined_options) {}
11801
ScriptOrigin(Local<Value> resource_name,int line_offset,int column_offset,bool is_shared_cross_origin,int script_id,Local<Value> source_map_url,bool is_opaque,bool is_wasm,bool is_module,Local<PrimitiveArray> host_defined_options)11802 ScriptOrigin::ScriptOrigin(Local<Value> resource_name, int line_offset,
11803 int column_offset, bool is_shared_cross_origin,
11804 int script_id, Local<Value> source_map_url,
11805 bool is_opaque, bool is_wasm, bool is_module,
11806 Local<PrimitiveArray> host_defined_options)
11807 : isolate_(Isolate::GetCurrent()),
11808 resource_name_(resource_name),
11809 resource_line_offset_(line_offset),
11810 resource_column_offset_(column_offset),
11811 options_(is_shared_cross_origin, is_opaque, is_wasm, is_module),
11812 script_id_(script_id),
11813 source_map_url_(source_map_url),
11814 host_defined_options_(host_defined_options) {}
11815
ScriptOrigin(Isolate * isolate,Local<Value> resource_name,int line_offset,int column_offset,bool is_shared_cross_origin,int script_id,Local<Value> source_map_url,bool is_opaque,bool is_wasm,bool is_module,Local<PrimitiveArray> host_defined_options)11816 ScriptOrigin::ScriptOrigin(Isolate* isolate, Local<Value> resource_name,
11817 int line_offset, int column_offset,
11818 bool is_shared_cross_origin, int script_id,
11819 Local<Value> source_map_url, bool is_opaque,
11820 bool is_wasm, bool is_module,
11821 Local<PrimitiveArray> host_defined_options)
11822 : isolate_(isolate),
11823 resource_name_(resource_name),
11824 resource_line_offset_(line_offset),
11825 resource_column_offset_(column_offset),
11826 options_(is_shared_cross_origin, is_opaque, is_wasm, is_module),
11827 script_id_(script_id),
11828 source_map_url_(source_map_url),
11829 host_defined_options_(host_defined_options) {}
11830
ResourceName()11831 Local<Value> ScriptOrigin::ResourceName() const { return resource_name_; }
11832
HostDefinedOptions()11833 Local<PrimitiveArray> ScriptOrigin::HostDefinedOptions() const {
11834 return host_defined_options_;
11835 }
11836
ResourceLineOffset()11837 Local<Integer> ScriptOrigin::ResourceLineOffset() const {
11838 return v8::Integer::New(isolate_, resource_line_offset_);
11839 }
11840
ResourceColumnOffset()11841 Local<Integer> ScriptOrigin::ResourceColumnOffset() const {
11842 return v8::Integer::New(isolate_, resource_column_offset_);
11843 }
11844
ScriptID()11845 Local<Integer> ScriptOrigin::ScriptID() const {
11846 return v8::Integer::New(isolate_, script_id_);
11847 }
11848
LineOffset()11849 int ScriptOrigin::LineOffset() const { return resource_line_offset_; }
11850
ColumnOffset()11851 int ScriptOrigin::ColumnOffset() const { return resource_column_offset_; }
11852
ScriptId()11853 int ScriptOrigin::ScriptId() const { return script_id_; }
11854
SourceMapUrl()11855 Local<Value> ScriptOrigin::SourceMapUrl() const { return source_map_url_; }
11856
Source(Local<String> string,const ScriptOrigin & origin,CachedData * data)11857 ScriptCompiler::Source::Source(Local<String> string, const ScriptOrigin& origin,
11858 CachedData* data)
11859 : source_string(string),
11860 resource_name(origin.ResourceName()),
11861 resource_line_offset(origin.LineOffset()),
11862 resource_column_offset(origin.ColumnOffset()),
11863 resource_options(origin.Options()),
11864 source_map_url(origin.SourceMapUrl()),
11865 host_defined_options(origin.HostDefinedOptions()),
11866 cached_data(data) {}
11867
Source(Local<String> string,CachedData * data)11868 ScriptCompiler::Source::Source(Local<String> string,
11869 CachedData* data)
11870 : source_string(string), cached_data(data) {}
11871
11872
~Source()11873 ScriptCompiler::Source::~Source() {
11874 delete cached_data;
11875 }
11876
11877
GetCachedData()11878 const ScriptCompiler::CachedData* ScriptCompiler::Source::GetCachedData()
11879 const {
11880 return cached_data;
11881 }
11882
GetResourceOptions()11883 const ScriptOriginOptions& ScriptCompiler::Source::GetResourceOptions() const {
11884 return resource_options;
11885 }
11886
New(Isolate * isolate,bool value)11887 Local<Boolean> Boolean::New(Isolate* isolate, bool value) {
11888 return value ? True(isolate) : False(isolate);
11889 }
11890
Set(Isolate * isolate,const char * name,Local<Data> value)11891 void Template::Set(Isolate* isolate, const char* name, Local<Data> value) {
11892 Set(String::NewFromUtf8(isolate, name, NewStringType::kInternalized)
11893 .ToLocalChecked(),
11894 value);
11895 }
11896
Cast(Data * data)11897 FunctionTemplate* FunctionTemplate::Cast(Data* data) {
11898 #ifdef V8_ENABLE_CHECKS
11899 CheckCast(data);
11900 #endif
11901 return reinterpret_cast<FunctionTemplate*>(data);
11902 }
11903
Cast(Data * data)11904 ObjectTemplate* ObjectTemplate::Cast(Data* data) {
11905 #ifdef V8_ENABLE_CHECKS
11906 CheckCast(data);
11907 #endif
11908 return reinterpret_cast<ObjectTemplate*>(data);
11909 }
11910
Cast(Data * data)11911 Signature* Signature::Cast(Data* data) {
11912 #ifdef V8_ENABLE_CHECKS
11913 CheckCast(data);
11914 #endif
11915 return reinterpret_cast<Signature*>(data);
11916 }
11917
Cast(Data * data)11918 AccessorSignature* AccessorSignature::Cast(Data* data) {
11919 #ifdef V8_ENABLE_CHECKS
11920 CheckCast(data);
11921 #endif
11922 return reinterpret_cast<AccessorSignature*>(data);
11923 }
11924
GetInternalField(int index)11925 Local<Value> Object::GetInternalField(int index) {
11926 #ifndef V8_ENABLE_CHECKS
11927 using A = internal::Address;
11928 using I = internal::Internals;
11929 A obj = *reinterpret_cast<A*>(this);
11930 // Fast path: If the object is a plain JSObject, which is the common case, we
11931 // know where to find the internal fields and can return the value directly.
11932 auto instance_type = I::GetInstanceType(obj);
11933 if (instance_type == I::kJSObjectType ||
11934 instance_type == I::kJSApiObjectType ||
11935 instance_type == I::kJSSpecialApiObjectType) {
11936 int offset = I::kJSObjectHeaderSize + (I::kEmbedderDataSlotSize * index);
11937 A value = I::ReadRawField<A>(obj, offset);
11938 #ifdef V8_COMPRESS_POINTERS
11939 // We read the full pointer value and then decompress it in order to avoid
11940 // dealing with potential endiannes issues.
11941 value = I::DecompressTaggedAnyField(obj, static_cast<uint32_t>(value));
11942 #endif
11943 internal::Isolate* isolate =
11944 internal::IsolateFromNeverReadOnlySpaceObject(obj);
11945 A* result = HandleScope::CreateHandle(isolate, value);
11946 return Local<Value>(reinterpret_cast<Value*>(result));
11947 }
11948 #endif
11949 return SlowGetInternalField(index);
11950 }
11951
11952
GetAlignedPointerFromInternalField(int index)11953 void* Object::GetAlignedPointerFromInternalField(int index) {
11954 #ifndef V8_ENABLE_CHECKS
11955 using A = internal::Address;
11956 using I = internal::Internals;
11957 A obj = *reinterpret_cast<A*>(this);
11958 // Fast path: If the object is a plain JSObject, which is the common case, we
11959 // know where to find the internal fields and can return the value directly.
11960 auto instance_type = I::GetInstanceType(obj);
11961 if (V8_LIKELY(instance_type == I::kJSObjectType ||
11962 instance_type == I::kJSApiObjectType ||
11963 instance_type == I::kJSSpecialApiObjectType)) {
11964 int offset = I::kJSObjectHeaderSize + (I::kEmbedderDataSlotSize * index);
11965 #ifdef V8_HEAP_SANDBOX
11966 offset += I::kEmbedderDataSlotRawPayloadOffset;
11967 #endif
11968 internal::Isolate* isolate = I::GetIsolateForHeapSandbox(obj);
11969 A value = I::ReadExternalPointerField(
11970 isolate, obj, offset, internal::kEmbedderDataSlotPayloadTag);
11971 return reinterpret_cast<void*>(value);
11972 }
11973 #endif
11974 return SlowGetAlignedPointerFromInternalField(index);
11975 }
11976
Cast(v8::Data * data)11977 String* String::Cast(v8::Data* data) {
11978 #ifdef V8_ENABLE_CHECKS
11979 CheckCast(data);
11980 #endif
11981 return static_cast<String*>(data);
11982 }
11983
Empty(Isolate * isolate)11984 Local<String> String::Empty(Isolate* isolate) {
11985 using S = internal::Address;
11986 using I = internal::Internals;
11987 I::CheckInitialized(isolate);
11988 S* slot = I::GetRoot(isolate, I::kEmptyStringRootIndex);
11989 return Local<String>(reinterpret_cast<String*>(slot));
11990 }
11991
11992
GetExternalStringResource()11993 String::ExternalStringResource* String::GetExternalStringResource() const {
11994 using A = internal::Address;
11995 using I = internal::Internals;
11996 A obj = *reinterpret_cast<const A*>(this);
11997
11998 ExternalStringResource* result;
11999 if (I::IsExternalTwoByteString(I::GetInstanceType(obj))) {
12000 internal::Isolate* isolate = I::GetIsolateForHeapSandbox(obj);
12001 A value =
12002 I::ReadExternalPointerField(isolate, obj, I::kStringResourceOffset,
12003 internal::kExternalStringResourceTag);
12004 result = reinterpret_cast<String::ExternalStringResource*>(value);
12005 } else {
12006 result = GetExternalStringResourceSlow();
12007 }
12008 #ifdef V8_ENABLE_CHECKS
12009 VerifyExternalStringResource(result);
12010 #endif
12011 return result;
12012 }
12013
12014
GetExternalStringResourceBase(String::Encoding * encoding_out)12015 String::ExternalStringResourceBase* String::GetExternalStringResourceBase(
12016 String::Encoding* encoding_out) const {
12017 using A = internal::Address;
12018 using I = internal::Internals;
12019 A obj = *reinterpret_cast<const A*>(this);
12020 int type = I::GetInstanceType(obj) & I::kFullStringRepresentationMask;
12021 *encoding_out = static_cast<Encoding>(type & I::kStringEncodingMask);
12022 ExternalStringResourceBase* resource;
12023 if (type == I::kExternalOneByteRepresentationTag ||
12024 type == I::kExternalTwoByteRepresentationTag) {
12025 internal::Isolate* isolate = I::GetIsolateForHeapSandbox(obj);
12026 A value =
12027 I::ReadExternalPointerField(isolate, obj, I::kStringResourceOffset,
12028 internal::kExternalStringResourceTag);
12029 resource = reinterpret_cast<ExternalStringResourceBase*>(value);
12030 } else {
12031 resource = GetExternalStringResourceBaseSlow(encoding_out);
12032 }
12033 #ifdef V8_ENABLE_CHECKS
12034 VerifyExternalStringResourceBase(resource, *encoding_out);
12035 #endif
12036 return resource;
12037 }
12038
12039
IsUndefined()12040 bool Value::IsUndefined() const {
12041 #ifdef V8_ENABLE_CHECKS
12042 return FullIsUndefined();
12043 #else
12044 return QuickIsUndefined();
12045 #endif
12046 }
12047
QuickIsUndefined()12048 bool Value::QuickIsUndefined() const {
12049 using A = internal::Address;
12050 using I = internal::Internals;
12051 A obj = *reinterpret_cast<const A*>(this);
12052 if (!I::HasHeapObjectTag(obj)) return false;
12053 if (I::GetInstanceType(obj) != I::kOddballType) return false;
12054 return (I::GetOddballKind(obj) == I::kUndefinedOddballKind);
12055 }
12056
12057
IsNull()12058 bool Value::IsNull() const {
12059 #ifdef V8_ENABLE_CHECKS
12060 return FullIsNull();
12061 #else
12062 return QuickIsNull();
12063 #endif
12064 }
12065
QuickIsNull()12066 bool Value::QuickIsNull() const {
12067 using A = internal::Address;
12068 using I = internal::Internals;
12069 A obj = *reinterpret_cast<const A*>(this);
12070 if (!I::HasHeapObjectTag(obj)) return false;
12071 if (I::GetInstanceType(obj) != I::kOddballType) return false;
12072 return (I::GetOddballKind(obj) == I::kNullOddballKind);
12073 }
12074
IsNullOrUndefined()12075 bool Value::IsNullOrUndefined() const {
12076 #ifdef V8_ENABLE_CHECKS
12077 return FullIsNull() || FullIsUndefined();
12078 #else
12079 return QuickIsNullOrUndefined();
12080 #endif
12081 }
12082
QuickIsNullOrUndefined()12083 bool Value::QuickIsNullOrUndefined() const {
12084 using A = internal::Address;
12085 using I = internal::Internals;
12086 A obj = *reinterpret_cast<const A*>(this);
12087 if (!I::HasHeapObjectTag(obj)) return false;
12088 if (I::GetInstanceType(obj) != I::kOddballType) return false;
12089 int kind = I::GetOddballKind(obj);
12090 return kind == I::kNullOddballKind || kind == I::kUndefinedOddballKind;
12091 }
12092
IsString()12093 bool Value::IsString() const {
12094 #ifdef V8_ENABLE_CHECKS
12095 return FullIsString();
12096 #else
12097 return QuickIsString();
12098 #endif
12099 }
12100
QuickIsString()12101 bool Value::QuickIsString() const {
12102 using A = internal::Address;
12103 using I = internal::Internals;
12104 A obj = *reinterpret_cast<const A*>(this);
12105 if (!I::HasHeapObjectTag(obj)) return false;
12106 return (I::GetInstanceType(obj) < I::kFirstNonstringType);
12107 }
12108
12109
Cast(T * value)12110 template <class T> Value* Value::Cast(T* value) {
12111 return static_cast<Value*>(value);
12112 }
12113
12114 template <>
Cast(Data * value)12115 V8_INLINE Value* Value::Cast(Data* value) {
12116 #ifdef V8_ENABLE_CHECKS
12117 CheckCast(value);
12118 #endif
12119 return static_cast<Value*>(value);
12120 }
12121
Cast(v8::Data * data)12122 Boolean* Boolean::Cast(v8::Data* data) {
12123 #ifdef V8_ENABLE_CHECKS
12124 CheckCast(data);
12125 #endif
12126 return static_cast<Boolean*>(data);
12127 }
12128
Cast(v8::Data * data)12129 Name* Name::Cast(v8::Data* data) {
12130 #ifdef V8_ENABLE_CHECKS
12131 CheckCast(data);
12132 #endif
12133 return static_cast<Name*>(data);
12134 }
12135
Cast(v8::Data * data)12136 Symbol* Symbol::Cast(v8::Data* data) {
12137 #ifdef V8_ENABLE_CHECKS
12138 CheckCast(data);
12139 #endif
12140 return static_cast<Symbol*>(data);
12141 }
12142
Cast(Data * data)12143 Private* Private::Cast(Data* data) {
12144 #ifdef V8_ENABLE_CHECKS
12145 CheckCast(data);
12146 #endif
12147 return reinterpret_cast<Private*>(data);
12148 }
12149
Cast(Data * data)12150 ModuleRequest* ModuleRequest::Cast(Data* data) {
12151 #ifdef V8_ENABLE_CHECKS
12152 CheckCast(data);
12153 #endif
12154 return reinterpret_cast<ModuleRequest*>(data);
12155 }
12156
Cast(Data * data)12157 Module* Module::Cast(Data* data) {
12158 #ifdef V8_ENABLE_CHECKS
12159 CheckCast(data);
12160 #endif
12161 return reinterpret_cast<Module*>(data);
12162 }
12163
Cast(v8::Data * data)12164 Number* Number::Cast(v8::Data* data) {
12165 #ifdef V8_ENABLE_CHECKS
12166 CheckCast(data);
12167 #endif
12168 return static_cast<Number*>(data);
12169 }
12170
Cast(v8::Data * data)12171 Integer* Integer::Cast(v8::Data* data) {
12172 #ifdef V8_ENABLE_CHECKS
12173 CheckCast(data);
12174 #endif
12175 return static_cast<Integer*>(data);
12176 }
12177
Cast(v8::Data * data)12178 Int32* Int32::Cast(v8::Data* data) {
12179 #ifdef V8_ENABLE_CHECKS
12180 CheckCast(data);
12181 #endif
12182 return static_cast<Int32*>(data);
12183 }
12184
Cast(v8::Data * data)12185 Uint32* Uint32::Cast(v8::Data* data) {
12186 #ifdef V8_ENABLE_CHECKS
12187 CheckCast(data);
12188 #endif
12189 return static_cast<Uint32*>(data);
12190 }
12191
Cast(v8::Data * data)12192 BigInt* BigInt::Cast(v8::Data* data) {
12193 #ifdef V8_ENABLE_CHECKS
12194 CheckCast(data);
12195 #endif
12196 return static_cast<BigInt*>(data);
12197 }
12198
Cast(v8::Data * data)12199 Context* Context::Cast(v8::Data* data) {
12200 #ifdef V8_ENABLE_CHECKS
12201 CheckCast(data);
12202 #endif
12203 return static_cast<Context*>(data);
12204 }
12205
Cast(v8::Value * value)12206 Date* Date::Cast(v8::Value* value) {
12207 #ifdef V8_ENABLE_CHECKS
12208 CheckCast(value);
12209 #endif
12210 return static_cast<Date*>(value);
12211 }
12212
12213
Cast(v8::Value * value)12214 StringObject* StringObject::Cast(v8::Value* value) {
12215 #ifdef V8_ENABLE_CHECKS
12216 CheckCast(value);
12217 #endif
12218 return static_cast<StringObject*>(value);
12219 }
12220
12221
Cast(v8::Value * value)12222 SymbolObject* SymbolObject::Cast(v8::Value* value) {
12223 #ifdef V8_ENABLE_CHECKS
12224 CheckCast(value);
12225 #endif
12226 return static_cast<SymbolObject*>(value);
12227 }
12228
12229
Cast(v8::Value * value)12230 NumberObject* NumberObject::Cast(v8::Value* value) {
12231 #ifdef V8_ENABLE_CHECKS
12232 CheckCast(value);
12233 #endif
12234 return static_cast<NumberObject*>(value);
12235 }
12236
Cast(v8::Value * value)12237 BigIntObject* BigIntObject::Cast(v8::Value* value) {
12238 #ifdef V8_ENABLE_CHECKS
12239 CheckCast(value);
12240 #endif
12241 return static_cast<BigIntObject*>(value);
12242 }
12243
Cast(v8::Value * value)12244 BooleanObject* BooleanObject::Cast(v8::Value* value) {
12245 #ifdef V8_ENABLE_CHECKS
12246 CheckCast(value);
12247 #endif
12248 return static_cast<BooleanObject*>(value);
12249 }
12250
12251
Cast(v8::Value * value)12252 RegExp* RegExp::Cast(v8::Value* value) {
12253 #ifdef V8_ENABLE_CHECKS
12254 CheckCast(value);
12255 #endif
12256 return static_cast<RegExp*>(value);
12257 }
12258
12259
Cast(v8::Value * value)12260 Object* Object::Cast(v8::Value* value) {
12261 #ifdef V8_ENABLE_CHECKS
12262 CheckCast(value);
12263 #endif
12264 return static_cast<Object*>(value);
12265 }
12266
12267
Cast(v8::Value * value)12268 Array* Array::Cast(v8::Value* value) {
12269 #ifdef V8_ENABLE_CHECKS
12270 CheckCast(value);
12271 #endif
12272 return static_cast<Array*>(value);
12273 }
12274
12275
Cast(v8::Value * value)12276 Map* Map::Cast(v8::Value* value) {
12277 #ifdef V8_ENABLE_CHECKS
12278 CheckCast(value);
12279 #endif
12280 return static_cast<Map*>(value);
12281 }
12282
12283
Cast(v8::Value * value)12284 Set* Set::Cast(v8::Value* value) {
12285 #ifdef V8_ENABLE_CHECKS
12286 CheckCast(value);
12287 #endif
12288 return static_cast<Set*>(value);
12289 }
12290
12291
Cast(v8::Value * value)12292 Promise* Promise::Cast(v8::Value* value) {
12293 #ifdef V8_ENABLE_CHECKS
12294 CheckCast(value);
12295 #endif
12296 return static_cast<Promise*>(value);
12297 }
12298
12299
Cast(v8::Value * value)12300 Proxy* Proxy::Cast(v8::Value* value) {
12301 #ifdef V8_ENABLE_CHECKS
12302 CheckCast(value);
12303 #endif
12304 return static_cast<Proxy*>(value);
12305 }
12306
Cast(v8::Value * value)12307 WasmMemoryObject* WasmMemoryObject::Cast(v8::Value* value) {
12308 #ifdef V8_ENABLE_CHECKS
12309 CheckCast(value);
12310 #endif
12311 return static_cast<WasmMemoryObject*>(value);
12312 }
12313
Cast(v8::Value * value)12314 WasmModuleObject* WasmModuleObject::Cast(v8::Value* value) {
12315 #ifdef V8_ENABLE_CHECKS
12316 CheckCast(value);
12317 #endif
12318 return static_cast<WasmModuleObject*>(value);
12319 }
12320
Cast(v8::Value * value)12321 Promise::Resolver* Promise::Resolver::Cast(v8::Value* value) {
12322 #ifdef V8_ENABLE_CHECKS
12323 CheckCast(value);
12324 #endif
12325 return static_cast<Promise::Resolver*>(value);
12326 }
12327
12328
Cast(v8::Value * value)12329 ArrayBuffer* ArrayBuffer::Cast(v8::Value* value) {
12330 #ifdef V8_ENABLE_CHECKS
12331 CheckCast(value);
12332 #endif
12333 return static_cast<ArrayBuffer*>(value);
12334 }
12335
12336
Cast(v8::Value * value)12337 ArrayBufferView* ArrayBufferView::Cast(v8::Value* value) {
12338 #ifdef V8_ENABLE_CHECKS
12339 CheckCast(value);
12340 #endif
12341 return static_cast<ArrayBufferView*>(value);
12342 }
12343
12344
Cast(v8::Value * value)12345 TypedArray* TypedArray::Cast(v8::Value* value) {
12346 #ifdef V8_ENABLE_CHECKS
12347 CheckCast(value);
12348 #endif
12349 return static_cast<TypedArray*>(value);
12350 }
12351
12352
Cast(v8::Value * value)12353 Uint8Array* Uint8Array::Cast(v8::Value* value) {
12354 #ifdef V8_ENABLE_CHECKS
12355 CheckCast(value);
12356 #endif
12357 return static_cast<Uint8Array*>(value);
12358 }
12359
12360
Cast(v8::Value * value)12361 Int8Array* Int8Array::Cast(v8::Value* value) {
12362 #ifdef V8_ENABLE_CHECKS
12363 CheckCast(value);
12364 #endif
12365 return static_cast<Int8Array*>(value);
12366 }
12367
12368
Cast(v8::Value * value)12369 Uint16Array* Uint16Array::Cast(v8::Value* value) {
12370 #ifdef V8_ENABLE_CHECKS
12371 CheckCast(value);
12372 #endif
12373 return static_cast<Uint16Array*>(value);
12374 }
12375
12376
Cast(v8::Value * value)12377 Int16Array* Int16Array::Cast(v8::Value* value) {
12378 #ifdef V8_ENABLE_CHECKS
12379 CheckCast(value);
12380 #endif
12381 return static_cast<Int16Array*>(value);
12382 }
12383
12384
Cast(v8::Value * value)12385 Uint32Array* Uint32Array::Cast(v8::Value* value) {
12386 #ifdef V8_ENABLE_CHECKS
12387 CheckCast(value);
12388 #endif
12389 return static_cast<Uint32Array*>(value);
12390 }
12391
12392
Cast(v8::Value * value)12393 Int32Array* Int32Array::Cast(v8::Value* value) {
12394 #ifdef V8_ENABLE_CHECKS
12395 CheckCast(value);
12396 #endif
12397 return static_cast<Int32Array*>(value);
12398 }
12399
12400
Cast(v8::Value * value)12401 Float32Array* Float32Array::Cast(v8::Value* value) {
12402 #ifdef V8_ENABLE_CHECKS
12403 CheckCast(value);
12404 #endif
12405 return static_cast<Float32Array*>(value);
12406 }
12407
12408
Cast(v8::Value * value)12409 Float64Array* Float64Array::Cast(v8::Value* value) {
12410 #ifdef V8_ENABLE_CHECKS
12411 CheckCast(value);
12412 #endif
12413 return static_cast<Float64Array*>(value);
12414 }
12415
Cast(v8::Value * value)12416 BigInt64Array* BigInt64Array::Cast(v8::Value* value) {
12417 #ifdef V8_ENABLE_CHECKS
12418 CheckCast(value);
12419 #endif
12420 return static_cast<BigInt64Array*>(value);
12421 }
12422
Cast(v8::Value * value)12423 BigUint64Array* BigUint64Array::Cast(v8::Value* value) {
12424 #ifdef V8_ENABLE_CHECKS
12425 CheckCast(value);
12426 #endif
12427 return static_cast<BigUint64Array*>(value);
12428 }
12429
Cast(v8::Value * value)12430 Uint8ClampedArray* Uint8ClampedArray::Cast(v8::Value* value) {
12431 #ifdef V8_ENABLE_CHECKS
12432 CheckCast(value);
12433 #endif
12434 return static_cast<Uint8ClampedArray*>(value);
12435 }
12436
12437
Cast(v8::Value * value)12438 DataView* DataView::Cast(v8::Value* value) {
12439 #ifdef V8_ENABLE_CHECKS
12440 CheckCast(value);
12441 #endif
12442 return static_cast<DataView*>(value);
12443 }
12444
12445
Cast(v8::Value * value)12446 SharedArrayBuffer* SharedArrayBuffer::Cast(v8::Value* value) {
12447 #ifdef V8_ENABLE_CHECKS
12448 CheckCast(value);
12449 #endif
12450 return static_cast<SharedArrayBuffer*>(value);
12451 }
12452
12453
Cast(v8::Value * value)12454 Function* Function::Cast(v8::Value* value) {
12455 #ifdef V8_ENABLE_CHECKS
12456 CheckCast(value);
12457 #endif
12458 return static_cast<Function*>(value);
12459 }
12460
12461
Cast(v8::Value * value)12462 External* External::Cast(v8::Value* value) {
12463 #ifdef V8_ENABLE_CHECKS
12464 CheckCast(value);
12465 #endif
12466 return static_cast<External*>(value);
12467 }
12468
12469
12470 template<typename T>
GetIsolate()12471 Isolate* PropertyCallbackInfo<T>::GetIsolate() const {
12472 return *reinterpret_cast<Isolate**>(&args_[kIsolateIndex]);
12473 }
12474
12475
12476 template<typename T>
Data()12477 Local<Value> PropertyCallbackInfo<T>::Data() const {
12478 return Local<Value>(reinterpret_cast<Value*>(&args_[kDataIndex]));
12479 }
12480
12481
12482 template<typename T>
This()12483 Local<Object> PropertyCallbackInfo<T>::This() const {
12484 return Local<Object>(reinterpret_cast<Object*>(&args_[kThisIndex]));
12485 }
12486
12487
12488 template<typename T>
Holder()12489 Local<Object> PropertyCallbackInfo<T>::Holder() const {
12490 return Local<Object>(reinterpret_cast<Object*>(&args_[kHolderIndex]));
12491 }
12492
12493
12494 template<typename T>
GetReturnValue()12495 ReturnValue<T> PropertyCallbackInfo<T>::GetReturnValue() const {
12496 return ReturnValue<T>(&args_[kReturnValueIndex]);
12497 }
12498
12499 template <typename T>
ShouldThrowOnError()12500 bool PropertyCallbackInfo<T>::ShouldThrowOnError() const {
12501 using I = internal::Internals;
12502 if (args_[kShouldThrowOnErrorIndex] !=
12503 I::IntToSmi(I::kInferShouldThrowMode)) {
12504 return args_[kShouldThrowOnErrorIndex] != I::IntToSmi(I::kDontThrow);
12505 }
12506 return v8::internal::ShouldThrowOnError(
12507 reinterpret_cast<v8::internal::Isolate*>(GetIsolate()));
12508 }
12509
Undefined(Isolate * isolate)12510 Local<Primitive> Undefined(Isolate* isolate) {
12511 using S = internal::Address;
12512 using I = internal::Internals;
12513 I::CheckInitialized(isolate);
12514 S* slot = I::GetRoot(isolate, I::kUndefinedValueRootIndex);
12515 return Local<Primitive>(reinterpret_cast<Primitive*>(slot));
12516 }
12517
12518
Null(Isolate * isolate)12519 Local<Primitive> Null(Isolate* isolate) {
12520 using S = internal::Address;
12521 using I = internal::Internals;
12522 I::CheckInitialized(isolate);
12523 S* slot = I::GetRoot(isolate, I::kNullValueRootIndex);
12524 return Local<Primitive>(reinterpret_cast<Primitive*>(slot));
12525 }
12526
12527
True(Isolate * isolate)12528 Local<Boolean> True(Isolate* isolate) {
12529 using S = internal::Address;
12530 using I = internal::Internals;
12531 I::CheckInitialized(isolate);
12532 S* slot = I::GetRoot(isolate, I::kTrueValueRootIndex);
12533 return Local<Boolean>(reinterpret_cast<Boolean*>(slot));
12534 }
12535
12536
False(Isolate * isolate)12537 Local<Boolean> False(Isolate* isolate) {
12538 using S = internal::Address;
12539 using I = internal::Internals;
12540 I::CheckInitialized(isolate);
12541 S* slot = I::GetRoot(isolate, I::kFalseValueRootIndex);
12542 return Local<Boolean>(reinterpret_cast<Boolean*>(slot));
12543 }
12544
12545
SetData(uint32_t slot,void * data)12546 void Isolate::SetData(uint32_t slot, void* data) {
12547 using I = internal::Internals;
12548 I::SetEmbedderData(this, slot, data);
12549 }
12550
12551
GetData(uint32_t slot)12552 void* Isolate::GetData(uint32_t slot) {
12553 using I = internal::Internals;
12554 return I::GetEmbedderData(this, slot);
12555 }
12556
12557
GetNumberOfDataSlots()12558 uint32_t Isolate::GetNumberOfDataSlots() {
12559 using I = internal::Internals;
12560 return I::kNumIsolateDataSlots;
12561 }
12562
12563 template <class T>
GetDataFromSnapshotOnce(size_t index)12564 MaybeLocal<T> Isolate::GetDataFromSnapshotOnce(size_t index) {
12565 T* data = reinterpret_cast<T*>(GetDataFromSnapshotOnce(index));
12566 if (data) internal::PerformCastCheck(data);
12567 return Local<T>(data);
12568 }
12569
GetEmbedderData(int index)12570 Local<Value> Context::GetEmbedderData(int index) {
12571 #ifndef V8_ENABLE_CHECKS
12572 using A = internal::Address;
12573 using I = internal::Internals;
12574 A ctx = *reinterpret_cast<const A*>(this);
12575 A embedder_data =
12576 I::ReadTaggedPointerField(ctx, I::kNativeContextEmbedderDataOffset);
12577 int value_offset =
12578 I::kEmbedderDataArrayHeaderSize + (I::kEmbedderDataSlotSize * index);
12579 A value = I::ReadRawField<A>(embedder_data, value_offset);
12580 #ifdef V8_COMPRESS_POINTERS
12581 // We read the full pointer value and then decompress it in order to avoid
12582 // dealing with potential endiannes issues.
12583 value =
12584 I::DecompressTaggedAnyField(embedder_data, static_cast<uint32_t>(value));
12585 #endif
12586 internal::Isolate* isolate = internal::IsolateFromNeverReadOnlySpaceObject(
12587 *reinterpret_cast<A*>(this));
12588 A* result = HandleScope::CreateHandle(isolate, value);
12589 return Local<Value>(reinterpret_cast<Value*>(result));
12590 #else
12591 return SlowGetEmbedderData(index);
12592 #endif
12593 }
12594
12595
GetAlignedPointerFromEmbedderData(int index)12596 void* Context::GetAlignedPointerFromEmbedderData(int index) {
12597 #ifndef V8_ENABLE_CHECKS
12598 using A = internal::Address;
12599 using I = internal::Internals;
12600 A ctx = *reinterpret_cast<const A*>(this);
12601 A embedder_data =
12602 I::ReadTaggedPointerField(ctx, I::kNativeContextEmbedderDataOffset);
12603 int value_offset =
12604 I::kEmbedderDataArrayHeaderSize + (I::kEmbedderDataSlotSize * index);
12605 #ifdef V8_HEAP_SANDBOX
12606 value_offset += I::kEmbedderDataSlotRawPayloadOffset;
12607 #endif
12608 internal::Isolate* isolate = I::GetIsolateForHeapSandbox(ctx);
12609 return reinterpret_cast<void*>(
12610 I::ReadExternalPointerField(isolate, embedder_data, value_offset,
12611 internal::kEmbedderDataSlotPayloadTag));
12612 #else
12613 return SlowGetAlignedPointerFromEmbedderData(index);
12614 #endif
12615 }
12616
12617 template <class T>
GetDataFromSnapshotOnce(size_t index)12618 MaybeLocal<T> Context::GetDataFromSnapshotOnce(size_t index) {
12619 T* data = reinterpret_cast<T*>(GetDataFromSnapshotOnce(index));
12620 if (data) internal::PerformCastCheck(data);
12621 return Local<T>(data);
12622 }
12623
12624 template <class T>
AddData(Local<Context> context,Local<T> object)12625 size_t SnapshotCreator::AddData(Local<Context> context, Local<T> object) {
12626 T* object_ptr = *object;
12627 internal::Address* p = reinterpret_cast<internal::Address*>(object_ptr);
12628 return AddData(context, *p);
12629 }
12630
12631 template <class T>
AddData(Local<T> object)12632 size_t SnapshotCreator::AddData(Local<T> object) {
12633 T* object_ptr = *object;
12634 internal::Address* p = reinterpret_cast<internal::Address*>(object_ptr);
12635 return AddData(*p);
12636 }
12637
12638 /**
12639 * \example shell.cc
12640 * A simple shell that takes a list of expressions on the
12641 * command-line and executes them.
12642 */
12643
12644
12645 /**
12646 * \example process.cc
12647 */
12648
12649
12650 } // namespace v8
12651
12652 #endif // INCLUDE_V8_H_
12653