Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove stake lock #84

Merged
merged 9 commits into from
Oct 31, 2024
Merged
Show file tree
Hide file tree
Changes from 8 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 4 additions & 28 deletions contracts/sfc/ConstantsManager.sol
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,8 @@ contract ConstantsManager is Ownable {
uint256 public burntFeeShare;
// The percentage of fees to transfer to treasury address, e.g., 10%
uint256 public treasuryFeeShare;
// The ratio of the reward rate at base rate (no lock), e.g., 30%
uint256 public unlockedRewardRatio;
// The minimum duration of a stake/delegation lockup, e.g. 2 weeks
uint256 public minLockupDuration;
// The maximum duration of a stake/delegation lockup, e.g. 1 year
uint256 public maxLockupDuration;
// The ratio of the reward rate, e.g., 30%
uint256 public rewardRatio;
// the number of epochs that undelegated stake is locked for
uint256 public withdrawalPeriodEpochs;
// the number of seconds that undelegated stake is locked for
Expand Down Expand Up @@ -87,34 +83,14 @@ contract ConstantsManager is Ownable {
treasuryFeeShare = v;
}

function updateUnlockedRewardRatio(uint256 v) external virtual onlyOwner {
function updateRewardRatio(uint256 v) external virtual onlyOwner {
thaarok marked this conversation as resolved.
Show resolved Hide resolved
if (v < (5 * Decimal.unit()) / 100) {
revert ValueTooSmall();
}
if (v > Decimal.unit() / 2) {
revert ValueTooLarge();
}
unlockedRewardRatio = v;
}

function updateMinLockupDuration(uint256 v) external virtual onlyOwner {
if (v < 86400) {
revert ValueTooSmall();
}
if (v > 86400 * 30) {
revert ValueTooLarge();
}
minLockupDuration = v;
}

function updateMaxLockupDuration(uint256 v) external virtual onlyOwner {
if (v < 86400 * 30) {
revert ValueTooSmall();
}
if (v > 86400 * 1460) {
revert ValueTooLarge();
}
maxLockupDuration = v;
rewardRatio = v;
}

function updateWithdrawalPeriodEpochs(uint256 v) external virtual onlyOwner {
Expand Down
4 changes: 1 addition & 3 deletions contracts/sfc/NetworkInitializer.sol
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,7 @@ contract NetworkInitializer {
consts.updateValidatorCommission((15 * Decimal.unit()) / 100);
consts.updateBurntFeeShare((20 * Decimal.unit()) / 100);
consts.updateTreasuryFeeShare((10 * Decimal.unit()) / 100);
consts.updateUnlockedRewardRatio((30 * Decimal.unit()) / 100);
consts.updateMinLockupDuration(86400 * 14);
consts.updateMaxLockupDuration(86400 * 365);
consts.updateRewardRatio((30 * Decimal.unit()) / 100);
consts.updateWithdrawalPeriodEpochs(3);
consts.updateWithdrawalPeriodTime(60 * 60 * 24 * 7);
consts.updateBaseRewardPerSecond(2668658453701531600);
Expand Down
24 changes: 2 additions & 22 deletions contracts/sfc/NodeDriver.sol
Original file line number Diff line number Diff line change
Expand Up @@ -110,28 +110,8 @@ contract NodeDriver is Initializable {
);
}
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We may simplify setGenesisValidator too:

    function setGenesisValidator(
        address _auth,
        uint256 validatorID,
        bytes calldata pubkey
    )


function setGenesisDelegation(
address delegator,
uint256 toValidatorID,
uint256 stake,
uint256 lockedStake,
uint256 lockupFromEpoch,
uint256 lockupEndTime,
uint256 lockupDuration,
uint256 earlyUnlockPenalty,
uint256 rewards
) external onlyNode {
backend.setGenesisDelegation(
delegator,
toValidatorID,
stake,
lockedStake,
lockupFromEpoch,
lockupEndTime,
lockupDuration,
earlyUnlockPenalty,
rewards
);
function setGenesisDelegation(address delegator, uint256 toValidatorID, uint256 stake) external onlyNode {
backend.setGenesisDelegation(delegator, toValidatorID, stake);
}

function deactivateValidator(uint256 validatorID, uint256 status) external onlyNode {
Expand Down
24 changes: 2 additions & 22 deletions contracts/sfc/NodeDriverAuth.sol
Original file line number Diff line number Diff line change
Expand Up @@ -141,28 +141,8 @@ contract NodeDriverAuth is Initializable, Ownable {
);
}

function setGenesisDelegation(
address delegator,
uint256 toValidatorID,
uint256 stake,
uint256 lockedStake,
uint256 lockupFromEpoch,
uint256 lockupEndTime,
uint256 lockupDuration,
uint256 earlyUnlockPenalty,
uint256 rewards
) external onlyDriver {
sfc.setGenesisDelegation(
delegator,
toValidatorID,
stake,
lockedStake,
lockupFromEpoch,
lockupEndTime,
lockupDuration,
earlyUnlockPenalty,
rewards
);
function setGenesisDelegation(address delegator, uint256 toValidatorID, uint256 stake) external onlyDriver {
sfc.setGenesisDelegation(delegator, toValidatorID, stake);
}

function deactivateValidator(uint256 validatorID, uint256 status) external onlyDriver {
Expand Down
12 changes: 1 addition & 11 deletions contracts/sfc/NodeDriverI.sol
Original file line number Diff line number Diff line change
Expand Up @@ -13,17 +13,7 @@ interface NodeDriverI {
uint256 deactivatedTime
) external;

function setGenesisDelegation(
address delegator,
uint256 toValidatorID,
uint256 stake,
uint256 lockedStake,
uint256 lockupFromEpoch,
uint256 lockupEndTime,
uint256 lockupDuration,
uint256 earlyUnlockPenalty,
uint256 rewards
) external;
function setGenesisDelegation(address delegator, uint256 toValidatorID, uint256 stake) external;

function deactivateValidator(uint256 validatorID, uint256 status) external;

Expand Down
23 changes: 3 additions & 20 deletions contracts/sfc/SFC.sol
Original file line number Diff line number Diff line change
Expand Up @@ -87,8 +87,7 @@ contract SFC is SFCBase, Version {
}

function rewardsStash(address delegator, uint256 validatorID) public view returns (uint256) {
Rewards memory stash = _rewardsStash[delegator][validatorID];
return stash.lockupBaseReward + stash.lockupExtraReward + stash.unlockedReward;
return _rewardsStash[delegator][validatorID];
}

/*
Expand Down Expand Up @@ -295,25 +294,9 @@ contract SFC is SFCBase, Version {
uint256 commissionRewardFull = _calcValidatorCommission(rawReward, c.validatorCommission());
uint256 selfStake = getStake[validatorAddr][validatorID];
if (selfStake != 0) {
uint256 lCommissionRewardFull = (commissionRewardFull * getLockedStake(validatorAddr, validatorID)) /
selfStake;
uint256 uCommissionRewardFull = commissionRewardFull - lCommissionRewardFull;
Rewards memory lCommissionReward = _scaleLockupReward(
lCommissionRewardFull,
getLockupInfo[validatorAddr][validatorID].duration
);
Rewards memory uCommissionReward = _scaleLockupReward(uCommissionRewardFull, 0);
_rewardsStash[validatorAddr][validatorID] = sumRewards(
_rewardsStash[validatorAddr][validatorID],
lCommissionReward,
uCommissionReward
);
getStashedLockupRewards[validatorAddr][validatorID] = sumRewards(
getStashedLockupRewards[validatorAddr][validatorID],
lCommissionReward,
uCommissionReward
);
_rewardsStash[validatorAddr][validatorID] += _scaleReward(commissionRewardFull);
}

// accounting reward per token for delegators
uint256 delegatorsReward = rawReward - commissionRewardFull;
// note: use latest stake for the sake of rewards distribution accuracy, not snapshot.receivedStake
Expand Down
55 changes: 2 additions & 53 deletions contracts/sfc/SFCBase.sol
Original file line number Diff line number Diff line change
Expand Up @@ -60,20 +60,10 @@ contract SFCBase is SFCState {
error GovVotesRecountFailed();

// staking
error LockedStakeGreaterThanTotalStake();
error InsufficientSelfStake();
error NotEnoughUnlockedStake();
error NotEnoughLockedStake();
error NotEnoughTimePassed();
error NotEnoughEpochsPassed();
error StakeIsFullySlashed();
error IncorrectDuration();
error ValidatorLockupTooShort();
error TooManyReLocks();
error TooFrequentReLocks();
error LockupDurationDecreased();
error AlreadyLockedUp();
error NotLockedUp();

// stashing
error NothingToStash();
Expand Down Expand Up @@ -132,35 +122,8 @@ contract SFCBase is SFCState {
totalSupply = totalSupply + amount;
}

function sumRewards(Rewards memory a, Rewards memory b) internal pure returns (Rewards memory) {
return
Rewards(
a.lockupExtraReward + b.lockupExtraReward,
a.lockupBaseReward + b.lockupBaseReward,
a.unlockedReward + b.unlockedReward
);
}

function sumRewards(Rewards memory a, Rewards memory b, Rewards memory c) internal pure returns (Rewards memory) {
return sumRewards(sumRewards(a, b), c);
}

function _scaleLockupReward(
uint256 fullReward,
uint256 lockupDuration
) internal view returns (Rewards memory reward) {
reward = Rewards(0, 0, 0);
uint256 unlockedRewardRatio = c.unlockedRewardRatio();
if (lockupDuration != 0) {
uint256 maxLockupExtraRatio = Decimal.unit() - unlockedRewardRatio;
uint256 lockupExtraRatio = (maxLockupExtraRatio * lockupDuration) / c.maxLockupDuration();
uint256 totalScaledReward = (fullReward * (unlockedRewardRatio + lockupExtraRatio)) / Decimal.unit();
reward.lockupBaseReward = (fullReward * unlockedRewardRatio) / Decimal.unit();
reward.lockupExtraReward = totalScaledReward - reward.lockupBaseReward;
} else {
reward.unlockedReward = (fullReward * unlockedRewardRatio) / Decimal.unit();
}
return reward;
function _scaleReward(uint256 fullReward) internal view returns (uint256) {
return (fullReward * c.rewardRatio()) / Decimal.unit();
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this seems to be better inline into its only usage

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The scaling goes away completely.

}

function _recountVotes(address delegator, address validatorAuth, bool strict) internal {
Expand Down Expand Up @@ -220,20 +183,6 @@ contract SFCBase is SFCState {
return (rawReward * commission) / Decimal.unit();
}

function getLockedStake(address delegator, uint256 toValidatorID) public view returns (uint256) {
if (!isLockedUp(delegator, toValidatorID)) {
return 0;
}
return getLockupInfo[delegator][toValidatorID].lockedStake;
}

function isLockedUp(address delegator, uint256 toValidatorID) public view returns (bool) {
return
getLockupInfo[delegator][toValidatorID].endTime != 0 &&
getLockupInfo[delegator][toValidatorID].lockedStake != 0 &&
_now() <= getLockupInfo[delegator][toValidatorID].endTime;
}

function _now() internal view virtual returns (uint256) {
return block.timestamp;
}
Expand Down
54 changes: 3 additions & 51 deletions contracts/sfc/SFCI.sol
Original file line number Diff line number Diff line change
Expand Up @@ -11,23 +11,9 @@ interface SFCI {
event Delegated(address indexed delegator, uint256 indexed toValidatorID, uint256 amount);
event Undelegated(address indexed delegator, uint256 indexed toValidatorID, uint256 indexed wrID, uint256 amount);
event Withdrawn(address indexed delegator, uint256 indexed toValidatorID, uint256 indexed wrID, uint256 amount);
event ClaimedRewards(
address indexed delegator,
uint256 indexed toValidatorID,
uint256 lockupExtraReward,
uint256 lockupBaseReward,
uint256 unlockedReward
);
event RestakedRewards(
address indexed delegator,
uint256 indexed toValidatorID,
uint256 lockupExtraReward,
uint256 lockupBaseReward,
uint256 unlockedReward
);
event ClaimedRewards(address indexed delegator, uint256 indexed toValidatorID, uint256 rewards);
event RestakedRewards(address indexed delegator, uint256 indexed toValidatorID, uint256 rewards);
event BurntFTM(uint256 amount);
event LockedUpStake(address indexed delegator, uint256 indexed validatorID, uint256 duration, uint256 amount);
event UnlockedStake(address indexed delegator, uint256 indexed validatorID, uint256 amount, uint256 penalty);
event UpdatedSlashingRefundRatio(uint256 indexed validatorID, uint256 refundRatio);
event RefundedSlashedLegacyDelegation(address indexed delegator, uint256 indexed validatorID, uint256 amount);

Expand All @@ -53,18 +39,8 @@ interface SFCI {
uint256 totalSupply
);

function getLockupInfo(
address,
uint256
) external view returns (uint256 lockedStake, uint256 fromEpoch, uint256 endTime, uint256 duration);

function getStake(address, uint256) external view returns (uint256);

function getStashedLockupRewards(
address,
uint256
) external view returns (uint256 lockupExtraReward, uint256 lockupBaseReward, uint256 unlockedReward);

function getValidator(
uint256
)
Expand Down Expand Up @@ -106,8 +82,6 @@ interface SFCI {

function totalActiveStake() external view returns (uint256);

function totalSlashedStake() external view returns (uint256);

function totalStake() external view returns (uint256);

function totalSupply() external view returns (uint256);
Expand Down Expand Up @@ -142,8 +116,6 @@ interface SFCI {

function rewardsStash(address delegator, uint256 validatorID) external view returns (uint256);

function getLockedStake(address delegator, uint256 toValidatorID) external view returns (uint256);

function createValidator(bytes calldata pubkey) external payable;

function getSelfStake(uint256 validatorID) external view returns (uint256);
Expand Down Expand Up @@ -186,16 +158,6 @@ interface SFCI {

function sealEpochValidators(uint256[] calldata nextValidatorIDs) external;

function isLockedUp(address delegator, uint256 toValidatorID) external view returns (bool);

function getUnlockedStake(address delegator, uint256 toValidatorID) external view returns (uint256);

function lockStake(uint256 toValidatorID, uint256 lockupDuration, uint256 amount) external;

function relockStake(uint256 toValidatorID, uint256 lockupDuration, uint256 amount) external;

function unlockStake(uint256 toValidatorID, uint256 amount) external returns (uint256);

function initialize(
uint256 sealedEpoch,
uint256 _totalSupply,
Expand All @@ -216,17 +178,7 @@ interface SFCI {
uint256 deactivatedTime
) external;

function setGenesisDelegation(
address delegator,
uint256 toValidatorID,
uint256 stake,
uint256 lockedStake,
uint256 lockupFromEpoch,
uint256 lockupEndTime,
uint256 lockupDuration,
uint256 earlyUnlockPenalty,
uint256 rewards
) external;
function setGenesisDelegation(address delegator, uint256 toValidatorID, uint256 stake) external;

function updateVoteBookAddress(address v) external;

Expand Down
Loading
Loading