зеркало из https://github.com/mozilla/pjs.git
Bug 728086 - Poison the stack when not in use (r=luke)
This commit is contained in:
Родитель
d85e772fe4
Коммит
db42dc186d
|
@ -0,0 +1,65 @@
|
||||||
|
var expected = '';
|
||||||
|
function TestCase(n, d, e, a) {}
|
||||||
|
function reportFailure (msg) {}
|
||||||
|
function toPrinted(value) {
|
||||||
|
value = value.replace(/\\\n/g, 'NL')
|
||||||
|
.replace(/[^\x20-\x7E]+/g, escapeString);
|
||||||
|
}
|
||||||
|
function escapeString (str) {}
|
||||||
|
function reportCompare (expected, actual, description) {
|
||||||
|
var expected_t = typeof expected;
|
||||||
|
var actual_t = typeof actual;
|
||||||
|
var output = "";
|
||||||
|
var testcase = new TestCase("unknown-test-name", description, expected, actual);
|
||||||
|
reportFailure (description + " : " + output);
|
||||||
|
}
|
||||||
|
function enterFunc (funcName)
|
||||||
|
callStack.push(funcName);
|
||||||
|
try {
|
||||||
|
reportCompare(expectCompile, actualCompile,
|
||||||
|
summary + ': compile actual');
|
||||||
|
} catch(ex) { }
|
||||||
|
var lfcode = new Array();
|
||||||
|
lfcode.push("gczeal(2);\
|
||||||
|
enterFunc ('test');\
|
||||||
|
");
|
||||||
|
lfcode.push("{}");
|
||||||
|
lfcode.push("noexist.js");
|
||||||
|
lfcode.push("var BUGNUMBER = 305064;\
|
||||||
|
var summary = 'Tests the trim, trimRight and trimLeft methods';\
|
||||||
|
var trimMethods = ['trim', 'trimLeft', 'trimRight'];\
|
||||||
|
var whitespace = [\
|
||||||
|
{s : '\\u0009', t : 'HORIZONTAL TAB'},\
|
||||||
|
{s : '\\u200A', t : 'HAIR SPACE'},\
|
||||||
|
];\
|
||||||
|
for (var j = 0; j < trimMethods.length; ++j)\
|
||||||
|
var method = trimMethods[j];\
|
||||||
|
reportCompare(true, true, 'Test skipped. String.prototype.' + method + ' is not supported');\
|
||||||
|
str = '';\
|
||||||
|
for (var i = 0; i < whitespace.length; ++i) {\
|
||||||
|
var v = whitespace[i].s;\
|
||||||
|
var t = (summary)[i].t;\
|
||||||
|
v = v + v + v;\
|
||||||
|
print('Test ' + method + ' with with leading whitespace. : ' + t);\
|
||||||
|
actual = str[method]();\
|
||||||
|
reportCompare(expected, actual, t + ':' + '\"' + toPrinted(str) + '\".' + method + '()');\
|
||||||
|
str = v + 'a' + v;\
|
||||||
|
}\
|
||||||
|
");
|
||||||
|
while (true) {
|
||||||
|
var file = lfcode.shift(); if (file == undefined) { break; }
|
||||||
|
if (file == "evaluate") {
|
||||||
|
} else {
|
||||||
|
loadFile(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
function loadFile(lfVarx) {
|
||||||
|
try {
|
||||||
|
if (lfVarx.substr(-3) == ".js") {
|
||||||
|
switch (lfRunTypeId) {
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
eval(lfVarx);
|
||||||
|
}
|
||||||
|
} catch (lfVare) { }
|
||||||
|
}
|
|
@ -792,9 +792,9 @@ CrossCompartmentWrapper::nativeCall(JSContext *cx, JSObject *wrapper, Class *cla
|
||||||
if (!Wrapper::nativeCall(cx, wrapper, clasp, native, dstArgs))
|
if (!Wrapper::nativeCall(cx, wrapper, clasp, native, dstArgs))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
srcArgs.rval() = dstArgs.rval();
|
||||||
dstArgs.pop();
|
dstArgs.pop();
|
||||||
call.leave();
|
call.leave();
|
||||||
srcArgs.rval() = dstArgs.rval();
|
|
||||||
return call.origin->wrap(cx, &srcArgs.rval());
|
return call.origin->wrap(cx, &srcArgs.rval());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -413,6 +413,7 @@ StackSpace::init()
|
||||||
trustedEnd_ = base_ + CAPACITY_VALS;
|
trustedEnd_ = base_ + CAPACITY_VALS;
|
||||||
conservativeEnd_ = defaultEnd_ = trustedEnd_ - BUFFER_VALS;
|
conservativeEnd_ = defaultEnd_ = trustedEnd_ - BUFFER_VALS;
|
||||||
#endif
|
#endif
|
||||||
|
Debug_SetValueRangeToCrashOnTouch(base_, trustedEnd_);
|
||||||
assertInvariants();
|
assertInvariants();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -736,6 +737,8 @@ ContextStack::pushInvokeArgs(JSContext *cx, uintN argc, InvokeArgsGuard *iag)
|
||||||
if (!firstUnused)
|
if (!firstUnused)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
|
MakeRangeGCSafe(firstUnused, argc);
|
||||||
|
|
||||||
ImplicitCast<CallArgs>(*iag) = CallArgsFromVp(argc, firstUnused);
|
ImplicitCast<CallArgs>(*iag) = CallArgsFromVp(argc, firstUnused);
|
||||||
|
|
||||||
seg_->pushCall(*iag);
|
seg_->pushCall(*iag);
|
||||||
|
@ -751,9 +754,19 @@ ContextStack::popInvokeArgs(const InvokeArgsGuard &iag)
|
||||||
JS_ASSERT(onTop());
|
JS_ASSERT(onTop());
|
||||||
JS_ASSERT(space().firstUnused() == seg_->calls().end());
|
JS_ASSERT(space().firstUnused() == seg_->calls().end());
|
||||||
|
|
||||||
|
Value *oldend = seg_->end();
|
||||||
|
Value *oldbeg;
|
||||||
|
|
||||||
seg_->popCall();
|
seg_->popCall();
|
||||||
if (iag.pushedSeg_)
|
if (iag.pushedSeg_) {
|
||||||
|
oldbeg = reinterpret_cast<Value *>(seg_);
|
||||||
popSegment();
|
popSegment();
|
||||||
|
} else {
|
||||||
|
oldbeg = seg_->end();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (seg_)
|
||||||
|
Debug_SetValueRangeToCrashOnTouch(oldbeg, oldend);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
@ -866,9 +879,19 @@ ContextStack::popFrame(const FrameGuard &fg)
|
||||||
if (fg.regs_.fp()->isNonEvalFunctionFrame())
|
if (fg.regs_.fp()->isNonEvalFunctionFrame())
|
||||||
fg.regs_.fp()->functionEpilogue();
|
fg.regs_.fp()->functionEpilogue();
|
||||||
|
|
||||||
|
Value *oldend = seg_->end();
|
||||||
|
Value *oldbeg;
|
||||||
|
|
||||||
seg_->popRegs(fg.prevRegs_);
|
seg_->popRegs(fg.prevRegs_);
|
||||||
if (fg.pushedSeg_)
|
if (fg.pushedSeg_) {
|
||||||
|
oldbeg = reinterpret_cast<Value *>(seg_);
|
||||||
popSegment();
|
popSegment();
|
||||||
|
} else {
|
||||||
|
oldbeg = seg_->end();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (seg_)
|
||||||
|
Debug_SetValueRangeToCrashOnTouch(oldbeg, oldend);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* NB: this code can call out and observe the stack (e.g., through GC), so
|
* NB: this code can call out and observe the stack (e.g., through GC), so
|
||||||
|
|
|
@ -95,10 +95,10 @@ namespace detail {
|
||||||
*
|
*
|
||||||
* SpiderMonkey uses a per-thread stack to store the activation records,
|
* SpiderMonkey uses a per-thread stack to store the activation records,
|
||||||
* parameters, locals, and expression temporaries for the stack of actively
|
* parameters, locals, and expression temporaries for the stack of actively
|
||||||
* executing scripts, functions and generators. The per-thread stack is owned
|
* executing scripts, functions and generators. The stack is owned by the
|
||||||
* by the StackSpace object stored in the thread's ThreadData.
|
* StackSpace object stored in the runtime.
|
||||||
*
|
*
|
||||||
* The per-thread stack is subdivided into contiguous segments of memory which
|
* The stack is subdivided into contiguous segments of memory which
|
||||||
* have a memory layout invariant that allows fixed offsets to be used for stack
|
* have a memory layout invariant that allows fixed offsets to be used for stack
|
||||||
* access (by jit code) as well as fast call/return. This memory layout is
|
* access (by jit code) as well as fast call/return. This memory layout is
|
||||||
* encapsulated by a set of types that describe different regions of memory.
|
* encapsulated by a set of types that describe different regions of memory.
|
||||||
|
|
Загрузка…
Ссылка в новой задаче