Skip to content

Commit

Permalink
example: Blake3 permutation using channels API (#10)
Browse files Browse the repository at this point in the history
* Support for Karatsuba "infinity" point in evaluation & interpolation domains

* [sumcheck] Small field zerocheck and its HAL support removed

* [ring_switch] Optimize RingSwitchEqInd::multilinear_extension

* [clippy]: avoid needless pass by value

* [math] Fix `fold_right` crash on big multilinears and make it single threaded

* [math] Use specialized zero variable folding in the first sumcheck round.

* [test]: add test coverage for eq_ind_partial_eval

* [test]: add test coverage for inner_product_par

* [test]: test coverage for MultilinearQuery update

* [tracing] Display proof size in graph

* [ci]: Setting Up GitHub Pipelines

* [ci]: Setting Up Mirror to GitLab (#8)

* Fix typos (#2)

[nicetohave] fix typos

* [ci]: Improvements  (IrreducibleOSS#17)

[ci]: Removing continue or error, and depricating Gitlab pipelines

* Improve test compilation time (#10)

Co-authored-by: Dmytro Gordon <[email protected]>

This MR addresses tow issues that make cargo test slow:

Thin LTO slows down compilation of all the crates a bit.
It takes quite a time to compile and link all the examples with test profile which are not actually executed. So I've added an alias to compile and run tests only for fast local usage.

* [serialization] Add canonical serialize/deserialize traits + derive macros

Introduces the following traits:

SerializeCanonical (which replaces most uses of SerializeBytes)
DeserializeCanonical (which replaces most uses of DeserializeBytes)
Conveniently, this also comes with proc-macros for deriving these traits for an arbitrary struct/enum (unions are not supported).

* [security]: Add CODEOWNERS file for GitHub

* [scripts] Added benchmarking script

This adds the script to benchmark various of our examples, default sampling is set to 5 to reduce total time to benchmark.

* [field] Implement PackedField::unzip

* [cleanup]: Remove some useless checked_log_2 calls

* [field] Add TowerField::min_tower_level(self), and use it to derive ArithExpr tower_level from its constants (#6)

In contrast to TowerField::TOWER_LEVEL, TowerField::binary_tower_level(self) returns the smallest tower level that can fit the current value. This can be useful for shrinking field values to the smaller container that fits them, for the purpose of making arithmetic operations (in particular multiplication) cheaper.

* [core]: simplify merkle tree `verify_opening` (IrreducibleOSS#14)

* [ci] Adjusting nightly benchmark repository (IrreducibleOSS#23)

* [ci]: Adjusting nightly benchmark repository
* [ci]: Adjusting CODEOWNERS for .github/ subdir

* [circuits] Simplify usage of ConstraintSystemBuilder by making it less generic (IrreducibleOSS#22)

[circuits] Simplfy ConstraintSystemBuilder to only support BinaryField128b for the top field.

* [field] Simplify usage of PackedExtension, RepackedExtension by making each trait imply its bounds (IrreducibleOSS#24)

* [macros] Remove unused IterOracles, IterPolys derive proc macros (IrreducibleOSS#25)

* [matrix]: simplify scale_row (IrreducibleOSS#31)

* [field] Remove unnecessary `WithUnderlier` trait bound (IrreducibleOSS#32)

* [field] Optimize SIMD element access for Zen4 architecture as well. (IrreducibleOSS#28)

* refactor: Use binary_tower_level for base field detection (IrreducibleOSS#30)

* [serialization] impl SerializeCanonical, DeserializeCanonical for ConstraintSystem (IrreducibleOSS#11)

* [circuits] Optimize plain_lookup using selector flushing (IrreducibleOSS#29)

* [scripts] Remove groestl run from benchmark script (IrreducibleOSS#26)

* [arith_expr]: Statically compile exponentiation in ArithCircuitPoly (IrreducibleOSS#15)

* [serialization] Introduce SerializationMode (IrreducibleOSS#36)

Changes:

Adds SerializaitonMode that specifies whether to use native (fast) or canonical (needed for transcript) serialization/deserializtion. You need to use the same mode for serialization and deserialization.
SerializeCanonical is renamed to SerializeBytes, and takes an extra argument of type SerializationMode
DeserializeCanonical is renamed to DeserializeBytes and takes an extra argument of type SerializationMode
SerializeBytes and DeserializeBytes are now required bounds for the Field trait, rather than being generically implemented for TowerField.
u16, u32, u64, u128 now serialize to/deserialize from little-endian rather than big-endian byte order, to be consistent with BinaryField*b serialization.
The serialization traits are moved back to binius_utils
Automatic implementations of SerializeBytes for Box<T: SerializeBytes> and &(T: SerializeBytes)
Automatic implementation of DeserializeBytes for Box<T: DeserializeBytes>

* [gkr_int_mul] Fix type bounds (IrreducibleOSS#34)

* feat: Blake3 G function gadget (IrreducibleOSS#16)

* [circuits] Add test_circuit helper (IrreducibleOSS#27)

* Leave only the object-safe version of the `CompositionPoly` trait (IrreducibleOSS#43)

* ]field] Byte-sliced fields changes (IrreducibleOSS#21)

* Refactor a bit TowerLevels to remove packed field parameter from the TowerLevel to the Data associated type. This also makes generic bounds a bit more clean, since TowerLevel itself doesn't depend on a concrete packed field type.
* Add support of byte-sliced fields with arbitrary register size, i.e. 128b, 256b, 512b.
* Add shifts and unpack low/high within 128-bit lanes to UnderlierWithBitOps. This allows implementing transposition in an efficient way.
* Add the transparent implementation of UnderlierWithBitOps for PackedScaledUnderlier as we need it to re-use PackedScaledField.

* feat: Add example of LinearCombination column usage

* ci: Add basic Rust CI (#2)

* ci: Add basic Rust CI

* Fix test flags

* example: Linear combination with offset  (#4)

* example: Add linear-combination-with-offset usage example

* chore: Add example for bit masking using LinearCombination

* chore: Add byte decomposition constraint

* example: Implement bit-shifting/rotating and packing (#5)

* example: Add example of Shifted column usage

* example: Add example of Packed column usage

* chore: Add 'unconstrained gadgets' warning

* example: Projected / Repeated columns usage (#6)

* example: Add example of Projected column usage

* example: Add example of Repeated column usage

* example: Add example of ZeroPadded column usage

* examples: Transparent columns usage (part 1) (#8)

* feat: Add example of Transparent (Constant) column usage

* example: Add example of Transparent (Powers) column usage

* example: Add example of Transparent (DisjointProduct) column usage

* example: Add example of Transparent (EqIndPartialEval) column usage

* examples: Transparent columns usage (part 2) (#9)

* example: Add example of Transparent (MultilinearExtensionTransparent) column usage

* example: Add example of Transparent (SelectRow) column usage

* example: Add example of Transparent (ShiftIndPartialEval) column usage

* example: Add example of Transparent (StepDown) column usage

* example: Add example of Transparent (StepUp) column usage

* example: Add example of Transparent (TowerBasis) column usage

* chore: Forward port

* feat: Blake3 permutation using channels API

* chore: Formatting

---------

Co-authored-by: Nikita Lesnikov <[email protected]>
Co-authored-by: Dmitry Gordon <[email protected]>
Co-authored-by: Thomas Coratger <[email protected]>
Co-authored-by: Aliaksei Dziadziuk <[email protected]>
Co-authored-by: Milos Backonja <[email protected]>
Co-authored-by: Milos Backonja <[email protected]>
Co-authored-by: chloefeal <[email protected]>
Co-authored-by: Dmytro Gordon <[email protected]>
Co-authored-by: Tobias Bergkvist <[email protected]>
Co-authored-by: Anex007 <[email protected]>
Co-authored-by: Thomas Coratger <[email protected]>
Co-authored-by: Nikita Lesnikov <[email protected]>
Co-authored-by: Joseph Johnston <[email protected]>
Co-authored-by: Samuel Burnham <[email protected]>
  • Loading branch information
15 people committed Feb 25, 2025
1 parent be6150b commit 0ae1156
Show file tree
Hide file tree
Showing 23 changed files with 191 additions and 206 deletions.
78 changes: 0 additions & 78 deletions .github/workflows/benchmark.yml

This file was deleted.

26 changes: 0 additions & 26 deletions .github/workflows/mirror.yml

This file was deleted.

11 changes: 11 additions & 0 deletions crates/core/src/protocols/gkr_gpa/gpa_sumcheck/prove.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,11 @@ where

impl<'a, F, FDomain, P, Composition, M, Backend> GPAProver<'a, FDomain, P, Composition, M, Backend>
where
<<<<<<< HEAD
F: TowerField + ExtensionField<FDomain>,
=======
F: Field,
>>>>>>> 082235c (example: Blake3 permutation using channels API (#10))
FDomain: Field,
P: PackedFieldIndexable<Scalar = F> + PackedExtension<FDomain>,
Composition: CompositionPoly<P>,
Expand Down Expand Up @@ -99,7 +103,14 @@ where
.map(|claim| claim.composition)
.collect();

<<<<<<< HEAD
let nontrivial_evaluation_points = get_nontrivial_evaluation_points(&domains)?;
=======
let evaluation_points = domains
.iter()
.max_by_key(|domain| domain.size())
.map_or_else(|| Vec::new(), |domain| domain.finite_points().to_vec());
>>>>>>> 082235c (example: Blake3 permutation using channels API (#10))

let state = ProverState::new(
multilinears,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,6 @@ where
.collect();

let nontrivial_evaluation_points = get_nontrivial_evaluation_points(&domains)?;

let state = ProverState::new(
multilinears,
claimed_sums,
Expand Down
10 changes: 7 additions & 3 deletions examples/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -77,9 +77,9 @@ path = "b32_mul.rs"
name = "acc-linear-combination"
path = "acc-linear-combination.rs"

[[example]]
name = "acc-linear-combination-with-offset"
path = "acc-linear-combination-with-offset.rs"
#[[example]]
#name = "acc-linear-combination-with-offset"
#path = "acc-linear-combination-with-offset.rs"

[[example]]
name = "acc-shifted"
Expand Down Expand Up @@ -141,6 +141,10 @@ path = "acc-step-up.rs"
name = "acc-tower-basis"
path = "acc-tower-basis.rs"

[[example]]
name = "acc-permutation-channels"
path = "acc-permutation-channels.rs"

[lints.clippy]
needless_range_loop = "allow"

Expand Down
10 changes: 4 additions & 6 deletions examples/acc-constants.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,7 @@ use binius_core::{
constraint_system::validate::validate_witness, oracle::OracleId,
transparent::constant::Constant,
};
use binius_field::{arch::OptimalUnderlier, BinaryField128b, BinaryField1b, BinaryField32b};

type U = OptimalUnderlier;
type F128 = BinaryField128b;
use binius_field::{BinaryField1b, BinaryField32b};
type F32 = BinaryField32b;
type F1 = BinaryField1b;

Expand All @@ -17,7 +14,7 @@ const LOG_SIZE: usize = 4;
fn constants_gadget(
name: impl ToString,
log_size: usize,
builder: &mut ConstraintSystemBuilder<U, F128>,
builder: &mut ConstraintSystemBuilder,
constant_value: u32,
) -> OracleId {
builder.push_namespace(name);
Expand Down Expand Up @@ -45,7 +42,8 @@ fn constants_gadget(
// Transparent column.
fn main() {
let allocator = bumpalo::Bump::new();
let mut builder = ConstraintSystemBuilder::<U, F128>::new_with_witness(&allocator);

let mut builder = ConstraintSystemBuilder::new_with_witness(&allocator);

pub const SHA256_INIT: [u32; 8] = [
0x6a09e667, 0xbb67ae85, 0x3c6ef372, 0xa54ff53a, 0x510e527f, 0x9b05688c, 0x1f83d9ab,
Expand Down
8 changes: 2 additions & 6 deletions examples/acc-disjoint-product.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,8 @@ use binius_core::{
constraint_system::validate::validate_witness,
transparent::{constant::Constant, disjoint_product::DisjointProduct, powers::Powers},
};
use binius_field::{
arch::OptimalUnderlier, BinaryField, BinaryField128b, BinaryField8b, PackedField,
};
use binius_field::{BinaryField, BinaryField8b, PackedField};

type U = OptimalUnderlier;
type F128 = BinaryField128b;
type F8 = BinaryField8b;

const LOG_SIZE: usize = 4;
Expand All @@ -29,7 +25,7 @@ const LOG_SIZE: usize = 4;
// of heights (n_vars) of Powers and Constant, so actual data could be repeated multiple times
fn main() {
let allocator = bumpalo::Bump::new();
let mut builder = ConstraintSystemBuilder::<U, F128>::new_with_witness(&allocator);
let mut builder = ConstraintSystemBuilder::new_with_witness(&allocator);

let generator = F8::MULTIPLICATIVE_GENERATOR;
let powers = Powers::new(LOG_SIZE, generator.into());
Expand Down
6 changes: 3 additions & 3 deletions examples/acc-eq-ind-partial-eval.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,8 @@ use binius_circuits::builder::ConstraintSystemBuilder;
use binius_core::{
constraint_system::validate::validate_witness, transparent::eq_ind::EqIndPartialEval,
};
use binius_field::{arch::OptimalUnderlier, BinaryField128b, PackedField};
use binius_field::{BinaryField128b, PackedField};

type U = OptimalUnderlier;
type F128 = BinaryField128b;

const LOG_SIZE: usize = 3;
Expand All @@ -21,7 +20,8 @@ const LOG_SIZE: usize = 3;
//
fn main() {
let allocator = bumpalo::Bump::new();
let mut builder = ConstraintSystemBuilder::<U, F128>::new_with_witness(&allocator);

let mut builder = ConstraintSystemBuilder::new_with_witness(&allocator);

// A truth table [000, 001, 010, 011 ... 111] where each row is in reversed order
let rev_basis = [
Expand Down
13 changes: 5 additions & 8 deletions examples/acc-linear-combination.rs
Original file line number Diff line number Diff line change
@@ -1,20 +1,17 @@
use binius_circuits::{builder::ConstraintSystemBuilder, unconstrained::unconstrained};
use binius_core::{constraint_system::validate::validate_witness, oracle::OracleId};
use binius_field::{
arch::OptimalUnderlier, packed::set_packed_slice, BinaryField128b, BinaryField1b,
BinaryField8b, ExtensionField, TowerField,
packed::set_packed_slice, BinaryField1b, BinaryField8b, ExtensionField, TowerField,
};
use binius_macros::arith_expr;

type U = OptimalUnderlier;
type F128 = BinaryField128b;
type F8 = BinaryField8b;
type F1 = BinaryField1b;

// FIXME: Following gadgets are unconstrained. Only for demonstrative purpose, don't use in production

fn bytes_decomposition_gadget(
builder: &mut ConstraintSystemBuilder<U, F128>,
builder: &mut ConstraintSystemBuilder,
name: impl ToString,
log_size: usize,
input: OracleId,
Expand Down Expand Up @@ -146,7 +143,7 @@ fn bytes_decomposition_gadget(
}

fn elder_4bits_masking_gadget(
builder: &mut ConstraintSystemBuilder<U, F128>,
builder: &mut ConstraintSystemBuilder,
name: impl ToString,
log_size: usize,
input: OracleId,
Expand Down Expand Up @@ -241,12 +238,12 @@ fn elder_4bits_masking_gadget(

fn main() {
let allocator = bumpalo::Bump::new();
let mut builder = ConstraintSystemBuilder::<U, F128>::new_with_witness(&allocator);
let mut builder = ConstraintSystemBuilder::new_with_witness(&allocator);

let log_size = 1usize;

// Define set of bytes that we want to decompose
let p_in = unconstrained::<U, F128, F8>(&mut builder, "p_in".to_string(), log_size).unwrap();
let p_in = unconstrained::<F8>(&mut builder, "p_in".to_string(), log_size).unwrap();

let _ =
bytes_decomposition_gadget(&mut builder, "bytes decomposition", log_size, p_in).unwrap();
Expand Down
6 changes: 3 additions & 3 deletions examples/acc-multilinear-extension-transparent.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ type F128 = BinaryField128b;
type F1 = BinaryField1b;

// From a perspective of circuits creation, MultilinearExtensionTransparent can be used naturally for decomposing integers to bits
fn decompose_transparent_u64(builder: &mut ConstraintSystemBuilder<U, F128>, x: u64) {
fn decompose_transparent_u64(builder: &mut ConstraintSystemBuilder, x: u64) {
builder.push_namespace("decompose_transparent_u64");

let log_bits = log2_ceil_usize(64);
Expand Down Expand Up @@ -42,7 +42,7 @@ fn decompose_transparent_u64(builder: &mut ConstraintSystemBuilder<U, F128>, x:
builder.pop_namespace();
}

fn decompose_transparent_u32(builder: &mut ConstraintSystemBuilder<U, F128>, x: u32) {
fn decompose_transparent_u32(builder: &mut ConstraintSystemBuilder, x: u32) {
builder.push_namespace("decompose_transparent_u32");

let log_bits = log2_ceil_usize(32);
Expand Down Expand Up @@ -72,7 +72,7 @@ fn decompose_transparent_u32(builder: &mut ConstraintSystemBuilder<U, F128>, x:

fn main() {
let allocator = bumpalo::Bump::new();
let mut builder = ConstraintSystemBuilder::<U, F128>::new_with_witness(&allocator);
let mut builder = ConstraintSystemBuilder::new_with_witness(&allocator);

decompose_transparent_u64(&mut builder, 0xff00ff00ff00ff00);
decompose_transparent_u32(&mut builder, 0x00ff00ff);
Expand Down
21 changes: 8 additions & 13 deletions examples/acc-packed.rs
Original file line number Diff line number Diff line change
@@ -1,23 +1,18 @@
use binius_circuits::{builder::ConstraintSystemBuilder, unconstrained::unconstrained};
use binius_core::constraint_system::validate::validate_witness;
use binius_field::{
arch::OptimalUnderlier, BinaryField128b, BinaryField16b, BinaryField1b, BinaryField32b,
BinaryField8b, TowerField,
};
use binius_field::{BinaryField16b, BinaryField1b, BinaryField32b, BinaryField8b, TowerField};

type U = OptimalUnderlier;
type F128 = BinaryField128b;
type F32 = BinaryField32b;
type F16 = BinaryField16b;
type F8 = BinaryField8b;
type F1 = BinaryField1b;

// FIXME: Following gadgets are unconstrained. Only for demonstrative purpose, don't use in production

fn packing_32_bits_to_u32(builder: &mut ConstraintSystemBuilder<U, F128>) {
fn packing_32_bits_to_u32(builder: &mut ConstraintSystemBuilder) {
builder.push_namespace("packing_32_bits_to_u32");

let bits = unconstrained::<U, F128, F1>(builder, "bits", F32::TOWER_LEVEL).unwrap();
let bits = unconstrained::<F1>(builder, "bits", F32::TOWER_LEVEL).unwrap();
let packed = builder
.add_packed("packed", bits, F32::TOWER_LEVEL)
.unwrap();
Expand Down Expand Up @@ -49,10 +44,10 @@ fn packing_32_bits_to_u32(builder: &mut ConstraintSystemBuilder<U, F128>) {
builder.pop_namespace();
}

fn packing_4_bytes_to_u32(builder: &mut ConstraintSystemBuilder<U, F128>) {
fn packing_4_bytes_to_u32(builder: &mut ConstraintSystemBuilder) {
builder.push_namespace("packing_4_bytes_to_u32");

let bytes = unconstrained::<U, F128, F8>(builder, "bytes", F16::TOWER_LEVEL).unwrap();
let bytes = unconstrained::<F8>(builder, "bytes", F16::TOWER_LEVEL).unwrap();
let packed = builder
.add_packed("packed", bytes, F16::TOWER_LEVEL)
.unwrap();
Expand All @@ -76,10 +71,10 @@ fn packing_4_bytes_to_u32(builder: &mut ConstraintSystemBuilder<U, F128>) {
builder.pop_namespace();
}

fn packing_8_bits_to_u8(builder: &mut ConstraintSystemBuilder<U, F128>) {
fn packing_8_bits_to_u8(builder: &mut ConstraintSystemBuilder) {
builder.push_namespace("packing_8_bits_to_u8");

let bits = unconstrained::<U, F128, F1>(builder, "bits", F8::TOWER_LEVEL).unwrap();
let bits = unconstrained::<F1>(builder, "bits", F8::TOWER_LEVEL).unwrap();
let packed = builder.add_packed("packed", bits, F8::TOWER_LEVEL).unwrap();

if let Some(witness) = builder.witness() {
Expand All @@ -94,7 +89,7 @@ fn packing_8_bits_to_u8(builder: &mut ConstraintSystemBuilder<U, F128>) {
fn main() {
let allocator = bumpalo::Bump::new();

let mut builder = ConstraintSystemBuilder::<U, F128>::new_with_witness(&allocator);
let mut builder = ConstraintSystemBuilder::new_with_witness(&allocator);

packing_32_bits_to_u32(&mut builder);
packing_4_bytes_to_u32(&mut builder);
Expand Down
Loading

0 comments on commit 0ae1156

Please sign in to comment.