| Index: test/cctest/compiler/test-run-bytecode-graph-builder.cc
|
| diff --git a/test/cctest/compiler/test-run-bytecode-graph-builder.cc b/test/cctest/compiler/test-run-bytecode-graph-builder.cc
|
| index e60afdfdf4418ce6ac6f5c09392e930f8012a24a..5b5876f3ccffb98c22d25946ac7c654d6dafd3dd 100644
|
| --- a/test/cctest/compiler/test-run-bytecode-graph-builder.cc
|
| +++ b/test/cctest/compiler/test-run-bytecode-graph-builder.cc
|
| @@ -67,7 +67,8 @@ class BytecodeGraphCallable {
|
|
|
| class BytecodeGraphTester {
|
| public:
|
| - BytecodeGraphTester(Isolate* isolate, Zone* zone, const char* script)
|
| + BytecodeGraphTester(Isolate* isolate, Zone* zone, const char* script,
|
| + const char* filter = kFunctionName)
|
| : isolate_(isolate), zone_(zone), script_(script) {
|
| i::FLAG_ignition = true;
|
| i::FLAG_always_opt = false;
|
| @@ -75,7 +76,7 @@ class BytecodeGraphTester {
|
| // Set ignition filter flag via SetFlagsFromString to avoid double-free
|
| // (or potential leak with StrDup() based on ownership confusion).
|
| ScopedVector<char> ignition_filter(64);
|
| - SNPrintF(ignition_filter, "--ignition-filter=%s", kFunctionName);
|
| + SNPrintF(ignition_filter, "--ignition-filter=%s", filter);
|
| FlagList::SetFlagsFromString(ignition_filter.start(),
|
| ignition_filter.length());
|
| // Ensure handler table is generated.
|
| @@ -84,8 +85,9 @@ class BytecodeGraphTester {
|
| virtual ~BytecodeGraphTester() {}
|
|
|
| template <class... A>
|
| - BytecodeGraphCallable<A...> GetCallable() {
|
| - return BytecodeGraphCallable<A...>(isolate_, GetFunction());
|
| + BytecodeGraphCallable<A...> GetCallable(
|
| + const char* functionName = kFunctionName) {
|
| + return BytecodeGraphCallable<A...>(isolate_, GetFunction(functionName));
|
| }
|
|
|
| Local<Message> CheckThrowsReturnMessage() {
|
| @@ -109,11 +111,11 @@ class BytecodeGraphTester {
|
| Zone* zone_;
|
| const char* script_;
|
|
|
| - Handle<JSFunction> GetFunction() {
|
| + Handle<JSFunction> GetFunction(const char* functionName) {
|
| CompileRun(script_);
|
| Local<Function> api_function = Local<Function>::Cast(
|
| CcTest::global()
|
| - ->Get(CcTest::isolate()->GetCurrentContext(), v8_str(kFunctionName))
|
| + ->Get(CcTest::isolate()->GetCurrentContext(), v8_str(functionName))
|
| .ToLocalChecked());
|
| Handle<JSFunction> function =
|
| Handle<JSFunction>::cast(v8::Utils::OpenHandle(*api_function));
|
| @@ -1002,6 +1004,133 @@ TEST(BytecodeGraphBuilderThrow) {
|
| }
|
| }
|
|
|
| +
|
| +TEST(BytecodeGraphBuilderContext) {
|
| + HandleAndZoneScope scope;
|
| + Isolate* isolate = scope.main_isolate();
|
| + Zone* zone = scope.main_zone();
|
| + Factory* factory = isolate->factory();
|
| +
|
| + ExpectedSnippet<0> snippets[] = {
|
| + {"var x = 'outer';"
|
| + "function f() {"
|
| + " 'use strict';"
|
| + " {"
|
| + " let x = 'inner';"
|
| + " (function() {x});"
|
| + " }"
|
| + "return(x);"
|
| + "}"
|
| + "f();",
|
| + {factory->NewStringFromStaticChars("outer")}},
|
| + {"var x = 'outer';"
|
| + "function f() {"
|
| + " 'use strict';"
|
| + " {"
|
| + " let x = 'inner ';"
|
| + " var innerFunc = function() {return x};"
|
| + " }"
|
| + "return(innerFunc() + x);"
|
| + "}"
|
| + "f();",
|
| + {factory->NewStringFromStaticChars("inner outer")}},
|
| + {"var x = 'outer';"
|
| + "function f() {"
|
| + " 'use strict';"
|
| + " {"
|
| + " let x = 'inner ';"
|
| + " var innerFunc = function() {return x;};"
|
| + " {"
|
| + " let x = 'innermost ';"
|
| + " var innerMostFunc = function() {return x + innerFunc();};"
|
| + " }"
|
| + " x = 'inner_changed ';"
|
| + " }"
|
| + " return(innerMostFunc() + x);"
|
| + "}"
|
| + "f();",
|
| + {factory->NewStringFromStaticChars("innermost inner_changed outer")}},
|
| + };
|
| +
|
| + size_t num_snippets = sizeof(snippets) / sizeof(snippets[0]);
|
| + for (size_t i = 0; i < num_snippets; i++) {
|
| + ScopedVector<char> script(1024);
|
| + SNPrintF(script, "%s", snippets[i].code_snippet);
|
| +
|
| + BytecodeGraphTester tester(isolate, zone, script.start(), "f");
|
| + auto callable = tester.GetCallable<>("f");
|
| + Handle<Object> return_value = callable().ToHandleChecked();
|
| + CHECK(return_value->SameValue(*snippets[i].return_value()));
|
| + }
|
| +}
|
| +
|
| +
|
| +TEST(BytecodeGraphBuilderLoadContext) {
|
| + HandleAndZoneScope scope;
|
| + Isolate* isolate = scope.main_isolate();
|
| + Zone* zone = scope.main_zone();
|
| + Factory* factory = isolate->factory();
|
| +
|
| + ExpectedSnippet<1> snippets[] = {
|
| + {"function Outer() {"
|
| + " var outerVar = 2;"
|
| + " function Inner(innerArg) {"
|
| + " this.innerFunc = function () {"
|
| + " return outerVar * innerArg;"
|
| + " };"
|
| + " };"
|
| + " this.getInnerFunc = function GetInner() {"
|
| + " return new Inner(3).innerFunc;"
|
| + " }"
|
| + "}"
|
| + "var f = new Outer().getInnerFunc();"
|
| + "f();",
|
| + {factory->NewNumberFromInt(6), factory->undefined_value()}},
|
| + {"function Outer() {"
|
| + " var outerVar = 2;"
|
| + " function Inner(innerArg) {"
|
| + " this.innerFunc = function () {"
|
| + " outerVar = innerArg; return outerVar;"
|
| + " };"
|
| + " };"
|
| + " this.getInnerFunc = function GetInner() {"
|
| + " return new Inner(10).innerFunc;"
|
| + " }"
|
| + "}"
|
| + "var f = new Outer().getInnerFunc();"
|
| + "f();",
|
| + {factory->NewNumberFromInt(10), factory->undefined_value()}},
|
| + {"function testOuter(outerArg) {"
|
| + " this.testinnerFunc = function testInner(innerArg) {"
|
| + " return innerArg + outerArg;"
|
| + " }"
|
| + "}"
|
| + "var f = new testOuter(10).testinnerFunc;"
|
| + "f(0);",
|
| + {factory->NewNumberFromInt(14), factory->NewNumberFromInt(4)}},
|
| + {"function testOuter(outerArg) {"
|
| + " var outerVar = outerArg * 2;"
|
| + " this.testinnerFunc = function testInner(innerArg) {"
|
| + " outerVar = outerVar + innerArg; return outerVar;"
|
| + " }"
|
| + "}"
|
| + "var f = new testOuter(10).testinnerFunc;"
|
| + "f(0);",
|
| + {factory->NewNumberFromInt(24), factory->NewNumberFromInt(4)}}};
|
| +
|
| + size_t num_snippets = sizeof(snippets) / sizeof(snippets[0]);
|
| + for (size_t i = 0; i < num_snippets; i++) {
|
| + ScopedVector<char> script(1024);
|
| + SNPrintF(script, "%s", snippets[i].code_snippet);
|
| +
|
| + BytecodeGraphTester tester(isolate, zone, script.start(), "*");
|
| + auto callable = tester.GetCallable<Handle<Object>>("f");
|
| + Handle<Object> return_value =
|
| + callable(snippets[i].parameter(0)).ToHandleChecked();
|
| + CHECK(return_value->SameValue(*snippets[i].return_value()));
|
| + }
|
| +}
|
| +
|
| } // namespace compiler
|
| } // namespace internal
|
| } // namespace v8
|
|
|