IncentiveRewardsDistributor
Overview
IncentiveRewardsDistributor is a reward distribution contract closely integrated with the escrow voting and token locking ecosystem of EYWA. It leverages and extends the core logic from RewardsDistributor, providing:
Epoch-based (weekly) reward distribution.
Deposit and withdrawal of locked tokens, which influence the allocation of rewards.
Calculation and claiming of earned rewards for token owners.
Enforcement of whitelisting for new reward tokens to ensure controlled reward distribution.
Authorization checks that restrict certain actions (e.g.,
getReward
andnotifyRewardAmount
) exclusively toESCROW_VOTE_MANAGER
.
By integrating with EscrowVoteManager and EscrowManager, the IncentiveRewardsDistributor ensures that reward distributions are fair, secure, and directly linked to voting power and locked tokens, aligning incentives with governance outcomes.
Inherited Contracts and Interfaces
IncentiveRewardsDistributor inherits from:
RewardsDistributor (abstract): Provides foundational logic for depositing/withdrawing votes, calculating earned rewards, notifying new rewards, and facilitating reward claims.
IIncentiveRewardsDistributor: Defines additional interfaces for
getReward
andnotifyRewardAmount
, integrating authorization and token whitelisting checks.IRewardsDistributor: Interface specifying core reward distribution functions and data structures, which
RewardsDistributor
implements.IEscrowVoteManagerV1, IEscrowManager: External interfaces providing information about ownership, voting power, and token whitelisting.
State Variables (Inherited from RewardsDistributor)
The IncentiveRewardsDistributor does not introduce new state variables. It relies entirely on those inherited from RewardsDistributor
:
ESCROW_VOTE_MANAGER (address)
: The address of the escrow vote manager contract, which must authorize certain calls.ESCROW_MANAGER (address)
: The address of the escrow manager contract, providing ownership data for tokens.s_rewardTokens (address[])
: Array of addresses of recognized reward tokens.s_initialIncentiveTimestamp (uint256)
: The timestamp indicating when incentive distribution began.s_totalSupplyByEpoch (mapping(uint256 => uint256))
: The total amount of deposited (voted) tokens per epoch.s_isRewardToken (mapping(address => bool))
: Indicates whether a token is recognized as a reward token.s_balanceByOwnerAndEpoch (mapping(address => mapping(uint256 => uint256)))
: Tracks each ownerβs deposited token amount by epoch.s_rewardAmountByTokenAndEpoch (mapping(address => mapping(uint256 => uint256)))
: The reward amount allocated for each token in each epoch.s_lastRewardClaimByOwnerAndToken (mapping(address => mapping(address => uint256)))
: Records the last epoch timestamp when the owner claimed rewards for a given token.
All these variables are described in the RewardsDistributor
documentation.
Constructor
Signature:
Description:
Initializes the contract by calling the RewardsDistributor
constructor with the escrow vote manager and escrow manager addresses. After construction, the contract is ready to handle reward-related operations based on the inherited logic.
Parameters:
escrowVoteManager_
: Address of the escrow vote manager contract.escrowManager_
: Address of the escrow manager contract.
External Functions (IncentiveRewardsDistributor Specific)
getReward(...)
getReward(...)
Signature:
Description:
Allows ESCROW_VOTE_MANAGER
to claim rewards on behalf of a specified owner_
for a set of rewardTokens_
. Only ESCROW_VOTE_MANAGER
is authorized to call this function, ensuring that claims are directly tied to authorized voting operations and locked token states.
Parameters:
owner_
: The address of the owner claiming rewards.rewardTokens_
: An array of reward token addresses to claim.
Checks:
msg.sender
must beESCROW_VOTE_MANAGER
. Otherwise,UnauthorizedAccess()
is thrown.
Effects:
Internally calls
_getReward(owner_, rewardTokens_)
fromRewardsDistributor
to calculate and distribute the earned rewards to theowner_
.
notifyRewardAmount(...)
notifyRewardAmount(...)
Signature:
Description:
Notifies the contract of a new reward allocation for rewardToken_
. If this token is not yet recognized as a reward token, this call checks whether the token is whitelisted via IEscrowVoteManagerV1(ESCROW_VOTE_MANAGER).s_isWhitelistedToken(rewardToken_)
. If not whitelisted, NotWhitelisted()
is thrown. This ensures controlled introduction of new reward tokens.
Parameters:
rewardToken_
: The address of the reward token being added.rewardAmount_
: The amount of the token to add as rewards.
Checks:
If
rewardToken_
is not already ins_isRewardToken
, checks if it is whitelisted.rewardAmount_
must be non-zero.
Effects:
If new token recognized, it is added to
s_rewardTokens
and marked as a reward token.Calls
_notifyRewardAmount(msg.sender, rewardToken_, rewardAmount_)
fromRewardsDistributor
to handle token transfer and epoch accounting.
Inherited External Functions (from RewardsDistributor)
The following functions are defined in IRewardsDistributor
and implemented in RewardsDistributor
. The IncentiveRewardsDistributor
inherits them without modification:
deposit(...)
deposit(...)
Signature:
Description:
Deposits an amount of βvoting powerβ (associated with a token ID) into the contract for the current epoch. Only ESCROW_VOTE_MANAGER
can call this. This updates s_totalSupplyByEpoch
and s_balanceByOwnerAndEpoch
to reflect the deposited amount.
Parameters:
amount_
: The amount of tokens (voting power) being deposited.tokenId_
: The token ID associated with this deposit.
Checks:
msg.sender
must beESCROW_VOTE_MANAGER
. Otherwise,UnauthorizedAccess()
is thrown.
Effects:
Increases
s_totalSupplyByEpoch[currentEpochStart]
ands_balanceByOwnerAndEpoch[ownerOf(tokenId_)][currentEpochStart]
byamount_
.Emits
TokensDeposited
.
withdraw(...)
withdraw(...)
Signature:
Description:
Withdraws previously deposited voting power from the current epoch, reducing the total supply and the ownerβs balance for that epoch. Only ESCROW_VOTE_MANAGER
can call this function.
Parameters:
amount_
: The amount to withdraw.tokenId_
: The token ID associated with the withdrawal.
Checks:
msg.sender
must beESCROW_VOTE_MANAGER
.
Effects:
Decreases
s_totalSupplyByEpoch[currentEpochStart]
ands_balanceByOwnerAndEpoch[ownerOf(tokenId_)][currentEpochStart]
byamount_
.Emits
TokensWithdrawn
.
getRewardTokensCount()
getRewardTokensCount()
Signature:
Description:
Returns the number of reward tokens currently recognized by the contract (the length of s_rewardTokens
array).
Return:
uint256
: The count of reward tokens.
earned(...)
earned(...)
Signature:
Description:
Calculates the total amount of rewards owner_
has earned for rewardToken_
since the last claim, iterating through past epochs up to a limit (52 epochs by default).
Parameters:
owner_
: The address of the owner.rewardToken_
: The reward token to check.
Return:
(uint256 totalEarned, uint256 lastRewardClaimTimestamp)
: Total earned rewards and the updated timestamp after calculating earnings.
earnedByEpoch(...)
earnedByEpoch(...)
Signature:
Description:
Calculates how many rewards owner_
earned for rewardToken_
during a specific epoch_
.
Parameters:
owner_
: Ownerβs address.rewardToken_
: The reward token.epoch_
: The epoch start timestamp to check.
Return:
uint256
: The amount of rewards earned in that specific epoch.
rewardPerToken(...)
rewardPerToken(...)
Signature:
Description:
Calculates the reward per token deposited for a given rewardToken_
in a specific epoch_
. This is used in the calculation of each ownerβs earned rewards by epoch.
Parameters:
rewardToken_
: The reward token.epoch_
: The epoch start timestamp.
Return:
uint256
: The reward per token amount for the epoch.
Internal Functions (from RewardsDistributor)
_getReward(owner_, rewardTokens_)
and _notifyRewardAmount(sender_, rewardToken_, rewardAmount_)
are internal functions in RewardsDistributor
inherited by IncentiveRewardsDistributor
:
_getReward(owner_, rewardTokens_)
: Iterates through the given reward tokens, calculates the earned amount usingearned(...)
, updates thes_lastRewardClaimByOwnerAndToken
mapping, and transfers the calculated rewards toowner_
. EmitsRewardsClaimed
for each token._notifyRewardAmount(sender_, rewardToken_, rewardAmount_)
: TransfersrewardAmount_
ofrewardToken_
fromsender_
to the contract, updatess_rewardAmountByTokenAndEpoch[rewardToken_][currentEpochStart]
, setss_initialIncentiveTimestamp
if not set, and emitsRewardNotified
.
These internal functions are leveraged by IncentiveRewardsDistributor
through getReward
and notifyRewardAmount
after performing authorization and whitelisting checks.
Events
Inherited from RewardsDistributor
and IRewardsDistributor
:
TokensDeposited
: Emitted when tokens are deposited for a given tokenId.TokensWithdrawn
: Emitted when tokens are withdrawn.RewardNotified
: Emitted when a new reward amount is notified for an epoch.RewardsClaimed
: Emitted when an owner claims rewards.
IncentiveRewardsDistributor
does not introduce additional events beyond these inherited ones.
Errors
From RewardsDistributor
and IRewardsDistributor
:
InvalidRewardToken()
UnauthorizedAccess()
ZeroAmountProvided()
NotWhitelisted()
IncentiveRewardsDistributor
triggers UnauthorizedAccess()
if getReward
is called by anyone other than ESCROW_VOTE_MANAGER
, and NotWhitelisted()
if notifyRewardAmount
is called with a token not previously recognized and not whitelisted.
Summary
IncentiveRewardsDistributor extends the RewardsDistributor
by adding authorization and whitelisting checks for reward-related operations. It integrates seamlessly with the EYWA governance ecosystem, ensuring that rewards are distributed to token owners in proportion to their votes and locked tokens, while preventing unauthorized actions and distribution of unapproved reward tokens. This design maintains transparency, fairness, and security in the incentive allocation process.
Last updated