[Interpreter]: Add fake support for try/catch/finally.

Adds fake try/catch/finally support hidden behind the flag
--ignition-fake-try-catch.

BUG=v8:4280
LOG=N

Review URL: https://codereview.chromium.org/1402093002

Cr-Commit-Position: refs/heads/master@{#31288}
This commit is contained in:
rmcilroy 2015-10-15 03:35:18 -07:00 committed by Commit bot
parent 4937cc9457
commit 370984018f
5 changed files with 115 additions and 1 deletions

View File

@ -288,6 +288,8 @@ DEFINE_IMPLICATION(ignition, vector_stores)
DEFINE_STRING(ignition_filter, "~~", "filter for ignition interpreter")
DEFINE_STRING(ignition_script_filter, "",
"script filter for ignition interpreter")
DEFINE_BOOL(ignition_fake_try_catch, false,
"enable fake try-catch-finally blocks in ignition for testing")
DEFINE_BOOL(print_bytecode, false,
"print bytecode generated by ignition interpreter")
DEFINE_BOOL(trace_ignition_codegen, false,

View File

@ -433,11 +433,20 @@ void BytecodeGenerator::VisitForOfStatement(ForOfStatement* stmt) {
void BytecodeGenerator::VisitTryCatchStatement(TryCatchStatement* stmt) {
if (FLAG_ignition_fake_try_catch) {
Visit(stmt->try_block());
return;
}
UNIMPLEMENTED();
}
void BytecodeGenerator::VisitTryFinallyStatement(TryFinallyStatement* stmt) {
if (FLAG_ignition_fake_try_catch) {
Visit(stmt->try_block());
Visit(stmt->finally_block());
return;
}
UNIMPLEMENTED();
}

View File

@ -25,6 +25,7 @@ class BytecodeGeneratorHelper {
BytecodeGeneratorHelper() {
i::FLAG_vector_stores = true;
i::FLAG_ignition = true;
i::FLAG_ignition_fake_try_catch = true;
i::FLAG_ignition_filter = StrDup(kFunctionName);
i::FLAG_always_opt = false;
i::FLAG_allow_natives_syntax = true;
@ -2596,6 +2597,79 @@ TEST(TopLevelObjectLiterals) {
}
}
TEST(TryCatch) {
InitializedHandleScope handle_scope;
BytecodeGeneratorHelper helper;
// TODO(rmcilroy): modify tests when we have real try catch support.
ExpectedSnippet<int> snippets[] = {
{"try { return 1; } catch(e) { return 2; }",
0,
1,
5,
{
B(LdaSmi8), U8(1), //
B(Return), //
B(LdaUndefined), //
B(Return), //
},
0},
};
for (size_t i = 0; i < arraysize(snippets); i++) {
Handle<BytecodeArray> bytecode_array =
helper.MakeBytecodeForFunctionBody(snippets[i].code_snippet);
CheckBytecodeArrayEqual(snippets[i], bytecode_array);
}
}
TEST(TryFinally) {
InitializedHandleScope handle_scope;
BytecodeGeneratorHelper helper;
// TODO(rmcilroy): modify tests when we have real try finally support.
ExpectedSnippet<int> snippets[] = {
{"var a = 1; try { a = 2; } finally { a = 3; }",
1 * kPointerSize,
1,
14,
{
B(LdaSmi8), U8(1), //
B(Star), R(0), //
B(LdaSmi8), U8(2), //
B(Star), R(0), //
B(LdaSmi8), U8(3), //
B(Star), R(0), //
B(LdaUndefined), //
B(Return), //
},
0},
{"var a = 1; try { a = 2; } catch(e) { a = 20 } finally { a = 3; }",
1 * kPointerSize,
1,
14,
{
B(LdaSmi8), U8(1), //
B(Star), R(0), //
B(LdaSmi8), U8(2), //
B(Star), R(0), //
B(LdaSmi8), U8(3), //
B(Star), R(0), //
B(LdaUndefined), //
B(Return), //
},
0},
};
for (size_t i = 0; i < arraysize(snippets); i++) {
Handle<BytecodeArray> bytecode_array =
helper.MakeBytecodeForFunctionBody(snippets[i].code_snippet);
CheckBytecodeArrayEqual(snippets[i], bytecode_array);
}
}
} // namespace interpreter
} // namespace internal
} // namespace v8

View File

@ -65,6 +65,7 @@ class InterpreterTester {
feedback_vector_(feedback_vector) {
i::FLAG_vector_stores = true;
i::FLAG_ignition = true;
i::FLAG_ignition_fake_try_catch = true;
i::FLAG_always_opt = false;
// Set ignition filter flag via SetFlagsFromString to avoid double-free
// (or potential leak with StrDup() based on ownership confusion).
@ -1811,3 +1812,31 @@ TEST(InterpreterLogicalAnd) {
CHECK(return_value->SameValue(*literals[i].second));
}
}
TEST(InterpreterTryCatch) {
HandleAndZoneScope handles;
// TODO(rmcilroy): modify tests when we have real try catch support.
std::string source(InterpreterTester::SourceForBody(
"var a = 1; try { a = a + 1; } catch(e) { a = a + 2; }; return a;"));
InterpreterTester tester(handles.main_isolate(), source.c_str());
auto callable = tester.GetCallable<>();
Handle<Object> return_val = callable().ToHandleChecked();
CHECK_EQ(Smi::cast(*return_val), Smi::FromInt(2));
}
TEST(InterpreterTryFinally) {
HandleAndZoneScope handles;
// TODO(rmcilroy): modify tests when we have real try finally support.
std::string source(InterpreterTester::SourceForBody(
"var a = 1; try { a = a + 1; } finally { a = a + 2; }; return a;"));
InterpreterTester tester(handles.main_isolate(), source.c_str());
auto callable = tester.GetCallable<>();
Handle<Object> return_val = callable().ToHandleChecked();
CHECK_EQ(Smi::cast(*return_val), Smi::FromInt(4));
}

View File

@ -129,7 +129,7 @@ class Test262TestSuite(testsuite.TestSuite):
# support the test262 test harness code.
flags = testcase.flags
if '--ignition' in flags:
flags += [self.ignition_script_filter]
flags += [self.ignition_script_filter, "--ignition-fake-try-catch"]
return (flags + context.mode_flags + self.harness +
self.GetIncludesForTest(testcase) + ["--harmony"] +