public void ProcessJustificationAndFinalization(BeaconState state) { _logger.LogInformation(Event.ProcessJustificationAndFinalization, "Process epoch justification and finalization state {BeaconState}", state); var currentEpoch = _beaconStateAccessor.GetCurrentEpoch(state); if (currentEpoch <= _initialValueOptions.CurrentValue.GenesisEpoch + new Epoch(1)) { return; //throw new ArgumentOutOfRangeException(nameof(state), currentEpoch, "Current epoch of state must be more than one away from genesis epoch."); } var previousEpoch = _beaconStateAccessor.GetPreviousEpoch(state); var oldPreviousJustifiedCheckpoint = state.PreviousJustifiedCheckpoint; var oldCurrentJustifiedCheckpoint = state.CurrentJustifiedCheckpoint; // Process justifications state.SetPreviousJustifiedCheckpoint(state.CurrentJustifiedCheckpoint); state.JustificationBitsShift(); // Previous Epoch var matchingTargetAttestationsPreviousEpoch = GetMatchingTargetAttestations(state, previousEpoch); var attestingBalancePreviousEpoch = GetAttestingBalance(state, matchingTargetAttestationsPreviousEpoch); var totalActiveBalance = _beaconStateAccessor.GetTotalActiveBalance(state); if (attestingBalancePreviousEpoch * 3 >= totalActiveBalance * 2) { var blockRoot = _beaconStateAccessor.GetBlockRoot(state, previousEpoch); var checkpoint = new Checkpoint(previousEpoch, blockRoot); state.SetCurrentJustifiedCheckpoint(checkpoint); state.JustificationBits.Set(1, true); } // Current Epoch var matchingTargetAttestationsCurrentEpoch = GetMatchingTargetAttestations(state, currentEpoch); var attestingBalanceCurrentEpoch = GetAttestingBalance(state, matchingTargetAttestationsCurrentEpoch); if (attestingBalanceCurrentEpoch * 3 >= totalActiveBalance * 2) { var blockRoot = _beaconStateAccessor.GetBlockRoot(state, currentEpoch); var checkpoint = new Checkpoint(currentEpoch, blockRoot); state.SetCurrentJustifiedCheckpoint(checkpoint); state.JustificationBits.Set(0, true); } // Process finalizations var bits = state.JustificationBits; // The 2nd/3rd/4th most recent epochs are justified, the 2nd using the 4th as source if ((oldPreviousJustifiedCheckpoint.Epoch + new Epoch(3) == currentEpoch) && bits.Cast <bool>().Skip(1).Take(3).All(x => x)) { state.SetFinalizedCheckpoint(oldPreviousJustifiedCheckpoint); } // The 2nd/3rd most recent epochs are justified, the 2nd using the 3rd as source if ((oldPreviousJustifiedCheckpoint.Epoch + new Epoch(2) == currentEpoch) && bits.Cast <bool>().Skip(1).Take(2).All(x => x)) { state.SetFinalizedCheckpoint(oldPreviousJustifiedCheckpoint); } // The 1st/2nd/3rd most recent epochs are justified, the 1st using the 3rd as source if ((oldCurrentJustifiedCheckpoint.Epoch + new Epoch(2) == currentEpoch) && bits.Cast <bool>().Take(3).All(x => x)) { state.SetFinalizedCheckpoint(oldCurrentJustifiedCheckpoint); } // The 1st/2nd most recent epochs are justified, the 1st using the 2nd as source if ((oldCurrentJustifiedCheckpoint.Epoch + new Epoch(1) == currentEpoch) && bits.Cast <bool>().Take(2).All(x => x)) { state.SetFinalizedCheckpoint(oldCurrentJustifiedCheckpoint); } }