| OLD | NEW |
| 1 // Copyright 2007-2009 the V8 project authors. All rights reserved. | 1 // Copyright 2007-2009 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 92 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 103 class Data; | 103 class Data; |
| 104 class AccessorInfo; | 104 class AccessorInfo; |
| 105 class StackTrace; | 105 class StackTrace; |
| 106 class StackFrame; | 106 class StackFrame; |
| 107 | 107 |
| 108 namespace internal { | 108 namespace internal { |
| 109 | 109 |
| 110 class Arguments; | 110 class Arguments; |
| 111 class Object; | 111 class Object; |
| 112 class Heap; | 112 class Heap; |
| 113 class Top; | 113 class HeapObject; |
| 114 class Isolate; |
| 114 } | 115 } |
| 115 | 116 |
| 116 | 117 |
| 117 // --- W e a k H a n d l e s | 118 // --- W e a k H a n d l e s |
| 118 | 119 |
| 119 | 120 |
| 120 /** | 121 /** |
| 121 * A weak reference callback function. | 122 * A weak reference callback function. |
| 122 * | 123 * |
| 123 * This callback should either explicitly invoke Dispose on |object| if | 124 * This callback should either explicitly invoke Dispose on |object| if |
| (...skipping 312 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 436 | 437 |
| 437 /** | 438 /** |
| 438 * Counts the number of allocated handles. | 439 * Counts the number of allocated handles. |
| 439 */ | 440 */ |
| 440 static int NumberOfHandles(); | 441 static int NumberOfHandles(); |
| 441 | 442 |
| 442 /** | 443 /** |
| 443 * Creates a new handle with the given value. | 444 * Creates a new handle with the given value. |
| 444 */ | 445 */ |
| 445 static internal::Object** CreateHandle(internal::Object* value); | 446 static internal::Object** CreateHandle(internal::Object* value); |
| 447 // Faster version, uses HeapObject to obtain the current Isolate. |
| 448 static internal::Object** CreateHandle(internal::HeapObject* value); |
| 446 | 449 |
| 447 private: | 450 private: |
| 448 // Make it impossible to create heap-allocated or illegal handle | 451 // Make it impossible to create heap-allocated or illegal handle |
| 449 // scopes by disallowing certain operations. | 452 // scopes by disallowing certain operations. |
| 450 HandleScope(const HandleScope&); | 453 HandleScope(const HandleScope&); |
| 451 void operator=(const HandleScope&); | 454 void operator=(const HandleScope&); |
| 452 void* operator new(size_t size); | 455 void* operator new(size_t size); |
| 453 void operator delete(void*, size_t); | 456 void operator delete(void*, size_t); |
| 454 | 457 |
| 455 // This Data class is accessible internally as HandleScopeData through a | 458 // This Data class is accessible internally as HandleScopeData through a |
| 456 // typedef in the ImplementationUtilities class. | 459 // typedef in the ImplementationUtilities class. |
| 457 class V8EXPORT Data { | 460 class V8EXPORT Data { |
| 458 public: | 461 public: |
| 459 internal::Object** next; | 462 internal::Object** next; |
| 460 internal::Object** limit; | 463 internal::Object** limit; |
| 461 int level; | 464 int level; |
| 462 | |
| 463 inline void Initialize() { | 465 inline void Initialize() { |
| 464 next = limit = NULL; | 466 next = limit = NULL; |
| 465 level = 0; | 467 level = 0; |
| 466 } | 468 } |
| 467 }; | 469 }; |
| 468 | 470 |
| 469 void Leave(); | 471 void Leave(); |
| 470 | 472 |
| 473 internal::Isolate* isolate_; |
| 471 internal::Object** prev_next_; | 474 internal::Object** prev_next_; |
| 472 internal::Object** prev_limit_; | 475 internal::Object** prev_limit_; |
| 473 | 476 |
| 474 // Allow for the active closing of HandleScopes which allows to pass a handle | 477 // Allow for the active closing of HandleScopes which allows to pass a handle |
| 475 // from the HandleScope being closed to the next top most HandleScope. | 478 // from the HandleScope being closed to the next top most HandleScope. |
| 476 bool is_closed_; | 479 bool is_closed_; |
| 477 internal::Object** RawClose(internal::Object** value); | 480 internal::Object** RawClose(internal::Object** value); |
| 478 | 481 |
| 479 friend class ImplementationUtilities; | 482 friend class ImplementationUtilities; |
| 480 }; | 483 }; |
| (...skipping 2060 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2541 size_t used_heap_size_; | 2544 size_t used_heap_size_; |
| 2542 size_t heap_size_limit_; | 2545 size_t heap_size_limit_; |
| 2543 | 2546 |
| 2544 friend class V8; | 2547 friend class V8; |
| 2545 }; | 2548 }; |
| 2546 | 2549 |
| 2547 | 2550 |
| 2548 class RetainedObjectInfo; | 2551 class RetainedObjectInfo; |
| 2549 | 2552 |
| 2550 /** | 2553 /** |
| 2554 * Isolate represents an isolated instance of the V8 engine. V8 |
| 2555 * isolates have completely separate states. Objects from one isolate |
| 2556 * must not be used in other isolates. When V8 is initialized a |
| 2557 * default isolate is implicitly created and entered. The embedder |
| 2558 * can create additional isolates and use them in parallel in multiple |
| 2559 * threads. An isolate can be entered by at most one thread at any |
| 2560 * given time. The Locker/Unlocker API can be used to synchronize. |
| 2561 */ |
| 2562 class V8EXPORT Isolate { |
| 2563 public: |
| 2564 /** |
| 2565 * Stack-allocated class which sets the isolate for all operations |
| 2566 * executed within a local scope. |
| 2567 */ |
| 2568 class V8EXPORT Scope { |
| 2569 public: |
| 2570 explicit Scope(Isolate* isolate) : isolate_(isolate) { |
| 2571 isolate->Enter(); |
| 2572 } |
| 2573 |
| 2574 ~Scope() { isolate_->Exit(); } |
| 2575 |
| 2576 private: |
| 2577 Isolate* const isolate_; |
| 2578 |
| 2579 // Prevent copying of Scope objects. |
| 2580 Scope(const Scope&); |
| 2581 Scope& operator=(const Scope&); |
| 2582 }; |
| 2583 |
| 2584 /** |
| 2585 * Creates a new isolate. Does not change the currently entered |
| 2586 * isolate. |
| 2587 * |
| 2588 * When an isolate is no longer used its resources should be freed |
| 2589 * by calling Dispose(). Using the delete operator is not allowed. |
| 2590 */ |
| 2591 static Isolate* New(); |
| 2592 |
| 2593 /** |
| 2594 * Returns the entered isolate for the current thread or NULL in |
| 2595 * case there is no current isolate. |
| 2596 */ |
| 2597 static Isolate* GetCurrent(); |
| 2598 |
| 2599 /** |
| 2600 * Methods below this point require holding a lock (using Locker) in |
| 2601 * a multi-threaded environment. |
| 2602 */ |
| 2603 |
| 2604 /** |
| 2605 * Sets this isolate as the entered one for the current thread. |
| 2606 * Saves the previously entered one (if any), so that it can be |
| 2607 * restored when exiting. Re-entering an isolate is allowed. |
| 2608 */ |
| 2609 void Enter(); |
| 2610 |
| 2611 /** |
| 2612 * Exits this isolate by restoring the previously entered one in the |
| 2613 * current thread. The isolate may still stay the same, if it was |
| 2614 * entered more than once. |
| 2615 * |
| 2616 * Requires: this == Isolate::GetCurrent(). |
| 2617 */ |
| 2618 void Exit(); |
| 2619 |
| 2620 /** |
| 2621 * Disposes the isolate. The isolate must not be entered by any |
| 2622 * thread to be disposable. |
| 2623 */ |
| 2624 void Dispose(); |
| 2625 |
| 2626 private: |
| 2627 |
| 2628 Isolate(); |
| 2629 Isolate(const Isolate&); |
| 2630 ~Isolate(); |
| 2631 Isolate& operator=(const Isolate&); |
| 2632 void* operator new(size_t size); |
| 2633 void operator delete(void*, size_t); |
| 2634 }; |
| 2635 |
| 2636 |
| 2637 /** |
| 2551 * Container class for static utility functions. | 2638 * Container class for static utility functions. |
| 2552 */ | 2639 */ |
| 2553 class V8EXPORT V8 { | 2640 class V8EXPORT V8 { |
| 2554 public: | 2641 public: |
| 2555 /** Set the callback to invoke in case of fatal errors. */ | 2642 /** Set the callback to invoke in case of fatal errors. */ |
| 2556 static void SetFatalErrorHandler(FatalErrorCallback that); | 2643 static void SetFatalErrorHandler(FatalErrorCallback that); |
| 2557 | 2644 |
| 2558 /** | 2645 /** |
| 2559 * Ignore out-of-memory exceptions. | 2646 * Ignore out-of-memory exceptions. |
| 2560 * | 2647 * |
| (...skipping 304 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2865 * continue the propagation of the termination exception if needed. | 2952 * continue the propagation of the termination exception if needed. |
| 2866 * | 2953 * |
| 2867 * The thread id passed to TerminateExecution must have been | 2954 * The thread id passed to TerminateExecution must have been |
| 2868 * obtained by calling GetCurrentThreadId on the thread in question. | 2955 * obtained by calling GetCurrentThreadId on the thread in question. |
| 2869 * | 2956 * |
| 2870 * \param thread_id The thread id of the thread to terminate. | 2957 * \param thread_id The thread id of the thread to terminate. |
| 2871 */ | 2958 */ |
| 2872 static void TerminateExecution(int thread_id); | 2959 static void TerminateExecution(int thread_id); |
| 2873 | 2960 |
| 2874 /** | 2961 /** |
| 2875 * Forcefully terminate the current thread of JavaScript execution. | 2962 * Forcefully terminate the current thread of JavaScript execution |
| 2963 * in the given isolate. If no isolate is provided, the default |
| 2964 * isolate is used. |
| 2876 * | 2965 * |
| 2877 * This method can be used by any thread even if that thread has not | 2966 * This method can be used by any thread even if that thread has not |
| 2878 * acquired the V8 lock with a Locker object. | 2967 * acquired the V8 lock with a Locker object. |
| 2968 * |
| 2969 * \param isolate The isolate in which to terminate the current JS execution. |
| 2879 */ | 2970 */ |
| 2880 static void TerminateExecution(); | 2971 static void TerminateExecution(Isolate* isolate = NULL); |
| 2881 | 2972 |
| 2882 /** | 2973 /** |
| 2883 * Is V8 terminating JavaScript execution. | 2974 * Is V8 terminating JavaScript execution. |
| 2884 * | 2975 * |
| 2885 * Returns true if JavaScript execution is currently terminating | 2976 * Returns true if JavaScript execution is currently terminating |
| 2886 * because of a call to TerminateExecution. In that case there are | 2977 * because of a call to TerminateExecution. In that case there are |
| 2887 * still JavaScript frames on the stack and the termination | 2978 * still JavaScript frames on the stack and the termination |
| 2888 * exception is still active. | 2979 * exception is still active. |
| 2889 */ | 2980 */ |
| 2890 static bool IsExecutionTerminating(); | 2981 static bool IsExecutionTerminating(); |
| (...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3048 | 3139 |
| 3049 private: | 3140 private: |
| 3050 void* next_; | 3141 void* next_; |
| 3051 void* exception_; | 3142 void* exception_; |
| 3052 void* message_; | 3143 void* message_; |
| 3053 bool is_verbose_ : 1; | 3144 bool is_verbose_ : 1; |
| 3054 bool can_continue_ : 1; | 3145 bool can_continue_ : 1; |
| 3055 bool capture_message_ : 1; | 3146 bool capture_message_ : 1; |
| 3056 bool rethrow_ : 1; | 3147 bool rethrow_ : 1; |
| 3057 | 3148 |
| 3058 friend class v8::internal::Top; | 3149 friend class v8::internal::Isolate; |
| 3059 }; | 3150 }; |
| 3060 | 3151 |
| 3061 | 3152 |
| 3062 // --- C o n t e x t --- | 3153 // --- C o n t e x t --- |
| 3063 | 3154 |
| 3064 | 3155 |
| 3065 /** | 3156 /** |
| 3066 * Ignore | 3157 * Ignore |
| 3067 */ | 3158 */ |
| 3068 class V8EXPORT ExtensionConfiguration { | 3159 class V8EXPORT ExtensionConfiguration { |
| (...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3211 private: | 3302 private: |
| 3212 friend class Value; | 3303 friend class Value; |
| 3213 friend class Script; | 3304 friend class Script; |
| 3214 friend class Object; | 3305 friend class Object; |
| 3215 friend class Function; | 3306 friend class Function; |
| 3216 }; | 3307 }; |
| 3217 | 3308 |
| 3218 | 3309 |
| 3219 /** | 3310 /** |
| 3220 * Multiple threads in V8 are allowed, but only one thread at a time | 3311 * Multiple threads in V8 are allowed, but only one thread at a time |
| 3221 * is allowed to use V8. The definition of 'using V8' includes | 3312 * is allowed to use any given V8 isolate. See Isolate class |
| 3222 * accessing handles or holding onto object pointers obtained from V8 | 3313 * comments. The definition of 'using V8 isolate' includes |
| 3223 * handles. It is up to the user of V8 to ensure (perhaps with | 3314 * accessing handles or holding onto object pointers obtained |
| 3224 * locking) that this constraint is not violated. | 3315 * from V8 handles while in the particular V8 isolate. It is up |
| 3316 * to the user of V8 to ensure (perhaps with locking) that this |
| 3317 * constraint is not violated. |
| 3225 * | 3318 * |
| 3226 * If you wish to start using V8 in a thread you can do this by constructing | 3319 * More then one thread and multiple V8 isolates can be used |
| 3227 * a v8::Locker object. After the code using V8 has completed for the | 3320 * without any locking if each isolate is created and accessed |
| 3228 * current thread you can call the destructor. This can be combined | 3321 * by a single thread only. For example, one thread can use |
| 3229 * with C++ scope-based construction as follows: | 3322 * multiple isolates or multiple threads can each create and run |
| 3323 * their own isolate. |
| 3324 * |
| 3325 * If you wish to start using V8 isolate in more then one thread |
| 3326 * you can do this by constructing a v8::Locker object to guard |
| 3327 * access to the isolate. After the code using V8 has completed |
| 3328 * for the current thread you can call the destructor. This can |
| 3329 * be combined with C++ scope-based construction as follows |
| 3330 * (assumes the default isolate that is used if not specified as |
| 3331 * a parameter for the Locker): |
| 3230 * | 3332 * |
| 3231 * \code | 3333 * \code |
| 3232 * ... | 3334 * ... |
| 3233 * { | 3335 * { |
| 3234 * v8::Locker locker; | 3336 * v8::Locker locker; |
| 3235 * ... | 3337 * ... |
| 3236 * // Code using V8 goes here. | 3338 * // Code using V8 goes here. |
| 3237 * ... | 3339 * ... |
| 3238 * } // Destructor called here | 3340 * } // Destructor called here |
| 3239 * \endcode | 3341 * \endcode |
| (...skipping 221 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3461 * This class exports constants and functionality from within v8 that | 3563 * This class exports constants and functionality from within v8 that |
| 3462 * is necessary to implement inline functions in the v8 api. Don't | 3564 * is necessary to implement inline functions in the v8 api. Don't |
| 3463 * depend on functions and constants defined here. | 3565 * depend on functions and constants defined here. |
| 3464 */ | 3566 */ |
| 3465 class Internals { | 3567 class Internals { |
| 3466 public: | 3568 public: |
| 3467 | 3569 |
| 3468 // These values match non-compiler-dependent values defined within | 3570 // These values match non-compiler-dependent values defined within |
| 3469 // the implementation of v8. | 3571 // the implementation of v8. |
| 3470 static const int kHeapObjectMapOffset = 0; | 3572 static const int kHeapObjectMapOffset = 0; |
| 3471 static const int kMapInstanceTypeOffset = kApiPointerSize + kApiIntSize; | 3573 static const int kMapInstanceTypeOffset = 1 * kApiPointerSize + kApiIntSize; |
| 3472 static const int kStringResourceOffset = | 3574 static const int kStringResourceOffset = |
| 3473 InternalConstants<kApiPointerSize>::kStringResourceOffset; | 3575 InternalConstants<kApiPointerSize>::kStringResourceOffset; |
| 3474 | 3576 |
| 3475 static const int kProxyProxyOffset = kApiPointerSize; | 3577 static const int kProxyProxyOffset = kApiPointerSize; |
| 3476 static const int kJSObjectHeaderSize = 3 * kApiPointerSize; | 3578 static const int kJSObjectHeaderSize = 3 * kApiPointerSize; |
| 3477 static const int kFullStringRepresentationMask = 0x07; | 3579 static const int kFullStringRepresentationMask = 0x07; |
| 3478 static const int kExternalTwoByteRepresentationTag = 0x02; | 3580 static const int kExternalTwoByteRepresentationTag = 0x02; |
| 3479 | 3581 |
| 3480 static const int kJSObjectType = 0xa0; | 3582 static const int kJSObjectType = 0xa0; |
| 3481 static const int kFirstNonstringType = 0x80; | 3583 static const int kFirstNonstringType = 0x80; |
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3518 static inline bool IsExternalTwoByteString(int instance_type) { | 3620 static inline bool IsExternalTwoByteString(int instance_type) { |
| 3519 int representation = (instance_type & kFullStringRepresentationMask); | 3621 int representation = (instance_type & kFullStringRepresentationMask); |
| 3520 return representation == kExternalTwoByteRepresentationTag; | 3622 return representation == kExternalTwoByteRepresentationTag; |
| 3521 } | 3623 } |
| 3522 | 3624 |
| 3523 template <typename T> | 3625 template <typename T> |
| 3524 static inline T ReadField(Object* ptr, int offset) { | 3626 static inline T ReadField(Object* ptr, int offset) { |
| 3525 uint8_t* addr = reinterpret_cast<uint8_t*>(ptr) + offset - kHeapObjectTag; | 3627 uint8_t* addr = reinterpret_cast<uint8_t*>(ptr) + offset - kHeapObjectTag; |
| 3526 return *reinterpret_cast<T*>(addr); | 3628 return *reinterpret_cast<T*>(addr); |
| 3527 } | 3629 } |
| 3630 |
| 3631 static inline bool CanCastToHeapObject(void* o) { return false; } |
| 3632 static inline bool CanCastToHeapObject(Context* o) { return true; } |
| 3633 static inline bool CanCastToHeapObject(String* o) { return true; } |
| 3634 static inline bool CanCastToHeapObject(Object* o) { return true; } |
| 3635 static inline bool CanCastToHeapObject(Message* o) { return true; } |
| 3636 static inline bool CanCastToHeapObject(StackTrace* o) { return true; } |
| 3637 static inline bool CanCastToHeapObject(StackFrame* o) { return true; } |
| 3528 }; | 3638 }; |
| 3529 | 3639 |
| 3530 } // namespace internal | 3640 } // namespace internal |
| 3531 | 3641 |
| 3532 | 3642 |
| 3533 template <class T> | 3643 template <class T> |
| 3534 Handle<T>::Handle() : val_(0) { } | 3644 Handle<T>::Handle() : val_(0) { } |
| 3535 | 3645 |
| 3536 | 3646 |
| 3537 template <class T> | 3647 template <class T> |
| 3538 Local<T>::Local() : Handle<T>() { } | 3648 Local<T>::Local() : Handle<T>() { } |
| 3539 | 3649 |
| 3540 | 3650 |
| 3541 template <class T> | 3651 template <class T> |
| 3542 Local<T> Local<T>::New(Handle<T> that) { | 3652 Local<T> Local<T>::New(Handle<T> that) { |
| 3543 if (that.IsEmpty()) return Local<T>(); | 3653 if (that.IsEmpty()) return Local<T>(); |
| 3544 internal::Object** p = reinterpret_cast<internal::Object**>(*that); | 3654 T* that_ptr = *that; |
| 3655 internal::Object** p = reinterpret_cast<internal::Object**>(that_ptr); |
| 3656 if (internal::Internals::CanCastToHeapObject(that_ptr)) { |
| 3657 return Local<T>(reinterpret_cast<T*>(HandleScope::CreateHandle( |
| 3658 reinterpret_cast<internal::HeapObject*>(*p)))); |
| 3659 } |
| 3545 return Local<T>(reinterpret_cast<T*>(HandleScope::CreateHandle(*p))); | 3660 return Local<T>(reinterpret_cast<T*>(HandleScope::CreateHandle(*p))); |
| 3546 } | 3661 } |
| 3547 | 3662 |
| 3548 | 3663 |
| 3549 template <class T> | 3664 template <class T> |
| 3550 Persistent<T> Persistent<T>::New(Handle<T> that) { | 3665 Persistent<T> Persistent<T>::New(Handle<T> that) { |
| 3551 if (that.IsEmpty()) return Persistent<T>(); | 3666 if (that.IsEmpty()) return Persistent<T>(); |
| 3552 internal::Object** p = reinterpret_cast<internal::Object**>(*that); | 3667 internal::Object** p = reinterpret_cast<internal::Object**>(*that); |
| 3553 return Persistent<T>(reinterpret_cast<T*>(V8::GlobalizeReference(p))); | 3668 return Persistent<T>(reinterpret_cast<T*>(V8::GlobalizeReference(p))); |
| 3554 } | 3669 } |
| (...skipping 316 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3871 | 3986 |
| 3872 | 3987 |
| 3873 } // namespace v8 | 3988 } // namespace v8 |
| 3874 | 3989 |
| 3875 | 3990 |
| 3876 #undef V8EXPORT | 3991 #undef V8EXPORT |
| 3877 #undef TYPE_CHECK | 3992 #undef TYPE_CHECK |
| 3878 | 3993 |
| 3879 | 3994 |
| 3880 #endif // V8_H_ | 3995 #endif // V8_H_ |
| OLD | NEW |