From 46281c28eb7097bfeb4f084da1ef01e93f9a7387 Mon Sep 17 00:00:00 2001 From: nemo Date: Thu, 16 May 2024 16:00:46 -0400 Subject: [PATCH] feat: enforce FIP-0090 bounds on NI-PoRep aggregation counts --- filecoin-proofs/src/api/seal.rs | 19 ++++++++++++++++++- filecoin-proofs/src/constants.rs | 4 ++++ filecoin-proofs/tests/api.rs | 6 +++--- 3 files changed, 25 insertions(+), 4 deletions(-) diff --git a/filecoin-proofs/src/api/seal.rs b/filecoin-proofs/src/api/seal.rs index 95c852323..e4bc95d00 100644 --- a/filecoin-proofs/src/api/seal.rs +++ b/filecoin-proofs/src/api/seal.rs @@ -41,7 +41,9 @@ use crate::{ get_stacked_verifying_key, }, constants::{ - DefaultBinaryTree, DefaultPieceDomain, DefaultPieceHasher, SINGLE_PARTITION_PROOF_LEN, + DefaultBinaryTree, DefaultPieceDomain, DefaultPieceHasher, + FIP90_MAX_NI_POREP_AGGREGATION_PROOFS, FIP90_MIN_NI_POREP_AGGREGATION_PROOFS, + SINGLE_PARTITION_PROOF_LEN, }, parameters::setup_params, pieces::{self, verify_pieces}, @@ -749,6 +751,20 @@ pub fn aggregate_seal_commit_proofs( "cannot aggregate with empty outputs" ); + // Note that the 'normal' case of generating a single + // (non-aggregated) NI-PoRep proof will pass in a single + // commit_output. FIP-0090 aggregation is only considered when + // there are multiple NI-PoRep commit_outputs that are to be + // aggregated together. + if porep_config.feature_enabled(ApiFeature::NonInteractivePoRep) && commit_outputs.len() > 1 { + ensure!( + commit_outputs.len() >= FIP90_MIN_NI_POREP_AGGREGATION_PROOFS + && commit_outputs.len() <= FIP90_MAX_NI_POREP_AGGREGATION_PROOFS, + "{} proofs is outside of FIP-0090 specified NI-PoRep aggregation bounds", + commit_outputs.len() + ); + } + let partitions = usize::from(porep_config.partitions); let verifying_key = get_stacked_verifying_key::(porep_config)?; let mut proofs: Vec<_> = @@ -777,6 +793,7 @@ pub fn aggregate_seal_commit_proofs( target_proofs_len > 1, "cannot aggregate less than two proofs" ); + trace!( "aggregate_seal_commit_proofs will pad proofs to target_len {}", target_proofs_len diff --git a/filecoin-proofs/src/constants.rs b/filecoin-proofs/src/constants.rs index b2d7df7b9..d51be18fc 100644 --- a/filecoin-proofs/src/constants.rs +++ b/filecoin-proofs/src/constants.rs @@ -33,6 +33,10 @@ pub const WINDOW_POST_CHALLENGE_COUNT: usize = 10; pub const MAX_LEGACY_REGISTERED_SEAL_PROOF_ID: u64 = MAX_LEGACY_POREP_REGISTERED_PROOF_ID; +// Constant NI-PoRep aggregation bounds specified in FIP-0090 +pub const FIP90_MIN_NI_POREP_AGGREGATION_PROOFS: usize = 2; +pub const FIP90_MAX_NI_POREP_AGGREGATION_PROOFS: usize = 65; + /// Sector sizes for which parameters are supported. pub const SUPPORTED_SECTOR_SIZES: [u64; 10] = [ SECTOR_SIZE_2_KIB, diff --git a/filecoin-proofs/tests/api.rs b/filecoin-proofs/tests/api.rs index 092b4aefd..2ad5f5824 100644 --- a/filecoin-proofs/tests/api.rs +++ b/filecoin-proofs/tests/api.rs @@ -624,7 +624,7 @@ fn test_seal_proof_aggregation_2kib() -> Result<()> { (1, 5, ApiVersion::V1_1_0, vec![]), (5, 5, ApiVersion::V1_2_0, vec![ApiFeature::SyntheticPoRep]), ( - 257, + 65, 5, ApiVersion::V1_2_0, vec![ApiFeature::NonInteractivePoRep], @@ -653,7 +653,7 @@ fn test_seal_proof_aggregation_4kib() -> Result<()> { (7, 5, ApiVersion::V1_1_0, vec![]), (24, 5, ApiVersion::V1_2_0, vec![ApiFeature::SyntheticPoRep]), ( - 123, + 17, 5, ApiVersion::V1_2_0, vec![ApiFeature::NonInteractivePoRep], @@ -682,7 +682,7 @@ fn test_seal_proof_aggregation_32kib() -> Result<()> { (220, 5, ApiVersion::V1_1_0, vec![]), (500, 5, ApiVersion::V1_2_0, vec![ApiFeature::SyntheticPoRep]), ( - 818, + 5, 5, ApiVersion::V1_2_0, vec![ApiFeature::NonInteractivePoRep],