Export to GitHub

phantomjs - issue #741

Segmentation fault with closure callback


Posted on Aug 30, 2012 by Quick Monkey

Which version of PhantomJS are you using?

1.7.0 (development)

What steps will reproduce the problem?

This script crashes PhantomJS with a segmentation fault:

function closure() { var x; return function(){ x; }; } var f = closure(); f(); require('webpage').create().open('http://www.google.com/', f);

Similar crashes happen with other callbacks (onAlert, onConsoleMessage, onLoadFinished, onLoadStarted, onResourceReceived, onResourceRequested, onUrlChanged) but some callbacks seem fine (onConfirm, onError, onPrompt, onInitialized). Weird that onAlert crashes it but not onConfirm!

Comment #1

Posted on Sep 1, 2012 by Massive Horse

Can you give an example of somewhere where it crashes with onAlert? I can't seem to reproduce that.

Comment #2

Posted on Sep 1, 2012 by Massive Horse

Here is a stack trace I got out of the original example:

0 0x00007fffb004f3ce in ?? ()

1 0x0000000001d864fa in ?? ()

2 0x000000001638a565 in ?? ()

3 0x000000000000000d in ?? ()

4 0x00000000004d5f2a in translate (c=0x7ffff46d4000 "P\001\367\367\377\177", hash=4294955776, location=@0x7ffff4136b28: 0x7fffaffa6b40)

at ../../JavaScriptCore/runtime/Identifier.cpp:106

5 translate (location=@0x7ffff4136b28: 0x7fffaffa6b40, hashCode=4294955776, key=) at ../../JavaScriptCore/wtf/HashSet.h:108

6 addPassingHashCode, char const*, JSC::IdentifierCStringTranslator> > (this=0x7ffff52e75a0, extra=, key=) at ../../JavaScriptCore/wtf/HashTable.h:740

7 add (value=, this=0x7ffff52e75a0) at ../../JavaScriptCore/wtf/HashSet.h:189

8 JSC::IdentifierTable::add (this=0x7ffff52e75a0, value=0x7ffff46d4000 "P\001\367\367\377\177")

at ../../JavaScriptCore/runtime/Identifier.cpp:55

9 0x00000000004d748a in JSC::Identifier::add (globalData=, c=0x8 ) at ../../JavaScriptCore/runtime/Identifier.cpp:130

10 0x00007fffafc33ed0 in ?? ()

11 0x00007ffff7f6b218 in ?? ()

12 0x000000000051a624 in JSC::Bindings::QtConnectionObject::execute (this=0x293ed70, argv=) at ../../WebCore/bridge/qt/qt_runtime.cpp:1863

13 0x000000000051ad4b in JSC::Bindings::QtConnectionObject::qt_metacall (this=0x293ed70, _c=QMetaObject::InvokeMetaMethod, _id=, _a=0x7fffffffd720)

at ../../WebCore/bridge/qt/qt_runtime.cpp:1807

14 0x0000000001bfa7ce in QMetaObject::activate (sender=0x2908310, m=, local_signal_index=, argv=0x7fffffffd720)

at kernel/qobject.cpp:3563

15 0x0000000000451683 in WebPage::loadFinished (this=, _t1=...) at moc_webpage.cpp:327

16 0x00000000004155d2 in WebPage::finish (this=0x2908310, ok=) at webpage.cpp:513

17 0x000000000045189d in WebPage::qt_static_metacall (_o=0x2908310, _c=, _id=, _a=0x2901ed0) at moc_webpage.cpp:209

18 0x0000000001bfe8de in QObject::event (this=0x2908310, e=) at kernel/qobject.cpp:1192

19 0x0000000001558e34 in notify_helper (e=0x29947b0, receiver=0x2908310, this=0x289dd10) at kernel/qapplication.cpp:4551

20 QApplicationPrivate::notify_helper (this=0x289dd10, receiver=0x2908310, e=0x29947b0) at kernel/qapplication.cpp:4523

21 0x000000000155d690 in QApplication::notify (this=0x7fffffffe0f0, receiver=0x2908310, e=0x29947b0) at kernel/qapplication.cpp:4412

22 0x0000000001be711c in QCoreApplication::notifyInternal (this=0x7fffffffe0f0, receiver=0x2908310, event=0x29947b0) at kernel/qcoreapplication.cpp:915

23 0x0000000001beab17 in sendEvent (event=0x29947b0, receiver=0x2908310) at ../../include/QtCore/../../src/corelib/kernel/qcoreapplication.h:231

24 QCoreApplicationPrivate::sendPostedEvents (receiver=0x0, event_type=0, data=0x289adb0) at kernel/qcoreapplication.cpp:1536

25 0x0000000001c0f7a0 in QEventDispatcherUNIX::processEvents (this=, flags=...) at kernel/qeventdispatcher_unix.cpp:898

26 0x00000000015ae64a in QEventDispatcherQPA::processEvents (this=0x289a010, flags=...) at kernel/qeventdispatcher_qpa.cpp:246

27 0x0000000001be5ec2 in QEventLoop::processEvents (this=, flags=...) at kernel/qeventloop.cpp:149

28 0x0000000001be611f in QEventLoop::exec (this=0x7fffffffe010, flags=...) at kernel/qeventloop.cpp:200

29 0x0000000001bead72 in QCoreApplication::exec () at kernel/qcoreapplication.cpp:1187

30 0x000000000040ce3e in main (argc=2, argv=, envp=0x7fffffffe280) at main.cpp:137

This is really hard to debug without getting rid of the ??s. Also there doesn't seem to be instructions on how to get rid of the -O2 compilation flags which makes debugging incredibly difficult.

From what I can see it seems like its the call to JSC::Identifier::add with a bad string that's causing this, but I don't think I can get any more specific then that.

Comment #3

Posted on Sep 15, 2012 by Quick Monkey

Can you give an example of somewhere where it crashes with onAlert?

function closure() { var x; return function(){ x; }; } var p = require('webpage').create(), f = closure(); f(); p.onAlert = f; p.evaluate(function(){ alert(); });

To round out the list of affected callbacks: server.listen also crashes, page.includeJs does not.

PhantomJS has two different ways of invoking callbacks, and one of them seems crash-prone. Some callbacks, like onAlert, use Qt signals; others, like onConfirm, use direct function calls (see webpage.cpp, webserver.cpp, webpage.js, and webserver.js). The callbacks that crash are the ones that use signals. So changing all callbacks to use direct invocation and seeing what that does would be a good first step.

This bug is kinda hard to trigger, though, and probably not a major cause of PhantomJS crashes. It only occurs if a closure f is an immediate callback (e.g., "p.open(url, f)" crashes, but "p.open(url, function(){ f() })" works fine) and f is also called elsewhere in the script. I ran into this bug by doing "log = closure(); log('hi'); p.onConsoleMessage = log;". Triggering it with onLoadFinished seems unlikely -- few users would write such a script (maybe something like "p.onLoadFinished = loadNextPage; loadNextPage();").

As a workaround, change "p.someCallback = f" to "p.someCallback = function(){ f() }".

Comment #4

Posted on Mar 16, 2013 by Happy Horse

Closing. This issue has been moved to GitHub: https://github.com/ariya/phantomjs/issues/10741

Status: Migrated

Labels:
Type-Defect Priority-Medium