Windows bindings for rust (#259)
This commit is contained in:
parent
47ddabde63
commit
b30983fc9a
|
@ -9,7 +9,13 @@ on:
|
|||
|
||||
jobs:
|
||||
tests:
|
||||
runs-on: ubuntu-latest
|
||||
runs-on: ${{ matrix.os }}
|
||||
strategy:
|
||||
matrix:
|
||||
os:
|
||||
- ubuntu-latest
|
||||
- windows-latest
|
||||
- macos-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
with:
|
||||
|
|
|
@ -42,7 +42,7 @@ dependencies = [
|
|||
"regex",
|
||||
"rustc-hash",
|
||||
"shlex",
|
||||
"syn 2.0.8",
|
||||
"syn 2.0.13",
|
||||
"which",
|
||||
]
|
||||
|
||||
|
@ -74,6 +74,7 @@ version = "0.1.0"
|
|||
dependencies = [
|
||||
"bindgen",
|
||||
"blst",
|
||||
"cc",
|
||||
"criterion",
|
||||
"glob",
|
||||
"hex",
|
||||
|
@ -139,9 +140,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "clang-sys"
|
||||
version = "1.6.0"
|
||||
version = "1.6.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "77ed9a53e5d4d9c573ae844bfac6872b159cb1d1585a83b29e7a64b7eef7332a"
|
||||
checksum = "c688fc74432808e3eb684cae8830a86be1d66a2bd58e1f248ed0960a590baf6f"
|
||||
dependencies = [
|
||||
"glob",
|
||||
"libc",
|
||||
|
@ -309,9 +310,9 @@ checksum = "7f24254aa9a54b5c858eaee2f5bccdb46aaf0e486a595ed5fd8f86ba55232a70"
|
|||
|
||||
[[package]]
|
||||
name = "indexmap"
|
||||
version = "1.9.2"
|
||||
version = "1.9.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1885e79c1fc4b10f0e172c475f458b7f7b93061064d98c3293e98c5ba0c8b399"
|
||||
checksum = "bd070e393353796e801d209ad339e89596eb4c8d430d18ede6a1cced8fafbd99"
|
||||
dependencies = [
|
||||
"autocfg",
|
||||
"hashbrown",
|
||||
|
@ -355,9 +356,9 @@ checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55"
|
|||
|
||||
[[package]]
|
||||
name = "libc"
|
||||
version = "0.2.140"
|
||||
version = "0.2.141"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "99227334921fae1a979cf0bfdfcc6b3e5ce376ef57e16fb6fb3ea2ed6095f80c"
|
||||
checksum = "3304a64d199bb964be99741b7a14d26972741915b3649639149b2479bb46f4b5"
|
||||
|
||||
[[package]]
|
||||
name = "libloading"
|
||||
|
@ -488,9 +489,9 @@ checksum = "5b40af805b3121feab8a3c29f04d8ad262fa8e0561883e7653e024ae4479e6de"
|
|||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.53"
|
||||
version = "1.0.56"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ba466839c78239c09faf015484e5cc04860f88242cff4d03eb038f04b4699b73"
|
||||
checksum = "2b63bdb0cd06f1f4dedf69b254734f9b45af66e4a031e42a7480257d9898b435"
|
||||
dependencies = [
|
||||
"unicode-ident",
|
||||
]
|
||||
|
@ -558,9 +559,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "regex"
|
||||
version = "1.7.2"
|
||||
version = "1.7.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "cce168fea28d3e05f158bda4576cf0c844d5045bc2cc3620fa0292ed5bb5814c"
|
||||
checksum = "8b1f693b24f6ac912f4893ef08244d70b6067480d2f1a46e950c9691e6749d1d"
|
||||
dependencies = [
|
||||
"regex-syntax",
|
||||
]
|
||||
|
@ -600,29 +601,29 @@ checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd"
|
|||
|
||||
[[package]]
|
||||
name = "serde"
|
||||
version = "1.0.158"
|
||||
version = "1.0.159"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "771d4d9c4163ee138805e12c710dd365e4f44be8be0503cb1bb9eb989425d9c9"
|
||||
checksum = "3c04e8343c3daeec41f58990b9d77068df31209f2af111e059e9fe9646693065"
|
||||
dependencies = [
|
||||
"serde_derive",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_derive"
|
||||
version = "1.0.158"
|
||||
version = "1.0.159"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e801c1712f48475582b7696ac71e0ca34ebb30e09338425384269d9717c62cad"
|
||||
checksum = "4c614d17805b093df4b147b51339e7e44bf05ef59fba1e45d83500bcfb4d8585"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.8",
|
||||
"syn 2.0.13",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "serde_json"
|
||||
version = "1.0.94"
|
||||
version = "1.0.95"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1c533a59c9d8a93a09c6ab31f0fd5e5f4dd1b8fc9434804029839884765d04ea"
|
||||
checksum = "d721eca97ac802aa7777b701877c8004d950fc142651367300d21c1cc0194744"
|
||||
dependencies = [
|
||||
"itoa",
|
||||
"ryu",
|
||||
|
@ -661,9 +662,9 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.8"
|
||||
version = "2.0.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bcc02725fd69ab9f26eab07fad303e2497fad6fb9eba4f96c4d1687bdf704ad9"
|
||||
checksum = "4c9da457c5285ac1f936ebd076af6dac17a61cfe7826f2076b4d015cf47bc8ec"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
|
@ -846,5 +847,5 @@ checksum = "ce36e65b0d2999d2aafac989fb249189a141aee1f53c612c1f37d72631959f69"
|
|||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.8",
|
||||
"syn 2.0.13",
|
||||
]
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
name = "c-kzg"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
links = "ckzg"
|
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
|
||||
|
@ -24,6 +25,7 @@ serde_yaml = "0.9.17"
|
|||
|
||||
[build-dependencies]
|
||||
bindgen = { git = "https://github.com/rust-lang/rust-bindgen" , rev = "0de11f0a521611ac8738b7b01d19dddaf3899e66" }
|
||||
cc = "1.0"
|
||||
|
||||
[[bench]]
|
||||
name = "kzg_benches"
|
||||
|
|
|
@ -1,18 +1,9 @@
|
|||
use std::env;
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::process::Command;
|
||||
use std::path::PathBuf;
|
||||
|
||||
const MAINNET_FIELD_ELEMENTS_PER_BLOB: usize = 4096;
|
||||
const MINIMAL_FIELD_ELEMENTS_PER_BLOB: usize = 4;
|
||||
|
||||
fn move_file(src: &Path, dst: &Path) -> Result<(), String> {
|
||||
std::fs::copy(src, dst)
|
||||
.map_err(|_| format!("Failed to copy {} to {}", src.display(), dst.display()))?;
|
||||
std::fs::remove_file(src)
|
||||
.map_err(|_| format!("Failed to remove file {} from source", src.display()))?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn main() {
|
||||
let cargo_dir = PathBuf::from(env::var("CARGO_MANIFEST_DIR").unwrap());
|
||||
let root_dir = cargo_dir
|
||||
|
@ -20,7 +11,6 @@ fn main() {
|
|||
.expect("rust dir is nested")
|
||||
.parent()
|
||||
.expect("bindings dir is nested");
|
||||
let out_dir = PathBuf::from(env::var("OUT_DIR").unwrap());
|
||||
|
||||
let field_elements_per_blob = if cfg!(feature = "minimal-spec") {
|
||||
MINIMAL_FIELD_ELEMENTS_PER_BLOB
|
||||
|
@ -30,38 +20,24 @@ fn main() {
|
|||
|
||||
eprintln!("Using FIELD_ELEMENTS_PER_BLOB={}", field_elements_per_blob);
|
||||
|
||||
// Deleting any existing assembly and object files to ensure that compiling with a different
|
||||
// feature flag changes the final linked library file.
|
||||
let obj_file = root_dir.join("src").join("c_kzg_4844.o");
|
||||
if obj_file.exists() {
|
||||
std::fs::remove_file(obj_file).unwrap();
|
||||
}
|
||||
// Obtain the header files exposed by blst-bindings' crate.
|
||||
let blst_headers_dir =
|
||||
std::env::var_os("DEP_BLST_BINDINGS").expect("BLST exposes header files for bindings");
|
||||
|
||||
// Ensure libckzg exists in `OUT_DIR`
|
||||
Command::new("make")
|
||||
.current_dir(root_dir.join("src"))
|
||||
.arg("c_kzg_4844.o")
|
||||
.arg(format!(
|
||||
"FIELD_ELEMENTS_PER_BLOB={}",
|
||||
field_elements_per_blob
|
||||
))
|
||||
.status()
|
||||
.unwrap();
|
||||
let c_src_dir = root_dir.join("src");
|
||||
|
||||
Command::new("ar")
|
||||
.current_dir(&root_dir.join("src"))
|
||||
.args(["crus", "libckzg.a", "c_kzg_4844.o"])
|
||||
.status()
|
||||
.unwrap();
|
||||
move_file(
|
||||
root_dir.join("src").join("libckzg.a").as_path(),
|
||||
out_dir.join("libckzg.a").as_path(),
|
||||
)
|
||||
.unwrap();
|
||||
let mut cc = cc::Build::new();
|
||||
|
||||
#[cfg(windows)]
|
||||
cc.compiler("clang").flag("-D_CRT_SECURE_NO_WARNINGS");
|
||||
|
||||
cc.include(blst_headers_dir.clone());
|
||||
cc.warnings(false);
|
||||
cc.flag(format!("-DFIELD_ELEMENTS_PER_BLOB={}", field_elements_per_blob).as_str());
|
||||
cc.file(c_src_dir.join("c_kzg_4844.c"));
|
||||
|
||||
cc.try_compile("ckzg").expect("Failed to compile ckzg");
|
||||
|
||||
println!("cargo:rustc-link-search={}", out_dir.display());
|
||||
println!("cargo:rustc-link-search={}", out_dir.display());
|
||||
println!("cargo:rustc-link-lib=static=ckzg");
|
||||
// Tell cargo to search for the static blst exposed by the blst-bindings' crate.
|
||||
println!("cargo:rustc-link-lib=static=blst");
|
||||
|
||||
|
@ -71,12 +47,9 @@ fn main() {
|
|||
"bindings_{build_target}_{field_elements_per_blob}.rs"
|
||||
));
|
||||
|
||||
let header_file_path = root_dir.join("src").join("c_kzg_4844.h");
|
||||
let header_file_path = c_src_dir.join("c_kzg_4844.h");
|
||||
let header_file = header_file_path.to_str().expect("valid header file");
|
||||
|
||||
// Obtain the header files exposed by blst-bindings' crate.
|
||||
let blst_headers_dir =
|
||||
std::env::var_os("DEP_BLST_BINDINGS").expect("BLST exposes header files for bindings");
|
||||
make_bindings(
|
||||
field_elements_per_blob,
|
||||
header_file,
|
||||
|
@ -85,11 +58,8 @@ fn main() {
|
|||
snapshot_path,
|
||||
);
|
||||
|
||||
// Cleanup
|
||||
let obj_file = root_dir.join("src").join("c_kzg_4844.o");
|
||||
if obj_file.exists() {
|
||||
std::fs::remove_file(obj_file).unwrap();
|
||||
}
|
||||
// Finally, tell cargo this provides ckzg
|
||||
println!("cargo:rustc-link-lib=ckzg");
|
||||
}
|
||||
|
||||
fn make_bindings<P>(
|
||||
|
|
|
@ -6,10 +6,8 @@ mod test_formats;
|
|||
|
||||
include!("generated.rs");
|
||||
|
||||
use libc::fopen;
|
||||
use std::ffi::CString;
|
||||
use std::mem::MaybeUninit;
|
||||
use std::os::unix::prelude::OsStrExt;
|
||||
use std::path::PathBuf;
|
||||
|
||||
pub const BYTES_PER_G1_POINT: usize = 48;
|
||||
|
@ -102,12 +100,41 @@ impl KZGSettings {
|
|||
/// FIELD_ELEMENT_PER_BLOB g1 byte values
|
||||
/// 65 g2 byte values
|
||||
pub fn load_trusted_setup_file(file_path: PathBuf) -> Result<Self, Error> {
|
||||
let file_path = CString::new(file_path.as_os_str().as_bytes()).map_err(|e| {
|
||||
Error::InvalidTrustedSetup(format!("Invalid trusted setup file: {:?}", e))
|
||||
})?;
|
||||
// SAFETY: vec![b'r'] has no 0 bytes.
|
||||
let mode = unsafe { CString::from_vec_unchecked(vec![b'r']) };
|
||||
|
||||
#[cfg(unix)]
|
||||
let file_path_bytes = {
|
||||
use std::os::unix::prelude::OsStrExt;
|
||||
file_path.as_os_str().as_bytes()
|
||||
};
|
||||
|
||||
#[cfg(windows)]
|
||||
let file_path_bytes = {
|
||||
file_path
|
||||
.as_os_str()
|
||||
.to_str()
|
||||
.ok_or(Error::InvalidTrustedSetup(format!(
|
||||
"Unsuported non unicode file path"
|
||||
)))?
|
||||
.as_bytes()
|
||||
};
|
||||
|
||||
let file_path = CString::new(file_path_bytes)
|
||||
.map_err(|e| Error::InvalidTrustedSetup(format!("Invalid trusted setup file: {e}")))?;
|
||||
|
||||
// SAFETY:
|
||||
// - .as_ptr(): pointer is not dangling because file_path has not been dropped.
|
||||
// Usage or ptr: File will not be written to it by the c code.
|
||||
let file_ptr = unsafe { libc::fopen(file_path.as_ptr(), mode.as_ptr()) };
|
||||
if file_ptr.is_null() {
|
||||
let e = std::io::Error::last_os_error();
|
||||
return Err(Error::InvalidTrustedSetup(format!(
|
||||
"Failed to open trusted setup file {e}"
|
||||
)));
|
||||
}
|
||||
let mut kzg_settings = MaybeUninit::<KZGSettings>::uninit();
|
||||
unsafe {
|
||||
let file_ptr = fopen(file_path.as_ptr(), &('r' as libc::c_char));
|
||||
let result = unsafe {
|
||||
let res = load_trusted_setup_file(kzg_settings.as_mut_ptr(), file_ptr);
|
||||
if let C_KZG_RET::C_KZG_OK = res {
|
||||
Ok(kzg_settings.assume_init())
|
||||
|
@ -117,7 +144,13 @@ impl KZGSettings {
|
|||
res
|
||||
)))
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// We don't really care if this succeeds.
|
||||
let _uncheched_close_result = unsafe { libc::fclose(file_ptr) };
|
||||
drop(file_path);
|
||||
|
||||
result
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -8,7 +8,7 @@ pub use bindings::{
|
|||
// Expose the constants.
|
||||
pub use bindings::{
|
||||
BYTES_PER_BLOB, BYTES_PER_COMMITMENT, BYTES_PER_FIELD_ELEMENT, BYTES_PER_PROOF,
|
||||
FIELD_ELEMENTS_PER_BLOB,
|
||||
FIELD_ELEMENTS_PER_BLOB, BYTES_PER_G1_POINT, BYTES_PER_G2_POINT
|
||||
};
|
||||
// Expose the remaining relevant types.
|
||||
pub use bindings::{Blob, Bytes32, Bytes48, Error, FFTSettings};
|
||||
|
|
Loading…
Reference in New Issue