@lodestar/beacon-node 1.42.0-dev.efc1ab8e31 → 1.42.0-dev.f866249fa3
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/lib/api/impl/beacon/blocks/index.d.ts.map +1 -1
- package/lib/api/impl/beacon/blocks/index.js +11 -11
- package/lib/api/impl/beacon/blocks/index.js.map +1 -1
- package/lib/api/impl/beacon/pool/index.d.ts.map +1 -1
- package/lib/api/impl/beacon/pool/index.js +4 -0
- package/lib/api/impl/beacon/pool/index.js.map +1 -1
- package/lib/api/impl/beacon/state/index.d.ts.map +1 -1
- package/lib/api/impl/beacon/state/index.js +13 -10
- package/lib/api/impl/beacon/state/index.js.map +1 -1
- package/lib/api/impl/debug/index.js.map +1 -1
- package/lib/api/impl/lodestar/index.d.ts.map +1 -1
- package/lib/api/impl/lodestar/index.js +4 -0
- package/lib/api/impl/lodestar/index.js.map +1 -1
- package/lib/api/impl/validator/index.d.ts.map +1 -1
- package/lib/api/impl/validator/index.js +7 -1
- package/lib/api/impl/validator/index.js.map +1 -1
- package/lib/chain/ColumnReconstructionTracker.d.ts +2 -1
- package/lib/chain/ColumnReconstructionTracker.d.ts.map +1 -1
- package/lib/chain/ColumnReconstructionTracker.js +5 -5
- package/lib/chain/ColumnReconstructionTracker.js.map +1 -1
- package/lib/chain/GetBlobsTracker.d.ts +2 -1
- package/lib/chain/GetBlobsTracker.d.ts.map +1 -1
- package/lib/chain/GetBlobsTracker.js +14 -12
- package/lib/chain/GetBlobsTracker.js.map +1 -1
- package/lib/chain/blocks/blockInput/blockInput.d.ts +5 -5
- package/lib/chain/blocks/blockInput/blockInput.d.ts.map +1 -1
- package/lib/chain/blocks/blockInput/blockInput.js.map +1 -1
- package/lib/chain/blocks/blockInput/types.d.ts +4 -4
- package/lib/chain/blocks/blockInput/types.d.ts.map +1 -1
- package/lib/chain/blocks/importBlock.d.ts.map +1 -1
- package/lib/chain/blocks/importBlock.js +19 -5
- package/lib/chain/blocks/importBlock.js.map +1 -1
- package/lib/chain/blocks/importExecutionPayload.d.ts.map +1 -1
- package/lib/chain/blocks/importExecutionPayload.js +7 -1
- package/lib/chain/blocks/importExecutionPayload.js.map +1 -1
- package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.d.ts +14 -6
- package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.d.ts.map +1 -1
- package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.js +33 -2
- package/lib/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.js.map +1 -1
- package/lib/chain/blocks/payloadEnvelopeInput/types.d.ts +2 -1
- package/lib/chain/blocks/payloadEnvelopeInput/types.d.ts.map +1 -1
- package/lib/chain/blocks/verifyBlocksExecutionPayloads.d.ts.map +1 -1
- package/lib/chain/blocks/verifyBlocksExecutionPayloads.js +3 -2
- package/lib/chain/blocks/verifyBlocksExecutionPayloads.js.map +1 -1
- package/lib/chain/blocks/verifyBlocksSignatures.d.ts.map +1 -1
- package/lib/chain/blocks/verifyBlocksSignatures.js +4 -2
- package/lib/chain/blocks/verifyBlocksSignatures.js.map +1 -1
- package/lib/chain/chain.d.ts +3 -2
- package/lib/chain/chain.d.ts.map +1 -1
- package/lib/chain/chain.js +64 -24
- package/lib/chain/chain.js.map +1 -1
- package/lib/chain/emitter.d.ts +29 -7
- package/lib/chain/emitter.d.ts.map +1 -1
- package/lib/chain/emitter.js +12 -3
- package/lib/chain/emitter.js.map +1 -1
- package/lib/chain/errors/dataColumnSidecarError.d.ts +31 -1
- package/lib/chain/errors/dataColumnSidecarError.d.ts.map +1 -1
- package/lib/chain/errors/dataColumnSidecarError.js +7 -0
- package/lib/chain/errors/dataColumnSidecarError.js.map +1 -1
- package/lib/chain/forkChoice/index.d.ts.map +1 -1
- package/lib/chain/forkChoice/index.js +10 -8
- package/lib/chain/forkChoice/index.js.map +1 -1
- package/lib/chain/interface.d.ts +4 -2
- package/lib/chain/interface.d.ts.map +1 -1
- package/lib/chain/lightClient/index.d.ts +2 -2
- package/lib/chain/lightClient/index.d.ts.map +1 -1
- package/lib/chain/lightClient/index.js.map +1 -1
- package/lib/chain/opPools/aggregatedAttestationPool.d.ts.map +1 -1
- package/lib/chain/opPools/aggregatedAttestationPool.js +5 -2
- package/lib/chain/opPools/aggregatedAttestationPool.js.map +1 -1
- package/lib/chain/prepareNextSlot.d.ts.map +1 -1
- package/lib/chain/prepareNextSlot.js +7 -1
- package/lib/chain/prepareNextSlot.js.map +1 -1
- package/lib/chain/produceBlock/computeNewStateRoot.d.ts +2 -2
- package/lib/chain/produceBlock/computeNewStateRoot.d.ts.map +1 -1
- package/lib/chain/produceBlock/computeNewStateRoot.js.map +1 -1
- package/lib/chain/produceBlock/produceBlockBody.d.ts +3 -3
- package/lib/chain/produceBlock/produceBlockBody.d.ts.map +1 -1
- package/lib/chain/produceBlock/produceBlockBody.js +10 -1
- package/lib/chain/produceBlock/produceBlockBody.js.map +1 -1
- package/lib/chain/seenCache/seenGossipBlockInput.d.ts +1 -1
- package/lib/chain/seenCache/seenGossipBlockInput.d.ts.map +1 -1
- package/lib/chain/seenCache/seenGossipBlockInput.js +2 -2
- package/lib/chain/seenCache/seenGossipBlockInput.js.map +1 -1
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.d.ts +1 -1
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.d.ts.map +1 -1
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.js +2 -2
- package/lib/chain/seenCache/seenPayloadEnvelopeInput.js.map +1 -1
- package/lib/chain/validation/block.d.ts.map +1 -1
- package/lib/chain/validation/block.js +2 -2
- package/lib/chain/validation/block.js.map +1 -1
- package/lib/chain/validation/dataColumnSidecar.d.ts +11 -4
- package/lib/chain/validation/dataColumnSidecar.d.ts.map +1 -1
- package/lib/chain/validation/dataColumnSidecar.js +184 -5
- package/lib/chain/validation/dataColumnSidecar.js.map +1 -1
- package/lib/chain/validation/executionPayloadBid.d.ts.map +1 -1
- package/lib/chain/validation/executionPayloadBid.js +4 -1
- package/lib/chain/validation/executionPayloadBid.js.map +1 -1
- package/lib/chain/validation/executionPayloadEnvelope.d.ts.map +1 -1
- package/lib/chain/validation/executionPayloadEnvelope.js +4 -1
- package/lib/chain/validation/executionPayloadEnvelope.js.map +1 -1
- package/lib/chain/validation/payloadAttestationMessage.d.ts.map +1 -1
- package/lib/chain/validation/payloadAttestationMessage.js +4 -1
- package/lib/chain/validation/payloadAttestationMessage.js.map +1 -1
- package/lib/chain/validation/syncCommittee.d.ts.map +1 -1
- package/lib/chain/validation/syncCommittee.js +4 -0
- package/lib/chain/validation/syncCommittee.js.map +1 -1
- package/lib/chain/validation/syncCommitteeContributionAndProof.js +4 -1
- package/lib/chain/validation/syncCommitteeContributionAndProof.js.map +1 -1
- package/lib/chain/validatorMonitor.d.ts.map +1 -1
- package/lib/chain/validatorMonitor.js +3 -3
- package/lib/chain/validatorMonitor.js.map +1 -1
- package/lib/db/buckets.d.ts +2 -2
- package/lib/db/buckets.d.ts.map +1 -1
- package/lib/db/buckets.js +2 -2
- package/lib/db/buckets.js.map +1 -1
- package/lib/db/repositories/blockArchiveIndex.d.ts +2 -2
- package/lib/db/repositories/blockArchiveIndex.d.ts.map +1 -1
- package/lib/db/repositories/dataColumnSidecar.d.ts.map +1 -1
- package/lib/db/repositories/dataColumnSidecar.js +4 -2
- package/lib/db/repositories/dataColumnSidecar.js.map +1 -1
- package/lib/db/repositories/dataColumnSidecarArchive.d.ts.map +1 -1
- package/lib/db/repositories/dataColumnSidecarArchive.js +4 -2
- package/lib/db/repositories/dataColumnSidecarArchive.js.map +1 -1
- package/lib/metrics/metrics/lodestar.d.ts +20 -0
- package/lib/metrics/metrics/lodestar.d.ts.map +1 -1
- package/lib/metrics/metrics/lodestar.js +33 -0
- package/lib/metrics/metrics/lodestar.js.map +1 -1
- package/lib/network/gossip/topic.d.ts +727 -0
- package/lib/network/gossip/topic.d.ts.map +1 -1
- package/lib/network/interface.d.ts +3 -2
- package/lib/network/interface.d.ts.map +1 -1
- package/lib/network/libp2p/index.d.ts.map +1 -1
- package/lib/network/libp2p/index.js +19 -13
- package/lib/network/libp2p/index.js.map +1 -1
- package/lib/network/network.d.ts +3 -2
- package/lib/network/network.d.ts.map +1 -1
- package/lib/network/network.js +3 -0
- package/lib/network/network.js.map +1 -1
- package/lib/network/options.d.ts.map +1 -1
- package/lib/network/options.js +7 -2
- package/lib/network/options.js.map +1 -1
- package/lib/network/processor/extractSlotRootFns.d.ts +1 -1
- package/lib/network/processor/extractSlotRootFns.d.ts.map +1 -1
- package/lib/network/processor/extractSlotRootFns.js +25 -5
- package/lib/network/processor/extractSlotRootFns.js.map +1 -1
- package/lib/network/processor/gossipHandlers.d.ts.map +1 -1
- package/lib/network/processor/gossipHandlers.js +242 -66
- package/lib/network/processor/gossipHandlers.js.map +1 -1
- package/lib/network/processor/index.d.ts +11 -1
- package/lib/network/processor/index.d.ts.map +1 -1
- package/lib/network/processor/index.js +234 -22
- package/lib/network/processor/index.js.map +1 -1
- package/lib/network/reqresp/types.d.ts +3 -3
- package/lib/network/reqresp/types.d.ts.map +1 -1
- package/lib/network/reqresp/types.js +9 -3
- package/lib/network/reqresp/types.js.map +1 -1
- package/lib/node/nodejs.d.ts.map +1 -1
- package/lib/node/nodejs.js +4 -1
- package/lib/node/nodejs.js.map +1 -1
- package/lib/node/notifier.d.ts.map +1 -1
- package/lib/node/notifier.js +2 -2
- package/lib/node/notifier.js.map +1 -1
- package/lib/sync/unknownBlock.js +2 -2
- package/lib/sync/unknownBlock.js.map +1 -1
- package/lib/sync/utils/downloadByRange.d.ts +3 -3
- package/lib/sync/utils/downloadByRange.d.ts.map +1 -1
- package/lib/sync/utils/downloadByRange.js +4 -2
- package/lib/sync/utils/downloadByRange.js.map +1 -1
- package/lib/sync/utils/downloadByRoot.d.ts +3 -3
- package/lib/sync/utils/downloadByRoot.d.ts.map +1 -1
- package/lib/sync/utils/downloadByRoot.js +10 -5
- package/lib/sync/utils/downloadByRoot.js.map +1 -1
- package/lib/util/blobs.d.ts +3 -3
- package/lib/util/blobs.d.ts.map +1 -1
- package/lib/util/blobs.js +21 -10
- package/lib/util/blobs.js.map +1 -1
- package/lib/util/dataColumns.d.ts +18 -11
- package/lib/util/dataColumns.d.ts.map +1 -1
- package/lib/util/dataColumns.js +51 -17
- package/lib/util/dataColumns.js.map +1 -1
- package/lib/util/execution.d.ts +6 -2
- package/lib/util/execution.d.ts.map +1 -1
- package/lib/util/execution.js +49 -25
- package/lib/util/execution.js.map +1 -1
- package/lib/util/sszBytes.d.ts +25 -1
- package/lib/util/sszBytes.d.ts.map +1 -1
- package/lib/util/sszBytes.js +189 -2
- package/lib/util/sszBytes.js.map +1 -1
- package/package.json +15 -15
- package/src/api/impl/beacon/blocks/index.ts +17 -14
- package/src/api/impl/beacon/pool/index.ts +4 -0
- package/src/api/impl/beacon/state/index.ts +15 -15
- package/src/api/impl/debug/index.ts +2 -2
- package/src/api/impl/lodestar/index.ts +4 -0
- package/src/api/impl/validator/index.ts +7 -0
- package/src/chain/ColumnReconstructionTracker.ts +6 -5
- package/src/chain/GetBlobsTracker.ts +14 -12
- package/src/chain/blocks/blockInput/blockInput.ts +8 -8
- package/src/chain/blocks/blockInput/types.ts +4 -4
- package/src/chain/blocks/importBlock.ts +29 -8
- package/src/chain/blocks/importExecutionPayload.ts +7 -1
- package/src/chain/blocks/payloadEnvelopeInput/payloadEnvelopeInput.ts +53 -12
- package/src/chain/blocks/payloadEnvelopeInput/types.ts +2 -1
- package/src/chain/blocks/verifyBlocksExecutionPayloads.ts +2 -1
- package/src/chain/blocks/verifyBlocksSignatures.ts +9 -2
- package/src/chain/chain.ts +73 -28
- package/src/chain/emitter.ts +25 -7
- package/src/chain/errors/dataColumnSidecarError.ts +32 -1
- package/src/chain/forkChoice/index.ts +11 -8
- package/src/chain/interface.ts +4 -2
- package/src/chain/lightClient/index.ts +7 -3
- package/src/chain/opPools/aggregatedAttestationPool.ts +6 -1
- package/src/chain/prepareNextSlot.ts +8 -0
- package/src/chain/produceBlock/computeNewStateRoot.ts +2 -1
- package/src/chain/produceBlock/produceBlockBody.ts +25 -5
- package/src/chain/seenCache/seenGossipBlockInput.ts +2 -2
- package/src/chain/seenCache/seenPayloadEnvelopeInput.ts +2 -2
- package/src/chain/validation/block.ts +2 -1
- package/src/chain/validation/dataColumnSidecar.ts +230 -7
- package/src/chain/validation/executionPayloadBid.ts +4 -0
- package/src/chain/validation/executionPayloadEnvelope.ts +8 -1
- package/src/chain/validation/payloadAttestationMessage.ts +4 -0
- package/src/chain/validation/syncCommittee.ts +5 -1
- package/src/chain/validation/syncCommitteeContributionAndProof.ts +5 -1
- package/src/chain/validatorMonitor.ts +3 -2
- package/src/db/buckets.ts +2 -2
- package/src/db/repositories/dataColumnSidecar.ts +4 -2
- package/src/db/repositories/dataColumnSidecarArchive.ts +4 -2
- package/src/metrics/metrics/lodestar.ts +34 -0
- package/src/network/interface.ts +3 -2
- package/src/network/libp2p/index.ts +21 -15
- package/src/network/network.ts +7 -4
- package/src/network/options.ts +7 -2
- package/src/network/processor/extractSlotRootFns.ts +32 -6
- package/src/network/processor/gossipHandlers.ts +305 -79
- package/src/network/processor/index.ts +304 -22
- package/src/network/reqresp/types.ts +13 -5
- package/src/node/nodejs.ts +5 -2
- package/src/node/notifier.ts +7 -2
- package/src/sync/unknownBlock.ts +3 -3
- package/src/sync/utils/downloadByRange.ts +9 -7
- package/src/sync/utils/downloadByRoot.ts +16 -12
- package/src/util/blobs.ts +35 -15
- package/src/util/dataColumns.ts +69 -25
- package/src/util/execution.ts +49 -30
- package/src/util/sszBytes.ts +245 -3
package/src/chain/chain.ts
CHANGED
|
@@ -15,9 +15,9 @@ import {
|
|
|
15
15
|
BUILDER_INDEX_SELF_BUILD,
|
|
16
16
|
EFFECTIVE_BALANCE_INCREMENT,
|
|
17
17
|
type ForkPostFulu,
|
|
18
|
+
type ForkPostGloas,
|
|
18
19
|
GENESIS_SLOT,
|
|
19
20
|
SLOTS_PER_EPOCH,
|
|
20
|
-
isForkPostElectra,
|
|
21
21
|
isForkPostGloas,
|
|
22
22
|
} from "@lodestar/params";
|
|
23
23
|
import {
|
|
@@ -29,12 +29,15 @@ import {
|
|
|
29
29
|
computeEpochAtSlot,
|
|
30
30
|
computeStartSlotAtEpoch,
|
|
31
31
|
getEffectiveBalancesFromStateBytes,
|
|
32
|
+
isStatePostAltair,
|
|
33
|
+
isStatePostElectra,
|
|
34
|
+
isStatePostGloas,
|
|
32
35
|
} from "@lodestar/state-transition";
|
|
33
36
|
import {
|
|
34
37
|
BeaconBlock,
|
|
35
38
|
BlindedBeaconBlock,
|
|
36
39
|
BlindedBeaconBlockBody,
|
|
37
|
-
|
|
40
|
+
DataColumnSidecar,
|
|
38
41
|
Epoch,
|
|
39
42
|
Root,
|
|
40
43
|
RootHex,
|
|
@@ -504,7 +507,11 @@ export class BeaconChain implements IBeaconChain {
|
|
|
504
507
|
}
|
|
505
508
|
|
|
506
509
|
seenBlock(blockRoot: RootHex): boolean {
|
|
507
|
-
return this.seenBlockInputCache.
|
|
510
|
+
return this.seenBlockInputCache.hasBlock(blockRoot) || this.forkChoice.hasBlockHexUnsafe(blockRoot);
|
|
511
|
+
}
|
|
512
|
+
|
|
513
|
+
seenPayloadEnvelope(blockRoot: RootHex): boolean {
|
|
514
|
+
return this.seenPayloadEnvelopeInputCache.hasPayload(blockRoot) || this.forkChoice.hasPayloadHexUnsafe(blockRoot);
|
|
508
515
|
}
|
|
509
516
|
|
|
510
517
|
regenCanAcceptWork(): boolean {
|
|
@@ -873,20 +880,32 @@ export class BeaconChain implements IBeaconChain {
|
|
|
873
880
|
);
|
|
874
881
|
}
|
|
875
882
|
|
|
876
|
-
async getDataColumnSidecars(blockSlot: Slot, blockRootHex: string): Promise<
|
|
877
|
-
const
|
|
878
|
-
|
|
879
|
-
|
|
880
|
-
|
|
883
|
+
async getDataColumnSidecars(blockSlot: Slot, blockRootHex: string): Promise<DataColumnSidecar[]> {
|
|
884
|
+
const fork = this.config.getForkName(blockSlot);
|
|
885
|
+
|
|
886
|
+
if (isForkPostGloas(fork)) {
|
|
887
|
+
// After gloas, columns are tracked in PayloadEnvelopeInput
|
|
888
|
+
const payloadInput = this.seenPayloadEnvelopeInputCache.get(blockRootHex);
|
|
889
|
+
if (payloadInput) {
|
|
890
|
+
return payloadInput.getAllColumns();
|
|
891
|
+
}
|
|
892
|
+
} else {
|
|
893
|
+
// Before gloas, columns are tracked in BlockInput
|
|
894
|
+
const blockInput = this.seenBlockInputCache.get(blockRootHex);
|
|
895
|
+
if (blockInput) {
|
|
896
|
+
if (!isBlockInputColumns(blockInput)) {
|
|
897
|
+
throw new Error(`Expected block input to have columns: slot=${blockSlot} root=${blockRootHex}`);
|
|
898
|
+
}
|
|
899
|
+
return blockInput.getAllColumns();
|
|
881
900
|
}
|
|
882
|
-
return blockInput.getAllColumns();
|
|
883
901
|
}
|
|
902
|
+
|
|
884
903
|
const sidecarsUnfinalized = await this.db.dataColumnSidecar.values(fromHex(blockRootHex));
|
|
885
904
|
if (sidecarsUnfinalized.length > 0) {
|
|
886
|
-
return sidecarsUnfinalized
|
|
905
|
+
return sidecarsUnfinalized;
|
|
887
906
|
}
|
|
888
907
|
const sidecarsFinalized = await this.db.dataColumnSidecarArchive.values(blockSlot);
|
|
889
|
-
return sidecarsFinalized
|
|
908
|
+
return sidecarsFinalized;
|
|
890
909
|
}
|
|
891
910
|
|
|
892
911
|
async getSerializedDataColumnSidecars(
|
|
@@ -894,23 +913,45 @@ export class BeaconChain implements IBeaconChain {
|
|
|
894
913
|
blockRootHex: string,
|
|
895
914
|
indices: number[]
|
|
896
915
|
): Promise<(Uint8Array | undefined)[]> {
|
|
897
|
-
const
|
|
898
|
-
|
|
899
|
-
|
|
900
|
-
|
|
916
|
+
const fork = this.config.getForkName(blockSlot);
|
|
917
|
+
|
|
918
|
+
if (isForkPostGloas(fork)) {
|
|
919
|
+
// After gloas, columns are tracked in PayloadEnvelopeInput
|
|
920
|
+
const payloadInput = this.seenPayloadEnvelopeInputCache.get(blockRootHex);
|
|
921
|
+
if (payloadInput) {
|
|
922
|
+
return indices.map((index) => {
|
|
923
|
+
const sidecar = payloadInput.getColumn(index);
|
|
924
|
+
if (!sidecar) {
|
|
925
|
+
return undefined;
|
|
926
|
+
}
|
|
927
|
+
const serialized = this.serializedCache.get(sidecar);
|
|
928
|
+
if (serialized) {
|
|
929
|
+
return serialized;
|
|
930
|
+
}
|
|
931
|
+
return sszTypesFor(fork as ForkPostGloas).DataColumnSidecar.serialize(sidecar);
|
|
932
|
+
});
|
|
901
933
|
}
|
|
902
|
-
|
|
903
|
-
|
|
904
|
-
|
|
905
|
-
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
if (serialized) {
|
|
909
|
-
return serialized;
|
|
934
|
+
} else {
|
|
935
|
+
// Before gloas, columns are tracked in BlockInput
|
|
936
|
+
const blockInput = this.seenBlockInputCache.get(blockRootHex);
|
|
937
|
+
if (blockInput) {
|
|
938
|
+
if (!isBlockInputColumns(blockInput)) {
|
|
939
|
+
throw new Error(`Expected block input to have columns: slot=${blockSlot} root=${blockRootHex}`);
|
|
910
940
|
}
|
|
911
|
-
return
|
|
912
|
-
|
|
941
|
+
return indices.map((index) => {
|
|
942
|
+
const sidecar = blockInput.getColumn(index);
|
|
943
|
+
if (!sidecar) {
|
|
944
|
+
return undefined;
|
|
945
|
+
}
|
|
946
|
+
const serialized = this.serializedCache.get(sidecar);
|
|
947
|
+
if (serialized) {
|
|
948
|
+
return serialized;
|
|
949
|
+
}
|
|
950
|
+
return sszTypesFor(blockInput.forkName as ForkPostFulu).DataColumnSidecar.serialize(sidecar);
|
|
951
|
+
});
|
|
952
|
+
}
|
|
913
953
|
}
|
|
954
|
+
|
|
914
955
|
const sidecarsUnfinalized = await this.db.dataColumnSidecar.getManyBinary(fromHex(blockRootHex), indices);
|
|
915
956
|
if (sidecarsUnfinalized.some((sidecar) => sidecar != null)) {
|
|
916
957
|
return sidecarsUnfinalized;
|
|
@@ -1037,6 +1078,9 @@ export class BeaconChain implements IBeaconChain {
|
|
|
1037
1078
|
slot,
|
|
1038
1079
|
stateRoot: ZERO_HASH,
|
|
1039
1080
|
};
|
|
1081
|
+
if (!isStatePostGloas(postState)) {
|
|
1082
|
+
throw Error(`Expected gloas+ post-state for execution payload envelope, got fork=${postState.forkName}`);
|
|
1083
|
+
}
|
|
1040
1084
|
const envelopeStateRoot = computeEnvelopeStateRoot(this.metrics, postState, envelope);
|
|
1041
1085
|
gloasResult.envelopeStateRoot = envelopeStateRoot;
|
|
1042
1086
|
}
|
|
@@ -1365,9 +1409,7 @@ export class BeaconChain implements IBeaconChain {
|
|
|
1365
1409
|
metrics.chain.blacklistedBlocks.set(this.blacklistedBlocks.size);
|
|
1366
1410
|
|
|
1367
1411
|
const headState = this.getHeadState();
|
|
1368
|
-
|
|
1369
|
-
|
|
1370
|
-
if (isForkPostElectra(fork)) {
|
|
1412
|
+
if (isStatePostElectra(headState)) {
|
|
1371
1413
|
metrics.pendingDeposits.set(headState.pendingDepositsCount);
|
|
1372
1414
|
metrics.pendingPartialWithdrawals.set(headState.pendingPartialWithdrawalsCount);
|
|
1373
1415
|
metrics.pendingConsolidations.set(headState.pendingConsolidationsCount);
|
|
@@ -1614,6 +1656,9 @@ export class BeaconChain implements IBeaconChain {
|
|
|
1614
1656
|
}
|
|
1615
1657
|
|
|
1616
1658
|
preState = preState.processSlots(block.slot); // Dial preState's slot to block.slot
|
|
1659
|
+
if (!isStatePostAltair(preState)) {
|
|
1660
|
+
throw new Error("Sync committee rewards are not supported before Altair");
|
|
1661
|
+
}
|
|
1617
1662
|
|
|
1618
1663
|
return preState.computeSyncCommitteeRewards(block, validatorIds ?? []);
|
|
1619
1664
|
}
|
package/src/chain/emitter.ts
CHANGED
|
@@ -3,7 +3,8 @@ import {StrictEventEmitter} from "strict-event-emitter-types";
|
|
|
3
3
|
import {routes} from "@lodestar/api";
|
|
4
4
|
import {CheckpointWithPayloadStatus} from "@lodestar/fork-choice";
|
|
5
5
|
import {IBeaconStateView} from "@lodestar/state-transition";
|
|
6
|
-
import {
|
|
6
|
+
import {DataColumnSidecar, RootHex, deneb, phase0} from "@lodestar/types";
|
|
7
|
+
import {SignedExecutionPayloadEnvelope} from "@lodestar/types/gloas";
|
|
7
8
|
import {PeerIdStr} from "../util/peerId.js";
|
|
8
9
|
import {BlockInputSource, IBlockInput} from "./blocks/blockInput/types.js";
|
|
9
10
|
|
|
@@ -54,13 +55,22 @@ export enum ChainEvent {
|
|
|
54
55
|
*/
|
|
55
56
|
updateStatus = "updateStatus",
|
|
56
57
|
/**
|
|
57
|
-
* Trigger
|
|
58
|
+
* Trigger BlockInputSync to find parent of a SignedBeaconBlock received
|
|
59
|
+
* Post-gloas, missing parent could be a SignedBeaconBlock and/or a SignedExecutionPayloadEnvelope
|
|
58
60
|
*/
|
|
59
|
-
|
|
61
|
+
blockUnknownParent = "blockUnknownParent",
|
|
60
62
|
/**
|
|
61
|
-
* Trigger BlockInputSync
|
|
63
|
+
* Trigger BlockInputSync to find a SignedBeaconBlock given a SignedExecutionPayloadEnvelop received
|
|
64
|
+
*/
|
|
65
|
+
envelopeUnknownBlock = "envelopeUnknownBlock",
|
|
66
|
+
/**
|
|
67
|
+
* Trigger BlockInputSync to find a SignedBeaconBlock with specified block root.
|
|
62
68
|
*/
|
|
63
69
|
unknownBlockRoot = "unknownBlockRoot",
|
|
70
|
+
/**
|
|
71
|
+
* Trigger BlockInputSync to find a SignedExecutionPayloadEnvelope with specified block root.
|
|
72
|
+
*/
|
|
73
|
+
unknownEnvelopeBlockRoot = "unknownEnvelopeBlockRoot",
|
|
64
74
|
/**
|
|
65
75
|
* Trigger BlockInputSync for blocks that are partially received via gossip but are not complete by time the
|
|
66
76
|
* cut-off window passes for waiting on gossip
|
|
@@ -75,9 +85,15 @@ export type ReorgEventData = routes.events.EventData[routes.events.EventType.cha
|
|
|
75
85
|
type ApiEvents = {[K in routes.events.EventType]: (data: routes.events.EventData[K]) => void};
|
|
76
86
|
|
|
77
87
|
export type ChainEventData = {
|
|
78
|
-
[ChainEvent.
|
|
88
|
+
[ChainEvent.blockUnknownParent]: {blockInput: IBlockInput; peer: PeerIdStr; source: BlockInputSource};
|
|
89
|
+
[ChainEvent.envelopeUnknownBlock]: {
|
|
90
|
+
envelope: SignedExecutionPayloadEnvelope;
|
|
91
|
+
peer?: PeerIdStr;
|
|
92
|
+
source: BlockInputSource;
|
|
93
|
+
};
|
|
79
94
|
[ChainEvent.unknownBlockRoot]: {rootHex: RootHex; peer?: PeerIdStr; source: BlockInputSource};
|
|
80
95
|
[ChainEvent.incompleteBlockInput]: {blockInput: IBlockInput; peer: PeerIdStr; source: BlockInputSource};
|
|
96
|
+
[ChainEvent.unknownEnvelopeBlockRoot]: {rootHex: RootHex; peer?: PeerIdStr; source: BlockInputSource};
|
|
81
97
|
};
|
|
82
98
|
|
|
83
99
|
export type IChainEvents = ApiEvents & {
|
|
@@ -88,7 +104,7 @@ export type IChainEvents = ApiEvents & {
|
|
|
88
104
|
|
|
89
105
|
[ChainEvent.updateTargetCustodyGroupCount]: (targetGroupCount: number) => void;
|
|
90
106
|
|
|
91
|
-
[ChainEvent.publishDataColumns]: (sidecars:
|
|
107
|
+
[ChainEvent.publishDataColumns]: (sidecars: DataColumnSidecar[]) => void;
|
|
92
108
|
|
|
93
109
|
[ChainEvent.publishBlobSidecars]: (sidecars: deneb.BlobSidecar[]) => void;
|
|
94
110
|
|
|
@@ -96,9 +112,11 @@ export type IChainEvents = ApiEvents & {
|
|
|
96
112
|
|
|
97
113
|
// Sync events that are chain->chain. Initiated from network requests but do not cross the network
|
|
98
114
|
// barrier so are considered ChainEvent(s).
|
|
99
|
-
[ChainEvent.
|
|
115
|
+
[ChainEvent.blockUnknownParent]: (data: ChainEventData[ChainEvent.blockUnknownParent]) => void;
|
|
116
|
+
[ChainEvent.envelopeUnknownBlock]: (data: ChainEventData[ChainEvent.envelopeUnknownBlock]) => void;
|
|
100
117
|
[ChainEvent.unknownBlockRoot]: (data: ChainEventData[ChainEvent.unknownBlockRoot]) => void;
|
|
101
118
|
[ChainEvent.incompleteBlockInput]: (data: ChainEventData[ChainEvent.incompleteBlockInput]) => void;
|
|
119
|
+
[ChainEvent.unknownEnvelopeBlockRoot]: (data: ChainEventData[ChainEvent.unknownEnvelopeBlockRoot]) => void;
|
|
102
120
|
};
|
|
103
121
|
|
|
104
122
|
/**
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import {ForkName} from "@lodestar/params";
|
|
1
2
|
import {RootHex, Slot, SubnetID} from "@lodestar/types";
|
|
2
3
|
import {LodestarError} from "@lodestar/utils";
|
|
3
4
|
import {GossipActionError} from "./gossipValidation.js";
|
|
@@ -6,6 +7,7 @@ export enum DataColumnSidecarErrorCode {
|
|
|
6
7
|
INVALID_INDEX = "DATA_COLUMN_SIDECAR_ERROR_INVALID_INDEX",
|
|
7
8
|
NO_COMMITMENTS = "DATA_COLUMN_SIDECAR_ERROR_NO_COMMITMENTS",
|
|
8
9
|
MISMATCHED_LENGTHS = "DATA_COLUMN_SIDECAR_ERROR_MISMATCHED_LENGTHS",
|
|
10
|
+
INCORRECT_TYPE = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_TYPE",
|
|
9
11
|
INVALID_SUBNET = "DATA_COLUMN_SIDECAR_ERROR_INVALID_SUBNET",
|
|
10
12
|
INVALID_KZG_PROOF = "DATA_COLUMN_SIDECAR_ERROR_INVALID_KZG_PROOF",
|
|
11
13
|
TOO_MANY_KZG_COMMITMENTS = "DATA_COLUMN_SIDECAR_ERROR_TOO_MANY_KZG_COMMITMENTS",
|
|
@@ -18,6 +20,10 @@ export enum DataColumnSidecarErrorCode {
|
|
|
18
20
|
INCORRECT_SIDECAR_COUNT = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_SIDECAR_COUNT",
|
|
19
21
|
/** Sidecar doesn't match block */
|
|
20
22
|
INCORRECT_BLOCK = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_BLOCK",
|
|
23
|
+
/** Sidecar slot doesn't match block slot */
|
|
24
|
+
INCORRECT_SIDECAR_SLOT = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_SIDECAR_SLOT",
|
|
25
|
+
/** Sidecar referenced block is not the expected block type */
|
|
26
|
+
INCORRECT_BLOCK_TYPE = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_BLOCK_TYPE",
|
|
21
27
|
/** Sidecar cell count not as expected */
|
|
22
28
|
INCORRECT_CELL_COUNT = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_CELL_COUNT",
|
|
23
29
|
/** Sidecar kzg proof count not as expected */
|
|
@@ -32,10 +38,12 @@ export enum DataColumnSidecarErrorCode {
|
|
|
32
38
|
FUTURE_SLOT = "DATA_COLUMN_SIDECAR_ERROR_FUTURE_SLOT",
|
|
33
39
|
WOULD_REVERT_FINALIZED_SLOT = "DATA_COLUMN_SIDECAR_ERROR_WOULD_REVERT_FINALIZED_SLOT",
|
|
34
40
|
PARENT_UNKNOWN = "DATA_COLUMN_SIDECAR_ERROR_PARENT_UNKNOWN",
|
|
41
|
+
BLOCK_UNKNOWN = "DATA_COLUMN_SIDECAR_ERROR_BLOCK_UNKNOWN",
|
|
35
42
|
NOT_LATER_THAN_PARENT = "DATA_COLUMN_SIDECAR_ERROR_NOT_LATER_THAN_PARENT",
|
|
36
43
|
PROPOSAL_SIGNATURE_INVALID = "DATA_COLUMN_SIDECAR_ERROR_PROPOSAL_SIGNATURE_INVALID",
|
|
37
44
|
INCLUSION_PROOF_INVALID = "DATA_COLUMN_SIDECAR_ERROR_INCLUSION_PROOF_INVALID",
|
|
38
45
|
INCORRECT_PROPOSER = "DATA_COLUMN_SIDECAR_ERROR_INCORRECT_PROPOSER",
|
|
46
|
+
PAYLOAD_ENVELOPE_INPUT_MISSING = "DATA_COLUMN_SIDECAR_ERROR_PAYLOAD_ENVELOPE_INPUT_MISSING",
|
|
39
47
|
}
|
|
40
48
|
|
|
41
49
|
export type DataColumnSidecarErrorType =
|
|
@@ -47,6 +55,12 @@ export type DataColumnSidecarErrorType =
|
|
|
47
55
|
commitmentsLength: number;
|
|
48
56
|
proofsLength: number;
|
|
49
57
|
}
|
|
58
|
+
| {
|
|
59
|
+
code: DataColumnSidecarErrorCode.INCORRECT_TYPE;
|
|
60
|
+
slot: Slot;
|
|
61
|
+
columnIndex: number;
|
|
62
|
+
fork: ForkName;
|
|
63
|
+
}
|
|
50
64
|
| {code: DataColumnSidecarErrorCode.INVALID_SUBNET; columnIndex: number; gossipSubnet: SubnetID}
|
|
51
65
|
| {
|
|
52
66
|
code: DataColumnSidecarErrorCode.TOO_MANY_KZG_COMMITMENTS;
|
|
@@ -63,6 +77,11 @@ export type DataColumnSidecarErrorType =
|
|
|
63
77
|
parentRoot: RootHex;
|
|
64
78
|
slot: Slot;
|
|
65
79
|
}
|
|
80
|
+
| {
|
|
81
|
+
code: DataColumnSidecarErrorCode.BLOCK_UNKNOWN;
|
|
82
|
+
blockRoot: RootHex;
|
|
83
|
+
slot: Slot;
|
|
84
|
+
}
|
|
66
85
|
| {
|
|
67
86
|
code: DataColumnSidecarErrorCode.PROPOSAL_SIGNATURE_INVALID;
|
|
68
87
|
slot: Slot;
|
|
@@ -80,6 +99,17 @@ export type DataColumnSidecarErrorType =
|
|
|
80
99
|
expected: string;
|
|
81
100
|
actual: string;
|
|
82
101
|
}
|
|
102
|
+
| {
|
|
103
|
+
code: DataColumnSidecarErrorCode.INCORRECT_BLOCK_TYPE;
|
|
104
|
+
slot: Slot;
|
|
105
|
+
columnIndex: number;
|
|
106
|
+
}
|
|
107
|
+
| {
|
|
108
|
+
code: DataColumnSidecarErrorCode.INCORRECT_SIDECAR_SLOT;
|
|
109
|
+
columnIndex: number;
|
|
110
|
+
expected: Slot;
|
|
111
|
+
actual: Slot;
|
|
112
|
+
}
|
|
83
113
|
| {
|
|
84
114
|
code: DataColumnSidecarErrorCode.INCORRECT_HEADER_ROOT;
|
|
85
115
|
slot: number;
|
|
@@ -97,7 +127,8 @@ export type DataColumnSidecarErrorType =
|
|
|
97
127
|
actual: number;
|
|
98
128
|
}
|
|
99
129
|
| {code: DataColumnSidecarErrorCode.INVALID_KZG_PROOF_BATCH; slot: number; reason: string}
|
|
100
|
-
| {code: DataColumnSidecarErrorCode.INCORRECT_PROPOSER; actualProposerIndex: number; expectedProposerIndex: number}
|
|
130
|
+
| {code: DataColumnSidecarErrorCode.INCORRECT_PROPOSER; actualProposerIndex: number; expectedProposerIndex: number}
|
|
131
|
+
| {code: DataColumnSidecarErrorCode.PAYLOAD_ENVELOPE_INPUT_MISSING; slot: Slot; blockRoot: RootHex};
|
|
101
132
|
|
|
102
133
|
export class DataColumnSidecarGossipError extends GossipActionError<DataColumnSidecarErrorType> {}
|
|
103
134
|
export class DataColumnSidecarValidationError extends LodestarError<DataColumnSidecarErrorType> {}
|
|
@@ -10,12 +10,14 @@ import {
|
|
|
10
10
|
ForkChoiceOpts as RawForkChoiceOpts,
|
|
11
11
|
getCheckpointPayloadStatus,
|
|
12
12
|
} from "@lodestar/fork-choice";
|
|
13
|
-
import {
|
|
13
|
+
import {ZERO_HASH_HEX} from "@lodestar/params";
|
|
14
14
|
import {
|
|
15
15
|
DataAvailabilityStatus,
|
|
16
16
|
IBeaconStateView,
|
|
17
17
|
computeEpochAtSlot,
|
|
18
18
|
computeStartSlotAtEpoch,
|
|
19
|
+
isStatePostBellatrix,
|
|
20
|
+
isStatePostGloas,
|
|
19
21
|
} from "@lodestar/state-transition";
|
|
20
22
|
import {Slot, ssz} from "@lodestar/types";
|
|
21
23
|
import {Logger, toRootHex} from "@lodestar/utils";
|
|
@@ -142,19 +144,19 @@ export function initializeForkChoiceFromFinalizedState(
|
|
|
142
144
|
unrealizedFinalizedEpoch: finalizedCheckpoint.epoch,
|
|
143
145
|
unrealizedFinalizedRoot: toRootHex(finalizedCheckpoint.root),
|
|
144
146
|
|
|
145
|
-
...(state.isExecutionStateType && state.isMergeTransitionComplete
|
|
147
|
+
...(isStatePostBellatrix(state) && state.isExecutionStateType && state.isMergeTransitionComplete
|
|
146
148
|
? {
|
|
147
149
|
executionPayloadBlockHash: toRootHex(state.latestBlockHash),
|
|
148
150
|
// TODO GLOAS: executionPayloadNumber is not tracked in BeaconState post-gloas (EIP-7732 removed
|
|
149
151
|
// latestExecutionPayloadHeader). Using 0 as unavailable fallback until a solution is found.
|
|
150
|
-
executionPayloadNumber:
|
|
152
|
+
executionPayloadNumber: isStatePostGloas(state) ? 0 : state.payloadBlockNumber,
|
|
151
153
|
executionStatus: blockHeader.slot === GENESIS_SLOT ? ExecutionStatus.Valid : ExecutionStatus.Syncing,
|
|
152
154
|
}
|
|
153
155
|
: {executionPayloadBlockHash: null, executionStatus: ExecutionStatus.PreMerge}),
|
|
154
156
|
|
|
155
157
|
dataAvailabilityStatus: DataAvailabilityStatus.PreData,
|
|
156
158
|
payloadStatus: isForkPostGloas ? PayloadStatus.PENDING : PayloadStatus.FULL, // TODO GLOAS: Post-gloas how do we know if the checkpoint payload is FULL or EMPTY?
|
|
157
|
-
parentBlockHash:
|
|
159
|
+
parentBlockHash: isStatePostGloas(state) ? toRootHex(state.latestBlockHash) : null,
|
|
158
160
|
},
|
|
159
161
|
currentSlot
|
|
160
162
|
),
|
|
@@ -237,20 +239,21 @@ export function initializeForkChoiceFromUnfinalizedState(
|
|
|
237
239
|
unrealizedFinalizedEpoch: finalizedCheckpoint.epoch,
|
|
238
240
|
unrealizedFinalizedRoot: toRootHex(finalizedCheckpoint.root),
|
|
239
241
|
|
|
240
|
-
...(unfinalizedState
|
|
242
|
+
...(isStatePostBellatrix(unfinalizedState) &&
|
|
243
|
+
unfinalizedState.isExecutionStateType &&
|
|
244
|
+
unfinalizedState.isMergeTransitionComplete
|
|
241
245
|
? {
|
|
242
246
|
executionPayloadBlockHash: toRootHex(unfinalizedState.latestBlockHash),
|
|
243
247
|
// TODO GLOAS: executionPayloadNumber is not tracked in BeaconState post-gloas (EIP-7732 removed
|
|
244
248
|
// latestExecutionPayloadHeader). Using 0 as unavailable fallback until a solution is found.
|
|
245
|
-
executionPayloadNumber:
|
|
246
|
-
config.getForkSeq(unfinalizedState.slot) >= ForkSeq.gloas ? 0 : unfinalizedState.payloadBlockNumber,
|
|
249
|
+
executionPayloadNumber: isStatePostGloas(unfinalizedState) ? 0 : unfinalizedState.payloadBlockNumber,
|
|
247
250
|
executionStatus: blockHeader.slot === GENESIS_SLOT ? ExecutionStatus.Valid : ExecutionStatus.Syncing,
|
|
248
251
|
}
|
|
249
252
|
: {executionPayloadBlockHash: null, executionStatus: ExecutionStatus.PreMerge}),
|
|
250
253
|
|
|
251
254
|
dataAvailabilityStatus: DataAvailabilityStatus.PreData,
|
|
252
255
|
payloadStatus: isForkPostGloas ? PayloadStatus.PENDING : PayloadStatus.FULL, // TODO GLOAS: Post-gloas how do we know if the checkpoint payload is FULL or EMPTY?
|
|
253
|
-
parentBlockHash:
|
|
256
|
+
parentBlockHash: isStatePostGloas(unfinalizedState) ? toRootHex(unfinalizedState.latestBlockHash) : null,
|
|
254
257
|
};
|
|
255
258
|
|
|
256
259
|
const parentSlot = blockHeader.slot - 1;
|
package/src/chain/interface.ts
CHANGED
|
@@ -5,7 +5,7 @@ import {EpochShuffling, IBeaconStateView, PubkeyCache} from "@lodestar/state-tra
|
|
|
5
5
|
import {
|
|
6
6
|
BeaconBlock,
|
|
7
7
|
BlindedBeaconBlock,
|
|
8
|
-
|
|
8
|
+
DataColumnSidecar,
|
|
9
9
|
Epoch,
|
|
10
10
|
Root,
|
|
11
11
|
RootHex,
|
|
@@ -159,6 +159,8 @@ export interface IBeaconChain {
|
|
|
159
159
|
close(): Promise<void>;
|
|
160
160
|
/** Chain has seen the specified block root or not. The block may not be processed yet, use forkchoice.hasBlock to check it */
|
|
161
161
|
seenBlock(blockRoot: RootHex): boolean;
|
|
162
|
+
/** Chain has seen a SignedExecutionPayloadEnvelope for this block root (via seenCache or fork choice FULL variant) */
|
|
163
|
+
seenPayloadEnvelope(blockRoot: RootHex): boolean;
|
|
162
164
|
/** Populate in-memory caches with persisted data. Call at least once on startup */
|
|
163
165
|
loadFromDisk(): Promise<void>;
|
|
164
166
|
/** Persist in-memory data to the DB. Call at least once before stopping the process */
|
|
@@ -217,7 +219,7 @@ export interface IBeaconChain {
|
|
|
217
219
|
): Promise<{block: SignedBeaconBlock; executionOptimistic: boolean; finalized: boolean} | null>;
|
|
218
220
|
getBlobSidecars(blockSlot: Slot, blockRootHex: string): Promise<deneb.BlobSidecars | null>;
|
|
219
221
|
getSerializedBlobSidecars(blockSlot: Slot, blockRootHex: string): Promise<Uint8Array | null>;
|
|
220
|
-
getDataColumnSidecars(blockSlot: Slot, blockRootHex: string): Promise<
|
|
222
|
+
getDataColumnSidecars(blockSlot: Slot, blockRootHex: string): Promise<DataColumnSidecar[]>;
|
|
221
223
|
getSerializedDataColumnSidecars(
|
|
222
224
|
blockSlot: Slot,
|
|
223
225
|
blockRootHex: string,
|
|
@@ -21,7 +21,7 @@ import {
|
|
|
21
21
|
isForkPostElectra,
|
|
22
22
|
} from "@lodestar/params";
|
|
23
23
|
import {
|
|
24
|
-
|
|
24
|
+
type IBeaconStateViewAltair,
|
|
25
25
|
computeStartSlotAtEpoch,
|
|
26
26
|
computeSyncPeriodAtEpoch,
|
|
27
27
|
computeSyncPeriodAtSlot,
|
|
@@ -260,7 +260,11 @@ export class LightClientServer {
|
|
|
260
260
|
* - Persist state witness
|
|
261
261
|
* - Use block's syncAggregate
|
|
262
262
|
*/
|
|
263
|
-
onImportBlockHead(
|
|
263
|
+
onImportBlockHead(
|
|
264
|
+
block: BeaconBlock<ForkPostAltair>,
|
|
265
|
+
postState: IBeaconStateViewAltair,
|
|
266
|
+
parentBlockSlot: Slot
|
|
267
|
+
): void {
|
|
264
268
|
// TEMP: To disable this functionality for fork_choice spec tests.
|
|
265
269
|
// Since the tests have deep-reorgs attested data is not available often printing lots of error logs.
|
|
266
270
|
// While this function is only called for head blocks, best to disable.
|
|
@@ -396,7 +400,7 @@ export class LightClientServer {
|
|
|
396
400
|
|
|
397
401
|
private async persistPostBlockImportData(
|
|
398
402
|
block: BeaconBlock<ForkPostAltair>,
|
|
399
|
-
postState:
|
|
403
|
+
postState: IBeaconStateViewAltair,
|
|
400
404
|
parentBlockSlot: Slot
|
|
401
405
|
): Promise<void> {
|
|
402
406
|
const blockSlot = block.slot;
|
|
@@ -26,6 +26,8 @@ import {
|
|
|
26
26
|
computeSlotsSinceEpochStart,
|
|
27
27
|
computeStartSlotAtEpoch,
|
|
28
28
|
getAttestationParticipationStatus,
|
|
29
|
+
isStatePostAltair,
|
|
30
|
+
isStatePostGloas,
|
|
29
31
|
} from "@lodestar/state-transition";
|
|
30
32
|
import {Attestation, Epoch, RootHex, Slot, electra, isElectraAttestation, phase0, ssz} from "@lodestar/types";
|
|
31
33
|
import {MapDef, assert, toRootHex} from "@lodestar/utils";
|
|
@@ -359,7 +361,7 @@ export class AggregatedAttestationPool {
|
|
|
359
361
|
inclusionDistance,
|
|
360
362
|
stateEpoch,
|
|
361
363
|
rootCache,
|
|
362
|
-
|
|
364
|
+
isStatePostGloas(state) ? state.executionPayloadAvailability : null
|
|
363
365
|
);
|
|
364
366
|
|
|
365
367
|
const weight =
|
|
@@ -742,6 +744,9 @@ export function getNotSeenValidatorsFn(
|
|
|
742
744
|
if (config.getForkName(stateSlot) === ForkName.phase0) {
|
|
743
745
|
throw new Error("getNotSeenValidatorsFn is not supported phase0 state");
|
|
744
746
|
}
|
|
747
|
+
if (!isStatePostAltair(state)) {
|
|
748
|
+
throw new Error("Expected Altair state for participation tracking");
|
|
749
|
+
}
|
|
745
750
|
|
|
746
751
|
// altair and future forks
|
|
747
752
|
// Get attestations to be included in an altair block.
|
|
@@ -7,6 +7,7 @@ import {
|
|
|
7
7
|
StateHashTreeRootSource,
|
|
8
8
|
computeEpochAtSlot,
|
|
9
9
|
computeTimeAtSlot,
|
|
10
|
+
isStatePostBellatrix,
|
|
10
11
|
} from "@lodestar/state-transition";
|
|
11
12
|
import {Slot} from "@lodestar/types";
|
|
12
13
|
import {Logger, fromHex, isErrorAborted, sleep} from "@lodestar/utils";
|
|
@@ -159,6 +160,9 @@ export class PrepareNextSlotScheduler {
|
|
|
159
160
|
const preparationTime =
|
|
160
161
|
computeTimeAtSlot(this.config, prepareSlot, this.chain.genesisTime) - Date.now() / 1000;
|
|
161
162
|
this.metrics?.blockPayload.payloadAdvancePrepTime.observe(preparationTime);
|
|
163
|
+
if (!isStatePostBellatrix(updatedPrepareState)) {
|
|
164
|
+
throw new Error("Expected Bellatrix state for payload preparation");
|
|
165
|
+
}
|
|
162
166
|
|
|
163
167
|
const safeBlockHash = getSafeExecutionBlockHash(this.chain.forkChoice);
|
|
164
168
|
const finalizedBlockHash =
|
|
@@ -183,6 +187,10 @@ export class PrepareNextSlotScheduler {
|
|
|
183
187
|
});
|
|
184
188
|
}
|
|
185
189
|
|
|
190
|
+
if (!isStatePostBellatrix(updatedPrepareState)) {
|
|
191
|
+
throw new Error("Expected Bellatrix state for payload attributes");
|
|
192
|
+
}
|
|
193
|
+
|
|
186
194
|
this.computeStateHashTreeRoot(updatedPrepareState, isEpochTransition);
|
|
187
195
|
|
|
188
196
|
// If emitPayloadAttributes is true emit a SSE payloadAttributes event
|
|
@@ -3,6 +3,7 @@ import {
|
|
|
3
3
|
ExecutionPayloadStatus,
|
|
4
4
|
G2_POINT_AT_INFINITY,
|
|
5
5
|
IBeaconStateView,
|
|
6
|
+
IBeaconStateViewGloas,
|
|
6
7
|
StateHashTreeRootSource,
|
|
7
8
|
} from "@lodestar/state-transition";
|
|
8
9
|
import {BeaconBlock, BlindedBeaconBlock, Gwei, Root, gloas} from "@lodestar/types";
|
|
@@ -60,7 +61,7 @@ export function computeNewStateRoot(
|
|
|
60
61
|
*/
|
|
61
62
|
export function computeEnvelopeStateRoot(
|
|
62
63
|
metrics: Metrics | null,
|
|
63
|
-
postBlockState:
|
|
64
|
+
postBlockState: IBeaconStateViewGloas,
|
|
64
65
|
envelope: gloas.ExecutionPayloadEnvelope
|
|
65
66
|
): Root {
|
|
66
67
|
const signedEnvelope: gloas.SignedExecutionPayloadEnvelope = {
|
|
@@ -14,7 +14,15 @@ import {
|
|
|
14
14
|
isForkPostBellatrix,
|
|
15
15
|
isForkPostGloas,
|
|
16
16
|
} from "@lodestar/params";
|
|
17
|
-
import {
|
|
17
|
+
import {
|
|
18
|
+
G2_POINT_AT_INFINITY,
|
|
19
|
+
IBeaconStateView,
|
|
20
|
+
type IBeaconStateViewBellatrix,
|
|
21
|
+
computeTimeAtSlot,
|
|
22
|
+
isStatePostBellatrix,
|
|
23
|
+
isStatePostCapella,
|
|
24
|
+
isStatePostGloas,
|
|
25
|
+
} from "@lodestar/state-transition";
|
|
18
26
|
import {
|
|
19
27
|
BLSPubkey,
|
|
20
28
|
BLSSignature,
|
|
@@ -191,6 +199,10 @@ export async function produceBlockBody<T extends BlockType>(
|
|
|
191
199
|
this.logger.verbose("Producing beacon block body", logMeta);
|
|
192
200
|
|
|
193
201
|
if (isForkPostGloas(fork)) {
|
|
202
|
+
if (!isStatePostGloas(currentState)) {
|
|
203
|
+
throw new Error("Expected Gloas state for Gloas block production");
|
|
204
|
+
}
|
|
205
|
+
|
|
194
206
|
// TODO GLOAS: support non self-building here, the block type differentiation between
|
|
195
207
|
// full and blinded no longer makes sense in gloas, it might be a good idea to move
|
|
196
208
|
// this into a completely separate function and have pre/post gloas more separated
|
|
@@ -297,6 +309,10 @@ export async function produceBlockBody<T extends BlockType>(
|
|
|
297
309
|
shouldOverrideBuilder,
|
|
298
310
|
});
|
|
299
311
|
} else if (isForkPostBellatrix(fork)) {
|
|
312
|
+
if (!isStatePostBellatrix(currentState)) {
|
|
313
|
+
throw new Error("Expected Bellatrix state for execution block production");
|
|
314
|
+
}
|
|
315
|
+
|
|
300
316
|
const safeBlockHash = getSafeExecutionBlockHash(this.forkChoice);
|
|
301
317
|
const finalizedBlockHash = this.forkChoice.getFinalizedBlock().executionPayloadBlockHash ?? ZERO_HASH_HEX;
|
|
302
318
|
const feeRecipient = requestedFeeRecipient ?? this.beaconProposerCache.getOrDefault(proposerIndex);
|
|
@@ -598,7 +614,7 @@ export async function prepareExecutionPayload(
|
|
|
598
614
|
parentBlockRoot: Root,
|
|
599
615
|
safeBlockHash: RootHex,
|
|
600
616
|
finalizedBlockHash: RootHex,
|
|
601
|
-
state:
|
|
617
|
+
state: IBeaconStateViewBellatrix,
|
|
602
618
|
suggestedFeeRecipient: string
|
|
603
619
|
): Promise<{prepType: PayloadPreparationType; payloadId: PayloadId}> {
|
|
604
620
|
const parentHash = state.latestBlockHash;
|
|
@@ -666,7 +682,7 @@ async function prepareExecutionPayloadHeader(
|
|
|
666
682
|
config: ChainForkConfig;
|
|
667
683
|
},
|
|
668
684
|
fork: ForkPostBellatrix,
|
|
669
|
-
state:
|
|
685
|
+
state: IBeaconStateViewBellatrix,
|
|
670
686
|
proposerPubKey: BLSPubkey
|
|
671
687
|
): Promise<{
|
|
672
688
|
header: ExecutionPayloadHeader;
|
|
@@ -693,7 +709,7 @@ export function getPayloadAttributesForSSE(
|
|
|
693
709
|
prepareSlot,
|
|
694
710
|
parentBlockRoot,
|
|
695
711
|
feeRecipient,
|
|
696
|
-
}: {prepareState:
|
|
712
|
+
}: {prepareState: IBeaconStateViewBellatrix; prepareSlot: Slot; parentBlockRoot: Root; feeRecipient: string}
|
|
697
713
|
): SSEPayloadAttributes {
|
|
698
714
|
const parentHash = prepareState.latestBlockHash;
|
|
699
715
|
const payloadAttributes = preparePayloadAttributes(fork, chain, {
|
|
@@ -736,7 +752,7 @@ function preparePayloadAttributes(
|
|
|
736
752
|
parentBlockRoot,
|
|
737
753
|
feeRecipient,
|
|
738
754
|
}: {
|
|
739
|
-
prepareState:
|
|
755
|
+
prepareState: IBeaconStateViewBellatrix;
|
|
740
756
|
prepareSlot: Slot;
|
|
741
757
|
parentBlockRoot: Root;
|
|
742
758
|
feeRecipient: string;
|
|
@@ -751,6 +767,10 @@ function preparePayloadAttributes(
|
|
|
751
767
|
};
|
|
752
768
|
|
|
753
769
|
if (ForkSeq[fork] >= ForkSeq.capella) {
|
|
770
|
+
if (!isStatePostCapella(prepareState)) {
|
|
771
|
+
throw new Error("Expected Capella state for withdrawals");
|
|
772
|
+
}
|
|
773
|
+
|
|
754
774
|
// withdrawals logic is now fork aware as it changes on electra fork post capella
|
|
755
775
|
(payloadAttributes as capella.SSEPayloadAttributes["payloadAttributes"]).withdrawals =
|
|
756
776
|
prepareState.getExpectedWithdrawals().expectedWithdrawals;
|
|
@@ -149,8 +149,8 @@ export class SeenBlockInput {
|
|
|
149
149
|
});
|
|
150
150
|
}
|
|
151
151
|
|
|
152
|
-
|
|
153
|
-
return this.blockInputs.
|
|
152
|
+
hasBlock(rootHex: RootHex): boolean {
|
|
153
|
+
return this.blockInputs.get(rootHex)?.hasBlock() ?? false;
|
|
154
154
|
}
|
|
155
155
|
|
|
156
156
|
get(rootHex: RootHex): IBlockInput | undefined {
|
|
@@ -84,8 +84,8 @@ export class SeenPayloadEnvelopeInput {
|
|
|
84
84
|
return this.payloadInputs.get(blockRootHex);
|
|
85
85
|
}
|
|
86
86
|
|
|
87
|
-
|
|
88
|
-
return this.payloadInputs.
|
|
87
|
+
hasPayload(blockRootHex: RootHex): boolean {
|
|
88
|
+
return this.payloadInputs.get(blockRootHex)?.hasPayloadEnvelope() ?? false;
|
|
89
89
|
}
|
|
90
90
|
|
|
91
91
|
prune(blockRootHex: RootHex): void {
|
|
@@ -6,6 +6,7 @@ import {
|
|
|
6
6
|
computeTimeAtSlot,
|
|
7
7
|
getBlockProposerSignatureSet,
|
|
8
8
|
isExecutionBlockBodyType,
|
|
9
|
+
isStatePostBellatrix,
|
|
9
10
|
} from "@lodestar/state-transition";
|
|
10
11
|
import {SignedBeaconBlock, deneb, gloas, isGloasBeaconBlock} from "@lodestar/types";
|
|
11
12
|
import {byteArrayEquals, sleep, toRootHex} from "@lodestar/utils";
|
|
@@ -174,7 +175,7 @@ export async function validateGossipBlock(
|
|
|
174
175
|
if (isForkPostBellatrix(fork) && !isForkPostGloas(fork)) {
|
|
175
176
|
if (!isExecutionBlockBodyType(block.body)) throw Error("Not execution block body type");
|
|
176
177
|
const executionPayload = block.body.executionPayload;
|
|
177
|
-
if (blockState.isExecutionStateType && blockState.isExecutionEnabled(block)) {
|
|
178
|
+
if (isStatePostBellatrix(blockState) && blockState.isExecutionStateType && blockState.isExecutionEnabled(block)) {
|
|
178
179
|
const expectedTimestamp = computeTimeAtSlot(config, blockSlot, chain.genesisTime);
|
|
179
180
|
if (executionPayload.timestamp !== computeTimeAtSlot(config, blockSlot, chain.genesisTime)) {
|
|
180
181
|
throw new BlockGossipError(GossipAction.REJECT, {
|