Skip to content

Commit

Permalink
Use Rust Loader for running examples (#993)
Browse files Browse the repository at this point in the history
This change:
- Updates examples to use Rust Loader
- Updates macro and scripts for running Rust Loader
- Makes Oak CI to use Rust Loader for running examples
- Builds Rust Oak Loader with Cargo
- Fixes minor issues with gRPC server/client pseudo-Nodes

Fixes #725
Fixes #874
Fixes #901
Ref #945
  • Loading branch information
ipetr0v authored May 21, 2020
1 parent ce3a154 commit 68fbbe3
Show file tree
Hide file tree
Showing 55 changed files with 844 additions and 431 deletions.
3 changes: 2 additions & 1 deletion Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

10 changes: 5 additions & 5 deletions cloudbuild.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -52,21 +52,21 @@ steps:
waitFor: ['build_server_no_debug']
timeout: 60m
entrypoint: 'bash'
args: ['./scripts/build_server', '-s', 'base']
args: ['./scripts/build_server', '-s', 'rust']
- name: 'gcr.io/oak-ci/oak:latest'
id: build_server_rust
id: build_server_base
waitFor: ['bazel_init']
timeout: 60m
entrypoint: 'bash'
args: ['./scripts/build_server', '-s', 'rust']
args: ['./scripts/build_server', '-s', 'base']

# Package the Hello World application in a Docker image.
- name: 'gcr.io/oak-ci/oak:latest'
id: build_server_docker
waitFor: ['build_server']
timeout: 60m
entrypoint: 'bash'
args: ['./scripts/build_example', '-e', 'hello_world', '-i', 'base']
args: ['./scripts/build_example', '-e', 'hello_world', '-i', 'rust']

- name: 'gcr.io/oak-ci/oak:latest'
id: run_tests
Expand All @@ -87,7 +87,7 @@ steps:
id: run_examples
timeout: 60m
entrypoint: 'bash'
args: ['./scripts/run_examples', '-s', 'base']
args: ['./scripts/run_examples', '-s', 'rust']
# TODO(#942): Reenable `run_examples` with `asan` and `tsan`.
# - name: 'gcr.io/oak-ci/oak:latest'
# id: run_examples_asan
Expand Down
40 changes: 32 additions & 8 deletions docs/programming-oak.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,19 +43,25 @@ the internal state of the Node itself (which may be empty), implement the
[`oak::Node`](https://project-oak.github.io/oak/doc/oak/trait.Node.html) trait
for it, then define an
[`entrypoint`](https://project-oak.github.io/oak/doc/oak/macro.entrypoint.html)
so the Oak SDK knows how to instantiate it:
so the Oak SDK knows how to instantiate it.

The defined entrypoint should run an `oak::run_event_loop` function that is
specified with a channel handle (used for reading messages) and an Oak Node that
receives these messages. Fox example, such a handle could be provided by the
gRPC server pseudo-Node:

<!-- prettier-ignore-start -->
[embedmd]:# (../examples/machine_learning/module/rust/src/lib.rs Rust /^oak::entrypoint.*/ /}\);$/)
```Rust
oak::entrypoint!(oak_main => {
oak::entrypoint!(oak_main => |in_channel| {
oak::logger::init_default();
Node {
let node = Node {
training_set_size: 1000,
test_set_size: 1000,
config: None,
model: NaiveBayes::new(),
}
};
oak::run_event_loop(node, in_channel);
});
```
<!-- prettier-ignore-end -->
Expand Down Expand Up @@ -93,9 +99,10 @@ with the automatically generated `Dispatcher`, as described in the next section.
<!-- prettier-ignore-start -->
[embedmd]:# (../examples/rustfmt/module/rust/src/lib.rs Rust /oak::entrypoint!/ /^}/)
```Rust
oak::entrypoint!(oak_main => {
oak::entrypoint!(oak_main => |in_channel| {
oak::logger::init_default();
FormatServiceDispatcher::new(Node)
let dispatcher = FormatServiceDispatcher::new(Node);
oak::run_event_loop(dispatcher, in_channel);
}
```
<!-- prettier-ignore-end -->
Expand Down Expand Up @@ -124,7 +131,10 @@ pub extern "C" fn frontend_oak_main(in_handle: u64) {
oak::set_panic_hook();
let node = FrontendNode::new();
let dispatcher = OakAbiTestServiceDispatcher::new(node);
oak::run_event_loop(dispatcher, in_handle);
let in_channel = ::oak::ReadHandle {
handle: ::oak::Handle::from_raw(in_handle),
};
oak::run_event_loop(dispatcher, in_channel);
});
}
```
Expand Down Expand Up @@ -217,13 +227,27 @@ node_configs {
module_bytes: "<bytes>"
}
}
node_configs {
name: "translator"
wasm_config {
module_bytes: "<bytes>"
}
}
node_configs {
name: "grpc-server"
grpc_server_config {
address: "[::]:8080"
grpc_tls_private_key: "<bytes>"
grpc_tls_certificate: "<bytes>"
}
}
node_configs {
name: "log"
log_config {}
}
grpc_port: 8080
initial_node_config_name: "app"
initial_entrypoint_name: "oak_main"
initial_entrypoint_name: "grpc_oak_main"
```
<!-- prettier-ignore-end -->

Expand Down
39 changes: 33 additions & 6 deletions examples/abitest/client/abitest.cc
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,10 @@
#include "oak/server/storage/memory_provider.h"
#include "oak/server/storage/storage_service.h"

ABSL_FLAG(std::string, address, "127.0.0.1:8080", "Address of the Oak application to connect to");
ABSL_FLAG(std::string, address, "localhost:8080", "Address of the Oak application to connect to");
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");
ABSL_FLAG(int, storage_port, 7867,
"Port on which the test Storage Server listens; set to zero to disable.");
ABSL_FLAG(int, grpc_test_port, 7878,
Expand Down Expand Up @@ -139,11 +141,11 @@ void run_storage_server(int storage_port, grpc::Server** storage_server) {
LOG(INFO) << "Storage server done";
}

void run_grpc_test_server(int grpc_test_port, grpc::Server** grpc_test_server) {
void run_grpc_test_server(int grpc_test_port, grpc::Server** grpc_test_server,
std::shared_ptr<grpc::ServerCredentials> credentials) {
LOG(INFO) << "Creating test gRPC service on :" << grpc_test_port;
grpc::ServerBuilder builder;
std::string server_address = absl::StrCat("[::]:", grpc_test_port);
std::shared_ptr<grpc::ServerCredentials> credentials = grpc::InsecureServerCredentials();
builder.AddListeningPort(server_address, credentials);

oak::test::GrpcTestServer grpc_test_service;
Expand All @@ -158,6 +160,16 @@ void run_grpc_test_server(int grpc_test_port, grpc::Server** grpc_test_server) {

} // namespace

std::shared_ptr<grpc::ServerCredentials> CreateGrpcCredentialsOrDie(const std::string& private_key,
const std::string& cert_chain,
const std::string& ca_cert) {
grpc::SslServerCredentialsOptions::PemKeyCertPair key_cert_pair = {private_key, cert_chain};
grpc::SslServerCredentialsOptions options;
options.pem_root_certs = ca_cert;
options.pem_key_cert_pairs.push_back(key_cert_pair);
return grpc::SslServerCredentials(options);
}

int main(int argc, char** argv) {
absl::ParseCommandLine(argc, argv);

Expand All @@ -169,20 +181,35 @@ int main(int argc, char** argv) {
absl::make_unique<std::thread>(run_storage_server, storage_port, &storage_server);
}

std::string ca_cert = oak::ApplicationClient::LoadRootCert(absl::GetFlag(FLAGS_ca_cert));

int grpc_test_port = absl::GetFlag(FLAGS_grpc_test_port);
std::unique_ptr<std::thread> grpc_test_thread;
grpc::Server* grpc_test_server;

if (grpc_test_port > 0) {
grpc_test_thread =
absl::make_unique<std::thread>(run_grpc_test_server, grpc_test_port, &grpc_test_server);
std::string private_key_path = absl::GetFlag(FLAGS_private_key);
std::string cert_chain_path = absl::GetFlag(FLAGS_cert_chain);
if (private_key_path.empty()) {
LOG(FATAL) << "No private key file specified";
}
if (cert_chain_path.empty()) {
LOG(FATAL) << "No certificate chain file specified";
}
std::string private_key = oak::utils::read_file(private_key_path);
std::string cert_chain = oak::utils::read_file(cert_chain_path);

std::shared_ptr<grpc::ServerCredentials> grpc_credentials =
CreateGrpcCredentialsOrDie(private_key, cert_chain, ca_cert);
grpc_test_thread = absl::make_unique<std::thread>(run_grpc_test_server, grpc_test_port,
&grpc_test_server, grpc_credentials);
}

const std::string& include = absl::GetFlag(FLAGS_test_include);
const std::string& exclude = absl::GetFlag(FLAGS_test_exclude);

// Connect to the Oak Application.
std::string address = absl::GetFlag(FLAGS_address);
std::string ca_cert = oak::ApplicationClient::LoadRootCert(absl::GetFlag(FLAGS_ca_cert));
LOG(INFO) << "Connecting to Oak Application: " << address;

auto stub =
Expand Down
14 changes: 12 additions & 2 deletions examples/abitest/config/config.textproto
Original file line number Diff line number Diff line change
Expand Up @@ -26,17 +26,27 @@ node_configs {
address: "test.invalid:9999"
}
}
node_configs {
name: "grpc-server"
grpc_server_config {
address: "[::]:8080"
grpc_tls_private_key: "<bytes>"
grpc_tls_certificate: "<bytes>"
}
}
node_configs {
name: "grpc-client"
grpc_client_config {
uri: "https://localhost:7878"
root_tls_certificate: "<bytes>"
address: "localhost:7878"
}
}
node_configs {
name: "absent-grpc-client"
grpc_client_config {
uri: "https://localhost:9999"
uri: "https://test.invalid:9999"
root_tls_certificate: "<bytes>"
address: "test.invalid:9999"
}
}
Expand All @@ -52,4 +62,4 @@ node_configs {
}
grpc_port: 8080
initial_node_config_name: "frontend-config"
initial_entrypoint_name: "frontend_oak_main"
initial_entrypoint_name: "grpc_frontend_oak_main"
Loading

0 comments on commit 68fbbe3

Please sign in to comment.