Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

rust: add Proxy-WASM for Rust (MVP). #46

Merged
merged 2 commits into from
Mar 22, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,4 @@ TAGS
.vimrc
.vs
.vscode
**/Cargo.lock
8 changes: 4 additions & 4 deletions api/wasm/cpp/Makefile.base
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
API:=$(shell git rev-parse --show-toplevel)/api/wasm/cpp
CPP_API:=$(shell git rev-parse --show-toplevel)/api/wasm/cpp

ifdef NO_CONTEXT
CONTEXT_LIB =
else
CONTEXT_LIB = ${API}/proxy_wasm_intrinsics.cc
CONTEXT_LIB = ${CPP_API}/proxy_wasm_intrinsics.cc
endif

%.wasm %.wat: %.cc ${API}/proxy_wasm_intrinsics.h ${API}/proxy_wasm_intrinsics.js
em++ -s WASM=1 -s LEGALIZE_JS_FFI=0 -s EMIT_EMSCRIPTEN_METADATA=1 --std=c++17 -O3 -g3 -I${API} --js-library ${API}/proxy_wasm_intrinsics.js $*.cc ${CONTEXT_LIB} -o $*.js
%.wasm %.wat: %.cc ${CPP_API}/proxy_wasm_intrinsics.h ${CPP_API}/proxy_wasm_intrinsics.js
em++ -s WASM=1 -s LEGALIZE_JS_FFI=0 -s EMIT_EMSCRIPTEN_METADATA=1 --std=c++17 -O3 -g3 -I${CPP_API} --js-library ${CPP_API}/proxy_wasm_intrinsics.js $*.cc ${CONTEXT_LIB} -o $*.js
wavm-disas $*.wasm $*.wat
wavm-compile $*.wasm $*.wasm
rm -f $*.js $*.wast
Expand Down
14 changes: 14 additions & 0 deletions api/wasm/rust/Cargo.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
[package]
description = "Proxy-WASM for Rust"
name = "proxy_wasm"
version = "0.0.1"
authors = ["Piotr Sikora <piotrsikora@google.com>"]
edition = "2018"

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

update?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is Rust edition (think: C/C++ standard revisions), 2018 is the latest.


[dependencies]
log = "0.4"

[profile.release]
lto = true
opt-level = 3
panic = "abort"
9 changes: 9 additions & 0 deletions api/wasm/rust/Makefile.base
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
RUST_API:=$(shell git rev-parse --show-toplevel)/api/wasm/rust

%.wasm %.wat: %/src/lib.rs %/Cargo.toml ${RUST_API}/src/lib.rs ${RUST_API}/Cargo.toml
cd $* && cargo build --target=wasm32-unknown-unknown --release
mv $*/target/wasm32-unknown-unknown/release/$*.wasm .
rm -rf $*/target
wasm-gc $*.wasm
wavm-disas $*.wasm $*.wat
chmod 644 $*.wat
71 changes: 71 additions & 0 deletions api/wasm/rust/src/lib.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
/// Logger that integrates with host's logging system.
pub struct Logger;

static LOGGER: Logger = Logger;

impl Logger {
pub fn init() -> Result<(), log::SetLoggerError> {
log::set_logger(&LOGGER).map(|()| log::set_max_level(log::LevelFilter::Trace))
}

fn proxywasm_loglevel(level: log::Level) -> u32 {
match level {
log::Level::Trace => 0,
log::Level::Debug => 1,
log::Level::Info => 2,
log::Level::Warn => 3,
log::Level::Error => 4,
}
}
}

impl log::Log for Logger {
fn enabled(&self, _metadata: &log::Metadata) -> bool {
true
}

fn log(&self, record: &log::Record) {
let level = Logger::proxywasm_loglevel(record.level());
let message = record.args().to_string();
unsafe {
host::proxy_log(level, message.as_ptr(), message.len());
}
}

fn flush(&self) {}
}

/// Always hook into host's logging system.
#[no_mangle]
fn __post_instantiate() {
Logger::init().unwrap();
}

/// Allow host to allocate memory.
#[no_mangle]
fn _malloc(size: usize) -> *mut u8 {
let mut vec: Vec<u8> = Vec::with_capacity(size);
unsafe {
vec.set_len(size);
}
let slice = vec.into_boxed_slice();
Box::into_raw(slice) as *mut u8
}

/// Allow host to free memory.
#[no_mangle]
fn _free(ptr: *mut u8) {
if !ptr.is_null() {
unsafe {
Box::from_raw(ptr);
}
}
}

/// Low-level Proxy-WASM APIs for the host functions.
pub mod host {
extern "C" {
#[link_name = "_proxy_log"]
pub fn proxy_log(level: u32, message_data: *const u8, message_size: usize);
}
}
3 changes: 2 additions & 1 deletion test/extensions/wasm/test_data/Makefile
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
NO_CONTEXT = true

all: logging_cpp.wasm bad_signature_cpp.wasm segv_cpp.wasm emscripten_cpp.wasm asm2wasm_cpp.wasm
all: logging_cpp.wasm logging_rust.wasm bad_signature_cpp.wasm segv_cpp.wasm emscripten_cpp.wasm asm2wasm_cpp.wasm

include ../../../../api/wasm/cpp/Makefile.base
include ../../../../api/wasm/rust/Makefile.base
5 changes: 3 additions & 2 deletions test/extensions/wasm/test_data/logging_cpp.cc
Original file line number Diff line number Diff line change
Expand Up @@ -8,10 +8,11 @@ extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onConfigure(char* configuration, int
}

extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onStart() {
logTrace(std::string("test trace") + " logging");
logDebug(std::string("test debug") + " logging");
logInfo(std::string("test info") + " logging");
logError(std::string("test error") + " logging");
}

extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onTick() {
logError(std::string("test tick") + " logging");
logInfo(std::string("test tick") + " logging");
}
Binary file modified test/extensions/wasm/test_data/logging_cpp.wasm
Binary file not shown.
Loading