Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

generating the permutation trace for CpuChip does not consider the different Interaction kind #1930

Closed
2 tasks
gavin-ygy opened this issue Jan 14, 2025 · 1 comment

Comments

@gavin-ygy
Copy link

Component

Other (please describe)

Have you ensured that all of these are up to date?

  • SP1 SDK
  • cargo prove CLI/sp1up

What version of SP1 SDK are you on?

No response

What version of the cargo prove CLI are you on?

No response

Operating System

Linux (Ubuntu)

Describe the bug

Generating the permutation trace for CpuChip does not consider the different Interaction(kind) in the [the latest permutation.rs ](https://github.com/succinctlabs/sp1/blob/dev/crates/stark/src/permutation.rs .)
The CpuChip's sends have different Interactions, but the different interactions(kind) may be used to count the same row[i].
`pub fn populate_permutation_row<F: PrimeField, EF: ExtensionField>(
row: &mut [EF],
preprocessed_row: &[F],
main_row: &[F],
sends: &[Interaction],
receives: &[Interaction],
random_elements: &[EF],
batch_size: usize,
) {
let alpha = random_elements[0];

// Generate the RLC elements to uniquely identify each item in the looked up tuple.
let betas = random_elements[1].powers();

let interaction_chunks = &sends
    .iter()
    .map(|int| (int, true))
    .chain(receives.iter().map(|int| (int, false)))
    .chunks(batch_size);

// Compute the denominators \prod_{i\in B} row_fingerprint(alpha, beta).
for (value, chunk) in row.iter_mut().zip(interaction_chunks) {
    *value = chunk    //the different kind interaction maybe in the same chunk
        .into_iter()
        .map(|(interaction, is_send)| {
            let mut denominator = alpha;
            let mut betas = betas.clone();
            denominator +=
                betas.next().unwrap() * EF::from_canonical_usize(interaction.argument_index());
            for (columns, beta) in interaction.values.iter().zip(betas) {
                denominator += beta * columns.apply::<F, F>(preprocessed_row, main_row);
            }
            let mut mult = interaction.multiplicity.apply::<F, F>(preprocessed_row, main_row);

            if !is_send {
                mult = -mult;
            }

            EF::from_base(mult) / denominator
        })
        .sum();
}

}
`
Steps:

  1. change the fibonacci-script at :
    //let n = 1000u32; //less n, less time to execute it.
    let n = 20u32;

  2. print the sends and receives in the
    pub fn generate_permutation_trace<F: PrimeField, EF: ExtensionField>(
    sends: &[Interaction],
    receives: &[Interaction],
    preprocessed: Option<&RowMajorMatrix>,
    main: &RowMajorMatrix,
    random_elements: &[EF],
    batch_size: usize, //=2
    ) -> (RowMajorMatrix, EF, EF) {
    //...
    let row_range = match scope {
    InteractionScope::Global => {
    0..*grouped_widths.get(&InteractionScope::Global).expect("Expected global scope")
    }
    InteractionScope::Local => {
    let global_perm_width =
    *grouped_widths.get(&InteractionScope::Global).expect("Expected global scope");
    let local_perm_width =
    *grouped_widths.get(&InteractionScope::Local).expect("Expected local scope");
    global_perm_width..global_perm_width + local_perm_width
    }
    };

    println!("generate_permutation_trace, scope:{}, sends:{:?}, receives:{:?}",scope, sends, receives);
    

//...
}
3. print the CPU chip name in stark/src/prover.rs
fn open(
&self,
pk: &StarkProvingKey,
global_data: Option<ShardMainData<SC, Self::DeviceMatrix, Self::DeviceProverData>>,
local_data: ShardMainData<SC, Self::DeviceMatrix, Self::DeviceProverData>,
challenger: &mut ::Challenger,
global_permutation_challenges: &[SC::Challenge],
) -> Result<ShardProof, Self::Error> {
//...
tracing::debug_span!("generate permutation traces").in_scope(|| {
chips
//.par_iter()
//.zip(all_shard_data.par_iter())
.iter()
.zip(all_shard_data.iter())
.map(|(chip, shard_data)| {
tracing::debug!("--------generate permutation traces ,chip.name:{}",chip.name());
let preprocessed_trace =
pk.chip_ordering.get(&chip.name()).map(|&index| &pk.traces[index]);
let (perm_trace, global_sum, local_sum) = chip.generate_permutation_trace(
preprocessed_trace,
shard_data.trace,
&permutation_challenges,
);
//...
}
4. Then , cargo build -r .
5. RUST_LOG=trace ../target/release/fibonacci-script
6. the logs :
�[2m2025-01-14T09:05:43.688358Z�[0m �[34mDEBUG�[0m �[1mprove_core�[0m:�[1mphase 2 prover�[0m:�[1mbatch�[0m:�[1mopening�[0m:�[1mgenerate permutation traces�[0m: --------generate permutation traces ,chip.name:CPU
generate_permutation_trace, scope:Local, sends:[Interaction { kind: Program, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Alu, scope: Local, .. }, Interaction { kind: Syscall, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }], receives:[Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }, Interaction { kind: Memory, scope: Local, .. }]

  1. the first two Interactions's kind is different: Interaction { kind: Program, scope: Local, .. }, Interaction { kind: Byte, scope: Local, .. }
@jtguibas
Copy link
Contributor

This is not an issue because we encode argument_index on the interaction inside the RLC. The argument_index is an integer presenting the interaction kind.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants