binius_circuits/
pack.rs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
// Copyright 2024-2025 Irreducible Inc.

use anyhow::Result;
use binius_core::oracle::OracleId;
use binius_field::{
	as_packed_field::PackScalar, underlier::UnderlierType, ExtensionField, TowerField,
};

use crate::builder::ConstraintSystemBuilder;

pub fn pack<U, F, FInput, FOutput>(
	oracle_id: OracleId,
	builder: &mut ConstraintSystemBuilder<U, F>,
	name: impl ToString,
) -> Result<OracleId>
where
	F: TowerField + ExtensionField<FInput> + ExtensionField<FOutput>,
	FInput: TowerField,
	FOutput: TowerField + ExtensionField<FInput>,
	U: UnderlierType + PackScalar<F> + PackScalar<FInput> + PackScalar<FOutput>,
{
	if FInput::TOWER_LEVEL == FOutput::TOWER_LEVEL {
		return Ok(oracle_id);
	}

	let packed_id =
		builder.add_packed(name, oracle_id, FOutput::TOWER_LEVEL - FInput::TOWER_LEVEL)?;

	if let Some(witness) = builder.witness() {
		let values_witness = witness.get::<FInput>(oracle_id)?;

		witness.set(packed_id, values_witness.repacked::<FOutput>())?;
	}

	Ok(packed_id)
}