以下代码适用于OS X,但是当我编译&在Ubuntu中运行它,在调用baton->callback
函数时遇到段错误。似乎Persistent<Function>
不会持续超过最初的Aysnc::Start
方法。
如果是这种情况,为什么它适用于OS X ? 我可以做些什么来使其跨平台工作?
如果我做错了,我需要做些什么才能从callback
调用AfterWork
?
// Async.h
#include <v8.h>
#include <node.h>
#include <string>
using namespace node;
using namespace v8;
class Async : public ObjectWrap {
public:
static Persistent<Function> constructor_template;
static void Initialize(Handle<v8::Object> target);
protected:
Async() {}
~Async() {}
static Handle<Value> Start(const Arguments& args);
static void Work(uv_work_t* req);
static void AfterWork(uv_work_t* req);
private:
struct Baton {
uv_work_t request;
Persistent<Function> callback;
};
};
// Async.cc
Handle<Value> Async::Start(const Arguments& args) {
HandleScope scope;
if(args.Length() == 0 || !args[0]->IsFunction()) {
return ThrowException(Exception::Error(String::New("Callback is required and must be a Function.")));
}
Baton *baton = new Baton();
baton->request.data = baton;
baton->callback = Persistent<Function>::New(Handle<Function>::Cast(args[0]));
uv_queue_work(uv_default_loop(), &baton->request, Work, (uv_after_work_cb)AfterWork);
return Undefined();
}
void Async::Work(uv_work_t *req) {
printf("Work\n");
}
void Async::AfterWork(uv_work_t *req) {
printf("AfterWork\n");
HandleScope scope;
Baton *baton = static_cast<Baton *>(req->data);
delete req;
Local<Value> argv[1] = {
Local<Value>::New(Null());
};
TryCatch try_catch;
// Segfault occurs here
baton->callback->Call(Context::GetCurrent()->Global(), 1, argv);
if (try_catch.HasCaught()) {
node::FatalException(try_catch);
}
}
答案 0 :(得分:2)
我不熟悉libuv
,但考虑到您对Baton
的定义,并假设传递到uv_work_t*
的{{1}}与传入的AfterWork()
相同uv_queue_work()
,您的delete req
语句实际上会删除您的Baton
结构,然后您可以从中尝试阅读callback
字段。我尝试删除delete req
并在delete baton
的最后添加AfterWork()
。