Skip to content

Commit

Permalink
Add wasm bindings for Pubkey and Keypair
Browse files Browse the repository at this point in the history
  • Loading branch information
mvines committed Dec 9, 2021
1 parent 6919c48 commit 488dc37
Show file tree
Hide file tree
Showing 23 changed files with 537 additions and 15 deletions.
24 changes: 24 additions & 0 deletions Cargo.lock

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

13 changes: 13 additions & 0 deletions ci/buildkite-pipeline.sh
Original file line number Diff line number Diff line change
Expand Up @@ -226,6 +226,19 @@ EOF
annotate --style info \
"downstream-projects skipped as no relevant files were modified"
fi

# Wasm support
if affects \
^ci/test-wasm.sh \
^ci/test-stable.sh \
^sdk/ \
; then
command_step wasm ". ci/rust-version.sh; ci/docker-run.sh \$\$rust_stable_docker_image ci/test-wasm.sh" 20
else
annotate --style info \
"wasm skipped as no relevant files were modified"
fi

# Benches...
if affects \
.rs$ \
Expand Down
5 changes: 5 additions & 0 deletions ci/docker-rust/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ RUN set -x \
&& apt-get install apt-transport-https \
&& echo deb https://apt.buildkite.com/buildkite-agent stable main > /etc/apt/sources.list.d/buildkite-agent.list \
&& apt-key adv --no-tty --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 32A37959C2FA5C3C99EFBC32A79206696452D198 \
&& curl -fsSL https://deb.nodesource.com/setup_current.x | bash - \
&& apt update \
&& apt install -y \
buildkite-agent \
Expand All @@ -19,15 +20,19 @@ RUN set -x \
lcov \
libudev-dev \
mscgen \
nodejs \
net-tools \
rsync \
sudo \
golang \
unzip \
\
&& rm -rf /var/lib/apt/lists/* \
&& node --version \
&& npm --version \
&& rustup component add rustfmt \
&& rustup component add clippy \
&& rustup target add wasm32-unknown-unknown \
&& cargo install cargo-audit \
&& cargo install mdbook \
&& cargo install mdbook-linkcheck \
Expand Down
13 changes: 13 additions & 0 deletions ci/test-stable.sh
Original file line number Diff line number Diff line change
Expand Up @@ -103,6 +103,19 @@ test-local-cluster)
_ "$cargo" stable test --release --package solana-local-cluster ${V:+--verbose} -- --nocapture --test-threads=1
exit 0
;;
test-wasm)
_ node --version
_ npm --version
for dir in sdk/{program,}; do
if [[ -r "$dir"/package.json ]]; then
pushd "$dir"
_ npm install
_ npm test
popd
fi
done
exit 0
;;
*)
echo "Error: Unknown test: $testName"
;;
Expand Down
1 change: 1 addition & 0 deletions ci/test-wasm.sh
48 changes: 36 additions & 12 deletions programs/bpf/Cargo.lock

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

4 changes: 3 additions & 1 deletion sdk/.gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,4 @@
/target/
/farf/
/node_modules/
/package-lock.json
/target/
4 changes: 4 additions & 0 deletions sdk/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,10 @@ solana-program = { path = "program", version = "=1.10.0" }
solana-sdk-macro = { path = "macro", version = "=1.10.0" }
thiserror = "1.0"
uriparse = "0.6.3"
wasm-bindgen = "0.2"

[target.'cfg(target_arch = "wasm32")'.dependencies]
js-sys = "0.3.55"

[dev-dependencies]
curve25519-dalek = "3.2.0"
Expand Down
28 changes: 28 additions & 0 deletions sdk/macro/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -373,3 +373,31 @@ pub fn pubkeys(input: TokenStream) -> TokenStream {
let pubkeys = parse_macro_input!(input as Pubkeys);
TokenStream::from(quote! {#pubkeys})
}

// The normal `wasm_bindgen` macro generates a .bss section which causes the resulting
// BPF program to fail to load, so for now this stub should be used when building for BPF
#[proc_macro_attribute]
pub fn wasm_bindgen_stub(_attr: TokenStream, item: TokenStream) -> TokenStream {
match parse_macro_input!(item as syn::Item) {
syn::Item::Struct(mut item_struct) => {
if let syn::Fields::Named(fields) = &mut item_struct.fields {
// Strip out any `#[wasm_bindgen]` added to struct fields. This is custom
// syntax supplied by the normal `wasm_bindgen` macro.
for field in fields.named.iter_mut() {
field.attrs.retain(|attr| {
!attr
.path
.segments
.iter()
.any(|segment| segment.ident == "wasm_bindgen")
});
}
}
quote! { #item_struct }
}
item => {
quote!(#item)
}
}
.into()
}
1 change: 1 addition & 0 deletions sdk/package.json
2 changes: 2 additions & 0 deletions sdk/program/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
/node_modules/
/package-lock.json
7 changes: 7 additions & 0 deletions sdk/program/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,13 @@ libsecp256k1 = "0.6.0"
rand = "0.7.0"
solana-logger = { path = "../../logger", version = "=1.10.0" }
itertools = "0.10.1"
wasm-bindgen = "0.2"

[target.'cfg(target_arch = "wasm32")'.dependencies]
console_error_panic_hook = "0.1.7"
console_log = "0.2.0"
js-sys = "0.3.55"
getrandom = { version = "0.1", features = ["wasm-bindgen"] }

[target.'cfg(not(target_pointer_width = "64"))'.dependencies]
parking_lot = "0.11"
Expand Down
14 changes: 14 additions & 0 deletions sdk/program/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"devDependencies": {
"chai": "^4.3.4",
"mocha": "^9.1.2",
"prettier": "^2.4.1"
},
"scripts": {
"postinstall": "npm run build",
"build": "wasm-pack build --target nodejs --dev --out-dir node_modules/crate --out-name crate",
"pretty": "prettier --check 'tests/*.mjs'",
"pretty:fix": "prettier --write 'tests/*.mjs'",
"test": "mocha 'tests/*.mjs'"
}
}
6 changes: 6 additions & 0 deletions sdk/program/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,12 @@ pub mod stake_history;
pub mod system_instruction;
pub mod system_program;
pub mod sysvar;
pub mod wasm;

#[cfg(target_arch = "bpf")]
pub use solana_sdk_macro::wasm_bindgen_stub as wasm_bindgen;
#[cfg(not(target_arch = "bpf"))]
pub use wasm_bindgen::prelude::wasm_bindgen;

pub mod config {
pub mod program {
Expand Down
5 changes: 3 additions & 2 deletions sdk/program/src/pubkey.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#![allow(clippy::integer_arithmetic)]
use {
crate::{decode_error::DecodeError, hash::hashv},
crate::{decode_error::DecodeError, hash::hashv, wasm_bindgen},
borsh::{BorshDeserialize, BorshSchema, BorshSerialize},
bytemuck::{Pod, Zeroable},
num_derive::{FromPrimitive, ToPrimitive},
Expand Down Expand Up @@ -48,6 +48,7 @@ impl From<u64> for PubkeyError {
}
}

#[wasm_bindgen]
#[repr(transparent)]
#[derive(
AbiExample,
Expand All @@ -67,7 +68,7 @@ impl From<u64> for PubkeyError {
Serialize,
Zeroable,
)]
pub struct Pubkey([u8; 32]);
pub struct Pubkey(pub(crate) [u8; 32]);

impl crate::sanitize::Sanitize for Pubkey {}

Expand Down
16 changes: 16 additions & 0 deletions sdk/program/src/wasm/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
//! solana-program Javascript interface
#![cfg(target_arch = "wasm32")]
use wasm_bindgen::prelude::*;

pub mod pubkey;

/// Initialize Javascript logging and panic handler
#[wasm_bindgen]
pub fn init() {
std::panic::set_hook(Box::new(console_error_panic_hook::hook));
console_log::init_with_level(log::Level::Info).unwrap();
}

pub fn display_to_jsvalue<T: std::fmt::Display>(display: T) -> JsValue {
display.to_string().into()
}
Loading

0 comments on commit 488dc37

Please sign in to comment.