Closed
Bug 1354527
Opened 8 years ago
Closed 8 years ago
Crash [@ js::jit::RInstructionResults::operator[]]
Categories
(Core :: JavaScript Engine, defect)
Tracking
()
RESOLVED
FIXED
mozilla55
Tracking | Status | |
---|---|---|
firefox-esr45 | --- | unaffected |
firefox52 | --- | unaffected |
firefox-esr52 | --- | unaffected |
firefox53 | --- | unaffected |
firefox54 | --- | unaffected |
firefox55 | --- | fixed |
People
(Reporter: gkw, Assigned: evilpie)
References
Details
(Keywords: bugmon, crash, testcase, Whiteboard: [jsbugmon:update])
Crash Data
Attachments
(2 files, 1 obsolete file)
(deleted),
text/plain
|
Details | |
(deleted),
patch
|
jandem
:
review+
|
Details | Diff | Splinter Review |
The following testcase crashes on mozilla-central revision 10ea10d9993c (build with --enable-debug --enable-more-deterministic, run with --fuzzing-safe --no-threads):
"use strict";
for (var j = 0; j < 34; ++j) {
for (var k = 0; k < 30; ++k) {
try {
(function (x) {
(x ? 0 : ([y] = []));
})();
} catch (e) {}
}
}
Backtrace:
#0 0x00000000007461b6 in js::jit::RInstructionResults::operator[] (index=0, this=0x0) at js/src/jit/JitFrames.cpp:1720
#1 js::jit::SnapshotIterator::fromInstructionResult (this=0x7fffde16dc20, index=0) at js/src/jit/JitFrames.cpp:2222
#2 0x00000000007462c2 in js::jit::SnapshotIterator::allocationValue (this=this@entry=0x7fffde16dc20, alloc=..., rm=rm@entry=js::jit::SnapshotIterator::RM_Normal) at js/src/jit/JitFrames.cpp:1947
#3 0x000000000074ad09 in js::jit::SnapshotIterator::read (this=0x7fffde16dc20) at js/src/jit/JitFrameIterator.h:540
#4 js::jit::CloseLiveIteratorIon (tn=<optimized out>, frame=..., cx=0x7f5886075000) at js/src/jit/JitFrames.cpp:351
#5 js::jit::HandleExceptionIon (overrecursed=0x7fffde16da5f, rfe=0x7fffde16e0b8, frame=..., cx=0x7f5886075000) at js/src/jit/JitFrames.cpp:449
#6 js::jit::HandleException (rfe=<optimized out>) at js/src/jit/JitFrames.cpp:873
/snip
For detailed crash information, see attachment.
Setting s-s because a recently-fixed similar bug 1342049 was marked s-s.
Reporter | ||
Comment 1•8 years ago
|
||
Reporter | ||
Comment 2•8 years ago
|
||
autoBisect shows this is probably related to the following changeset:
The first bad revision is:
changeset: https://hg.mozilla.org/mozilla-central/rev/df2d145e4c40
user: Tom Schuster
date: Wed Apr 05 20:35:01 2017 +0200
summary: Bug 1353170 - Implement scalar replacement for NewArrayIterator. r=jandem
Tom, is bug 1353170 a likely regressor?
Blocks: 1353170
Reporter | ||
Updated•8 years ago
|
Flags: needinfo?(evilpies)
Assignee | ||
Comment 3•8 years ago
|
||
Yes, I think I know what's going on. CloseLiveIteratorIon doesn't expect the iterator object to be a recover instruction, i.e. eliminated. I am relatively sure this could be triggered before if somebody took the time to write their own Iterator that would be eliminated by scalar replacement.
Flags: needinfo?(evilpies)
Assignee | ||
Updated•8 years ago
|
Assignee: nobody → evilpies
Updated•8 years ago
|
status-firefox52:
--- → unaffected
status-firefox53:
--- → unaffected
status-firefox54:
--- → unaffected
status-firefox-esr45:
--- → unaffected
status-firefox-esr52:
--- → unaffected
Assignee | ||
Comment 4•8 years ago
|
||
This fixes the crash and seems to correctly recover the object. I am just not sure if the way I constructed MaybeReadFallback makes sense.
Attachment #8855930 -
Flags: feedback?(jdemooij)
Comment 5•8 years ago
|
||
Comment on attachment 8855930 [details] [diff] [review]
POC
Review of attachment 8855930 [details] [diff] [review]:
-----------------------------------------------------------------
Makes sense, but I'm curious about the v.isObject check.
Also, if the iterator closing is not observable for the array iterator, maybe we could assert in debug builds and just return?
::: js/src/jit/JitFrames.cpp
@@ +349,5 @@
> si.skip();
>
> + MaybeReadFallback recover(cx, cx->activation()->asJit(), &frame.frame(), MaybeReadFallback::Fallback_DoNothing);
> + Value v = si.maybeRead(recover);
> + if (!v.isObject())
When is v.isObject() false?
Attachment #8855930 -
Flags: feedback?(jdemooij) → feedback+
Assignee | ||
Comment 6•8 years ago
|
||
Comment on attachment 8855930 [details] [diff] [review]
POC
Review of attachment 8855930 [details] [diff] [review]:
-----------------------------------------------------------------
::: js/src/jit/JitFrames.cpp
@@ +349,5 @@
> si.skip();
>
> + MaybeReadFallback recover(cx, cx->activation()->asJit(), &frame.frame(), MaybeReadFallback::Fallback_DoNothing);
> + Value v = si.maybeRead(recover);
> + if (!v.isObject())
Actually it shouldn't be possible. canRecoverResults is always true when we have a context.
Assignee | ||
Comment 7•8 years ago
|
||
What should we assert for array iterator? A user could probably add their own "return" method to the array iterator prototype anyway. Oh and what fallback behavior should we use: Fallback_DoNothing or Invalidate?
Reporter | ||
Comment 9•8 years ago
|
||
I'm guessing Jan might be able to answer comment 7...
Flags: needinfo?(jdemooij)
Comment 10•8 years ago
|
||
(In reply to Andrew McCreight [:mccr8] from comment #8)
> Is this just a null deref? We could unhide it then.
Yes, this is always a null-deref because the instructionResult_ is initialized to null[1,4,5] and the RInstructionResults[2] given as argument to the operator[] [3] would always be null, as it is not initialized.
(In reply to Jan de Mooij [:jandem] from comment #5)
> > + MaybeReadFallback recover(cx, cx->activation()->asJit(), &frame.frame(), MaybeReadFallback::Fallback_DoNothing);
> > + Value v = si.maybeRead(recover);
> > + if (!v.isObject())
>
> When is v.isObject() false?
At least not from the recover instruction mechanism, In case of a failure[5], we abort with an un-handled oom[6].
[1] http://searchfox.org/mozilla-central/source/js/src/jit/JitFrames.cpp#1743,1752
[2] http://searchfox.org/mozilla-central/source/js/src/jit/JitFrames.cpp#2219-2224
[3] http://searchfox.org/mozilla-central/source/js/src/jit/JitFrames.cpp#1718
[4] http://searchfox.org/mozilla-central/source/js/src/jit/JitFrames.cpp#2165
[5] http://searchfox.org/mozilla-central/source/js/src/jit/JitFrames.cpp#2193
[6] http://searchfox.org/mozilla-central/source/js/src/jit/JitFrames.cpp#1981-1982
Flags: needinfo?(jdemooij)
Assignee | ||
Comment 11•8 years ago
|
||
Okay let's get this finished. Is this patch okay like this or should I change Fallback_DoNothing to Fallback_Invalidate?
Flags: needinfo?(nicolas.b.pierron)
Comment 12•8 years ago
|
||
Fallback_DoNothing should be fine as we are under HandleException, which implies that we are not going to resume the execution of the frame from which we recover the instruction, thus we are not going to diverge from what the execution should have been.
Fallback_Invalidate is used to prevent the diverging executions (i-e getting 2 different allocations for what is supposed to be the same object) by invalidating the code, thus forcing a bailout with the same information as the one recovered while being on an inner function (a different frame).
Flags: needinfo?(nicolas.b.pierron)
Assignee | ||
Comment 13•8 years ago
|
||
Attachment #8855930 -
Attachment is obsolete: true
Attachment #8861118 -
Flags: review?(jdemooij)
Comment 14•8 years ago
|
||
Comment on attachment 8861118 [details] [diff] [review]
Fix
Review of attachment 8861118 [details] [diff] [review]:
-----------------------------------------------------------------
Sorry for the delay.
Attachment #8861118 -
Flags: review?(jdemooij) → review+
Comment 15•8 years ago
|
||
Oh, if this is not a sec-high/crit, can we add a testcase?
Assignee | ||
Comment 16•8 years ago
|
||
Not critical, I landed with a testcase and we should unrestrict this bug.
https://hg.mozilla.org/integration/mozilla-inbound/rev/34f2d83ee773
Comment 17•8 years ago
|
||
bugherder |
Status: NEW → RESOLVED
Closed: 8 years ago
Resolution: --- → FIXED
Target Milestone: --- → mozilla55
You need to log in
before you can comment on or make changes to this bug.
Description
•