Use LIB_PREFIX in Rust bindings (#317)

This commit is contained in:
Michael Sproul 2023-06-29 04:55:28 +10:00 committed by GitHub
parent 16e83cec65
commit 13cec820c0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 93 additions and 33 deletions

View File

@ -1,2 +1 @@
src/bindings/generated.rs
target/ target/

View File

@ -2,7 +2,9 @@
name = "c-kzg" name = "c-kzg"
version = "0.1.0" version = "0.1.0"
edition = "2021" edition = "2021"
links = "ckzg" # XXX: Note that we don't set a `links` attribute for Cargo, because this library may link
# either `ckzg` or `ckzg_min`. This allows the crate to be linked twice as minimal/mainnet variants
# without Cargo complaining.
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

View File

@ -125,13 +125,14 @@ fn main() {
.parent() .parent()
.expect("bindings dir is nested"); .expect("bindings dir is nested");
let field_elements_per_blob = if cfg!(feature = "minimal-spec") { let (lib_name, field_elements_per_blob) = if cfg!(feature = "minimal-spec") {
MINIMAL_FIELD_ELEMENTS_PER_BLOB ("ckzg_min", MINIMAL_FIELD_ELEMENTS_PER_BLOB)
} else { } else {
MAINNET_FIELD_ELEMENTS_PER_BLOB ("ckzg", MAINNET_FIELD_ELEMENTS_PER_BLOB)
}; };
eprintln!("Using FIELD_ELEMENTS_PER_BLOB={}", field_elements_per_blob); eprintln!("Using LIB_PREFIX={lib_name}");
eprintln!("Using FIELD_ELEMENTS_PER_BLOB={field_elements_per_blob}");
let blst_base_dir = root_dir.join("blst"); let blst_base_dir = root_dir.join("blst");
compile_blst(blst_base_dir.clone()); compile_blst(blst_base_dir.clone());
@ -148,30 +149,34 @@ fn main() {
cc.include(blst_headers_dir.clone()); cc.include(blst_headers_dir.clone());
cc.warnings(false); cc.warnings(false);
cc.flag(format!("-DLIB_PREFIX={lib_name}").as_str());
cc.flag(format!("-DFIELD_ELEMENTS_PER_BLOB={}", field_elements_per_blob).as_str()); cc.flag(format!("-DFIELD_ELEMENTS_PER_BLOB={}", field_elements_per_blob).as_str());
cc.file(c_src_dir.join("c_kzg_4844.c")); cc.file(c_src_dir.join("c_kzg_4844.c"));
cc.try_compile("ckzg").expect("Failed to compile ckzg"); cc.try_compile(lib_name).expect("Failed to compile ckzg");
// Tell cargo to search for the static blst exposed by the blst-bindings' crate. // Tell cargo to search for the static blst exposed by the blst-bindings' crate.
println!("cargo:rustc-link-lib=static=blst"); println!("cargo:rustc-link-lib=static=blst");
let bindings_out_path = cargo_dir.join("src").join("bindings").join("generated.rs"); 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_path = c_src_dir.join("c_kzg_4844.h");
let header_file = header_file_path.to_str().expect("valid header file"); let header_file = header_file_path.to_str().expect("valid header file");
make_bindings( make_bindings(
lib_name,
field_elements_per_blob, field_elements_per_blob,
header_file, header_file,
&blst_headers_dir.to_string_lossy(), &blst_headers_dir.to_string_lossy(),
bindings_out_path, bindings_out_path,
); );
// Finally, tell cargo this provides ckzg // Finally, tell cargo this provides ckzg/ckzg_min
println!("cargo:rustc-link-lib=ckzg"); println!("cargo:rustc-link-lib={lib_name}");
} }
fn make_bindings<P>( fn make_bindings<P>(
lib_name: &str,
field_elements_per_blob: usize, field_elements_per_blob: usize,
header_path: &str, header_path: &str,
blst_headers_dir: &str, blst_headers_dir: &str,
@ -207,11 +212,15 @@ fn make_bindings<P>(
// -D is not supported by bindgen https://github.com/rust-lang/rust-bindgen/issues/2394 // -D is not supported by bindgen https://github.com/rust-lang/rust-bindgen/issues/2394
.header_contents( .header_contents(
"consts", "consts",
&format!("#define FIELD_ELEMENTS_PER_BLOB {field_elements_per_blob}"), &format!(
"#define LIB_PREFIX {lib_name}
#define FIELD_ELEMENTS_PER_BLOB {field_elements_per_blob}"
),
) )
.header(header_path) .header(header_path)
.clang_args([format!("-I{blst_headers_dir}")]) .clang_args([format!("-I{blst_headers_dir}")])
// Since this is not part of the header file, needs to be allowed explicitly. // Since this is not part of the header file, needs to be allowed explicitly.
.allowlist_var("LIB_PREFIX")
.allowlist_var("FIELD_ELEMENTS_PER_BLOB") .allowlist_var("FIELD_ELEMENTS_PER_BLOB")
// Get bindings only for the header file. // Get bindings only for the header file.
.allowlist_file(".*c_kzg_4844.h") .allowlist_file(".*c_kzg_4844.h")

View File

@ -4,7 +4,31 @@
mod test_formats; mod test_formats;
include!("generated.rs"); include!(concat!(env!("OUT_DIR"), "/generated.rs"));
#[cfg(not(feature = "minimal-spec"))]
use {
ckzg_blob_to_kzg_commitment as blob_to_kzg_commitment,
ckzg_compute_blob_kzg_proof as compute_blob_kzg_proof,
ckzg_compute_kzg_proof as compute_kzg_proof, ckzg_free_trusted_setup as free_trusted_setup,
ckzg_load_trusted_setup as load_trusted_setup,
ckzg_load_trusted_setup_file as load_trusted_setup_file,
ckzg_verify_blob_kzg_proof as verify_blob_kzg_proof,
ckzg_verify_blob_kzg_proof_batch as verify_blob_kzg_proof_batch,
ckzg_verify_kzg_proof as verify_kzg_proof,
};
#[cfg(feature = "minimal-spec")]
use {
ckzg_min_blob_to_kzg_commitment as blob_to_kzg_commitment,
ckzg_min_compute_blob_kzg_proof as compute_blob_kzg_proof,
ckzg_min_compute_kzg_proof as compute_kzg_proof,
ckzg_min_free_trusted_setup as free_trusted_setup,
ckzg_min_load_trusted_setup as load_trusted_setup,
ckzg_min_load_trusted_setup_file as load_trusted_setup_file,
ckzg_min_verify_blob_kzg_proof as verify_blob_kzg_proof,
ckzg_min_verify_blob_kzg_proof_batch as verify_blob_kzg_proof_batch,
ckzg_min_verify_kzg_proof as verify_kzg_proof,
};
use std::ffi::CString; use std::ffi::CString;
use std::mem::MaybeUninit; use std::mem::MaybeUninit;

View File

@ -887,7 +887,7 @@ static C_KZG_RET poly_to_kzg_commitment(
* @param[in] blob The blob representing the polynomial to be committed to * @param[in] blob The blob representing the polynomial to be committed to
* @param[in] s The trusted setup * @param[in] s The trusted setup
*/ */
C_KZG_RET blob_to_kzg_commitment( C_KZG_RET BLOB_TO_KZG_COMMITMENT(
KZGCommitment *out, const Blob *blob, const KZGSettings *s KZGCommitment *out, const Blob *blob, const KZGSettings *s
) { ) {
C_KZG_RET ret; C_KZG_RET ret;
@ -922,7 +922,7 @@ static C_KZG_RET verify_kzg_proof_impl(
* @param[in] kzg_proof The KZG proof * @param[in] kzg_proof The KZG proof
* @param[in] s The trusted setup * @param[in] s The trusted setup
*/ */
C_KZG_RET verify_kzg_proof( C_KZG_RET VERIFY_KZG_PROOF(
bool *ok, bool *ok,
const Bytes48 *commitment_bytes, const Bytes48 *commitment_bytes,
const Bytes32 *z_bytes, const Bytes32 *z_bytes,
@ -1011,7 +1011,7 @@ static C_KZG_RET compute_kzg_proof_impl(
* @param[in] z The generator z-value for the evaluation points * @param[in] z The generator z-value for the evaluation points
* @param[in] s The trusted setup * @param[in] s The trusted setup
*/ */
C_KZG_RET compute_kzg_proof( C_KZG_RET COMPUTE_KZG_PROOF(
KZGProof *proof_out, KZGProof *proof_out,
Bytes32 *y_out, Bytes32 *y_out,
const Blob *blob, const Blob *blob,
@ -1137,7 +1137,7 @@ out:
* @param[in] commitment_bytes Commitment to verify * @param[in] commitment_bytes Commitment to verify
* @param[in] s The trusted setup * @param[in] s The trusted setup
*/ */
C_KZG_RET compute_blob_kzg_proof( C_KZG_RET COMPUTE_BLOB_KZG_PROOF(
KZGProof *out, KZGProof *out,
const Blob *blob, const Blob *blob,
const Bytes48 *commitment_bytes, const Bytes48 *commitment_bytes,
@ -1178,7 +1178,7 @@ out:
* @param[in] proof_bytes Proof used for verification * @param[in] proof_bytes Proof used for verification
* @param[in] s The trusted setup * @param[in] s The trusted setup
*/ */
C_KZG_RET verify_blob_kzg_proof( C_KZG_RET VERIFY_BLOB_KZG_PROOF(
bool *ok, bool *ok,
const Blob *blob, const Blob *blob,
const Bytes48 *commitment_bytes, const Bytes48 *commitment_bytes,
@ -1391,7 +1391,7 @@ out:
* @param[in] n The number of blobs/commitments/proofs * @param[in] n The number of blobs/commitments/proofs
* @param[in] s The trusted setup * @param[in] s The trusted setup
*/ */
C_KZG_RET verify_blob_kzg_proof_batch( C_KZG_RET VERIFY_BLOB_KZG_PROOF_BATCH(
bool *ok, bool *ok,
const Blob *blobs, const Blob *blobs,
const Bytes48 *commitments_bytes, const Bytes48 *commitments_bytes,
@ -1413,7 +1413,7 @@ C_KZG_RET verify_blob_kzg_proof_batch(
/* For a single blob, just do a regular single verification */ /* For a single blob, just do a regular single verification */
if (n == 1) { if (n == 1) {
return verify_blob_kzg_proof( return VERIFY_BLOB_KZG_PROOF(
ok, &blobs[0], &commitments_bytes[0], &proofs_bytes[0], s ok, &blobs[0], &commitments_bytes[0], &proofs_bytes[0], s
); );
} }
@ -1648,7 +1648,7 @@ out:
* *
* @param[in] s The trusted setup to free * @param[in] s The trusted setup to free
*/ */
void free_trusted_setup(KZGSettings *s) { void FREE_TRUSTED_SETUP(KZGSettings *s) {
if (s == NULL) return; if (s == NULL) return;
s->max_width = 0; s->max_width = 0;
c_kzg_free(s->roots_of_unity); c_kzg_free(s->roots_of_unity);
@ -1694,7 +1694,7 @@ static C_KZG_RET is_trusted_setup_in_lagrange_form(
* @param[in] g2_bytes Array of G2 points in monomial form * @param[in] g2_bytes Array of G2 points in monomial form
* @param[in] n2 Number of `g2` points in g2_bytes * @param[in] n2 Number of `g2` points in g2_bytes
*/ */
C_KZG_RET load_trusted_setup( C_KZG_RET LOAD_TRUSTED_SETUP(
KZGSettings *out, KZGSettings *out,
const uint8_t *g1_bytes, const uint8_t *g1_bytes,
size_t n1, size_t n1,
@ -1772,7 +1772,7 @@ out_error:
* (roots_of_unity, g1_values, g2_values). It does not free the KZGSettings * (roots_of_unity, g1_values, g2_values). It does not free the KZGSettings
* structure memory. If necessary, that must be done by the caller. * structure memory. If necessary, that must be done by the caller.
*/ */
free_trusted_setup(out); FREE_TRUSTED_SETUP(out);
out_success: out_success:
return ret; return ret;
} }
@ -1790,7 +1790,7 @@ out_success:
* @param[out] out Pointer to the loaded trusted setup data * @param[out] out Pointer to the loaded trusted setup data
* @param[in] in File handle for input * @param[in] in File handle for input
*/ */
C_KZG_RET load_trusted_setup_file(KZGSettings *out, FILE *in) { C_KZG_RET LOAD_TRUSTED_SETUP_FILE(KZGSettings *out, FILE *in) {
int num_matches; int num_matches;
uint64_t i; uint64_t i;
uint8_t g1_bytes[TRUSTED_SETUP_NUM_G1_POINTS * BYTES_PER_G1]; uint8_t g1_bytes[TRUSTED_SETUP_NUM_G1_POINTS * BYTES_PER_G1];
@ -1818,7 +1818,7 @@ C_KZG_RET load_trusted_setup_file(KZGSettings *out, FILE *in) {
CHECK(num_matches == 1); CHECK(num_matches == 1);
} }
return load_trusted_setup( return LOAD_TRUSTED_SETUP(
out, out,
g1_bytes, g1_bytes,
TRUSTED_SETUP_NUM_G1_POINTS, TRUSTED_SETUP_NUM_G1_POINTS,

View File

@ -36,6 +36,32 @@ extern "C" {
// Macros // Macros
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
/*
* Helper function for when LIB_PREFIX is defined.
*/
#ifdef LIB_PREFIX
#define CONCAT_IMPL(a, b) a##_##b
#define CONCAT(a, b) CONCAT_IMPL(a, b)
#define PREFIX_FUNCNAME(name) CONCAT(LIB_PREFIX, name)
#else
#define PREFIX_FUNCNAME(name) (name)
#endif /* LIB_PREFIX */
/*
* If LIB_PREFIX is defined, the following functions will prepend `LIB_PREFIX`
* to all public methods of this library. If LIB_PREFIX is undefined,
* everything stays as is.
*/
#define BLOB_TO_KZG_COMMITMENT PREFIX_FUNCNAME(blob_to_kzg_commitment)
#define COMPUTE_KZG_PROOF PREFIX_FUNCNAME(compute_kzg_proof)
#define COMPUTE_BLOB_KZG_PROOF PREFIX_FUNCNAME(compute_blob_kzg_proof)
#define VERIFY_KZG_PROOF PREFIX_FUNCNAME(verify_kzg_proof)
#define VERIFY_BLOB_KZG_PROOF PREFIX_FUNCNAME(verify_blob_kzg_proof)
#define VERIFY_BLOB_KZG_PROOF_BATCH PREFIX_FUNCNAME(verify_blob_kzg_proof_batch)
#define LOAD_TRUSTED_SETUP PREFIX_FUNCNAME(load_trusted_setup)
#define LOAD_TRUSTED_SETUP_FILE PREFIX_FUNCNAME(load_trusted_setup_file)
#define FREE_TRUSTED_SETUP PREFIX_FUNCNAME(free_trusted_setup)
/* /*
* This value represents the number of field elements in a blob. It must be * This value represents the number of field elements in a blob. It must be
* supplied externally. It is expected to be 4096 for mainnet and 4 for minimal. * supplied externally. It is expected to be 4096 for mainnet and 4 for minimal.
@ -150,7 +176,7 @@ typedef struct {
// Interface functions // Interface functions
/////////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////////
C_KZG_RET load_trusted_setup( C_KZG_RET LOAD_TRUSTED_SETUP(
KZGSettings *out, KZGSettings *out,
const uint8_t *g1_bytes, /* n1 * 48 bytes */ const uint8_t *g1_bytes, /* n1 * 48 bytes */
size_t n1, size_t n1,
@ -158,15 +184,15 @@ C_KZG_RET load_trusted_setup(
size_t n2 size_t n2
); );
C_KZG_RET load_trusted_setup_file(KZGSettings *out, FILE *in); C_KZG_RET LOAD_TRUSTED_SETUP_FILE(KZGSettings *out, FILE *in);
void free_trusted_setup(KZGSettings *s); void FREE_TRUSTED_SETUP(KZGSettings *s);
C_KZG_RET blob_to_kzg_commitment( C_KZG_RET BLOB_TO_KZG_COMMITMENT(
KZGCommitment *out, const Blob *blob, const KZGSettings *s KZGCommitment *out, const Blob *blob, const KZGSettings *s
); );
C_KZG_RET compute_kzg_proof( C_KZG_RET COMPUTE_KZG_PROOF(
KZGProof *proof_out, KZGProof *proof_out,
Bytes32 *y_out, Bytes32 *y_out,
const Blob *blob, const Blob *blob,
@ -174,14 +200,14 @@ C_KZG_RET compute_kzg_proof(
const KZGSettings *s const KZGSettings *s
); );
C_KZG_RET compute_blob_kzg_proof( C_KZG_RET COMPUTE_BLOB_KZG_PROOF(
KZGProof *out, KZGProof *out,
const Blob *blob, const Blob *blob,
const Bytes48 *commitment_bytes, const Bytes48 *commitment_bytes,
const KZGSettings *s const KZGSettings *s
); );
C_KZG_RET verify_kzg_proof( C_KZG_RET VERIFY_KZG_PROOF(
bool *ok, bool *ok,
const Bytes48 *commitment_bytes, const Bytes48 *commitment_bytes,
const Bytes32 *z_bytes, const Bytes32 *z_bytes,
@ -190,7 +216,7 @@ C_KZG_RET verify_kzg_proof(
const KZGSettings *s const KZGSettings *s
); );
C_KZG_RET verify_blob_kzg_proof( C_KZG_RET VERIFY_BLOB_KZG_PROOF(
bool *ok, bool *ok,
const Blob *blob, const Blob *blob,
const Bytes48 *commitment_bytes, const Bytes48 *commitment_bytes,
@ -198,7 +224,7 @@ C_KZG_RET verify_blob_kzg_proof(
const KZGSettings *s const KZGSettings *s
); );
C_KZG_RET verify_blob_kzg_proof_batch( C_KZG_RET VERIFY_BLOB_KZG_PROOF_BATCH(
bool *ok, bool *ok,
const Blob *blobs, const Blob *blobs,
const Bytes48 *commitments_bytes, const Bytes48 *commitments_bytes,