diff --git a/solidity/contracts/governance/WonderGovernor.sol b/solidity/contracts/governance/WonderGovernor.sol index d5f2fdc..67d2f87 100644 --- a/solidity/contracts/governance/WonderGovernor.sol +++ b/solidity/contracts/governance/WonderGovernor.sol @@ -11,8 +11,7 @@ import {DoubleEndedQueue} from '@openzeppelin/contracts/utils/structs/DoubleEnde import {Address} from '@openzeppelin/contracts/utils/Address.sol'; import {Context} from '@openzeppelin/contracts/utils/Context.sol'; import {Nonces} from '@openzeppelin/contracts/utils/Nonces.sol'; -import {IGovernor} from '@openzeppelin/contracts/governance/IGovernor.sol'; -import {IERC6372} from '@openzeppelin/contracts/interfaces/IERC6372.sol'; +import {IWonderGovernor, IERC6372} from '../../interfaces/governance/IWonderGovernor.sol'; /** * @dev Core of the governance system, designed to be extended through various modules. @@ -23,7 +22,15 @@ import {IERC6372} from '@openzeppelin/contracts/interfaces/IERC6372.sol'; * - A voting module must implement {_getVotes} * - Additionally, {votingPeriod} must also be implemented */ -abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, IERC721Receiver, IERC1155Receiver { +abstract contract WonderGovernor is + Context, + ERC165, + EIP712, + Nonces, + IWonderGovernor, + IERC721Receiver, + IERC1155Receiver +{ using DoubleEndedQueue for DoubleEndedQueue.Bytes32Deque; bytes32 public constant BALLOT_TYPEHASH = @@ -32,6 +39,7 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, keccak256('ExtendedBallot(uint256 proposalId,uint8 support,address voter,uint256 nonce,string reason,bytes params)'); struct ProposalCore { + uint8 proposalType; address proposer; uint48 voteStart; uint32 voteDuration; @@ -66,6 +74,16 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, _; } + /** + * @dev Checks if the proposalType is supported by the governor + */ + modifier validProposalType(uint8 proposalType) { + if (!_isValidProposalType(proposalType)) { + revert InvalidProposalType(proposalType); + } + _; + } + /** * @dev Sets the value for {name} and {version} */ @@ -86,26 +104,26 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, * @dev See {IERC165-supportsInterface}. */ function supportsInterface(bytes4 interfaceId) public view virtual override(IERC165, ERC165) returns (bool) { - return interfaceId == type(IGovernor).interfaceId || interfaceId == type(IERC1155Receiver).interfaceId + return interfaceId == type(IWonderGovernor).interfaceId || interfaceId == type(IERC1155Receiver).interfaceId || super.supportsInterface(interfaceId); } /** - * @dev See {IGovernor-name}. + * @dev See {IWonderGovernor-name}. */ function name() public view virtual returns (string memory) { return _name; } /** - * @dev See {IGovernor-version}. + * @dev See {IWonderGovernor-version}. */ function version() public view virtual returns (string memory) { return '1'; } /** - * @dev See {IGovernor-hashProposal}. + * @dev See {IWonderGovernor-hashProposal}. * * The proposal id is produced by hashing the ABI encoded `targets` array, the `values` array, the `calldatas` array * and the descriptionHash (bytes32 which itself is the keccak256 hash of the description string). This proposal id @@ -118,16 +136,17 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, * governor) the proposer will have to change the description in order to avoid proposal id conflicts. */ function hashProposal( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, bytes32 descriptionHash ) public pure virtual returns (uint256) { - return uint256(keccak256(abi.encode(targets, values, calldatas, descriptionHash))); + return uint256(keccak256(abi.encode(proposalType, targets, values, calldatas, descriptionHash))); } /** - * @dev See {IGovernor-state}. + * @dev See {IWonderGovernor-state}. */ function state(uint256 proposalId) public view virtual returns (ProposalState) { // We read the struct fields into the stack at once so Solidity emits a single SLOAD @@ -169,42 +188,40 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-proposalThreshold}. + * @dev See {IWonderGovernor-proposalThreshold}. */ - function proposalThreshold() public view virtual returns (uint256) { - return 0; - } + function proposalThreshold(uint8 proposalType) public view virtual returns (uint256); /** - * @dev See {IGovernor-proposalSnapshot}. + * @dev See {IWonderGovernor-proposalSnapshot}. */ function proposalSnapshot(uint256 proposalId) public view virtual returns (uint256) { return _proposals[proposalId].voteStart; } /** - * @dev See {IGovernor-proposalDeadline}. + * @dev See {IWonderGovernor-proposalDeadline}. */ function proposalDeadline(uint256 proposalId) public view virtual returns (uint256) { return _proposals[proposalId].voteStart + _proposals[proposalId].voteDuration; } /** - * @dev See {IGovernor-proposalProposer}. + * @dev See {IWonderGovernor-proposalProposer}. */ function proposalProposer(uint256 proposalId) public view virtual returns (address) { return _proposals[proposalId].proposer; } /** - * @dev See {IGovernor-proposalEta}. + * @dev See {IWonderGovernor-proposalEta}. */ function proposalEta(uint256 proposalId) public view virtual returns (uint256) { return _proposals[proposalId].etaSeconds; } /** - * @dev See {IGovernor-proposalNeedsQueuing}. + * @dev See {IWonderGovernor-proposalNeedsQueuing}. */ function proposalNeedsQueuing(uint256) public view virtual returns (bool) { return false; @@ -236,10 +253,25 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, */ function _voteSucceeded(uint256 proposalId) internal view virtual returns (bool); + /** + * @dev Is the proposalType valid or not + */ + function _isValidProposalType(uint8 proposalType) internal view virtual returns (bool); + + /** + * @dev Returns the `proposalTypes` supported. + */ + function _proposalTypes() internal view virtual returns (uint8[] memory); + /** * @dev Get the voting weight of `account` at a specific `timepoint`, for a vote as described by `params`. */ - function _getVotes(address account, uint256 timepoint, bytes memory params) internal view virtual returns (uint256); + function _getVotes( + address account, + uint8 proposalType, + uint256 timepoint, + bytes memory params + ) internal view virtual returns (uint256); /** * @dev Register a vote for `proposalId` by `account` with a given `support`, voting `weight` and voting `params`. @@ -265,14 +297,15 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-propose}. This function has opt-in frontrunning protection, described in {_isValidDescriptionForProposer}. + * @dev See {IWonderGovernor-propose}. This function has opt-in frontrunning protection, described in {_isValidDescriptionForProposer}. */ function propose( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, string memory description - ) public virtual returns (uint256) { + ) public virtual validProposalType(proposalType) returns (uint256) { address proposer = _msgSender(); // check description restriction @@ -281,28 +314,29 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } // check proposal threshold - uint256 proposerVotes = getVotes(proposer, clock() - 1); - uint256 votesThreshold = proposalThreshold(); + uint256 proposerVotes = getVotes(proposer, proposalType, clock() - 1); + uint256 votesThreshold = proposalThreshold(proposalType); if (proposerVotes < votesThreshold) { revert GovernorInsufficientProposerVotes(proposer, proposerVotes, votesThreshold); } - return _propose(targets, values, calldatas, description, proposer); + return _propose(proposalType, targets, values, calldatas, description, proposer); } /** * @dev Internal propose mechanism. Can be overridden to add more logic on proposal creation. * - * Emits a {IGovernor-ProposalCreated} event. + * Emits a {IWonderGovernor-ProposalCreated} event. */ function _propose( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, string memory description, address proposer ) internal virtual returns (uint256 proposalId) { - proposalId = hashProposal(targets, values, calldatas, keccak256(bytes(description))); + proposalId = hashProposal(proposalType, targets, values, calldatas, keccak256(bytes(description))); if (targets.length != values.length || targets.length != calldatas.length || targets.length == 0) { revert GovernorInvalidProposalLength(targets.length, calldatas.length, values.length); @@ -315,12 +349,14 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, uint256 duration = votingPeriod(); ProposalCore storage proposal = _proposals[proposalId]; + proposal.proposalType = proposalType; proposal.proposer = proposer; proposal.voteStart = SafeCast.toUint48(snapshot); proposal.voteDuration = SafeCast.toUint32(duration); emit ProposalCreated( proposalId, + proposalType, proposer, targets, values, @@ -335,15 +371,16 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-queue}. + * @dev See {IWonderGovernor-queue}. */ function queue( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, bytes32 descriptionHash ) public virtual returns (uint256) { - uint256 proposalId = hashProposal(targets, values, calldatas, descriptionHash); + uint256 proposalId = hashProposal(proposalType, targets, values, calldatas, descriptionHash); _validateStateBitmap(proposalId, _encodeStateBitmap(ProposalState.Succeeded)); @@ -383,15 +420,16 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-execute}. + * @dev See {IWonderGovernor-execute}. */ function execute( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, bytes32 descriptionHash ) public payable virtual returns (uint256) { - uint256 proposalId = hashProposal(targets, values, calldatas, descriptionHash); + uint256 proposalId = hashProposal(proposalType, targets, values, calldatas, descriptionHash); _validateStateBitmap( proposalId, _encodeStateBitmap(ProposalState.Succeeded) | _encodeStateBitmap(ProposalState.Queued) @@ -442,9 +480,10 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-cancel}. + * @dev See {IWonderGovernor-cancel}. */ function cancel( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, @@ -453,7 +492,7 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, // The proposalId will be recomputed in the `_cancel` call further down. However we need the value before we // do the internal call, because we need to check the proposal state BEFORE the internal `_cancel` call // changes it. The `hashProposal` duplication has a cost that is limited, and that we accept. - uint256 proposalId = hashProposal(targets, values, calldatas, descriptionHash); + uint256 proposalId = hashProposal(proposalType, targets, values, calldatas, descriptionHash); // public cancel restrictions (on top of existing _cancel restrictions). _validateStateBitmap(proposalId, _encodeStateBitmap(ProposalState.Pending)); @@ -461,22 +500,23 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, revert GovernorOnlyProposer(_msgSender()); } - return _cancel(targets, values, calldatas, descriptionHash); + return _cancel(proposalType, targets, values, calldatas, descriptionHash); } /** * @dev Internal cancel mechanism with minimal restrictions. A proposal can be cancelled in any state other than * Canceled, Expired, or Executed. Once cancelled a proposal can't be re-submitted. * - * Emits a {IGovernor-ProposalCanceled} event. + * Emits a {IWonderGovernor-ProposalCanceled} event. */ function _cancel( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, bytes32 descriptionHash ) internal virtual returns (uint256) { - uint256 proposalId = hashProposal(targets, values, calldatas, descriptionHash); + uint256 proposalId = hashProposal(proposalType, targets, values, calldatas, descriptionHash); _validateStateBitmap( proposalId, @@ -491,25 +531,26 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-getVotes}. + * @dev See {IWonderGovernor-getVotes}. */ - function getVotes(address account, uint256 timepoint) public view virtual returns (uint256) { - return _getVotes(account, timepoint, _defaultParams()); + function getVotes(address account, uint8 proposalType, uint256 timepoint) public view virtual returns (uint256) { + return _getVotes(account, proposalType, timepoint, _defaultParams()); } /** - * @dev See {IGovernor-getVotesWithParams}. + * @dev See {IWonderGovernor-getVotesWithParams}. */ function getVotesWithParams( address account, + uint8 proposalType, uint256 timepoint, bytes memory params ) public view virtual returns (uint256) { - return _getVotes(account, timepoint, params); + return _getVotes(account, proposalType, timepoint, params); } /** - * @dev See {IGovernor-castVote}. + * @dev See {IWonderGovernor-castVote}. */ function castVote(uint256 proposalId, uint8 support) public virtual returns (uint256) { address voter = _msgSender(); @@ -517,7 +558,7 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-castVoteWithReason}. + * @dev See {IWonderGovernor-castVoteWithReason}. */ function castVoteWithReason( uint256 proposalId, @@ -529,7 +570,7 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-castVoteWithReasonAndParams}. + * @dev See {IWonderGovernor-castVoteWithReasonAndParams}. */ function castVoteWithReasonAndParams( uint256 proposalId, @@ -542,7 +583,7 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-castVoteBySig}. + * @dev See {IWonderGovernor-castVoteBySig}. */ function castVoteBySig( uint256 proposalId, @@ -564,7 +605,7 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, } /** - * @dev See {IGovernor-castVoteWithReasonAndParamsBySig}. + * @dev See {IWonderGovernor-castVoteWithReasonAndParamsBySig}. */ function castVoteWithReasonAndParamsBySig( uint256 proposalId, @@ -601,9 +642,9 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, /** * @dev Internal vote casting mechanism: Check that the vote is pending, that it has not been cast yet, retrieve - * voting weight using {IGovernor-getVotes} and call the {_countVote} internal function. Uses the _defaultParams(). + * voting weight using {IWonderGovernor-getVotes} and call the {_countVote} internal function. Uses the _defaultParams(). * - * Emits a {IGovernor-VoteCast} event. + * Emits a {IWonderGovernor-VoteCast} event. */ function _castVote( uint256 proposalId, @@ -616,9 +657,9 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, /** * @dev Internal vote casting mechanism: Check that the vote is pending, that it has not been cast yet, retrieve - * voting weight using {IGovernor-getVotes} and call the {_countVote} internal function. + * voting weight using {IWonderGovernor-getVotes} and call the {_countVote} internal function. * - * Emits a {IGovernor-VoteCast} event. + * Emits a {IWonderGovernor-VoteCast} event. */ function _castVote( uint256 proposalId, @@ -629,7 +670,9 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, ) internal virtual returns (uint256) { _validateStateBitmap(proposalId, _encodeStateBitmap(ProposalState.Active)); - uint256 weight = _getVotes(account, proposalSnapshot(proposalId), params); + uint8 _proposalType = _proposals[proposalId].proposalType; + + uint256 weight = _getVotes(account, _proposalType, proposalSnapshot(proposalId), params); _countVote(proposalId, account, support, weight, params); if (params.length == 0) { @@ -826,17 +869,24 @@ abstract contract WonderGovernor is Context, ERC165, EIP712, Nonces, IGovernor, function CLOCK_MODE() public view virtual returns (string memory); /** - * @inheritdoc IGovernor + * @inheritdoc IWonderGovernor */ function votingDelay() public view virtual returns (uint256); /** - * @inheritdoc IGovernor + * @inheritdoc IWonderGovernor */ function votingPeriod() public view virtual returns (uint256); /** - * @inheritdoc IGovernor + * @inheritdoc IWonderGovernor */ - function quorum(uint256 timepoint) public view virtual returns (uint256); + function quorum(uint256 timepoint, uint8 proposalType) public view virtual returns (uint256); + + /** + * @inheritdoc IWonderGovernor + */ + function proposalTypes() public view virtual override returns (uint8[] memory) { + return _proposalTypes(); + } } diff --git a/solidity/contracts/governance/utils/WonderVotes.sol b/solidity/contracts/governance/utils/WonderVotes.sol index e4b22fa..f2903f2 100644 --- a/solidity/contracts/governance/utils/WonderVotes.sol +++ b/solidity/contracts/governance/utils/WonderVotes.sol @@ -143,7 +143,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes function delegate(address delegatee, uint8 proposalType) public virtual validProposalType(proposalType) { address account = _msgSender(); Delegate[] memory _singleDelegate = new Delegate[](1); - _singleDelegate[0] = Delegate({account: delegatee, weight: _totalWeight()}); + _singleDelegate[0] = Delegate({account: delegatee, weight: _weightNormalizer()}); _delegate(account, proposalType, _singleDelegate); } @@ -153,7 +153,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes function delegate(address delegatee) public virtual { address account = _msgSender(); Delegate[] memory _singleDelegate = new Delegate[](1); - _singleDelegate[0] = Delegate({account: delegatee, weight: _totalWeight()}); + _singleDelegate[0] = Delegate({account: delegatee, weight: _weightNormalizer()}); uint8[] memory proposalTypes = _getProposalTypes(); @@ -163,10 +163,10 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes } /** - * @dev See {IWonderVotes-totalWeight}. + * @dev See {IWonderVotes-weightNormalizer}. */ - function totalWeight() external view virtual returns (uint256) { - return _totalWeight(); + function weightNormalizer() external view virtual returns (uint256) { + return _weightNormalizer(); } /** @@ -211,7 +211,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes bytes32 s ) public virtual validProposalType(proposalType) { Delegate[] memory _singleDelegate = new Delegate[](1); - _singleDelegate[0] = Delegate({account: delegatee, weight: _totalWeight()}); + _singleDelegate[0] = Delegate({account: delegatee, weight: _weightNormalizer()}); delegateBySig(_singleDelegate, proposalType, nonce, expiry, v, r, s); } @@ -227,7 +227,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes bytes32 s ) public virtual { Delegate[] memory _singleDelegate = new Delegate[](1); - _singleDelegate[0] = Delegate({account: delegatee, weight: _totalWeight()}); + _singleDelegate[0] = Delegate({account: delegatee, weight: _weightNormalizer()}); uint8[] memory proposalTypes = _getProposalTypes(); @@ -249,7 +249,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes if (delegatees[i].weight == 0) revert ZeroWeight(); _weightSum += delegatees[i].weight; } - if (_weightSum != _totalWeight()) revert InvalidWeightSum(_weightSum); + if (_weightSum != _weightNormalizer()) revert InvalidWeightSum(_weightSum); Delegate[] memory _oldDelegates = delegates(account, proposalType); _delegatees[account][proposalType] = delegatees; @@ -287,7 +287,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes * @dev Moves delegated votes from one delegate to another. */ function _moveDelegateVotes(uint8 proposalType, Delegate[] memory from, Delegate[] memory to, uint256 amount) private { - uint256 _weightSum = _totalWeight(); + uint256 _weightSum = _weightNormalizer(); uint256 _weight; for (uint256 i = 0; i < from.length; i++) { @@ -353,7 +353,7 @@ abstract contract WonderVotes is Context, EIP712, Nonces, IERC6372, IWonderVotes /** * @dev Returns the total weight that each delegation should sum. */ - function _totalWeight() internal view virtual returns (uint256); + function _weightNormalizer() internal view virtual returns (uint256); /** * @dev Returns the types of proposals that are supported by the implementation. diff --git a/solidity/interfaces/governance/IWonderGovernor.sol b/solidity/interfaces/governance/IWonderGovernor.sol index cf6ed59..2e49684 100644 --- a/solidity/interfaces/governance/IWonderGovernor.sol +++ b/solidity/interfaces/governance/IWonderGovernor.sol @@ -5,7 +5,7 @@ import {IERC165} from '@openzeppelin/contracts/interfaces/IERC165.sol'; import {IERC6372} from '@openzeppelin/contracts/interfaces/IERC6372.sol'; /** - * @dev Interface of the {Governor} core. + * @dev Interface of the {WonderGovernor} core. */ interface IWonderGovernor is IERC165, IERC6372 { enum ProposalState { @@ -102,11 +102,17 @@ interface IWonderGovernor is IERC165, IERC6372 { */ error GovernorInvalidSignature(address voter); + /** + * @dev The proposalType is not supported by the governor. + */ + error InvalidProposalType(uint8 proposalType); + /** * @dev Emitted when a proposal is created. */ event ProposalCreated( uint256 proposalId, + uint8 proposalType, address proposer, address[] targets, uint256[] values, @@ -191,6 +197,7 @@ interface IWonderGovernor is IERC165, IERC6372 { * @dev Hashing function used to (re)build the proposal id from the proposal details.. */ function hashProposal( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, @@ -205,9 +212,9 @@ interface IWonderGovernor is IERC165, IERC6372 { /** * @notice module:core - * @dev The number of votes required in order for a voter to become a proposer. + * @dev The number of votes required in order for a voter to become a proposer given a proposalType. */ - function proposalThreshold() external view returns (uint256); + function proposalThreshold(uint8 proposalType) external view returns (uint256); /** * @notice module:core @@ -273,27 +280,32 @@ interface IWonderGovernor is IERC165, IERC6372 { /** * @notice module:user-config - * @dev Minimum number of cast voted required for a proposal to be successful. + * @dev Minimum number of cast voted required for a proposal type to be successful. * * NOTE: The `timepoint` parameter corresponds to the snapshot used for counting vote. This allows to scale the * quorum depending on values such as the totalSupply of a token at this timepoint (see {ERC20Votes}). */ - function quorum(uint256 timepoint) external view returns (uint256); + function quorum(uint256 timepoint, uint8 proposalType) external view returns (uint256); /** * @notice module:reputation - * @dev Voting power of an `account` at a specific `timepoint`. + * @dev Voting power of an `account` at a specific `timepoint` for a given `proposalType`. * * Note: this can be implemented in a number of ways, for example by reading the delegated balance from one (or * multiple), {ERC20Votes} tokens. */ - function getVotes(address account, uint256 timepoint) external view returns (uint256); + function getVotes(address account, uint8 proposalType, uint256 timepoint) external view returns (uint256); /** * @notice module:reputation - * @dev Voting power of an `account` at a specific `timepoint` given additional encoded parameters. + * @dev Voting power of an `account` at a specific `timepoint` for a given `proposalType` and additional encoded parameters. */ - function getVotesWithParams(address account, uint256 timepoint, bytes memory params) external view returns (uint256); + function getVotesWithParams( + address account, + uint8 proposalType, + uint256 timepoint, + bytes memory params + ) external view returns (uint256); /** * @notice module:voting @@ -308,6 +320,7 @@ interface IWonderGovernor is IERC165, IERC6372 { * Emits a {ProposalCreated} event. */ function propose( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, @@ -322,6 +335,7 @@ interface IWonderGovernor is IERC165, IERC6372 { * Emits a {ProposalQueued} event. */ function queue( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, @@ -338,6 +352,7 @@ interface IWonderGovernor is IERC165, IERC6372 { * NOTE: Some modules can modify the requirements for execution, for example by adding an additional timelock. */ function execute( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, @@ -351,6 +366,7 @@ interface IWonderGovernor is IERC165, IERC6372 { * Emits a {ProposalCanceled} event. */ function cancel( + uint8 proposalType, address[] memory targets, uint256[] memory values, bytes[] memory calldatas, @@ -413,4 +429,9 @@ interface IWonderGovernor is IERC165, IERC6372 { bytes memory params, bytes memory signature ) external returns (uint256 balance); + + /** + * @notice Returns the types of proposals that are supported by the governor. + */ + function proposalTypes() external view returns (uint8[] memory); } diff --git a/solidity/interfaces/governance/utils/IWonderVotes.sol b/solidity/interfaces/governance/utils/IWonderVotes.sol index 2f6c8af..f8944eb 100644 --- a/solidity/interfaces/governance/utils/IWonderVotes.sol +++ b/solidity/interfaces/governance/utils/IWonderVotes.sol @@ -17,7 +17,11 @@ interface IWonderVotes { error VotesExpiredSignature(uint256 expiry); /** + * <<<<<<< HEAD * @dev The weight delegation sum is different from totalWeight. + * ======= + * @dev The weight delegation sum is different from weightNormalizer. + * >>>>>>> c4a138a767bdf917be05f63ff44a3bb810d8b9db */ error InvalidWeightSum(uint256 weightSum); @@ -124,10 +128,15 @@ interface IWonderVotes { * used to calculate the amount of votes when partial delegating to more than 1 delegate. * Example: 100% = 10000 - beware of precision loss from division and overflows from multiplications */ - function totalWeight() external view returns (uint256); + function weightNormalizer() external view returns (uint256); /** * @dev Returns the maximum amount of delegates that a `proposalType` can be delegated to. */ function maxDelegates() external view returns (uint8); + + /** + * @dev Returns the `proposalTypes` supported. + */ + function proposalTypes() external view returns (uint8[] memory); }