revm_precompile/bls12_381/
g2_add.rs1use super::utils::{pad_g2_point, remove_g2_padding};
3use crate::bls12_381_const::{
4 G2_ADD_ADDRESS, G2_ADD_BASE_GAS_FEE, G2_ADD_INPUT_LENGTH, PADDED_G2_LENGTH,
5};
6use crate::{crypto, PrecompileError, PrecompileOutput, PrecompileResult, PrecompileWithAddress};
7
8pub const PRECOMPILE: PrecompileWithAddress = PrecompileWithAddress(G2_ADD_ADDRESS, g2_add);
10
11pub fn g2_add(input: &[u8], gas_limit: u64) -> PrecompileResult {
18 if G2_ADD_BASE_GAS_FEE > gas_limit {
19 return Err(PrecompileError::OutOfGas);
20 }
21
22 if input.len() != G2_ADD_INPUT_LENGTH {
23 return Err(PrecompileError::Other(format!(
24 "G2ADD input should be {G2_ADD_INPUT_LENGTH} bytes, was {}",
25 input.len()
26 )));
27 }
28
29 let [a_x_0, a_x_1, a_y_0, a_y_1] = remove_g2_padding(&input[..PADDED_G2_LENGTH])?;
31 let [b_x_0, b_x_1, b_y_0, b_y_1] = remove_g2_padding(&input[PADDED_G2_LENGTH..])?;
32
33 let a = (*a_x_0, *a_x_1, *a_y_0, *a_y_1);
34 let b = (*b_x_0, *b_x_1, *b_y_0, *b_y_1);
35
36 let unpadded_result = crypto().bls12_381_g2_add(a, b)?;
37
38 let padded_result = pad_g2_point(&unpadded_result);
40
41 Ok(PrecompileOutput::new(
42 G2_ADD_BASE_GAS_FEE,
43 padded_result.into(),
44 ))
45}