From a3a6c916b236c9e8904090303f0c38ae49db1002 Mon Sep 17 00:00:00 2001 From: kevaundray Date: Thu, 27 Jun 2024 20:17:14 +0100 Subject: [PATCH] Remove proof parameter from `recover_cells_and_kzg_proofs` (#3819) --- specs/_features/eip7594/das-core.md | 3 +- .../polynomial-commitments-sampling.md | 20 ++-- .../test_polynomial_commitments.py | 5 +- .../kzg_7594/recover_cells_and_kzg_proofs.md | 2 +- tests/generators/kzg_7594/main.py | 108 ++++-------------- 5 files changed, 35 insertions(+), 103 deletions(-) diff --git a/specs/_features/eip7594/das-core.md b/specs/_features/eip7594/das-core.md index b2d21d1a0..0d6530226 100644 --- a/specs/_features/eip7594/das-core.md +++ b/specs/_features/eip7594/das-core.md @@ -179,9 +179,8 @@ def recover_matrix(partial_matrix: Sequence[MatrixEntry], for blob_index in range(blob_count): cell_indices = [e.column_index for e in partial_matrix if e.row_index == blob_index] cells = [e.cell for e in partial_matrix if e.row_index == blob_index] - proofs = [e.kzg_proof for e in partial_matrix if e.row_index == blob_index] - recovered_cells, recovered_proofs = recover_cells_and_kzg_proofs(cell_indices, cells, proofs) + recovered_cells, recovered_proofs = recover_cells_and_kzg_proofs(cell_indices, cells) for cell_index, (cell, proof) in enumerate(zip(recovered_cells, recovered_proofs)): extended_matrix.append(MatrixEntry( cell=cell, diff --git a/specs/_features/eip7594/polynomial-commitments-sampling.md b/specs/_features/eip7594/polynomial-commitments-sampling.md index 7be1a4a05..d7090c673 100644 --- a/specs/_features/eip7594/polynomial-commitments-sampling.md +++ b/specs/_features/eip7594/polynomial-commitments-sampling.md @@ -645,8 +645,7 @@ def recover_data(cell_indices: Sequence[CellIndex], ```python def recover_cells_and_kzg_proofs(cell_indices: Sequence[CellIndex], - cells: Sequence[Cell], - proofs_bytes: Sequence[Bytes48]) -> Tuple[ + cells: Sequence[Cell]) -> Tuple[ Vector[Cell, CELLS_PER_EXT_BLOB], Vector[KZGProof, CELLS_PER_EXT_BLOB]]: """ @@ -660,7 +659,7 @@ def recover_cells_and_kzg_proofs(cell_indices: Sequence[CellIndex], Public method. """ - assert len(cell_indices) == len(cells) == len(proofs_bytes) + assert len(cell_indices) == len(cells) # Check we have enough cells to be able to perform the reconstruction assert CELLS_PER_EXT_BLOB / 2 <= len(cell_indices) <= CELLS_PER_EXT_BLOB # Check for duplicates @@ -671,9 +670,6 @@ def recover_cells_and_kzg_proofs(cell_indices: Sequence[CellIndex], # Check that each cell is the correct length for cell in cells: assert len(cell) == BYTES_PER_CELL - # Check that each proof is the correct length - for proof_bytes in proofs_bytes: - assert len(proof_bytes) == BYTES_PER_PROOF # Convert cells to coset evals cosets_evals = [cell_to_coset_evals(cell) for cell in cells] @@ -692,14 +688,12 @@ def recover_cells_and_kzg_proofs(cell_indices: Sequence[CellIndex], polynomial_eval = reconstructed_data[:FIELD_ELEMENTS_PER_BLOB] polynomial_coeff = polynomial_eval_to_coeff(polynomial_eval) recovered_proofs = [None] * CELLS_PER_EXT_BLOB - for i, cell_index in enumerate(cell_indices): - recovered_proofs[cell_index] = bytes_to_kzg_proof(proofs_bytes[i]) + for i in range(CELLS_PER_EXT_BLOB): - if recovered_proofs[i] is None: - coset = coset_for_cell(CellIndex(i)) - proof, ys = compute_kzg_proof_multi_impl(polynomial_coeff, coset) - assert coset_evals_to_cell(ys) == recovered_cells[i] - recovered_proofs[i] = proof + coset = coset_for_cell(CellIndex(i)) + proof, ys = compute_kzg_proof_multi_impl(polynomial_coeff, coset) + assert coset_evals_to_cell(ys) == recovered_cells[i] + recovered_proofs[i] = proof return recovered_cells, recovered_proofs ``` diff --git a/tests/core/pyspec/eth2spec/test/eip7594/unittests/polynomial_commitments/test_polynomial_commitments.py b/tests/core/pyspec/eth2spec/test/eip7594/unittests/polynomial_commitments/test_polynomial_commitments.py index 5bc3a4330..e7f066501 100644 --- a/tests/core/pyspec/eth2spec/test/eip7594/unittests/polynomial_commitments/test_polynomial_commitments.py +++ b/tests/core/pyspec/eth2spec/test/eip7594/unittests/polynomial_commitments/test_polynomial_commitments.py @@ -164,12 +164,11 @@ def test_recover_cells_and_kzg_proofs(spec): while j in cell_indices: j = rng.randint(0, spec.CELLS_PER_EXT_BLOB - 1) cell_indices.append(j) - # Now the cells/proofs themselves + # Now the cells themselves known_cells = [cells[cell_index] for cell_index in cell_indices] - known_proofs = [proofs[cell_index] for cell_index in cell_indices] # Recover the missing cells and proofs - recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, known_cells, known_proofs) + recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, known_cells) recovered_data = [x for xs in recovered_cells for x in xs] # Check that the original data match the non-extended portion of the recovered data diff --git a/tests/formats/kzg_7594/recover_cells_and_kzg_proofs.md b/tests/formats/kzg_7594/recover_cells_and_kzg_proofs.md index 4e839c8ff..37c5950c5 100644 --- a/tests/formats/kzg_7594/recover_cells_and_kzg_proofs.md +++ b/tests/formats/kzg_7594/recover_cells_and_kzg_proofs.md @@ -21,4 +21,4 @@ All byte(s) fields are encoded as strings, hexadecimal encoding, prefixed with ` ## Condition -The `recover_cells_and_kzg_proofs` handler should recover missing cells and proofs, and the result should match the expected `output`. If any cell is invalid (e.g. incorrect length or one of the 32-byte blocks does not represent a BLS field element), any proof is invalid (e.g. not on the curve or not in the G1 subgroup of the BLS curve), or any `cell_index` is invalid (e.g. greater than the number of cells for an extended blob), it should error, i.e. the output should be `null`. +The `recover_cells_and_kzg_proofs` handler should recover missing cells and proofs, and the result should match the expected `output`. If any cell is invalid (e.g. incorrect length or one of the 32-byte blocks does not represent a BLS field element), or any `cell_index` is invalid (e.g. greater than the number of cells for an extended blob), it should error, i.e. the output should be `null`. diff --git a/tests/generators/kzg_7594/main.py b/tests/generators/kzg_7594/main.py index e39b9d64c..428baa566 100644 --- a/tests/generators/kzg_7594/main.py +++ b/tests/generators/kzg_7594/main.py @@ -13,7 +13,6 @@ from eth2spec.test.helpers.typing import SpecForkName from eth2spec.test.utils.kzg_tests import ( CELL_RANDOM_VALID1, CELL_RANDOM_VALID2, - G1, INVALID_BLOBS, INVALID_G1_POINTS, INVALID_INDIVIDUAL_CELL_BYTES, @@ -593,15 +592,14 @@ def case_recover_cells_and_kzg_proofs(): # Valid: No missing cells cells, proofs = VALID_CELLS_AND_PROOFS[0] cell_indices = list(range(spec.CELLS_PER_EXT_BLOB)) - recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, cells, proofs) + recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, cells) assert recovered_cells == cells assert recovered_proofs == proofs - identifier = make_id(cell_indices, cells, proofs) + identifier = make_id(cell_indices, cells) yield f'recover_cells_and_kzg_proofs_case_valid_no_missing_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(cells), - 'proofs': encode_hex_list(proofs), }, 'output': (encode_hex_list(recovered_cells), encode_hex_list(recovered_proofs)) } @@ -610,16 +608,14 @@ def case_recover_cells_and_kzg_proofs(): cells, proofs = VALID_CELLS_AND_PROOFS[1] cell_indices = list(range(0, spec.CELLS_PER_EXT_BLOB, 2)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, partial_cells, partial_proofs) + recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, partial_cells) assert recovered_cells == cells assert recovered_proofs == proofs - identifier = make_id(cell_indices, partial_cells, partial_proofs) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_valid_half_missing_every_other_cell_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': (encode_hex_list(recovered_cells), encode_hex_list(recovered_proofs)) } @@ -628,8 +624,7 @@ def case_recover_cells_and_kzg_proofs(): cells, proofs = VALID_CELLS_AND_PROOFS[2] cell_indices = list(range(0, spec.CELLS_PER_EXT_BLOB // 2)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, partial_cells, partial_proofs) + recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, partial_cells) assert recovered_cells == cells assert recovered_proofs == proofs identifier = make_id(cell_indices, partial_cells) @@ -637,7 +632,6 @@ def case_recover_cells_and_kzg_proofs(): 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': (encode_hex_list(recovered_cells), encode_hex_list(recovered_proofs)) } @@ -646,8 +640,7 @@ def case_recover_cells_and_kzg_proofs(): cells, proofs = VALID_CELLS_AND_PROOFS[3] cell_indices = list(range(spec.CELLS_PER_EXT_BLOB // 2, spec.CELLS_PER_EXT_BLOB)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, partial_cells, partial_proofs) + recovered_cells, recovered_proofs = spec.recover_cells_and_kzg_proofs(cell_indices, partial_cells) assert recovered_cells == cells assert recovered_proofs == proofs identifier = make_id(cell_indices, partial_cells) @@ -655,7 +648,6 @@ def case_recover_cells_and_kzg_proofs(): 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': (encode_hex_list(recovered_cells), encode_hex_list(recovered_proofs)) } @@ -668,95 +660,67 @@ def case_recover_cells_and_kzg_proofs(): 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } # Edge case: More than half missing - cells, proofs = VALID_CELLS_AND_PROOFS[4] + cells, _ = VALID_CELLS_AND_PROOFS[4] cell_indices = list(range(spec.CELLS_PER_EXT_BLOB // 2 - 1)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_more_than_half_missing_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } # Edge case: More cells provided than CELLS_PER_EXT_BLOB - cells, proofs = VALID_CELLS_AND_PROOFS[5] + cells, _ = VALID_CELLS_AND_PROOFS[5] cell_indices = list(range(spec.CELLS_PER_EXT_BLOB)) + [0] partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_more_cells_than_cells_per_ext_blob_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } # Edge case: Invalid cell_index - cells, proofs = VALID_CELLS_AND_PROOFS[6] + cells, _ = VALID_CELLS_AND_PROOFS[6] cell_indices = list(range(spec.CELLS_PER_EXT_BLOB // 2)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] # Replace first cell_index with an invalid value cell_indices[0] = spec.CELLS_PER_EXT_BLOB - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_cell_index_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } # Edge case: Invalid cell for cell in INVALID_INDIVIDUAL_CELL_BYTES: - cells, proofs = VALID_CELLS_AND_PROOFS[6] + cells, _ = VALID_CELLS_AND_PROOFS[6] cell_indices = list(range(spec.CELLS_PER_EXT_BLOB // 2)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] # Replace first cell with an invalid value partial_cells[0] = cell - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_cell_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), - }, - 'output': None - } - - # Edge case: Invalid proof - for proof in INVALID_G1_POINTS: - cells, proofs = VALID_CELLS_AND_PROOFS[0] - cell_indices = list(range(spec.CELLS_PER_EXT_BLOB // 2)) - partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - # Replace first proof with an invalid value - partial_proofs[0] = proof - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) - yield f'recover_cells_and_kzg_proofs_case_invalid_proof_{identifier}', { - 'input': { - 'cell_indices': cell_indices, - 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } @@ -765,16 +729,14 @@ def case_recover_cells_and_kzg_proofs(): cells, proofs = VALID_CELLS_AND_PROOFS[0] cell_indices = list(range(0, spec.CELLS_PER_EXT_BLOB, 2)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] # Add another cell_index cell_indices.append(spec.CELLS_PER_EXT_BLOB - 1) - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_more_cell_indices_than_cells_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } @@ -783,34 +745,14 @@ def case_recover_cells_and_kzg_proofs(): cells, proofs = VALID_CELLS_AND_PROOFS[1] cell_indices = list(range(0, spec.CELLS_PER_EXT_BLOB, 2)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] # Add another cell partial_cells.append(CELL_RANDOM_VALID1) - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_more_cells_than_cell_indices_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), - }, - 'output': None - } - - # Edge case: More proofs than cell_indices - cells, proofs = VALID_CELLS_AND_PROOFS[1] - cell_indices = list(range(0, spec.CELLS_PER_EXT_BLOB, 2)) - partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] - # Add another proof - partial_proofs.append(G1) - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) - yield f'recover_cells_and_kzg_proofs_case_invalid_more_proofs_than_cell_indices_{identifier}', { - 'input': { - 'cell_indices': cell_indices, - 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None } @@ -824,16 +766,14 @@ def case_recover_cells_and_kzg_proofs(): # to insufficient cell count, not because of a duplicate cell. cell_indices = list(range(spec.CELLS_PER_EXT_BLOB // 2 + 1)) partial_cells = [cells[cell_index] for cell_index in cell_indices] - partial_proofs = [proofs[cell_index] for cell_index in cell_indices] # Replace first cell_index with the second cell_index cell_indices[0] = cell_indices[1] - expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells, partial_proofs) - identifier = make_id(cell_indices, partial_cells, partial_proofs) + expect_exception(spec.recover_cells_and_kzg_proofs, cell_indices, partial_cells) + identifier = make_id(cell_indices, partial_cells) yield f'recover_cells_and_kzg_proofs_case_invalid_duplicate_cell_index_{identifier}', { 'input': { 'cell_indices': cell_indices, 'cells': encode_hex_list(partial_cells), - 'proofs': encode_hex_list(partial_proofs), }, 'output': None }