Skip to content

Commit

Permalink
Update testsuite and implement table64
Browse files Browse the repository at this point in the history
See WebAssembly/memory64#51

Includes workaround for #2422
  • Loading branch information
sbc100 committed May 15, 2024
1 parent d1e54a8 commit 20983a7
Show file tree
Hide file tree
Showing 50 changed files with 4,191 additions and 352 deletions.
3 changes: 3 additions & 0 deletions include/wabt/interp/interp.h
Original file line number Diff line number Diff line change
Expand Up @@ -1123,6 +1123,9 @@ class Thread {
T WABT_VECTORCALL Pop();
Value Pop();
u64 PopPtr(const Memory::Ptr& memory);
u64 PopPtr(const Table::Ptr& table);
void PushPtr(const Memory::Ptr& memory, u64 value);
void PushPtr(const Table::Ptr& table, u64 value);

template <typename T>
void WABT_VECTORCALL Push(T);
Expand Down
19 changes: 10 additions & 9 deletions include/wabt/type-checker.h
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,8 @@ class TypeChecker {
Result EndBrTable();
Result OnCall(const TypeVector& param_types, const TypeVector& result_types);
Result OnCallIndirect(const TypeVector& param_types,
const TypeVector& result_types);
const TypeVector& result_types,
const Limits& table_limits);
Result OnIndexedFuncRef(Index* out_index);
Result OnReturnCall(const TypeVector& param_types,
const TypeVector& result_types);
Expand All @@ -99,20 +100,20 @@ class TypeChecker {
Result OnLocalSet(Type);
Result OnLocalTee(Type);
Result OnLoop(const TypeVector& param_types, const TypeVector& result_types);
Result OnMemoryCopy(const Limits& dstlimits, const Limits& srclimits);
Result OnMemoryCopy(const Limits& dst_limits, const Limits& src_limits);
Result OnDataDrop(Index);
Result OnMemoryFill(const Limits& limits);
Result OnMemoryGrow(const Limits& limits);
Result OnMemoryInit(Index, const Limits& limits);
Result OnMemorySize(const Limits& limits);
Result OnTableCopy();
Result OnTableCopy(const Limits& dst_limits, const Limits& src_limits);
Result OnElemDrop(Index);
Result OnTableInit(Index, Index);
Result OnTableGet(Type elem_type);
Result OnTableSet(Type elem_type);
Result OnTableGrow(Type elem_type);
Result OnTableSize();
Result OnTableFill(Type elem_type);
Result OnTableInit(Index, const Limits& limits);
Result OnTableGet(Type elem_type, const Limits& limits);
Result OnTableSet(Type elem_type, const Limits& limits);
Result OnTableGrow(Type elem_type, const Limits& limits);
Result OnTableSize(const Limits& limits);
Result OnTableFill(Type elem_type, const Limits& limits);
Result OnRefFuncExpr(Index func_type, bool force_generic_funcref);
Result OnRefNullExpr(Type type);
Result OnRefIsNullExpr();
Expand Down
3 changes: 3 additions & 0 deletions src/binary-reader-objdump.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1644,6 +1644,9 @@ Result BinaryReaderObjdump::OnTable(Index index,
if (!name.empty()) {
PrintDetails(" <" PRIstringview ">", WABT_PRINTF_STRING_VIEW_ARG(name));
}
if (elem_limits->is_64) {
PrintDetails(" i64");
}
PrintDetails("\n");
return Result::Ok;
}
Expand Down
4 changes: 3 additions & 1 deletion src/binary-reader.cc
Original file line number Diff line number Diff line change
Expand Up @@ -582,14 +582,16 @@ Result BinaryReader::ReadTable(Type* out_elem_type, Limits* out_elem_limits) {
bool is_64 = flags & WABT_BINARY_LIMITS_IS_64_FLAG;
const uint8_t unknown_flags = flags & ~WABT_BINARY_LIMITS_ALL_FLAGS;
ERROR_IF(is_shared, "tables may not be shared");
ERROR_IF(is_64, "tables may not be 64-bit");
ERROR_IF(is_64 && !options_.features.memory64_enabled(),
"memory64 not allowed");
ERROR_UNLESS(unknown_flags == 0, "malformed table limits flag: %d", flags);
CHECK_RESULT(ReadU32Leb128(&initial, "table initial elem count"));
if (has_max) {
CHECK_RESULT(ReadU32Leb128(&max, "table max elem count"));
}

out_elem_limits->has_max = has_max;
out_elem_limits->is_64 = is_64;
out_elem_limits->initial = initial;
out_elem_limits->max = max;
return Result::Ok;
Expand Down
16 changes: 12 additions & 4 deletions src/c-writer.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1292,7 +1292,15 @@ void CWriter::Write(const Const& const_) {
// Negative zero. Special-cased so it isn't written as -0 below.
Writef("-0.0");
} else {
Writef("%.17g", Bitcast<double>(f64_bits));
char buf[128];
snprintf(buf, sizeof(buf), "%.17g", Bitcast<double>(f64_bits));
// Append .0 to if sprint didn't include a decimal point or use the
// exponent ('e') form.
// Works around https://github.com/WebAssembly/wabt/issues/2422
if (!strchr(buf, '.') && !strchr(buf, 'e')) {
strcat(buf, ".0");
}
Writef("%s", buf);
}
break;
}
Expand Down Expand Up @@ -3636,18 +3644,18 @@ void CWriter::Write(const ExprList& exprs) {

case ExprType::TableGrow: {
const Table* table = module_->GetTable(cast<TableGrowExpr>(&expr)->var);
Write(StackVar(1, Type::I32), " = wasm_rt_grow_",
Write(StackVar(1, table->elem_limits.IndexType()), " = wasm_rt_grow_",
GetReferenceTypeName(table->elem_type), "_table(",
ExternalInstancePtr(ModuleFieldType::Table, table->name), ", ",
StackVar(0), ", ", StackVar(1), ");", Newline());
DropTypes(2);
PushType(Type::I32);
PushType(table->elem_limits.IndexType());
} break;

case ExprType::TableSize: {
const Table* table = module_->GetTable(cast<TableSizeExpr>(&expr)->var);

PushType(Type::I32);
PushType(table->elem_limits.IndexType());
Write(StackVar(0), " = ",
ExternalInstanceRef(ModuleFieldType::Table, table->name),
".size;", Newline());
Expand Down
28 changes: 19 additions & 9 deletions src/interp/binary-reader-interp.cc
Original file line number Diff line number Diff line change
Expand Up @@ -306,7 +306,7 @@ class BinaryReaderInterp : public BinaryReaderNop {
Index keep_extra,
Index* out_drop_count,
Index* out_keep_count);
Result BeginInitExpr(Type type, FuncDesc* init_func);
Result BeginInitExpr(FuncDesc* init_func);
Result EndInitExpr();

void EmitBr(Index depth,
Expand Down Expand Up @@ -631,7 +631,7 @@ Result BinaryReaderInterp::BeginGlobal(Index index, Type type, bool mutable_) {

Result BinaryReaderInterp::BeginGlobalInitExpr(Index index) {
GlobalDesc& global = module_.globals.back();
return BeginInitExpr(global.type.type, &global.init_func);
return BeginInitExpr(&global.init_func);
}

Result BinaryReaderInterp::EndInitExpr() {
Expand All @@ -642,10 +642,11 @@ Result BinaryReaderInterp::EndInitExpr() {
return Result::Ok;
}

Result BinaryReaderInterp::BeginInitExpr(Type type, FuncDesc* func) {
Result BinaryReaderInterp::BeginInitExpr(FuncDesc* func) {
label_stack_.clear();
func_ = func;
func_->code_offset = istream_.end();
Type type = func->type.results[0];
CHECK_RESULT(validator_.BeginInitExpr(GetLocation(), type));
// Push implicit init func label (equivalent to return).
PushLabel(LabelKind::Try, Istream::kInvalidOffset, Istream::kInvalidOffset);
Expand Down Expand Up @@ -709,16 +710,21 @@ Result BinaryReaderInterp::BeginElemSegment(Index index,
CHECK_RESULT(validator_.OnElemSegment(GetLocation(),
Var(table_index, GetLocation()), mode));

ValueType offset_type = ValueType::I32;
if (table_index < table_types_.size() &&
table_types_[table_index].limits.is_64) {
offset_type = ValueType::I64;
}
FuncDesc init_func{
FuncType{{}, {ValueType::I32}}, {}, Istream::kInvalidOffset, {}};
FuncType{{}, {offset_type}}, {}, Istream::kInvalidOffset, {}};
ElemDesc desc{{}, ValueType::Void, mode, table_index, init_func};
module_.elems.push_back(desc);
return Result::Ok;
}

Result BinaryReaderInterp::BeginElemSegmentInitExpr(Index index) {
ElemDesc& elem = module_.elems.back();
return BeginInitExpr(Type::I32, &elem.init_func);
return BeginInitExpr(&elem.init_func);
}

Result BinaryReaderInterp::EndElemSegmentInitExpr(Index index) {
Expand All @@ -744,7 +750,7 @@ Result BinaryReaderInterp::BeginElemExpr(Index elem_index, Index expr_index) {
elem.elements.push_back(
{FuncType{{}, {elem.type}}, {}, Istream::kInvalidOffset, {}});
assert(expr_index == elem.elements.size() - 1);
return BeginInitExpr(elem.type, &elem.elements.back());
return BeginInitExpr(&elem.elements.back());
}

Result BinaryReaderInterp::EndElemExpr(Index elem_index, Index expr_index) {
Expand All @@ -758,9 +764,8 @@ Result BinaryReaderInterp::OnDataCount(Index count) {
}

Result BinaryReaderInterp::BeginDataSegmentInitExpr(Index index) {
MemoryType t = memory_types_[0];
DataDesc& data = module_.datas.back();
return BeginInitExpr(t.limits.is_64 ? Type::I64 : Type::I32, &data.init_func);
return BeginInitExpr(&data.init_func);
}

Result BinaryReaderInterp::EndDataSegmentInitExpr(Index index) {
Expand All @@ -774,8 +779,13 @@ Result BinaryReaderInterp::BeginDataSegment(Index index,
CHECK_RESULT(validator_.OnDataSegment(
GetLocation(), Var(memory_index, GetLocation()), mode));

ValueType offset_type = ValueType::I32;
if (memory_index < memory_types_.size() &&
memory_types_[memory_index].limits.is_64) {
offset_type = ValueType::I64;
}
FuncDesc init_func{
FuncType{{}, {ValueType::I32}}, {}, Istream::kInvalidOffset, {}};
FuncType{{}, {offset_type}}, {}, Istream::kInvalidOffset, {}};
DataDesc desc{{}, mode, memory_index, init_func};
module_.datas.push_back(desc);
return Result::Ok;
Expand Down
Loading

0 comments on commit 20983a7

Please sign in to comment.