LCOV - code coverage report
Current view: top level - src - api.h (source / functions) Hit Total Coverage
Test: app.info Lines: 66 70 94.3 %
Date: 2017-04-26 Functions: 31 35 88.6 %

          Line data    Source code
       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             : #ifndef V8_API_H_
       6             : #define V8_API_H_
       7             : 
       8             : #include "include/v8-testing.h"
       9             : #include "src/contexts.h"
      10             : #include "src/debug/debug-interface.h"
      11             : #include "src/factory.h"
      12             : #include "src/isolate.h"
      13             : #include "src/list.h"
      14             : 
      15             : namespace v8 {
      16             : 
      17             : // Constants used in the implementation of the API.  The most natural thing
      18             : // would usually be to place these with the classes that use them, but
      19             : // we want to keep them out of v8.h because it is an externally
      20             : // visible file.
      21             : class Consts {
      22             :  public:
      23             :   enum TemplateType {
      24             :     FUNCTION_TEMPLATE = 0,
      25             :     OBJECT_TEMPLATE = 1
      26             :   };
      27             : };
      28             : 
      29    39487748 : template <typename T> inline T ToCData(v8::internal::Object* obj) {
      30             :   STATIC_ASSERT(sizeof(T) == sizeof(v8::internal::Address));
      31    94760529 :   if (obj == v8::internal::Smi::kZero) return nullptr;
      32             :   return reinterpret_cast<T>(
      33             :       reinterpret_cast<intptr_t>(
      34    94532125 :           v8::internal::Foreign::cast(obj)->foreign_address()));
      35             : }
      36             : 
      37             : 
      38             : template <typename T>
      39     4006353 : inline v8::internal::Handle<v8::internal::Object> FromCData(
      40             :     v8::internal::Isolate* isolate, T obj) {
      41             :   STATIC_ASSERT(sizeof(T) == sizeof(v8::internal::Address));
      42     4008310 :   if (obj == nullptr) return handle(v8::internal::Smi::kZero, isolate);
      43             :   return isolate->factory()->NewForeign(
      44     4004396 :       reinterpret_cast<v8::internal::Address>(reinterpret_cast<intptr_t>(obj)));
      45             : }
      46             : 
      47             : 
      48             : class ApiFunction {
      49             :  public:
      50      143230 :   explicit ApiFunction(v8::internal::Address addr) : addr_(addr) { }
      51      143230 :   v8::internal::Address address() { return addr_; }
      52             :  private:
      53             :   v8::internal::Address addr_;
      54             : };
      55             : 
      56             : 
      57             : 
      58             : class RegisteredExtension {
      59             :  public:
      60             :   explicit RegisteredExtension(Extension* extension);
      61             :   static void Register(RegisteredExtension* that);
      62             :   static void UnregisterAll();
      63             :   Extension* extension() { return extension_; }
      64             :   RegisteredExtension* next() { return next_; }
      65      112086 :   static RegisteredExtension* first_extension() { return first_extension_; }
      66             :  private:
      67             :   Extension* extension_;
      68             :   RegisteredExtension* next_;
      69             :   static RegisteredExtension* first_extension_;
      70             : };
      71             : 
      72             : #define OPEN_HANDLE_LIST(V)                    \
      73             :   V(Template, TemplateInfo)                    \
      74             :   V(FunctionTemplate, FunctionTemplateInfo)    \
      75             :   V(ObjectTemplate, ObjectTemplateInfo)        \
      76             :   V(Signature, FunctionTemplateInfo)           \
      77             :   V(AccessorSignature, FunctionTemplateInfo)   \
      78             :   V(Data, Object)                              \
      79             :   V(RegExp, JSRegExp)                          \
      80             :   V(Object, JSReceiver)                        \
      81             :   V(Array, JSArray)                            \
      82             :   V(Map, JSMap)                                \
      83             :   V(Set, JSSet)                                \
      84             :   V(ArrayBuffer, JSArrayBuffer)                \
      85             :   V(ArrayBufferView, JSArrayBufferView)        \
      86             :   V(TypedArray, JSTypedArray)                  \
      87             :   V(Uint8Array, JSTypedArray)                  \
      88             :   V(Uint8ClampedArray, JSTypedArray)           \
      89             :   V(Int8Array, JSTypedArray)                   \
      90             :   V(Uint16Array, JSTypedArray)                 \
      91             :   V(Int16Array, JSTypedArray)                  \
      92             :   V(Uint32Array, JSTypedArray)                 \
      93             :   V(Int32Array, JSTypedArray)                  \
      94             :   V(Float32Array, JSTypedArray)                \
      95             :   V(Float64Array, JSTypedArray)                \
      96             :   V(DataView, JSDataView)                      \
      97             :   V(SharedArrayBuffer, JSArrayBuffer)          \
      98             :   V(Name, Name)                                \
      99             :   V(String, String)                            \
     100             :   V(Symbol, Symbol)                            \
     101             :   V(Script, JSFunction)                        \
     102             :   V(UnboundScript, SharedFunctionInfo)         \
     103             :   V(Module, Module)                            \
     104             :   V(Function, JSReceiver)                      \
     105             :   V(Message, JSMessageObject)                  \
     106             :   V(Context, Context)                          \
     107             :   V(External, Object)                          \
     108             :   V(StackTrace, FixedArray)                    \
     109             :   V(StackFrame, StackFrameInfo)                \
     110             :   V(Proxy, JSProxy)                            \
     111             :   V(NativeWeakMap, JSWeakMap)                  \
     112             :   V(debug::GeneratorObject, JSGeneratorObject) \
     113             :   V(debug::Script, Script)                     \
     114             :   V(Promise, JSPromise)                        \
     115             :   V(DynamicImportResult, JSPromise)
     116             : 
     117             : class Utils {
     118             :  public:
     119             :   static inline bool ApiCheck(bool condition,
     120             :                               const char* location,
     121             :                               const char* message) {
     122   917276620 :     if (!condition) Utils::ReportApiFailure(location, message);
     123             :     return condition;
     124             :   }
     125             :   static void ReportOOMFailure(const char* location, bool is_heap_oom);
     126             : 
     127             :   static inline Local<Context> ToLocal(
     128             :       v8::internal::Handle<v8::internal::Context> obj);
     129             :   static inline Local<Value> ToLocal(
     130             :       v8::internal::Handle<v8::internal::Object> obj);
     131             :   static inline Local<Module> ToLocal(
     132             :       v8::internal::Handle<v8::internal::Module> obj);
     133             :   static inline Local<Name> ToLocal(
     134             :       v8::internal::Handle<v8::internal::Name> obj);
     135             :   static inline Local<String> ToLocal(
     136             :       v8::internal::Handle<v8::internal::String> obj);
     137             :   static inline Local<Symbol> ToLocal(
     138             :       v8::internal::Handle<v8::internal::Symbol> obj);
     139             :   static inline Local<RegExp> ToLocal(
     140             :       v8::internal::Handle<v8::internal::JSRegExp> obj);
     141             :   static inline Local<Object> ToLocal(
     142             :       v8::internal::Handle<v8::internal::JSReceiver> obj);
     143             :   static inline Local<Object> ToLocal(
     144             :       v8::internal::Handle<v8::internal::JSObject> obj);
     145             :   static inline Local<Function> ToLocal(
     146             :       v8::internal::Handle<v8::internal::JSFunction> obj);
     147             :   static inline Local<Array> ToLocal(
     148             :       v8::internal::Handle<v8::internal::JSArray> obj);
     149             :   static inline Local<Map> ToLocal(
     150             :       v8::internal::Handle<v8::internal::JSMap> obj);
     151             :   static inline Local<Set> ToLocal(
     152             :       v8::internal::Handle<v8::internal::JSSet> obj);
     153             :   static inline Local<Proxy> ToLocal(
     154             :       v8::internal::Handle<v8::internal::JSProxy> obj);
     155             :   static inline Local<ArrayBuffer> ToLocal(
     156             :       v8::internal::Handle<v8::internal::JSArrayBuffer> obj);
     157             :   static inline Local<ArrayBufferView> ToLocal(
     158             :       v8::internal::Handle<v8::internal::JSArrayBufferView> obj);
     159             :   static inline Local<DataView> ToLocal(
     160             :       v8::internal::Handle<v8::internal::JSDataView> obj);
     161             :   static inline Local<TypedArray> ToLocal(
     162             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     163             :   static inline Local<Uint8Array> ToLocalUint8Array(
     164             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     165             :   static inline Local<Uint8ClampedArray> ToLocalUint8ClampedArray(
     166             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     167             :   static inline Local<Int8Array> ToLocalInt8Array(
     168             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     169             :   static inline Local<Uint16Array> ToLocalUint16Array(
     170             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     171             :   static inline Local<Int16Array> ToLocalInt16Array(
     172             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     173             :   static inline Local<Uint32Array> ToLocalUint32Array(
     174             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     175             :   static inline Local<Int32Array> ToLocalInt32Array(
     176             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     177             :   static inline Local<Float32Array> ToLocalFloat32Array(
     178             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     179             :   static inline Local<Float64Array> ToLocalFloat64Array(
     180             :       v8::internal::Handle<v8::internal::JSTypedArray> obj);
     181             : 
     182             :   static inline Local<SharedArrayBuffer> ToLocalShared(
     183             :       v8::internal::Handle<v8::internal::JSArrayBuffer> obj);
     184             : 
     185             :   static inline Local<Message> MessageToLocal(
     186             :       v8::internal::Handle<v8::internal::Object> obj);
     187             :   static inline Local<Promise> PromiseToLocal(
     188             :       v8::internal::Handle<v8::internal::JSObject> obj);
     189             :   static inline Local<DynamicImportResult> PromiseToDynamicImportResult(
     190             :       v8::internal::Handle<v8::internal::JSPromise> obj);
     191             :   static inline Local<StackTrace> StackTraceToLocal(
     192             :       v8::internal::Handle<v8::internal::FixedArray> obj);
     193             :   static inline Local<StackFrame> StackFrameToLocal(
     194             :       v8::internal::Handle<v8::internal::StackFrameInfo> obj);
     195             :   static inline Local<Number> NumberToLocal(
     196             :       v8::internal::Handle<v8::internal::Object> obj);
     197             :   static inline Local<Integer> IntegerToLocal(
     198             :       v8::internal::Handle<v8::internal::Object> obj);
     199             :   static inline Local<Uint32> Uint32ToLocal(
     200             :       v8::internal::Handle<v8::internal::Object> obj);
     201             :   static inline Local<FunctionTemplate> ToLocal(
     202             :       v8::internal::Handle<v8::internal::FunctionTemplateInfo> obj);
     203             :   static inline Local<ObjectTemplate> ToLocal(
     204             :       v8::internal::Handle<v8::internal::ObjectTemplateInfo> obj);
     205             :   static inline Local<Signature> SignatureToLocal(
     206             :       v8::internal::Handle<v8::internal::FunctionTemplateInfo> obj);
     207             :   static inline Local<AccessorSignature> AccessorSignatureToLocal(
     208             :       v8::internal::Handle<v8::internal::FunctionTemplateInfo> obj);
     209             :   static inline Local<External> ExternalToLocal(
     210             :       v8::internal::Handle<v8::internal::JSObject> obj);
     211             :   static inline Local<NativeWeakMap> NativeWeakMapToLocal(
     212             :       v8::internal::Handle<v8::internal::JSWeakMap> obj);
     213             :   static inline Local<Function> CallableToLocal(
     214             :       v8::internal::Handle<v8::internal::JSReceiver> obj);
     215             : 
     216             : #define DECLARE_OPEN_HANDLE(From, To) \
     217             :   static inline v8::internal::Handle<v8::internal::To> \
     218             :       OpenHandle(const From* that, bool allow_empty_handle = false);
     219             : 
     220             : OPEN_HANDLE_LIST(DECLARE_OPEN_HANDLE)
     221             : 
     222             : #undef DECLARE_OPEN_HANDLE
     223             : 
     224             :   template<class From, class To>
     225             :   static inline Local<To> Convert(v8::internal::Handle<From> obj) {
     226             :     DCHECK(obj.is_null() ||
     227             :            (obj->IsSmi() ||
     228             :             !obj->IsTheHole(i::HeapObject::cast(*obj)->GetIsolate())));
     229             :     return Local<To>(reinterpret_cast<To*>(obj.location()));
     230             :   }
     231             : 
     232             :   template <class T>
     233             :   static inline v8::internal::Handle<v8::internal::Object> OpenPersistent(
     234             :       const v8::Persistent<T>& persistent) {
     235             :     return v8::internal::Handle<v8::internal::Object>(
     236          18 :         reinterpret_cast<v8::internal::Object**>(persistent.val_));
     237             :   }
     238             : 
     239             :   template <class T>
     240             :   static inline v8::internal::Handle<v8::internal::Object> OpenPersistent(
     241             :       v8::Persistent<T>* persistent) {
     242             :     return OpenPersistent(*persistent);
     243             :   }
     244             : 
     245             :   template <class From, class To>
     246             :   static inline v8::internal::Handle<To> OpenHandle(v8::Local<From> handle) {
     247             :     return OpenHandle(*handle);
     248             :   }
     249             : 
     250             :  private:
     251             :   static void ReportApiFailure(const char* location, const char* message);
     252             : };
     253             : 
     254             : 
     255             : template <class T>
     256             : inline T* ToApi(v8::internal::Handle<v8::internal::Object> obj) {
     257             :   return reinterpret_cast<T*>(obj.location());
     258             : }
     259             : 
     260             : template <class T>
     261             : inline v8::Local<T> ToApiHandle(
     262             :     v8::internal::Handle<v8::internal::Object> obj) {
     263             :   return Utils::Convert<v8::internal::Object, T>(obj);
     264             : }
     265             : 
     266             : 
     267             : template <class T>
     268             : inline bool ToLocal(v8::internal::MaybeHandle<v8::internal::Object> maybe,
     269             :                     Local<T>* local) {
     270             :   v8::internal::Handle<v8::internal::Object> handle;
     271    30147015 :   if (maybe.ToHandle(&handle)) {
     272             :     *local = Utils::Convert<v8::internal::Object, T>(handle);
     273             :     return true;
     274             :   }
     275             :   return false;
     276             : }
     277             : 
     278             : 
     279             : // Implementations of ToLocal
     280             : 
     281             : #define MAKE_TO_LOCAL(Name, From, To)                                       \
     282             :   Local<v8::To> Utils::Name(v8::internal::Handle<v8::internal::From> obj) { \
     283             :     return Convert<v8::internal::From, v8::To>(obj);  \
     284             :   }
     285             : 
     286             : 
     287             : #define MAKE_TO_LOCAL_TYPED_ARRAY(Type, typeName, TYPE, ctype, size)  \
     288             :   Local<v8::Type##Array> Utils::ToLocal##Type##Array(                 \
     289             :       v8::internal::Handle<v8::internal::JSTypedArray> obj) {         \
     290             :     DCHECK(obj->type() == v8::internal::kExternal##Type##Array);      \
     291             :     return Convert<v8::internal::JSTypedArray, v8::Type##Array>(obj); \
     292             :   }
     293             : 
     294             : 
     295             : MAKE_TO_LOCAL(ToLocal, Context, Context)
     296             : MAKE_TO_LOCAL(ToLocal, Object, Value)
     297             : MAKE_TO_LOCAL(ToLocal, Module, Module)
     298             : MAKE_TO_LOCAL(ToLocal, Name, Name)
     299        1089 : MAKE_TO_LOCAL(ToLocal, String, String)
     300             : MAKE_TO_LOCAL(ToLocal, Symbol, Symbol)
     301             : MAKE_TO_LOCAL(ToLocal, JSRegExp, RegExp)
     302             : MAKE_TO_LOCAL(ToLocal, JSReceiver, Object)
     303             : MAKE_TO_LOCAL(ToLocal, JSObject, Object)
     304             : MAKE_TO_LOCAL(ToLocal, JSFunction, Function)
     305             : MAKE_TO_LOCAL(ToLocal, JSArray, Array)
     306             : MAKE_TO_LOCAL(ToLocal, JSMap, Map)
     307             : MAKE_TO_LOCAL(ToLocal, JSSet, Set)
     308             : MAKE_TO_LOCAL(ToLocal, JSProxy, Proxy)
     309             : MAKE_TO_LOCAL(ToLocal, JSArrayBuffer, ArrayBuffer)
     310             : MAKE_TO_LOCAL(ToLocal, JSArrayBufferView, ArrayBufferView)
     311             : MAKE_TO_LOCAL(ToLocal, JSDataView, DataView)
     312             : MAKE_TO_LOCAL(ToLocal, JSTypedArray, TypedArray)
     313             : MAKE_TO_LOCAL(ToLocalShared, JSArrayBuffer, SharedArrayBuffer)
     314             : 
     315             : TYPED_ARRAYS(MAKE_TO_LOCAL_TYPED_ARRAY)
     316             : 
     317             : MAKE_TO_LOCAL(ToLocal, FunctionTemplateInfo, FunctionTemplate)
     318             : MAKE_TO_LOCAL(ToLocal, ObjectTemplateInfo, ObjectTemplate)
     319             : MAKE_TO_LOCAL(SignatureToLocal, FunctionTemplateInfo, Signature)
     320             : MAKE_TO_LOCAL(AccessorSignatureToLocal, FunctionTemplateInfo, AccessorSignature)
     321             : MAKE_TO_LOCAL(MessageToLocal, Object, Message)
     322             : MAKE_TO_LOCAL(PromiseToLocal, JSObject, Promise)
     323             : MAKE_TO_LOCAL(PromiseToDynamicImportResult, JSPromise, DynamicImportResult)
     324             : MAKE_TO_LOCAL(StackTraceToLocal, FixedArray, StackTrace)
     325             : MAKE_TO_LOCAL(StackFrameToLocal, StackFrameInfo, StackFrame)
     326             : MAKE_TO_LOCAL(NumberToLocal, Object, Number)
     327             : MAKE_TO_LOCAL(IntegerToLocal, Object, Integer)
     328             : MAKE_TO_LOCAL(Uint32ToLocal, Object, Uint32)
     329             : MAKE_TO_LOCAL(ExternalToLocal, JSObject, External)
     330             : MAKE_TO_LOCAL(NativeWeakMapToLocal, JSWeakMap, NativeWeakMap)
     331             : MAKE_TO_LOCAL(CallableToLocal, JSReceiver, Function)
     332             : 
     333             : #undef MAKE_TO_LOCAL_TYPED_ARRAY
     334             : #undef MAKE_TO_LOCAL
     335             : 
     336             : 
     337             : // Implementations of OpenHandle
     338             : 
     339             : #define MAKE_OPEN_HANDLE(From, To)                                             \
     340             :   v8::internal::Handle<v8::internal::To> Utils::OpenHandle(                    \
     341             :       const v8::From* that, bool allow_empty_handle) {                         \
     342             :     DCHECK(allow_empty_handle || that != NULL);                                \
     343             :     DCHECK(that == NULL ||                                                     \
     344             :            (*reinterpret_cast<v8::internal::Object* const*>(that))->Is##To()); \
     345             :     return v8::internal::Handle<v8::internal::To>(                             \
     346             :         reinterpret_cast<v8::internal::To**>(const_cast<v8::From*>(that)));    \
     347             :   }
     348             : 
     349         210 : OPEN_HANDLE_LIST(MAKE_OPEN_HANDLE)
     350             : 
     351             : #undef MAKE_OPEN_HANDLE
     352             : #undef OPEN_HANDLE_LIST
     353             : 
     354             : extern Isolate* IsolateNewImpl(internal::Isolate* isolate,
     355             :                                const Isolate::CreateParams& params);
     356             : 
     357             : namespace internal {
     358             : 
     359             : class V8_EXPORT_PRIVATE DeferredHandles {
     360             :  public:
     361             :   ~DeferredHandles();
     362             : 
     363             :  private:
     364             :   DeferredHandles(Object** first_block_limit, Isolate* isolate)
     365             :       : next_(NULL),
     366             :         previous_(NULL),
     367             :         first_block_limit_(first_block_limit),
     368      150621 :         isolate_(isolate) {
     369      150621 :     isolate->LinkDeferredHandles(this);
     370             :   }
     371             : 
     372             :   void Iterate(RootVisitor* v);
     373             : 
     374             :   List<Object**> blocks_;
     375             :   DeferredHandles* next_;
     376             :   DeferredHandles* previous_;
     377             :   Object** first_block_limit_;
     378             :   Isolate* isolate_;
     379             : 
     380             :   friend class HandleScopeImplementer;
     381             :   friend class Isolate;
     382             : };
     383             : 
     384             : 
     385             : // This class is here in order to be able to declare it a friend of
     386             : // HandleScope.  Moving these methods to be members of HandleScope would be
     387             : // neat in some ways, but it would expose internal implementation details in
     388             : // our public header file, which is undesirable.
     389             : //
     390             : // An isolate has a single instance of this class to hold the current thread's
     391             : // data. In multithreaded V8 programs this data is copied in and out of storage
     392             : // so that the currently executing thread always has its own copy of this
     393             : // data.
     394             : class HandleScopeImplementer {
     395             :  public:
     396             :   explicit HandleScopeImplementer(Isolate* isolate)
     397             :       : isolate_(isolate),
     398             :         blocks_(0),
     399             :         entered_contexts_(0),
     400             :         saved_contexts_(0),
     401             :         microtask_context_(nullptr),
     402             :         spare_(NULL),
     403             :         call_depth_(0),
     404             :         microtasks_depth_(0),
     405             :         microtasks_suppressions_(0),
     406             :         entered_context_count_during_microtasks_(0),
     407             : #ifdef DEBUG
     408             :         debug_microtasks_depth_(0),
     409             : #endif
     410             :         microtasks_policy_(v8::MicrotasksPolicy::kAuto),
     411      121564 :         last_handle_before_deferred_block_(NULL) { }
     412             : 
     413       59285 :   ~HandleScopeImplementer() {
     414       59285 :     DeleteArray(spare_);
     415       59285 :   }
     416             : 
     417             :   // Threading support for handle data.
     418             :   static int ArchiveSpacePerThread();
     419             :   char* RestoreThread(char* from);
     420             :   char* ArchiveThread(char* to);
     421             :   void FreeThreadResources();
     422             : 
     423             :   // Garbage collection support.
     424             :   void Iterate(v8::internal::RootVisitor* v);
     425             :   static char* Iterate(v8::internal::RootVisitor* v, char* data);
     426             : 
     427             :   inline internal::Object** GetSpareOrNewBlock();
     428             :   inline void DeleteExtensions(internal::Object** prev_limit);
     429             : 
     430             :   // Call depth represents nested v8 api calls.
     431   242526806 :   inline void IncrementCallDepth() {call_depth_++;}
     432   242526784 :   inline void DecrementCallDepth() {call_depth_--;}
     433       19710 :   inline bool CallDepthIsZero() { return call_depth_ == 0; }
     434             : 
     435             :   // Microtasks scope depth represents nested scopes controlling microtasks
     436             :   // invocation, which happens when depth reaches zero.
     437       75091 :   inline void IncrementMicrotasksScopeDepth() {microtasks_depth_++;}
     438       75091 :   inline void DecrementMicrotasksScopeDepth() {microtasks_depth_--;}
     439             :   inline int GetMicrotasksScopeDepth() { return microtasks_depth_; }
     440             : 
     441             :   // Possibly nested microtasks suppression scopes prevent microtasks
     442             :   // from running.
     443       69057 :   inline void IncrementMicrotasksSuppressions() {microtasks_suppressions_++;}
     444       69057 :   inline void DecrementMicrotasksSuppressions() {microtasks_suppressions_--;}
     445             :   inline bool HasMicrotasksSuppressions() { return !!microtasks_suppressions_; }
     446             : 
     447             : #ifdef DEBUG
     448             :   // In debug we check that calls not intended to invoke microtasks are
     449             :   // still correctly wrapped with microtask scopes.
     450             :   inline void IncrementDebugMicrotasksScopeDepth() {debug_microtasks_depth_++;}
     451             :   inline void DecrementDebugMicrotasksScopeDepth() {debug_microtasks_depth_--;}
     452             :   inline bool DebugMicrotasksScopeDepthIsZero() {
     453             :     return debug_microtasks_depth_ == 0;
     454             :   }
     455             : #endif
     456             : 
     457             :   inline void set_microtasks_policy(v8::MicrotasksPolicy policy);
     458             :   inline v8::MicrotasksPolicy microtasks_policy() const;
     459             : 
     460             :   inline void EnterContext(Handle<Context> context);
     461             :   inline void LeaveContext();
     462             :   inline bool LastEnteredContextWas(Handle<Context> context);
     463             : 
     464             :   // Returns the last entered context or an empty handle if no
     465             :   // contexts have been entered.
     466             :   inline Handle<Context> LastEnteredContext();
     467             : 
     468             :   inline void EnterMicrotaskContext(Handle<Context> context);
     469             :   inline void LeaveMicrotaskContext();
     470             :   inline Handle<Context> MicrotaskContext();
     471             :   inline bool MicrotaskContextIsLastEnteredContext() const {
     472     1799799 :     return microtask_context_ &&
     473           0 :            entered_context_count_during_microtasks_ ==
     474           0 :                entered_contexts_.length();
     475             :   }
     476             : 
     477             :   inline void SaveContext(Context* context);
     478             :   inline Context* RestoreContext();
     479             :   inline bool HasSavedContexts();
     480             : 
     481             :   inline List<internal::Object**>* blocks() { return &blocks_; }
     482             :   Isolate* isolate() const { return isolate_; }
     483             : 
     484             :   void ReturnBlock(Object** block) {
     485             :     DCHECK(block != NULL);
     486      151151 :     if (spare_ != NULL) DeleteArray(spare_);
     487      151151 :     spare_ = block;
     488             :   }
     489             : 
     490             :  private:
     491             :   void ResetAfterArchive() {
     492             :     blocks_.Initialize(0);
     493             :     entered_contexts_.Initialize(0);
     494             :     saved_contexts_.Initialize(0);
     495       22574 :     microtask_context_ = nullptr;
     496       22574 :     entered_context_count_during_microtasks_ = 0;
     497       22574 :     spare_ = NULL;
     498       22574 :     last_handle_before_deferred_block_ = NULL;
     499       22574 :     call_depth_ = 0;
     500             :   }
     501             : 
     502        6863 :   void Free() {
     503             :     DCHECK(blocks_.length() == 0);
     504             :     DCHECK(entered_contexts_.length() == 0);
     505             :     DCHECK(saved_contexts_.length() == 0);
     506             :     DCHECK(!microtask_context_);
     507             :     blocks_.Free();
     508             :     entered_contexts_.Free();
     509             :     saved_contexts_.Free();
     510        6863 :     if (spare_ != NULL) {
     511             :       DeleteArray(spare_);
     512        6784 :       spare_ = NULL;
     513             :     }
     514             :     DCHECK(call_depth_ == 0);
     515        6863 :   }
     516             : 
     517             :   void BeginDeferredScope();
     518             :   DeferredHandles* Detach(Object** prev_limit);
     519             : 
     520             :   Isolate* isolate_;
     521             :   List<internal::Object**> blocks_;
     522             :   // Used as a stack to keep track of entered contexts.
     523             :   List<Context*> entered_contexts_;
     524             :   // Used as a stack to keep track of saved contexts.
     525             :   List<Context*> saved_contexts_;
     526             :   Context* microtask_context_;
     527             :   Object** spare_;
     528             :   int call_depth_;
     529             :   int microtasks_depth_;
     530             :   int microtasks_suppressions_;
     531             :   int entered_context_count_during_microtasks_;
     532             : #ifdef DEBUG
     533             :   int debug_microtasks_depth_;
     534             : #endif
     535             :   v8::MicrotasksPolicy microtasks_policy_;
     536             :   Object** last_handle_before_deferred_block_;
     537             :   // This is only used for threading support.
     538             :   HandleScopeData handle_scope_data_;
     539             : 
     540             :   void IterateThis(RootVisitor* v);
     541             :   char* RestoreThreadHelper(char* from);
     542             :   char* ArchiveThreadHelper(char* to);
     543             : 
     544             :   friend class DeferredHandles;
     545             :   friend class DeferredHandleScope;
     546             : 
     547             :   DISALLOW_COPY_AND_ASSIGN(HandleScopeImplementer);
     548             : };
     549             : 
     550             : 
     551             : const int kHandleBlockSize = v8::internal::KB - 2;  // fit in one page
     552             : 
     553             : 
     554             : void HandleScopeImplementer::set_microtasks_policy(
     555             :     v8::MicrotasksPolicy policy) {
     556        1477 :   microtasks_policy_ = policy;
     557             : }
     558             : 
     559             : 
     560             : v8::MicrotasksPolicy HandleScopeImplementer::microtasks_policy() const {
     561             :   return microtasks_policy_;
     562             : }
     563             : 
     564             : 
     565             : void HandleScopeImplementer::SaveContext(Context* context) {
     566     3232151 :   saved_contexts_.Add(context);
     567             : }
     568             : 
     569             : 
     570             : Context* HandleScopeImplementer::RestoreContext() {
     571     3215962 :   return saved_contexts_.RemoveLast();
     572             : }
     573             : 
     574             : 
     575             : bool HandleScopeImplementer::HasSavedContexts() {
     576             :   return !saved_contexts_.is_empty();
     577             : }
     578             : 
     579             : 
     580             : void HandleScopeImplementer::EnterContext(Handle<Context> context) {
     581     3232139 :   entered_contexts_.Add(*context);
     582             : }
     583             : 
     584             : 
     585             : void HandleScopeImplementer::LeaveContext() {
     586     3215959 :   entered_contexts_.RemoveLast();
     587             : }
     588             : 
     589             : 
     590             : bool HandleScopeImplementer::LastEnteredContextWas(Handle<Context> context) {
     591   727607098 :   return !entered_contexts_.is_empty() && entered_contexts_.last() == *context;
     592             : }
     593             : 
     594             : 
     595     1861834 : Handle<Context> HandleScopeImplementer::LastEnteredContext() {
     596     1861834 :   if (entered_contexts_.is_empty()) return Handle<Context>::null();
     597     3723668 :   return Handle<Context>(entered_contexts_.last());
     598             : }
     599             : 
     600             : void HandleScopeImplementer::EnterMicrotaskContext(Handle<Context> context) {
     601             :   DCHECK(!microtask_context_);
     602      255467 :   microtask_context_ = *context;
     603      255467 :   entered_context_count_during_microtasks_ = entered_contexts_.length();
     604             : }
     605             : 
     606             : void HandleScopeImplementer::LeaveMicrotaskContext() {
     607             :   DCHECK(microtask_context_);
     608      255467 :   microtask_context_ = nullptr;
     609      255467 :   entered_context_count_during_microtasks_ = 0;
     610             : }
     611             : 
     612           0 : Handle<Context> HandleScopeImplementer::MicrotaskContext() {
     613           0 :   if (microtask_context_) return Handle<Context>(microtask_context_);
     614             :   return Handle<Context>::null();
     615             : }
     616             : 
     617             : // If there's a spare block, use it for growing the current scope.
     618             : internal::Object** HandleScopeImplementer::GetSpareOrNewBlock() {
     619     1985617 :   internal::Object** block = (spare_ != NULL) ?
     620             :       spare_ :
     621     1985617 :       NewArray<internal::Object*>(kHandleBlockSize);
     622     1985617 :   spare_ = NULL;
     623             :   return block;
     624             : }
     625             : 
     626             : 
     627     1547607 : void HandleScopeImplementer::DeleteExtensions(internal::Object** prev_limit) {
     628     4929669 :   while (!blocks_.is_empty()) {
     629     5914342 :     internal::Object** block_start = blocks_.last();
     630     2532280 :     internal::Object** block_limit = block_start + kHandleBlockSize;
     631             : 
     632             :     // SealHandleScope may make the prev_limit to point inside the block.
     633     2532280 :     if (block_start <= prev_limit && prev_limit <= block_limit) {
     634             : #ifdef ENABLE_HANDLE_ZAPPING
     635             :       internal::HandleScope::ZapRange(prev_limit, block_limit);
     636             : #endif
     637             :       break;
     638             :     }
     639             : 
     640     1834450 :     blocks_.RemoveLast();
     641             : #ifdef ENABLE_HANDLE_ZAPPING
     642             :     internal::HandleScope::ZapRange(block_start, block_limit);
     643             : #endif
     644     1834455 :     if (spare_ != NULL) {
     645             :       DeleteArray(spare_);
     646             :     }
     647     1834455 :     spare_ = block_start;
     648             :   }
     649             :   DCHECK((blocks_.is_empty() && prev_limit == NULL) ||
     650             :          (!blocks_.is_empty() && prev_limit != NULL));
     651     1547612 : }
     652             : 
     653             : // Interceptor functions called from generated inline caches to notify
     654             : // CPU profiler that external callbacks are invoked.
     655             : void InvokeAccessorGetterCallback(
     656             :     v8::Local<v8::Name> property,
     657             :     const v8::PropertyCallbackInfo<v8::Value>& info,
     658             :     v8::AccessorNameGetterCallback getter);
     659             : 
     660             : void InvokeFunctionCallback(const v8::FunctionCallbackInfo<v8::Value>& info,
     661             :                             v8::FunctionCallback callback);
     662             : 
     663             : class Testing {
     664             :  public:
     665       40297 :   static v8::Testing::StressType stress_type() { return stress_type_; }
     666             :   static void set_stress_type(v8::Testing::StressType stress_type) {
     667        8061 :     stress_type_ = stress_type;
     668             :   }
     669             : 
     670             :  private:
     671             :   static v8::Testing::StressType stress_type_;
     672             : };
     673             : 
     674             : }  // namespace internal
     675             : }  // namespace v8
     676             : 
     677             : #endif  // V8_API_H_

Generated by: LCOV version 1.10