Make Rust `bindgen` build dependency optional (#382)
This commit is contained in:
parent
5efe8d092f
commit
fd669bfa36
|
@ -0,0 +1 @@
|
|||
bindings/rust/src/bindings/generated.rs linguist-generated
|
|
@ -23,6 +23,8 @@ jobs:
|
|||
- name: cargo hack
|
||||
working-directory: bindings/rust
|
||||
run: cargo hack check --feature-powerset --depth 2
|
||||
- name: Check that bindings are up to date
|
||||
run: git diff --exit-code bindings/rust/src/bindings/generated.rs
|
||||
|
||||
tests:
|
||||
runs-on: ${{ matrix.host }}
|
||||
|
@ -58,7 +60,9 @@ jobs:
|
|||
|
||||
- name: Build and Test
|
||||
working-directory: bindings/rust
|
||||
run: cargo test --target ${{ matrix.target }}
|
||||
run: cargo test --target ${{ matrix.target }} --features generate-bindings
|
||||
- name: Check that bindings are up to date
|
||||
run: git diff --exit-code bindings/rust/src/bindings/generated.rs
|
||||
- name: Benchmark
|
||||
working-directory: bindings/rust
|
||||
run: cargo bench --target ${{ matrix.target }}
|
||||
|
|
|
@ -31,17 +31,17 @@ checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
|
|||
|
||||
[[package]]
|
||||
name = "bindgen"
|
||||
version = "0.69.2"
|
||||
version = "0.69.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a4c69fae65a523209d34240b60abe0c42d33d1045d445c0839d8a4894a736e2d"
|
||||
checksum = "a00dc851838a2120612785d195287475a3ac45514741da670b735818822129a0"
|
||||
dependencies = [
|
||||
"bitflags",
|
||||
"cexpr",
|
||||
"clang-sys",
|
||||
"itertools",
|
||||
"lazy_static",
|
||||
"lazycell",
|
||||
"log",
|
||||
"peeking_take_while",
|
||||
"prettyplease",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
|
@ -486,12 +486,6 @@ version = "11.1.3"
|
|||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0ab1bc2a289d34bd04a330323ac98a1b4bc82c9d9fcb1e66b63caa84da26b575"
|
||||
|
||||
[[package]]
|
||||
name = "peeking_take_while"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "19b17cddbe7ec3f8bc800887bab5e717348c95ea2ca0b1bf0837fb964dc67099"
|
||||
|
||||
[[package]]
|
||||
name = "plotters"
|
||||
version = "0.3.5"
|
||||
|
|
|
@ -11,6 +11,7 @@ links = "ckzg"
|
|||
default = ["std", "blst/portable"]
|
||||
std = ["hex/std", "libc/std", "serde?/std"]
|
||||
serde = ["dep:serde"]
|
||||
generate-bindings = ["dep:bindgen"]
|
||||
|
||||
# BLST Compilation:
|
||||
# Suppress multi-threading.
|
||||
|
@ -18,13 +19,13 @@ serde = ["dep:serde"]
|
|||
no-threads = ["blst/no-threads"]
|
||||
|
||||
[dependencies]
|
||||
blst = { version = "0.3.11", default-features = false }
|
||||
hex = { version = "0.4.2", default-features = false, features = ["alloc"] }
|
||||
libc = { version = "0.2", default-features = false }
|
||||
serde = { version = "1.0", optional = true, default-features = false, features = [
|
||||
"alloc",
|
||||
"derive",
|
||||
] }
|
||||
blst = { version = "0.3.11", default-features = false }
|
||||
|
||||
[dev-dependencies]
|
||||
criterion = "0.5.1"
|
||||
|
@ -35,7 +36,7 @@ serde_yaml = "0.9.17"
|
|||
serde_json = "1.0.105"
|
||||
|
||||
[build-dependencies]
|
||||
bindgen = "0.69"
|
||||
bindgen = { version = "0.69", optional = true }
|
||||
cc = "1.0"
|
||||
|
||||
[target.'cfg(target_env = "msvc")'.build-dependencies]
|
||||
|
|
|
@ -34,25 +34,23 @@ fn main() {
|
|||
|
||||
cc.try_compile("ckzg").expect("Failed to compile ckzg");
|
||||
|
||||
let out_dir = PathBuf::from(env::var("OUT_DIR").unwrap());
|
||||
let bindings_out_path = out_dir.join("generated.rs");
|
||||
let header_file_path = c_src_dir.join("c_kzg_4844.h");
|
||||
let header_file = header_file_path.to_str().expect("valid header file");
|
||||
|
||||
#[cfg(feature = "generate-bindings")]
|
||||
{
|
||||
let header_path = c_src_dir.join("c_kzg_4844.h");
|
||||
let bindings_out_path = concat!(env!("CARGO_MANIFEST_DIR"), "/src/bindings/generated.rs");
|
||||
make_bindings(
|
||||
header_file,
|
||||
&blst_headers_dir.to_string_lossy(),
|
||||
bindings_out_path,
|
||||
header_path.to_str().expect("valid header path"),
|
||||
blst_headers_dir.to_str().expect("valid blst header path"),
|
||||
bindings_out_path.as_ref(),
|
||||
);
|
||||
}
|
||||
|
||||
// Finally, tell cargo this provides ckzg/ckzg_min
|
||||
println!("cargo:rustc-link-lib=ckzg");
|
||||
}
|
||||
|
||||
fn make_bindings<P>(header_path: &str, blst_headers_dir: &str, bindings_out_path: P)
|
||||
where
|
||||
P: AsRef<std::path::Path>,
|
||||
{
|
||||
#[cfg(feature = "generate-bindings")]
|
||||
fn make_bindings(header_path: &str, blst_headers_dir: &str, bindings_out_path: &std::path::Path) {
|
||||
use bindgen::Builder;
|
||||
|
||||
#[derive(Debug)]
|
||||
|
@ -123,7 +121,41 @@ where
|
|||
.generate()
|
||||
.unwrap();
|
||||
|
||||
bindings
|
||||
.write_to_file(bindings_out_path)
|
||||
.expect("Failed to write bindings");
|
||||
let mut bindings = bindings.to_string();
|
||||
bindings = replace_ckzg_ret_repr(bindings);
|
||||
std::fs::write(bindings_out_path, bindings).expect("Failed to write bindings");
|
||||
}
|
||||
|
||||
// Here we hardcode the C_KZG_RET enum to use C representation. Bindgen
|
||||
// will use repr(u32) on Unix and repr(i32) on Windows. We would like to
|
||||
// use the same generated bindings for all platforms. This can be removed
|
||||
// if/when bindgen fixes this or allows us to choose our own representation
|
||||
// for types. Using repr(C) is equivalent to repr(u*) for fieldless enums,
|
||||
// so this should be safe to do. The alternative was to modify C_KZG_RET in
|
||||
// C and we decided this was the lesser of two evils. There should be only
|
||||
// one instance where repr(C) isn't used: C_KZG_RET.
|
||||
// See: https://github.com/rust-lang/rust-bindgen/issues/1907
|
||||
#[cfg(feature = "generate-bindings")]
|
||||
fn replace_ckzg_ret_repr(mut bindings: String) -> String {
|
||||
let target = env::var("TARGET").unwrap_or_default();
|
||||
let repr_to_replace = if target.contains("windows") {
|
||||
"#[repr(i32)]"
|
||||
} else {
|
||||
"#[repr(u32)]"
|
||||
};
|
||||
|
||||
// Find `repr_to_replace` as an attribute of `enum C_KZG_RET`.
|
||||
let ckzg_ret = bindings
|
||||
.find("enum C_KZG_RET")
|
||||
.expect("Could not find C_KZG_RET in bindings");
|
||||
let repr_start = bindings[..ckzg_ret]
|
||||
.rfind(repr_to_replace)
|
||||
.expect("Could not find repr to replace in bindings");
|
||||
|
||||
// Sanity check that it's an attribute of `C_KZG_RET` and not another type.
|
||||
assert!(repr_start > bindings[..ckzg_ret].rfind('}').unwrap());
|
||||
|
||||
bindings.replace_range(repr_start..repr_start + repr_to_replace.len(), "#[repr(C)]");
|
||||
|
||||
bindings
|
||||
}
|
||||
|
|
|
@ -0,0 +1,138 @@
|
|||
/* automatically generated by rust-bindgen 0.69.4 */
|
||||
|
||||
use libc::FILE;
|
||||
|
||||
pub const BYTES_PER_COMMITMENT: usize = 48;
|
||||
pub const BYTES_PER_PROOF: usize = 48;
|
||||
pub const BYTES_PER_FIELD_ELEMENT: usize = 32;
|
||||
pub const FIELD_ELEMENTS_PER_BLOB: usize = 4096;
|
||||
pub const BYTES_PER_BLOB: usize = 131072;
|
||||
pub type limb_t = u64;
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct blst_fr {
|
||||
l: [limb_t; 4usize],
|
||||
}
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct blst_fp {
|
||||
l: [limb_t; 6usize],
|
||||
}
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct blst_fp2 {
|
||||
fp: [blst_fp; 2usize],
|
||||
}
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct blst_p1 {
|
||||
x: blst_fp,
|
||||
y: blst_fp,
|
||||
z: blst_fp,
|
||||
}
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct blst_p2 {
|
||||
x: blst_fp2,
|
||||
y: blst_fp2,
|
||||
z: blst_fp2,
|
||||
}
|
||||
pub type g1_t = blst_p1;
|
||||
pub type g2_t = blst_p2;
|
||||
pub type fr_t = blst_fr;
|
||||
#[doc = " An array of 32 bytes. Represents an untrusted\n (potentially invalid) field element."]
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct Bytes32 {
|
||||
bytes: [u8; 32usize],
|
||||
}
|
||||
#[doc = " An array of 48 bytes. Represents an untrusted\n (potentially invalid) commitment/proof."]
|
||||
#[repr(C)]
|
||||
#[derive(Debug, Copy, Clone, PartialEq, Eq)]
|
||||
pub struct Bytes48 {
|
||||
bytes: [u8; 48usize],
|
||||
}
|
||||
#[doc = " A basic blob data."]
|
||||
#[repr(C)]
|
||||
#[derive(Debug, PartialEq, Eq)]
|
||||
pub struct Blob {
|
||||
bytes: [u8; 131072usize],
|
||||
}
|
||||
#[repr(C)]
|
||||
#[doc = " The common return type for all routines in which something can go wrong."]
|
||||
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq)]
|
||||
pub enum C_KZG_RET {
|
||||
#[doc = "< Success!"]
|
||||
C_KZG_OK = 0,
|
||||
#[doc = "< The supplied data is invalid in some way."]
|
||||
C_KZG_BADARGS = 1,
|
||||
#[doc = "< Internal error - this should never occur."]
|
||||
C_KZG_ERROR = 2,
|
||||
#[doc = "< Could not allocate memory."]
|
||||
C_KZG_MALLOC = 3,
|
||||
}
|
||||
#[doc = " Stores the setup and parameters needed for computing KZG proofs."]
|
||||
#[repr(C)]
|
||||
#[derive(Debug, PartialEq, Eq)]
|
||||
pub struct KZGSettings {
|
||||
#[doc = " The length of `roots_of_unity`, a power of 2."]
|
||||
max_width: u64,
|
||||
#[doc = " Powers of the primitive root of unity determined by\n `SCALE2_ROOT_OF_UNITY` in bit-reversal permutation order,\n length `max_width`."]
|
||||
roots_of_unity: *mut fr_t,
|
||||
#[doc = " G1 group elements from the trusted setup,\n in Lagrange form bit-reversal permutation."]
|
||||
g1_values: *mut g1_t,
|
||||
#[doc = " G2 group elements from the trusted setup."]
|
||||
g2_values: *mut g2_t,
|
||||
}
|
||||
extern "C" {
|
||||
pub fn load_trusted_setup(
|
||||
out: *mut KZGSettings,
|
||||
g1_bytes: *const u8,
|
||||
n1: usize,
|
||||
g2_bytes: *const u8,
|
||||
n2: usize,
|
||||
) -> C_KZG_RET;
|
||||
pub fn load_trusted_setup_file(out: *mut KZGSettings, in_: *mut FILE) -> C_KZG_RET;
|
||||
pub fn free_trusted_setup(s: *mut KZGSettings);
|
||||
pub fn blob_to_kzg_commitment(
|
||||
out: *mut KZGCommitment,
|
||||
blob: *const Blob,
|
||||
s: *const KZGSettings,
|
||||
) -> C_KZG_RET;
|
||||
pub fn compute_kzg_proof(
|
||||
proof_out: *mut KZGProof,
|
||||
y_out: *mut Bytes32,
|
||||
blob: *const Blob,
|
||||
z_bytes: *const Bytes32,
|
||||
s: *const KZGSettings,
|
||||
) -> C_KZG_RET;
|
||||
pub fn compute_blob_kzg_proof(
|
||||
out: *mut KZGProof,
|
||||
blob: *const Blob,
|
||||
commitment_bytes: *const Bytes48,
|
||||
s: *const KZGSettings,
|
||||
) -> C_KZG_RET;
|
||||
pub fn verify_kzg_proof(
|
||||
ok: *mut bool,
|
||||
commitment_bytes: *const Bytes48,
|
||||
z_bytes: *const Bytes32,
|
||||
y_bytes: *const Bytes32,
|
||||
proof_bytes: *const Bytes48,
|
||||
s: *const KZGSettings,
|
||||
) -> C_KZG_RET;
|
||||
pub fn verify_blob_kzg_proof(
|
||||
ok: *mut bool,
|
||||
blob: *const Blob,
|
||||
commitment_bytes: *const Bytes48,
|
||||
proof_bytes: *const Bytes48,
|
||||
s: *const KZGSettings,
|
||||
) -> C_KZG_RET;
|
||||
pub fn verify_blob_kzg_proof_batch(
|
||||
ok: *mut bool,
|
||||
blobs: *const Blob,
|
||||
commitments_bytes: *const Bytes48,
|
||||
proofs_bytes: *const Bytes48,
|
||||
n: usize,
|
||||
s: *const KZGSettings,
|
||||
) -> C_KZG_RET;
|
||||
}
|
|
@ -1,13 +1,11 @@
|
|||
#![allow(non_upper_case_globals)]
|
||||
#![allow(non_camel_case_types)]
|
||||
#![allow(non_snake_case)]
|
||||
#![allow(non_camel_case_types, non_snake_case, non_upper_case_globals)]
|
||||
|
||||
#[cfg(feature = "serde")]
|
||||
mod serde;
|
||||
#[cfg(test)]
|
||||
mod test_formats;
|
||||
|
||||
include!(concat!(env!("OUT_DIR"), "/generated.rs"));
|
||||
include!("./generated.rs");
|
||||
|
||||
use alloc::string::String;
|
||||
use alloc::vec::Vec;
|
||||
|
|
Loading…
Reference in New Issue