Summary: | Crash Firing Signals Through QtWebKit Bridge | ||||||
---|---|---|---|---|---|---|---|
Product: | WebKit | Reporter: | Ryan Cumming <rcumming> | ||||
Component: | WebKit Qt | Assignee: | Nobody <webkit-unassigned> | ||||
Status: | RESOLVED CONFIGURATION CHANGED | ||||||
Severity: | Major | CC: | ahmad.saleem792, ap, bfulgham, npotter, rniwa | ||||
Priority: | P2 | ||||||
Version: | 528+ (Nightly build) | ||||||
Hardware: | All | ||||||
OS: | All | ||||||
Attachments: |
|
Confirmed the crash also occurs on 64bit Qt 4.8.0 Mac OS X 10.7.3 with GCC 4.2.1. The backtrace looks the same: Program received signal EXC_BAD_ACCESS, Could not access memory. Reason: KERN_INVALID_ADDRESS at address: 0xffffffffffffffc0 0x00002725e6a00a7e in ?? () (gdb) bt #0 0x00002725e6a00a7e in ?? () #1 0x0000000100e6c5cd in JSC::Interpreter::executeCall () #2 0x0000000100f0a901 in JSC::call () #3 0x000000010052cec4 in JSC::Bindings::QtConnectionObject::execute () #4 0x000000010052d820 in JSC::Bindings::QtConnectionObject::qt_metacall () #5 0x0000000103022446 in QMetaObject::activate () Relevant Valgrind output on Ubuntu 12.04 32bit with the stock Ubuntu libqtwebkit-2.2.1-1ubuntu4 package. Nothing unusual happens before: ==1944== Invalid read of size 4 ==1944== at 0xB82259F: ??? ==1944== by 0x5292868: JSC::Interpreter::executeCall(JSC::ExecState*, JSC::JSObject*, JSC::CallType, JSC::CallData const&, JSC::JSValue, JSC::ArgList const&) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0x52B09F1: JSC::call(JSC::ExecState*, JSC::JSValue, JSC::CallType, JSC::CallData const&, JSC::JSValue, JSC::ArgList const&) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0x49F7973: JSC::Bindings::QtConnectionObject::execute(void**) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0x49F81F1: JSC::Bindings::QtConnectionObject::qt_metacall(QMetaObject::Call, int, void**) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0xF95ECCF: ??? ==1944== Address 0xffffffc0 is not stack'd, malloc'd or (recently) free'd ==1944== ==1944== ==1944== Process terminating with default action of signal 11 (SIGSEGV) ==1944== Access not within mapped region at address 0xFFFFFFC0 ==1944== at 0xB82259F: ??? ==1944== by 0x5292868: JSC::Interpreter::executeCall(JSC::ExecState*, JSC::JSObject*, JSC::CallType, JSC::CallData const&, JSC::JSValue, JSC::ArgList const&) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0x52B09F1: JSC::call(JSC::ExecState*, JSC::JSValue, JSC::CallType, JSC::CallData const&, JSC::JSValue, JSC::ArgList const&) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0x49F7973: JSC::Bindings::QtConnectionObject::execute(void**) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0x49F81F1: JSC::Bindings::QtConnectionObject::qt_metacall(QMetaObject::Call, int, void**) (in /usr/lib/i386-linux-gnu/libQtWebKit.so.4.9.0) ==1944== by 0xF95ECCF: ??? The root of the problem is this code in Source/WebCore/bridge/qt/qt_runtime.cpp: // Stuff in the __qt_sender property, if we can ScopeChainNode* oldsc = 0; JSFunction* fimp = 0; if (m_funcObject->inherits(&JSFunction::s_info)) { fimp = static_cast<JSFunction*>(m_funcObject.get()); JSObject* qt_sender = QtInstance::getQtInstance(sender(), ro, QScriptEngine::QtOwnership)->createRuntimeObject(exec); JSObject* wrapper = constructEmptyObject(exec, createEmptyObjectStructure(exec->globalData(), jsNull())); PutPropertySlot slot; wrapper->put(exec, Identifier(exec, "__qt_sender__"), qt_sender, slot); oldsc = fimp->scope(); fimp->setScope(exec->globalData(), oldsc->push(wrapper)); } This code is trying to expose the "__qt_sender__" object in the scope of the called JavaScript function. To accomplish this it creates an empty object, adds __qt_sender__ then temporarily inserts it in to the called function's scope chain. However, the only objects allowed in the JavaScript scope chain are variable objects (JSVariableObject in JSC). This causes JavaScriptCore to blow up if we try to walk the scope chain up to the __qt_sender__ container scope. The correct thing to do seems to be to instantiate a JSStaticScope instead of a JSObject but we don't need the __qt_sender__ feature so I've merely commented out the code. Qt Support has confirmed that this is indeed a crash. This is a blocker for us. Qt framework for Webkit Builds is not supported anymore and there is no build for Qt in Buildbots. https://ews-build.webkit.org/#/builders Can we marked this as "RESOLVED WONTFIX"? Thanks1 |
Created attachment 134141 [details] Test Qt project that will demonstrate the crash on startup Firing signals from a Qt object through the QtWebKit bridge will frequently cause a crash if the attached function is non-trivial. The use of Function.apply seems to reliably cause a crash. The following JavaScript snippet assumes there is an object called "signalTest" added using QWebFrame::addToJavaScriptWindowObject() that emits fired() whenever fire() is called: var proxy = function(fn, context) { return function() { return fn.apply(context); } } var proxiedFunction = proxy(function() { alert("Hello, world!"); }, window); // This works proxiedFunction(); signalTest.fired.connect(proxiedFunction); // CRASHES HERE signalTest.fire(); The crash seems to come from JIT generated code trying to read from 0xffffffc0 with the following stack trace: 0f091444() QtWebKitd4.dll!JSC::JITCode::execute(JSC::RegisterFile * registerFile, JSC::ExecState * callFrame, JSC::JSGlobalData * globalData) Line 77 + 0x22 bytes C++ QtWebKitd4.dll!JSC::Interpreter::executeCall(JSC::ExecState * callFrame, JSC::JSObject * function, JSC::CallType callType, const JSC::CallData & callData, JSC::JSValue thisValue, const JSC::ArgList & args) Line 838 + 0x2a bytes C++ QtWebKitd4.dll!JSC::call(JSC::ExecState * exec, JSC::JSValue functionObject, JSC::CallType callType, const JSC::CallData & callData, JSC::JSValue thisValue, const JSC::ArgList & args) Line 38 + 0x3c bytes C++ QtWebKitd4.dll!JSC::Bindings::QtConnectionObject::execute(void * * argv) Line 1863 + 0x6f bytes C++ QtWebKitd4.dll!JSC::Bindings::QtConnectionObject::qt_metacall(QMetaObject::Call _c, int _id, void * * _a) Line 1809 C++ QtCored4.dll!QMetaObject::metacall(QObject * object, QMetaObject::Call cl, int idx, void * * argv) Line 238 C++ The disassembly around the crash looks like: 0F0913DA call cti_op_call_arityCheck (3E876B0h) 0F0913DF mov edi,eax 0F0913E1 jmp 0F090004 0F0913E6 add byte ptr [eax],al 0F0913E8 pop ecx 0F0913E9 mov dword ptr [edi-10h],ecx 0F0913EC mov dword ptr [edi-8],182092A0h 0F0913F3 lea edx,[edi+98h] 0F0913F9 cmp dword ptr ds:[0BF927F0h],edx 0F0913FF jb 0F091DDC 0F091405 mov dword ptr [edi],0 0F09140B mov dword ptr [edi+4],0FFFFFFFCh 0F091412 mov dword ptr [edi+8],0 0F091419 mov dword ptr [edi+0Ch],0FFFFFFFCh 0F091420 mov dword ptr [edi+8],0 0F091427 mov dword ptr [edi+0Ch],0FFFFFFFAh 0F09142E mov dword ptr [edi],0 0F091434 mov dword ptr [edi+4],0FFFFFFFAh 0F09143B mov ecx,dword ptr [edi-18h] 0F09143E mov ecx,dword ptr [ecx+10h] 0F091441 mov ecx,dword ptr [ecx+34h] <=== CRASH 0F091444 mov eax,dword ptr [ecx-40h] The attached Qt project demonstrates the problem by reliably crashing on startup. I built it with a fresh install of Qt SDK 1.2 against Qt 4.8.0 using MSVC 2010 SP1