mirror of
https://github.com/logos-storage/plonky2.git
synced 2026-01-07 00:03:10 +00:00
Compiles
This commit is contained in:
parent
5caf92a39a
commit
cdea0d9f96
@ -3,6 +3,7 @@ use std::ops::Range;
|
||||
|
||||
use plonky2::field::extension_field::{Extendable, FieldExtension};
|
||||
use plonky2::field::field_types::Field;
|
||||
use plonky2::gates::batchable::MultiOpsGate;
|
||||
use plonky2::gates::gate::Gate;
|
||||
use plonky2::gates::util::StridedConstraintConsumer;
|
||||
use plonky2::hash::hash_types::RichField;
|
||||
@ -242,6 +243,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for InsertionGate<
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for InsertionGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct InsertionGenerator<F: RichField + Extendable<D>, const D: usize> {
|
||||
gate_index: usize,
|
||||
|
||||
@ -2,6 +2,7 @@ use std::ops::Range;
|
||||
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
|
||||
use crate::gates::batchable::BatchableGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::hash::hash_types::RichField;
|
||||
use crate::iop::ext_target::ExtensionTarget;
|
||||
@ -12,7 +13,7 @@ use crate::plonk::circuit_builder::CircuitBuilder;
|
||||
/// with the given size, and whose values are extension field elements, given by input wires.
|
||||
/// Outputs the evaluation of the interpolant at a given (extension field) evaluation point.
|
||||
pub(crate) trait InterpolationGate<F: RichField + Extendable<D>, const D: usize>:
|
||||
Gate<F, D> + Copy
|
||||
BatchableGate<F, D> + Copy
|
||||
{
|
||||
fn new(subgroup_bits: usize) -> Self;
|
||||
|
||||
|
||||
@ -1,6 +1,7 @@
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -151,6 +152,20 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for ArithmeticGate
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for ArithmeticGate {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_ops
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
vec![
|
||||
Target::wire(gate_index, Self::wire_ith_multiplicand_0(i)),
|
||||
Target::wire(gate_index, Self::wire_ith_multiplicand_1(i)),
|
||||
Target::wire(gate_index, Self::wire_ith_addend(i)),
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D> for ArithmeticGate {
|
||||
fn eval_unfiltered_base_packed<P: PackedField<Scalar = F>>(
|
||||
&self,
|
||||
|
||||
@ -3,6 +3,7 @@ use std::ops::Range;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::extension_field::FieldExtension;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -158,6 +159,23 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for ArithmeticExte
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D>
|
||||
for ArithmeticExtensionGate<D>
|
||||
{
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_ops
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
[
|
||||
ExtensionTarget::<D>::from_range(gate_index, Self::wires_ith_multiplicand_0(i)).0,
|
||||
ExtensionTarget::<D>::from_range(gate_index, Self::wires_ith_multiplicand_1(i)).0,
|
||||
ExtensionTarget::<D>::from_range(gate_index, Self::wires_ith_addend(i)).0,
|
||||
]
|
||||
.concat()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
struct ArithmeticExtensionGenerator<F: RichField + Extendable<D>, const D: usize> {
|
||||
gate_index: usize,
|
||||
|
||||
@ -5,6 +5,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -232,6 +233,20 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for U32ArithmeticG
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for U32ArithmeticGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_ops
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
vec![
|
||||
Target::wire(gate_index, self.wire_ith_multiplicand_0(i)),
|
||||
Target::wire(gate_index, self.wire_ith_multiplicand_1(i)),
|
||||
Target::wire(gate_index, self.wire_ith_addend(i)),
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D>
|
||||
for U32ArithmeticGate<F, D>
|
||||
{
|
||||
|
||||
@ -5,6 +5,7 @@ use plonky2_field::field_types::{Field, PrimeField};
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
use plonky2_util::{bits_u64, ceil_div_usize};
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -280,6 +281,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for AssertLessThan
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for AssertLessThanGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D>
|
||||
for AssertLessThanGate<F, D>
|
||||
{
|
||||
|
||||
@ -4,6 +4,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::{Field, PrimeField};
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -135,6 +136,17 @@ impl<F: RichField + Extendable<D>, const D: usize, const B: usize> Gate<F, D> fo
|
||||
1 + self.num_limbs
|
||||
}
|
||||
}
|
||||
impl<F: RichField + Extendable<D>, const D: usize, const B: usize> MultiOpsGate<F, D>
|
||||
for BaseSumGate<B>
|
||||
{
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize, const B: usize> PackedEvaluableBase<F, D>
|
||||
for BaseSumGate<B>
|
||||
|
||||
@ -1,28 +1,94 @@
|
||||
use std::collections::HashMap;
|
||||
use std::hash::Hash;
|
||||
use std::fmt::{Debug, Error, Formatter};
|
||||
use std::hash::{Hash, Hasher};
|
||||
use std::marker::PhantomData;
|
||||
use std::sync::Arc;
|
||||
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::hash::hash_types::RichField;
|
||||
use crate::iop::target::Target;
|
||||
use crate::plonk::circuit_builder::CircuitBuilder;
|
||||
|
||||
pub trait BatchableGate<F: RichField + Extendable<D>, const D: usize>: Gate<F, D> {
|
||||
type Parameters: Copy;
|
||||
|
||||
fn find_available_slot(&self, params: Self::Parameters) -> (usize, usize);
|
||||
|
||||
fn fill_gate(&self, params: Self::Parameters, builder: &mut CircuitBuilder<F, D>);
|
||||
// TODO: It would be nice to have a `Parameters` associated type.
|
||||
fn fill_gate(
|
||||
&self,
|
||||
params: &[F],
|
||||
current_slot: &CurrentSlot<F, D>,
|
||||
builder: &mut CircuitBuilder<F, D>,
|
||||
);
|
||||
}
|
||||
|
||||
pub struct CurrentSlot<F: RichField + Extendable<D>, const D: usize, G: BatchableGate<F, D>> {
|
||||
current_slot: HashMap<G::Parameters, (usize, usize)>,
|
||||
pub struct CurrentSlot<F: RichField + Extendable<D>, const D: usize> {
|
||||
current_slot: HashMap<Vec<F>, (usize, usize)>,
|
||||
}
|
||||
|
||||
// pub struct Yo<F: RichField + Extendable<D>, const D: usize>(
|
||||
// CurrentSlot<F, D, dyn BatchableGate<F, D>>,
|
||||
// );
|
||||
#[derive(Clone)]
|
||||
pub struct GateRef<F: RichField + Extendable<D>, const D: usize>(
|
||||
pub(crate) Arc<dyn BatchableGate<F, D>>,
|
||||
);
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> GateRef<F, D> {
|
||||
pub fn new<G: BatchableGate<F, D>>(gate: G) -> GateRef<F, D> {
|
||||
GateRef(Arc::new(gate))
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PartialEq for GateRef<F, D> {
|
||||
fn eq(&self, other: &Self) -> bool {
|
||||
self.0.id() == other.0.id()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> Hash for GateRef<F, D> {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
self.0.id().hash(state)
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> Eq for GateRef<F, D> {}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> Debug for GateRef<F, D> {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), Error> {
|
||||
write!(f, "{}", self.0.id())
|
||||
}
|
||||
}
|
||||
|
||||
// pub trait SingleOpGate<F: RichField + Extendable<D>, const D: usize>: Gate<F, D> {}
|
||||
// impl<F: RichField + Extendable<D>, G: SingleOpGate<F, D>, const D: usize> MultiOpsGate<F, D> for G {
|
||||
// fn num_ops(&self) -> usize {
|
||||
// 1
|
||||
// }
|
||||
//
|
||||
// fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
// unreachable!()
|
||||
// }
|
||||
// }
|
||||
|
||||
pub trait MultiOpsGate<F: RichField + Extendable<D>, const D: usize>: Gate<F, D> {
|
||||
fn num_ops(&self) -> usize;
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target>;
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, G: MultiOpsGate<F, D>, const D: usize> BatchableGate<F, D>
|
||||
for G
|
||||
{
|
||||
fn fill_gate(
|
||||
&self,
|
||||
params: &[F],
|
||||
current_slot: &CurrentSlot<F, D>,
|
||||
builder: &mut CircuitBuilder<F, D>,
|
||||
) {
|
||||
if let Some(&(gate_index, op)) = current_slot.current_slot.get(params) {
|
||||
let zero = builder.zero();
|
||||
for i in op..self.num_ops() {
|
||||
for dep in self.dependencies_ith_op(gate_index, i) {
|
||||
builder.connect(dep, zero);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -5,6 +5,7 @@ use plonky2_field::field_types::{Field, PrimeField};
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
use plonky2_util::{bits_u64, ceil_div_usize};
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -313,6 +314,26 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for ComparisonGate
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for ComparisonGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
// impl<F: Richfield + Extendable<d>, const D: usize> Singleopgate<f, d> for multiopsgate<f, d> {
|
||||
// fn num_ops(&self) -> usize {
|
||||
// 1
|
||||
// }
|
||||
//
|
||||
// fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
// unreachable!()
|
||||
// }
|
||||
// }
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D>
|
||||
for ComparisonGate<F, D>
|
||||
{
|
||||
|
||||
@ -4,6 +4,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -102,6 +103,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for ConstantGate {
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for ConstantGate {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_consts
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
vec![]
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D> for ConstantGate {
|
||||
fn eval_unfiltered_base_packed<P: PackedField<Scalar = F>>(
|
||||
&self,
|
||||
|
||||
@ -5,6 +5,7 @@ use plonky2_field::field_types::Field;
|
||||
use plonky2_field::ops::Square;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::{BatchableGate, MultiOpsGate};
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -190,6 +191,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for Exponentiation
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for ExponentiationGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D>
|
||||
for ExponentiationGate<F, D>
|
||||
{
|
||||
|
||||
@ -6,6 +6,7 @@ use plonky2_field::batch_util::batch_multiply_inplace;
|
||||
use plonky2_field::extension_field::{Extendable, FieldExtension};
|
||||
use plonky2_field::field_types::Field;
|
||||
|
||||
use crate::gates::batchable::GateRef;
|
||||
use crate::gates::gate_tree::Tree;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -141,35 +142,35 @@ pub trait Gate<F: RichField + Extendable<D>, const D: usize>: 'static + Send + S
|
||||
fn num_constraints(&self) -> usize;
|
||||
}
|
||||
|
||||
/// A wrapper around an `Rc<Gate>` which implements `PartialEq`, `Eq` and `Hash` based on gate IDs.
|
||||
#[derive(Clone)]
|
||||
pub struct GateRef<F: RichField + Extendable<D>, const D: usize>(pub(crate) Arc<dyn Gate<F, D>>);
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> GateRef<F, D> {
|
||||
pub fn new<G: Gate<F, D>>(gate: G) -> GateRef<F, D> {
|
||||
GateRef(Arc::new(gate))
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PartialEq for GateRef<F, D> {
|
||||
fn eq(&self, other: &Self) -> bool {
|
||||
self.0.id() == other.0.id()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> Hash for GateRef<F, D> {
|
||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
self.0.id().hash(state)
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> Eq for GateRef<F, D> {}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> Debug for GateRef<F, D> {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), Error> {
|
||||
write!(f, "{}", self.0.id())
|
||||
}
|
||||
}
|
||||
// /// A wrapper around an `Rc<Gate>` which implements `PartialEq`, `Eq` and `Hash` based on gate IDs.
|
||||
// #[derive(Clone)]
|
||||
// pub struct GateRef<F: RichField + Extendable<D>, const D: usize>(pub(crate) Arc<dyn Gate<F, D>>);
|
||||
//
|
||||
// impl<F: RichField + Extendable<D>, const D: usize> GateRef<F, D> {
|
||||
// pub fn new<G: Gate<F, D>>(gate: G) -> GateRef<F, D> {
|
||||
// GateRef(Arc::new(gate))
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// impl<F: RichField + Extendable<D>, const D: usize> PartialEq for GateRef<F, D> {
|
||||
// fn eq(&self, other: &Self) -> bool {
|
||||
// self.0.id() == other.0.id()
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// impl<F: RichField + Extendable<D>, const D: usize> Hash for GateRef<F, D> {
|
||||
// fn hash<H: Hasher>(&self, state: &mut H) {
|
||||
// self.0.id().hash(state)
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// impl<F: RichField + Extendable<D>, const D: usize> Eq for GateRef<F, D> {}
|
||||
//
|
||||
// impl<F: RichField + Extendable<D>, const D: usize> Debug for GateRef<F, D> {
|
||||
// fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), Error> {
|
||||
// write!(f, "{}", self.0.id())
|
||||
// }
|
||||
// }
|
||||
|
||||
/// A gate along with any constants used to configure it.
|
||||
pub struct GateInstance<F: RichField + Extendable<D>, const D: usize> {
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
use log::debug;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
|
||||
use crate::gates::gate::GateRef;
|
||||
use crate::gates::batchable::GateRef;
|
||||
use crate::hash::hash_types::RichField;
|
||||
|
||||
/// A binary tree where leaves hold some type `T` and other nodes are empty.
|
||||
|
||||
@ -4,6 +4,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -215,6 +216,17 @@ impl<F: RichField + Extendable<D> + GMiMC<WIDTH>, const D: usize, const WIDTH: u
|
||||
gmimc::NUM_ROUNDS + WIDTH + 1
|
||||
}
|
||||
}
|
||||
impl<F: RichField + Extendable<D> + GMiMC<WIDTH>, const D: usize, const WIDTH: usize>
|
||||
MultiOpsGate<F, D> for GMiMCGate<F, D, WIDTH>
|
||||
{
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D> + GMiMC<WIDTH>, const D: usize, const WIDTH: usize>
|
||||
PackedEvaluableBase<F, D> for GMiMCGate<F, D, WIDTH>
|
||||
|
||||
@ -8,6 +8,7 @@ use plonky2_field::polynomial::PolynomialCoeffs;
|
||||
|
||||
use crate::gadgets::interpolation::InterpolationGate;
|
||||
use crate::gadgets::polynomial::PolynomialCoeffsExtAlgebraTarget;
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -202,6 +203,17 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D>
|
||||
self.num_points() * D + D
|
||||
}
|
||||
}
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D>
|
||||
for HighDegreeInterpolationGate<F, D>
|
||||
{
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct InterpolationGenerator<F: RichField + Extendable<D>, const D: usize> {
|
||||
|
||||
@ -9,6 +9,7 @@ use plonky2_field::polynomial::PolynomialCoeffs;
|
||||
|
||||
use crate::gadgets::interpolation::InterpolationGate;
|
||||
use crate::gadgets::polynomial::PolynomialCoeffsExtAlgebraTarget;
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -294,6 +295,18 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for LowDegreeInter
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D>
|
||||
for LowDegreeInterpolationGate<F, D>
|
||||
{
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct InterpolationGenerator<F: RichField + Extendable<D>, const D: usize> {
|
||||
gate_index: usize,
|
||||
|
||||
@ -3,6 +3,7 @@ use std::ops::Range;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::extension_field::FieldExtension;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -145,6 +146,20 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for MulExtensionGa
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for MulExtensionGate<D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_ops
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
[
|
||||
ExtensionTarget::<D>::from_range(gate_index, Self::wires_ith_multiplicand_0(i)).0,
|
||||
ExtensionTarget::<D>::from_range(gate_index, Self::wires_ith_multiplicand_1(i)).0,
|
||||
]
|
||||
.concat()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
struct MulExtensionGenerator<F: RichField + Extendable<D>, const D: usize> {
|
||||
gate_index: usize,
|
||||
|
||||
@ -1,9 +1,11 @@
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::hash::hash_types::RichField;
|
||||
use crate::iop::ext_target::ExtensionTarget;
|
||||
use crate::iop::generator::WitnessGenerator;
|
||||
use crate::iop::target::Target;
|
||||
use crate::plonk::circuit_builder::CircuitBuilder;
|
||||
use crate::plonk::vars::{EvaluationTargets, EvaluationVars, EvaluationVarsBaseBatch};
|
||||
|
||||
@ -56,6 +58,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for NoopGate {
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for NoopGate {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use plonky2_field::goldilocks_field::GoldilocksField;
|
||||
|
||||
@ -3,6 +3,7 @@ use std::marker::PhantomData;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::poseidon_mds::PoseidonMdsGate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -406,6 +407,15 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for PoseidonGate<F
|
||||
+ 4
|
||||
}
|
||||
}
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for PoseidonGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct PoseidonGenerator<F: RichField + Extendable<D> + Poseidon, const D: usize> {
|
||||
|
||||
@ -6,6 +6,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::extension_field::FieldExtension;
|
||||
use plonky2_field::field_types::Field;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -196,6 +197,17 @@ impl<F: RichField + Extendable<D> + Poseidon, const D: usize> Gate<F, D> for Pos
|
||||
SPONGE_WIDTH * D
|
||||
}
|
||||
}
|
||||
impl<F: RichField + Extendable<D> + Poseidon, const D: usize> MultiOpsGate<F, D>
|
||||
for PoseidonMdsGate<F, D>
|
||||
{
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
struct PoseidonMdsGenerator<const D: usize> {
|
||||
|
||||
@ -3,12 +3,14 @@ use std::ops::Range;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
use crate::iop::ext_target::ExtensionTarget;
|
||||
use crate::iop::generator::WitnessGenerator;
|
||||
use crate::iop::target::Target;
|
||||
use crate::plonk::circuit_builder::CircuitBuilder;
|
||||
use crate::plonk::vars::{
|
||||
EvaluationTargets, EvaluationVars, EvaluationVarsBase, EvaluationVarsBaseBatch,
|
||||
@ -87,6 +89,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for PublicInputGat
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for PublicInputGate {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D> for PublicInputGate {
|
||||
fn eval_unfiltered_base_packed<P: PackedField<Scalar = F>>(
|
||||
&self,
|
||||
|
||||
@ -5,6 +5,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -230,6 +231,21 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for RandomAccessGa
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for RandomAccessGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_copies
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
RandomAccessGenerator {
|
||||
gate_index,
|
||||
gate: *self,
|
||||
copy: i,
|
||||
}
|
||||
.dependencies()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D>
|
||||
for RandomAccessGate<F, D>
|
||||
{
|
||||
|
||||
@ -3,6 +3,7 @@ use std::ops::Range;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::extension_field::FieldExtension;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -166,6 +167,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for ReducingGate<D
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for ReducingGate<D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct ReducingGenerator<const D: usize> {
|
||||
gate_index: usize,
|
||||
|
||||
@ -3,6 +3,7 @@ use std::ops::Range;
|
||||
use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::extension_field::FieldExtension;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
use crate::hash::hash_types::RichField;
|
||||
@ -166,6 +167,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for ReducingExtens
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for ReducingExtensionGate<D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
1
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
unreachable!()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
struct ReducingGenerator<const D: usize> {
|
||||
gate_index: usize,
|
||||
|
||||
@ -4,6 +4,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -221,6 +222,22 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for U32Subtraction
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for U32SubtractionGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_ops
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
U32SubtractionGenerator {
|
||||
gate: *self,
|
||||
gate_index,
|
||||
i,
|
||||
_phantom: Default::default(),
|
||||
}
|
||||
.dependencies()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D>
|
||||
for U32SubtractionGate<F, D>
|
||||
{
|
||||
|
||||
@ -5,6 +5,7 @@ use plonky2_field::extension_field::Extendable;
|
||||
use plonky2_field::field_types::Field;
|
||||
use plonky2_field::packed_field::PackedField;
|
||||
|
||||
use crate::gates::batchable::MultiOpsGate;
|
||||
use crate::gates::gate::Gate;
|
||||
use crate::gates::packed_util::PackedEvaluableBase;
|
||||
use crate::gates::util::StridedConstraintConsumer;
|
||||
@ -189,6 +190,16 @@ impl<F: RichField + Extendable<D>, const D: usize> Gate<F, D> for SwitchGate<F,
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> MultiOpsGate<F, D> for SwitchGate<F, D> {
|
||||
fn num_ops(&self) -> usize {
|
||||
self.num_copies
|
||||
}
|
||||
|
||||
fn dependencies_ith_op(&self, gate_index: usize, i: usize) -> Vec<Target> {
|
||||
todo!()
|
||||
}
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> PackedEvaluableBase<F, D> for SwitchGate<F, D> {
|
||||
fn eval_unfiltered_base_packed<P: PackedField<Scalar = F>>(
|
||||
&self,
|
||||
|
||||
@ -18,9 +18,9 @@ use crate::gadgets::arithmetic_u32::U32Target;
|
||||
use crate::gates::arithmetic_base::ArithmeticGate;
|
||||
use crate::gates::arithmetic_extension::ArithmeticExtensionGate;
|
||||
use crate::gates::arithmetic_u32::U32ArithmeticGate;
|
||||
use crate::gates::batchable::{BatchableGate, CurrentSlot};
|
||||
use crate::gates::batchable::{BatchableGate, CurrentSlot, GateRef};
|
||||
use crate::gates::constant::ConstantGate;
|
||||
use crate::gates::gate::{Gate, GateInstance, GateRef, PrefixedGate};
|
||||
use crate::gates::gate::{Gate, GateInstance, PrefixedGate};
|
||||
use crate::gates::gate_tree::Tree;
|
||||
use crate::gates::multiplication_extension::MulExtensionGate;
|
||||
use crate::gates::noop::NoopGate;
|
||||
@ -86,6 +86,8 @@ pub struct CircuitBuilder<F: RichField + Extendable<D>, const D: usize> {
|
||||
|
||||
// yo: Vec<Yo<F, D, dyn Copy>>,
|
||||
batched_gates: BatchedGates<F, D>,
|
||||
|
||||
current_slots: HashMap<GateRef<F, D>, CurrentSlot<F, D>>,
|
||||
}
|
||||
|
||||
impl<F: RichField + Extendable<D>, const D: usize> CircuitBuilder<F, D> {
|
||||
@ -105,6 +107,7 @@ impl<F: RichField + Extendable<D>, const D: usize> CircuitBuilder<F, D> {
|
||||
arithmetic_results: HashMap::new(),
|
||||
targets_to_constants: HashMap::new(),
|
||||
batched_gates: BatchedGates::new(),
|
||||
current_slots: HashMap::new(),
|
||||
};
|
||||
builder.check_config();
|
||||
builder
|
||||
@ -189,7 +192,7 @@ impl<F: RichField + Extendable<D>, const D: usize> CircuitBuilder<F, D> {
|
||||
}
|
||||
|
||||
/// Adds a gate to the circuit, and returns its index.
|
||||
pub fn add_gate<G: Gate<F, D>>(&mut self, gate_type: G, constants: Vec<F>) -> usize {
|
||||
pub fn add_gate<G: BatchableGate<F, D>>(&mut self, gate_type: G, constants: Vec<F>) -> usize {
|
||||
self.check_gate_compatibility(&gate_type);
|
||||
assert_eq!(
|
||||
gate_type.num_constants(),
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user