@aztec/p2p 0.0.1-commit.f2ce05ee → 0.0.1-commit.f81dbcf
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dest/client/factory.d.ts +8 -8
- package/dest/client/factory.d.ts.map +1 -1
- package/dest/client/factory.js +42 -13
- package/dest/client/interface.d.ts +39 -33
- package/dest/client/interface.d.ts.map +1 -1
- package/dest/client/p2p_client.d.ts +37 -50
- package/dest/client/p2p_client.d.ts.map +1 -1
- package/dest/client/p2p_client.js +144 -223
- package/dest/client/test/tx_proposal_collector/proposal_tx_collector_worker.js +6 -7
- package/dest/config.d.ts +47 -11
- package/dest/config.d.ts.map +1 -1
- package/dest/config.js +94 -31
- package/dest/errors/tx-pool.error.d.ts +8 -0
- package/dest/errors/tx-pool.error.d.ts.map +1 -0
- package/dest/errors/tx-pool.error.js +9 -0
- package/dest/index.d.ts +2 -1
- package/dest/index.d.ts.map +1 -1
- package/dest/index.js +1 -0
- package/dest/mem_pools/attestation_pool/attestation_pool.d.ts +21 -12
- package/dest/mem_pools/attestation_pool/attestation_pool.d.ts.map +1 -1
- package/dest/mem_pools/attestation_pool/attestation_pool.js +67 -37
- package/dest/mem_pools/attestation_pool/attestation_pool_test_suite.d.ts +1 -1
- package/dest/mem_pools/attestation_pool/attestation_pool_test_suite.d.ts.map +1 -1
- package/dest/mem_pools/attestation_pool/attestation_pool_test_suite.js +53 -53
- package/dest/mem_pools/attestation_pool/index.d.ts +2 -2
- package/dest/mem_pools/attestation_pool/index.d.ts.map +1 -1
- package/dest/mem_pools/attestation_pool/index.js +1 -1
- package/dest/mem_pools/attestation_pool/mocks.d.ts +2 -2
- package/dest/mem_pools/attestation_pool/mocks.d.ts.map +1 -1
- package/dest/mem_pools/attestation_pool/mocks.js +2 -2
- package/dest/mem_pools/index.d.ts +2 -1
- package/dest/mem_pools/index.d.ts.map +1 -1
- package/dest/mem_pools/interface.d.ts +3 -3
- package/dest/mem_pools/interface.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool/eviction/invalid_txs_after_mining_rule.js +3 -3
- package/dest/mem_pools/tx_pool/priority.d.ts +2 -2
- package/dest/mem_pools/tx_pool/priority.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool/priority.js +4 -4
- package/dest/mem_pools/tx_pool/tx_pool_test_suite.d.ts +1 -1
- package/dest/mem_pools/tx_pool/tx_pool_test_suite.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool/tx_pool_test_suite.js +3 -1
- package/dest/mem_pools/tx_pool_v2/deleted_pool.d.ts +104 -0
- package/dest/mem_pools/tx_pool_v2/deleted_pool.d.ts.map +1 -0
- package/dest/mem_pools/tx_pool_v2/deleted_pool.js +251 -0
- package/dest/mem_pools/tx_pool_v2/eviction/eviction_manager.d.ts +3 -3
- package/dest/mem_pools/tx_pool_v2/eviction/eviction_manager.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/eviction_manager.js +18 -9
- package/dest/mem_pools/tx_pool_v2/eviction/fee_payer_balance_eviction_rule.d.ts +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/fee_payer_balance_eviction_rule.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/fee_payer_balance_eviction_rule.js +5 -2
- package/dest/mem_pools/tx_pool_v2/eviction/fee_payer_balance_pre_add_rule.d.ts +3 -3
- package/dest/mem_pools/tx_pool_v2/eviction/fee_payer_balance_pre_add_rule.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/fee_payer_balance_pre_add_rule.js +12 -4
- package/dest/mem_pools/tx_pool_v2/eviction/index.d.ts +2 -2
- package/dest/mem_pools/tx_pool_v2/eviction/index.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/index.js +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/interfaces.d.ts +54 -5
- package/dest/mem_pools/tx_pool_v2/eviction/interfaces.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/interfaces.js +8 -0
- package/dest/mem_pools/tx_pool_v2/eviction/invalid_txs_after_mining_rule.js +7 -5
- package/dest/mem_pools/tx_pool_v2/eviction/invalid_txs_after_reorg_rule.js +7 -5
- package/dest/mem_pools/tx_pool_v2/eviction/low_priority_eviction_rule.d.ts +2 -2
- package/dest/mem_pools/tx_pool_v2/eviction/low_priority_eviction_rule.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/low_priority_eviction_rule.js +14 -6
- package/dest/mem_pools/tx_pool_v2/eviction/low_priority_pre_add_rule.d.ts +4 -4
- package/dest/mem_pools/tx_pool_v2/eviction/low_priority_pre_add_rule.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/low_priority_pre_add_rule.js +16 -4
- package/dest/mem_pools/tx_pool_v2/eviction/nullifier_conflict_rule.d.ts +3 -3
- package/dest/mem_pools/tx_pool_v2/eviction/nullifier_conflict_rule.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/eviction/nullifier_conflict_rule.js +3 -3
- package/dest/mem_pools/tx_pool_v2/index.d.ts +3 -2
- package/dest/mem_pools/tx_pool_v2/index.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/index.js +2 -1
- package/dest/mem_pools/tx_pool_v2/instrumentation.d.ts +15 -0
- package/dest/mem_pools/tx_pool_v2/instrumentation.d.ts.map +1 -0
- package/dest/mem_pools/tx_pool_v2/instrumentation.js +43 -0
- package/dest/mem_pools/tx_pool_v2/interfaces.d.ts +22 -8
- package/dest/mem_pools/tx_pool_v2/interfaces.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/interfaces.js +4 -1
- package/dest/mem_pools/tx_pool_v2/tx_metadata.d.ts +68 -11
- package/dest/mem_pools/tx_pool_v2/tx_metadata.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/tx_metadata.js +132 -17
- package/dest/mem_pools/tx_pool_v2/tx_pool_indices.d.ts +12 -3
- package/dest/mem_pools/tx_pool_v2/tx_pool_indices.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/tx_pool_indices.js +36 -14
- package/dest/mem_pools/tx_pool_v2/tx_pool_v2.d.ts +9 -4
- package/dest/mem_pools/tx_pool_v2/tx_pool_v2.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/tx_pool_v2.js +11 -6
- package/dest/mem_pools/tx_pool_v2/tx_pool_v2_impl.d.ts +13 -5
- package/dest/mem_pools/tx_pool_v2/tx_pool_v2_impl.d.ts.map +1 -1
- package/dest/mem_pools/tx_pool_v2/tx_pool_v2_impl.js +336 -185
- package/dest/msg_validators/proposal_validator/block_proposal_validator.d.ts +6 -4
- package/dest/msg_validators/proposal_validator/block_proposal_validator.d.ts.map +1 -1
- package/dest/msg_validators/proposal_validator/block_proposal_validator.js +10 -2
- package/dest/msg_validators/proposal_validator/checkpoint_proposal_validator.d.ts +6 -4
- package/dest/msg_validators/proposal_validator/checkpoint_proposal_validator.d.ts.map +1 -1
- package/dest/msg_validators/proposal_validator/checkpoint_proposal_validator.js +16 -2
- package/dest/msg_validators/proposal_validator/proposal_validator.d.ts +13 -8
- package/dest/msg_validators/proposal_validator/proposal_validator.d.ts.map +1 -1
- package/dest/msg_validators/proposal_validator/proposal_validator.js +48 -36
- package/dest/msg_validators/tx_validator/aggregate_tx_validator.d.ts +4 -4
- package/dest/msg_validators/tx_validator/aggregate_tx_validator.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/aggregate_tx_validator.js +3 -3
- package/dest/msg_validators/tx_validator/allowed_public_setup.d.ts +2 -1
- package/dest/msg_validators/tx_validator/allowed_public_setup.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/allowed_public_setup.js +24 -20
- package/dest/msg_validators/tx_validator/allowed_setup_helpers.d.ts +17 -0
- package/dest/msg_validators/tx_validator/allowed_setup_helpers.d.ts.map +1 -0
- package/dest/msg_validators/tx_validator/allowed_setup_helpers.js +24 -0
- package/dest/msg_validators/tx_validator/block_header_validator.d.ts +16 -3
- package/dest/msg_validators/tx_validator/block_header_validator.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/block_header_validator.js +1 -1
- package/dest/msg_validators/tx_validator/contract_instance_validator.d.ts +9 -0
- package/dest/msg_validators/tx_validator/contract_instance_validator.d.ts.map +1 -0
- package/dest/msg_validators/tx_validator/contract_instance_validator.js +48 -0
- package/dest/msg_validators/tx_validator/double_spend_validator.d.ts +13 -3
- package/dest/msg_validators/tx_validator/double_spend_validator.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/double_spend_validator.js +4 -4
- package/dest/msg_validators/tx_validator/factory.d.ts +125 -6
- package/dest/msg_validators/tx_validator/factory.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/factory.js +233 -59
- package/dest/msg_validators/tx_validator/fee_payer_balance.d.ts +1 -1
- package/dest/msg_validators/tx_validator/fee_payer_balance.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/fee_payer_balance.js +6 -2
- package/dest/msg_validators/tx_validator/gas_validator.d.ts +67 -3
- package/dest/msg_validators/tx_validator/gas_validator.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/gas_validator.js +104 -37
- package/dest/msg_validators/tx_validator/index.d.ts +3 -1
- package/dest/msg_validators/tx_validator/index.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/index.js +2 -0
- package/dest/msg_validators/tx_validator/nullifier_cache.d.ts +14 -0
- package/dest/msg_validators/tx_validator/nullifier_cache.d.ts.map +1 -0
- package/dest/msg_validators/tx_validator/nullifier_cache.js +24 -0
- package/dest/msg_validators/tx_validator/phases_validator.d.ts +2 -2
- package/dest/msg_validators/tx_validator/phases_validator.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/phases_validator.js +44 -23
- package/dest/msg_validators/tx_validator/timestamp_validator.d.ts +20 -4
- package/dest/msg_validators/tx_validator/timestamp_validator.d.ts.map +1 -1
- package/dest/msg_validators/tx_validator/timestamp_validator.js +6 -6
- package/dest/services/dummy_service.d.ts +9 -5
- package/dest/services/dummy_service.d.ts.map +1 -1
- package/dest/services/dummy_service.js +7 -4
- package/dest/services/encoding.d.ts +3 -3
- package/dest/services/encoding.d.ts.map +1 -1
- package/dest/services/encoding.js +11 -10
- package/dest/services/gossipsub/topic_score_params.d.ts +18 -6
- package/dest/services/gossipsub/topic_score_params.d.ts.map +1 -1
- package/dest/services/gossipsub/topic_score_params.js +32 -10
- package/dest/services/libp2p/libp2p_service.d.ts +25 -14
- package/dest/services/libp2p/libp2p_service.d.ts.map +1 -1
- package/dest/services/libp2p/libp2p_service.js +158 -123
- package/dest/services/reqresp/batch-tx-requester/batch_tx_requester.d.ts +4 -3
- package/dest/services/reqresp/batch-tx-requester/batch_tx_requester.d.ts.map +1 -1
- package/dest/services/reqresp/batch-tx-requester/batch_tx_requester.js +5 -9
- package/dest/services/reqresp/batch-tx-requester/interface.d.ts +2 -6
- package/dest/services/reqresp/batch-tx-requester/interface.d.ts.map +1 -1
- package/dest/services/reqresp/batch-tx-requester/missing_txs.d.ts +10 -13
- package/dest/services/reqresp/batch-tx-requester/missing_txs.d.ts.map +1 -1
- package/dest/services/reqresp/batch-tx-requester/missing_txs.js +25 -46
- package/dest/services/reqresp/batch-tx-requester/tx_validator.js +2 -2
- package/dest/services/reqresp/interface.d.ts +10 -1
- package/dest/services/reqresp/interface.d.ts.map +1 -1
- package/dest/services/reqresp/interface.js +15 -1
- package/dest/services/reqresp/protocols/block_txs/block_txs_handler.d.ts +3 -3
- package/dest/services/reqresp/protocols/block_txs/block_txs_handler.d.ts.map +1 -1
- package/dest/services/reqresp/protocols/block_txs/block_txs_reqresp.d.ts +7 -1
- package/dest/services/reqresp/protocols/block_txs/block_txs_reqresp.d.ts.map +1 -1
- package/dest/services/reqresp/protocols/block_txs/block_txs_reqresp.js +15 -0
- package/dest/services/reqresp/protocols/tx.d.ts +7 -1
- package/dest/services/reqresp/protocols/tx.d.ts.map +1 -1
- package/dest/services/reqresp/protocols/tx.js +20 -0
- package/dest/services/reqresp/reqresp.d.ts +1 -1
- package/dest/services/reqresp/reqresp.d.ts.map +1 -1
- package/dest/services/reqresp/reqresp.js +11 -4
- package/dest/services/service.d.ts +22 -3
- package/dest/services/service.d.ts.map +1 -1
- package/dest/services/tx_collection/config.d.ts +19 -1
- package/dest/services/tx_collection/config.d.ts.map +1 -1
- package/dest/services/tx_collection/config.js +46 -0
- package/dest/services/tx_collection/fast_tx_collection.d.ts +3 -1
- package/dest/services/tx_collection/fast_tx_collection.d.ts.map +1 -1
- package/dest/services/tx_collection/fast_tx_collection.js +56 -36
- package/dest/services/tx_collection/file_store_tx_collection.d.ts +53 -0
- package/dest/services/tx_collection/file_store_tx_collection.d.ts.map +1 -0
- package/dest/services/tx_collection/file_store_tx_collection.js +167 -0
- package/dest/services/tx_collection/file_store_tx_source.d.ts +37 -0
- package/dest/services/tx_collection/file_store_tx_source.d.ts.map +1 -0
- package/dest/services/tx_collection/file_store_tx_source.js +90 -0
- package/dest/services/tx_collection/index.d.ts +2 -1
- package/dest/services/tx_collection/index.d.ts.map +1 -1
- package/dest/services/tx_collection/index.js +1 -0
- package/dest/services/tx_collection/instrumentation.d.ts +1 -1
- package/dest/services/tx_collection/instrumentation.d.ts.map +1 -1
- package/dest/services/tx_collection/instrumentation.js +2 -1
- package/dest/services/tx_collection/missing_txs_tracker.d.ts +32 -0
- package/dest/services/tx_collection/missing_txs_tracker.d.ts.map +1 -0
- package/dest/services/tx_collection/missing_txs_tracker.js +27 -0
- package/dest/services/tx_collection/proposal_tx_collector.d.ts +7 -6
- package/dest/services/tx_collection/proposal_tx_collector.d.ts.map +1 -1
- package/dest/services/tx_collection/proposal_tx_collector.js +5 -4
- package/dest/services/tx_collection/slow_tx_collection.d.ts +7 -3
- package/dest/services/tx_collection/slow_tx_collection.d.ts.map +1 -1
- package/dest/services/tx_collection/slow_tx_collection.js +60 -26
- package/dest/services/tx_collection/tx_collection.d.ts +23 -10
- package/dest/services/tx_collection/tx_collection.d.ts.map +1 -1
- package/dest/services/tx_collection/tx_collection.js +75 -3
- package/dest/services/tx_collection/tx_collection_sink.d.ts +18 -8
- package/dest/services/tx_collection/tx_collection_sink.d.ts.map +1 -1
- package/dest/services/tx_collection/tx_collection_sink.js +26 -29
- package/dest/services/tx_collection/tx_source.d.ts +8 -3
- package/dest/services/tx_collection/tx_source.d.ts.map +1 -1
- package/dest/services/tx_collection/tx_source.js +19 -2
- package/dest/services/tx_file_store/config.d.ts +1 -3
- package/dest/services/tx_file_store/config.d.ts.map +1 -1
- package/dest/services/tx_file_store/config.js +0 -4
- package/dest/services/tx_file_store/tx_file_store.d.ts +4 -3
- package/dest/services/tx_file_store/tx_file_store.d.ts.map +1 -1
- package/dest/services/tx_file_store/tx_file_store.js +9 -6
- package/dest/services/tx_provider.d.ts +4 -4
- package/dest/services/tx_provider.d.ts.map +1 -1
- package/dest/services/tx_provider.js +9 -8
- package/dest/test-helpers/make-test-p2p-clients.d.ts +7 -8
- package/dest/test-helpers/make-test-p2p-clients.d.ts.map +1 -1
- package/dest/test-helpers/make-test-p2p-clients.js +1 -2
- package/dest/test-helpers/mock-pubsub.d.ts +30 -4
- package/dest/test-helpers/mock-pubsub.d.ts.map +1 -1
- package/dest/test-helpers/mock-pubsub.js +105 -4
- package/dest/test-helpers/reqresp-nodes.d.ts +2 -3
- package/dest/test-helpers/reqresp-nodes.d.ts.map +1 -1
- package/dest/test-helpers/reqresp-nodes.js +2 -2
- package/dest/test-helpers/testbench-utils.d.ts +35 -24
- package/dest/test-helpers/testbench-utils.d.ts.map +1 -1
- package/dest/test-helpers/testbench-utils.js +95 -36
- package/dest/testbench/p2p_client_testbench_worker.d.ts +2 -2
- package/dest/testbench/p2p_client_testbench_worker.d.ts.map +1 -1
- package/dest/testbench/p2p_client_testbench_worker.js +16 -15
- package/dest/testbench/worker_client_manager.d.ts +3 -1
- package/dest/testbench/worker_client_manager.d.ts.map +1 -1
- package/dest/testbench/worker_client_manager.js +4 -1
- package/dest/util.d.ts +2 -2
- package/dest/util.d.ts.map +1 -1
- package/package.json +14 -14
- package/src/client/factory.ts +77 -23
- package/src/client/interface.ts +43 -33
- package/src/client/p2p_client.ts +165 -265
- package/src/client/test/tx_proposal_collector/proposal_tx_collector_worker.ts +19 -10
- package/src/config.ts +139 -33
- package/src/errors/tx-pool.error.ts +12 -0
- package/src/index.ts +1 -0
- package/src/mem_pools/attestation_pool/attestation_pool.ts +95 -44
- package/src/mem_pools/attestation_pool/attestation_pool_test_suite.ts +57 -53
- package/src/mem_pools/attestation_pool/index.ts +3 -3
- package/src/mem_pools/attestation_pool/mocks.ts +2 -1
- package/src/mem_pools/index.ts +3 -0
- package/src/mem_pools/interface.ts +2 -2
- package/src/mem_pools/tx_pool/README.md +1 -1
- package/src/mem_pools/tx_pool/eviction/invalid_txs_after_mining_rule.ts +3 -3
- package/src/mem_pools/tx_pool/priority.ts +4 -4
- package/src/mem_pools/tx_pool/tx_pool_test_suite.ts +3 -1
- package/src/mem_pools/tx_pool_v2/README.md +85 -11
- package/src/mem_pools/tx_pool_v2/deleted_pool.ts +321 -0
- package/src/mem_pools/tx_pool_v2/eviction/eviction_manager.ts +21 -8
- package/src/mem_pools/tx_pool_v2/eviction/fee_payer_balance_eviction_rule.ts +5 -2
- package/src/mem_pools/tx_pool_v2/eviction/fee_payer_balance_pre_add_rule.ts +18 -4
- package/src/mem_pools/tx_pool_v2/eviction/index.ts +4 -0
- package/src/mem_pools/tx_pool_v2/eviction/interfaces.ts +59 -4
- package/src/mem_pools/tx_pool_v2/eviction/invalid_txs_after_mining_rule.ts +5 -5
- package/src/mem_pools/tx_pool_v2/eviction/invalid_txs_after_reorg_rule.ts +5 -5
- package/src/mem_pools/tx_pool_v2/eviction/low_priority_eviction_rule.ts +14 -9
- package/src/mem_pools/tx_pool_v2/eviction/low_priority_pre_add_rule.ts +33 -6
- package/src/mem_pools/tx_pool_v2/eviction/nullifier_conflict_rule.ts +4 -3
- package/src/mem_pools/tx_pool_v2/index.ts +2 -1
- package/src/mem_pools/tx_pool_v2/instrumentation.ts +69 -0
- package/src/mem_pools/tx_pool_v2/interfaces.ts +23 -8
- package/src/mem_pools/tx_pool_v2/tx_metadata.ts +189 -23
- package/src/mem_pools/tx_pool_v2/tx_pool_indices.ts +43 -16
- package/src/mem_pools/tx_pool_v2/tx_pool_v2.ts +18 -7
- package/src/mem_pools/tx_pool_v2/tx_pool_v2_impl.ts +379 -182
- package/src/msg_validators/proposal_validator/block_proposal_validator.ts +14 -4
- package/src/msg_validators/proposal_validator/checkpoint_proposal_validator.ts +20 -7
- package/src/msg_validators/proposal_validator/proposal_validator.ts +63 -40
- package/src/msg_validators/tx_validator/README.md +115 -0
- package/src/msg_validators/tx_validator/aggregate_tx_validator.ts +5 -5
- package/src/msg_validators/tx_validator/allowed_public_setup.ts +22 -27
- package/src/msg_validators/tx_validator/allowed_setup_helpers.ts +31 -0
- package/src/msg_validators/tx_validator/block_header_validator.ts +15 -3
- package/src/msg_validators/tx_validator/contract_instance_validator.ts +56 -0
- package/src/msg_validators/tx_validator/double_spend_validator.ts +11 -6
- package/src/msg_validators/tx_validator/factory.ts +373 -77
- package/src/msg_validators/tx_validator/fee_payer_balance.ts +6 -2
- package/src/msg_validators/tx_validator/gas_validator.ts +123 -27
- package/src/msg_validators/tx_validator/index.ts +2 -0
- package/src/msg_validators/tx_validator/nullifier_cache.ts +30 -0
- package/src/msg_validators/tx_validator/phases_validator.ts +51 -26
- package/src/msg_validators/tx_validator/timestamp_validator.ts +23 -18
- package/src/services/dummy_service.ts +12 -6
- package/src/services/encoding.ts +9 -9
- package/src/services/gossipsub/README.md +29 -14
- package/src/services/gossipsub/topic_score_params.ts +49 -13
- package/src/services/libp2p/libp2p_service.ts +170 -132
- package/src/services/reqresp/batch-tx-requester/batch_tx_requester.ts +6 -6
- package/src/services/reqresp/batch-tx-requester/interface.ts +1 -5
- package/src/services/reqresp/batch-tx-requester/missing_txs.ts +23 -71
- package/src/services/reqresp/batch-tx-requester/tx_validator.ts +2 -2
- package/src/services/reqresp/interface.ts +26 -1
- package/src/services/reqresp/protocols/block_txs/block_txs_handler.ts +2 -2
- package/src/services/reqresp/protocols/block_txs/block_txs_reqresp.ts +17 -0
- package/src/services/reqresp/protocols/tx.ts +22 -0
- package/src/services/reqresp/reqresp.ts +13 -3
- package/src/services/service.ts +31 -2
- package/src/services/tx_collection/config.ts +68 -0
- package/src/services/tx_collection/fast_tx_collection.ts +65 -32
- package/src/services/tx_collection/file_store_tx_collection.ts +202 -0
- package/src/services/tx_collection/file_store_tx_source.ts +117 -0
- package/src/services/tx_collection/index.ts +1 -0
- package/src/services/tx_collection/instrumentation.ts +7 -1
- package/src/services/tx_collection/missing_txs_tracker.ts +52 -0
- package/src/services/tx_collection/proposal_tx_collector.ts +8 -7
- package/src/services/tx_collection/slow_tx_collection.ts +66 -33
- package/src/services/tx_collection/tx_collection.ts +113 -16
- package/src/services/tx_collection/tx_collection_sink.ts +30 -34
- package/src/services/tx_collection/tx_source.ts +22 -3
- package/src/services/tx_file_store/config.ts +0 -6
- package/src/services/tx_file_store/tx_file_store.ts +10 -8
- package/src/services/tx_provider.ts +10 -9
- package/src/test-helpers/make-test-p2p-clients.ts +3 -5
- package/src/test-helpers/mock-pubsub.ts +146 -9
- package/src/test-helpers/reqresp-nodes.ts +2 -5
- package/src/test-helpers/testbench-utils.ts +109 -40
- package/src/testbench/p2p_client_testbench_worker.ts +24 -20
- package/src/testbench/worker_client_manager.ts +11 -4
- package/src/util.ts +7 -1
- package/dest/msg_validators/proposal_validator/proposal_validator_test_suite.d.ts +0 -23
- package/dest/msg_validators/proposal_validator/proposal_validator_test_suite.d.ts.map +0 -1
- package/dest/msg_validators/proposal_validator/proposal_validator_test_suite.js +0 -212
- package/src/msg_validators/proposal_validator/proposal_validator_test_suite.ts +0 -230
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import type { EpochCacheInterface } from '@aztec/epoch-cache';
|
|
2
2
|
import { BlockNumber, type SlotNumber } from '@aztec/foundation/branded-types';
|
|
3
|
-
import {
|
|
3
|
+
import { maxBy } from '@aztec/foundation/collection';
|
|
4
4
|
import { Fr } from '@aztec/foundation/curves/bn254';
|
|
5
5
|
import { type Logger, createLibp2pComponentLogger, createLogger } from '@aztec/foundation/log';
|
|
6
6
|
import { RunningPromise } from '@aztec/foundation/running-promise';
|
|
@@ -17,13 +17,13 @@ import {
|
|
|
17
17
|
CheckpointProposal,
|
|
18
18
|
type CheckpointProposalCore,
|
|
19
19
|
type Gossipable,
|
|
20
|
-
P2PClientType,
|
|
21
20
|
P2PMessage,
|
|
22
21
|
type ValidationResult as P2PValidationResult,
|
|
23
22
|
PeerErrorSeverity,
|
|
23
|
+
PeerErrorSeverityByHarshness,
|
|
24
24
|
TopicType,
|
|
25
25
|
createTopicString,
|
|
26
|
-
|
|
26
|
+
getTopicsForConfig,
|
|
27
27
|
metricsTopicStrToLabels,
|
|
28
28
|
} from '@aztec/stdlib/p2p';
|
|
29
29
|
import { MerkleTreeId } from '@aztec/stdlib/trees';
|
|
@@ -70,9 +70,11 @@ import {
|
|
|
70
70
|
} from '../../msg_validators/index.js';
|
|
71
71
|
import { MessageSeenValidator } from '../../msg_validators/msg_seen_validator/msg_seen_validator.js';
|
|
72
72
|
import {
|
|
73
|
-
type
|
|
74
|
-
|
|
75
|
-
|
|
73
|
+
type TransactionValidator,
|
|
74
|
+
createFirstStageTxValidationsForGossipedTransactions,
|
|
75
|
+
createSecondStageTxValidationsForGossipedTransactions,
|
|
76
|
+
createTxValidatorForBlockProposalReceivedTxs,
|
|
77
|
+
createTxValidatorForReqResponseReceivedTxs,
|
|
76
78
|
} from '../../msg_validators/tx_validator/factory.js';
|
|
77
79
|
import { GossipSubEvent } from '../../types/index.js';
|
|
78
80
|
import { type PubSubLibp2p, convertToMultiaddr } from '../../util.js';
|
|
@@ -88,6 +90,9 @@ import { PeerScoring } from '../peer-manager/peer_scoring.js';
|
|
|
88
90
|
import type { BatchTxRequesterLibP2PService } from '../reqresp/batch-tx-requester/interface.js';
|
|
89
91
|
import type { P2PReqRespConfig } from '../reqresp/config.js';
|
|
90
92
|
import {
|
|
93
|
+
AuthRequest,
|
|
94
|
+
BlockTxsRequest,
|
|
95
|
+
BlockTxsResponse,
|
|
91
96
|
DEFAULT_SUB_PROTOCOL_VALIDATORS,
|
|
92
97
|
type ReqRespInterface,
|
|
93
98
|
type ReqRespResponse,
|
|
@@ -95,14 +100,9 @@ import {
|
|
|
95
100
|
type ReqRespSubProtocolHandler,
|
|
96
101
|
type ReqRespSubProtocolHandlers,
|
|
97
102
|
type ReqRespSubProtocolValidators,
|
|
103
|
+
StatusMessage,
|
|
98
104
|
type SubProtocolMap,
|
|
99
105
|
ValidationError,
|
|
100
|
-
} from '../reqresp/index.js';
|
|
101
|
-
import {
|
|
102
|
-
AuthRequest,
|
|
103
|
-
BlockTxsRequest,
|
|
104
|
-
BlockTxsResponse,
|
|
105
|
-
StatusMessage,
|
|
106
106
|
pingHandler,
|
|
107
107
|
reqGoodbyeHandler,
|
|
108
108
|
reqRespBlockHandler,
|
|
@@ -114,6 +114,7 @@ import { ReqResp } from '../reqresp/reqresp.js';
|
|
|
114
114
|
import type {
|
|
115
115
|
P2PBlockReceivedCallback,
|
|
116
116
|
P2PCheckpointReceivedCallback,
|
|
117
|
+
P2PDuplicateAttestationCallback,
|
|
117
118
|
P2PService,
|
|
118
119
|
PeerDiscoveryService,
|
|
119
120
|
} from '../service.js';
|
|
@@ -135,7 +136,7 @@ type ReceivedMessageValidationResult<T, M = undefined> =
|
|
|
135
136
|
/**
|
|
136
137
|
* Lib P2P implementation of the P2PService interface.
|
|
137
138
|
*/
|
|
138
|
-
export class LibP2PService
|
|
139
|
+
export class LibP2PService extends WithTracer implements P2PService {
|
|
139
140
|
private discoveryRunningPromise?: RunningPromise;
|
|
140
141
|
private msgIdSeenValidators: Record<TopicType, MessageSeenValidator> = {} as Record<TopicType, MessageSeenValidator>;
|
|
141
142
|
|
|
@@ -156,6 +157,9 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
156
157
|
type: 'checkpoint' | 'block';
|
|
157
158
|
}) => void;
|
|
158
159
|
|
|
160
|
+
/** Callback invoked when a duplicate attestation is detected (triggers slashing). */
|
|
161
|
+
private duplicateAttestationCallback?: P2PDuplicateAttestationCallback;
|
|
162
|
+
|
|
159
163
|
/**
|
|
160
164
|
* Callback for when a block is received from a peer.
|
|
161
165
|
* @param block - The block received from the peer.
|
|
@@ -179,7 +183,6 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
179
183
|
protected logger: Logger;
|
|
180
184
|
|
|
181
185
|
constructor(
|
|
182
|
-
private clientType: T,
|
|
183
186
|
private config: P2PConfig,
|
|
184
187
|
protected node: PubSubLibp2p,
|
|
185
188
|
private peerDiscoveryService: PeerDiscoveryService,
|
|
@@ -221,10 +224,12 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
221
224
|
this.protocolVersion,
|
|
222
225
|
);
|
|
223
226
|
|
|
224
|
-
|
|
225
|
-
this.checkpointProposalValidator = new CheckpointProposalValidator(epochCache, {
|
|
227
|
+
const proposalValidatorOpts = {
|
|
226
228
|
txsPermitted: !config.disableTransactions,
|
|
227
|
-
|
|
229
|
+
maxTxsPerBlock: config.validateMaxTxsPerBlock ?? config.validateMaxTxsPerCheckpoint,
|
|
230
|
+
};
|
|
231
|
+
this.blockProposalValidator = new BlockProposalValidator(epochCache, proposalValidatorOpts);
|
|
232
|
+
this.checkpointProposalValidator = new CheckpointProposalValidator(epochCache, proposalValidatorOpts);
|
|
228
233
|
this.checkpointAttestationValidator = config.fishermanMode
|
|
229
234
|
? new FishermanAttestationValidator(epochCache, mempools.attestationPool, telemetry)
|
|
230
235
|
: new CheckpointAttestationValidator(epochCache);
|
|
@@ -232,11 +237,11 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
232
237
|
this.gossipSubEventHandler = this.handleGossipSubEvent.bind(this);
|
|
233
238
|
|
|
234
239
|
this.blockReceivedCallback = async (block: BlockProposal): Promise<boolean> => {
|
|
235
|
-
this.logger.
|
|
236
|
-
`Handler not yet registered
|
|
240
|
+
this.logger.warn(
|
|
241
|
+
`Handler for block received not yet registered on P2P service. Received block ${block.blockNumber} for slot ${block.slotNumber} from peer.`,
|
|
237
242
|
{ p2pMessageIdentifier: await block.p2pMessageLoggingIdentifier() },
|
|
238
243
|
);
|
|
239
|
-
return
|
|
244
|
+
return true;
|
|
240
245
|
};
|
|
241
246
|
|
|
242
247
|
this.checkpointReceivedCallback = (
|
|
@@ -259,8 +264,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
259
264
|
* @param txPool - The transaction pool to be accessed by the service.
|
|
260
265
|
* @returns The new service.
|
|
261
266
|
*/
|
|
262
|
-
public static async new
|
|
263
|
-
clientType: T,
|
|
267
|
+
public static async new(
|
|
264
268
|
config: P2PConfig,
|
|
265
269
|
peerId: PeerId,
|
|
266
270
|
deps: {
|
|
@@ -338,6 +342,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
338
342
|
heartbeatIntervalMs: config.gossipsubInterval,
|
|
339
343
|
targetCommitteeSize: l1Constants.targetCommitteeSize,
|
|
340
344
|
blockDurationMs: config.blockDurationMs,
|
|
345
|
+
expectedBlockProposalsPerSlot: config.expectedBlockProposalsPerSlot,
|
|
341
346
|
});
|
|
342
347
|
|
|
343
348
|
const node = await createLibp2p({
|
|
@@ -471,7 +476,6 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
471
476
|
peerManager.shouldDisableP2PGossip(peerId) ? -Infinity : peerManager.getPeerScore(peerId);
|
|
472
477
|
|
|
473
478
|
return new LibP2PService(
|
|
474
|
-
clientType,
|
|
475
479
|
config,
|
|
476
480
|
node,
|
|
477
481
|
peerDiscoveryService,
|
|
@@ -545,7 +549,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
545
549
|
await this.node.start();
|
|
546
550
|
|
|
547
551
|
// Subscribe to standard GossipSub topics by default
|
|
548
|
-
for (const topic of
|
|
552
|
+
for (const topic of getTopicsForConfig(this.config.disableTransactions)) {
|
|
549
553
|
this.subscribeToTopic(this.topicStrings[topic]);
|
|
550
554
|
}
|
|
551
555
|
|
|
@@ -611,6 +615,10 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
611
615
|
return this.peerManager.getPeers(includePending);
|
|
612
616
|
}
|
|
613
617
|
|
|
618
|
+
public getGossipMeshPeerCount(topicType: TopicType): number {
|
|
619
|
+
return this.node.services.pubsub.getMeshPeers(this.topicStrings[topicType]).length;
|
|
620
|
+
}
|
|
621
|
+
|
|
614
622
|
private handleGossipSubEvent(e: CustomEvent<GossipsubMessage>) {
|
|
615
623
|
this.logger.trace(`Received PUBSUB message.`);
|
|
616
624
|
|
|
@@ -673,6 +681,15 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
673
681
|
this.duplicateProposalCallback = callback;
|
|
674
682
|
}
|
|
675
683
|
|
|
684
|
+
/**
|
|
685
|
+
* Registers a callback to be invoked when a duplicate attestation is detected.
|
|
686
|
+
* A validator signing attestations for different proposals at the same slot.
|
|
687
|
+
* This callback is triggered on the first duplicate (when count goes from 1 to 2).
|
|
688
|
+
*/
|
|
689
|
+
public registerDuplicateAttestationCallback(callback: P2PDuplicateAttestationCallback): void {
|
|
690
|
+
this.duplicateAttestationCallback = callback;
|
|
691
|
+
}
|
|
692
|
+
|
|
676
693
|
/**
|
|
677
694
|
* Subscribes to a topic.
|
|
678
695
|
* @param topic - The topic to subscribe to.
|
|
@@ -801,9 +818,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
801
818
|
if (msg.topic === this.topicStrings[TopicType.tx]) {
|
|
802
819
|
await this.handleGossipedTx(p2pMessage.payload, msgId, source);
|
|
803
820
|
} else if (msg.topic === this.topicStrings[TopicType.checkpoint_attestation]) {
|
|
804
|
-
|
|
805
|
-
await this.processCheckpointAttestationFromPeer(p2pMessage.payload, msgId, source);
|
|
806
|
-
}
|
|
821
|
+
await this.processCheckpointAttestationFromPeer(p2pMessage.payload, msgId, source);
|
|
807
822
|
} else if (msg.topic === this.topicStrings[TopicType.block_proposal]) {
|
|
808
823
|
await this.processBlockFromPeer(p2pMessage.payload, msgId, source);
|
|
809
824
|
} else if (msg.topic === this.topicStrings[TopicType.checkpoint_proposal]) {
|
|
@@ -889,21 +904,63 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
889
904
|
protected async handleGossipedTx(payloadData: Buffer, msgId: string, source: PeerId) {
|
|
890
905
|
const validationFunc: () => Promise<ReceivedMessageValidationResult<Tx>> = async () => {
|
|
891
906
|
const tx = Tx.fromBuffer(payloadData);
|
|
892
|
-
|
|
893
|
-
const
|
|
907
|
+
|
|
908
|
+
const currentBlockNumber = await this.archiver.getBlockNumber();
|
|
909
|
+
const { ts: nextSlotTimestamp } = this.epochCache.getEpochAndSlotInNextL1Slot();
|
|
910
|
+
|
|
911
|
+
// Stage 1: fast validators (metadata, data, timestamps, double-spend, gas, phases, block header)
|
|
912
|
+
const firstStageValidators = await this.createFirstStageMessageValidators(currentBlockNumber, nextSlotTimestamp);
|
|
913
|
+
const firstStageOutcome = await this.runValidations(tx, firstStageValidators);
|
|
914
|
+
if (!firstStageOutcome.allPassed) {
|
|
915
|
+
const { name } = firstStageOutcome.failure;
|
|
916
|
+
let { severity } = firstStageOutcome.failure;
|
|
917
|
+
|
|
918
|
+
// Double spend validator has a special case handler. We perform more detailed examination
|
|
919
|
+
// as to how recently the nullifier was entered into the tree and if the transaction should
|
|
920
|
+
// have 'known' the nullifier existed. This determines the severity of the penalty applied to the peer.
|
|
921
|
+
if (name === 'doubleSpendValidator') {
|
|
922
|
+
const txBlockNumber = BlockNumber(currentBlockNumber + 1);
|
|
923
|
+
severity = await this.handleDoubleSpendFailure(tx, txBlockNumber);
|
|
924
|
+
}
|
|
925
|
+
|
|
926
|
+
this.peerManager.penalizePeer(source, severity);
|
|
927
|
+
return { result: TopicValidatorResult.Reject };
|
|
928
|
+
}
|
|
929
|
+
|
|
930
|
+
// Pool pre-check: see if the pool would accept this tx before doing expensive proof verification
|
|
931
|
+
const canAdd = await this.mempools.txPool.canAddPendingTx(tx);
|
|
932
|
+
if (canAdd === 'ignored') {
|
|
933
|
+
return { result: TopicValidatorResult.Ignore, obj: tx };
|
|
934
|
+
}
|
|
935
|
+
|
|
936
|
+
// Stage 2: expensive proof verification
|
|
937
|
+
const secondStageValidators = this.createSecondStageMessageValidators();
|
|
938
|
+
const secondStageOutcome = await this.runValidations(tx, secondStageValidators);
|
|
939
|
+
if (!secondStageOutcome.allPassed) {
|
|
940
|
+
const { severity } = secondStageOutcome.failure;
|
|
941
|
+
this.peerManager.penalizePeer(source, severity);
|
|
942
|
+
return { result: TopicValidatorResult.Reject };
|
|
943
|
+
}
|
|
944
|
+
|
|
945
|
+
// Pool add: persist the tx
|
|
946
|
+
const txHash = tx.getTxHash();
|
|
947
|
+
const addResult = await this.mempools.txPool.addPendingTxs([tx], { source: 'gossip' });
|
|
948
|
+
|
|
949
|
+
const wasAccepted = addResult.accepted.some(h => h.equals(txHash));
|
|
950
|
+
const wasIgnored = addResult.ignored.some(h => h.equals(txHash));
|
|
894
951
|
|
|
895
952
|
this.logger.trace(`Validate propagated tx`, {
|
|
896
|
-
|
|
897
|
-
|
|
953
|
+
wasAccepted,
|
|
954
|
+
wasIgnored,
|
|
898
955
|
[Attributes.P2P_ID]: source.toString(),
|
|
899
956
|
});
|
|
900
957
|
|
|
901
|
-
if (
|
|
902
|
-
return { result: TopicValidatorResult.
|
|
903
|
-
} else if (
|
|
958
|
+
if (wasAccepted) {
|
|
959
|
+
return { result: TopicValidatorResult.Accept, obj: tx };
|
|
960
|
+
} else if (wasIgnored) {
|
|
904
961
|
return { result: TopicValidatorResult.Ignore, obj: tx };
|
|
905
962
|
} else {
|
|
906
|
-
return { result: TopicValidatorResult.
|
|
963
|
+
return { result: TopicValidatorResult.Reject };
|
|
907
964
|
}
|
|
908
965
|
};
|
|
909
966
|
|
|
@@ -912,6 +969,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
912
969
|
return;
|
|
913
970
|
}
|
|
914
971
|
|
|
972
|
+
// Tx was accepted into pool and will be propagated - just log and record metrics
|
|
915
973
|
const txHash = tx.getTxHash();
|
|
916
974
|
const txHashString = txHash.toString();
|
|
917
975
|
this.logger.verbose(`Received tx ${txHashString} from external peer ${source.toString()} via gossip`, {
|
|
@@ -919,13 +977,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
919
977
|
txHash: txHashString,
|
|
920
978
|
});
|
|
921
979
|
|
|
922
|
-
if (this.config.dropTransactions && randomInt(1000) < this.config.dropTransactionsProbability * 1000) {
|
|
923
|
-
this.logger.warn(`Intentionally dropping tx ${txHashString} (probability rule)`);
|
|
924
|
-
return;
|
|
925
|
-
}
|
|
926
|
-
|
|
927
980
|
this.instrumentation.incrementTxReceived(1);
|
|
928
|
-
await this.mempools.txPool.addTxs([tx]);
|
|
929
981
|
}
|
|
930
982
|
|
|
931
983
|
/**
|
|
@@ -979,40 +1031,53 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
979
1031
|
return { result: TopicValidatorResult.Ignore, obj: attestation };
|
|
980
1032
|
}
|
|
981
1033
|
|
|
982
|
-
// Get committee size for the attestation's slot
|
|
983
|
-
const slot = attestation.payload.header.slotNumber;
|
|
984
|
-
const { committee } = await this.epochCache.getCommittee(slot);
|
|
985
|
-
const committeeSize = committee?.length ?? 0;
|
|
986
|
-
|
|
987
1034
|
// Try to add the attestation: this handles existence check, cap check, and adding in one call
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
1035
|
+
// count is the number of attestations by this signer for this slot (for duplicate detection)
|
|
1036
|
+
const slot = attestation.payload.header.slotNumber;
|
|
1037
|
+
const { added, alreadyExists, count } =
|
|
1038
|
+
await this.mempools.attestationPool.tryAddCheckpointAttestation(attestation);
|
|
992
1039
|
|
|
993
1040
|
this.logger.trace(`Validate propagated checkpoint attestation`, {
|
|
994
1041
|
added,
|
|
995
1042
|
alreadyExists,
|
|
1043
|
+
count,
|
|
996
1044
|
[Attributes.SLOT_NUMBER]: slot.toString(),
|
|
997
1045
|
[Attributes.P2P_ID]: peerId.toString(),
|
|
998
1046
|
});
|
|
999
1047
|
|
|
1000
|
-
//
|
|
1048
|
+
// Exact same attestation received, no need to re-broadcast
|
|
1001
1049
|
if (alreadyExists) {
|
|
1002
1050
|
return { result: TopicValidatorResult.Ignore, obj: attestation };
|
|
1003
1051
|
}
|
|
1004
1052
|
|
|
1005
|
-
// Could not add (cap reached), no need to re-broadcast
|
|
1053
|
+
// Could not add (cap reached for signer), no need to re-broadcast
|
|
1006
1054
|
if (!added) {
|
|
1007
|
-
this.logger.warn(`Dropping checkpoint attestation due to
|
|
1055
|
+
this.logger.warn(`Dropping checkpoint attestation due to cap`, {
|
|
1008
1056
|
slot: slot.toString(),
|
|
1009
1057
|
archive: attestation.archive.toString(),
|
|
1010
1058
|
source: peerId.toString(),
|
|
1059
|
+
attester: attestation.getSender()?.toString(),
|
|
1060
|
+
count,
|
|
1011
1061
|
});
|
|
1012
1062
|
return { result: TopicValidatorResult.Ignore, obj: attestation };
|
|
1013
1063
|
}
|
|
1014
1064
|
|
|
1015
|
-
//
|
|
1065
|
+
// Check if this is a duplicate attestation (signer attested to a different proposal at the same slot)
|
|
1066
|
+
// count is the number of attestations by this signer for this slot
|
|
1067
|
+
if (count === 2) {
|
|
1068
|
+
const attester = attestation.getSender();
|
|
1069
|
+
if (attester) {
|
|
1070
|
+
this.logger.warn(`Detected duplicate attestation (equivocation) at slot ${slot}`, {
|
|
1071
|
+
slot: slot.toString(),
|
|
1072
|
+
archive: attestation.archive.toString(),
|
|
1073
|
+
source: peerId.toString(),
|
|
1074
|
+
attester: attester.toString(),
|
|
1075
|
+
});
|
|
1076
|
+
this.duplicateAttestationCallback?.({ slot, attester });
|
|
1077
|
+
}
|
|
1078
|
+
}
|
|
1079
|
+
|
|
1080
|
+
// Attestation was added successfully - accept it so other nodes can also detect the equivocation
|
|
1016
1081
|
return { result: TopicValidatorResult.Accept, obj: attestation };
|
|
1017
1082
|
}
|
|
1018
1083
|
|
|
@@ -1058,8 +1123,8 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1058
1123
|
}
|
|
1059
1124
|
|
|
1060
1125
|
// Try to add the proposal: this handles existence check, cap check, and adding in one call
|
|
1061
|
-
const { added, alreadyExists,
|
|
1062
|
-
const isEquivocated =
|
|
1126
|
+
const { added, alreadyExists, count } = await this.mempools.attestationPool.tryAddBlockProposal(block);
|
|
1127
|
+
const isEquivocated = count !== undefined && count > 1;
|
|
1063
1128
|
|
|
1064
1129
|
// Duplicate proposal received, no need to re-broadcast
|
|
1065
1130
|
if (alreadyExists) {
|
|
@@ -1078,7 +1143,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1078
1143
|
this.logger.warn(`Penalizing peer for block proposal exceeding per-position cap`, {
|
|
1079
1144
|
...block.toBlockInfo(),
|
|
1080
1145
|
indexWithinCheckpoint: block.indexWithinCheckpoint,
|
|
1081
|
-
|
|
1146
|
+
count,
|
|
1082
1147
|
proposer: block.getSender()?.toString(),
|
|
1083
1148
|
source: peerId.toString(),
|
|
1084
1149
|
});
|
|
@@ -1095,7 +1160,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1095
1160
|
proposer: proposer?.toString(),
|
|
1096
1161
|
});
|
|
1097
1162
|
// Invoke the duplicate callback on the first duplicate spotted only
|
|
1098
|
-
if (proposer &&
|
|
1163
|
+
if (proposer && count === 2) {
|
|
1099
1164
|
this.duplicateProposalCallback?.({ slot: block.slotNumber, proposer, type: 'block' });
|
|
1100
1165
|
}
|
|
1101
1166
|
return { result: TopicValidatorResult.Accept, obj: block, metadata: { isEquivocated } };
|
|
@@ -1120,14 +1185,14 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1120
1185
|
...block.toBlockInfo(),
|
|
1121
1186
|
});
|
|
1122
1187
|
|
|
1123
|
-
// Mark the txs in this proposal as
|
|
1124
|
-
await this.mempools.txPool.
|
|
1188
|
+
// Mark the txs in this proposal as protected
|
|
1189
|
+
await this.mempools.txPool.protectTxs(block.txHashes, block.blockHeader);
|
|
1125
1190
|
|
|
1126
1191
|
// Call the block received callback to validate the proposal.
|
|
1127
1192
|
// Note: Validators do NOT attest to individual blocks, only to checkpoint proposals.
|
|
1128
1193
|
const isValid = await this.blockReceivedCallback(block, sender);
|
|
1129
1194
|
if (!isValid) {
|
|
1130
|
-
this.logger.
|
|
1195
|
+
this.logger.info(`Block proposal validation failed for block ${block.blockNumber}`, block.toBlockInfo());
|
|
1131
1196
|
}
|
|
1132
1197
|
}
|
|
1133
1198
|
|
|
@@ -1212,8 +1277,8 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1212
1277
|
// Try to add the checkpoint proposal core: this handles existence check, cap check, and adding in one call
|
|
1213
1278
|
const checkpointCore = checkpoint.toCore();
|
|
1214
1279
|
const tryAddResult = await this.mempools.attestationPool.tryAddCheckpointProposal(checkpointCore);
|
|
1215
|
-
const { added, alreadyExists,
|
|
1216
|
-
const isEquivocated =
|
|
1280
|
+
const { added, alreadyExists, count } = tryAddResult;
|
|
1281
|
+
const isEquivocated = count !== undefined && count > 1;
|
|
1217
1282
|
|
|
1218
1283
|
// Duplicate proposal received, do not re-broadcast
|
|
1219
1284
|
if (alreadyExists) {
|
|
@@ -1234,7 +1299,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1234
1299
|
this.peerManager.penalizePeer(peerId, PeerErrorSeverity.HighToleranceError);
|
|
1235
1300
|
this.logger.warn(`Penalizing peer for checkpoint proposal exceeding per-slot cap`, {
|
|
1236
1301
|
...checkpoint.toCheckpointInfo(),
|
|
1237
|
-
|
|
1302
|
+
count,
|
|
1238
1303
|
source: peerId.toString(),
|
|
1239
1304
|
});
|
|
1240
1305
|
return { result: TopicValidatorResult.Reject, obj: checkpoint, metadata: { isEquivocated, processBlock } };
|
|
@@ -1250,7 +1315,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1250
1315
|
proposer: proposer?.toString(),
|
|
1251
1316
|
});
|
|
1252
1317
|
// Invoke the duplicate callback on the first duplicate spotted only
|
|
1253
|
-
if (proposer &&
|
|
1318
|
+
if (proposer && count === 2) {
|
|
1254
1319
|
this.duplicateProposalCallback?.({ slot: checkpoint.slotNumber, proposer, type: 'checkpoint' });
|
|
1255
1320
|
}
|
|
1256
1321
|
return {
|
|
@@ -1499,43 +1564,12 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1499
1564
|
}
|
|
1500
1565
|
|
|
1501
1566
|
protected createRequestedTxValidator(): TxValidator {
|
|
1502
|
-
return
|
|
1567
|
+
return createTxValidatorForReqResponseReceivedTxs(this.proofVerifier, {
|
|
1503
1568
|
l1ChainId: this.config.l1ChainId,
|
|
1504
1569
|
rollupVersion: this.config.rollupVersion,
|
|
1505
1570
|
});
|
|
1506
1571
|
}
|
|
1507
1572
|
|
|
1508
|
-
@trackSpan('Libp2pService.validatePropagatedTx', tx => ({
|
|
1509
|
-
[Attributes.TX_HASH]: tx.getTxHash().toString(),
|
|
1510
|
-
}))
|
|
1511
|
-
private async validatePropagatedTx(tx: Tx, peerId: PeerId): Promise<boolean> {
|
|
1512
|
-
const currentBlockNumber = await this.archiver.getBlockNumber();
|
|
1513
|
-
|
|
1514
|
-
// We accept transactions if they are not expired by the next slot (checked based on the IncludeByTimestamp field)
|
|
1515
|
-
const { ts: nextSlotTimestamp } = this.epochCache.getEpochAndSlotInNextL1Slot();
|
|
1516
|
-
const messageValidators = await this.createMessageValidators(currentBlockNumber, nextSlotTimestamp);
|
|
1517
|
-
|
|
1518
|
-
for (const validator of messageValidators) {
|
|
1519
|
-
const outcome = await this.runValidations(tx, validator);
|
|
1520
|
-
|
|
1521
|
-
if (outcome.allPassed) {
|
|
1522
|
-
continue;
|
|
1523
|
-
}
|
|
1524
|
-
const { name } = outcome.failure;
|
|
1525
|
-
let { severity } = outcome.failure;
|
|
1526
|
-
|
|
1527
|
-
// Double spend validator has a special case handler
|
|
1528
|
-
if (name === 'doubleSpendValidator') {
|
|
1529
|
-
const txBlockNumber = BlockNumber(currentBlockNumber + 1); // tx is expected to be in the next block
|
|
1530
|
-
severity = await this.handleDoubleSpendFailure(tx, txBlockNumber);
|
|
1531
|
-
}
|
|
1532
|
-
|
|
1533
|
-
this.peerManager.penalizePeer(peerId, severity);
|
|
1534
|
-
return false;
|
|
1535
|
-
}
|
|
1536
|
-
return true;
|
|
1537
|
-
}
|
|
1538
|
-
|
|
1539
1573
|
private async getGasFees(blockNumber: BlockNumber): Promise<GasFees> {
|
|
1540
1574
|
if (blockNumber === this.feesCache?.blockNumber) {
|
|
1541
1575
|
return this.feesCache.gasFees;
|
|
@@ -1563,60 +1597,62 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1563
1597
|
};
|
|
1564
1598
|
}
|
|
1565
1599
|
|
|
1566
|
-
public async
|
|
1567
|
-
const
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
|
|
1571
|
-
|
|
1600
|
+
public async validateTxsReceivedInBlockProposal(txs: Tx[]): Promise<void> {
|
|
1601
|
+
const validator = createTxValidatorForBlockProposalReceivedTxs(
|
|
1602
|
+
this.proofVerifier,
|
|
1603
|
+
{ l1ChainId: this.config.l1ChainId, rollupVersion: this.config.rollupVersion },
|
|
1604
|
+
this.logger.getBindings(),
|
|
1605
|
+
);
|
|
1572
1606
|
|
|
1573
|
-
await Promise.all(
|
|
1607
|
+
const results = await Promise.all(
|
|
1574
1608
|
txs.map(async tx => {
|
|
1575
|
-
|
|
1576
|
-
|
|
1577
|
-
if (!outcome.allPassed) {
|
|
1578
|
-
throw new Error('Invalid tx detected', { cause: { outcome } });
|
|
1579
|
-
}
|
|
1580
|
-
}
|
|
1609
|
+
const result = await validator.validateTx(tx);
|
|
1610
|
+
return result.result !== 'invalid';
|
|
1581
1611
|
}),
|
|
1582
1612
|
);
|
|
1613
|
+
if (results.some(value => value === false)) {
|
|
1614
|
+
throw new Error('Invalid tx detected');
|
|
1615
|
+
}
|
|
1583
1616
|
}
|
|
1584
1617
|
|
|
1585
|
-
/**
|
|
1586
|
-
|
|
1587
|
-
*
|
|
1588
|
-
* Each validator is a pair of a validator and a severity.
|
|
1589
|
-
* If a validator fails, the peer is penalized with the severity of the validator.
|
|
1590
|
-
*
|
|
1591
|
-
* @param currentBlockNumber - The current synced block number.
|
|
1592
|
-
* @param nextSlotTimestamp - The timestamp of the next slot (used to validate txs are not expired).
|
|
1593
|
-
* @returns The message validators.
|
|
1594
|
-
*/
|
|
1595
|
-
private async createMessageValidators(
|
|
1618
|
+
/** Creates the first stage (fast) validators for gossiped transactions. */
|
|
1619
|
+
protected async createFirstStageMessageValidators(
|
|
1596
1620
|
currentBlockNumber: BlockNumber,
|
|
1597
1621
|
nextSlotTimestamp: UInt64,
|
|
1598
|
-
): Promise<Record<string,
|
|
1622
|
+
): Promise<Record<string, TransactionValidator>> {
|
|
1599
1623
|
const gasFees = await this.getGasFees(currentBlockNumber);
|
|
1600
|
-
const allowedInSetup =
|
|
1601
|
-
|
|
1602
|
-
|
|
1603
|
-
|
|
1604
|
-
|
|
1624
|
+
const allowedInSetup = [
|
|
1625
|
+
...(await getDefaultAllowedSetupFunctions()),
|
|
1626
|
+
...(this.config.txPublicSetupAllowListExtend ?? []),
|
|
1627
|
+
];
|
|
1628
|
+
const blockNumber = BlockNumber(currentBlockNumber + 1);
|
|
1629
|
+
const l1Constants = await this.archiver.getL1Constants();
|
|
1630
|
+
|
|
1631
|
+
return createFirstStageTxValidationsForGossipedTransactions(
|
|
1605
1632
|
nextSlotTimestamp,
|
|
1606
|
-
|
|
1633
|
+
blockNumber,
|
|
1607
1634
|
this.worldStateSynchronizer,
|
|
1608
1635
|
gasFees,
|
|
1609
1636
|
this.config.l1ChainId,
|
|
1610
1637
|
this.config.rollupVersion,
|
|
1611
1638
|
protocolContractsHash,
|
|
1612
1639
|
this.archiver,
|
|
1613
|
-
this.proofVerifier,
|
|
1614
1640
|
!this.config.disableTransactions,
|
|
1615
1641
|
allowedInSetup,
|
|
1616
1642
|
this.logger.getBindings(),
|
|
1643
|
+
{
|
|
1644
|
+
rollupManaLimit: l1Constants.rollupManaLimit,
|
|
1645
|
+
maxBlockL2Gas: this.config.validateMaxL2BlockGas,
|
|
1646
|
+
maxBlockDAGas: this.config.validateMaxDABlockGas,
|
|
1647
|
+
},
|
|
1617
1648
|
);
|
|
1618
1649
|
}
|
|
1619
1650
|
|
|
1651
|
+
/** Creates the second stage (expensive proof verification) validators for gossiped transactions. */
|
|
1652
|
+
protected createSecondStageMessageValidators(): Record<string, TransactionValidator> {
|
|
1653
|
+
return createSecondStageTxValidationsForGossipedTransactions(this.proofVerifier, this.logger.getBindings());
|
|
1654
|
+
}
|
|
1655
|
+
|
|
1620
1656
|
/**
|
|
1621
1657
|
* Run validations on a tx.
|
|
1622
1658
|
* @param tx - The tx to validate.
|
|
@@ -1625,7 +1661,7 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1625
1661
|
*/
|
|
1626
1662
|
private async runValidations(
|
|
1627
1663
|
tx: Tx,
|
|
1628
|
-
messageValidators: Record<string,
|
|
1664
|
+
messageValidators: Record<string, TransactionValidator>,
|
|
1629
1665
|
): Promise<ValidationOutcome> {
|
|
1630
1666
|
const validationPromises = Object.entries(messageValidators).map(async ([name, { validator, severity }]) => {
|
|
1631
1667
|
const { result } = await validator.validateTx(tx);
|
|
@@ -1634,8 +1670,10 @@ export class LibP2PService<T extends P2PClientType = P2PClientType.Full> extends
|
|
|
1634
1670
|
|
|
1635
1671
|
// A promise that resolves when all validations have been run
|
|
1636
1672
|
const allValidations = await Promise.all(validationPromises);
|
|
1637
|
-
const
|
|
1638
|
-
if (
|
|
1673
|
+
const failures = allValidations.filter(x => !x.isValid);
|
|
1674
|
+
if (failures.length > 0) {
|
|
1675
|
+
// Pick the most severe failure (lowest tolerance = harshest penalty)
|
|
1676
|
+
const failed = maxBy(failures, f => PeerErrorSeverityByHarshness.indexOf(f.severity))!;
|
|
1639
1677
|
return {
|
|
1640
1678
|
allPassed: false,
|
|
1641
1679
|
failure: {
|
|
@@ -10,6 +10,7 @@ import { Tx, TxArray, TxHash } from '@aztec/stdlib/tx';
|
|
|
10
10
|
import type { PeerId } from '@libp2p/interface';
|
|
11
11
|
import { peerIdFromString } from '@libp2p/peer-id';
|
|
12
12
|
|
|
13
|
+
import type { IMissingTxsTracker } from '../../tx_collection/missing_txs_tracker.js';
|
|
13
14
|
import { ReqRespSubProtocol } from '.././interface.js';
|
|
14
15
|
import { BlockTxsRequest, BlockTxsResponse, type BlockTxsSource } from '.././protocols/index.js';
|
|
15
16
|
import { ReqRespStatus } from '.././status.js';
|
|
@@ -20,7 +21,7 @@ import {
|
|
|
20
21
|
DEFAULT_BATCH_TX_REQUESTER_TX_BATCH_SIZE,
|
|
21
22
|
} from './config.js';
|
|
22
23
|
import type { BatchTxRequesterLibP2PService, BatchTxRequesterOptions, ITxMetadataCollection } from './interface.js';
|
|
23
|
-
import {
|
|
24
|
+
import { MissingTxMetadataCollection } from './missing_txs.js';
|
|
24
25
|
import { type IPeerCollection, PeerCollection } from './peer_collection.js';
|
|
25
26
|
import { BatchRequestTxValidator, type IBatchRequestTxValidator } from './tx_validator.js';
|
|
26
27
|
|
|
@@ -60,7 +61,7 @@ export class BatchTxRequester {
|
|
|
60
61
|
private readonly txBatchSize: number;
|
|
61
62
|
|
|
62
63
|
constructor(
|
|
63
|
-
|
|
64
|
+
missingTxsTracker: IMissingTxsTracker,
|
|
64
65
|
blockTxsSource: BlockTxsSource,
|
|
65
66
|
pinnedPeer: PeerId | undefined,
|
|
66
67
|
timeoutMs: number,
|
|
@@ -99,8 +100,7 @@ export class BatchTxRequester {
|
|
|
99
100
|
this.p2pService.peerScoring,
|
|
100
101
|
);
|
|
101
102
|
}
|
|
102
|
-
|
|
103
|
-
this.txsMetadata = new MissingTxMetadataCollection(entries, this.txBatchSize);
|
|
103
|
+
this.txsMetadata = new MissingTxMetadataCollection(missingTxsTracker, this.txBatchSize);
|
|
104
104
|
this.smartRequesterSemaphore = this.opts.semaphore ?? new Semaphore(0);
|
|
105
105
|
}
|
|
106
106
|
|
|
@@ -661,7 +661,7 @@ export class BatchTxRequester {
|
|
|
661
661
|
/*
|
|
662
662
|
* @returns true if all missing txs have been fetched */
|
|
663
663
|
private fetchedAllTxs() {
|
|
664
|
-
return
|
|
664
|
+
return this.txsMetadata.getMissingTxHashes().size == 0;
|
|
665
665
|
}
|
|
666
666
|
|
|
667
667
|
/*
|
|
@@ -679,7 +679,7 @@ export class BatchTxRequester {
|
|
|
679
679
|
this.unlockSmartRequesterSemaphores();
|
|
680
680
|
}
|
|
681
681
|
|
|
682
|
-
return aborted || this.
|
|
682
|
+
return aborted || this.fetchedAllTxs() || this.dateProvider.now() > this.deadline;
|
|
683
683
|
}
|
|
684
684
|
|
|
685
685
|
/*
|
|
@@ -6,7 +6,6 @@ import type { PeerId } from '@libp2p/interface';
|
|
|
6
6
|
|
|
7
7
|
import type { ConnectionSampler } from '../connection-sampler/connection_sampler.js';
|
|
8
8
|
import type { ReqRespInterface } from '../interface.js';
|
|
9
|
-
import type { MissingTxMetadata } from './missing_txs.js';
|
|
10
9
|
import type { IPeerCollection } from './peer_collection.js';
|
|
11
10
|
import type { BatchRequestTxValidatorConfig, IBatchRequestTxValidator } from './tx_validator.js';
|
|
12
11
|
|
|
@@ -15,18 +14,15 @@ export interface IPeerPenalizer {
|
|
|
15
14
|
}
|
|
16
15
|
|
|
17
16
|
export interface ITxMetadataCollection {
|
|
18
|
-
size: number;
|
|
19
|
-
values(): IterableIterator<MissingTxMetadata>;
|
|
20
17
|
getMissingTxHashes(): Set<string>;
|
|
18
|
+
markFetched(peerId: PeerId, tx: Tx): boolean;
|
|
21
19
|
getTxsToRequestFromThePeer(peer: PeerId): TxHash[];
|
|
22
20
|
markRequested(txHash: TxHash): void;
|
|
23
21
|
markInFlightBySmartPeer(txHash: TxHash): void;
|
|
24
22
|
markNotInFlightBySmartPeer(txHash: TxHash): void;
|
|
25
23
|
alreadyFetched(txHash: TxHash): boolean;
|
|
26
24
|
// Returns true if tx was marked as fetched, false if it was already marked as fetched
|
|
27
|
-
markFetched(peerId: PeerId, tx: Tx): boolean;
|
|
28
25
|
markPeerHas(peerId: PeerId, txHashes: TxHash[]): void;
|
|
29
|
-
getFetchedTxs(): Tx[];
|
|
30
26
|
}
|
|
31
27
|
|
|
32
28
|
/**
|