/// <summary>Publish a signed block.</summary>
        /// <param name="beacon_block">The `BeaconBlock` object, as sent from the beacon node originally, but now with the signature field completed.</param>
        /// <returns>The block was validated successfully and has been broadcast. It has also been integrated into the beacon node's database.</returns>
        public async Task Block2Async(BeaconBlock beacon_block)
        {
            if (_logger.IsInfo())
            {
                Log.BlockPublished(_logger, beacon_block.Slot,
                                   Bytes.ToHexString(beacon_block.Body.Randao_reveal),
                                   beacon_block.Parent_root, beacon_block.State_root,
                                   Bytes.ToHexString(beacon_block.Body.Graffiti),
                                   beacon_block.Signature, null);
            }

            Core2.Containers.BeaconBlock signedBlock = new Core2.Containers.BeaconBlock(
                new Slot((ulong)beacon_block.Slot),
                new Hash32(Bytes.FromHexString(beacon_block.Parent_root)),
                new Hash32(Bytes.FromHexString(beacon_block.State_root)),
                new Core2.Containers.BeaconBlockBody(
                    new BlsSignature(beacon_block.Body.Randao_reveal),
                    new Eth1Data(
                        new Hash32(beacon_block.Body.Eth1_data.Deposit_root),
                        (ulong)beacon_block.Body.Eth1_data.Deposit_count,
                        new Hash32(beacon_block.Body.Eth1_data.Block_hash)
                        ),
                    new Bytes32(beacon_block.Body.Graffiti),
                    beacon_block.Body.Proposer_slashings.Select(x => new ProposerSlashing(
                                                                    new ValidatorIndex((ulong)x.Proposer_index),
                                                                    MapBeaconBlockHeader(x.Header_1),
                                                                    MapBeaconBlockHeader(x.Header_2)
                                                                    )),
                    beacon_block.Body.Attester_slashings.Select(x => new AttesterSlashing(
                                                                    MapIndexedAttestation(x.Attestation_1),
                                                                    MapIndexedAttestation(x.Attestation_2)
                                                                    )),
                    beacon_block.Body.Attestations.Select(x =>
                                                          new Core2.Containers.Attestation(
                                                              new BitArray(x.Aggregation_bits),
                                                              MapAttestationData(x.Data),
                                                              new BlsSignature(x.Signature)
                                                              )
                                                          ),
                    beacon_block.Body.Deposits.Select(x =>
                                                      new Core2.Containers.Deposit(
                                                          x.Proof.Select(y => new Hash32(y)),
                                                          new DepositData(
                                                              new BlsPublicKey(x.Data.Pubkey),
                                                              new Hash32(x.Data.Withdrawal_credentials),
                                                              new Gwei((ulong)x.Data.Amount),
                                                              new BlsSignature(x.Data.Signature)
                                                              )
                                                          )
                                                      ),
                    beacon_block.Body.Voluntary_exits.Select(x =>
                                                             new Core2.Containers.VoluntaryExit(
                                                                 new Epoch((ulong)x.Epoch),
                                                                 new ValidatorIndex((ulong)x.Validator_index),
                                                                 new BlsSignature((x.Signature))
                                                                 )
                                                             )
                    ),
                new BlsSignature(Bytes.FromHexString(beacon_block.Signature))
                );

            bool acceptedLocally = await _beaconNode.PublishBlockAsync(signedBlock, CancellationToken.None);

            // TODO: return 200 or 202 based on whether accepted locally or not
        }
Example #2
0
        public async Task <bool> PublishBlockAsync(Core2.Containers.BeaconBlock block, CancellationToken cancellationToken)
        {
            BeaconNode.OApiClient.BeaconBlock data = new BeaconNode.OApiClient.BeaconBlock()
            {
                Slot        = block.Slot,
                Parent_root = block.ParentRoot.ToString(),
                State_root  = block.StateRoot.ToString(),
                Signature   = block.Signature.ToString(),
                Body        = new BeaconNode.OApiClient.BeaconBlockBody()
                {
                    Randao_reveal = block.Body !.RandaoReveal.AsSpan().ToArray(),
                    Eth1_data     = new Eth1_data()
                    {
                        Block_hash    = block.Body.Eth1Data.BlockHash.Bytes,
                        Deposit_count = block.Body.Eth1Data.DepositCount,
                        Deposit_root  = block.Body.Eth1Data.DepositRoot.Bytes
                    },
                    Graffiti           = block.Body.Graffiti.AsSpan().ToArray(),
                    Proposer_slashings = block.Body.ProposerSlashings.Select(x => new Proposer_slashings()
                    {
                        Header_1       = MapBeaconBlockHeader(x.Header1),
                        Header_2       = MapBeaconBlockHeader(x.Header2),
                        Proposer_index = x.ProposerIndex
                    }).ToList(),
                    Attester_slashings = block.Body.AttesterSlashings.Select(x => new Attester_slashings()
                    {
                        Attestation_1 = MapIndexedAttestation(x.Attestation1),
                        Attestation_2 = MapIndexedAttestation(x.Attestation2)
                    }).ToList(),
                    Attestations = block.Body.Attestations.Select(x => new Attestations()
                    {
                        Signature        = x.Signature.Bytes,
                        Aggregation_bits = x.AggregationBits.Cast <byte>().ToArray(),
                        Custody_bits     = new byte[0],
                        Data             = MapAttestationData(x.Data)
                    }).ToList(),
                    Voluntary_exits = block.Body.VoluntaryExits.Select(x => new Voluntary_exits()
                    {
                        Validator_index = x.ValidatorIndex,
                        Epoch           = x.Epoch,
                        Signature       = x.Signature.Bytes
                    }).ToList(),
                    Deposits = block.Body.Deposits.Select((x, index) => new Deposits()
                    {
                        Index = (ulong)index,
                        Proof = x.Proof.Select(y => y.Bytes).ToList(),
                        Data  = new Data()
                        {
                            Amount    = x.Data.Amount,
                            Pubkey    = x.Data.PublicKey.Bytes,
                            Signature = x.Data.Signature.Bytes,
                            Withdrawal_credentials = x.Data.WithdrawalCredentials.Bytes
                        }
                    }).ToList(),
                }
            };

            await ClientOperationWithRetry(async (oapiClient, innerCancellationToken) =>
            {
                await oapiClient.Block2Async(data, innerCancellationToken).ConfigureAwait(false);
            }, cancellationToken).ConfigureAwait(false);

            // TODO: Parse 202 result separate from 200 result

            return(true);
        }
        /// <summary>Produce a new block, without signature.</summary>
        /// <param name="slot">The slot for which the block should be proposed.</param>
        /// <param name="randao_reveal">The validator's randao reveal value.</param>
        /// <returns>Success response</returns>
        public async Task <BeaconBlock> BlockAsync(ulong slot, byte[] randao_reveal)
        {
            if (_logger.IsInfo())
            {
                Log.NewBlockRequested(_logger, slot, Bytes.ToHexString(randao_reveal), null);
            }

            Core2.Containers.BeaconBlock data =
                await _beaconNode.NewBlockAsync(new Slot(slot), new BlsSignature(randao_reveal), CancellationToken.None);

            OApi.BeaconBlock result = new OApi.BeaconBlock()
            {
                Slot        = (ulong)data.Slot,
                Parent_root = data.ParentRoot.ToString(),
                State_root  = data.StateRoot.ToString(),
                Signature   = data.Signature.ToString(),
                Body        = new OApi.BeaconBlockBody()
                {
                    Randao_reveal = data.Body !.RandaoReveal.AsSpan().ToArray(),
                    Eth1_data     = new Eth1_data()
                    {
                        Block_hash    = data.Body.Eth1Data.BlockHash.Bytes,
                        Deposit_count = data.Body.Eth1Data.DepositCount,
                        Deposit_root  = data.Body.Eth1Data.DepositRoot.Bytes
                    },
                    Graffiti           = data.Body.Graffiti.AsSpan().ToArray(),
                    Proposer_slashings = data.Body.ProposerSlashings.Select(x => new Proposer_slashings()
                    {
                        Header_1       = MapBeaconBlockHeader(x.Header1),
                        Header_2       = MapBeaconBlockHeader(x.Header2),
                        Proposer_index = x.ProposerIndex
                    }).ToList(),
                    Attester_slashings = data.Body.AttesterSlashings.Select(x => new Attester_slashings()
                    {
                        Attestation_1 = MapIndexedAttestation(x.Attestation1),
                        Attestation_2 = MapIndexedAttestation(x.Attestation2)
                    }).ToList(),
                    Attestations = data.Body.Attestations.Select(x => new Attestations()
                    {
                        Signature        = x.Signature.Bytes,
                        Aggregation_bits = x.AggregationBits.Cast <byte>().ToArray(),
                        Custody_bits     = new byte[0],
                        Data             = MapAttestationData(x.Data)
                    }).ToList(),
                    Voluntary_exits = data.Body.VoluntaryExits.Select(x => new Voluntary_exits()
                    {
                        Validator_index = x.ValidatorIndex,
                        Epoch           = x.Epoch,
                        Signature       = x.Signature.Bytes
                    }).ToList(),
                    Deposits = data.Body.Deposits.Select((x, index) => new Deposits()
                    {
                        Index = (ulong)index,
                        Proof = x.Proof.Select(y => y.Bytes).ToList(),
                        Data  = new Data()
                        {
                            Amount    = x.Data.Amount,
                            Pubkey    = x.Data.PublicKey.Bytes,
                            Signature = x.Data.Signature.Bytes,
                            Withdrawal_credentials = x.Data.WithdrawalCredentials.Bytes
                        }
                    }).ToList(),
                    Transfers = new List <Transfers>()
                }
            };
            return(result);
        }
Example #4
0
        public async Task <Core2.Containers.BeaconBlock> NewBlockAsync(Slot slot, BlsSignature randaoReveal, CancellationToken cancellationToken)
        {
            ulong slotValue = (ulong)slot;

            byte[] randaoRevealBytes = randaoReveal.Bytes;

            BeaconNode.OApiClient.BeaconBlock?result = null;
            await ClientOperationWithRetry(async (oapiClient, innerCancellationToken) =>
            {
                result = await oapiClient.BlockAsync(slotValue, randaoRevealBytes, innerCancellationToken).ConfigureAwait(false);
            }, cancellationToken).ConfigureAwait(false);

            BeaconNode.OApiClient.BeaconBlock oapiBeaconBlock = result !;
            Core2.Containers.BeaconBlock      beaconBlock     = new Core2.Containers.BeaconBlock(
                new Slot((ulong)oapiBeaconBlock.Slot),
                new Hash32(Bytes.FromHexString(oapiBeaconBlock.Parent_root)),
                new Hash32(Bytes.FromHexString(oapiBeaconBlock.State_root)),
                new Core2.Containers.BeaconBlockBody(
                    new BlsSignature(oapiBeaconBlock.Body.Randao_reveal),
                    new Eth1Data(
                        new Hash32(oapiBeaconBlock.Body.Eth1_data.Deposit_root),
                        (ulong)oapiBeaconBlock.Body.Eth1_data.Deposit_count,
                        new Hash32(oapiBeaconBlock.Body.Eth1_data.Block_hash)
                        ),
                    new Bytes32(oapiBeaconBlock.Body.Graffiti),
                    oapiBeaconBlock.Body.Proposer_slashings.Select(x => new ProposerSlashing(
                                                                       new ValidatorIndex((ulong)x.Proposer_index),
                                                                       MapBeaconBlockHeader(x.Header_1),
                                                                       MapBeaconBlockHeader(x.Header_2)
                                                                       )),
                    oapiBeaconBlock.Body.Attester_slashings.Select(x => new AttesterSlashing(
                                                                       MapIndexedAttestation(x.Attestation_1),
                                                                       MapIndexedAttestation(x.Attestation_2)
                                                                       )),
                    oapiBeaconBlock.Body.Attestations.Select(x =>
                                                             new Core2.Containers.Attestation(
                                                                 new BitArray(x.Aggregation_bits),
                                                                 MapAttestationData(x.Data),
                                                                 new BlsSignature(x.Signature)
                                                                 )
                                                             ),
                    oapiBeaconBlock.Body.Deposits.Select(x =>
                                                         new Core2.Containers.Deposit(
                                                             x.Proof.Select(y => new Hash32(y)),
                                                             new DepositData(
                                                                 new BlsPublicKey(x.Data.Pubkey),
                                                                 new Hash32(x.Data.Withdrawal_credentials),
                                                                 new Gwei((ulong)x.Data.Amount),
                                                                 new BlsSignature(x.Data.Signature)
                                                                 )
                                                             )
                                                         ),
                    oapiBeaconBlock.Body.Voluntary_exits.Select(x =>
                                                                new VoluntaryExit(
                                                                    new Epoch((ulong)x.Epoch),
                                                                    new ValidatorIndex((ulong)x.Validator_index),
                                                                    new BlsSignature((x.Signature))
                                                                    )
                                                                )
                    ),
                BlsSignature.Empty
                );

            return(beaconBlock);
        }