summaryrefslogtreecommitdiffstats
path: root/gin/function_template.h
diff options
context:
space:
mode:
authorjochen@chromium.org <jochen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-02-11 15:06:12 +0000
committerjochen@chromium.org <jochen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-02-11 15:06:12 +0000
commitbf0142900b6bde5b2cc6ca35be3d81899ebf09b7 (patch)
tree96fca93bcbbcc847831dab5ce449c0609a66e931 /gin/function_template.h
parent58e576ffab5279ae312df42d6e41151dbf9598b6 (diff)
downloadchromium_src-bf0142900b6bde5b2cc6ca35be3d81899ebf09b7.zip
chromium_src-bf0142900b6bde5b2cc6ca35be3d81899ebf09b7.tar.gz
chromium_src-bf0142900b6bde5b2cc6ca35be3d81899ebf09b7.tar.bz2
gin: Only use primitive types for creating function templates
Otherwise, the function template will keep the context alive it was created in. BUG=342272 R=dcarney@chromium.org,aa@chromium.org,haraken@chromium.org Review URL: https://codereview.chromium.org/141143012 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@250412 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'gin/function_template.h')
-rw-r--r--gin/function_template.h84
1 files changed, 51 insertions, 33 deletions
diff --git a/gin/function_template.h b/gin/function_template.h
index 29cb336..fe95f51 100644
--- a/gin/function_template.h
+++ b/gin/function_template.h
@@ -16,11 +16,6 @@
#include "gin/arguments.h"
#include "gin/converter.h"
#include "gin/gin_export.h"
-#include "gin/handle.h"
-#include "gin/public/gin_embedders.h"
-#include "gin/public/wrapper_info.h"
-#include "gin/wrappable.h"
-
#include "v8/include/v8.h"
namespace gin {
@@ -50,31 +45,39 @@ struct CallbackParamTraits<const T*> {
// CallbackHolder and CallbackHolderBase are used to pass a base::Callback from
// CreateFunctionTemplate through v8 (via v8::FunctionTemplate) to
// DispatchToCallback, where it is invoked.
-//
-// v8::FunctionTemplate only supports passing void* as data so how do we know
-// when to delete the base::Callback? That's where CallbackHolderBase comes in.
-// It inherits from Wrappable, which delete itself when both (a) the refcount
-// via base::RefCounted has dropped to zero, and (b) there are no more
-// JavaScript references in V8.
// This simple base class is used so that we can share a single object template
// among every CallbackHolder instance.
-class GIN_EXPORT CallbackHolderBase : public Wrappable<CallbackHolderBase> {
+class GIN_EXPORT CallbackHolderBase {
public:
- static WrapperInfo kWrapperInfo;
+ v8::Handle<v8::External> GetHandle(v8::Isolate* isolate);
+
protected:
- virtual ~CallbackHolderBase() {}
+ explicit CallbackHolderBase(v8::Isolate* isolate);
+ virtual ~CallbackHolderBase();
+
+ private:
+ static void WeakCallback(
+ const v8::WeakCallbackData<v8::External, CallbackHolderBase>& data);
+
+ v8::Persistent<v8::External> v8_ref_;
+
+ DISALLOW_COPY_AND_ASSIGN(CallbackHolderBase);
};
template<typename Sig>
class CallbackHolder : public CallbackHolderBase {
public:
- CallbackHolder(const base::Callback<Sig>& callback, int flags)
- : callback(callback), flags(flags) {}
+ CallbackHolder(v8::Isolate* isolate,
+ const base::Callback<Sig>& callback,
+ int flags)
+ : CallbackHolderBase(isolate), callback(callback), flags(flags) {}
base::Callback<Sig> callback;
int flags;
private:
virtual ~CallbackHolder() {}
+
+ DISALLOW_COPY_AND_ASSIGN(CallbackHolder);
};
@@ -293,8 +296,10 @@ struct Dispatcher<R()> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R()> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -308,8 +313,10 @@ struct Dispatcher<R(P1)> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R(P1)> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -329,8 +336,10 @@ struct Dispatcher<R(P1, P2)> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R(P1, P2)> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -352,8 +361,10 @@ struct Dispatcher<R(P1, P2, P3)> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R(P1, P2, P3)> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -377,8 +388,10 @@ struct Dispatcher<R(P1, P2, P3, P4)> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R(P1, P2, P3, P4)> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -405,8 +418,10 @@ struct Dispatcher<R(P1, P2, P3, P4, P5)> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R(P1, P2, P3, P4, P5)> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -436,8 +451,10 @@ struct Dispatcher<R(P1, P2, P3, P4, P5, P6)> {
static void DispatchToCallback(
const v8::FunctionCallbackInfo<v8::Value>& info) {
Arguments args(info);
- CallbackHolderBase* holder_base = NULL;
- CHECK(args.GetData(&holder_base));
+ v8::Handle<v8::External> v8_holder;
+ CHECK(args.GetData(&v8_holder));
+ CallbackHolderBase* holder_base = reinterpret_cast<CallbackHolderBase*>(
+ v8_holder->Value());
typedef CallbackHolder<R(P1, P2, P3, P4, P5, P6)> HolderT;
HolderT* holder = static_cast<HolderT*>(holder_base);
@@ -475,12 +492,13 @@ v8::Local<v8::FunctionTemplate> CreateFunctionTemplate(
v8::Isolate* isolate, const base::Callback<Sig> callback,
int callback_flags = 0) {
typedef internal::CallbackHolder<Sig> HolderT;
- gin::Handle<HolderT> holder = CreateHandle(
- isolate, new HolderT(callback, callback_flags));
+ HolderT* holder = new HolderT(isolate, callback, callback_flags);
+
return v8::FunctionTemplate::New(
isolate,
&internal::Dispatcher<Sig>::DispatchToCallback,
- ConvertToV8<internal::CallbackHolderBase*>(isolate, holder.get()));
+ ConvertToV8<v8::Handle<v8::External> >(isolate,
+ holder->GetHandle(isolate)));
}
} // namespace gin