@lodestar/beacon-node 1.42.0-dev.5007abf468 → 1.42.0-dev.50605dac9f

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.
Files changed (289) hide show
  1. package/lib/api/impl/beacon/blocks/index.d.ts.map +1 -1
  2. package/lib/api/impl/beacon/blocks/index.js +24 -12
  3. package/lib/api/impl/beacon/blocks/index.js.map +1 -1
  4. package/lib/api/impl/beacon/pool/index.d.ts.map +1 -1
  5. package/lib/api/impl/beacon/pool/index.js +4 -0
  6. package/lib/api/impl/beacon/pool/index.js.map +1 -1
  7. package/lib/api/impl/beacon/state/index.d.ts.map +1 -1
  8. package/lib/api/impl/beacon/state/index.js +13 -10
  9. package/lib/api/impl/beacon/state/index.js.map +1 -1
  10. package/lib/api/impl/debug/index.js.map +1 -1
  11. package/lib/api/impl/lodestar/index.d.ts.map +1 -1
  12. package/lib/api/impl/lodestar/index.js +4 -0
  13. package/lib/api/impl/lodestar/index.js.map +1 -1
  14. package/lib/api/impl/validator/index.d.ts.map +1 -1
  15. package/lib/api/impl/validator/index.js +7 -1
  16. package/lib/api/impl/validator/index.js.map +1 -1
  17. package/lib/chain/ColumnReconstructionTracker.d.ts +2 -1
  18. package/lib/chain/ColumnReconstructionTracker.d.ts.map +1 -1
  19. package/lib/chain/ColumnReconstructionTracker.js +5 -5
  20. package/lib/chain/ColumnReconstructionTracker.js.map +1 -1
  21. package/lib/chain/GetBlobsTracker.d.ts +2 -1
  22. package/lib/chain/GetBlobsTracker.d.ts.map +1 -1
  23. package/lib/chain/GetBlobsTracker.js +14 -12
  24. package/lib/chain/GetBlobsTracker.js.map +1 -1
  25. package/lib/chain/archiveStore/archiveStore.d.ts.map +1 -1
  26. package/lib/chain/archiveStore/archiveStore.js +1 -0
  27. package/lib/chain/archiveStore/archiveStore.js.map +1 -1
  28. package/lib/chain/archiveStore/historicalState/getHistoricalState.d.ts +3 -3
  29. package/lib/chain/archiveStore/historicalState/getHistoricalState.d.ts.map +1 -1
  30. package/lib/chain/archiveStore/historicalState/getHistoricalState.js +6 -4
  31. package/lib/chain/archiveStore/historicalState/getHistoricalState.js.map +1 -1
  32. package/lib/chain/archiveStore/historicalState/historicalStateRegen.d.ts +2 -2
  33. package/lib/chain/archiveStore/historicalState/historicalStateRegen.d.ts.map +1 -1
  34. package/lib/chain/archiveStore/historicalState/historicalStateRegen.js +1 -0
  35. package/lib/chain/archiveStore/historicalState/historicalStateRegen.js.map +1 -1
  36. package/lib/chain/archiveStore/historicalState/types.d.ts +2 -0
  37. package/lib/chain/archiveStore/historicalState/types.d.ts.map +1 -1
  38. package/lib/chain/archiveStore/historicalState/types.js.map +1 -1
  39. package/lib/chain/archiveStore/historicalState/worker.js +1 -4
  40. package/lib/chain/archiveStore/historicalState/worker.js.map +1 -1
  41. package/lib/chain/archiveStore/interface.d.ts +1 -0
  42. package/lib/chain/archiveStore/interface.d.ts.map +1 -1
  43. package/lib/chain/blocks/blockInput/blockInput.d.ts +5 -5
  44. package/lib/chain/blocks/blockInput/blockInput.d.ts.map +1 -1
  45. package/lib/chain/blocks/blockInput/blockInput.js.map +1 -1
  46. package/lib/chain/blocks/blockInput/types.d.ts +4 -4
  47. package/lib/chain/blocks/blockInput/types.d.ts.map +1 -1
  48. package/lib/chain/blocks/importBlock.d.ts.map +1 -1
  49. package/lib/chain/blocks/importBlock.js +34 -20
  50. package/lib/chain/blocks/importBlock.js.map +1 -1
  51. package/lib/chain/blocks/importExecutionPayload.d.ts +10 -8
  52. package/lib/chain/blocks/importExecutionPayload.d.ts.map +1 -1
  53. package/lib/chain/blocks/importExecutionPayload.js +86 -49
  54. package/lib/chain/blocks/importExecutionPayload.js.map +1 -1
  55. package/lib/chain/blocks/index.d.ts.map +1 -1
  56. package/lib/chain/blocks/index.js +2 -1
  57. package/lib/chain/blocks/index.js.map +1 -1
  58. package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.d.ts +14 -6
  59. package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.d.ts.map +1 -1
  60. package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.js +33 -2
  61. package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.js.map +1 -1
  62. package/lib/chain/blocks/payloadEnvelopeInput/types.d.ts +2 -1
  63. package/lib/chain/blocks/payloadEnvelopeInput/types.d.ts.map +1 -1
  64. package/lib/chain/blocks/types.d.ts +20 -14
  65. package/lib/chain/blocks/types.d.ts.map +1 -1
  66. package/lib/chain/blocks/verifyBlocksExecutionPayloads.d.ts +2 -2
  67. package/lib/chain/blocks/verifyBlocksExecutionPayloads.d.ts.map +1 -1
  68. package/lib/chain/blocks/verifyBlocksExecutionPayloads.js +4 -3
  69. package/lib/chain/blocks/verifyBlocksExecutionPayloads.js.map +1 -1
  70. package/lib/chain/blocks/verifyBlocksSignatures.d.ts.map +1 -1
  71. package/lib/chain/blocks/verifyBlocksSignatures.js +4 -2
  72. package/lib/chain/blocks/verifyBlocksSignatures.js.map +1 -1
  73. package/lib/chain/chain.d.ts +3 -2
  74. package/lib/chain/chain.d.ts.map +1 -1
  75. package/lib/chain/chain.js +64 -24
  76. package/lib/chain/chain.js.map +1 -1
  77. package/lib/chain/emitter.d.ts +29 -7
  78. package/lib/chain/emitter.d.ts.map +1 -1
  79. package/lib/chain/emitter.js +12 -3
  80. package/lib/chain/emitter.js.map +1 -1
  81. package/lib/chain/errors/dataColumnSidecarError.d.ts +31 -1
  82. package/lib/chain/errors/dataColumnSidecarError.d.ts.map +1 -1
  83. package/lib/chain/errors/dataColumnSidecarError.js +7 -0
  84. package/lib/chain/errors/dataColumnSidecarError.js.map +1 -1
  85. package/lib/chain/forkChoice/index.d.ts.map +1 -1
  86. package/lib/chain/forkChoice/index.js +10 -8
  87. package/lib/chain/forkChoice/index.js.map +1 -1
  88. package/lib/chain/interface.d.ts +4 -2
  89. package/lib/chain/interface.d.ts.map +1 -1
  90. package/lib/chain/lightClient/index.d.ts +2 -2
  91. package/lib/chain/lightClient/index.d.ts.map +1 -1
  92. package/lib/chain/lightClient/index.js +7 -0
  93. package/lib/chain/lightClient/index.js.map +1 -1
  94. package/lib/chain/opPools/aggregatedAttestationPool.d.ts.map +1 -1
  95. package/lib/chain/opPools/aggregatedAttestationPool.js +5 -2
  96. package/lib/chain/opPools/aggregatedAttestationPool.js.map +1 -1
  97. package/lib/chain/opPools/executionPayloadBidPool.d.ts +2 -2
  98. package/lib/chain/opPools/executionPayloadBidPool.d.ts.map +1 -1
  99. package/lib/chain/opPools/executionPayloadBidPool.js +2 -2
  100. package/lib/chain/opPools/executionPayloadBidPool.js.map +1 -1
  101. package/lib/chain/options.d.ts +1 -0
  102. package/lib/chain/options.d.ts.map +1 -1
  103. package/lib/chain/options.js +1 -0
  104. package/lib/chain/options.js.map +1 -1
  105. package/lib/chain/prepareNextSlot.d.ts.map +1 -1
  106. package/lib/chain/prepareNextSlot.js +7 -1
  107. package/lib/chain/prepareNextSlot.js.map +1 -1
  108. package/lib/chain/produceBlock/computeNewStateRoot.d.ts +2 -2
  109. package/lib/chain/produceBlock/computeNewStateRoot.d.ts.map +1 -1
  110. package/lib/chain/produceBlock/computeNewStateRoot.js.map +1 -1
  111. package/lib/chain/produceBlock/produceBlockBody.d.ts +3 -3
  112. package/lib/chain/produceBlock/produceBlockBody.d.ts.map +1 -1
  113. package/lib/chain/produceBlock/produceBlockBody.js +10 -1
  114. package/lib/chain/produceBlock/produceBlockBody.js.map +1 -1
  115. package/lib/chain/seenCache/seenGossipBlockInput.d.ts +1 -1
  116. package/lib/chain/seenCache/seenGossipBlockInput.d.ts.map +1 -1
  117. package/lib/chain/seenCache/seenGossipBlockInput.js +2 -2
  118. package/lib/chain/seenCache/seenGossipBlockInput.js.map +1 -1
  119. package/lib/chain/seenCache/seenPayloadEnvelopeInput.d.ts +1 -1
  120. package/lib/chain/seenCache/seenPayloadEnvelopeInput.d.ts.map +1 -1
  121. package/lib/chain/seenCache/seenPayloadEnvelopeInput.js +2 -2
  122. package/lib/chain/seenCache/seenPayloadEnvelopeInput.js.map +1 -1
  123. package/lib/chain/validation/block.d.ts.map +1 -1
  124. package/lib/chain/validation/block.js +2 -2
  125. package/lib/chain/validation/block.js.map +1 -1
  126. package/lib/chain/validation/dataColumnSidecar.d.ts +11 -4
  127. package/lib/chain/validation/dataColumnSidecar.d.ts.map +1 -1
  128. package/lib/chain/validation/dataColumnSidecar.js +184 -5
  129. package/lib/chain/validation/dataColumnSidecar.js.map +1 -1
  130. package/lib/chain/validation/executionPayloadBid.d.ts.map +1 -1
  131. package/lib/chain/validation/executionPayloadBid.js +7 -4
  132. package/lib/chain/validation/executionPayloadBid.js.map +1 -1
  133. package/lib/chain/validation/executionPayloadEnvelope.d.ts.map +1 -1
  134. package/lib/chain/validation/executionPayloadEnvelope.js +6 -1
  135. package/lib/chain/validation/executionPayloadEnvelope.js.map +1 -1
  136. package/lib/chain/validation/payloadAttestationMessage.d.ts.map +1 -1
  137. package/lib/chain/validation/payloadAttestationMessage.js +4 -1
  138. package/lib/chain/validation/payloadAttestationMessage.js.map +1 -1
  139. package/lib/chain/validation/syncCommittee.d.ts.map +1 -1
  140. package/lib/chain/validation/syncCommittee.js +4 -0
  141. package/lib/chain/validation/syncCommittee.js.map +1 -1
  142. package/lib/chain/validation/syncCommitteeContributionAndProof.js +4 -1
  143. package/lib/chain/validation/syncCommitteeContributionAndProof.js.map +1 -1
  144. package/lib/chain/validatorMonitor.d.ts.map +1 -1
  145. package/lib/chain/validatorMonitor.js +3 -3
  146. package/lib/chain/validatorMonitor.js.map +1 -1
  147. package/lib/db/buckets.d.ts +2 -2
  148. package/lib/db/buckets.d.ts.map +1 -1
  149. package/lib/db/buckets.js +2 -2
  150. package/lib/db/buckets.js.map +1 -1
  151. package/lib/db/repositories/blockArchiveIndex.d.ts +2 -2
  152. package/lib/db/repositories/blockArchiveIndex.d.ts.map +1 -1
  153. package/lib/db/repositories/dataColumnSidecar.d.ts.map +1 -1
  154. package/lib/db/repositories/dataColumnSidecar.js +4 -2
  155. package/lib/db/repositories/dataColumnSidecar.js.map +1 -1
  156. package/lib/db/repositories/dataColumnSidecarArchive.d.ts.map +1 -1
  157. package/lib/db/repositories/dataColumnSidecarArchive.js +4 -2
  158. package/lib/db/repositories/dataColumnSidecarArchive.js.map +1 -1
  159. package/lib/metrics/metrics/lodestar.d.ts +20 -0
  160. package/lib/metrics/metrics/lodestar.d.ts.map +1 -1
  161. package/lib/metrics/metrics/lodestar.js +33 -0
  162. package/lib/metrics/metrics/lodestar.js.map +1 -1
  163. package/lib/network/interface.d.ts +3 -2
  164. package/lib/network/interface.d.ts.map +1 -1
  165. package/lib/network/libp2p/index.d.ts.map +1 -1
  166. package/lib/network/libp2p/index.js +19 -13
  167. package/lib/network/libp2p/index.js.map +1 -1
  168. package/lib/network/network.d.ts +3 -2
  169. package/lib/network/network.d.ts.map +1 -1
  170. package/lib/network/network.js +3 -0
  171. package/lib/network/network.js.map +1 -1
  172. package/lib/network/options.d.ts.map +1 -1
  173. package/lib/network/options.js +7 -2
  174. package/lib/network/options.js.map +1 -1
  175. package/lib/network/processor/extractSlotRootFns.d.ts +1 -1
  176. package/lib/network/processor/extractSlotRootFns.d.ts.map +1 -1
  177. package/lib/network/processor/extractSlotRootFns.js +25 -5
  178. package/lib/network/processor/extractSlotRootFns.js.map +1 -1
  179. package/lib/network/processor/gossipHandlers.d.ts.map +1 -1
  180. package/lib/network/processor/gossipHandlers.js +260 -73
  181. package/lib/network/processor/gossipHandlers.js.map +1 -1
  182. package/lib/network/processor/index.d.ts +11 -1
  183. package/lib/network/processor/index.d.ts.map +1 -1
  184. package/lib/network/processor/index.js +234 -22
  185. package/lib/network/processor/index.js.map +1 -1
  186. package/lib/network/reqresp/types.d.ts +3 -3
  187. package/lib/network/reqresp/types.d.ts.map +1 -1
  188. package/lib/network/reqresp/types.js +9 -3
  189. package/lib/network/reqresp/types.js.map +1 -1
  190. package/lib/node/nodejs.d.ts.map +1 -1
  191. package/lib/node/nodejs.js +4 -1
  192. package/lib/node/nodejs.js.map +1 -1
  193. package/lib/node/notifier.d.ts.map +1 -1
  194. package/lib/node/notifier.js +2 -2
  195. package/lib/node/notifier.js.map +1 -1
  196. package/lib/sync/unknownBlock.js +2 -2
  197. package/lib/sync/unknownBlock.js.map +1 -1
  198. package/lib/sync/utils/downloadByRange.d.ts +3 -3
  199. package/lib/sync/utils/downloadByRange.d.ts.map +1 -1
  200. package/lib/sync/utils/downloadByRange.js +4 -2
  201. package/lib/sync/utils/downloadByRange.js.map +1 -1
  202. package/lib/sync/utils/downloadByRoot.d.ts +3 -3
  203. package/lib/sync/utils/downloadByRoot.d.ts.map +1 -1
  204. package/lib/sync/utils/downloadByRoot.js +10 -5
  205. package/lib/sync/utils/downloadByRoot.js.map +1 -1
  206. package/lib/util/blobs.d.ts +3 -3
  207. package/lib/util/blobs.d.ts.map +1 -1
  208. package/lib/util/blobs.js +21 -10
  209. package/lib/util/blobs.js.map +1 -1
  210. package/lib/util/dataColumns.d.ts +18 -11
  211. package/lib/util/dataColumns.d.ts.map +1 -1
  212. package/lib/util/dataColumns.js +51 -17
  213. package/lib/util/dataColumns.js.map +1 -1
  214. package/lib/util/execution.d.ts +6 -2
  215. package/lib/util/execution.d.ts.map +1 -1
  216. package/lib/util/execution.js +49 -25
  217. package/lib/util/execution.js.map +1 -1
  218. package/lib/util/sszBytes.d.ts +25 -1
  219. package/lib/util/sszBytes.d.ts.map +1 -1
  220. package/lib/util/sszBytes.js +189 -2
  221. package/lib/util/sszBytes.js.map +1 -1
  222. package/package.json +15 -15
  223. package/src/api/impl/beacon/blocks/index.ts +32 -15
  224. package/src/api/impl/beacon/pool/index.ts +4 -0
  225. package/src/api/impl/beacon/state/index.ts +15 -15
  226. package/src/api/impl/debug/index.ts +2 -2
  227. package/src/api/impl/lodestar/index.ts +4 -0
  228. package/src/api/impl/validator/index.ts +7 -0
  229. package/src/chain/ColumnReconstructionTracker.ts +6 -5
  230. package/src/chain/GetBlobsTracker.ts +14 -12
  231. package/src/chain/archiveStore/archiveStore.ts +1 -0
  232. package/src/chain/archiveStore/historicalState/getHistoricalState.ts +6 -5
  233. package/src/chain/archiveStore/historicalState/historicalStateRegen.ts +2 -1
  234. package/src/chain/archiveStore/historicalState/types.ts +2 -0
  235. package/src/chain/archiveStore/historicalState/worker.ts +1 -5
  236. package/src/chain/archiveStore/interface.ts +1 -0
  237. package/src/chain/blocks/blockInput/blockInput.ts +8 -8
  238. package/src/chain/blocks/blockInput/types.ts +4 -4
  239. package/src/chain/blocks/importBlock.ts +45 -23
  240. package/src/chain/blocks/importExecutionPayload.ts +94 -53
  241. package/src/chain/blocks/index.ts +2 -1
  242. package/src/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.ts +53 -12
  243. package/src/chain/blocks/payloadEnvelopeInput/types.ts +2 -1
  244. package/src/chain/blocks/types.ts +25 -14
  245. package/src/chain/blocks/verifyBlocksExecutionPayloads.ts +6 -5
  246. package/src/chain/blocks/verifyBlocksSignatures.ts +9 -2
  247. package/src/chain/chain.ts +73 -28
  248. package/src/chain/emitter.ts +25 -7
  249. package/src/chain/errors/dataColumnSidecarError.ts +32 -1
  250. package/src/chain/forkChoice/index.ts +11 -8
  251. package/src/chain/interface.ts +4 -2
  252. package/src/chain/lightClient/index.ts +15 -3
  253. package/src/chain/opPools/aggregatedAttestationPool.ts +6 -1
  254. package/src/chain/opPools/executionPayloadBidPool.ts +3 -3
  255. package/src/chain/options.ts +2 -0
  256. package/src/chain/prepareNextSlot.ts +8 -0
  257. package/src/chain/produceBlock/computeNewStateRoot.ts +2 -1
  258. package/src/chain/produceBlock/produceBlockBody.ts +25 -5
  259. package/src/chain/seenCache/seenGossipBlockInput.ts +2 -2
  260. package/src/chain/seenCache/seenPayloadEnvelopeInput.ts +2 -2
  261. package/src/chain/validation/block.ts +2 -1
  262. package/src/chain/validation/dataColumnSidecar.ts +230 -7
  263. package/src/chain/validation/executionPayloadBid.ts +7 -3
  264. package/src/chain/validation/executionPayloadEnvelope.ts +10 -1
  265. package/src/chain/validation/payloadAttestationMessage.ts +4 -0
  266. package/src/chain/validation/syncCommittee.ts +5 -1
  267. package/src/chain/validation/syncCommitteeContributionAndProof.ts +5 -1
  268. package/src/chain/validatorMonitor.ts +3 -2
  269. package/src/db/buckets.ts +2 -2
  270. package/src/db/repositories/dataColumnSidecar.ts +4 -2
  271. package/src/db/repositories/dataColumnSidecarArchive.ts +4 -2
  272. package/src/metrics/metrics/lodestar.ts +34 -0
  273. package/src/network/interface.ts +3 -2
  274. package/src/network/libp2p/index.ts +21 -15
  275. package/src/network/network.ts +7 -4
  276. package/src/network/options.ts +7 -2
  277. package/src/network/processor/extractSlotRootFns.ts +32 -6
  278. package/src/network/processor/gossipHandlers.ts +325 -86
  279. package/src/network/processor/index.ts +304 -22
  280. package/src/network/reqresp/types.ts +13 -5
  281. package/src/node/nodejs.ts +5 -2
  282. package/src/node/notifier.ts +7 -2
  283. package/src/sync/unknownBlock.ts +3 -3
  284. package/src/sync/utils/downloadByRange.ts +9 -7
  285. package/src/sync/utils/downloadByRoot.ts +16 -12
  286. package/src/util/blobs.ts +35 -15
  287. package/src/util/dataColumns.ts +69 -25
  288. package/src/util/execution.ts +49 -30
  289. package/src/util/sszBytes.ts +245 -3
@@ -3,6 +3,7 @@ import {
3
3
  createSingleSignatureSetFromComponents,
4
4
  getExecutionPayloadBidSigningRoot,
5
5
  isActiveBuilder,
6
+ isStatePostGloas,
6
7
  } from "@lodestar/state-transition";
7
8
  import {gloas} from "@lodestar/types";
8
9
  import {toRootHex} from "@lodestar/utils";
@@ -32,6 +33,9 @@ async function validateExecutionPayloadBid(
32
33
  const parentBlockRootHex = toRootHex(bid.parentBlockRoot);
33
34
  const parentBlockHashHex = toRootHex(bid.parentBlockHash);
34
35
  const state = await chain.getHeadStateAtCurrentEpoch(RegenCaller.validateGossipExecutionPayloadBid);
36
+ if (!isStatePostGloas(state)) {
37
+ throw new Error(`Expected gloas+ state for execution payload bid validation, got fork=${state.forkName}`);
38
+ }
35
39
 
36
40
  // [IGNORE] `bid.slot` is the current slot or the next slot.
37
41
  const currentSlot = chain.clock.currentSlot;
@@ -83,9 +87,9 @@ async function validateExecutionPayloadBid(
83
87
  });
84
88
  }
85
89
 
86
- // [IGNORE] this bid is the highest value bid seen for the corresponding slot
87
- // and the given parent block hash.
88
- const bestBid = chain.executionPayloadBidPool.getBestBid(parentBlockRootHex, parentBlockHashHex, bid.slot);
90
+ // [IGNORE] this bid is the highest value bid seen for the tuple
91
+ // `(bid.slot, bid.parent_block_hash, bid.parent_block_root)`.
92
+ const bestBid = chain.executionPayloadBidPool.getBestBid(bid.slot, parentBlockHashHex, parentBlockRootHex);
89
93
  if (bestBid !== null && bestBid.value >= bid.value) {
90
94
  throw new ExecutionPayloadBidError(GossipAction.IGNORE, {
91
95
  code: ExecutionPayloadBidErrorCode.BID_TOO_LOW,
@@ -1,5 +1,9 @@
1
1
  import {PayloadStatus} from "@lodestar/fork-choice";
2
- import {computeStartSlotAtEpoch, getExecutionPayloadEnvelopeSignatureSet} from "@lodestar/state-transition";
2
+ import {
3
+ computeStartSlotAtEpoch,
4
+ getExecutionPayloadEnvelopeSignatureSet,
5
+ isStatePostGloas,
6
+ } from "@lodestar/state-transition";
3
7
  import {gloas} from "@lodestar/types";
4
8
  import {toRootHex} from "@lodestar/utils";
5
9
  import {ExecutionPayloadEnvelopeError, ExecutionPayloadEnvelopeErrorCode, GossipAction} from "../errors/index.js";
@@ -113,7 +117,12 @@ async function validateExecutionPayloadEnvelope(
113
117
  slot: envelope.slot,
114
118
  });
115
119
  });
120
+ if (!isStatePostGloas(blockState)) {
121
+ throw new Error(`Expected gloas+ state for execution payload envelope validation, got fork=${blockState.forkName}`);
122
+ }
116
123
 
124
+ // [REJECT] `signed_execution_payload_envelope.signature` is valid as verified
125
+ // by `verify_execution_payload_envelope_signature`.
117
126
  const signatureSet = getExecutionPayloadEnvelopeSignatureSet(
118
127
  chain.config,
119
128
  chain.pubkeyCache,
@@ -2,6 +2,7 @@ import {
2
2
  computeEpochAtSlot,
3
3
  createSingleSignatureSetFromComponents,
4
4
  getPayloadAttestationDataSigningRoot,
5
+ isStatePostGloas,
5
6
  } from "@lodestar/state-transition";
6
7
  import {RootHex, gloas, ssz} from "@lodestar/types";
7
8
  import {toRootHex} from "@lodestar/utils";
@@ -66,6 +67,9 @@ async function validatePayloadAttestationMessage(
66
67
  }
67
68
 
68
69
  const state = chain.getHeadState();
70
+ if (!isStatePostGloas(state)) {
71
+ throw new Error(`Expected gloas+ state for payload attestation validation, got fork=${state.forkName}`);
72
+ }
69
73
 
70
74
  // [REJECT] The message's block `data.beacon_block_root` passes validation.
71
75
  // TODO GLOAS: implement this. Technically if we cannot get proto block from fork choice,
@@ -1,5 +1,5 @@
1
1
  import {SYNC_COMMITTEE_SUBNET_COUNT, SYNC_COMMITTEE_SUBNET_SIZE} from "@lodestar/params";
2
- import {IBeaconStateView} from "@lodestar/state-transition";
2
+ import {IBeaconStateView, isStatePostAltair} from "@lodestar/state-transition";
3
3
  import {SubnetID, altair} from "@lodestar/types";
4
4
  import {toRootHex} from "@lodestar/utils";
5
5
  import {GossipAction, SyncCommitteeError, SyncCommitteeErrorCode} from "../errors/index.js";
@@ -148,6 +148,10 @@ function getIndicesInSubcommittee(
148
148
  subnet: SubnetID,
149
149
  data: Pick<altair.SyncCommitteeMessage, "slot" | "validatorIndex">
150
150
  ): IndexInSubcommittee[] | null {
151
+ if (!isStatePostAltair(headState)) {
152
+ return null;
153
+ }
154
+
151
155
  const syncCommittee = headState.getIndexedSyncCommittee(data.slot);
152
156
  const indexesInCommittee = syncCommittee.validatorIndexMap.get(data.validatorIndex);
153
157
  if (indexesInCommittee === undefined) {
@@ -1,5 +1,5 @@
1
1
  import {SYNC_COMMITTEE_SUBNET_SIZE} from "@lodestar/params";
2
- import {IBeaconStateView, isSyncCommitteeAggregator} from "@lodestar/state-transition";
2
+ import {IBeaconStateView, isStatePostAltair, isSyncCommitteeAggregator} from "@lodestar/state-transition";
3
3
  import {ValidatorIndex, altair} from "@lodestar/types";
4
4
  import {GossipAction, SyncCommitteeError, SyncCommitteeErrorCode} from "../errors/index.js";
5
5
  import {IBeaconChain} from "../interface.js";
@@ -107,6 +107,10 @@ function getContributionIndices(
107
107
  state: IBeaconStateView,
108
108
  contribution: altair.SyncCommitteeContribution
109
109
  ): ValidatorIndex[] {
110
+ if (!isStatePostAltair(state)) {
111
+ throw new Error("Expected Altair state for sync committee contribution");
112
+ }
113
+
110
114
  const startIndex = contribution.subcommitteeIndex * SYNC_COMMITTEE_SUBNET_SIZE;
111
115
 
112
116
  const syncCommittee = state.getIndexedSyncCommittee(contribution.slot);
@@ -1,5 +1,5 @@
1
1
  import {ChainForkConfig} from "@lodestar/config";
2
- import {ForkSeq, MIN_ATTESTATION_INCLUSION_DELAY, SLOTS_PER_EPOCH} from "@lodestar/params";
2
+ import {MIN_ATTESTATION_INCLUSION_DELAY, SLOTS_PER_EPOCH} from "@lodestar/params";
3
3
  import {
4
4
  IBeaconStateView,
5
5
  ParticipationFlags,
@@ -7,6 +7,7 @@ import {
7
7
  computeStartSlotAtEpoch,
8
8
  computeTimeAtSlot,
9
9
  getCurrentSlot,
10
+ isStatePostAltair,
10
11
  parseAttesterFlags,
11
12
  parseParticipationFlags,
12
13
  } from "@lodestar/state-transition";
@@ -740,7 +741,7 @@ export function createValidatorMonitor(
740
741
 
741
742
  const rootCache = new RootHexCache(headState);
742
743
 
743
- if (config.getForkSeq(headState.slot) >= ForkSeq.altair) {
744
+ if (isStatePostAltair(headState)) {
744
745
  const prevEpochStartSlot = computeStartSlotAtEpoch(prevEpoch);
745
746
  const prevEpochTargetRoot = toRootHex(headState.getBlockRootAtSlot(prevEpochStartSlot));
746
747
 
package/src/db/buckets.ts CHANGED
@@ -67,8 +67,8 @@ export enum Bucket {
67
67
  // lightClient_bestLightClientUpdate = 55, // SyncPeriod -> LightClientUpdate // DEPRECATED on v1.5.0
68
68
  lightClient_bestLightClientUpdate = 56, // SyncPeriod -> [Slot, LightClientUpdate]
69
69
 
70
- fulu_dataColumnSidecars = 57, // FULU BeaconBlockRoot -> DataColumnSidecars
71
- fulu_dataColumnSidecarsArchive = 58, // FULU BeaconBlockSlot -> DataColumnSidecars
70
+ allForks_dataColumnSidecars = 57, // BeaconBlockRoot -> DataColumnSidecars
71
+ allForks_dataColumnSidecarsArchive = 58, // BeaconBlockSlot -> DataColumnSidecars
72
72
 
73
73
  gloas_executionPayloadEnvelope = 59, // GLOAS BeaconBlockRoot -> SignedExecutionPayloadEnvelope
74
74
  gloas_executionPayloadEnvelopeArchive = 60, // GLOAS Slot -> SignedExecutionPayloadEnvelope
@@ -18,8 +18,10 @@ type BlockRoot = Root;
18
18
  */
19
19
  export class DataColumnSidecarRepository extends PrefixedRepository<BlockRoot, ColumnIndex, DataColumnSidecar> {
20
20
  constructor(config: ChainForkConfig, db: Db) {
21
- const bucket = Bucket.fulu_dataColumnSidecars;
22
- super(config, db, bucket, ssz.fulu.DataColumnSidecar, getBucketNameByValue(bucket));
21
+ const bucket = Bucket.allForks_dataColumnSidecars;
22
+ // Type won't be used since we select it dynamically based on fork
23
+ const type = ssz.fulu.DataColumnSidecar;
24
+ super(config, db, bucket, type, getBucketNameByValue(bucket));
23
25
  }
24
26
 
25
27
  /**
@@ -16,8 +16,10 @@ const SLOT_BYTE_SIZE = 8;
16
16
  */
17
17
  export class DataColumnSidecarArchiveRepository extends PrefixedRepository<Slot, ColumnIndex, DataColumnSidecar> {
18
18
  constructor(config: ChainForkConfig, db: Db) {
19
- const bucket = Bucket.fulu_dataColumnSidecarsArchive;
20
- super(config, db, bucket, ssz.fulu.DataColumnSidecar, getBucketNameByValue(bucket));
19
+ const bucket = Bucket.allForks_dataColumnSidecarsArchive;
20
+ // Type won't be used since we select it dynamically based on fork
21
+ const type = ssz.fulu.DataColumnSidecar;
22
+ super(config, db, bucket, type, getBucketNameByValue(bucket));
21
23
  }
22
24
 
23
25
  /**
@@ -1746,6 +1746,40 @@ export function createLodestarMetrics(
1746
1746
  }),
1747
1747
  },
1748
1748
 
1749
+ // some gossip messages need to wait for payload to be processed before they can be processed
1750
+ awaitingPayloadGossipMessages: {
1751
+ queue: register.gauge<{topic: GossipType}>({
1752
+ name: "lodestar_awaiting_payload_gossip_messages_total",
1753
+ help: "Total number of gossip messages waiting for payload to be processed",
1754
+ labelNames: ["topic"],
1755
+ }),
1756
+ countPerSlot: register.gauge({
1757
+ name: "lodestar_awaiting_payload_gossip_messages_per_slot_total",
1758
+ help: "Total number of gossip messages waiting for payload to be processed per slot",
1759
+ }),
1760
+ resolve: register.gauge<{topic: GossipType}>({
1761
+ name: "lodestar_awaiting_payload_gossip_messages_resolve_total",
1762
+ help: "Total number of gossip messages are reprocessed",
1763
+ labelNames: ["topic"],
1764
+ }),
1765
+ waitSecBeforeResolve: register.gauge<{topic: GossipType}>({
1766
+ name: "lodestar_awaiting_payload_gossip_messages_wait_time_resolve_seconds",
1767
+ help: "Time to wait for unknown payload in seconds",
1768
+ labelNames: ["topic"],
1769
+ }),
1770
+ // having 2 labels here is not great for performance, however it's rarely happening and having the reason label is important for debugging
1771
+ reject: register.gauge<{reason: ReprocessRejectReason; topic: GossipType}>({
1772
+ name: "lodestar_awaiting_payload_gossip_messages_reject_total",
1773
+ help: "Total number of gossip messages are rejected to reprocess",
1774
+ labelNames: ["reason", "topic"],
1775
+ }),
1776
+ waitSecBeforeReject: register.gauge<{reason: ReprocessRejectReason; topic: GossipType}>({
1777
+ name: "lodestar_awaiting_payload_gossip_messages_wait_time_reject_seconds",
1778
+ help: "Time to wait for unknown payload before being rejected",
1779
+ labelNames: ["reason", "topic"],
1780
+ }),
1781
+ },
1782
+
1749
1783
  lightclientServer: {
1750
1784
  onSyncAggregate: register.gauge<{event: string}>({
1751
1785
  name: "lodestar_lightclient_server_on_sync_aggregate_event_total",
@@ -74,6 +74,7 @@ export interface INetwork extends INetworkCorePublic {
74
74
  shouldAggregate(subnet: SubnetID, slot: Slot): boolean;
75
75
  reStatusPeers(peers: PeerIdStr[]): Promise<void>;
76
76
  searchUnknownBlock(slotRoot: SlotRootHex, source: BlockInputSource, peer?: PeerIdStr): void;
77
+ searchUnknownEnvelope(slotRoot: SlotRootHex, source: BlockInputSource, peer?: PeerIdStr): void;
77
78
  // ReqResp
78
79
  sendBeaconBlocksByRange(peerId: PeerIdStr, request: phase0.BeaconBlocksByRangeRequest): Promise<SignedBeaconBlock[]>;
79
80
  sendBeaconBlocksByRoot(peerId: PeerIdStr, request: BeaconBlocksByRootRequest): Promise<SignedBeaconBlock[]>;
@@ -82,11 +83,11 @@ export interface INetwork extends INetworkCorePublic {
82
83
  sendDataColumnSidecarsByRange(
83
84
  peerId: PeerIdStr,
84
85
  request: fulu.DataColumnSidecarsByRangeRequest
85
- ): Promise<fulu.DataColumnSidecar[]>;
86
+ ): Promise<DataColumnSidecar[]>;
86
87
  sendDataColumnSidecarsByRoot(
87
88
  peerId: PeerIdStr,
88
89
  request: DataColumnSidecarsByRootRequest
89
- ): Promise<fulu.DataColumnSidecar[]>;
90
+ ): Promise<DataColumnSidecar[]>;
90
91
  sendExecutionPayloadEnvelopesByRange(
91
92
  peerId: PeerIdStr,
92
93
  request: gloas.ExecutionPayloadEnvelopesByRangeRequest
@@ -44,6 +44,8 @@ export async function createNodeJsLibp2p(
44
44
  ): Promise<Libp2p> {
45
45
  const localMultiaddrs = networkOpts.localMultiaddrs || defaultNetworkOptions.localMultiaddrs;
46
46
  const disconnectThreshold = networkOpts.disconnectThreshold ?? defaultNetworkOptions.disconnectThreshold;
47
+ const tcpEnabled = networkOpts.tcp ?? defaultNetworkOptions.tcp;
48
+ const quicEnabled = networkOpts.quic ?? defaultNetworkOptions.quic;
47
49
  const {peerStoreDir, disablePeerDiscovery} = nodeJsLibp2pOpts;
48
50
 
49
51
  let datastore: undefined | Eth2PeerDataStore = undefined;
@@ -58,7 +60,7 @@ export async function createNodeJsLibp2p(
58
60
  ...(networkOpts.bootMultiaddrs ?? defaultNetworkOptions.bootMultiaddrs ?? []),
59
61
  // Append discv5.bootEnrs to bootMultiaddrs if requested
60
62
  ...(networkOpts.connectToDiscv5Bootnodes
61
- ? await getDiscv5Multiaddrs(networkOpts.discv5?.bootEnrs ?? [], networkOpts.quic)
63
+ ? await getDiscv5Multiaddrs(networkOpts.discv5?.bootEnrs ?? [], quicEnabled)
62
64
  : []),
63
65
  ];
64
66
 
@@ -71,7 +73,7 @@ export async function createNodeJsLibp2p(
71
73
  }
72
74
  }
73
75
  const transports: Libp2pInit["transports"] = [];
74
- if (networkOpts.tcp ?? true) {
76
+ if (tcpEnabled) {
75
77
  transports.unshift(
76
78
  tcp({
77
79
  // Reject connections when the server's connection count gets high
@@ -87,22 +89,26 @@ export async function createNodeJsLibp2p(
87
89
  })
88
90
  );
89
91
  }
90
- if (networkOpts.quic) {
92
+ if (quicEnabled) {
91
93
  const quicMultiaddrs = localMultiaddrs.filter((ma) => ma.includes("/quic-v1"));
92
94
  const hasIpv4Quic = quicMultiaddrs.some((ma) => ma.includes("/ip4/"));
93
95
  const hasIpv6Quic = quicMultiaddrs.some((ma) => ma.includes("/ip6/"));
94
- transports.unshift(
95
- quic({
96
- handshakeTimeout: 5_000,
97
- maxIdleTimeout: 10_000,
98
- keepAliveInterval: 5_000,
99
- maxConcurrentStreamLimit: 256,
100
- maxStreamData: 10_000_000,
101
- maxConnectionData: 15_000_000,
102
- ipv4: hasIpv4Quic,
103
- ipv6: hasIpv6Quic,
104
- })
105
- );
96
+ // Only add QUIC transport if at least one QUIC listen address is configured,
97
+ // otherwise the transport constructor will throw
98
+ if (hasIpv4Quic || hasIpv6Quic) {
99
+ transports.unshift(
100
+ quic({
101
+ handshakeTimeout: 5_000,
102
+ maxIdleTimeout: 10_000,
103
+ keepAliveInterval: 5_000,
104
+ maxConcurrentStreamLimit: 256,
105
+ maxStreamData: 10_000_000,
106
+ maxConnectionData: 15_000_000,
107
+ ipv4: hasIpv4Quic,
108
+ ipv6: hasIpv6Quic,
109
+ })
110
+ );
111
+ }
106
112
  }
107
113
 
108
114
  const noiseCrypto = {
@@ -11,7 +11,6 @@ import {computeEpochAtSlot} from "@lodestar/state-transition";
11
11
  import {
12
12
  AttesterSlashing,
13
13
  DataColumnSidecar,
14
- DataColumnSidecars,
15
14
  LightClientBootstrap,
16
15
  LightClientFinalityUpdate,
17
16
  LightClientOptimisticUpdate,
@@ -286,6 +285,10 @@ export class Network implements INetwork {
286
285
  this.networkProcessor.searchUnknownBlock(slotRoot, source, peer);
287
286
  }
288
287
 
288
+ searchUnknownEnvelope(slotRoot: SlotRootHex, source: BlockInputSource, peer?: PeerIdStr): void {
289
+ this.networkProcessor.searchUnknownEnvelope(slotRoot, source, peer);
290
+ }
291
+
289
292
  async reportPeer(peer: PeerIdStr, action: PeerAction, actionName: string): Promise<void> {
290
293
  return this.core.reportPeer(peer, action, actionName);
291
294
  }
@@ -621,7 +624,7 @@ export class Network implements INetwork {
621
624
  async sendDataColumnSidecarsByRange(
622
625
  peerId: PeerIdStr,
623
626
  request: fulu.DataColumnSidecarsByRangeRequest
624
- ): Promise<fulu.DataColumnSidecar[]> {
627
+ ): Promise<DataColumnSidecar[]> {
625
628
  return collectMaxResponseTyped(
626
629
  this.sendReqRespRequest(peerId, ReqRespMethod.DataColumnSidecarsByRange, [Version.V1], request),
627
630
  request.count * request.columns.length,
@@ -632,7 +635,7 @@ export class Network implements INetwork {
632
635
  async sendDataColumnSidecarsByRoot(
633
636
  peerId: PeerIdStr,
634
637
  request: DataColumnSidecarsByRootRequest
635
- ): Promise<fulu.DataColumnSidecar[]> {
638
+ ): Promise<DataColumnSidecar[]> {
636
639
  return collectMaxResponseTyped(
637
640
  this.sendReqRespRequest(peerId, ReqRespMethod.DataColumnSidecarsByRoot, [Version.V1], request),
638
641
  request.reduce((total, {columns}) => total + columns.length, 0),
@@ -812,7 +815,7 @@ export class Network implements INetwork {
812
815
  this.core.setTargetGroupCount(count);
813
816
  };
814
817
 
815
- private onPublishDataColumns = (sidecars: DataColumnSidecars): Promise<number[]> => {
818
+ private onPublishDataColumns = (sidecars: DataColumnSidecar[]): Promise<number[]> => {
816
819
  return promiseAllMaybeAsync(sidecars.map((sidecar) => () => this.publishDataColumnSidecar(sidecar)));
817
820
  };
818
821
 
@@ -55,7 +55,12 @@ export const defaultNetworkOptions: NetworkOptions = {
55
55
  maxPeers: 210, // Allow some room above targetPeers for new inbound peers
56
56
  targetPeers: 200,
57
57
  // In CLI usage this is typically overridden; when unset it serves as a fallback default (e.g. programmatic usage/tests)
58
- localMultiaddrs: ["/ip4/0.0.0.0/tcp/9000", "/ip6/::/tcp/9000"],
58
+ localMultiaddrs: [
59
+ "/ip4/0.0.0.0/udp/9001/quic-v1",
60
+ "/ip6/::/udp/9001/quic-v1",
61
+ "/ip4/0.0.0.0/tcp/9000",
62
+ "/ip6/::/tcp/9000",
63
+ ],
59
64
  bootMultiaddrs: [],
60
65
  /** disabled by default */
61
66
  discv5: null,
@@ -69,7 +74,7 @@ export const defaultNetworkOptions: NetworkOptions = {
69
74
  slotsToSubscribeBeforeAggregatorDuty: 2,
70
75
  // This will enable the light client server by default
71
76
  disableLightClientServer: false,
72
- quic: false,
77
+ quic: true,
73
78
  tcp: true,
74
79
  // specific option for fulu
75
80
  // - this is the same to TARGET_SUBNET_PEERS
@@ -1,23 +1,25 @@
1
- import {ForkName, isForkPostGloas} from "@lodestar/params";
1
+ import {ForkName, ForkSeq} from "@lodestar/params";
2
2
  import {SlotOptionalRoot, SlotRootHex} from "@lodestar/types";
3
3
  import {
4
4
  getBeaconBlockRootFromDataColumnSidecarSerialized,
5
- getBeaconBlockRootFromExecutionPayloadEnvelopeSerialized,
6
5
  getBlockRootFromBeaconAttestationSerialized,
6
+ getBlockRootFromPayloadAttestationMessageSerialized,
7
7
  getBlockRootFromSignedAggregateAndProofSerialized,
8
8
  getSlotFromBeaconAttestationSerialized,
9
9
  getSlotFromBlobSidecarSerialized,
10
10
  getSlotFromDataColumnSidecarSerialized,
11
11
  getSlotFromExecutionPayloadEnvelopeSerialized,
12
+ getSlotFromPayloadAttestationMessageSerialized,
12
13
  getSlotFromSignedAggregateAndProofSerialized,
13
14
  getSlotFromSignedBeaconBlockSerialized,
15
+ getSlotFromSignedExecutionPayloadBidSerialized,
14
16
  } from "../../util/sszBytes.js";
15
17
  import {GossipType} from "../gossip/index.js";
16
18
  import {ExtractSlotRootFns} from "./types.js";
17
19
 
18
20
  /**
19
21
  * Extract the slot and block root of a gossip message form serialized data.
20
- * Not applicable for all topics.
22
+ * Only do it for messages that have a slot and block root, and we want to await the block if the block root is not known.
21
23
  */
22
24
  export function createExtractBlockSlotRootFns(): ExtractSlotRootFns {
23
25
  return {
@@ -57,21 +59,45 @@ export function createExtractBlockSlotRootFns(): ExtractSlotRootFns {
57
59
  },
58
60
  [GossipType.data_column_sidecar]: (data: Uint8Array, fork: ForkName): SlotOptionalRoot | null => {
59
61
  const slot = getSlotFromDataColumnSidecarSerialized(data, fork);
62
+
60
63
  if (slot === null) {
61
64
  return null;
62
65
  }
63
66
 
64
- const root = isForkPostGloas(fork) ? getBeaconBlockRootFromDataColumnSidecarSerialized(data) : null;
67
+ if (ForkSeq[fork] < ForkSeq.gloas) {
68
+ return {slot};
69
+ }
70
+
71
+ const root = getBeaconBlockRootFromDataColumnSidecarSerialized(data);
72
+ // null root means the message is invalid here and will be ignored in gossip handler later
73
+ // returning the slot here helps check the earliest permissable slot in the network processor
65
74
  return root !== null ? {slot, root} : {slot};
66
75
  },
67
- [GossipType.execution_payload]: (data: Uint8Array): SlotRootHex | null => {
76
+ [GossipType.execution_payload]: (data: Uint8Array): SlotOptionalRoot | null => {
68
77
  const slot = getSlotFromExecutionPayloadEnvelopeSerialized(data);
69
- const root = getBeaconBlockRootFromExecutionPayloadEnvelopeSerialized(data);
78
+ // Do not extract the root here; the network processor will extract it in the 2nd round to trigger block search without awaiting.
79
+ if (slot === null) {
80
+ return null;
81
+ }
82
+ return {slot};
83
+ },
84
+ [GossipType.payload_attestation_message]: (data: Uint8Array): SlotRootHex | null => {
85
+ const slot = getSlotFromPayloadAttestationMessageSerialized(data);
86
+ const root = getBlockRootFromPayloadAttestationMessageSerialized(data);
70
87
 
71
88
  if (slot === null || root === null) {
72
89
  return null;
73
90
  }
74
91
  return {slot, root};
75
92
  },
93
+ [GossipType.execution_payload_bid]: (data: Uint8Array): SlotOptionalRoot | null => {
94
+ const slot = getSlotFromSignedExecutionPayloadBidSerialized(data);
95
+
96
+ if (slot === null) {
97
+ return null;
98
+ }
99
+
100
+ return {slot};
101
+ },
76
102
  };
77
103
  }