1// Copyright 2021 the V8 project authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#if !V8_ENABLE_WEBASSEMBLY 6#error This header should only be included if WebAssembly is enabled. 7#endif // !V8_ENABLE_WEBASSEMBLY 8 9#ifndef V8_WASM_INIT_EXPR_INTERFACE_H_ 10#define V8_WASM_INIT_EXPR_INTERFACE_H_ 11 12#include "src/wasm/decoder.h" 13#include "src/wasm/function-body-decoder-impl.h" 14#include "src/wasm/wasm-value.h" 15 16namespace v8 { 17namespace internal { 18 19class WasmInstanceObject; 20class JSArrayBuffer; 21 22namespace wasm { 23 24// An interface for WasmFullDecoder used to decode initializer expressions. This 25// interface has two modes: only validation (when {isolate_ == nullptr}), which 26// is used in module-decoder, and code-generation (when {isolate_ != nullptr}), 27// which is used in module-instantiate. We merge two distinct functionalities 28// in one class to reduce the number of WasmFullDecoder instantiations, and thus 29// V8 binary code size. 30class InitExprInterface { 31 public: 32 static constexpr Decoder::ValidateFlag validate = Decoder::kFullValidation; 33 static constexpr DecodingMode decoding_mode = kInitExpression; 34 35 struct Value : public ValueBase<validate> { 36 WasmValue runtime_value; 37 38 template <typename... Args> 39 explicit Value(Args&&... args) V8_NOEXCEPT 40 : ValueBase(std::forward<Args>(args)...) {} 41 }; 42 43 using Control = ControlBase<Value, validate>; 44 using FullDecoder = 45 WasmFullDecoder<validate, InitExprInterface, decoding_mode>; 46 47 InitExprInterface(const WasmModule* module, Isolate* isolate, 48 Handle<WasmInstanceObject> instance) 49 : module_(module), 50 outer_module_(nullptr), 51 isolate_(isolate), 52 instance_(instance) { 53 DCHECK_NOT_NULL(isolate); 54 } 55 56 explicit InitExprInterface(WasmModule* outer_module) 57 : module_(nullptr), outer_module_(outer_module), isolate_(nullptr) {} 58 59#define EMPTY_INTERFACE_FUNCTION(name, ...) \ 60 V8_INLINE void name(FullDecoder* decoder, ##__VA_ARGS__) {} 61 INTERFACE_META_FUNCTIONS(EMPTY_INTERFACE_FUNCTION) 62#undef EMPTY_INTERFACE_FUNCTION 63#define UNREACHABLE_INTERFACE_FUNCTION(name, ...) \ 64 V8_INLINE void name(FullDecoder* decoder, ##__VA_ARGS__) { UNREACHABLE(); } 65 INTERFACE_NON_CONSTANT_FUNCTIONS(UNREACHABLE_INTERFACE_FUNCTION) 66#undef UNREACHABLE_INTERFACE_FUNCTION 67 68#define DECLARE_INTERFACE_FUNCTION(name, ...) \ 69 void name(FullDecoder* decoder, ##__VA_ARGS__); 70 INTERFACE_CONSTANT_FUNCTIONS(DECLARE_INTERFACE_FUNCTION) 71#undef DECLARE_INTERFACE_FUNCTION 72 73 WasmValue result() { 74 DCHECK_NOT_NULL(isolate_); 75 return result_; 76 } 77 bool end_found() { return end_found_; } 78 bool runtime_error() { return error_ != nullptr; } 79 const char* runtime_error_msg() { return error_; } 80 81 private: 82 bool generate_result() { return isolate_ != nullptr && !runtime_error(); } 83 bool end_found_ = false; 84 const char* error_ = nullptr; 85 WasmValue result_; 86 const WasmModule* module_; 87 WasmModule* outer_module_; 88 Isolate* isolate_; 89 Handle<WasmInstanceObject> instance_; 90}; 91 92} // namespace wasm 93} // namespace internal 94} // namespace v8 95 96#endif // V8_WASM_INIT_EXPR_INTERFACE_H_ 97