-
Notifications
You must be signed in to change notification settings - Fork 58
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
cosscript crash with long running scripts #8
Comments
I got it to reproduce as well. Is this on 10.9.2? And I assume you're using the source straight from this repository? |
Yes. I'm currently running 10.9.2 using the latest pull from the repository. |
I'd be interested in that rev, just in case it suggests anything. One of my theories is that it's a problem relating to MOBox, which Mocha uses to associate a javascript object with a cocoa object. These are stored in a map with weak keys but strong values. The key is the cocoa object, so if that goes away, then I think that the MOBox will get dropped from the map. All of which should never happen, as MOBox sets up a retain cycle with the object it represents. If something breaks that cycles somehow though... |
With my hacked together Mocha 2.0 based version, I've managed to get this monster script to crash: for (var n = 0; n < 10000; n++) { |
Whereas this doesn't, even with 10 x the iterations: for (var n = 0; n < 100000; n++) { |
Well the actual revision where the break occurs is SVN r120897 of WebKit, but note that if I revert that particular revision it fixes the problem with the example script I gave above, but it does not fix it for other (more complicated) examples. Also note that it breaks both jstalk and Cocoascript, but I was just focusing on Cocoascript as it's being maintained. Here's the actual patch I made to try to revert it, in case you don't want to spend several hours or so checking out webkit, etc...
|
My suspicion is that it's some sort of memory overwrite coming from Mocha, in which case the WebKit revision might be a coincidence. If the memory access pattern changes slightly, it could mask the crash again for any given case of it. |
I currently believe this is more an issue with JavaScriptCore than with CS (or Mocha), so you can probably close this if you like. I've filed an Apple rdar://19378158 (http://openradar.appspot.com/radar?id=6174800997253120). I also feel this is similar or perhaps the same bug reported here (https://bugs.webkit.org/show_bug.cgi?id=131682), which is just raw JavaScriptCore functions. |
Any updates on this issue? I'm using CocoaScript to write Sketch plugins and I keep getting cti_op_call_NotJSFunction crashes. Even just iterating over a simple array with several 1000s elements crashes it. Interestingly, if I put in a delay of about a second after each few 100s, it doesn't crash! But that makes execution way too slow and unreliable. Please let me know how I can help and what the progress with fixing this major issue is. |
No response from the Apple or WebKit guys. I still believe that JSC is garbage collecting some object when it shouldn't be, but I could spend hours single-stepping through the JSC framework and not get anywhere. I'll keep trying though. |
I'm wondering if a similar crash could be reproduce with JavaScript for Automation- and that's another way to get a real radar filed. I've not been able to reproduce it in Script Editor though. |
In case anyone is interested, I have a fix for this in my fork https://github.com/afedor/CocoaScript master branch. It uses the dreaded JSValueProtect/Unprotect, so it's a bit of a hack, but it works really well. I've been using it in production code with many scripts some running several hundred lines long. |
It's a nice pragmatic workaround... |
And thus it was merged. We'll see how this goes :) |
FYI #24 is not related to this bug, although it does help a bit. |
It looks like we might have an alternative fix here: https://github.com/logancollins/Mocha/pull/23. The Mocha code in the main branch of Cocoascript is a copied-in version of Mocha 1.0 (with a few modifications). I have a branch which is re-worked to pull in Mocha 2.0 as a submodule. We should be able switch over to using that (for Sketch, at least), which means we can pull in that Mocha fix directly. |
Sounds good, where's the branch? I can merge that guy in (or if you want to do a pull request, that's super easy as well). |
This is actually just a smarter implementation of my fix #24 (or logaincollins/Mocha#21), which, while it does help some things, it doesn't actually fix the crashes, either on the master or 2.0 branch of Mocha |
I could provide a pull request that reverts my change and uses this one if you want. It's currently on the same branch as my previous pull |
Hello. So, I've been trying to get Cocoa Script (mainline) to crash using some simple examples, and can't seem to do it anymore on 10.10.4. Anyone got an example that still does it? I'm also trying out the address sanitizer, to see if that finds anything. |
wooooooo:
|
I have some Unit Tests written for the Mocha framework that illustrate it. I could adapt them for CS |
I'd love to see one, danke. |
Some notes to myself here. If I change a script from to: var data = newDoc.dataOfType("public.png") Then I don't get a crasher from an overrelease of an NSData object. |
Yay for address sanitizer - seems like just what we need here. |
Now if I can just get JSCore to build… |
If you're thinking of build JSCore from WebKit, it's easiest to just checkout the package from svn: svn co https://svn.webkit.org/repository/webkit/trunk and build all of webkit (takes a long time) ./Tools/Scripts/build-webkit --debug |
I'll try that out this evening, thanks. |
Well… I couldn't get JSCore to build with the sanitizer. Boo. |
Well if it helps, I don't think this is really a memory issue. It's really sort-of expected behavior. JSCore can garbage collect values at any time if it doesn't think they are being used internally or on the stack. What I can't figure out is that Mocha is supposed to get a Finalize callback when the objects are garbage collected so it can remove them from it's own reference, but that doesn't happen. |
Yeah, I still sort of suspect that it's a memory overwrite, which is perhaps causing JSCore to somehow fail to send that callback, maybe caused by the ffi stuff since that's the only real code which is messing about with memory at a lower level. I have no real evidence for this though, it's just a feeling in my waters :) |
I'm trying to track down two bugs. The first one is the one that @afedor has with his unit tests- this I believe is a JSCore bug. Anyway, spent a couple of hours yesterday doing that. I think Mocha is doing a bit too much retaining and releasing, so I'm trying to simplify that as well. |
Alright, now I see why distributed objects are evil. I've found a bug, or I guess you could say a problem, with the DO stuff. NSArrays an NSData objects are over released for some reason. I'm wondering if they are special cased somehow with DO, and copies are sent over the wire to the local address space, and it's just not getting taken care of correctly. I'll play with this some more later. |
Something just came up with Sketch, which might be relevant to this discussion. We have a crash with a script that accesses @randomsequence was looking into it, and tracked down these documentation references: https://www.mikeash.com/pyblog/friday-qa-2011-09-30-automatic-reference-counting.html
and https://developer.apple.com/library/ios/#releasenotes/ObjectiveC/RN-TransitioningToARC/_index.html
Via [http://stackoverflow.com/q/9146540/272473](Stack Overflow) |
He pointed out that Mocha is using an NSMapTable for the boxing, but the
|
It’s been a while since I looked at the Mocha implementation, so I can’t recall if this is still the case, but one or both of these points might be relevant to some of the script crashes we’ve seen. |
Here's what mocha does:
So, it sounds like this might be a problem. I don't think the zeroing weak ref is a problem though- I'm pretty sure we would have hit it already. But, I'm happy to be proven wrong. I wonder if there's something else we could drop in for the _objectsToBoxes ivar? |
There doesn't seem to be any harm in making the keys strong just for testing (just excess memory usage). It still fails some of my UnitTests with that change. But perhaps there's something to that line of thinking. |
any updates on this front? running into a sketch plugin crash with NSFont (but only on 3.4 beta, 3.3.3 works fine) cc @samdeane |
I'm not sure it's the same issue if it works in one version but not another. You can probably tell if you change the script slightly and the crash happens in a different place or not at all. Anyway, I have a hack that fixes it (See my Apr 2 comment), but this has lead me to be lazy about finding the real problem. |
Hmm... 3.4 beta definitely shouldn't have made things worse, so that might be a separate issue. Could you report that one to mail@bohemiancoding.com? |
Just sent an email! |
I think this is very similar to issue #5 but I though I'd leave a simple example script that illistrates it for me. It really only appears in 10.9 for me. I've spent a lot of time trying to find the cause but most of the JavaScript stuff is black magic to me. It appears though that due to some garbage collection, javascript objects are disappearing before I'm done using them, but this really only manifests itself when you have a long running javascript script. I even went back and bisected the JavaScriptCore framework to find where the change might have started. I found something around Jun 2012 that when I reverted fixed the problem in most cases (I can give you the exact rev if you want), but that didn't really help with the real problem of finding how I could update CocoaScript to avoid the problem.
Anyway, here's the script. It always seems to crash for me around loop 26, with:
1 0x7fff8d1a0fbc JSC::JSValue::get(JSC::ExecState_, unsigned int, JSC::PropertySlot&) const
2 0x7fff8d1d06fa JSC::getByVal(JSC::ExecState_, JSC::JSValue, JSC::JSValue, JSC::ReturnAddressPtr)
3 0x7fff8d1d034e cti_op_get_by_val_generic
4 0x5971a9c02bd7
5 0x7fff8d1168b6 JSC::Interpreter::execute(JSC::ProgramExecutable_, JSC::ExecState_, JSC::JSObject_)
6 0x7fff8d1156b6 JSC::evaluate(JSC::ExecState_, JSC::SourceCode const&, JSC::JSValue, JSC::JSValue*)
7 0x7fff8d1153ad JSEvaluateScript
8 0x106c1a535 -[Mocha evalJSString:scriptPath:]
9 0x106c1a405 -[Mocha evalJSString:]
10 0x106c1a34a -[Mocha evalString:]
11 0x106c3d1fc -[COScript executeString:baseURL:]
12 0x106c3cf8a -[COScript executeString:]
13 0x106c3b1eb main
14 0x7fff969955fd start
==== script ====
var toClass = {}.toString;
var itemDictPath = "/Applications/Xcode.app/Contents/Info.plist";
var itemDict = NSDictionary.dictionaryWithContentsOfFile_(itemDictPath);
var itemList = itemDict["CFBundleDocumentTypes"];
function readDict(item) {
var name = item["CFBundleTypeName"];
var role = item["CFBundleTypeRole"];
print("name class length " + name.length());
//NSLog("role class " + role.class() + " length " + role.length());
}
for (var j = 0; j < 100; j++) {
print(" === LOOP " + j + " ====");
for (var i = 0; i < itemList.count(); i++) {
readDict(itemList[i]);
}
}
The text was updated successfully, but these errors were encountered: