[wasm] Refactor WASM test usage of TestingModule.

This cleans up and makes the tests easier to write and understand.
Also prepares for adding the WASM interpreter which needs a
different initialization sequence in tests.

R=ahaas@chromium.org
BUG=

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

Cr-Commit-Position: refs/heads/master@{#34123}
This commit is contained in:
titzer 2016-02-18 07:58:02 -08:00 committed by Commit bot
parent 2363a6a6d9
commit e96a54f7b5
3 changed files with 261 additions and 232 deletions

View File

@ -122,9 +122,9 @@ void EXPECT_CALL(double expected, Handle<JSFunction> jsfunc, double a,
TEST(Run_Int32Sub_jswrapped) {
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.i_ii());
WasmFunctionCompiler t(sigs.i_ii(), &module);
BUILD(t, WASM_I32_SUB(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
EXPECT_CALL(33, jsfunc, 44, 11);
EXPECT_CALL(-8723487, jsfunc, -8000000, 723487);
@ -134,9 +134,9 @@ TEST(Run_Int32Sub_jswrapped) {
TEST(Run_Float32Div_jswrapped) {
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.f_ff());
WasmFunctionCompiler t(sigs.f_ff(), &module);
BUILD(t, WASM_F32_DIV(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
EXPECT_CALL(92, jsfunc, 46, 0.5);
EXPECT_CALL(64, jsfunc, -16, -0.25);
@ -146,9 +146,9 @@ TEST(Run_Float32Div_jswrapped) {
TEST(Run_Float64Add_jswrapped) {
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.d_dd());
WasmFunctionCompiler t(sigs.d_dd(), &module);
BUILD(t, WASM_F64_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
EXPECT_CALL(3, jsfunc, 2, 1);
EXPECT_CALL(-5.5, jsfunc, -5.25, -0.25);
@ -158,9 +158,9 @@ TEST(Run_Float64Add_jswrapped) {
TEST(Run_I32Popcount_jswrapped) {
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.i_i());
WasmFunctionCompiler t(sigs.i_i(), &module);
BUILD(t, WASM_I32_POPCNT(WASM_GET_LOCAL(0)));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
EXPECT_CALL(2, jsfunc, 9, 0);
EXPECT_CALL(3, jsfunc, 11, 0);
@ -180,7 +180,7 @@ TEST(Run_CallJS_Add_jswrapped) {
AddJsFunction(&module, sigs.i_i(), "(function(a) { return a + 99; })");
BUILD(t, WASM_CALL_FUNCTION(js_index, WASM_GET_LOCAL(0)));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
EXPECT_CALL(101, jsfunc, 2, -8);
EXPECT_CALL(199, jsfunc, 100, -1);
@ -218,7 +218,7 @@ void RunJSSelectTest(int which) {
t.Build(&code[0], &code[end]);
}
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
double expected = inputs.arg_d(which);
EXPECT_CALL(expected, jsfunc, 0.0, 0.0);
}
@ -256,7 +256,7 @@ void RunWASMSelectTest(int which) {
TestingModule module;
WasmFunctionCompiler t(&sig, &module);
BUILD(t, WASM_GET_LOCAL(which));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
Handle<Object> args[] = {
isolate->factory()->NewNumber(inputs.arg_d(0)),
@ -305,7 +305,7 @@ void RunWASMSelectAlignTest(int num_args, int num_params) {
TestingModule module;
WasmFunctionCompiler t(&sig, &module);
BUILD(t, WASM_GET_LOCAL(which));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
Handle<Object> args[] = {
isolate->factory()->NewNumber(inputs.arg_d(0)),
@ -382,7 +382,7 @@ void RunJSSelectAlignTest(int num_args, int num_params) {
WasmFunctionCompiler t(&sig, &module);
t.Build(&code[0], &code[end]);
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd(&module));
Handle<JSFunction> jsfunc = WrapCode(&module, t.CompileAndAdd());
Handle<Object> args[] = {
factory->NewNumber(inputs.arg_d(0)),

View File

@ -26,7 +26,7 @@ using namespace v8::internal::wasm;
TEST(Run_WasmInt8Const) {
WasmRunner<int8_t> r;
WasmRunner<int32_t> r;
const byte kExpectedValue = 121;
// return(kExpectedValue)
BUILD(r, WASM_I8(kExpectedValue));
@ -35,7 +35,7 @@ TEST(Run_WasmInt8Const) {
TEST(Run_WasmInt8Const_fallthru1) {
WasmRunner<int8_t> r;
WasmRunner<int32_t> r;
const byte kExpectedValue = 122;
// kExpectedValue
BUILD(r, WASM_I8(kExpectedValue));
@ -44,7 +44,7 @@ TEST(Run_WasmInt8Const_fallthru1) {
TEST(Run_WasmInt8Const_fallthru2) {
WasmRunner<int8_t> r;
WasmRunner<int32_t> r;
const byte kExpectedValue = 123;
// -99 kExpectedValue
BUILD(r, WASM_I8(-99), WASM_I8(kExpectedValue));
@ -54,10 +54,10 @@ TEST(Run_WasmInt8Const_fallthru2) {
TEST(Run_WasmInt8Const_all) {
for (int value = -128; value <= 127; value++) {
WasmRunner<int8_t> r;
WasmRunner<int32_t> r;
// return(value)
BUILD(r, WASM_I8(value));
int8_t result = r.Call();
int32_t result = r.Call();
CHECK_EQ(value, result);
}
}
@ -84,10 +84,9 @@ TEST(Run_WasmInt32Const_many) {
TEST(Run_WasmMemorySize) {
WasmRunner<int32_t> r;
TestingModule module;
WasmRunner<int32_t> r(&module);
module.AddMemory(1024);
r.env()->module = &module;
BUILD(r, kExprMemorySize);
CHECK_EQ(1024, r.Call());
}
@ -605,10 +604,9 @@ TEST(Run_WASM_Int32DivU_byzero_const) {
TEST(Run_WASM_Int32DivS_trap_effect) {
WasmRunner<int32_t> r(MachineType::Int32(), MachineType::Int32());
TestingModule module;
module.AddMemoryElems<int32_t>(8);
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32(), MachineType::Int32());
BUILD(r,
WASM_IF_ELSE(WASM_GET_LOCAL(0),
@ -1223,10 +1221,9 @@ TEST(Run_Wasm_TableSwitch4_fallthru_br) {
TEST(Run_Wasm_F32ReinterpretI32) {
WasmRunner<int32_t> r;
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(8);
r.env()->module = &module;
WasmRunner<int32_t> r(&module);
BUILD(r, WASM_I32_REINTERPRET_F32(
WASM_LOAD_MEM(MachineType::Float32(), WASM_ZERO)));
@ -1240,10 +1237,9 @@ TEST(Run_Wasm_F32ReinterpretI32) {
TEST(Run_Wasm_I32ReinterpretF32) {
WasmRunner<int32_t> r(MachineType::Int32());
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(8);
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_BLOCK(
2, WASM_STORE_MEM(MachineType::Float32(), WASM_ZERO,
@ -1259,10 +1255,9 @@ TEST(Run_Wasm_I32ReinterpretF32) {
TEST(Run_Wasm_ReturnStore) {
WasmRunner<int32_t> r;
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(8);
r.env()->module = &module;
WasmRunner<int32_t> r(&module);
BUILD(r, WASM_STORE_MEM(MachineType::Int32(), WASM_ZERO,
WASM_LOAD_MEM(MachineType::Int32(), WASM_ZERO)));
@ -1281,9 +1276,9 @@ TEST(Run_Wasm_VoidReturn1) {
// Build the test function.
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.v_v());
WasmFunctionCompiler t(sigs.v_v(), &module);
BUILD(t, kExprNop);
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
const int32_t kExpected = -414444;
// Build the calling function.
@ -1301,9 +1296,9 @@ TEST(Run_Wasm_VoidReturn2) {
// Build the test function.
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.v_v());
WasmFunctionCompiler t(sigs.v_v(), &module);
BUILD(t, WASM_RETURN0);
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
const int32_t kExpected = -414444;
// Build the calling function.
@ -1499,11 +1494,10 @@ TEST(Run_Wasm_Loop_if_break_fallthru) {
TEST(Run_Wasm_LoadMemI32) {
WasmRunner<int32_t> r(MachineType::Int32());
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(8);
WasmRunner<int32_t> r(&module, MachineType::Int32());
module.RandomizeMemory(1111);
r.env()->module = &module;
BUILD(r, WASM_LOAD_MEM(MachineType::Int32(), WASM_I8(0)));
@ -1519,11 +1513,10 @@ TEST(Run_Wasm_LoadMemI32) {
TEST(Run_Wasm_LoadMemI32_oob) {
WasmRunner<int32_t> r(MachineType::Uint32());
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(8);
WasmRunner<int32_t> r(&module, MachineType::Uint32());
module.RandomizeMemory(1111);
r.env()->module = &module;
BUILD(r, WASM_LOAD_MEM(MachineType::Int32(), WASM_GET_LOCAL(0)));
@ -1540,12 +1533,11 @@ TEST(Run_Wasm_LoadMemI32_oob) {
TEST(Run_Wasm_LoadMemI32_oob_asm) {
WasmRunner<int32_t> r(MachineType::Uint32());
TestingModule module;
module.asm_js = true;
int32_t* memory = module.AddMemoryElems<int32_t>(8);
WasmRunner<int32_t> r(&module, MachineType::Uint32());
module.RandomizeMemory(1112);
r.env()->module = &module;
BUILD(r, WASM_LOAD_MEM(MachineType::Int32(), WASM_GET_LOCAL(0)));
@ -1574,8 +1566,7 @@ TEST(Run_Wasm_LoadMem_offset_oob) {
for (size_t m = 0; m < arraysize(machineTypes); m++) {
module.RandomizeMemory(1116 + static_cast<int>(m));
WasmRunner<int32_t> r(MachineType::Uint32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Uint32());
uint32_t boundary = 24 - WasmOpcodes::MemSize(machineTypes[m]);
BUILD(r, WASM_LOAD_MEM_OFFSET(machineTypes[m], 8, WASM_GET_LOCAL(0)),
@ -1591,11 +1582,10 @@ TEST(Run_Wasm_LoadMem_offset_oob) {
TEST(Run_Wasm_LoadMemI32_offset) {
WasmRunner<int32_t> r(MachineType::Int32());
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(4);
WasmRunner<int32_t> r(&module, MachineType::Int32());
module.RandomizeMemory(1111);
r.env()->module = &module;
BUILD(r, WASM_LOAD_MEM_OFFSET(MachineType::Int32(), 4, WASM_GET_LOCAL(0)));
@ -1620,15 +1610,14 @@ TEST(Run_Wasm_LoadMemI32_offset) {
#if !V8_TARGET_ARCH_MIPS && !V8_TARGET_ARCH_MIPS64
TEST(Run_Wasm_LoadMemI32_const_oob_misaligned) {
// TODO(titzer): Fix misaligned accesses on MIPS and re-enable.
TestingModule module;
const int kMemSize = 12;
module.AddMemoryElems<byte>(kMemSize);
// TODO(titzer): Fix misaligned accesses on MIPS and re-enable.
for (int offset = 0; offset < kMemSize + 5; offset++) {
for (int index = 0; index < kMemSize + 5; index++) {
WasmRunner<int32_t> r;
r.env()->module = &module;
TestingModule module;
module.AddMemoryElems<byte>(kMemSize);
WasmRunner<int32_t> r(&module);
module.RandomizeMemory();
BUILD(r,
@ -1647,14 +1636,13 @@ TEST(Run_Wasm_LoadMemI32_const_oob_misaligned) {
TEST(Run_Wasm_LoadMemI32_const_oob) {
TestingModule module;
const int kMemSize = 24;
module.AddMemoryElems<byte>(kMemSize);
for (int offset = 0; offset < kMemSize + 5; offset += 4) {
for (int index = 0; index < kMemSize + 5; index += 4) {
WasmRunner<int32_t> r;
r.env()->module = &module;
TestingModule module;
module.AddMemoryElems<byte>(kMemSize);
WasmRunner<int32_t> r(&module);
module.RandomizeMemory();
BUILD(r,
@ -1671,11 +1659,10 @@ TEST(Run_Wasm_LoadMemI32_const_oob) {
TEST(Run_Wasm_StoreMemI32_offset) {
WasmRunner<int32_t> r(MachineType::Int32());
const int32_t kWritten = 0xaabbccdd;
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(4);
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
const int32_t kWritten = 0xaabbccdd;
BUILD(r, WASM_STORE_MEM_OFFSET(MachineType::Int32(), 4, WASM_GET_LOCAL(0),
WASM_I32(kWritten)));
@ -1714,8 +1701,7 @@ TEST(Run_Wasm_StoreMem_offset_oob) {
for (size_t m = 0; m < arraysize(machineTypes); m++) {
module.RandomizeMemory(1119 + static_cast<int>(m));
WasmRunner<int32_t> r(MachineType::Uint32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Uint32());
BUILD(r, WASM_STORE_MEM_OFFSET(machineTypes[m], 8, WASM_GET_LOCAL(0),
WASM_LOAD_MEM(machineTypes[m], WASM_ZERO)),
@ -1735,10 +1721,9 @@ TEST(Run_Wasm_StoreMem_offset_oob) {
#if WASM_64
TEST(Run_Wasm_F64ReinterpretI64) {
WasmRunner<int64_t> r;
TestingModule module;
int64_t* memory = module.AddMemoryElems<int64_t>(8);
r.env()->module = &module;
WasmRunner<int64_t> r(&module);
BUILD(r, WASM_I64_REINTERPRET_F64(
WASM_LOAD_MEM(MachineType::Float64(), WASM_ZERO)));
@ -1752,10 +1737,9 @@ TEST(Run_Wasm_F64ReinterpretI64) {
TEST(Run_Wasm_I64ReinterpretF64) {
WasmRunner<int64_t> r(MachineType::Int64());
TestingModule module;
int64_t* memory = module.AddMemoryElems<int64_t>(8);
r.env()->module = &module;
WasmRunner<int64_t> r(&module, MachineType::Int64());
BUILD(r, WASM_BLOCK(
2, WASM_STORE_MEM(MachineType::Float64(), WASM_ZERO,
@ -1771,11 +1755,10 @@ TEST(Run_Wasm_I64ReinterpretF64) {
TEST(Run_Wasm_LoadMemI64) {
WasmRunner<int64_t> r;
TestingModule module;
int64_t* memory = module.AddMemoryElems<int64_t>(8);
module.RandomizeMemory(1111);
r.env()->module = &module;
WasmRunner<int64_t> r(&module);
BUILD(r, WASM_LOAD_MEM(MachineType::Int64(), WASM_I8(0)));
@ -1793,11 +1776,10 @@ TEST(Run_Wasm_LoadMemI64) {
TEST(Run_Wasm_LoadMemI32_P) {
const int kNumElems = 8;
WasmRunner<int32_t> r(MachineType::Int32());
TestingModule module;
int32_t* memory = module.AddMemoryElems<int32_t>(kNumElems);
WasmRunner<int32_t> r(&module, MachineType::Int32());
module.RandomizeMemory(2222);
r.env()->module = &module;
BUILD(r, WASM_LOAD_MEM(MachineType::Int32(), WASM_GET_LOCAL(0)));
@ -1808,12 +1790,11 @@ TEST(Run_Wasm_LoadMemI32_P) {
TEST(Run_Wasm_MemI32_Sum) {
WasmRunner<uint32_t> r(MachineType::Int32());
const int kNumElems = 20;
const byte kSum = r.AllocateLocal(kAstI32);
TestingModule module;
uint32_t* memory = module.AddMemoryElems<uint32_t>(kNumElems);
r.env()->module = &module;
WasmRunner<uint32_t> r(&module, MachineType::Int32());
const byte kSum = r.AllocateLocal(kAstI32);
BUILD(r, WASM_BLOCK(
2, WASM_WHILE(
@ -1842,11 +1823,10 @@ TEST(Run_Wasm_MemI32_Sum) {
TEST(Run_Wasm_CheckMachIntsZero) {
WasmRunner<uint32_t> r(MachineType::Int32());
const int kNumElems = 55;
TestingModule module;
module.AddMemoryElems<uint32_t>(kNumElems);
r.env()->module = &module;
WasmRunner<uint32_t> r(&module, MachineType::Int32());
BUILD(r, kExprBlock, 2, kExprLoop, 1, kExprIf, kExprGetLocal, 0, kExprBr, 0,
kExprIfElse, kExprI32LoadMem, 0, kExprGetLocal, 0, kExprBr, 2,
@ -1859,8 +1839,6 @@ TEST(Run_Wasm_CheckMachIntsZero) {
TEST(Run_Wasm_MemF32_Sum) {
WasmRunner<int32_t> r(MachineType::Int32());
const byte kSum = r.AllocateLocal(kAstF32);
const int kSize = 5;
TestingModule module;
module.AddMemoryElems<float>(kSize);
@ -1870,7 +1848,8 @@ TEST(Run_Wasm_MemF32_Sum) {
buffer[2] = -77.25;
buffer[3] = 66666.25;
buffer[4] = 5555.25;
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
const byte kSum = r.AllocateLocal(kAstF32);
BUILD(r, WASM_BLOCK(
3, WASM_WHILE(
@ -1895,12 +1874,11 @@ TEST(Run_Wasm_MemF32_Sum) {
#if WASM_64
TEST(Run_Wasm_MemI64_Sum) {
WasmRunner<uint64_t> r(MachineType::Int32());
const int kNumElems = 20;
const byte kSum = r.AllocateLocal(kAstI64);
TestingModule module;
uint64_t* memory = module.AddMemoryElems<uint64_t>(kNumElems);
r.env()->module = &module;
WasmRunner<uint64_t> r(&module, MachineType::Int32());
const byte kSum = r.AllocateLocal(kAstI64);
BUILD(r, WASM_BLOCK(
2, WASM_WHILE(
@ -1932,14 +1910,13 @@ TEST(Run_Wasm_MemI64_Sum) {
template <typename T>
T GenerateAndRunFold(WasmOpcode binop, T* buffer, size_t size,
LocalType astType, MachineType memType) {
WasmRunner<int32_t> r(MachineType::Int32());
const byte kAccum = r.AllocateLocal(astType);
TestingModule module;
module.AddMemoryElems<T>(size);
for (size_t i = 0; i < size; i++) {
module.raw_mem_start<T>()[i] = buffer[i];
}
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
const byte kAccum = r.AllocateLocal(astType);
BUILD(
r,
@ -1978,10 +1955,9 @@ TEST(Build_Wasm_Infinite_Loop) {
TEST(Build_Wasm_Infinite_Loop_effect) {
WasmRunner<int32_t> r(MachineType::Int32());
TestingModule module;
module.AddMemoryElems<int8_t>(16);
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
// Only build the graph and compile, don't run.
BUILD(r, WASM_LOOP(1, WASM_LOAD_MEM(MachineType::Int32(), WASM_ZERO)));
@ -2118,8 +2094,7 @@ TEST(Run_Wasm_Int32LoadInt8_signext) {
int8_t* memory = module.AddMemoryElems<int8_t>(kNumElems);
module.RandomizeMemory();
memory[0] = -1;
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_LOAD_MEM(MachineType::Int8(), WASM_GET_LOCAL(0)));
for (size_t i = 0; i < kNumElems; i++) {
@ -2134,8 +2109,7 @@ TEST(Run_Wasm_Int32LoadInt8_zeroext) {
byte* memory = module.AddMemory(kNumElems);
module.RandomizeMemory(77);
memory[0] = 255;
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_LOAD_MEM(MachineType::Uint8(), WASM_GET_LOCAL(0)));
for (size_t i = 0; i < kNumElems; i++) {
@ -2150,8 +2124,7 @@ TEST(Run_Wasm_Int32LoadInt16_signext) {
byte* memory = module.AddMemory(kNumBytes);
module.RandomizeMemory(888);
memory[1] = 200;
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_LOAD_MEM(MachineType::Int16(), WASM_GET_LOCAL(0)));
for (size_t i = 0; i < kNumBytes; i += 2) {
@ -2167,8 +2140,7 @@ TEST(Run_Wasm_Int32LoadInt16_zeroext) {
byte* memory = module.AddMemory(kNumBytes);
module.RandomizeMemory(9999);
memory[1] = 204;
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_LOAD_MEM(MachineType::Uint16(), WASM_GET_LOCAL(0)));
for (size_t i = 0; i < kNumBytes; i += 2) {
@ -2181,8 +2153,7 @@ TEST(Run_Wasm_Int32LoadInt16_zeroext) {
TEST(Run_WasmInt32Global) {
TestingModule module;
int32_t* global = module.AddGlobal<int32_t>(MachineType::Int32());
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
// global = global + p0
BUILD(r, WASM_STORE_GLOBAL(
0, WASM_I32_ADD(WASM_LOAD_GLOBAL(0), WASM_GET_LOCAL(0))));
@ -2205,8 +2176,7 @@ TEST(Run_WasmInt32Globals_DontAlias) {
for (int g = 0; g < kNumGlobals; g++) {
// global = global + p0
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_STORE_GLOBAL(
g, WASM_I32_ADD(WASM_LOAD_GLOBAL(g), WASM_GET_LOCAL(0))));
@ -2230,8 +2200,7 @@ TEST(Run_WasmInt32Globals_DontAlias) {
TEST(Run_WasmInt64Global) {
TestingModule module;
int64_t* global = module.AddGlobal<int64_t>(MachineType::Int64());
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
// global = global + p0
BUILD(r, WASM_BLOCK(2, WASM_STORE_GLOBAL(
0, WASM_I64_ADD(
@ -2252,8 +2221,7 @@ TEST(Run_WasmInt64Global) {
TEST(Run_WasmFloat32Global) {
TestingModule module;
float* global = module.AddGlobal<float>(MachineType::Float32());
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
// global = global + p0
BUILD(r, WASM_BLOCK(2, WASM_STORE_GLOBAL(
0, WASM_F32_ADD(
@ -2273,8 +2241,7 @@ TEST(Run_WasmFloat32Global) {
TEST(Run_WasmFloat64Global) {
TestingModule module;
double* global = module.AddGlobal<double>(MachineType::Float64());
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
// global = global + p0
BUILD(r, WASM_BLOCK(2, WASM_STORE_GLOBAL(
0, WASM_F64_ADD(
@ -2305,8 +2272,7 @@ TEST(Run_WasmMixedGlobals) {
float* var_float = module.AddGlobal<float>(MachineType::Float32());
double* var_double = module.AddGlobal<double>(MachineType::Float64());
WasmRunner<int32_t> r(MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(
r,
@ -2408,13 +2374,12 @@ TEST(Run_WasmCallEmpty) {
// Build the target function.
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.i_v());
WasmFunctionCompiler t(sigs.i_v(), &module);
BUILD(t, WASM_I32(kExpected));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the calling function.
WasmRunner<int32_t> r;
r.env()->module = &module;
WasmRunner<int32_t> r(&module);
BUILD(r, WASM_CALL_FUNCTION0(index));
int32_t result = r.Call();
@ -2428,13 +2393,12 @@ TEST(Run_WasmCallF32StackParameter) {
for (int i = 0; i < 20; i++) param_types[i] = kAstF32;
FunctionSig sig(1, 19, param_types);
TestingModule module;
WasmFunctionCompiler t(&sig);
WasmFunctionCompiler t(&sig, &module);
BUILD(t, WASM_GET_LOCAL(17));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the calling function.
WasmRunner<float> r;
r.env()->module = &module;
WasmRunner<float> r(&module);
BUILD(r, WASM_CALL_FUNCTION(
index, WASM_F32(1.0f), WASM_F32(2.0f), WASM_F32(4.0f),
WASM_F32(8.0f), WASM_F32(16.0f), WASM_F32(32.0f),
@ -2454,13 +2418,12 @@ TEST(Run_WasmCallF64StackParameter) {
for (int i = 0; i < 20; i++) param_types[i] = kAstF64;
FunctionSig sig(1, 19, param_types);
TestingModule module;
WasmFunctionCompiler t(&sig);
WasmFunctionCompiler t(&sig, &module);
BUILD(t, WASM_GET_LOCAL(17));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the calling function.
WasmRunner<double> r;
r.env()->module = &module;
WasmRunner<double> r(&module);
BUILD(r, WASM_CALL_FUNCTION(index, WASM_F64(1.0), WASM_F64(2.0),
WASM_F64(4.0), WASM_F64(8.0), WASM_F64(16.0),
WASM_F64(32.0), WASM_F64(64.0), WASM_F64(128.0),
@ -2482,13 +2445,13 @@ TEST(Run_WasmCallI64Parameter) {
FunctionSig sig(1, 19, param_types);
for (int i = 0; i < 19; i++) {
TestingModule module;
WasmFunctionCompiler t(&sig);
WasmFunctionCompiler t(&sig, &module);
if (i == 2 || i == 3) {
continue;
} else {
BUILD(t, WASM_GET_LOCAL(i));
}
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the calling function.
WasmRunner<int32_t> r;
@ -2527,15 +2490,13 @@ TEST(Run_WasmCallVoid) {
TestingModule module;
module.AddMemory(16);
module.RandomizeMemory();
WasmFunctionCompiler t(sigs.v_v());
t.env.module = &module;
WasmFunctionCompiler t(sigs.v_v(), &module);
BUILD(t, WASM_STORE_MEM(MachineType::Int32(), WASM_I8(kMemOffset),
WASM_I32(kExpected)));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the calling function.
WasmRunner<int32_t> r;
r.env()->module = &module;
WasmRunner<int32_t> r(&module);
BUILD(r, WASM_CALL_FUNCTION0(index),
WASM_LOAD_MEM(MachineType::Int32(), WASM_I8(kMemOffset)));
@ -2549,13 +2510,12 @@ TEST(Run_WasmCall_Int32Add) {
// Build the target function.
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.i_ii());
WasmFunctionCompiler t(sigs.i_ii(), &module);
BUILD(t, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the caller function.
WasmRunner<int32_t> r(MachineType::Int32(), MachineType::Int32());
r.env()->module = &module;
WasmRunner<int32_t> r(&module, MachineType::Int32(), MachineType::Int32());
BUILD(r, WASM_CALL_FUNCTION(index, WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
FOR_INT32_INPUTS(i) {
@ -2573,13 +2533,12 @@ TEST(Run_WasmCall_Int64Sub) {
// Build the target function.
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t(sigs.l_ll());
WasmFunctionCompiler t(sigs.l_ll(), &module);
BUILD(t, WASM_I64_SUB(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Build the caller function.
WasmRunner<int64_t> r(MachineType::Int64(), MachineType::Int64());
r.env()->module = &module;
WasmRunner<int64_t> r(&module, MachineType::Int64(), MachineType::Int64());
BUILD(r, WASM_CALL_FUNCTION(index, WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
FOR_INT32_INPUTS(i) {
@ -2600,16 +2559,15 @@ TEST(Run_WasmCall_Int64Sub) {
TEST(Run_WasmCall_Float32Sub) {
TestSignatures sigs;
WasmFunctionCompiler t(sigs.f_ff());
TestingModule module;
WasmFunctionCompiler t(sigs.f_ff(), &module);
// Build the target function.
TestingModule module;
BUILD(t, WASM_F32_SUB(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
uint32_t index = t.CompileAndAdd(&module);
uint32_t index = t.CompileAndAdd();
// Builder the caller function.
WasmRunner<float> r(MachineType::Float32(), MachineType::Float32());
r.env()->module = &module;
WasmRunner<float> r(&module, MachineType::Float32(), MachineType::Float32());
BUILD(r, WASM_CALL_FUNCTION(index, WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
FOR_FLOAT32_INPUTS(i) {
@ -2622,10 +2580,9 @@ TEST(Run_WasmCall_Float32Sub) {
TEST(Run_WasmCall_Float64Sub) {
WasmRunner<int32_t> r;
TestingModule module;
double* memory = module.AddMemoryElems<double>(16);
r.env()->module = &module;
WasmRunner<int32_t> r(&module);
// TODO(titzer): convert to a binop test.
BUILD(r, WASM_BLOCK(
@ -2695,36 +2652,32 @@ static void Run_WasmMixedCall_N(int start) {
for (int i = 0; i < num_params; i++) {
b.AddParam(WasmOpcodes::LocalTypeFor(memtypes[i]));
}
WasmFunctionCompiler t(b.Build());
t.env.module = &module;
WasmFunctionCompiler t(b.Build(), &module);
BUILD(t, WASM_GET_LOCAL(which));
index = t.CompileAndAdd(&module);
index = t.CompileAndAdd();
// =========================================================================
// Build the calling function.
// =========================================================================
WasmRunner<int32_t> r;
r.env()->module = &module;
WasmRunner<int32_t> r(&module);
{
std::vector<byte> code;
ADD_CODE(code,
static_cast<byte>(WasmOpcodes::LoadStoreOpcodeOf(result, true)),
WasmOpcodes::LoadStoreAccessOf(false));
ADD_CODE(code, WASM_ZERO);
ADD_CODE(code, kExprCallFunction, static_cast<byte>(index));
std::vector<byte> code;
ADD_CODE(code,
static_cast<byte>(WasmOpcodes::LoadStoreOpcodeOf(result, true)),
WasmOpcodes::LoadStoreAccessOf(false));
ADD_CODE(code, WASM_ZERO);
ADD_CODE(code, kExprCallFunction, static_cast<byte>(index));
for (int i = 0; i < num_params; i++) {
int offset = (i + 1) * kElemSize;
ADD_CODE(code, WASM_LOAD_MEM(memtypes[i], WASM_I8(offset)));
}
ADD_CODE(code, WASM_I32(kExpected));
size_t end = code.size();
code.push_back(0);
r.Build(&code[0], &code[end]);
for (int i = 0; i < num_params; i++) {
int offset = (i + 1) * kElemSize;
ADD_CODE(code, WASM_LOAD_MEM(memtypes[i], WASM_I8(offset)));
}
ADD_CODE(code, WASM_I32(kExpected));
size_t end = code.size();
code.push_back(0);
r.Build(&code[0], &code[end]);
// Run the code.
for (int t = 0; t < 10; t++) {
module.RandomizeMemory();
@ -2747,6 +2700,27 @@ TEST(Run_WasmMixedCall_1) { Run_WasmMixedCall_N(1); }
TEST(Run_WasmMixedCall_2) { Run_WasmMixedCall_N(2); }
TEST(Run_WasmMixedCall_3) { Run_WasmMixedCall_N(3); }
TEST(Run_Wasm_AddCall) {
TestSignatures sigs;
TestingModule module;
WasmFunctionCompiler t1(sigs.i_ii(), &module);
BUILD(t1, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t1.CompileAndAdd();
WasmRunner<int32_t> r(&module, MachineType::Int32());
byte local = r.AllocateLocal(kAstI32);
BUILD(r,
WASM_BLOCK(2, WASM_SET_LOCAL(local, WASM_I8(99)),
WASM_I32_ADD(
WASM_CALL_FUNCTION(t1.function_index_, WASM_GET_LOCAL(0),
WASM_GET_LOCAL(0)),
WASM_CALL_FUNCTION(t1.function_index_, WASM_GET_LOCAL(1),
WASM_GET_LOCAL(local)))));
CHECK_EQ(198, r.Call(0));
CHECK_EQ(200, r.Call(1));
CHECK_EQ(100, r.Call(-49));
}
TEST(Run_Wasm_CountDown_expr) {
WasmRunner<int32_t> r(MachineType::Int32());
@ -2916,10 +2890,9 @@ TEST(Run_Wasm_LoadStoreI64_sx) {
kExprI64LoadMem};
for (size_t m = 0; m < arraysize(loads); m++) {
WasmRunner<int64_t> r;
TestingModule module;
byte* memory = module.AddMemoryElems<byte>(16);
r.env()->module = &module;
WasmRunner<int64_t> r(&module);
byte code[] = {kExprI64StoreMem, 0, kExprI8Const, 8,
loads[m], 0, kExprI8Const, 0};
@ -2948,17 +2921,16 @@ TEST(Run_Wasm_LoadStoreI64_sx) {
TEST(Run_Wasm_SimpleCallIndirect) {
WasmRunner<int32_t> r(MachineType::Int32());
TestSignatures sigs;
TestingModule module;
r.env()->module = &module;
WasmFunctionCompiler t1(sigs.i_ii());
BUILD(t1, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t1.CompileAndAdd(&module, /*sig_index*/ 1);
WasmFunctionCompiler t2(sigs.i_ii());
WasmFunctionCompiler t1(sigs.i_ii(), &module);
BUILD(t1, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t1.CompileAndAdd(/*sig_index*/ 1);
WasmFunctionCompiler t2(sigs.i_ii(), &module);
BUILD(t2, WASM_I32_SUB(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t2.CompileAndAdd(&module, /*sig_index*/ 1);
t2.CompileAndAdd(/*sig_index*/ 1);
// Signature table.
module.AddSignature(sigs.f_ff());
@ -2971,6 +2943,7 @@ TEST(Run_Wasm_SimpleCallIndirect) {
module.PopulateIndirectFunctionTable();
// Builder the caller function.
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_CALL_INDIRECT(1, WASM_GET_LOCAL(0), WASM_I8(66), WASM_I8(22)));
CHECK_EQ(88, r.Call(0));
@ -2980,18 +2953,16 @@ TEST(Run_Wasm_SimpleCallIndirect) {
TEST(Run_Wasm_MultipleCallIndirect) {
WasmRunner<int32_t> r(MachineType::Int32(), MachineType::Int32(),
MachineType::Int32());
TestSignatures sigs;
TestingModule module;
r.env()->module = &module;
WasmFunctionCompiler t1(sigs.i_ii());
BUILD(t1, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t1.CompileAndAdd(&module, /*sig_index*/ 1);
WasmFunctionCompiler t2(sigs.i_ii());
WasmFunctionCompiler t1(sigs.i_ii(), &module);
BUILD(t1, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t1.CompileAndAdd(/*sig_index*/ 1);
WasmFunctionCompiler t2(sigs.i_ii(), &module);
BUILD(t2, WASM_I32_SUB(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t2.CompileAndAdd(&module, /*sig_index*/ 1);
t2.CompileAndAdd(/*sig_index*/ 1);
// Signature table.
module.AddSignature(sigs.f_ff());
@ -3004,6 +2975,8 @@ TEST(Run_Wasm_MultipleCallIndirect) {
module.PopulateIndirectFunctionTable();
// Builder the caller function.
WasmRunner<int32_t> r(&module, MachineType::Int32(), MachineType::Int32(),
MachineType::Int32());
BUILD(r,
WASM_I32_ADD(WASM_CALL_INDIRECT(1, WASM_GET_LOCAL(0), WASM_GET_LOCAL(1),
WASM_GET_LOCAL(2)),
@ -3022,20 +2995,20 @@ TEST(Run_Wasm_MultipleCallIndirect) {
}
TEST(Run_Wasm_CallIndirect_NoTable) {
WasmRunner<int32_t> r(MachineType::Int32());
TestSignatures sigs;
TestingModule module;
r.env()->module = &module;
// One function.
WasmFunctionCompiler t1(sigs.i_ii());
WasmFunctionCompiler t1(sigs.i_ii(), &module);
BUILD(t1, WASM_I32_ADD(WASM_GET_LOCAL(0), WASM_GET_LOCAL(1)));
t1.CompileAndAdd(&module, /*sig_index*/ 1);
t1.CompileAndAdd(/*sig_index*/ 1);
// Signature table.
module.AddSignature(sigs.f_ff());
module.AddSignature(sigs.i_ii());
// Builder the caller function.
WasmRunner<int32_t> r(&module, MachineType::Int32());
BUILD(r, WASM_CALL_INDIRECT(1, WASM_GET_LOCAL(0), WASM_I8(66), WASM_I8(22)));
CHECK_TRAP(r.Call(0));
@ -3458,8 +3431,7 @@ void CompileCallIndirectMany(LocalType param) {
module.AddSignature(sig);
module.AddIndirectFunctionTable(nullptr, 0);
WasmFunctionCompiler t(sig);
t.env.module = &module;
WasmFunctionCompiler t(sig, &module);
std::vector<byte> code;
ADD_CODE(code, kExprCallIndirect, 1);
@ -3469,7 +3441,7 @@ void CompileCallIndirectMany(LocalType param) {
}
t.Build(&code[0], &code[0] + code.size());
t.Compile(&module);
t.Compile();
}
}

View File

@ -36,6 +36,8 @@
#define WASM_64 0
#endif
static const uint32_t kMaxFunctions = 10;
// TODO(titzer): check traps more robustly in tests.
// Currently, in tests, we just return 0xdeadbeef from the function in which
// the trap occurs if the runtime context is not available to throw a JavaScript
@ -68,17 +70,20 @@ inline void init_env(FunctionEnv* env, FunctionSig* sig) {
const uint32_t kMaxGlobalsSize = 128;
// A helper for module environments that adds the ability to allocate memory
// and global variables. Contains a built-in {WasmModuleInstance}.
// and global variables. Contains a built-in {WasmModule} and
// {WasmModuleInstance}.
class TestingModule : public ModuleEnv {
public:
TestingModule() : instance_(nullptr), global_offset(0) {
TestingModule() : instance_(&module_), global_offset(0) {
module_.shared_isolate = CcTest::InitIsolateOnce();
module = &module_;
instance = &instance_;
instance->module = &module_;
instance->globals_start = global_data;
instance->globals_size = kMaxGlobalsSize;
instance->mem_start = nullptr;
instance->mem_size = 0;
instance->function_code = nullptr;
module = nullptr;
linker = nullptr;
asm_js = false;
memset(global_data, 0, sizeof(global_data));
@ -88,8 +93,9 @@ class TestingModule : public ModuleEnv {
if (instance->mem_start) {
free(instance->mem_start);
}
if (instance->function_code) delete instance->function_code;
if (module) delete module;
if (instance->function_code) {
delete instance->function_code;
}
}
byte* AddMemory(size_t size) {
@ -115,7 +121,6 @@ class TestingModule : public ModuleEnv {
}
byte AddSignature(FunctionSig* sig) {
AllocModule();
if (!module->signatures) {
module->signatures = new std::vector<FunctionSig*>();
}
@ -165,21 +170,27 @@ class TestingModule : public ModuleEnv {
rng.NextBytes(raw, end - raw);
}
WasmFunction* AddFunction(FunctionSig* sig, Handle<Code> code) {
AllocModule();
int AddFunction(FunctionSig* sig, Handle<Code> code) {
if (module->functions == nullptr) {
module->functions = new std::vector<WasmFunction>();
// TODO(titzer): Reserving space here to avoid the underlying WasmFunction
// structs from moving.
module->functions->reserve(kMaxFunctions);
instance->function_code = new std::vector<Handle<Code>>();
}
uint32_t index = static_cast<uint32_t>(module->functions->size());
module->functions->push_back(
{sig, index, 0, 0, 0, 0, 0, 0, 0, false, false});
instance->function_code->push_back(code);
return &module->functions->back();
DCHECK_LT(index, kMaxFunctions); // limited for testing.
return index;
}
void SetFunctionCode(uint32_t index, Handle<Code> code) {
instance->function_code->at(index) = code;
}
void AddIndirectFunctionTable(int* functions, int table_size) {
AllocModule();
Isolate* isolate = module->shared_isolate;
Handle<FixedArray> fixed =
isolate->factory()->NewFixedArray(2 * table_size);
@ -202,14 +213,13 @@ class TestingModule : public ModuleEnv {
}
}
private:
WasmModule module_;
WasmModuleInstance instance_;
uint32_t global_offset;
V8_ALIGNED(8) byte global_data[kMaxGlobalsSize]; // preallocated global data.
WasmGlobal* AddGlobal(MachineType mem_type) {
AllocModule();
if (!module->globals) {
module->globals = new std::vector<WasmGlobal>();
}
@ -221,15 +231,6 @@ class TestingModule : public ModuleEnv {
CHECK_LT(global_offset, kMaxGlobalsSize);
return &module->globals->back();
}
void AllocModule() {
if (module == nullptr) {
module = new WasmModule();
module->shared_isolate = CcTest::InitIsolateOnce();
module->globals = nullptr;
module->functions = nullptr;
module->data_segments = nullptr;
}
}
};
@ -393,23 +394,44 @@ class WasmFunctionWrapper : public HandleAndZoneScope,
Signature<MachineType>* signature_;
};
// A helper for compiling functions that are only internally callable WASM code.
// A helper for compiling WASM functions for testing. This class can create a
// standalone function if {module} is NULL or a function within a
// {TestingModule}. It contains the internal state for compilation (i.e.
// TurboFan graph) and, later, interpretation.
class WasmFunctionCompiler : public HandleAndZoneScope,
private GraphAndBuilders {
public:
explicit WasmFunctionCompiler(FunctionSig* sig, ModuleEnv* module = nullptr)
explicit WasmFunctionCompiler(FunctionSig* sig, TestingModule* module)
: GraphAndBuilders(main_zone()),
jsgraph(this->isolate(), this->graph(), this->common(), nullptr,
nullptr, this->machine()),
descriptor_(nullptr) {
descriptor_(nullptr),
testing_module_(module) {
init_env(&env, sig);
env.module = module;
if (module) {
// Get a new function from the testing module.
function_ = nullptr;
function_index_ = module->AddFunction(sig, Handle<Code>::null());
} else {
// Create our own function.
function_ = new WasmFunction();
function_->sig = sig;
function_index_ = 0;
}
}
~WasmFunctionCompiler() {
if (function_) delete function_;
}
JSGraph jsgraph;
FunctionEnv env;
// The call descriptor is initialized when the function is compiled.
CallDescriptor* descriptor_;
TestingModule* testing_module_;
WasmFunction* function_;
int function_index_;
Isolate* isolate() { return main_isolate(); }
Graph* graph() const { return main_graph_; }
@ -424,6 +446,13 @@ class WasmFunctionCompiler : public HandleAndZoneScope,
CallDescriptor* descriptor() { return descriptor_; }
void Build(const byte* start, const byte* end) {
// Transfer local counts before compiling.
function()->local_i32_count = env.local_i32_count;
function()->local_i64_count = env.local_i64_count;
function()->local_f32_count = env.local_f32_count;
function()->local_f64_count = env.local_f64_count;
// Build the TurboFan graph.
TestBuildingGraph(main_zone(), &jsgraph, &env, start, end);
}
@ -435,11 +464,12 @@ class WasmFunctionCompiler : public HandleAndZoneScope,
return b;
}
Handle<Code> Compile(ModuleEnv* module) {
// TODO(titzer): remove me.
Handle<Code> Compile() {
InitializeDescriptor();
CallDescriptor* desc = descriptor_;
if (kPointerSize == 4) {
desc = module->GetI32WasmCallDescriptor(this->zone(), desc);
desc = testing_module_->GetI32WasmCallDescriptor(this->zone(), desc);
}
CompilationInfo info("wasm compile", this->isolate(), this->zone());
Handle<Code> result =
@ -454,18 +484,21 @@ class WasmFunctionCompiler : public HandleAndZoneScope,
return result;
}
uint32_t CompileAndAdd(TestingModule* module, int sig_index = 0) {
uint32_t index = 0;
if (module->module && module->module->functions) {
index = static_cast<uint32_t>(module->module->functions->size());
}
WasmFunction* function = module->AddFunction(env.sig, Compile(module));
function->sig_index = sig_index;
return index;
// TODO(titzer): remove me.
uint32_t CompileAndAdd(uint16_t sig_index = 0) {
CHECK(testing_module_);
function()->sig_index = sig_index;
Handle<Code> code = Compile();
testing_module_->SetFunctionCode(function_index_, code);
return static_cast<uint32_t>(function_index_);
}
WasmFunction* function() {
if (function_) return function_;
return &testing_module_->module->functions->at(function_index_);
}
};
// A helper class to build graphs from Wasm bytecode, generate machine
// code, and run that code.
template <typename ReturnType>
@ -475,10 +508,28 @@ class WasmRunner {
MachineType p1 = MachineType::None(),
MachineType p2 = MachineType::None(),
MachineType p3 = MachineType::None())
: signature_(MachineTypeForC<ReturnType>() == MachineType::None() ? 0 : 1,
: compiled_(false),
signature_(MachineTypeForC<ReturnType>() == MachineType::None() ? 0 : 1,
GetParameterCount(p0, p1, p2, p3), storage_),
compiler_(&signature_),
compilation_done_(false) {
compiler_(&signature_, nullptr) {
InitSigStorage(p0, p1, p2, p3);
}
WasmRunner(TestingModule* module, MachineType p0 = MachineType::None(),
MachineType p1 = MachineType::None(),
MachineType p2 = MachineType::None(),
MachineType p3 = MachineType::None())
: compiled_(false),
signature_(MachineTypeForC<ReturnType>() == MachineType::None() ? 0 : 1,
GetParameterCount(p0, p1, p2, p3), storage_),
compiler_(&signature_, module) {
DCHECK(module);
InitSigStorage(p0, p1, p2, p3);
}
void InitSigStorage(MachineType p0, MachineType p1, MachineType p2,
MachineType p3) {
int index = 0;
MachineType ret = MachineTypeForC<ReturnType>();
if (ret != MachineType::None()) {
@ -497,39 +548,44 @@ class WasmRunner {
wrapper_.Init(compiler_.descriptor(), p0, p1, p2, p3);
}
FunctionEnv* env() { return &compiler_.env; }
// Builds a graph from the given Wasm code, and generates the machine
// Builds a graph from the given Wasm code and generates the machine
// code and call wrapper for that graph. This method must not be called
// more than once.
void Build(const byte* start, const byte* end) {
DCHECK(!compilation_done_);
compilation_done_ = true;
// Build the TF graph.
CHECK(!compiled_);
compiled_ = true;
// Build the TF graph within the compiler.
compiler_.Build(start, end);
// Generate code.
Handle<Code> code = compiler_.Compile(env()->module);
Handle<Code> code = compiler_.Compile();
if (compiler_.testing_module_) {
// Update the table of function code in the module.
compiler_.testing_module_->SetFunctionCode(compiler_.function_index_,
code);
}
wrapper_.SetInnerCode(code);
}
ReturnType Call() { return Call(nullptr, nullptr, nullptr, nullptr); }
ReturnType Call() { return Call(0, 0, 0, 0); }
template <typename P0>
ReturnType Call(P0 p0) {
return Call(p0, nullptr, nullptr, nullptr);
return Call(p0, 0, 0, 0);
}
template <typename P0, typename P1>
ReturnType Call(P0 p0, P1 p1) {
return Call(p0, p1, nullptr, nullptr);
return Call(p0, p1, 0, 0);
}
template <typename P0, typename P1, typename P2>
ReturnType Call(P0 p0, P1 p1, P2 p2) {
return Call(p0, p1, p2, nullptr);
return Call(p0, p1, p2, 0);
}
template <typename P0, typename P1, typename P2, typename P3>
@ -551,12 +607,13 @@ class WasmRunner {
return b;
}
private:
protected:
Zone zone;
bool compiled_;
LocalType storage_[WASM_RUNNER_MAX_NUM_PARAMETERS];
FunctionSig signature_;
WasmFunctionCompiler compiler_;
WasmFunctionWrapper<ReturnType> wrapper_;
bool compilation_done_;
static size_t GetParameterCount(MachineType p0, MachineType p1,
MachineType p2, MachineType p3) {