{-# LANGUAGE GeneralizedNewtypeDeriving #-}
module Ouroboros.Consensus.Committee.WFA
(
PersistentCommitteeSize (..)
, NonPersistentCommitteeSize (..)
, TotalPersistentStake (..)
, TotalNonPersistentStake (..)
, weightedFaitAccompliSplitSeats
, isAbovePersistentSeatThreshold
, SeatIndex (..)
, NumPoolsWithPositiveStake (..)
, WFAError (..)
, WFATiebreaker (..)
, wFATiebreakerWithEpochNonce
, ExtWFAStakeDistr (..)
, mkExtWFAStakeDistr
, getCandidateIfSeatWithinBounds
, unsafeGetCandidateInSeat
) where
import Cardano.Crypto.DSIGN (BLS12381MinSigDSIGN, DSIGNAlgorithm (SigDSIGN))
import qualified Cardano.Crypto.Hash as Hash
import Cardano.Ledger.BaseTypes (Nonce (NeutralNonce, Nonce))
import Cardano.Ledger.Binary (runByteBuilder)
import Cardano.Ledger.Core (HASH, Hash, KeyHash (unKeyHash))
import Control.Exception (assert)
import Data.Array (Array, Ix, listArray)
import qualified Data.Array as Array
import qualified Data.ByteString.Builder.Extra as BS
import Data.Function (on)
import qualified Data.List as List
import Data.Map.Strict (Map)
import qualified Data.Map.Strict as Map
import Data.Word (Word64)
import Ouroboros.Consensus.Committee.Types
( Cumulative (..)
, LedgerStake (..)
, PoolId
, TargetCommitteeSize (..)
, unPoolId
)
newtype PersistentCommitteeSize
= PersistentCommitteeSize
{ PersistentCommitteeSize -> Word64
unPersistentCommitteeSize :: Word64
}
deriving (Int -> PersistentCommitteeSize -> ShowS
[PersistentCommitteeSize] -> ShowS
PersistentCommitteeSize -> String
(Int -> PersistentCommitteeSize -> ShowS)
-> (PersistentCommitteeSize -> String)
-> ([PersistentCommitteeSize] -> ShowS)
-> Show PersistentCommitteeSize
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> PersistentCommitteeSize -> ShowS
showsPrec :: Int -> PersistentCommitteeSize -> ShowS
$cshow :: PersistentCommitteeSize -> String
show :: PersistentCommitteeSize -> String
$cshowList :: [PersistentCommitteeSize] -> ShowS
showList :: [PersistentCommitteeSize] -> ShowS
Show, PersistentCommitteeSize -> PersistentCommitteeSize -> Bool
(PersistentCommitteeSize -> PersistentCommitteeSize -> Bool)
-> (PersistentCommitteeSize -> PersistentCommitteeSize -> Bool)
-> Eq PersistentCommitteeSize
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: PersistentCommitteeSize -> PersistentCommitteeSize -> Bool
== :: PersistentCommitteeSize -> PersistentCommitteeSize -> Bool
$c/= :: PersistentCommitteeSize -> PersistentCommitteeSize -> Bool
/= :: PersistentCommitteeSize -> PersistentCommitteeSize -> Bool
Eq)
newtype NonPersistentCommitteeSize
= NonPersistentCommitteeSize
{ NonPersistentCommitteeSize -> Word64
unNonPersistentCommitteeSize :: Word64
}
deriving (Int -> NonPersistentCommitteeSize -> ShowS
[NonPersistentCommitteeSize] -> ShowS
NonPersistentCommitteeSize -> String
(Int -> NonPersistentCommitteeSize -> ShowS)
-> (NonPersistentCommitteeSize -> String)
-> ([NonPersistentCommitteeSize] -> ShowS)
-> Show NonPersistentCommitteeSize
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> NonPersistentCommitteeSize -> ShowS
showsPrec :: Int -> NonPersistentCommitteeSize -> ShowS
$cshow :: NonPersistentCommitteeSize -> String
show :: NonPersistentCommitteeSize -> String
$cshowList :: [NonPersistentCommitteeSize] -> ShowS
showList :: [NonPersistentCommitteeSize] -> ShowS
Show, NonPersistentCommitteeSize -> NonPersistentCommitteeSize -> Bool
(NonPersistentCommitteeSize -> NonPersistentCommitteeSize -> Bool)
-> (NonPersistentCommitteeSize
-> NonPersistentCommitteeSize -> Bool)
-> Eq NonPersistentCommitteeSize
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: NonPersistentCommitteeSize -> NonPersistentCommitteeSize -> Bool
== :: NonPersistentCommitteeSize -> NonPersistentCommitteeSize -> Bool
$c/= :: NonPersistentCommitteeSize -> NonPersistentCommitteeSize -> Bool
/= :: NonPersistentCommitteeSize -> NonPersistentCommitteeSize -> Bool
Eq)
newtype TotalPersistentStake
= TotalPersistentStake
{ TotalPersistentStake -> Cumulative LedgerStake
unTotalPersistentStake :: Cumulative LedgerStake
}
deriving (Int -> TotalPersistentStake -> ShowS
[TotalPersistentStake] -> ShowS
TotalPersistentStake -> String
(Int -> TotalPersistentStake -> ShowS)
-> (TotalPersistentStake -> String)
-> ([TotalPersistentStake] -> ShowS)
-> Show TotalPersistentStake
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> TotalPersistentStake -> ShowS
showsPrec :: Int -> TotalPersistentStake -> ShowS
$cshow :: TotalPersistentStake -> String
show :: TotalPersistentStake -> String
$cshowList :: [TotalPersistentStake] -> ShowS
showList :: [TotalPersistentStake] -> ShowS
Show, TotalPersistentStake -> TotalPersistentStake -> Bool
(TotalPersistentStake -> TotalPersistentStake -> Bool)
-> (TotalPersistentStake -> TotalPersistentStake -> Bool)
-> Eq TotalPersistentStake
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: TotalPersistentStake -> TotalPersistentStake -> Bool
== :: TotalPersistentStake -> TotalPersistentStake -> Bool
$c/= :: TotalPersistentStake -> TotalPersistentStake -> Bool
/= :: TotalPersistentStake -> TotalPersistentStake -> Bool
Eq)
newtype TotalNonPersistentStake
= TotalNonPersistentStake
{ TotalNonPersistentStake -> Cumulative LedgerStake
unTotalNonPersistentStake :: Cumulative LedgerStake
}
deriving (Int -> TotalNonPersistentStake -> ShowS
[TotalNonPersistentStake] -> ShowS
TotalNonPersistentStake -> String
(Int -> TotalNonPersistentStake -> ShowS)
-> (TotalNonPersistentStake -> String)
-> ([TotalNonPersistentStake] -> ShowS)
-> Show TotalNonPersistentStake
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> TotalNonPersistentStake -> ShowS
showsPrec :: Int -> TotalNonPersistentStake -> ShowS
$cshow :: TotalNonPersistentStake -> String
show :: TotalNonPersistentStake -> String
$cshowList :: [TotalNonPersistentStake] -> ShowS
showList :: [TotalNonPersistentStake] -> ShowS
Show, TotalNonPersistentStake -> TotalNonPersistentStake -> Bool
(TotalNonPersistentStake -> TotalNonPersistentStake -> Bool)
-> (TotalNonPersistentStake -> TotalNonPersistentStake -> Bool)
-> Eq TotalNonPersistentStake
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: TotalNonPersistentStake -> TotalNonPersistentStake -> Bool
== :: TotalNonPersistentStake -> TotalNonPersistentStake -> Bool
$c/= :: TotalNonPersistentStake -> TotalNonPersistentStake -> Bool
/= :: TotalNonPersistentStake -> TotalNonPersistentStake -> Bool
Eq)
data WFAError
=
EmptyStakeDistribution
|
NotEnoughPoolsWithPositiveStake
TargetCommitteeSize
NumPoolsWithPositiveStake
deriving (Int -> WFAError -> ShowS
[WFAError] -> ShowS
WFAError -> String
(Int -> WFAError -> ShowS)
-> (WFAError -> String) -> ([WFAError] -> ShowS) -> Show WFAError
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> WFAError -> ShowS
showsPrec :: Int -> WFAError -> ShowS
$cshow :: WFAError -> String
show :: WFAError -> String
$cshowList :: [WFAError] -> ShowS
showList :: [WFAError] -> ShowS
Show, WFAError -> WFAError -> Bool
(WFAError -> WFAError -> Bool)
-> (WFAError -> WFAError -> Bool) -> Eq WFAError
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: WFAError -> WFAError -> Bool
== :: WFAError -> WFAError -> Bool
$c/= :: WFAError -> WFAError -> Bool
/= :: WFAError -> WFAError -> Bool
Eq)
weightedFaitAccompliSplitSeats ::
ExtWFAStakeDistr c ->
TargetCommitteeSize ->
Either
WFAError
( PersistentCommitteeSize
, NonPersistentCommitteeSize
, TotalPersistentStake
, TotalNonPersistentStake
)
weightedFaitAccompliSplitSeats :: forall c.
ExtWFAStakeDistr c
-> TargetCommitteeSize
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
weightedFaitAccompliSplitSeats ExtWFAStakeDistr c
extWFAStakeDistr TargetCommitteeSize
totalSeats
| Bool
notEnoughPoolsWithPositiveStake =
WFAError
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
forall a b. a -> Either a b
Left
( TargetCommitteeSize -> NumPoolsWithPositiveStake -> WFAError
NotEnoughPoolsWithPositiveStake
TargetCommitteeSize
totalSeats
(ExtWFAStakeDistr c -> NumPoolsWithPositiveStake
forall a. ExtWFAStakeDistr a -> NumPoolsWithPositiveStake
numPoolsWithPositiveStake ExtWFAStakeDistr c
extWFAStakeDistr)
)
| Bool
otherwise =
Bool
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
forall a. (?callStack::CallStack) => Bool -> a -> a
assert (Word64
numPersistentVoters Word64 -> Word64 -> Bool
forall a. Ord a => a -> a -> Bool
<= TargetCommitteeSize -> Word64
unTargetCommitteeSize TargetCommitteeSize
totalSeats) (Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake))
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
forall a b. (a -> b) -> a -> b
$
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
-> Either
WFAError
(PersistentCommitteeSize, NonPersistentCommitteeSize,
TotalPersistentStake, TotalNonPersistentStake)
forall a b. b -> Either a b
Right
( Word64 -> PersistentCommitteeSize
PersistentCommitteeSize Word64
numPersistentVoters
, Word64 -> NonPersistentCommitteeSize
NonPersistentCommitteeSize Word64
numNonPersistentVoters
, Cumulative LedgerStake -> TotalPersistentStake
TotalPersistentStake (LedgerStake -> Cumulative LedgerStake
forall a. a -> Cumulative a
Cumulative (Rational -> LedgerStake
LedgerStake Rational
persistentStake))
, Cumulative LedgerStake -> TotalNonPersistentStake
TotalNonPersistentStake (LedgerStake -> Cumulative LedgerStake
forall a. a -> Cumulative a
Cumulative (Rational -> LedgerStake
LedgerStake Rational
nonPersistentStake))
)
where
notEnoughPoolsWithPositiveStake :: Bool
notEnoughPoolsWithPositiveStake =
NumPoolsWithPositiveStake -> Word64
unNumPoolsWithPositiveStake (ExtWFAStakeDistr c -> NumPoolsWithPositiveStake
forall a. ExtWFAStakeDistr a -> NumPoolsWithPositiveStake
numPoolsWithPositiveStake ExtWFAStakeDistr c
extWFAStakeDistr)
Word64 -> Word64 -> Bool
forall a. Ord a => a -> a -> Bool
< TargetCommitteeSize -> Word64
unTargetCommitteeSize TargetCommitteeSize
totalSeats
stakeDistrArray :: Array SeatIndex (PoolId, c, LedgerStake, Cumulative LedgerStake)
stakeDistrArray =
ExtWFAStakeDistr c
-> Array SeatIndex (PoolId, c, LedgerStake, Cumulative LedgerStake)
forall a.
ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
unExtWFAStakeDistr ExtWFAStakeDistr c
extWFAStakeDistr
( Word64
numPersistentVoters
, Rational
persistentStake
, Rational
nonPersistentStake
) =
(SeatIndex, SeatIndex)
-> Bool
-> Word64
-> Rational
-> Rational
-> (Word64, Rational, Rational)
forall {t}.
Num t =>
(SeatIndex, SeatIndex)
-> Bool -> t -> Rational -> Rational -> (t, Rational, Rational)
traverseSeats (Array SeatIndex (PoolId, c, LedgerStake, Cumulative LedgerStake)
-> (SeatIndex, SeatIndex)
forall i e. Array i e -> (i, i)
Array.bounds Array SeatIndex (PoolId, c, LedgerStake, Cumulative LedgerStake)
stakeDistrArray) Bool
True Word64
0 Rational
0 Rational
0
numNonPersistentVoters :: Word64
numNonPersistentVoters =
TargetCommitteeSize -> Word64
unTargetCommitteeSize TargetCommitteeSize
totalSeats
Word64 -> Word64 -> Word64
forall a. Num a => a -> a -> a
- Word64
numPersistentVoters
traverseSeats :: (SeatIndex, SeatIndex)
-> Bool -> t -> Rational -> Rational -> (t, Rational, Rational)
traverseSeats
(SeatIndex
currSeatIndex, SeatIndex
lastSeatIndex)
Bool
checkPersistentSeatThreshold
t
accNumPersistentVoters
Rational
accPersistentStake
Rational
accNonPersistentStake
| SeatIndex
currSeatIndex SeatIndex -> SeatIndex -> Bool
forall a. Ord a => a -> a -> Bool
> SeatIndex
lastSeatIndex =
( t
accNumPersistentVoters
, Rational
accPersistentStake
, Rational
accNonPersistentStake
)
| Bool
isPersistent =
(SeatIndex, SeatIndex)
-> Bool -> t -> Rational -> Rational -> (t, Rational, Rational)
traverseSeats
(SeatIndex -> SeatIndex
forall a. Enum a => a -> a
succ SeatIndex
currSeatIndex, SeatIndex
lastSeatIndex)
Bool
True
(t
accNumPersistentVoters t -> t -> t
forall a. Num a => a -> a -> a
+ t
1)
(Rational
accPersistentStake Rational -> Rational -> Rational
forall a. Num a => a -> a -> a
+ Rational
voterStake)
Rational
accNonPersistentStake
| Bool
otherwise =
(SeatIndex, SeatIndex)
-> Bool -> t -> Rational -> Rational -> (t, Rational, Rational)
traverseSeats
(SeatIndex -> SeatIndex
forall a. Enum a => a -> a
succ SeatIndex
currSeatIndex, SeatIndex
lastSeatIndex)
Bool
False
t
accNumPersistentVoters
Rational
accPersistentStake
(Rational
accNonPersistentStake Rational -> Rational -> Rational
forall a. Num a => a -> a -> a
+ Rational
voterStake)
where
(PoolId
_, c
_, LedgerStake Rational
voterStake, Cumulative LedgerStake
cumulativeStake) =
Array SeatIndex (PoolId, c, LedgerStake, Cumulative LedgerStake)
-> SeatIndex -> (PoolId, c, LedgerStake, Cumulative LedgerStake)
forall i e. Ix i => Array i e -> i -> e
(Array.!) Array SeatIndex (PoolId, c, LedgerStake, Cumulative LedgerStake)
stakeDistrArray SeatIndex
currSeatIndex
isPersistent :: Bool
isPersistent =
Bool
checkPersistentSeatThreshold
Bool -> Bool -> Bool
&& TargetCommitteeSize
-> SeatIndex -> LedgerStake -> Cumulative LedgerStake -> Bool
isAbovePersistentSeatThreshold
TargetCommitteeSize
totalSeats
SeatIndex
currSeatIndex
(Rational -> LedgerStake
LedgerStake Rational
voterStake)
Cumulative LedgerStake
cumulativeStake
isAbovePersistentSeatThreshold ::
TargetCommitteeSize ->
SeatIndex ->
LedgerStake ->
Cumulative LedgerStake ->
Bool
isAbovePersistentSeatThreshold :: TargetCommitteeSize
-> SeatIndex -> LedgerStake -> Cumulative LedgerStake -> Bool
isAbovePersistentSeatThreshold
(TargetCommitteeSize Word64
totalSeats)
(SeatIndex Word64
voterSeat)
(LedgerStake Rational
voterStake)
(Cumulative (LedgerStake Rational
cumulativeStake))
| Rational
cumulativeStake Rational -> Rational -> Bool
forall a. Ord a => a -> a -> Bool
<= Rational
0 =
Bool
False
| Word64
voterSeat Word64 -> Word64 -> Bool
forall a. Ord a => a -> a -> Bool
>= Word64
totalSeats =
Bool
False
| Bool
otherwise =
( (Rational
1 Rational -> Rational -> Rational
forall a. Num a => a -> a -> a
- (Rational
voterStake Rational -> Rational -> Rational
forall a. Fractional a => a -> a -> a
/ Rational
cumulativeStake))
Rational -> Integer -> Rational
forall a b. (Num a, Integral b) => a -> b -> a
^ (Integer
2 :: Integer)
)
Rational -> Rational -> Bool
forall a. Ord a => a -> a -> Bool
< ( Word64 -> Rational
forall a. Real a => a -> Rational
toRational (Word64
totalSeats Word64 -> Word64 -> Word64
forall a. Num a => a -> a -> a
- Word64
voterSeat Word64 -> Word64 -> Word64
forall a. Num a => a -> a -> a
- Word64
1)
Rational -> Rational -> Rational
forall a. Fractional a => a -> a -> a
/ Word64 -> Rational
forall a. Real a => a -> Rational
toRational (Word64
totalSeats Word64 -> Word64 -> Word64
forall a. Num a => a -> a -> a
- Word64
voterSeat)
)
newtype SeatIndex
= SeatIndex
{ SeatIndex -> Word64
unSeatIndex :: Word64
}
deriving (Int -> SeatIndex -> ShowS
[SeatIndex] -> ShowS
SeatIndex -> String
(Int -> SeatIndex -> ShowS)
-> (SeatIndex -> String)
-> ([SeatIndex] -> ShowS)
-> Show SeatIndex
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> SeatIndex -> ShowS
showsPrec :: Int -> SeatIndex -> ShowS
$cshow :: SeatIndex -> String
show :: SeatIndex -> String
$cshowList :: [SeatIndex] -> ShowS
showList :: [SeatIndex] -> ShowS
Show, SeatIndex -> SeatIndex -> Bool
(SeatIndex -> SeatIndex -> Bool)
-> (SeatIndex -> SeatIndex -> Bool) -> Eq SeatIndex
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: SeatIndex -> SeatIndex -> Bool
== :: SeatIndex -> SeatIndex -> Bool
$c/= :: SeatIndex -> SeatIndex -> Bool
/= :: SeatIndex -> SeatIndex -> Bool
Eq, Eq SeatIndex
Eq SeatIndex =>
(SeatIndex -> SeatIndex -> Ordering)
-> (SeatIndex -> SeatIndex -> Bool)
-> (SeatIndex -> SeatIndex -> Bool)
-> (SeatIndex -> SeatIndex -> Bool)
-> (SeatIndex -> SeatIndex -> Bool)
-> (SeatIndex -> SeatIndex -> SeatIndex)
-> (SeatIndex -> SeatIndex -> SeatIndex)
-> Ord SeatIndex
SeatIndex -> SeatIndex -> Bool
SeatIndex -> SeatIndex -> Ordering
SeatIndex -> SeatIndex -> SeatIndex
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: SeatIndex -> SeatIndex -> Ordering
compare :: SeatIndex -> SeatIndex -> Ordering
$c< :: SeatIndex -> SeatIndex -> Bool
< :: SeatIndex -> SeatIndex -> Bool
$c<= :: SeatIndex -> SeatIndex -> Bool
<= :: SeatIndex -> SeatIndex -> Bool
$c> :: SeatIndex -> SeatIndex -> Bool
> :: SeatIndex -> SeatIndex -> Bool
$c>= :: SeatIndex -> SeatIndex -> Bool
>= :: SeatIndex -> SeatIndex -> Bool
$cmax :: SeatIndex -> SeatIndex -> SeatIndex
max :: SeatIndex -> SeatIndex -> SeatIndex
$cmin :: SeatIndex -> SeatIndex -> SeatIndex
min :: SeatIndex -> SeatIndex -> SeatIndex
Ord, Int -> SeatIndex
SeatIndex -> Int
SeatIndex -> [SeatIndex]
SeatIndex -> SeatIndex
SeatIndex -> SeatIndex -> [SeatIndex]
SeatIndex -> SeatIndex -> SeatIndex -> [SeatIndex]
(SeatIndex -> SeatIndex)
-> (SeatIndex -> SeatIndex)
-> (Int -> SeatIndex)
-> (SeatIndex -> Int)
-> (SeatIndex -> [SeatIndex])
-> (SeatIndex -> SeatIndex -> [SeatIndex])
-> (SeatIndex -> SeatIndex -> [SeatIndex])
-> (SeatIndex -> SeatIndex -> SeatIndex -> [SeatIndex])
-> Enum SeatIndex
forall a.
(a -> a)
-> (a -> a)
-> (Int -> a)
-> (a -> Int)
-> (a -> [a])
-> (a -> a -> [a])
-> (a -> a -> [a])
-> (a -> a -> a -> [a])
-> Enum a
$csucc :: SeatIndex -> SeatIndex
succ :: SeatIndex -> SeatIndex
$cpred :: SeatIndex -> SeatIndex
pred :: SeatIndex -> SeatIndex
$ctoEnum :: Int -> SeatIndex
toEnum :: Int -> SeatIndex
$cfromEnum :: SeatIndex -> Int
fromEnum :: SeatIndex -> Int
$cenumFrom :: SeatIndex -> [SeatIndex]
enumFrom :: SeatIndex -> [SeatIndex]
$cenumFromThen :: SeatIndex -> SeatIndex -> [SeatIndex]
enumFromThen :: SeatIndex -> SeatIndex -> [SeatIndex]
$cenumFromTo :: SeatIndex -> SeatIndex -> [SeatIndex]
enumFromTo :: SeatIndex -> SeatIndex -> [SeatIndex]
$cenumFromThenTo :: SeatIndex -> SeatIndex -> SeatIndex -> [SeatIndex]
enumFromThenTo :: SeatIndex -> SeatIndex -> SeatIndex -> [SeatIndex]
Enum, Ord SeatIndex
Ord SeatIndex =>
((SeatIndex, SeatIndex) -> [SeatIndex])
-> ((SeatIndex, SeatIndex) -> SeatIndex -> Int)
-> ((SeatIndex, SeatIndex) -> SeatIndex -> Int)
-> ((SeatIndex, SeatIndex) -> SeatIndex -> Bool)
-> ((SeatIndex, SeatIndex) -> Int)
-> ((SeatIndex, SeatIndex) -> Int)
-> Ix SeatIndex
(SeatIndex, SeatIndex) -> Int
(SeatIndex, SeatIndex) -> [SeatIndex]
(SeatIndex, SeatIndex) -> SeatIndex -> Bool
(SeatIndex, SeatIndex) -> SeatIndex -> Int
forall a.
Ord a =>
((a, a) -> [a])
-> ((a, a) -> a -> Int)
-> ((a, a) -> a -> Int)
-> ((a, a) -> a -> Bool)
-> ((a, a) -> Int)
-> ((a, a) -> Int)
-> Ix a
$crange :: (SeatIndex, SeatIndex) -> [SeatIndex]
range :: (SeatIndex, SeatIndex) -> [SeatIndex]
$cindex :: (SeatIndex, SeatIndex) -> SeatIndex -> Int
index :: (SeatIndex, SeatIndex) -> SeatIndex -> Int
$cunsafeIndex :: (SeatIndex, SeatIndex) -> SeatIndex -> Int
unsafeIndex :: (SeatIndex, SeatIndex) -> SeatIndex -> Int
$cinRange :: (SeatIndex, SeatIndex) -> SeatIndex -> Bool
inRange :: (SeatIndex, SeatIndex) -> SeatIndex -> Bool
$crangeSize :: (SeatIndex, SeatIndex) -> Int
rangeSize :: (SeatIndex, SeatIndex) -> Int
$cunsafeRangeSize :: (SeatIndex, SeatIndex) -> Int
unsafeRangeSize :: (SeatIndex, SeatIndex) -> Int
Ix)
newtype NumPoolsWithPositiveStake
= NumPoolsWithPositiveStake
{ NumPoolsWithPositiveStake -> Word64
unNumPoolsWithPositiveStake :: Word64
}
deriving (Int -> NumPoolsWithPositiveStake -> ShowS
[NumPoolsWithPositiveStake] -> ShowS
NumPoolsWithPositiveStake -> String
(Int -> NumPoolsWithPositiveStake -> ShowS)
-> (NumPoolsWithPositiveStake -> String)
-> ([NumPoolsWithPositiveStake] -> ShowS)
-> Show NumPoolsWithPositiveStake
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> NumPoolsWithPositiveStake -> ShowS
showsPrec :: Int -> NumPoolsWithPositiveStake -> ShowS
$cshow :: NumPoolsWithPositiveStake -> String
show :: NumPoolsWithPositiveStake -> String
$cshowList :: [NumPoolsWithPositiveStake] -> ShowS
showList :: [NumPoolsWithPositiveStake] -> ShowS
Show, NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool
(NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool)
-> (NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool)
-> Eq NumPoolsWithPositiveStake
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool
== :: NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool
$c/= :: NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool
/= :: NumPoolsWithPositiveStake -> NumPoolsWithPositiveStake -> Bool
Eq)
newtype WFATiebreaker
= WFATiebreaker
{ WFATiebreaker -> PoolId -> PoolId -> Ordering
unWFATiebreaker :: PoolId -> PoolId -> Ordering
}
wFATiebreakerWithEpochNonce :: Nonce -> WFATiebreaker
wFATiebreakerWithEpochNonce :: Nonce -> WFATiebreaker
wFATiebreakerWithEpochNonce Nonce
epochNonce =
(PoolId -> PoolId -> Ordering) -> WFATiebreaker
WFATiebreaker (Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
-> Hash HASH (SigDSIGN BLS12381MinSigDSIGN) -> Ordering
forall a. Ord a => a -> a -> Ordering
compare (Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
-> Hash HASH (SigDSIGN BLS12381MinSigDSIGN) -> Ordering)
-> (PoolId -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN))
-> PoolId
-> PoolId
-> Ordering
forall b c a. (b -> b -> c) -> (a -> b) -> a -> a -> c
`on` PoolId -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
hashWithNonce)
where
hashWithNonce :: PoolId -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
hashWithNonce :: PoolId -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
hashWithNonce PoolId
poolId =
Hash HASH ByteString -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
forall h a b. Hash h a -> Hash h b
Hash.castHash
(Hash HASH ByteString -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN))
-> (Builder -> Hash HASH ByteString)
-> Builder
-> Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (ByteString -> ByteString) -> ByteString -> Hash HASH ByteString
forall h a. HashAlgorithm h => (a -> ByteString) -> a -> Hash h a
Hash.hashWith ByteString -> ByteString
forall a. a -> a
id
(ByteString -> Hash HASH ByteString)
-> (Builder -> ByteString) -> Builder -> Hash HASH ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Int -> Builder -> ByteString
runByteBuilder (Int
32 Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
32)
(Builder -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN))
-> Builder -> Hash HASH (SigDSIGN BLS12381MinSigDSIGN)
forall a b. (a -> b) -> a -> b
$ Builder
epochNonceBytes Builder -> Builder -> Builder
forall a. Semigroup a => a -> a -> a
<> Builder
poolIdBytes
where
epochNonceBytes :: Builder
epochNonceBytes =
case Nonce
epochNonce of
Nonce
NeutralNonce -> Builder
forall a. Monoid a => a
mempty
Nonce Hash HASH Nonce
h -> ByteString -> Builder
BS.byteStringCopy (Hash HASH Nonce -> ByteString
forall h a. Hash h a -> ByteString
Hash.hashToBytes Hash HASH Nonce
h)
poolIdBytes :: Builder
poolIdBytes =
ByteString -> Builder
BS.byteStringCopy
(ByteString -> Builder)
-> (PoolId -> ByteString) -> PoolId -> Builder
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Hash ADDRHASH (VerKeyDSIGN DSIGN) -> ByteString
forall h a. Hash h a -> ByteString
Hash.hashToBytes
(Hash ADDRHASH (VerKeyDSIGN DSIGN) -> ByteString)
-> (PoolId -> Hash ADDRHASH (VerKeyDSIGN DSIGN))
-> PoolId
-> ByteString
forall b c a. (b -> c) -> (a -> b) -> a -> c
. KeyHash StakePool -> Hash ADDRHASH (VerKeyDSIGN DSIGN)
forall (r :: KeyRole).
KeyHash r -> Hash ADDRHASH (VerKeyDSIGN DSIGN)
unKeyHash
(KeyHash StakePool -> Hash ADDRHASH (VerKeyDSIGN DSIGN))
-> (PoolId -> KeyHash StakePool)
-> PoolId
-> Hash ADDRHASH (VerKeyDSIGN DSIGN)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. PoolId -> KeyHash StakePool
unPoolId
(PoolId -> Builder) -> PoolId -> Builder
forall a b. (a -> b) -> a -> b
$ PoolId
poolId
data ExtWFAStakeDistr a
= ExtWFAStakeDistr
{ forall a.
ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
unExtWFAStakeDistr ::
Array
SeatIndex
( PoolId
, a
, LedgerStake
, Cumulative LedgerStake
)
, forall a. ExtWFAStakeDistr a -> NumPoolsWithPositiveStake
numPoolsWithPositiveStake :: NumPoolsWithPositiveStake
}
deriving Int -> ExtWFAStakeDistr a -> ShowS
[ExtWFAStakeDistr a] -> ShowS
ExtWFAStakeDistr a -> String
(Int -> ExtWFAStakeDistr a -> ShowS)
-> (ExtWFAStakeDistr a -> String)
-> ([ExtWFAStakeDistr a] -> ShowS)
-> Show (ExtWFAStakeDistr a)
forall a. Show a => Int -> ExtWFAStakeDistr a -> ShowS
forall a. Show a => [ExtWFAStakeDistr a] -> ShowS
forall a. Show a => ExtWFAStakeDistr a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Show a => Int -> ExtWFAStakeDistr a -> ShowS
showsPrec :: Int -> ExtWFAStakeDistr a -> ShowS
$cshow :: forall a. Show a => ExtWFAStakeDistr a -> String
show :: ExtWFAStakeDistr a -> String
$cshowList :: forall a. Show a => [ExtWFAStakeDistr a] -> ShowS
showList :: [ExtWFAStakeDistr a] -> ShowS
Show
mkExtWFAStakeDistr ::
WFATiebreaker ->
Map PoolId (LedgerStake, a) ->
Either WFAError (ExtWFAStakeDistr a)
mkExtWFAStakeDistr :: forall a.
WFATiebreaker
-> Map PoolId (LedgerStake, a)
-> Either WFAError (ExtWFAStakeDistr a)
mkExtWFAStakeDistr WFATiebreaker
tiebreaker Map PoolId (LedgerStake, a)
pools
| Map PoolId (LedgerStake, a) -> Bool
forall k a. Map k a -> Bool
Map.null Map PoolId (LedgerStake, a)
pools =
WFAError -> Either WFAError (ExtWFAStakeDistr a)
forall a b. a -> Either a b
Left
WFAError
EmptyStakeDistribution
| Bool
otherwise =
ExtWFAStakeDistr a -> Either WFAError (ExtWFAStakeDistr a)
forall a b. b -> Either a b
Right
ExtWFAStakeDistr
{ unExtWFAStakeDistr :: Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
unExtWFAStakeDistr = Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
stakeDistrArray
, numPoolsWithPositiveStake :: NumPoolsWithPositiveStake
numPoolsWithPositiveStake = NumPoolsWithPositiveStake
numPoolsWithPositiveStakeAcc
}
where
stakeDistrArray :: Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
stakeDistrArray =
(SeatIndex, SeatIndex)
-> [(PoolId, a, LedgerStake, Cumulative LedgerStake)]
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall i e. Ix i => (i, i) -> [e] -> Array i e
listArray
( Word64 -> SeatIndex
SeatIndex Word64
0
, Word64 -> SeatIndex
SeatIndex (Int -> Word64
forall a b. (Integral a, Num b) => a -> b
fromIntegral (Map PoolId (LedgerStake, a) -> Int
forall k a. Map k a -> Int
Map.size Map PoolId (LedgerStake, a)
pools) Word64 -> Word64 -> Word64
forall a. Num a => a -> a -> a
- Word64
1)
)
[(PoolId, a, LedgerStake, Cumulative LedgerStake)]
cumulativeStakeAndPools
((Cumulative LedgerStake
_totalStake, NumPoolsWithPositiveStake
numPoolsWithPositiveStakeAcc), [(PoolId, a, LedgerStake, Cumulative LedgerStake)]
cumulativeStakeAndPools) =
((Cumulative LedgerStake, NumPoolsWithPositiveStake)
-> (PoolId, (LedgerStake, a))
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
(PoolId, a, LedgerStake, Cumulative LedgerStake)))
-> (Cumulative LedgerStake, NumPoolsWithPositiveStake)
-> [(PoolId, (LedgerStake, a))]
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
[(PoolId, a, LedgerStake, Cumulative LedgerStake)])
forall (t :: * -> *) s a b.
Traversable t =>
(s -> a -> (s, b)) -> s -> t a -> (s, t b)
List.mapAccumR
(Cumulative LedgerStake, NumPoolsWithPositiveStake)
-> (PoolId, (LedgerStake, a))
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
(PoolId, a, LedgerStake, Cumulative LedgerStake))
forall {a} {b}.
(Cumulative LedgerStake, NumPoolsWithPositiveStake)
-> (a, (LedgerStake, b))
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
(a, b, LedgerStake, Cumulative LedgerStake))
accumStakeAndCountPoolsWithPositiveStake
( LedgerStake -> Cumulative LedgerStake
forall a. a -> Cumulative a
Cumulative (Rational -> LedgerStake
LedgerStake Rational
0)
, Word64 -> NumPoolsWithPositiveStake
NumPoolsWithPositiveStake Word64
0
)
([(PoolId, (LedgerStake, a))]
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
[(PoolId, a, LedgerStake, Cumulative LedgerStake)]))
-> (Map PoolId (LedgerStake, a) -> [(PoolId, (LedgerStake, a))])
-> Map PoolId (LedgerStake, a)
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
[(PoolId, a, LedgerStake, Cumulative LedgerStake)])
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ((PoolId, (LedgerStake, a))
-> (PoolId, (LedgerStake, a)) -> Ordering)
-> [(PoolId, (LedgerStake, a))] -> [(PoolId, (LedgerStake, a))]
forall a. (a -> a -> Ordering) -> [a] -> [a]
List.sortBy (PoolId, (LedgerStake, a))
-> (PoolId, (LedgerStake, a)) -> Ordering
forall {b} {b}.
(PoolId, (LedgerStake, b))
-> (PoolId, (LedgerStake, b)) -> Ordering
descendingStakeWithTiebreaker
([(PoolId, (LedgerStake, a))] -> [(PoolId, (LedgerStake, a))])
-> (Map PoolId (LedgerStake, a) -> [(PoolId, (LedgerStake, a))])
-> Map PoolId (LedgerStake, a)
-> [(PoolId, (LedgerStake, a))]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Map PoolId (LedgerStake, a) -> [(PoolId, (LedgerStake, a))]
forall k a. Map k a -> [(k, a)]
Map.toList
(Map PoolId (LedgerStake, a)
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
[(PoolId, a, LedgerStake, Cumulative LedgerStake)]))
-> Map PoolId (LedgerStake, a)
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
[(PoolId, a, LedgerStake, Cumulative LedgerStake)])
forall a b. (a -> b) -> a -> b
$ Map PoolId (LedgerStake, a)
pools
descendingStakeWithTiebreaker :: (PoolId, (LedgerStake, b))
-> (PoolId, (LedgerStake, b)) -> Ordering
descendingStakeWithTiebreaker
(PoolId
poolId1, (LedgerStake Rational
stake1, b
_))
(PoolId
poolId2, (LedgerStake Rational
stake2, b
_))
| Rational
stake1 Rational -> Rational -> Bool
forall a. Eq a => a -> a -> Bool
== Rational
stake2 = WFATiebreaker -> PoolId -> PoolId -> Ordering
unWFATiebreaker WFATiebreaker
tiebreaker PoolId
poolId1 PoolId
poolId2
| Bool
otherwise = Rational -> Rational -> Ordering
forall a. Ord a => a -> a -> Ordering
compare Rational
stake2 Rational
stake1
accumStakeAndCountPoolsWithPositiveStake :: (Cumulative LedgerStake, NumPoolsWithPositiveStake)
-> (a, (LedgerStake, b))
-> ((Cumulative LedgerStake, NumPoolsWithPositiveStake),
(a, b, LedgerStake, Cumulative LedgerStake))
accumStakeAndCountPoolsWithPositiveStake
(Cumulative (LedgerStake Rational
stakeAccR), NumPoolsWithPositiveStake Word64
numPoolsAccR)
(a
poolId, (LedgerStake Rational
poolStake, b
poolPublicKey)) =
let stakeAccR' :: Rational
stakeAccR' =
Rational
stakeAccR Rational -> Rational -> Rational
forall a. Num a => a -> a -> a
+ Rational
poolStake
numPoolsAccR' :: Word64
numPoolsAccR'
| Rational
poolStake Rational -> Rational -> Bool
forall a. Ord a => a -> a -> Bool
> Rational
0 = Word64
numPoolsAccR Word64 -> Word64 -> Word64
forall a. Num a => a -> a -> a
+ Word64
1
| Bool
otherwise = Word64
numPoolsAccR
in (
( LedgerStake -> Cumulative LedgerStake
forall a. a -> Cumulative a
Cumulative (Rational -> LedgerStake
LedgerStake Rational
stakeAccR')
, Word64 -> NumPoolsWithPositiveStake
NumPoolsWithPositiveStake Word64
numPoolsAccR'
)
,
( a
poolId
, b
poolPublicKey
, Rational -> LedgerStake
LedgerStake Rational
poolStake
, LedgerStake -> Cumulative LedgerStake
forall a. a -> Cumulative a
Cumulative (Rational -> LedgerStake
LedgerStake Rational
stakeAccR')
)
)
seatIndexWithinBounds :: SeatIndex -> ExtWFAStakeDistr a -> Bool
seatIndexWithinBounds :: forall a. SeatIndex -> ExtWFAStakeDistr a -> Bool
seatIndexWithinBounds SeatIndex
seatIndex ExtWFAStakeDistr a
distr =
SeatIndex -> Word64
unSeatIndex SeatIndex
seatIndex Word64 -> Word64 -> Bool
forall a. Ord a => a -> a -> Bool
>= SeatIndex -> Word64
unSeatIndex SeatIndex
lowerBound
Bool -> Bool -> Bool
&& SeatIndex -> Word64
unSeatIndex SeatIndex
seatIndex Word64 -> Word64 -> Bool
forall a. Ord a => a -> a -> Bool
<= SeatIndex -> Word64
unSeatIndex SeatIndex
upperBound
where
(SeatIndex
lowerBound, SeatIndex
upperBound) =
Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
-> (SeatIndex, SeatIndex)
forall i e. Array i e -> (i, i)
Array.bounds (ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a.
ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
unExtWFAStakeDistr ExtWFAStakeDistr a
distr)
getCandidateIfSeatWithinBounds ::
SeatIndex ->
ExtWFAStakeDistr a ->
Maybe (PoolId, a, LedgerStake, Cumulative LedgerStake)
getCandidateIfSeatWithinBounds :: forall a.
SeatIndex
-> ExtWFAStakeDistr a
-> Maybe (PoolId, a, LedgerStake, Cumulative LedgerStake)
getCandidateIfSeatWithinBounds SeatIndex
seatIndex ExtWFAStakeDistr a
distr
| SeatIndex -> ExtWFAStakeDistr a -> Bool
forall a. SeatIndex -> ExtWFAStakeDistr a -> Bool
seatIndexWithinBounds SeatIndex
seatIndex ExtWFAStakeDistr a
distr =
(PoolId, a, LedgerStake, Cumulative LedgerStake)
-> Maybe (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a. a -> Maybe a
Just ((PoolId, a, LedgerStake, Cumulative LedgerStake)
-> Maybe (PoolId, a, LedgerStake, Cumulative LedgerStake))
-> (PoolId, a, LedgerStake, Cumulative LedgerStake)
-> Maybe (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a b. (a -> b) -> a -> b
$ Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
-> SeatIndex -> (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall i e. Ix i => Array i e -> i -> e
(Array.!) (ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a.
ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
unExtWFAStakeDistr ExtWFAStakeDistr a
distr) SeatIndex
seatIndex
| Bool
otherwise =
Maybe (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a. Maybe a
Nothing
unsafeGetCandidateInSeat ::
SeatIndex ->
ExtWFAStakeDistr a ->
(PoolId, a, LedgerStake, Cumulative LedgerStake)
unsafeGetCandidateInSeat :: forall a.
SeatIndex
-> ExtWFAStakeDistr a
-> (PoolId, a, LedgerStake, Cumulative LedgerStake)
unsafeGetCandidateInSeat SeatIndex
seatIndex ExtWFAStakeDistr a
distr =
Bool
-> (PoolId, a, LedgerStake, Cumulative LedgerStake)
-> (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a. (?callStack::CallStack) => Bool -> a -> a
assert (SeatIndex -> ExtWFAStakeDistr a -> Bool
forall a. SeatIndex -> ExtWFAStakeDistr a -> Bool
seatIndexWithinBounds SeatIndex
seatIndex ExtWFAStakeDistr a
distr) ((PoolId, a, LedgerStake, Cumulative LedgerStake)
-> (PoolId, a, LedgerStake, Cumulative LedgerStake))
-> (PoolId, a, LedgerStake, Cumulative LedgerStake)
-> (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a b. (a -> b) -> a -> b
$
Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
-> SeatIndex -> (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall i e. Ix i => Array i e -> i -> e
(Array.!) (ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
forall a.
ExtWFAStakeDistr a
-> Array SeatIndex (PoolId, a, LedgerStake, Cumulative LedgerStake)
unExtWFAStakeDistr ExtWFAStakeDistr a
distr) SeatIndex
seatIndex