Closed
Bug 995679
Opened 11 years ago
Closed 11 years ago
Differential Testing: Different output message involving ArrayBuffer and neuter
Categories
(Core :: JavaScript Engine: JIT, defect)
Core
JavaScript Engine: JIT
Tracking
()
VERIFIED
FIXED
mozilla32
People
(Reporter: gkw, Assigned: Waldo)
References
Details
(Keywords: regression, sec-critical, testcase, Whiteboard: [adv-main30+][adv-esr24.6+])
Attachments
(3 files)
(deleted),
patch
|
sfink
:
review+
|
Details | Diff | Splinter Review |
(deleted),
patch
|
Details | Diff | Splinter Review | |
(deleted),
patch
|
Details | Diff | Splinter Review |
try {
Object.defineProperty(this, "x", {
get: function() {
return y.length
}
})
z = ArrayBuffer(4)
y = Int8Array(z)
z(x)
} catch (e) {}
for (v in x) {}
neuter(z)
print(x)
$ ./js-opt-64-dm-ts-darwin-ebdf2740dc3e --fuzzing-safe --ion-parallel-compile=off test.js
0
$ ./js-opt-64-dm-ts-darwin-ebdf2740dc3e --fuzzing-safe --ion-parallel-compile=off --ion-eager test.js
4
My configure flags are:
CC="clang -Qunused-arguments" CXX="clang++ -Qunused-arguments" AR=ar sh /Users/skywalker/trees/mozilla-central/js/src/configure --target=x86_64-apple-darwin12.5.0 --enable-optimize --disable-debug --enable-profiling --enable-gczeal --enable-debug-symbols --disable-tests --enable-more-deterministic --with-ccache --enable-threadsafe <other NSPR options>
autoBisect shows this is probably related to the following changeset:
The first bad revision is:
changeset: http://hg.mozilla.org/mozilla-central/rev/6d4ff510c117
user: Luke Wagner
date: Thu Oct 24 08:59:59 2013 -0500
summary: Bug 929786 - Add shell function to neutering (r=sfink)
(s-s because this involves ArrayBuffers)
Since this seems related to ArrayBuffers and neutering, I'm cc'ing the gurus here, Waldo and sfink. (Bug 929786 might just have exposed the issue)
Waldo, is this related?
Flags: needinfo?(jwalden+bmo)
Reporter | ||
Updated•11 years ago
|
status-firefox31:
--- → affected
Assignee | ||
Comment 1•11 years ago
|
||
Cleaner testcase:
var ab = new ArrayBuffer(4);
var ta = new Int8Array(ab);
function q() { return ta.length; }
q() + q();
neuter(ab);
assertEq(q(), 0);
We hit IonBuilder::getTypedArrayLength and inline the typed array's length. All fine, because when we do that we |obj->setImplicitlyUsedUnchecked();|. Or is it?
During the neutering operation we call MarkObjectStateChange on the typed array, which *should* throw away the JIT code that inlines the old length. But if I step into that call a bit, it's clearly not a constraint associated with |obj->setImplicitlyUsedUnchecked()| -- just a TypeCompilerConstraint<ConstraintDataFreezeObjectFlags> watching for the single flag OBJECT_FLAG_UNKNOWN_PROPERTIES (presumably not generated by this code at all).
As far as I can tell, there's no constraint added here that'll cause the inlined typed array length constant to ever be thrown away if the underlying ArrayBuffer is neutered. And, going back through blame, it looks like "implicitly used" is only relevant for purposes of preserving against DCE seemingly "dead" code to compute the object. It has *nothing* to do with a constraint watching for typed array/arraybuffer changes at all.
So, this is pretty much bug 982974 comment 33 and bug 982974 comment 43 (responding to that comment).
Taking. I'll post a fix Monday.
Assignee: nobody → jwalden+bmo
Status: NEW → ASSIGNED
Flags: needinfo?(jwalden+bmo)
OS: Mac OS X → All
Hardware: x86_64 → All
Assignee | ||
Comment 2•11 years ago
|
||
Attachment #8410541 -
Flags: review?(sphink)
Assignee | ||
Comment 3•11 years ago
|
||
The existing watchStateChangeForTypedArrayBuffer is inadequate because of bug 999651. And really, in this case, we don't really care about the data pointer changing anyway. Rather, we should just have this case guard on only the length. (The buffer case perhaps should depend on both, because implicitly it's a constraint that depends on Range(data pointer, length) always being valid. But that's for bug 999651.)
Attachment #8410544 -
Flags: review?(sphink)
Comment 4•11 years ago
|
||
Jeff, what security rating should we give this? sec-high? Just a leak?
Flags: needinfo?(jwalden+bmo)
Assignee | ||
Comment 5•11 years ago
|
||
The inlined-constant length can get burned into bounds checks in IonBuilder::jsop_getelem_typed and IonBuilder::jsop_setelem_typed. If you're careful, it looks like things will fall over accordingly. That makes this critical.
Flags: needinfo?(jwalden+bmo)
Keywords: sec-critical
Assignee | ||
Comment 6•11 years ago
|
||
Well, actually. This only gets used for bounds-checks in conjunction with getTypedArrayElements, which does have a guard in it that detects *some* neutering, per bug 999651. The object has to be constant for length inlining. But the data case has an *additional* restriction on when a not-neutered constraint is added -- the typed array data can't be in the nursery. So *if* the typed array's data is in the nursery, we'll inline a bad length, add no constraint, then load the data pointer out of the object. Because of the back-neutered-arrays-with-ballast trick from bug 982974, this shouldn't index out of bounds of actual memory (at least, not once bug 999140 lands, and ballasts are used everywhere). So maybe we are safe here against anything but incorrect results. Still, I wouldn't want to take that bet unless I absolutely had to.
Comment 8•11 years ago
|
||
Comment on attachment 8410541 [details] [diff] [review]
Test
Review of attachment 8410541 [details] [diff] [review]:
-----------------------------------------------------------------
I know it's something else, but could you also test a larger (always out-of-line) ArrayBuffer?
Attachment #8410541 -
Flags: review?(sphink) → review+
Comment 9•11 years ago
|
||
(In reply to Al Billings [:abillings] from comment #7)
> How far back does this go?
Given comment 6, it sounds like it requires GGC (which introduced the nursery), so just to 31? Waldo?
Comment 10•11 years ago
|
||
Comment on attachment 8410544 [details] [diff] [review]
Patch
Review of attachment 8410544 [details] [diff] [review]:
-----------------------------------------------------------------
I hate to pile things on someone else, but I'm too unfamiliar with the constraint system to feel confident in my ability to review this.
Attachment #8410544 -
Flags: review?(sphink) → review?(shu)
Comment 11•11 years ago
|
||
Comment on attachment 8410544 [details] [diff] [review]
Patch
Review of attachment 8410544 [details] [diff] [review]:
-----------------------------------------------------------------
I think we should just use the new ConstraintDataFreezeObjectForTypedArrayData as patched in bug 999651 instead of adding a new constraint just to check the length.
I highly doubt there are real perf gains to separate the two -- if the programmer neutered the array, I see no reason for us to take extra pains to stay in the JIT.
Attachment #8410544 -
Flags: review?(shu)
Updated•11 years ago
|
Group: javascript-core-security
Assignee | ||
Comment 12•11 years ago
|
||
The bad-length visible behavior dates back "a ways". The wrong code is in mozilla-beta, mozilla-release, and looks to be in b2g18 as well.
As for when bad-indexing happens, less clear. The GGC aspect of the data-access code doesn't date back so far. Prior to the GGC conditioning, it looks like bad lengths were inlined unconditionally for any deemed-constant object. So, GGC doesn't have much of anything to do with this issue, at least sometimes.
The safe inference/assumption is that this needs to be fixed everywhere, I think, with GGC being largely irrelevant to the analysis.
Updated•11 years ago
|
status-firefox32:
--- → affected
tracking-firefox32:
--- → +
Assignee | ||
Comment 13•11 years ago
|
||
I'm abandoning the patch (but not the test) here in favor of fixing this as part of bug 999651's ultimate patch.
Depends on: 999651
Assignee | ||
Comment 14•11 years ago
|
||
Fixed in a mega-rollup patch that also contains bug 999651's fix:
https://hg.mozilla.org/integration/mozilla-inbound/rev/2c631967ab9e
Test not to land yet, probably in a cycle or two.
Assignee | ||
Comment 15•11 years ago
|
||
Backed out, then relanded with CLOBBER:
https://hg.mozilla.org/integration/mozilla-inbound/rev/57b0932e2f06
Comment 16•11 years ago
|
||
Status: ASSIGNED → RESOLVED
Closed: 11 years ago
Resolution: --- → FIXED
Target Milestone: --- → mozilla32
Comment 17•11 years ago
|
||
Based on comment 9, marking 30 and ESR24 as unaffected.
status-firefox30:
--- → unaffected
status-firefox-esr24:
--- → unaffected
Reporter | ||
Comment 18•11 years ago
|
||
(In reply to Lawrence Mandel [:lmandel] from comment #17)
> Based on comment 9, marking 30 and ESR24 as unaffected.
Not true, see:
(In reply to Jeff Walden [:Waldo] (remove +bmo to email) from comment #12)
> The safe inference/assumption is that this needs to be fixed everywhere, I
> think, with GGC being largely irrelevant to the analysis.
Comment 19•11 years ago
|
||
Wow. Missed the end of comment 12. Good catch and thanks Gary.
Given that this is sec-critical, we need to consider branch patches. Given where we are in the cycle, the sooner the better but do take the time needed on central as the fix only landed today.
Assignee | ||
Comment 20•11 years ago
|
||
This is being patched and fixed in bug 999651's work -- fixed on trunk, fixed aurora/beta as of a few minutes ago, and further backports are almost ready to go for approval.
Comment 21•11 years ago
|
||
status-b2g-v1.2:
--- → affected
status-b2g-v1.3:
--- → affected
status-b2g-v1.3T:
--- → affected
status-b2g-v1.4:
--- → fixed
status-b2g-v2.0:
--- → fixed
status-firefox29:
--- → wontfix
Flags: in-testsuite?
Assignee | ||
Comment 22•11 years ago
|
||
Updated•11 years ago
|
Assignee | ||
Comment 23•10 years ago
|
||
Updated•10 years ago
|
Whiteboard: [adv-main30+][adv-esr24.6+]
Updated•10 years ago
|
Group: javascript-core-security
Updated•10 years ago
|
tracking-firefox-esr24:
--- → 30+
Comment 24•10 years ago
|
||
Hi Gary, any chance you can verify fixed on Fx30 and/or Fx24.6.0esr?
Flags: needinfo?(gary)
Reporter | ||
Comment 25•10 years ago
|
||
6d4ff510c117 is needed to expose the issue, and this changeset is not present on ESR 24.
neuter now accepts a different number of arguments on mozilla-beta (30), mozilla-aurora (31) and on mozilla-central (32), so the testcases no longer work the way they do. (e.g. now I get "Error: wrong number of arguments to neuter()" on all branches)
Waldo, any idea how the testcases should be changed? Else, we should just consider this fixed and move on.
Flags: needinfo?(gary) → needinfo?(jwalden+bmo)
Assignee | ||
Comment 26•10 years ago
|
||
Here's an updated test that deals with bug 999755's addition to all branches.
As I recall, this might have been one of the tests that on the very earliest branches (esr24, maybe b2g26 but I don't think so) I couldn't make fail pre-patch and pass post-patch. (I suspect because of object-constantizing constraints I didn't have enough knowledge to work through to write a working testcase. At least, not without spending too much time doing so.) So this may be unverifiable even with this slightly-updated test.
Flags: needinfo?(jwalden+bmo)
Reporter | ||
Comment 27•10 years ago
|
||
Thanks Waldo. I'll retry verification again soon. :)
Flags: needinfo?(gary)
Reporter | ||
Comment 28•10 years ago
|
||
Using Waldo's new tests in comment 26,
I was able to verify a "before (assert) / after (no assert)" situation for aurora (32) due to the original changeset listed in comment 0, rev ebdf2740dc3e, being present.
I was only able to verify "after (no assert)" situations for beta (31) and release (30) due to that changeset not existing on the branches.
Nonetheless, let's assume verified.
Status: RESOLVED → VERIFIED
Flags: needinfo?(gary)
Comment 29•10 years ago
|
||
trying to apply this to SeaMonkey 2.26.1 (Gecko 29) resulted in patch conflicts, and due to the nature of this patchset it seems like I won't be able to take it.
status-seamonkey2.26:
--- → wontfix
Comment 30•10 years ago
|
||
Flags: in-testsuite? → in-testsuite+
Updated•9 years ago
|
Group: core-security
You need to log in
before you can comment on or make changes to this bug.
Description
•