Woohoo!!! Generic weak persistent pointer wrapper and class generator template!

57 views
Skip to first unread message

Stephan Beal

unread,
Mar 9, 2009, 10:24:11 PM3/9/09
to v8-users
Hi, all!

i expanded that JSClassGenerator i demonstrated earlier, and now it
can provided weak pointers support generically. That is, in theory any
type can bound, including shared/static objects. It uses a client-
provided ctor/dtor pair to do the actual construction/destruction, so
it can also work with shared/static objects and opaque types. It also
adds the infamous "supplemental" GC to the object, and ties that in
with the weak pointer callback, so that only one or the other will
actually try to destroy the object.

A real example:

// A functor required by the wrapper generator: "destroys" objects
of the wrapped type.
// The default impl just calls (delete WrappedType), which is fine
for most cases
// but not this particular one.
struct devT_finalizer
{
template <typename DevT>
void operator()( DevT * obj ) const
{
if( obj ) obj->api->finalize(obj);
}
};

That's all we have to code for the dtor stuff, but we need a
constructor function with a slightly weird signature:

// Required by the wrapper generator: constructor function
whio_dev * dev_construct( Local<Object> self,
int argc,
Handle<Value> argv[],
std::string & exception // ctor should write error messages
here
)
{...}

The sig is explained in the API docs at the link below.

Now we use it:

////////////////////////////////////////////////////////////
// IODevice class:
{
v8::juice::WeakJSClassCreator<
whio_dev, // native type being wrapped
&dev_construct, // my constructor function
0, // number of internal fields we want to use
// ^^^ The wrapper generator adds 1 to store the
wrapped native (at the last internal field index)
devT_finalizer // finalizer functor
> // end template param
bindIOD( strings::IODevice /* class name string */,
whio /* my target, or "global" object
*/ );

bindIOD .Inherit( bindAbs )
.Set(strings::write, devT_write<whio_dev,true> )
...
.Set(strings::isGood,dev_isgood)
.Seal();
}


In JS:

var x = new whio.IODevice(...); // this will throw if the ctor
callback writes any error messages

That's all there is to it! The class also provides some static
functions to assist in converting Handle<Value> to the native object,
e.g. for (attempting to) convert argv.This() to a (WrappedType*).

Caveat: it requires a small bit of code from the core v8-juice libs.
It could be easily adapted to live without that code - just strip out
any lines containing "::juice::" and remove the GetBoundNativeMember
(). You'll lose the conversion helper func and the "supplemental"
garbage collection support, but no major functionality.

The code is here:

http://code.google.com/p/v8-juice/source/browse/trunk/src/include/v8/juice/WeakJSClassCreator.h

and an example of how it's used is here:

http://code.google.com/p/v8-juice/source/browse/trunk/src/lib/plugins/whio/v8-whio.cc

(Search for the second instance of the text "WeakJS".)
(Most of the dtor code in that file is now unused)
(There's certainly still more work to do on it, but the basics are all
in place.)

Happy hacking!
Reply all
Reply to author
Forward
0 new messages