ERC20Votes.sol 2.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. // SPDX-License-Identifier: MIT
  2. // OpenZeppelin Contracts (last updated v4.5.0) (token/ERC20/extensions/ERC20Votes.sol)
  3. pragma solidity ^0.8.0;
  4. import "../ERC20.sol";
  5. import "../../../governance/utils/Votes.sol";
  6. import "../../../utils/math/SafeCast.sol";
  7. /**
  8. * @dev Extension of ERC20 to support Compound-like voting and delegation. This version is more generic than Compound's,
  9. * and supports token supply up to 2^224^ - 1, while COMP is limited to 2^96^ - 1.
  10. *
  11. * NOTE: If exact COMP compatibility is required, use the {ERC20VotesComp} variant of this module.
  12. *
  13. * This extension keeps a history (checkpoints) of each account's vote power. Vote power can be delegated either
  14. * by calling the {delegate} function directly, or by providing a signature to be used with {delegateBySig}. Voting
  15. * power can be queried through the public accessors {getVotes} and {getPastVotes}.
  16. *
  17. * By default, token balance does not account for voting power. This makes transfers cheaper. The downside is that it
  18. * requires users to delegate to themselves in order to activate checkpoints and have their voting power tracked.
  19. *
  20. * _Available since v4.2._
  21. */
  22. abstract contract ERC20Votes is ERC20, Votes {
  23. /**
  24. * @dev Maximum token supply. Defaults to `type(uint224).max` (2^224^ - 1).
  25. */
  26. function _maxSupply() internal view virtual returns (uint224) {
  27. return type(uint224).max;
  28. }
  29. /**
  30. * @dev Move voting power when tokens are transferred.
  31. *
  32. * Emits a {IVotes-DelegateVotesChanged} event.
  33. */
  34. function _update(
  35. address from,
  36. address to,
  37. uint256 amount
  38. ) internal virtual override {
  39. super._update(from, to, amount);
  40. if (from == address(0)) {
  41. require(totalSupply() <= _maxSupply(), "ERC20Votes: total supply risks overflowing votes");
  42. }
  43. _transferVotingUnits(from, to, amount);
  44. }
  45. /**
  46. * @dev Get number of checkpoints for `account`.
  47. */
  48. function numCheckpoints(address account) public view virtual returns (uint32) {
  49. return _numCheckpoints(account);
  50. }
  51. /**
  52. * @dev Get the `pos`-th checkpoint for `account`.
  53. */
  54. function checkpoints(address account, uint32 pos) public view virtual returns (Checkpoints.Checkpoint memory) {
  55. return _checkpoints(account, pos);
  56. }
  57. /**
  58. * @dev Returns the balance of `account`.
  59. */
  60. function _getVotingUnits(address account) internal view virtual override returns (uint256) {
  61. return balanceOf(account);
  62. }
  63. }