2014-09-10 58 views
0

任何人都可以看到爲什麼調用持久性函數pfunc_on_open崩潰?訪問持久性函數時V8崩潰

Locker lock(isolate); 
HandleScope scope(isolate); 

v8::Local<v8::Context> context = v8::Local<v8::Context>::New(isolate, p_context); 
Context::Scope context_scope(context); 
Handle <v8::Object> global = context->Global(); 

Handle <Value> args[1]; 
if (event.compare(event_onopen) == 0) { 

    args[0] = v8::String::NewFromUtf8(isolate,message.c_str()); 

    v8::Local<v8::Function> processOnOpen = v8::Local<v8::Function>::New(isolate, pfunc_on_open); 

    processOnOpen->Call(global, 1, args); 
} 

回答

0

該函數與一個JavaScript方法通過下面的代碼相關聯:

void WebSocket::exposeWebSocket(Handle<ObjectTemplate> globalTemplate) 
{ 

globalTemplate->Set(String::NewFromUtf8(isolate,"WebSocket"), 
FunctionTemplate::New(isolate,WebSocketConstructor));} 

空隙WebSocketConstructor(常量V8 :: FunctionCallbackInfo &參數) {

LOGD(LOG_TAG, "In WebSocketConstructor()"); 

Locker lock(isolate); 
HandleScope scope(isolate); 

Handle<ObjectTemplate> websocket_templ= ObjectTemplate::New(); 
websocket_templ->SetInternalFieldCount(1); 

// Object methods 
websocket_templ->Set(String::NewFromUtf8(isolate,"send"), FunctionTemplate::New(isolate,WebSocket::exposed_method_send)); 
websocket_templ->Set(String::NewFromUtf8(isolate,"close"), FunctionTemplate::New(isolate,WebSocket::exposed_method_close)); 

// Set up properties as event handlers 
websocket_templ->SetAccessor(String::NewFromUtf8(isolate,"onopen"), AccessorGetterCallback(WebSocket::GetOnCallback), AccessorSetterCallback(WebSocket::SetOnOpen)); 
websocket_templ->SetAccessor(String::NewFromUtf8(isolate,"onmessage"), AccessorGetterCallback(WebSocket::GetOnCallback), AccessorSetterCallback(WebSocket::SetOnMessage)); 
websocket_templ->SetAccessor(String::NewFromUtf8(isolate,"onerror"), AccessorGetterCallback(WebSocket::GetOnCallback), AccessorSetterCallback(WebSocket::SetOnFail)); 
websocket_templ->SetAccessor(String::NewFromUtf8(isolate,"onclose"), AccessorGetterCallback(WebSocket::GetOnCallback), AccessorSetterCallback(WebSocket::SetOnClose)); 

Handle<Object> ws_instance; 

if (!args[0].IsEmpty() && args[0]->IsString()) { 

     String::Utf8Value p1(args[0]->ToString()); 

     LOGD(LOG_TAG, "WebSocketConstructor() - URL = %s", *p1); 

     // Create a C++ instance of this type 
     WebSocket* wsObject = new WebSocket(*p1); 

     //Handle<Object> self = Handle<Object>::New(isolate, args.Holder()); 

     ws_instance = websocket_templ->NewInstance(); 

     ws_instance->SetInternalField(0, v8::External::New(isolate, wsObject)); 

     args.GetReturnValue().Set(ws_instance); 

    } 

}

void WebSocket::SetOnOpen(Local<String> prop, Local<Value> value, constv8::PropertyCallbackInfo<void>& info) {

Locker lock(isolate); 
HandleScope scope(isolate); 

String::Utf8Value str(prop); 

LOGD(LOG_TAG, "SetOnOpen(): property = %s", *str); 

// Retrieve the WebSocket instance associated with this callback so the 
// appropriate map object can be used to store the callback address 
Handle <Object> self = info.Holder(); 
Handle <External> wrap = Handle <External> ::Cast(self->GetInternalField(0)); 

void* ptr = wrap->Value(); 

WebSocket* ws = static_cast<WebSocket*>(ptr); 

if (value->IsFunction()) { 

    // Store a persistent function handle in the callback map 
    Handle<Function> callback = Handle<Function>::Cast(value); 

    ws->pfunc_on_open.Reset(isolate, callback); 

    if(callback.IsEmpty()) 
    { 
     LOGD(LOG_TAG, "callback is null"); 
    } 

    // We may have a connection error to report 
    if (!ws->m_connection_error.empty() && std::string(*str).compare("onfail") == 0) 
    { 
     ws->callEventCallback(event_onfail, ws->m_connection_error); 
     ws->m_connection_error.clear(); 
    } 
} else { 
    LOGE(LOG_TAG, "SetOnOpen(): invalid parameter type - value is not a function"); 
} 

}