diff --git a/oak/server/grpc_client_node.cc b/oak/server/grpc_client_node.cc index cf1bc5a2947..e183660c5ac 100644 --- a/oak/server/grpc_client_node.cc +++ b/oak/server/grpc_client_node.cc @@ -31,9 +31,9 @@ namespace { void* tag(int i) { return (void*)static_cast(i); } } // namespace -GrpcClientNode::GrpcClientNode(BaseRuntime* runtime, const std::string& name, +GrpcClientNode::GrpcClientNode(BaseRuntime* runtime, const std::string& name, NodeId node_id, const std::string& grpc_address) - : NodeThread(runtime, name), + : NodeThread(runtime, name, node_id), channel_(grpc::CreateChannel(grpc_address, grpc::InsecureChannelCredentials())), stub_(new grpc::GenericStub(channel_)) { OAK_LOG(INFO) << "Created gRPC client node for " << grpc_address; @@ -79,6 +79,8 @@ bool GrpcClientNode::HandleInvocation(Handle invocation_handle) { cq.Next(&got_tag, &ok); if (!ok) { OAK_LOG(ERROR) << "Failed to start gRPC method call"; + FailInvocation(invocation->rsp_handle.get(), + grpc::Status(grpc::StatusCode::INTERNAL, "failed to start method call")); return false; } @@ -89,11 +91,15 @@ bool GrpcClientNode::HandleInvocation(Handle invocation_handle) { cq.Next(&got_tag, &ok); if (!ok) { OAK_LOG(ERROR) << "Failed to send gRPC request"; + FailInvocation(invocation->rsp_handle.get(), + grpc::Status(grpc::StatusCode::INTERNAL, "failed to write request")); return false; } call->WritesDone(tag(3)); cq.Next(&got_tag, &ok); if (!ok) { + FailInvocation(invocation->rsp_handle.get(), + grpc::Status(grpc::StatusCode::INTERNAL, "failed to close request")); OAK_LOG(ERROR) << "Failed to close gRPC request"; return false; } @@ -138,6 +144,8 @@ bool GrpcClientNode::HandleInvocation(Handle invocation_handle) { } if (!status.ok()) { // Final status includes an error, so pass it back on the response channel. + FailInvocation(invocation->rsp_handle.get(), status); + oak::encap::GrpcResponse grpc_rsp; grpc_rsp.set_last(true); grpc_rsp.mutable_status()->set_code(status.error_code()); @@ -158,6 +166,22 @@ bool GrpcClientNode::HandleInvocation(Handle invocation_handle) { return true; } +void GrpcClientNode::FailInvocation(Handle rsp_handle, grpc::Status status) { + oak::encap::GrpcResponse grpc_rsp; + grpc_rsp.set_last(true); + grpc_rsp.mutable_status()->set_code(status.error_code()); + grpc_rsp.mutable_status()->set_message(status.error_message()); + + auto rsp_msg = absl::make_unique(); + size_t serialized_size = grpc_rsp.ByteSizeLong(); + rsp_msg->data.resize(serialized_size); + grpc_rsp.SerializeToArray(rsp_msg->data.data(), rsp_msg->data.size()); + + OAK_LOG(INFO) << "Write final gRPC status of (" << status.error_code() << ", '" + << status.error_message() << "') to response channel"; + ChannelWrite(rsp_handle, std::move(rsp_msg)); +} + void GrpcClientNode::Run(Handle invocation_handle) { std::vector> channel_status; channel_status.push_back(absl::make_unique(invocation_handle)); diff --git a/oak/server/grpc_client_node.h b/oak/server/grpc_client_node.h index e6d3ed52b71..2ee07d02f2f 100644 --- a/oak/server/grpc_client_node.h +++ b/oak/server/grpc_client_node.h @@ -30,10 +30,12 @@ namespace oak { class GrpcClientNode final : public NodeThread { public: - GrpcClientNode(BaseRuntime* runtime, const std::string& name, const std::string& grpc_address); + GrpcClientNode(BaseRuntime* runtime, const std::string& name, NodeId node_id, + const std::string& grpc_address); private: bool HandleInvocation(Handle invocation_handle); + void FailInvocation(Handle rsp_handle, grpc::Status status); void Run(Handle handle) override; std::shared_ptr channel_; diff --git a/oak/server/loader/oak_runner_main.cc b/oak/server/loader/oak_runner_main.cc index 5b0fafd4558..cc26f9343ea 100644 --- a/oak/server/loader/oak_runner_main.cc +++ b/oak/server/loader/oak_runner_main.cc @@ -14,6 +14,7 @@ * limitations under the License. */ +#include #include #include @@ -30,6 +31,12 @@ ABSL_FLAG(std::string, ca_cert, "", "Path to the PEM-encoded CA root certificate ABSL_FLAG(std::string, private_key, "", "Path to the private key"); ABSL_FLAG(std::string, cert_chain, "", "Path to the PEM-encoded certificate chain"); +namespace { + +absl::Notification server_done; + +void sigint_handler(int) { server_done.Notify(); } + std::shared_ptr BuildTlsCredentials(std::string pem_root_certs, std::string private_key, std::string cert_chain) { @@ -40,10 +47,12 @@ std::shared_ptr BuildTlsCredentials(std::string pem_roo return grpc::SslServerCredentials(options); } +} // namespace + int main(int argc, char* argv[]) { absl::ParseCommandLine(argc, argv); - // Create loader instance. + // Create the loader instance. std::unique_ptr loader = absl::make_unique(); // Load application configuration. @@ -71,14 +80,16 @@ int main(int argc, char* argv[]) { OAK_LOG(ERROR) << "Failed to create application"; return 1; } + std::stringstream address; address << "0.0.0.0:" << application_config->grpc_port(); OAK_LOG(INFO) << "Oak Application: " << address.str(); - // Wait (same as `sleep(86400)`). - absl::Notification server_timeout; - server_timeout.WaitForNotificationWithTimeout(absl::Hours(24)); + // Wait until notification of signal termination. + std::signal(SIGINT, sigint_handler); + server_done.WaitForNotification(); + OAK_LOG(ERROR) << "Terminate Oak Application"; loader->TerminateApplication(); return 0; diff --git a/oak/server/logging_node.h b/oak/server/logging_node.h index 094ec9120a6..6f7cf70a3ee 100644 --- a/oak/server/logging_node.h +++ b/oak/server/logging_node.h @@ -29,7 +29,8 @@ namespace oak { // Pseudo-node to perform logging. class LoggingNode final : public NodeThread { public: - explicit LoggingNode(BaseRuntime* runtime, const std::string& name) : NodeThread(runtime, name) {} + explicit LoggingNode(BaseRuntime* runtime, const std::string& name, NodeId node_id) + : NodeThread(runtime, name, node_id) {} private: void Run(Handle handle) override; diff --git a/oak/server/node_thread.h b/oak/server/node_thread.h index 496003986f7..601a60179dd 100644 --- a/oak/server/node_thread.h +++ b/oak/server/node_thread.h @@ -29,7 +29,8 @@ namespace oak { class NodeThread : public OakNode { public: // Construct a thread, identified by the given name in diagnostic messages. - NodeThread(BaseRuntime* runtime, const std::string& name) : OakNode(runtime, name) {} + NodeThread(BaseRuntime* runtime, const std::string& name, NodeId node_id) + : OakNode(runtime, name, node_id) {} virtual ~NodeThread(); // Start kicks off a separate thread that invokes the Run() method. diff --git a/oak/server/oak_grpc_node.cc b/oak/server/oak_grpc_node.cc index cc875c22be3..22a74cdb4ee 100644 --- a/oak/server/oak_grpc_node.cc +++ b/oak/server/oak_grpc_node.cc @@ -25,9 +25,9 @@ namespace oak { std::unique_ptr OakGrpcNode::Create( - BaseRuntime* runtime, const std::string& name, + BaseRuntime* runtime, const std::string& name, NodeId node_id, std::shared_ptr grpc_credentials, const uint16_t port) { - std::unique_ptr node = absl::WrapUnique(new OakGrpcNode(runtime, name)); + std::unique_ptr node = absl::WrapUnique(new OakGrpcNode(runtime, name, node_id)); // Build Server grpc::ServerBuilder builder; diff --git a/oak/server/oak_grpc_node.h b/oak/server/oak_grpc_node.h index 1e2afab22ce..e3c4a26127f 100644 --- a/oak/server/oak_grpc_node.h +++ b/oak/server/oak_grpc_node.h @@ -31,7 +31,7 @@ class OakGrpcNode final : public OakNode { // Create an Oak node with the `name` and gRPC `port`. // If `port` equals 0, then gRPC port is assigned automatically. static std::unique_ptr Create( - BaseRuntime* runtime, const std::string& name, + BaseRuntime* runtime, const std::string& name, NodeId node_id, std::shared_ptr grpc_credentials, const uint16_t port = 0); virtual ~OakGrpcNode(){}; @@ -48,8 +48,8 @@ class OakGrpcNode final : public OakNode { private: friend class ModuleInvocation; - OakGrpcNode(BaseRuntime* runtime, const std::string& name) - : OakNode(runtime, name), next_stream_id_(1), handle_(kInvalidHandle) {} + OakGrpcNode(BaseRuntime* runtime, const std::string& name, NodeId node_id) + : OakNode(runtime, name, node_id), next_stream_id_(1), handle_(kInvalidHandle) {} OakGrpcNode(const OakGrpcNode&) = delete; OakGrpcNode& operator=(const OakGrpcNode&) = delete; diff --git a/oak/server/oak_node.h b/oak/server/oak_node.h index 1073c76a3d0..2a050255959 100644 --- a/oak/server/oak_node.h +++ b/oak/server/oak_node.h @@ -17,6 +17,8 @@ #ifndef OAK_SERVER_NODE_H_ #define OAK_SERVER_NODE_H_ +#include + #include #include #include @@ -57,10 +59,12 @@ struct NodeReadResult { std::unique_ptr msg; }; +using NodeId = uint64_t; + class OakNode { public: - OakNode(BaseRuntime* runtime, const std::string& name) - : name_(name), runtime_(runtime), prng_engine_() {} + OakNode(BaseRuntime* runtime, const std::string& name, NodeId node_id) + : name_(name), node_id_(node_id), runtime_(runtime), prng_engine_() {} virtual ~OakNode() {} virtual void Start(Handle handle) = 0; @@ -98,6 +102,7 @@ class OakNode { void ClearHandles() LOCKS_EXCLUDED(mu_); const std::string name_; + const NodeId node_id_; private: // Allow the Runtime to use internal methods. diff --git a/oak/server/oak_runtime.cc b/oak/server/oak_runtime.cc index b0aaaf09a27..862560c0116 100644 --- a/oak/server/oak_runtime.cc +++ b/oak/server/oak_runtime.cc @@ -69,18 +69,20 @@ grpc::Status OakRuntime::Initialize(const ApplicationConfiguration& config, } // Create a gRPC pseudo-Node. + NodeId grpc_node_id = NextNodeId(); const std::string grpc_name = kGrpcNodeName; const uint16_t grpc_port = config.grpc_port(); OAK_LOG(INFO) << "Create gRPC pseudo-Node named {" << grpc_name << "}"; std::unique_ptr grpc_node = - OakGrpcNode::Create(this, grpc_name, grpc_credentials, grpc_port); + OakGrpcNode::Create(this, grpc_name, grpc_node_id, grpc_credentials, grpc_port); grpc_node_ = grpc_node.get(); // borrowed copy nodes_[grpc_name] = std::move(grpc_node); // Create the initial Application Node. + NodeId app_node_id = NextNodeId(); std::string node_name; - app_node_ = - CreateNode(config.initial_node_config_name(), config.initial_entrypoint_name(), &node_name); + app_node_ = CreateNode(config.initial_node_config_name(), config.initial_entrypoint_name(), + app_node_id, &node_name); if (app_node_ == nullptr) { return grpc::Status(grpc::StatusCode::INVALID_ARGUMENT, "Failed to create initial Oak Node"); } @@ -105,28 +107,30 @@ std::string OakRuntime::NextNodeName(const std::string& config_name, return absl::StrCat(config_name, "-", index, "-", entrypoint_name); } +NodeId OakRuntime::NextNodeId() { return next_node_id_++; } + // Create (but don't start) a new Node instance. Return a borrowed pointer to // the new Node (or nullptr on failure). OakNode* OakRuntime::CreateNode(const std::string& config_name, const std::string& entrypoint_name, - std::string* node_name) { + NodeId node_id, std::string* node_name) { std::string name = NextNodeName(config_name, entrypoint_name); std::unique_ptr node; if (wasm_config_.count(config_name) > 0) { OAK_LOG(INFO) << "Create Wasm node named {" << name << "}"; const WebAssemblyConfiguration* wasm_cfg = wasm_config_[config_name].get(); - node = WasmNode::Create(this, name, wasm_cfg->module_bytes(), entrypoint_name); + node = WasmNode::Create(this, name, node_id, wasm_cfg->module_bytes(), entrypoint_name); } else if (log_config_.count(config_name) > 0) { OAK_LOG(INFO) << "Create log node named {" << name << "}"; - node = absl::make_unique(this, name); + node = absl::make_unique(this, name, node_id); } else if (storage_config_.count(config_name) > 0) { std::string address = *(storage_config_[config_name].get()); OAK_LOG(INFO) << "Create storage proxy node named {" << name << "} connecting to " << address; - node = absl::make_unique(this, name, address); + node = absl::make_unique(this, name, node_id, address); } else if (grpc_client_config_.count(config_name) > 0) { std::string address = *(grpc_client_config_[config_name].get()); OAK_LOG(INFO) << "Create gRPC client node named {" << name << "} connecting to " << address; - node = absl::make_unique(this, name, address); + node = absl::make_unique(this, name, node_id, address); } else { OAK_LOG(ERROR) << "failed to find config with name " << config_name; return nullptr; @@ -151,7 +155,8 @@ bool OakRuntime::CreateAndRunNode(const std::string& config_name, } absl::MutexLock lock(&mu_); - OakNode* node = CreateNode(config_name, entrypoint_name, node_name); + NodeId node_id = NextNodeId(); + OakNode* node = CreateNode(config_name, entrypoint_name, node_id, node_name); if (node == nullptr) { return false; } diff --git a/oak/server/oak_runtime.h b/oak/server/oak_runtime.h index e35de71f3d2..283cc86c6df 100644 --- a/oak/server/oak_runtime.h +++ b/oak/server/oak_runtime.h @@ -44,6 +44,7 @@ class OakRuntime : public BaseRuntime { grpc_handle_(kInvalidHandle), app_node_(nullptr), app_handle_(kInvalidHandle), + next_node_id_(0), termination_pending_(false) {} virtual ~OakRuntime() = default; @@ -67,9 +68,10 @@ class OakRuntime : public BaseRuntime { std::string NextNodeName(const std::string& config_name, const std::string& entrypoint_name) EXCLUSIVE_LOCKS_REQUIRED(mu_); + NodeId NextNodeId() EXCLUSIVE_LOCKS_REQUIRED(mu_); OakNode* CreateNode(const std::string& config_name, const std::string& entrypoint_name, - std::string* node_name) EXCLUSIVE_LOCKS_REQUIRED(mu_); + NodeId node_id, std::string* node_name) EXCLUSIVE_LOCKS_REQUIRED(mu_); // Information derived from ApplicationConfiguration; const after Initialize() called: @@ -93,16 +95,17 @@ class OakRuntime : public BaseRuntime { // to the initial Application Wasm Node. Handle app_handle_; - // Next index for node name generation. - mutable absl::Mutex mu_; // protects nodes_, next_index_; + // Next indexes for node name/ID generation. + mutable absl::Mutex mu_; // protects nodes_, next_index_, next_node_id_; std::map next_index_ GUARDED_BY(mu_); - - std::atomic_bool termination_pending_; + NodeId next_node_id_ GUARDED_BY(mu_); // Collection of running Nodes indexed by Node name. Note that Node name is // unique but is not visible to the running Application in any way. std::map> nodes_ GUARDED_BY(mu_); + std::atomic_bool termination_pending_; + }; // class OakRuntime } // namespace oak diff --git a/oak/server/rust/oak_runtime/Cargo.toml b/oak/server/rust/oak_runtime/Cargo.toml index c283c4e4c78..8e2cd7a870b 100644 --- a/oak/server/rust/oak_runtime/Cargo.toml +++ b/oak/server/rust/oak_runtime/Cargo.toml @@ -21,7 +21,7 @@ log = { version = "*" } oak_abi = "=0.1.0" prost = "*" prost-types = "*" -rand = { version = "*", default-features = false, features = ["alloc"] } +rand = "*" tokio = { version = "*", features = ["rt-core"] } wasmi = { version = "*", default-features = false, features = ["core"] } diff --git a/oak/server/rust/oak_runtime/src/node/wasm/mod.rs b/oak/server/rust/oak_runtime/src/node/wasm/mod.rs index 0e6120fac3a..a4cffd27b54 100644 --- a/oak/server/rust/oak_runtime/src/node/wasm/mod.rs +++ b/oak/server/rust/oak_runtime/src/node/wasm/mod.rs @@ -53,6 +53,8 @@ const CHANNEL_CREATE: usize = 3; const CHANNEL_WRITE: usize = 4; const CHANNEL_READ: usize = 5; const WAIT_ON_CHANNELS: usize = 6; +// TODO(#817): remove this +const WASI_STUB: usize = 7; type AbiHandle = u64; type AbiPointer = u32; @@ -663,6 +665,8 @@ impl wasmi::Externals for WasmInterface { map_host_errors(self.wait_on_channels(status_buff, handles_count)) } + WASI_STUB => panic!("Attempt to invoke unimplemented WASI function"), + _ => panic!("Unimplemented function at {}", index), } } @@ -748,6 +752,58 @@ impl wasmi::ModuleImportResolver for WasmInterface { } } +// Stub implementation of WASI exported functions, to allow partially-ported +// applications to be run. +// TODO(#817): remove WASI stubs +struct WasiStub; + +impl wasmi::ModuleImportResolver for WasiStub { + fn resolve_func( + &self, + field_name: &str, + signature: &wasmi::Signature, + ) -> Result { + let (index, sig) = match field_name { + "proc_exit" => (WASI_STUB, wasmi::Signature::new(&[ABI_U32][..], None)), + "fd_write" => ( + WASI_STUB, + wasmi::Signature::new(&[ABI_U32, ABI_U32, ABI_U32, ABI_U32][..], Some(ABI_U32)), + ), + "fd_seek" => ( + WASI_STUB, + wasmi::Signature::new(&[ABI_U32, ABI_U64, ABI_U32, ABI_U32][..], Some(ABI_U32)), + ), + "fd_close" => ( + WASI_STUB, + wasmi::Signature::new(&[ABI_U32][..], Some(ABI_U32)), + ), + "environ_sizes_get" => ( + WASI_STUB, + wasmi::Signature::new(&[ABI_U32, ABI_U32][..], Some(ABI_U32)), + ), + "environ_get" => ( + WASI_STUB, + wasmi::Signature::new(&[ABI_U32, ABI_U32][..], Some(ABI_U32)), + ), + _ => { + return Err(wasmi::Error::Instantiation(format!( + "Export {} not found", + field_name + ))) + } + }; + + if &sig != signature { + return Err(wasmi::Error::Instantiation(format!( + "Export `{}` doesnt match expected type {:?}", + field_name, signature + ))); + } + + Ok(wasmi::FuncInstance::alloc_host(sig, index)) + } +} + pub struct WasmNode { config_name: String, runtime: RuntimeProxy, @@ -799,9 +855,12 @@ impl super::Node for WasmNode { { let (abi, _) = WasmInterface::new(self.config_name.clone(), self.runtime.clone(), self.reader); + let wasi_stub = WasiStub; let instance = wasmi::ModuleInstance::new( &self.module, - &wasmi::ImportsBuilder::new().with_resolver("oak", &abi), + &wasmi::ImportsBuilder::new() + .with_resolver("oak", &abi) + .with_resolver("wasi_snapshot_preview1", &wasi_stub), ) .expect("failed to instantiate wasm module") .assert_no_start(); @@ -831,12 +890,15 @@ impl super::Node for WasmNode { .name(self.to_string()) .spawn(move || { let pretty_name = pretty_name_for_thread(&thread::current()); + let wasi_stub = WasiStub; let (mut abi, initial_handle) = WasmInterface::new(pretty_name, runtime.clone(), reader); let instance = wasmi::ModuleInstance::new( &module, - &wasmi::ImportsBuilder::new().with_resolver("oak", &abi), + &wasmi::ImportsBuilder::new() + .with_resolver("oak", &abi) + .with_resolver("wasi_snapshot_preview1", &wasi_stub), ) .expect("failed to instantiate wasm module") .assert_no_start(); diff --git a/oak/server/storage/storage_node.cc b/oak/server/storage/storage_node.cc index 2ca73d19ae1..0889be1b3b4 100644 --- a/oak/server/storage/storage_node.cc +++ b/oak/server/storage/storage_node.cc @@ -29,9 +29,9 @@ using ::oak_abi::OakStatus; namespace oak { -StorageNode::StorageNode(BaseRuntime* runtime, const std::string& name, +StorageNode::StorageNode(BaseRuntime* runtime, const std::string& name, NodeId node_id, const std::string& storage_address) - : NodeThread(runtime, name), storage_processor_(storage_address) {} + : NodeThread(runtime, name, node_id), storage_processor_(storage_address) {} void StorageNode::Run(Handle invocation_handle) { std::vector> channel_status; diff --git a/oak/server/storage/storage_node.h b/oak/server/storage/storage_node.h index fd659a636c9..b8c5e902588 100644 --- a/oak/server/storage/storage_node.h +++ b/oak/server/storage/storage_node.h @@ -30,7 +30,8 @@ namespace oak { class StorageNode final : public NodeThread { public: - StorageNode(BaseRuntime* runtime, const std::string& name, const std::string& storage_address); + StorageNode(BaseRuntime* runtime, const std::string& name, NodeId node_id, + const std::string& storage_address); private: void Run(Handle handle) override; diff --git a/oak/server/wasm_node.cc b/oak/server/wasm_node.cc index 1ac420243ec..1169384f26d 100644 --- a/oak/server/wasm_node.cc +++ b/oak/server/wasm_node.cc @@ -64,11 +64,11 @@ static void WriteMemory(wabt::interp::Environment* env, const uint32_t offset, } static void WriteI32(wabt::interp::Environment* env, const uint32_t offset, const int32_t value) { - return absl::little_endian::Store32(env->GetMemory(0)->data.data() + offset, value); + absl::little_endian::Store32(env->GetMemory(0)->data.data() + offset, value); } static void WriteU64(wabt::interp::Environment* env, const uint32_t offset, const uint64_t v) { - return absl::little_endian::Store64(env->GetMemory(0)->data.data() + offset, v); + absl::little_endian::Store64(env->GetMemory(0)->data.data() + offset, v); } static uint64_t ReadU64(wabt::interp::Environment* env, const uint32_t offset) { @@ -152,16 +152,17 @@ static bool CheckModuleExport(wabt::interp::Environment* env, wabt::interp::Modu return true; } -WasmNode::WasmNode(BaseRuntime* runtime, const std::string& name, +WasmNode::WasmNode(BaseRuntime* runtime, const std::string& name, NodeId node_id, const std::string& main_entrypoint) - : NodeThread(runtime, name), main_entrypoint_(main_entrypoint), prng_engine_() {} + : NodeThread(runtime, name, node_id), main_entrypoint_(main_entrypoint), prng_engine_() {} std::unique_ptr WasmNode::Create(BaseRuntime* runtime, const std::string& name, - const std::string& module, + NodeId node_id, const std::string& module, const std::string& main_entrypoint) { OAK_LOG(INFO) << "Creating Wasm Node"; - std::unique_ptr node = absl::WrapUnique(new WasmNode(runtime, name, main_entrypoint)); + std::unique_ptr node = + absl::WrapUnique(new WasmNode(runtime, name, node_id, main_entrypoint)); node->InitEnvironment(&node->env_); OAK_LOG(INFO) << "Host func count: " << node->env_.GetFuncCount(); diff --git a/oak/server/wasm_node.h b/oak/server/wasm_node.h index 9d55c5232ea..50ffafe6c96 100644 --- a/oak/server/wasm_node.h +++ b/oak/server/wasm_node.h @@ -29,12 +29,13 @@ class WasmNode final : public NodeThread { public: // Creates a Wasm Node by loading the Wasm module code. static std::unique_ptr Create(BaseRuntime* runtime, const std::string& name, - const std::string& module, + NodeId node_id, const std::string& module, const std::string& main_entrypoint); private: // Clients should construct WasmNode instances with Create() (which can fail). - WasmNode(BaseRuntime* runtime, const std::string& name, const std::string& main_entrypoint); + WasmNode(BaseRuntime* runtime, const std::string& name, NodeId node_id, + const std::string& main_entrypoint); void InitEnvironment(wabt::interp::Environment* env); diff --git a/oak/server/wasm_node_test.cc b/oak/server/wasm_node_test.cc index 32f8fe6c77c..9500f92da76 100644 --- a/oak/server/wasm_node_test.cc +++ b/oak/server/wasm_node_test.cc @@ -37,39 +37,40 @@ std::string DataFrom(const std::string& filename) { TEST(WasmNode, MalformedFailure) { // No magic. - ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", "", "oak_main")); + ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", 0, "", "oak_main")); // Wrong magic. ASSERT_EQ(nullptr, - WasmNode::Create(nullptr, "test", std::string("\x00\x61\x73\x6b\x01\x00\x00\x00", 8), + WasmNode::Create(nullptr, "test", 0, std::string("\x00\x61\x73\x6b\x01\x00\x00\x00", 8), "oak_main")); // Wrong version. ASSERT_EQ(nullptr, - WasmNode::Create(nullptr, "test", std::string("\x00\x61\x73\x6d\x09\x00\x00\x00", 8), + WasmNode::Create(nullptr, "test", 0, std::string("\x00\x61\x73\x6d\x09\x00\x00\x00", 8), "oak_main")); // Right magic+version, no contents. - ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", DataFrom("oak/server/testdata/empty.wasm"), - "oak_main")); + ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", 0, + DataFrom("oak/server/testdata/empty.wasm"), "oak_main")); } TEST(WasmNode, MinimalSuccess) { - std::unique_ptr node = - WasmNode::Create(nullptr, "test", DataFrom("oak/server/testdata/minimal.wasm"), "oak_main"); + std::unique_ptr node = WasmNode::Create( + nullptr, "test", 0, DataFrom("oak/server/testdata/minimal.wasm"), "oak_main"); EXPECT_NE(nullptr, node); } TEST(WasmNode, MissingExport) { - ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", DataFrom("oak/server/testdata/missing.wasm"), - "oak_main")); + ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", 0, + DataFrom("oak/server/testdata/missing.wasm"), "oak_main")); } TEST(WasmNode, WrongExport) { - ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", DataFrom("oak/server/testdata/minimal.wasm"), - "oak_other_main")); + ASSERT_EQ(nullptr, + WasmNode::Create(nullptr, "test", 0, DataFrom("oak/server/testdata/minimal.wasm"), + "oak_other_main")); } TEST(WasmNode, WrongSignature) { - ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", DataFrom("oak/server/testdata/wrong.wasm"), - "oak_main")); + ASSERT_EQ(nullptr, WasmNode::Create(nullptr, "test", 0, + DataFrom("oak/server/testdata/wrong.wasm"), "oak_main")); } } // namespace oak