[wasm] Test that compile errors contain function names

Even in streaming mode we want to generate deterministic compile
errors, in particular they should contain the function name.
This CL adds a test to check that the name is present in the error
message even if the blob containing the function names is not present
at the time the compile error is detected.

R=ahaas@chromium.org

Bug: v8:8814
Change-Id: I17eb1b3bca48ee2b58b462089c140c30a3511be8
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1526001
Commit-Queue: Clemens Hammacher <clemensh@chromium.org>
Reviewed-by: Andreas Haas <ahaas@chromium.org>
Cr-Commit-Position: refs/heads/master@{#60302}
This commit is contained in:
Clemens Hammacher 2019-03-18 16:34:58 +01:00 committed by Commit Bot
parent d922171717
commit 434066820f

View File

@ -94,9 +94,11 @@ enum class CompilationState {
class TestResolver : public CompilationResultResolver {
public:
TestResolver(CompilationState* state,
TestResolver(CompilationState* state, std::string* error_message,
std::shared_ptr<NativeModule>* native_module)
: state_(state), native_module_(native_module) {}
: state_(state),
error_message_(error_message),
native_module_(native_module) {}
void OnCompilationSucceeded(i::Handle<i::WasmModuleObject> module) override {
*state_ = CompilationState::kFinished;
@ -107,11 +109,15 @@ class TestResolver : public CompilationResultResolver {
void OnCompilationFailed(i::Handle<i::Object> error_reason) override {
*state_ = CompilationState::kFailed;
Handle<String> str =
Object::ToString(CcTest::i_isolate(), error_reason).ToHandleChecked();
error_message_->assign(str->ToCString().get());
}
private:
CompilationState* state_;
std::shared_ptr<NativeModule>* native_module_;
CompilationState* const state_;
std::string* const error_message_;
std::shared_ptr<NativeModule>* const native_module_;
};
class StreamTester {
@ -126,7 +132,8 @@ class StreamTester {
stream_ = i_isolate->wasm_engine()->StartStreamingCompilation(
i_isolate, kAllWasmFeatures, v8::Utils::OpenHandle(*context),
std::make_shared<TestResolver>(&state_, &native_module_));
std::make_shared<TestResolver>(&state_, &error_message_,
&native_module_));
}
std::shared_ptr<StreamingDecoder> stream() { return stream_; }
@ -157,11 +164,14 @@ class StreamTester {
Zone* zone() { return &zone_; }
const std::string& error_message() const { return error_message_; }
private:
AccountingAllocator allocator_;
Zone zone_;
i::HandleScope internal_scope_;
CompilationState state_ = CompilationState::kPending;
std::string error_message_;
std::shared_ptr<NativeModule> native_module_;
std::shared_ptr<StreamingDecoder> stream_;
};
@ -1152,6 +1162,61 @@ STREAM_TEST(TestSetModuleCompiledCallback) {
CHECK(callback_called);
}
// Test that a compile error contains the name of the function, even if the name
// section is not present at the time the error is detected.
STREAM_TEST(TestCompileErrorFunctionName) {
const uint8_t bytes_module_with_code[] = {
WASM_MODULE_HEADER, // module header
kTypeSectionCode, // section code
U32V_1(1 + SIZEOF_SIG_ENTRY_x_x), // section size
U32V_1(1), // type count
SIG_ENTRY_x_x(kLocalI32, kLocalI32), // signature entry
kFunctionSectionCode, // section code
U32V_1(2), // section size
U32V_1(1), // functions count
0, // signature index
kCodeSectionCode, // section code
U32V_1(3), // section size
U32V_1(1), // functions count
1, // body size
kExprNop, // body
};
const uint8_t bytes_names[] = {
kUnknownSectionCode, // section code
U32V_1(11), // section size
4, // section name length
'n', // section name
'a', // section name
'm', // section name
'e', // section name
NameSectionKindCode::kFunction, // name section kind
4, // name section kind length
1, // num function names
0, // function index
1, // function name length
'f', // function name
};
for (bool late_names : {false, true}) {
StreamTester tester;
tester.OnBytesReceived(bytes_module_with_code,
arraysize(bytes_module_with_code));
if (late_names) tester.RunCompilerTasks();
tester.OnBytesReceived(bytes_names, arraysize(bytes_names));
tester.FinishStream();
tester.RunCompilerTasks();
CHECK(tester.IsPromiseRejected());
CHECK_EQ(
"CompileError: WebAssembly.compile(): Compiling function #0:\"f\" "
"failed: function body must end with \"end\" opcode @+25",
tester.error_message());
}
}
#undef STREAM_TEST
} // namespace wasm