wiggle: emit a metadata module containing witx document (#1387)

* wiggle: emit a metadata module containing witx document

* wiggle: put metadata module behind a wiggle_metadata feature

* wasi-common: add wiggle_metadata feature and optional witx dep

* refactor according to alex's advice

* wasi-common: make snapshots pub

* wasi-common: i do need a wiggle_metadata feature to be available

* Tweak features and such

* wiggle: fix tests by passing metadata flag to wiggle-runtime

* wiggle: need to move wiggle-runtime to a non-dev dependency

so that the feature resolves for external users of the crates

Co-authored-by: Alex Crichton <alex@alexcrichton.com>
This commit is contained in:
Pat Hickey
2020-03-25 12:57:44 -07:00
committed by GitHub
parent 1f6890e070
commit bc1a11435e
11 changed files with 67 additions and 4 deletions

1
Cargo.lock generated
View File

@@ -2705,6 +2705,7 @@ name = "wiggle-runtime"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"thiserror", "thiserror",
"witx",
] ]
[[package]] [[package]]

View File

@@ -21,7 +21,7 @@ filetime = "0.2.7"
lazy_static = "1.4.0" lazy_static = "1.4.0"
num = { version = "0.2.0", default-features = false } num = { version = "0.2.0", default-features = false }
wig = { path = "wig", version = "0.12.0" } wig = { path = "wig", version = "0.12.0" }
wiggle = { path = "../wiggle" } wiggle = { path = "../wiggle", default-features = false }
wiggle-runtime = { path = "../wiggle/crates/runtime" } wiggle-runtime = { path = "../wiggle/crates/runtime" }
[target.'cfg(unix)'.dependencies] [target.'cfg(unix)'.dependencies]
@@ -34,3 +34,8 @@ cpu-time = "1.0"
[badges] [badges]
maintenance = { status = "actively-developed" } maintenance = { status = "actively-developed" }
[features]
# Need to make the wiggle_metadata feature available to consumers of this
# crate if they want the snapshots to have metadata available.
wiggle_metadata = ["wiggle/wiggle_metadata", "wiggle-runtime/wiggle_metadata"]

View File

@@ -31,7 +31,7 @@ pub mod old;
mod path; mod path;
mod poll; mod poll;
mod sandboxed_tty_writer; mod sandboxed_tty_writer;
mod snapshots; pub mod snapshots;
mod sys; mod sys;
mod virtfs; mod virtfs;
pub mod wasi; pub mod wasi;

View File

@@ -1 +1 @@
mod wasi_snapshot_preview1; pub mod wasi_snapshot_preview1;

View File

@@ -16,10 +16,22 @@ proc-macro = true
[dependencies] [dependencies]
wiggle-generate = { path = "crates/generate", version = "0.1.0" } wiggle-generate = { path = "crates/generate", version = "0.1.0" }
wiggle-runtime = { path = "crates/runtime", version = "0.1.0" }
witx = { path = "../wasi-common/wig/WASI/tools/witx", version = "0.8.4" } witx = { path = "../wasi-common/wig/WASI/tools/witx", version = "0.8.4" }
syn = { version = "1.0", features = ["full"] } syn = { version = "1.0", features = ["full"] }
[dev-dependencies] [dev-dependencies]
wiggle-runtime = { path = "crates/runtime", version = "0.1.0" }
wiggle-test = { path = "crates/test", version = "0.1.0" } wiggle-test = { path = "crates/test", version = "0.1.0" }
proptest = "0.9" proptest = "0.9"
[features]
# These features have no effect on the users of this crate. They are only
# necessary for testing.
# The wiggle proc-macro emits some code (inside `pub mod metadata`) guarded
# by the `wiggle_metadata` feature flag. We use this feature flag so that
# users of wiggle are not forced to take a direct dependency on the `witx`
# crate unless they want it.
wiggle_metadata = ["wiggle-runtime/wiggle_metadata"]
# In order to test that the contents of this metadata module meet
# expectations, we must have this feature enabled for the crate by default.
default = ["wiggle_metadata"]

View File

@@ -12,6 +12,7 @@ use syn::{
pub struct Config { pub struct Config {
pub witx: WitxConf, pub witx: WitxConf,
pub ctx: CtxConf, pub ctx: CtxConf,
pub emit_metadata: bool,
} }
#[derive(Debug, Clone)] #[derive(Debug, Clone)]
@@ -59,6 +60,7 @@ impl Config {
ctx: ctx ctx: ctx
.take() .take()
.ok_or_else(|| Error::new(err_loc, "`ctx` field required"))?, .ok_or_else(|| Error::new(err_loc, "`ctx` field required"))?,
emit_metadata: false,
}) })
} }
} }

View File

@@ -35,10 +35,25 @@ pub fn generate(doc: &witx::Document, config: &Config) -> TokenStream {
) )
}); });
let metadata = if config.emit_metadata {
let doc_text = &format!("{}", doc);
quote! {
pub mod metadata {
pub const DOC_TEXT: &str = #doc_text;
pub fn document() -> wiggle_runtime::witx::Document {
wiggle_runtime::witx::parse(DOC_TEXT).unwrap()
}
}
}
} else {
quote!()
};
quote!( quote!(
pub mod types { pub mod types {
#(#types)* #(#types)*
} }
#(#modules)* #(#modules)*
#metadata
) )
} }

View File

@@ -12,6 +12,10 @@ include = ["src/**/*", "LICENSE"]
[dependencies] [dependencies]
thiserror = "1" thiserror = "1"
witx = { path = "../../../wasi-common/wig/WASI/tools/witx", version = "0.8.4", optional = true }
[badges] [badges]
maintenance = { status = "actively-developed" } maintenance = { status = "actively-developed" }
[features]
wiggle_metadata = ['witx']

View File

@@ -6,6 +6,9 @@ use std::slice;
use std::str; use std::str;
use std::sync::Arc; use std::sync::Arc;
#[cfg(feature = "wiggle_metadata")]
pub use witx;
mod borrow; mod borrow;
mod error; mod error;
mod guest_type; mod guest_type;

View File

@@ -87,6 +87,12 @@ pub fn from_witx(args: TokenStream) -> TokenStream {
config.witx.make_paths_relative_to( config.witx.make_paths_relative_to(
std::env::var("CARGO_MANIFEST_DIR").expect("CARGO_MANIFEST_DIR env var"), std::env::var("CARGO_MANIFEST_DIR").expect("CARGO_MANIFEST_DIR env var"),
); );
#[cfg(feature = "wiggle_metadata")]
{
config.emit_metadata = true;
}
let doc = witx::load(&config.witx.paths).expect("loading witx"); let doc = witx::load(&config.witx.paths).expect("loading witx");
TokenStream::from(wiggle_generate::generate(&doc, &config)) TokenStream::from(wiggle_generate::generate(&doc, &config))
} }

View File

@@ -1,11 +1,26 @@
use wiggle_runtime::{GuestBorrows, GuestError, GuestErrorType, GuestPtr}; use wiggle_runtime::{GuestBorrows, GuestError, GuestErrorType, GuestPtr};
use wiggle_test::WasiCtx; use wiggle_test::WasiCtx;
// This test file exists to make sure that the entire `wasi.witx` file can be
// handled by wiggle, producing code that compiles correctly.
// The trait impls here are never executed, and just exist to validate that the
// witx is exposed with the type signatures that we expect.
wiggle::from_witx!({ wiggle::from_witx!({
witx: ["tests/wasi.witx"], witx: ["tests/wasi.witx"],
ctx: WasiCtx, ctx: WasiCtx,
}); });
// The only test in this file is to verify that the witx document provided by the
// proc macro in the `metadata` module is equal to the document on the disk.
#[test]
fn document_equivelant() {
let macro_doc = metadata::document();
let disk_doc = witx::load(&["tests/wasi.witx"]).expect("load wasi.witx from disk");
assert_eq!(macro_doc, disk_doc);
}
type Result<T> = std::result::Result<T, types::Errno>; type Result<T> = std::result::Result<T, types::Errno>;
impl<'a> GuestErrorType<'a> for types::Errno { impl<'a> GuestErrorType<'a> for types::Errno {