[asm.js] Fix and test assignment to function imports.
This tests and fixes validation failures caused by assignments to variables holding functions references (which are all considered immutable). Such references can come from "stdlib" or "foreign". R=clemensh@chromium.org TEST=mjsunit/asm/global-imports BUG=chromium:719382 Change-Id: Ic02be765e0773a6cc74a54e11a09d42ffb683cb8 Reviewed-on: https://chromium-review.googlesource.com/500188 Reviewed-by: Clemens Hammacher <clemensh@chromium.org> Commit-Queue: Michael Starzinger <mstarzinger@chromium.org> Cr-Commit-Position: refs/heads/master@{#45189}
This commit is contained in:
parent
dfddbd2d2a
commit
17d1530d21
@ -546,6 +546,7 @@ void AsmJsParser::ValidateModuleVarImport(VarInfo* info,
|
||||
info->kind = VarKind::kImportedFunction;
|
||||
info->import = new (zone()->New(sizeof(FunctionImportInfo)))
|
||||
FunctionImportInfo({name, WasmModuleBuilder::SignatureMap(zone())});
|
||||
info->mutable_variable = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1484,6 +1485,9 @@ AsmType* AsmJsParser::AssignmentExpression() {
|
||||
if (info->kind == VarKind::kUnused) {
|
||||
FAILn("Undeclared assignment target");
|
||||
}
|
||||
if (!info->mutable_variable) {
|
||||
FAILn("Expected mutable variable in assignment");
|
||||
}
|
||||
DCHECK(is_local ? info->kind == VarKind::kLocal
|
||||
: info->kind == VarKind::kGlobal);
|
||||
AsmType* value;
|
||||
@ -1494,9 +1498,6 @@ AsmType* AsmJsParser::AssignmentExpression() {
|
||||
if (info->kind == VarKind::kLocal) {
|
||||
current_function_builder_->EmitTeeLocal(info->index);
|
||||
} else if (info->kind == VarKind::kGlobal) {
|
||||
if (!info->mutable_variable) {
|
||||
FAILn("Expected mutable variable in assignment");
|
||||
}
|
||||
current_function_builder_->EmitWithU32V(kExprSetGlobal, VarIndex(info));
|
||||
current_function_builder_->EmitWithU32V(kExprGetGlobal, VarIndex(info));
|
||||
} else {
|
||||
|
@ -21,6 +21,7 @@ var throws = {};
|
||||
var test_count = 0;
|
||||
const stdlib = this;
|
||||
const buffer = new ArrayBuffer(1024);
|
||||
function p(x) { return x * x; }
|
||||
|
||||
function assertThrowsOrEquals(result, fun) {
|
||||
if (result === throws) {
|
||||
@ -52,6 +53,7 @@ function Run(imp, exp, imports, result, valid) {
|
||||
RunAsmJsTest(src, imports, result, valid);
|
||||
}
|
||||
|
||||
// Imports of values from foreign.
|
||||
Run("var x = foreign.x | 0", "(x + int) | 0", {x:12}, 13, true);
|
||||
Run("var x = foreign.x | 0", "(x = int) | 0", {x:12}, 1, true);
|
||||
Run("var x = foreign.x | 0", "+(x + dbl)", {x:12}, 16.2, false);
|
||||
@ -64,3 +66,9 @@ Run("const x = foreign.x | 0", "+(x + dbl)", {x:12}, 16.2, false);
|
||||
Run("const x = +foreign.x", "+(x + dbl)", {x:1.2}, 5.4, true);
|
||||
Run("const x = +foreign.x", "+(x = dbl)", {x:1.2}, throws, false);
|
||||
Run("const x = +foreign.x", "(x + int) | 0", {x:1.2}, 2, false);
|
||||
|
||||
// Imports of functions and values from stdlib and foreign.
|
||||
Run("var x = foreign.x", "x(dbl) | 0", { x:p }, 17, true);
|
||||
Run("var x = foreign.x", "(x = fround, x(dbl)) | 0", { x:p }, 4, false);
|
||||
Run("var x = stdlib.Math.E", "(x = 3.1415, 1) | 0", {}, 1, false);
|
||||
Run("var x = stdlib.Math.imul", "(x = fround, 1) | 0", {}, 1, false);
|
||||
|
Loading…
Reference in New Issue
Block a user