protected async Task ValidateEndorsement(RawEndorsementContent endorsement, RawBlock rawBlock) { var lastBlock = await Cache.Blocks.CurrentAsync(); if (endorsement.Level != lastBlock.Level) { throw new ValidationException("invalid endorsed block level"); } if (!Cache.Accounts.DelegateExists(endorsement.Metadata.Delegate)) { throw new ValidationException("invalid endorsement delegate"); } if (endorsement.Metadata.BalanceUpdates.Count != 0 && endorsement.Metadata.BalanceUpdates.Count != (Protocol.BlockReward0 > 0 ? 3 : 2)) { throw new ValidationException("invalid endorsement balance updates count"); } if (endorsement.Metadata.BalanceUpdates.Count > 0) { var contractUpdate = endorsement.Metadata.BalanceUpdates.FirstOrDefault(x => x is ContractUpdate) as ContractUpdate ?? throw new ValidationException("invalid endorsement contract balance updates"); var depostisUpdate = endorsement.Metadata.BalanceUpdates.FirstOrDefault(x => x is DepositsUpdate) as DepositsUpdate ?? throw new ValidationException("invalid endorsement depostis balance updates"); if (contractUpdate.Contract != endorsement.Metadata.Delegate || contractUpdate.Change != -endorsement.Metadata.Slots.Count * Protocol.EndorsementDeposit) { throw new ValidationException("invalid endorsement contract update"); } if (depostisUpdate.Delegate != endorsement.Metadata.Delegate || depostisUpdate.Change != endorsement.Metadata.Slots.Count * Protocol.EndorsementDeposit) { throw new ValidationException("invalid endorsement depostis update"); } if (Cycle >= (Protocol.PreservedCycles + 2)) { var rewardsUpdate = endorsement.Metadata.BalanceUpdates.FirstOrDefault(x => x is RewardsUpdate) as RewardsUpdate ?? throw new ValidationException("invalidendorsement rewards updates"); if (rewardsUpdate.Delegate != endorsement.Metadata.Delegate || rewardsUpdate.Change != GetEndorsementReward(endorsement.Metadata.Slots.Count, lastBlock.Priority)) { throw new ValidationException("invalid endorsement rewards update"); } } } }
public Task Init(Block block, RawOperation op, RawEndorsementContent content) { Endorsement = new EndorsementOperation { Id = Cache.AppState.NextOperationId(), Block = block, Level = block.Level, Timestamp = block.Timestamp, OpHash = op.Hash, Slots = content.Metadata.Slots.Count, Delegate = Cache.Accounts.GetDelegate(content.Metadata.Delegate), Reward = content.Metadata.BalanceUpdates.FirstOrDefault(x => x is RewardsUpdate)?.Change ?? 0 }; return(Task.CompletedTask); }
public static async Task <EndorsementsCommit> Apply(ProtocolHandler proto, Block block, RawOperation op, RawEndorsementContent content) { var commit = new EndorsementsCommit(proto); await commit.Init(block, op, content); await commit.Apply(); return(commit); }