Changed structure of accessor arguments passing to allow accessor
authorchristian.plesner.hansen@gmail.com <christian.plesner.hansen@gmail.com@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Wed, 30 Sep 2009 12:25:46 +0000 (12:25 +0000)
committerchristian.plesner.hansen@gmail.com <christian.plesner.hansen@gmail.com@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Wed, 30 Sep 2009 12:25:46 +0000 (12:25 +0000)
callbacks to be called directly from native code.

Review URL: http://codereview.chromium.org/242050

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@2995 ce2b1a6d-e550-0410-aec6-3dcde31c8c00

include/v8.h
src/api.cc
src/arguments.h
src/handles.cc
src/heap.cc
src/objects.cc
src/objects.h
src/stub-cache.cc
src/v8threads.cc

index ca3bfef..2232cb9 100644 (file)
@@ -130,6 +130,7 @@ class Data;
 namespace internal {
 
 class Object;
+class Arguments;
 
 }
 
@@ -1408,17 +1409,13 @@ class V8EXPORT Arguments {
  */
 class V8EXPORT AccessorInfo {
  public:
-  inline AccessorInfo(Local<Object> self,
-                      Local<Value> data,
-                      Local<Object> holder)
-      : self_(self), data_(data), holder_(holder) { }
+  inline AccessorInfo(internal::Object** args)
+      : args_(args) { }
   inline Local<Value> Data() const;
   inline Local<Object> This() const;
   inline Local<Object> Holder() const;
  private:
-  Local<Object> self_;
-  Local<Value> data_;
-  Local<Object> holder_;
+  internal::Object** args_;
 };
 
 
@@ -2873,21 +2870,6 @@ int Arguments::Length() const {
 }
 
 
-Local<Value> AccessorInfo::Data() const {
-  return data_;
-}
-
-
-Local<Object> AccessorInfo::This() const {
-  return self_;
-}
-
-
-Local<Object> AccessorInfo::Holder() const {
-  return holder_;
-}
-
-
 template <class T>
 Local<T> HandleScope::Close(Handle<T> value) {
   internal::Object** before = reinterpret_cast<internal::Object**>(*value);
@@ -3085,6 +3067,21 @@ External* External::Cast(v8::Value* value) {
 }
 
 
+Local<Value> AccessorInfo::Data() const {
+  return Local<Value>(reinterpret_cast<Value*>(&args_[-3]));
+}
+
+
+Local<Object> AccessorInfo::This() const {
+  return Local<Object>(reinterpret_cast<Object*>(&args_[0]));
+}
+
+
+Local<Object> AccessorInfo::Holder() const {
+  return Local<Object>(reinterpret_cast<Object*>(&args_[-1]));
+}
+
+
 /**
  * \example shell.cc
  * A simple shell that takes a list of expressions on the
index c859f12..f8c8978 100644 (file)
@@ -28,6 +28,7 @@
 #include "v8.h"
 
 #include "api.h"
+#include "arguments.h"
 #include "bootstrapper.h"
 #include "compiler.h"
 #include "debug.h"
index 80f9006..fbd8212 100644 (file)
@@ -45,6 +45,9 @@ namespace internal {
 
 class Arguments BASE_EMBEDDED {
  public:
+  Arguments(int length, Object** arguments)
+      : length_(length), arguments_(arguments) { }
+
   Object*& operator[] (int index) {
     ASSERT(0 <= index && index < length_);
     return arguments_[-index];
@@ -60,12 +63,35 @@ class Arguments BASE_EMBEDDED {
 
   // Get the total number of arguments including the receiver.
   int length() const { return length_; }
+  
+  Object** arguments() { return arguments_; }
 
  private:
   int length_;
   Object** arguments_;
 };
 
+
+// Cursom arguments replicate a small segment of stack that can be
+// accessed through an Arguments object the same way the actual stack
+// can.
+class CustomArguments : public Relocatable {
+public:
+  inline CustomArguments(Object *data,
+                         JSObject *self,
+                         JSObject *holder) {
+    values_[3] = self;
+    values_[2] = holder;
+    values_[1] = Smi::FromInt(0);
+    values_[0] = data;
+  }
+  void IterateInstance(ObjectVisitor* v);
+  Object** end() { return values_ + 3; }
+private:
+  Object* values_[4];
+};
+
+
 } }  // namespace v8::internal
 
 #endif  // V8_ARGUMENTS_H_
index ba57629..b43ec53 100644 (file)
@@ -29,6 +29,7 @@
 
 #include "accessors.h"
 #include "api.h"
+#include "arguments.h"
 #include "bootstrapper.h"
 #include "compiler.h"
 #include "debug.h"
@@ -479,15 +480,17 @@ int GetScriptLineNumber(Handle<Script> script, int code_pos) {
 }
 
 
+void CustomArguments::IterateInstance(ObjectVisitor* v) {
+  v->VisitPointers(values_, values_ + 4);
+}
+
+
 // Compute the property keys from the interceptor.
 v8::Handle<v8::Array> GetKeysForNamedInterceptor(Handle<JSObject> receiver,
                                                  Handle<JSObject> object) {
   Handle<InterceptorInfo> interceptor(object->GetNamedInterceptor());
-  Handle<Object> data(interceptor->data());
-  v8::AccessorInfo info(
-    v8::Utils::ToLocal(receiver),
-    v8::Utils::ToLocal(data),
-    v8::Utils::ToLocal(object));
+  CustomArguments args(interceptor->data(), *receiver, *object);
+  v8::AccessorInfo info(args.end());
   v8::Handle<v8::Array> result;
   if (!interceptor->enumerator()->IsUndefined()) {
     v8::NamedPropertyEnumerator enum_fun =
@@ -507,11 +510,8 @@ v8::Handle<v8::Array> GetKeysForNamedInterceptor(Handle<JSObject> receiver,
 v8::Handle<v8::Array> GetKeysForIndexedInterceptor(Handle<JSObject> receiver,
                                                    Handle<JSObject> object) {
   Handle<InterceptorInfo> interceptor(object->GetIndexedInterceptor());
-  Handle<Object> data(interceptor->data());
-  v8::AccessorInfo info(
-    v8::Utils::ToLocal(receiver),
-    v8::Utils::ToLocal(data),
-    v8::Utils::ToLocal(object));
+  CustomArguments args(interceptor->data(), *receiver, *object);
+  v8::AccessorInfo info(args.end());
   v8::Handle<v8::Array> result;
   if (!interceptor->enumerator()->IsUndefined()) {
     v8::IndexedPropertyEnumerator enum_fun =
index 1a80d64..cf7a046 100644 (file)
@@ -497,8 +497,8 @@ void Heap::PostGarbageCollectionProcessing() {
     DisableAssertNoAllocation allow_allocation;
     GlobalHandles::PostGarbageCollectionProcessing();
   }
-  // Update flat string readers.
-  FlatStringReader::PostGarbageCollectionProcessing();
+  // Update relocatables.
+  Relocatable::PostGarbageCollectionProcessing();
 }
 
 
@@ -3088,6 +3088,8 @@ void Heap::IterateStrongRoots(ObjectVisitor* v) {
   SYNCHRONIZE_TAG("bootstrapper");
   Top::Iterate(v);
   SYNCHRONIZE_TAG("top");
+  Relocatable::Iterate(v);
+  SYNCHRONIZE_TAG("relocatable");
 
 #ifdef ENABLE_DEBUGGER_SUPPORT
   Debug::Iterate(v);
index ea2c202..e2fa3b5 100644 (file)
@@ -28,6 +28,7 @@
 #include "v8.h"
 
 #include "api.h"
+#include "arguments.h"
 #include "bootstrapper.h"
 #include "debug.h"
 #include "execution.h"
@@ -158,14 +159,12 @@ Object* Object::GetPropertyWithCallback(Object* receiver,
     Object* fun_obj = data->getter();
     v8::AccessorGetter call_fun = v8::ToCData<v8::AccessorGetter>(fun_obj);
     HandleScope scope;
-    Handle<JSObject> self(JSObject::cast(receiver));
-    Handle<JSObject> holder_handle(JSObject::cast(holder));
+    JSObject* self = JSObject::cast(receiver);
+    JSObject* holder_handle = JSObject::cast(holder);
     Handle<String> key(name);
-    Handle<Object> fun_data(data->data());
-    LOG(ApiNamedPropertyAccess("load", *self, name));
-    v8::AccessorInfo info(v8::Utils::ToLocal(self),
-                          v8::Utils::ToLocal(fun_data),
-                          v8::Utils::ToLocal(holder_handle));
+    LOG(ApiNamedPropertyAccess("load", self, name));
+    CustomArguments args(data->data(), self, holder_handle);
+    v8::AccessorInfo info(args.end());
     v8::Handle<v8::Value> result;
     {
       // Leaving JavaScript.
@@ -1538,11 +1537,9 @@ Object* JSObject::SetPropertyWithInterceptor(String* name,
   Handle<Object> value_handle(value);
   Handle<InterceptorInfo> interceptor(GetNamedInterceptor());
   if (!interceptor->setter()->IsUndefined()) {
-    Handle<Object> data_handle(interceptor->data());
     LOG(ApiNamedPropertyAccess("interceptor-named-set", this, name));
-    v8::AccessorInfo info(v8::Utils::ToLocal(this_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(this_handle));
+    CustomArguments args(interceptor->data(), this, this);
+    v8::AccessorInfo info(args.end());
     v8::NamedPropertySetter setter =
         v8::ToCData<v8::NamedPropertySetter>(interceptor->setter());
     v8::Handle<v8::Value> result;
@@ -1605,14 +1602,10 @@ Object* JSObject::SetPropertyWithCallback(Object* structure,
     Object* call_obj = data->setter();
     v8::AccessorSetter call_fun = v8::ToCData<v8::AccessorSetter>(call_obj);
     if (call_fun == NULL) return value;
-    Handle<JSObject> self(this);
-    Handle<JSObject> holder_handle(JSObject::cast(holder));
     Handle<String> key(name);
-    Handle<Object> fun_data(data->data());
     LOG(ApiNamedPropertyAccess("store", this, name));
-    v8::AccessorInfo info(v8::Utils::ToLocal(self),
-                          v8::Utils::ToLocal(fun_data),
-                          v8::Utils::ToLocal(holder_handle));
+    CustomArguments args(data->data(), this, JSObject::cast(holder));
+    v8::AccessorInfo info(args.end());
     {
       // Leaving JavaScript.
       VMState state(EXTERNAL);
@@ -2036,10 +2029,8 @@ PropertyAttributes JSObject::GetPropertyAttributeWithInterceptor(
   Handle<JSObject> receiver_handle(receiver);
   Handle<JSObject> holder_handle(this);
   Handle<String> name_handle(name);
-  Handle<Object> data_handle(interceptor->data());
-  v8::AccessorInfo info(v8::Utils::ToLocal(receiver_handle),
-                        v8::Utils::ToLocal(data_handle),
-                        v8::Utils::ToLocal(holder_handle));
+  CustomArguments args(interceptor->data(), receiver, this);
+  v8::AccessorInfo info(args.end());
   if (!interceptor->query()->IsUndefined()) {
     v8::NamedPropertyQuery query =
         v8::ToCData<v8::NamedPropertyQuery>(interceptor->query());
@@ -2307,11 +2298,9 @@ Object* JSObject::DeletePropertyWithInterceptor(String* name) {
   if (!interceptor->deleter()->IsUndefined()) {
     v8::NamedPropertyDeleter deleter =
         v8::ToCData<v8::NamedPropertyDeleter>(interceptor->deleter());
-    Handle<Object> data_handle(interceptor->data());
     LOG(ApiNamedPropertyAccess("interceptor-named-delete", *this_handle, name));
-    v8::AccessorInfo info(v8::Utils::ToLocal(this_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(this_handle));
+    CustomArguments args(interceptor->data(), this, this);
+    v8::AccessorInfo info(args.end());
     v8::Handle<v8::Boolean> result;
     {
       // Leaving JavaScript.
@@ -2370,11 +2359,9 @@ Object* JSObject::DeleteElementWithInterceptor(uint32_t index) {
   v8::IndexedPropertyDeleter deleter =
       v8::ToCData<v8::IndexedPropertyDeleter>(interceptor->deleter());
   Handle<JSObject> this_handle(this);
-  Handle<Object> data_handle(interceptor->data());
   LOG(ApiIndexedPropertyAccess("interceptor-indexed-delete", this, index));
-  v8::AccessorInfo info(v8::Utils::ToLocal(this_handle),
-                        v8::Utils::ToLocal(data_handle),
-                        v8::Utils::ToLocal(this_handle));
+  CustomArguments args(interceptor->data(), this, this);
+  v8::AccessorInfo info(args.end());
   v8::Handle<v8::Boolean> result;
   {
     // Leaving JavaScript.
@@ -3971,35 +3958,75 @@ const unibrow::byte* String::ReadBlock(String* input,
 }
 
 
-FlatStringReader* FlatStringReader::top_ = NULL;
+Relocatable* Relocatable::top_ = NULL;
+
+
+void Relocatable::PostGarbageCollectionProcessing() {
+  Relocatable* current = top_;
+  while (current != NULL) {
+    current->PostGarbageCollection();
+    current = current->prev_;
+  }
+}
+
+
+// Reserve space for statics needing saving and restoring.
+int Relocatable::ArchiveSpacePerThread() {
+  return sizeof(top_);
+}
+
+
+// Archive statics that are thread local.
+char* Relocatable::ArchiveState(char* to) {
+  *reinterpret_cast<Relocatable**>(to) = top_;
+  top_ = NULL;
+  return to + ArchiveSpacePerThread();
+}
+
+
+// Restore statics that are thread local.
+char* Relocatable::RestoreState(char* from) {
+  top_ = *reinterpret_cast<Relocatable**>(from);
+  return from + ArchiveSpacePerThread();
+}
+
+
+char* Relocatable::Iterate(ObjectVisitor* v, char* thread_storage) {
+  Relocatable* top = *reinterpret_cast<Relocatable**>(thread_storage);
+  Iterate(v, top);
+  return thread_storage + ArchiveSpacePerThread();
+}
+
+
+void Relocatable::Iterate(ObjectVisitor* v) {
+  Iterate(v, top_);
+}
+
+
+void Relocatable::Iterate(ObjectVisitor* v, Relocatable* top) {
+  Relocatable* current = top;
+  while (current != NULL) {
+    current->IterateInstance(v);
+    current = current->prev_;
+  }
+}
 
 
 FlatStringReader::FlatStringReader(Handle<String> str)
     : str_(str.location()),
-      length_(str->length()),
-      prev_(top_) {
-  top_ = this;
-  RefreshState();
+      length_(str->length()) {
+  PostGarbageCollection();
 }
 
 
 FlatStringReader::FlatStringReader(Vector<const char> input)
-    : str_(NULL),
+    : str_(0),
       is_ascii_(true),
       length_(input.length()),
-      start_(input.start()),
-      prev_(top_) {
-  top_ = this;
-}
+      start_(input.start()) { }
 
 
-FlatStringReader::~FlatStringReader() {
-  ASSERT_EQ(top_, this);
-  top_ = prev_;
-}
-
-
-void FlatStringReader::RefreshState() {
+void FlatStringReader::PostGarbageCollection() {
   if (str_ == NULL) return;
   Handle<String> str(str_);
   ASSERT(str->IsFlat());
@@ -4012,15 +4039,6 @@ void FlatStringReader::RefreshState() {
 }
 
 
-void FlatStringReader::PostGarbageCollectionProcessing() {
-  FlatStringReader* current = top_;
-  while (current != NULL) {
-    current->RefreshState();
-    current = current->prev_;
-  }
-}
-
-
 void StringInputBuffer::Seek(unsigned pos) {
   Reset(pos, input_);
 }
@@ -5429,10 +5447,8 @@ bool JSObject::HasElementWithInterceptor(JSObject* receiver, uint32_t index) {
   Handle<InterceptorInfo> interceptor(GetIndexedInterceptor());
   Handle<JSObject> receiver_handle(receiver);
   Handle<JSObject> holder_handle(this);
-  Handle<Object> data_handle(interceptor->data());
-  v8::AccessorInfo info(v8::Utils::ToLocal(receiver_handle),
-                        v8::Utils::ToLocal(data_handle),
-                        v8::Utils::ToLocal(holder_handle));
+  CustomArguments args(interceptor->data(), receiver, this);
+  v8::AccessorInfo info(args.end());
   if (!interceptor->query()->IsUndefined()) {
     v8::IndexedPropertyQuery query =
         v8::ToCData<v8::IndexedPropertyQuery>(interceptor->query());
@@ -5564,11 +5580,9 @@ Object* JSObject::SetElementWithInterceptor(uint32_t index, Object* value) {
   if (!interceptor->setter()->IsUndefined()) {
     v8::IndexedPropertySetter setter =
         v8::ToCData<v8::IndexedPropertySetter>(interceptor->setter());
-    Handle<Object> data_handle(interceptor->data());
     LOG(ApiIndexedPropertyAccess("interceptor-indexed-set", this, index));
-    v8::AccessorInfo info(v8::Utils::ToLocal(this_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(this_handle));
+    CustomArguments args(interceptor->data(), this, this);
+    v8::AccessorInfo info(args.end());
     v8::Handle<v8::Value> result;
     {
       // Leaving JavaScript.
@@ -5836,13 +5850,11 @@ Object* JSObject::GetElementWithInterceptor(JSObject* receiver,
   Handle<JSObject> holder_handle(this);
 
   if (!interceptor->getter()->IsUndefined()) {
-    Handle<Object> data_handle(interceptor->data());
     v8::IndexedPropertyGetter getter =
         v8::ToCData<v8::IndexedPropertyGetter>(interceptor->getter());
     LOG(ApiIndexedPropertyAccess("interceptor-indexed-get", this, index));
-    v8::AccessorInfo info(v8::Utils::ToLocal(this_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(holder_handle));
+    CustomArguments args(interceptor->data(), receiver, this);
+    v8::AccessorInfo info(args.end());
     v8::Handle<v8::Value> result;
     {
       // Leaving JavaScript.
@@ -6074,15 +6086,13 @@ Object* JSObject::GetPropertyWithInterceptor(
   Handle<JSObject> receiver_handle(receiver);
   Handle<JSObject> holder_handle(this);
   Handle<String> name_handle(name);
-  Handle<Object> data_handle(interceptor->data());
 
   if (!interceptor->getter()->IsUndefined()) {
     v8::NamedPropertyGetter getter =
         v8::ToCData<v8::NamedPropertyGetter>(interceptor->getter());
     LOG(ApiNamedPropertyAccess("interceptor-named-get", *holder_handle, name));
-    v8::AccessorInfo info(v8::Utils::ToLocal(receiver_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(holder_handle));
+    CustomArguments args(interceptor->data(), receiver, this);
+    v8::AccessorInfo info(args.end());
     v8::Handle<v8::Value> result;
     {
       // Leaving JavaScript.
index 5be4929..e22eaa1 100644 (file)
@@ -4219,25 +4219,44 @@ class ExternalTwoByteString: public ExternalString {
 };
 
 
+// Utility superclass for stack-allocated objects that must be updated
+// on gc.  It provides two ways for the gc to update instances, either
+// iterating or updating after gc.
+class Relocatable BASE_EMBEDDED {
+public:
+  inline Relocatable() : prev_(top_) { top_ = this; }
+  virtual ~Relocatable() { ASSERT_EQ(top_, this); top_ = prev_; }
+  virtual void IterateInstance(ObjectVisitor* v) { }
+  virtual void PostGarbageCollection() { }
+
+  static void PostGarbageCollectionProcessing();
+  static int ArchiveSpacePerThread();
+  static char* ArchiveState(char* to);
+  static char* RestoreState(char* from);
+  static void Iterate(ObjectVisitor* v);
+  static void Iterate(ObjectVisitor* v, Relocatable* top);
+  static char* Iterate(ObjectVisitor* v, char* t);
+private:
+  static Relocatable* top_;
+  Relocatable* prev_;
+};
+
+
 // A flat string reader provides random access to the contents of a
 // string independent of the character width of the string.  The handle
 // must be valid as long as the reader is being used.
-class FlatStringReader BASE_EMBEDDED {
+class FlatStringReader : public Relocatable {
  public:
   explicit FlatStringReader(Handle<String> str);
   explicit FlatStringReader(Vector<const char> input);
-  ~FlatStringReader();
-  void RefreshState();
+  void PostGarbageCollection();
   inline uc32 Get(int index);
   int length() { return length_; }
-  static void PostGarbageCollectionProcessing();
  private:
   String** str_;
   bool is_ascii_;
   int length_;
   const void* start_;
-  FlatStringReader* prev_;
-  static FlatStringReader* top_;
 };
 
 
index 2906c22..e10dc61 100644 (file)
@@ -735,28 +735,17 @@ Handle<Code> ComputeCallMiss(int argc) {
 
 
 Object* LoadCallbackProperty(Arguments args) {
-  Handle<JSObject> recv = args.at<JSObject>(0);
-  Handle<JSObject> holder = args.at<JSObject>(1);
   AccessorInfo* callback = AccessorInfo::cast(args[2]);
-  Handle<Object> data = args.at<Object>(3);
   Address getter_address = v8::ToCData<Address>(callback->getter());
   v8::AccessorGetter fun = FUNCTION_CAST<v8::AccessorGetter>(getter_address);
   ASSERT(fun != NULL);
-  Handle<String> name = args.at<String>(4);
-  // NOTE: If we can align the structure of an AccessorInfo with the
-  // locations of the arguments to this function maybe we don't have
-  // to explicitly create the structure but can just pass a pointer
-  // into the stack.
-  LOG(ApiNamedPropertyAccess("load", *recv, *name));
-  v8::AccessorInfo info(v8::Utils::ToLocal(recv),
-                        v8::Utils::ToLocal(data),
-                        v8::Utils::ToLocal(holder));
+  v8::AccessorInfo info(args.arguments());
   HandleScope scope;
   v8::Handle<v8::Value> result;
   {
     // Leaving JavaScript.
     VMState state(EXTERNAL);
-    result = fun(v8::Utils::ToLocal(name), info);
+    result = fun(v8::Utils::ToLocal(args.at<String>(4)), info);
   }
   RETURN_IF_SCHEDULED_EXCEPTION();
   if (result.IsEmpty()) return Heap::undefined_value();
@@ -765,7 +754,7 @@ Object* LoadCallbackProperty(Arguments args) {
 
 
 Object* StoreCallbackProperty(Arguments args) {
-  Handle<JSObject> recv = args.at<JSObject>(0);
+  JSObject* recv = JSObject::cast(args[0]);
   AccessorInfo* callback = AccessorInfo::cast(args[1]);
   Address setter_address = v8::ToCData<Address>(callback->setter());
   v8::AccessorSetter fun = FUNCTION_CAST<v8::AccessorSetter>(setter_address);
@@ -773,11 +762,9 @@ Object* StoreCallbackProperty(Arguments args) {
   Handle<String> name = args.at<String>(2);
   Handle<Object> value = args.at<Object>(3);
   HandleScope scope;
-  Handle<Object> data(callback->data());
-  LOG(ApiNamedPropertyAccess("store", *recv, *name));
-  v8::AccessorInfo info(v8::Utils::ToLocal(recv),
-                        v8::Utils::ToLocal(data),
-                        v8::Utils::ToLocal(recv));
+  LOG(ApiNamedPropertyAccess("store", recv, *name));
+  CustomArguments custom_args(callback->data(), recv, recv);
+  v8::AccessorInfo info(custom_args.end());
   {
     // Leaving JavaScript.
     VMState state(EXTERNAL);
@@ -795,11 +782,11 @@ Object* StoreCallbackProperty(Arguments args) {
  * provide any value for the given name.
  */
 Object* LoadPropertyWithInterceptorOnly(Arguments args) {
-  Handle<JSObject> receiver_handle = args.at<JSObject>(0);
-  Handle<JSObject> holder_handle = args.at<JSObject>(1);
+  JSObject* receiver_handle = JSObject::cast(args[0]);
+  JSObject* holder_handle = JSObject::cast(args[1]);
   Handle<String> name_handle = args.at<String>(2);
   Handle<InterceptorInfo> interceptor_info = args.at<InterceptorInfo>(3);
-  Handle<Object> data_handle = args.at<Object>(4);
+  Object* data_handle = args[4];
 
   Address getter_address = v8::ToCData<Address>(interceptor_info->getter());
   v8::NamedPropertyGetter getter =
@@ -808,9 +795,8 @@ Object* LoadPropertyWithInterceptorOnly(Arguments args) {
 
   {
     // Use the interceptor getter.
-    v8::AccessorInfo info(v8::Utils::ToLocal(receiver_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(holder_handle));
+    CustomArguments args(data_handle, receiver_handle, holder_handle);
+    v8::AccessorInfo info(args.end());
     HandleScope scope;
     v8::Handle<v8::Value> r;
     {
@@ -861,9 +847,8 @@ static Object* LoadWithInterceptor(Arguments* args,
 
   {
     // Use the interceptor getter.
-    v8::AccessorInfo info(v8::Utils::ToLocal(receiver_handle),
-                          v8::Utils::ToLocal(data_handle),
-                          v8::Utils::ToLocal(holder_handle));
+    CustomArguments args(*data_handle, *receiver_handle, *holder_handle);
+    v8::AccessorInfo info(args.end());
     HandleScope scope;
     v8::Handle<v8::Value> r;
     {
index 23f8372..c774449 100644 (file)
@@ -146,6 +146,7 @@ bool ThreadManager::RestoreThread() {
   char* from = state->data();
   from = HandleScopeImplementer::RestoreThread(from);
   from = Top::RestoreThread(from);
+  from = Relocatable::RestoreState(from);
 #ifdef ENABLE_DEBUGGER_SUPPORT
   from = Debug::RestoreDebug(from);
 #endif
@@ -185,7 +186,8 @@ static int ArchiveSpacePerThread() {
 #endif
                      StackGuard::ArchiveSpacePerThread() +
                     RegExpStack::ArchiveSpacePerThread() +
-                   Bootstrapper::ArchiveSpacePerThread();
+                   Bootstrapper::ArchiveSpacePerThread() +
+                    Relocatable::ArchiveSpacePerThread();
 }
 
 
@@ -275,6 +277,7 @@ void ThreadManager::EagerlyArchiveThread() {
   // in ThreadManager::Iterate(ObjectVisitor*).
   to = HandleScopeImplementer::ArchiveThread(to);
   to = Top::ArchiveThread(to);
+  to = Relocatable::ArchiveState(to);
 #ifdef ENABLE_DEBUGGER_SUPPORT
   to = Debug::ArchiveDebug(to);
 #endif
@@ -311,6 +314,7 @@ void ThreadManager::Iterate(ObjectVisitor* v) {
     char* data = state->data();
     data = HandleScopeImplementer::Iterate(v, data);
     data = Top::Iterate(v, data);
+    data = Relocatable::Iterate(v, data);
   }
 }