Compare commits
133 Commits
v3.1.0-rc.
...
v3.3.0-sol
| Author | SHA1 | Date | |
|---|---|---|---|
| 40a15c0406 | |||
| a4fc50c501 | |||
| cddeaa226d | |||
| 6be5ffe54f | |||
| ba843f0ad9 | |||
| 4297be6ac1 | |||
| d2003a6fff | |||
| 1fccf6fa53 | |||
| 7f8fc584de | |||
| 1d1d2ba661 | |||
| 3881175d72 | |||
| f7bb84ce4c | |||
| c67d81bae1 | |||
| a5d1ac7ed0 | |||
| b8187aa529 | |||
| 877f440331 | |||
| 58892471a3 | |||
| 90ed1af972 | |||
| 21344b91ed | |||
| 3f9673c177 | |||
| fce2513827 | |||
| 3debb8820e | |||
| d3a4e31fe2 | |||
| 25ac33486c | |||
| 5803e11663 | |||
| b33372cc92 | |||
| bcb2b5d1cd | |||
| 3f2a2b5f62 | |||
| 4972bf4f23 | |||
| 3d2e5c0310 | |||
| f547b6ff27 | |||
| 5272799bdd | |||
| 1a230e3aa5 | |||
| 679b7d147c | |||
| 8effd1e02a | |||
| cb19930b83 | |||
| c6b07b33c5 | |||
| 47e37975c9 | |||
| 5472eedbad | |||
| af95fe7a93 | |||
| 705b0b0001 | |||
| 35c931126b | |||
| 6aada9d356 | |||
| da9161fc91 | |||
| 1e78adc28c | |||
| fcdf8f4618 | |||
| 8533499507 | |||
| fb4659c5d7 | |||
| a1408a3411 | |||
| f06738828b | |||
| b6b1c0130b | |||
| ea305cf32e | |||
| d41102d6c3 | |||
| 0c27ecc536 | |||
| 0f55c18595 | |||
| e5fbbda9ba | |||
| 7650210ad6 | |||
| ba125961d6 | |||
| 2bb06b1af4 | |||
| 8108f2f9b9 | |||
| 08dfaab829 | |||
| d1c121b599 | |||
| e98b187e64 | |||
| 87326f7313 | |||
| 7f3eee750a | |||
| ace35fdeda | |||
| bf4c9d700d | |||
| c7d99531a7 | |||
| ca7ee098ca | |||
| ec8efd52b4 | |||
| 9a83ced46e | |||
| 0d7bf01ac1 | |||
| 1229c28ce0 | |||
| f7ca35c9c6 | |||
| c08d1439dd | |||
| 09d437c1f9 | |||
| 492d4ac013 | |||
| 870ea2a88a | |||
| 29f4a38c0d | |||
| 1ada3b633e | |||
| 0ce14a078a | |||
| 45b81c969f | |||
| cfb7f80003 | |||
| 628dea7a08 | |||
| 22de765f3c | |||
| ae4e9845de | |||
| 95dc7525ac | |||
| f1cce7e223 | |||
| f2fb8cf23b | |||
| 9f900f6dba | |||
| 91f16a7e47 | |||
| 6bc2ae3731 | |||
| 885b76f66f | |||
| ded2b0a55c | |||
| 0f08b1d099 | |||
| aaa5ef81cf | |||
| cb791a1b21 | |||
| 0b489f4d79 | |||
| c187517395 | |||
| 89e2b7424b | |||
| 1f06fd7e66 | |||
| e5da0986bb | |||
| 0fc9578fe6 | |||
| b1ea59e814 | |||
| 7d48d79b53 | |||
| 6d5a73815d | |||
| d1f336d8fd | |||
| 48072e439d | |||
| 9700e6b4bd | |||
| 722879b32d | |||
| 943a663a31 | |||
| 2acb1abb1f | |||
| 4eb8d2bb10 | |||
| 04fc35707d | |||
| 09014f90f9 | |||
| 0c667ca32a | |||
| 7c4a2a0a29 | |||
| c801c8d2bb | |||
| 98e862e162 | |||
| b9d72d2991 | |||
| c6612871fb | |||
| b991fca341 | |||
| ef3bbbcf40 | |||
| 32f0fe5d08 | |||
| 6d987f1418 | |||
| de99bccbfd | |||
| 0cc882ef9d | |||
| 3f4420527b | |||
| 21d06999f6 | |||
| f3803d3a5d | |||
| c6da044dc5 | |||
| 02a6b05bde | |||
| 242400e9ea |
@ -1,84 +0,0 @@
|
||||
version: 2
|
||||
# 2.1 does not yet support local run
|
||||
# unless with workaround. For simplicity just use it.
|
||||
# https://github.com/CircleCI-Public/circleci-cli/issues/79
|
||||
|
||||
aliases:
|
||||
- &defaults
|
||||
docker:
|
||||
- image: circleci/node:10
|
||||
|
||||
- &cache_key_node_modules
|
||||
key: v1-node_modules-{{ checksum "package-lock.json" }}
|
||||
|
||||
jobs:
|
||||
dependencies:
|
||||
<<: *defaults
|
||||
steps:
|
||||
- checkout
|
||||
- restore_cache:
|
||||
<<: *cache_key_node_modules
|
||||
- run:
|
||||
name: Install npm dependencies and prepare
|
||||
command: |
|
||||
if [ ! -d node_modules ]; then
|
||||
npm ci
|
||||
else
|
||||
npm run prepare
|
||||
fi
|
||||
- persist_to_workspace:
|
||||
root: .
|
||||
paths:
|
||||
- node_modules
|
||||
- build
|
||||
- save_cache:
|
||||
paths:
|
||||
- node_modules
|
||||
<<: *cache_key_node_modules
|
||||
|
||||
lint:
|
||||
<<: *defaults
|
||||
steps:
|
||||
- checkout
|
||||
- attach_workspace:
|
||||
at: .
|
||||
- run:
|
||||
name: Linter
|
||||
command: npm run lint
|
||||
test:
|
||||
<<: *defaults
|
||||
steps:
|
||||
- checkout
|
||||
- attach_workspace:
|
||||
at: .
|
||||
- run:
|
||||
name: Unit tests
|
||||
command: npm run test
|
||||
|
||||
coverage:
|
||||
<<: *defaults
|
||||
steps:
|
||||
- checkout
|
||||
- attach_workspace:
|
||||
at: .
|
||||
- run:
|
||||
name: Unit tests with coverage report
|
||||
command: npm run coverage
|
||||
|
||||
# TODO(xinbenlv, #1839): run SOLC_NIGHTLY to be run but allow it to fail.
|
||||
|
||||
workflows:
|
||||
version: 2
|
||||
everything:
|
||||
jobs:
|
||||
- dependencies
|
||||
- lint:
|
||||
requires:
|
||||
- dependencies
|
||||
- test:
|
||||
requires:
|
||||
- dependencies
|
||||
- coverage:
|
||||
requires:
|
||||
- dependencies
|
||||
|
||||
@ -1,7 +0,0 @@
|
||||
version: 1
|
||||
|
||||
update_configs:
|
||||
- package_manager: "javascript"
|
||||
directory: "/"
|
||||
update_schedule: "weekly"
|
||||
version_requirement_updates: "increase_versions"
|
||||
@ -8,7 +8,7 @@ charset = utf-8
|
||||
end_of_line = lf
|
||||
indent_style = space
|
||||
insert_final_newline = true
|
||||
trim_trailing_whitespace = true
|
||||
trim_trailing_whitespace = false
|
||||
max_line_length = 120
|
||||
|
||||
[*.sol]
|
||||
@ -16,3 +16,6 @@ indent_size = 4
|
||||
|
||||
[*.js]
|
||||
indent_size = 2
|
||||
|
||||
[*.adoc]
|
||||
max_line_length = 0
|
||||
|
||||
@ -18,6 +18,8 @@
|
||||
"contract": false,
|
||||
"assert": false,
|
||||
"web3": false,
|
||||
"usePlugin": false,
|
||||
"extendEnvironment": false,
|
||||
},
|
||||
"rules": {
|
||||
|
||||
|
||||
45
.github/workflows/test.yml
vendored
Normal file
45
.github/workflows/test.yml
vendored
Normal file
@ -0,0 +1,45 @@
|
||||
name: Test
|
||||
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- master
|
||||
- release-v*
|
||||
pull_request: {}
|
||||
|
||||
jobs:
|
||||
test:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
with:
|
||||
node-version: 10.x
|
||||
- uses: actions/cache@v2
|
||||
id: cache
|
||||
with:
|
||||
path: '**/node_modules'
|
||||
key: npm-v2-${{ hashFiles('**/package-lock.json') }}
|
||||
restore-keys: npm-v2-
|
||||
- run: npm ci
|
||||
if: steps.cache.outputs.cache-hit != 'true'
|
||||
- run: npm run lint
|
||||
- run: npm run test
|
||||
|
||||
coverage:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v1
|
||||
with:
|
||||
node-version: 10.x
|
||||
- uses: actions/cache@v2
|
||||
id: cache
|
||||
with:
|
||||
path: '**/node_modules'
|
||||
key: npm-v2-${{ hashFiles('**/package-lock.json') }}
|
||||
restore-keys: npm-v2-
|
||||
- run: npm ci
|
||||
if: steps.cache.outputs.cache-hit != 'true'
|
||||
- run: npm run coverage
|
||||
- uses: codecov/codecov-action@v1
|
||||
7
.gitignore
vendored
7
.gitignore
vendored
@ -50,3 +50,10 @@ contracts/README.md
|
||||
|
||||
# temporary artifact from solidity-coverage
|
||||
allFiredEvents
|
||||
.coverage_artifacts
|
||||
.coverage_cache
|
||||
.coverage_contracts
|
||||
|
||||
# buidler
|
||||
cache
|
||||
artifacts
|
||||
|
||||
3
.mocharc.js
Normal file
3
.mocharc.js
Normal file
@ -0,0 +1,3 @@
|
||||
module.exports = {
|
||||
timeout: 4000,
|
||||
};
|
||||
@ -4,5 +4,8 @@ module.exports = {
|
||||
compileCommand: 'npm run compile',
|
||||
skipFiles: [
|
||||
'mocks',
|
||||
]
|
||||
],
|
||||
providerOptions: {
|
||||
default_balance_ether: '10000000000000000000000000',
|
||||
},
|
||||
}
|
||||
|
||||
@ -4,7 +4,9 @@
|
||||
"func-order": "off",
|
||||
"mark-callable-contracts": "off",
|
||||
"no-empty-blocks": "off",
|
||||
"compiler-version": ["error", "^0.6.0"],
|
||||
"private-vars-leading-underscore": "error"
|
||||
"compiler-version": "off",
|
||||
"private-vars-leading-underscore": "error",
|
||||
"reason-string": "off",
|
||||
"func-visibility": ["error", { "ignoreConstructors": true }]
|
||||
}
|
||||
}
|
||||
|
||||
38
CHANGELOG.md
38
CHANGELOG.md
@ -1,6 +1,42 @@
|
||||
# Changelog
|
||||
|
||||
## 3.1.0 (unreleased)
|
||||
## 3.3.0 (2020-11-26)
|
||||
|
||||
* Now supports both Solidity 0.6 and 0.7. Compiling with solc 0.7 will result in warnings. Install the `solc-0.7` tag to compile without warnings.
|
||||
* `Address`: added `functionStaticCall`, similar to the existing `functionCall`. ([#2333](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2333))
|
||||
* `TimelockController`: added a contract to augment access control schemes with a delay. ([#2354](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2354))
|
||||
* `EnumerableSet`: added `Bytes32Set`, for sets of `bytes32`. ([#2395](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2395))
|
||||
|
||||
## 3.2.2-solc-0.7 (2020-10-28)
|
||||
* Resolve warnings introduced by Solidity 0.7.4. ([#2396](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2396))
|
||||
|
||||
## 3.2.1-solc-0.7 (2020-09-15)
|
||||
* `ERC777`: Remove a warning about function state visibility in Solidity 0.7. ([#2327](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2327))
|
||||
|
||||
## 3.2.0 (2020-09-10)
|
||||
|
||||
### New features
|
||||
* Proxies: added the proxy contracts from OpenZeppelin SDK. ([#2335](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2335))
|
||||
|
||||
#### Proxy changes with respect to OpenZeppelin SDK
|
||||
|
||||
Aside from upgrading them from Solidity 0.5 to 0.6, we've changed a few minor things from the proxy contracts as they were found in OpenZeppelin SDK.
|
||||
|
||||
- `UpgradeabilityProxy` was renamed to `UpgradeableProxy`.
|
||||
- `AdminUpgradeabilityProxy` was renamed to `TransparentUpgradeableProxy`.
|
||||
- `Proxy._willFallback` was renamed to `Proxy._beforeFallback`.
|
||||
- `UpgradeabilityProxy._setImplementation` and `AdminUpgradeabilityProxy._setAdmin` were made private.
|
||||
|
||||
### Improvements
|
||||
* `Address.isContract`: switched from `extcodehash` to `extcodesize` for less gas usage. ([#2311](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2311))
|
||||
|
||||
### Breaking changes
|
||||
* `ERC20Snapshot`: switched to using `_beforeTokenTransfer` hook instead of overriding ERC20 operations. ([#2312](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2312))
|
||||
|
||||
This small change in the way we implemented `ERC20Snapshot` may affect users who are combining this contract with
|
||||
other ERC20 flavors, since it no longer overrides `_transfer`, `_mint`, and `_burn`. This can result in having to remove Solidity `override(...)` specifiers in derived contracts for these functions, and to instead have to add it for `_beforeTokenTransfer`. See [Using Hooks](https://docs.openzeppelin.com/contracts/3.x/extending-contracts#using-hooks) in the documentation.
|
||||
|
||||
## 3.1.0 (2020-06-23)
|
||||
|
||||
### New features
|
||||
* `SafeCast`: added functions to downcast signed integers (e.g. `toInt32`), improving usability of `SignedSafeMath`. ([#2243](https://github.com/OpenZeppelin/openzeppelin-contracts/pull/2243))
|
||||
|
||||
@ -1,69 +0,0 @@
|
||||
# Code Style
|
||||
|
||||
We value clean code and consistency, and those are prerequisites for us to
|
||||
include new code in the repository. Before proposing a change, please read this
|
||||
document and take some time to familiarize yourself with the style of the
|
||||
existing codebase.
|
||||
|
||||
## Solidity code
|
||||
|
||||
In order to be consistent with all the other Solidity projects, we follow the
|
||||
[official recommendations documented in the Solidity style guide](http://solidity.readthedocs.io/en/latest/style-guide.html).
|
||||
|
||||
Any exception or additions specific to our project are documented below.
|
||||
|
||||
### Naming
|
||||
|
||||
* Try to avoid acronyms and abbreviations.
|
||||
|
||||
* All state variables should be private.
|
||||
|
||||
* Private state variables should have an underscore prefix.
|
||||
|
||||
```
|
||||
contract TestContract {
|
||||
uint256 private _privateVar;
|
||||
uint256 internal _internalVar;
|
||||
}
|
||||
```
|
||||
|
||||
* Parameters must not be prefixed with an underscore.
|
||||
|
||||
```
|
||||
function test(uint256 testParameter1, uint256 testParameter2) {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
* Internal and private functions should have an underscore prefix.
|
||||
|
||||
```
|
||||
function _testInternal() internal {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
```
|
||||
function _testPrivate() private {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
* Events should be emitted immediately after the state change that they
|
||||
represent, and consequently they should be named in past tense.
|
||||
|
||||
```
|
||||
function _burn(address _who, uint256 _value) internal {
|
||||
super._burn(_who, _value);
|
||||
emit TokensBurned(_who, _value);
|
||||
}
|
||||
```
|
||||
|
||||
Some standards (e.g. ERC20) use present tense, and in those cases the
|
||||
standard specification prevails.
|
||||
|
||||
* Interface names should have a capital I prefix.
|
||||
|
||||
```
|
||||
interface IERC777 {
|
||||
```
|
||||
@ -44,13 +44,6 @@ npm test
|
||||
npm run lint
|
||||
```
|
||||
|
||||
or you can simply run CircleCI locally
|
||||
```bash
|
||||
circleci local execute --job build
|
||||
circleci local execute --job test
|
||||
```
|
||||
*Note*: requires installing CircleCI and docker locally on your machine.
|
||||
|
||||
5) Go to [github.com/OpenZeppelin/openzeppelin-contracts](https://github.com/OpenZeppelin/openzeppelin-contracts) in your web browser and issue a new pull request.
|
||||
|
||||
*IMPORTANT* Read the PR template very carefully and make sure to follow all the instructions. These instructions
|
||||
|
||||
@ -10,7 +10,7 @@ program that extracts the API Reference from source code.
|
||||
|
||||
The [`docs.openzeppelin.com`](https://github.com/OpenZeppelin/docs.openzeppelin.com)
|
||||
repository hosts the configuration for the entire site, which includes
|
||||
documetation for all of the OpenZeppelin projects.
|
||||
documentation for all of the OpenZeppelin projects.
|
||||
|
||||
To run the docs locally you should run `npm run docs:watch` on this
|
||||
repository.
|
||||
|
||||
@ -28,37 +28,78 @@ Consistency on the way classes are used is paramount to an easier understanding
|
||||
#### D6 - Regular Audits
|
||||
Following good programming practices is a way to reduce the risk of vulnerabilities, but professional code audits are still needed. We will perform regular code audits on major releases, and hire security professionals to provide independent review.
|
||||
|
||||
## Style Guidelines
|
||||
# Style Guidelines
|
||||
|
||||
The design guidelines have quite a high abstraction level. These style guidelines are more concrete and easier to apply, and also more opinionated.
|
||||
The design guidelines have quite a high abstraction level. These style guidelines are more concrete and easier to apply, and also more opinionated. We value clean code and consistency, and those are prerequisites for us to include new code in the repository. Before proposing a change, please read these guidelines and take some time to familiarize yourself with the style of the existing codebase.
|
||||
|
||||
### General
|
||||
## Solidity code
|
||||
|
||||
#### G0 - Default to Solidity's official style guide.
|
||||
In order to be consistent with all the other Solidity projects, we follow the
|
||||
[official recommendations documented in the Solidity style guide](http://solidity.readthedocs.io/en/latest/style-guide.html).
|
||||
|
||||
Follow the official Solidity style guide: https://solidity.readthedocs.io/en/latest/style-guide.html
|
||||
Any exception or additions specific to our project are documented below.
|
||||
|
||||
#### G1 - No Magic Constants
|
||||
* Try to avoid acronyms and abbreviations.
|
||||
|
||||
Avoid constants in the code as much as possible. Magic strings are also magic constants.
|
||||
* All state variables should be private.
|
||||
|
||||
#### G2 - Code that Fails Early
|
||||
* Private state variables should have an underscore prefix.
|
||||
|
||||
We ask our code to fail as soon as possible when an unexpected input was provided or unexpected state was found.
|
||||
```
|
||||
contract TestContract {
|
||||
uint256 private _privateVar;
|
||||
uint256 internal _internalVar;
|
||||
}
|
||||
```
|
||||
|
||||
#### G3 - Internal Amounts Must be Signed Integers and Represent the Smallest Units.
|
||||
* Parameters must not be prefixed with an underscore.
|
||||
|
||||
Avoid representation errors by always dealing with weis when handling ether. GUIs can convert to more human-friendly representations. Use Signed Integers (int) to prevent underflow problems.
|
||||
```
|
||||
function test(uint256 testParameter1, uint256 testParameter2) {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
* Internal and private functions should have an underscore prefix.
|
||||
|
||||
```
|
||||
function _testInternal() internal {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
```
|
||||
function _testPrivate() private {
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
* Events should be emitted immediately after the state change that they
|
||||
represent, and consequently they should be named in past tense.
|
||||
|
||||
```
|
||||
function _burn(address who, uint256 value) internal {
|
||||
super._burn(who, value);
|
||||
emit TokensBurned(who, value);
|
||||
}
|
||||
```
|
||||
|
||||
Some standards (e.g. ERC20) use present tense, and in those cases the
|
||||
standard specification prevails.
|
||||
|
||||
* Interface names should have a capital I prefix.
|
||||
|
||||
```
|
||||
interface IERC777 {
|
||||
```
|
||||
|
||||
|
||||
### Testing
|
||||
## Tests
|
||||
|
||||
#### T1 - Tests Must be Written Elegantly
|
||||
* Tests Must be Written Elegantly
|
||||
|
||||
Style guidelines are not relaxed for tests. Tests are a good way to show how to use the library, and maintaining them is extremely necessary.
|
||||
Tests are a good way to show how to use the library, and maintaining them is extremely necessary. Don't write long tests, write helper functions to make them be as short and concise as possible (they should take just a few lines each), and use good variable names.
|
||||
|
||||
Don't write long tests, write helper functions to make them be as short and concise as possible (they should take just a few lines each), and use good variable names.
|
||||
* Tests Must not be Random
|
||||
|
||||
#### T2 - Tests Must not be Random
|
||||
|
||||
Inputs for tests should not be generated randomly. Accounts used to create test contracts are an exception, those can be random. Also, the type and structure of outputs should be checked.
|
||||
Inputs for tests should not be generated randomly. Accounts used to create test contracts are an exception, those can be random. Also, the type and structure of outputs should be checked.
|
||||
|
||||
13
README.md
13
README.md
@ -1,8 +1,7 @@
|
||||
# <img src="logo.png" alt="OpenZeppelin" height="40px">
|
||||
# <img src="logo.svg" alt="OpenZeppelin" height="40px">
|
||||
|
||||
[](https://docs.openzeppelin.com/contracts)
|
||||
[](https://www.npmjs.org/package/@openzeppelin/contracts)
|
||||
[](https://circleci.com/gh/OpenZeppelin/openzeppelin-contracts)
|
||||
[](https://codecov.io/gh/OpenZeppelin/openzeppelin-contracts)
|
||||
|
||||
**A library for secure smart contract development.** Build on a solid foundation of community-vetted code.
|
||||
@ -11,7 +10,7 @@
|
||||
* Flexible [role-based permissioning](https://docs.openzeppelin.com/contracts/access-control) scheme.
|
||||
* Reusable [Solidity components](https://docs.openzeppelin.com/contracts/utilities) to build custom contracts and complex decentralized systems.
|
||||
* First-class integration with the [Gas Station Network](https://docs.openzeppelin.com/contracts/gsn) for systems with no gas fees!
|
||||
* Audited by leading security firms (_last full audit on v2.0.0_).
|
||||
* [Audited](https://github.com/OpenZeppelin/openzeppelin-contracts/tree/master/audit) by leading security firms (_last full audit on v2.0.0_).
|
||||
|
||||
## Overview
|
||||
|
||||
@ -28,12 +27,12 @@ OpenZeppelin Contracts features a [stable API](https://docs.openzeppelin.com/con
|
||||
Once installed, you can use the contracts in the library by importing them:
|
||||
|
||||
```solidity
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "@openzeppelin/contracts/token/ERC721/ERC721.sol";
|
||||
|
||||
contract MyNFT is ERC721 {
|
||||
constructor() ERC721("MyNFT", "MNFT") public {
|
||||
contract MyCollectible is ERC721 {
|
||||
constructor() ERC721("MyCollectible", "MCO") {
|
||||
}
|
||||
}
|
||||
```
|
||||
@ -44,7 +43,7 @@ To keep your system secure, you should **always** use the installed code as-is,
|
||||
|
||||
## Learn More
|
||||
|
||||
The guides in the sidebar will teach about different concepts, and how to use the related contracts that OpenZeppelin Contracts provides:
|
||||
The guides in the [docs site](https://docs.openzeppelin.com/contracts) will teach about different concepts, and how to use the related contracts that OpenZeppelin Contracts provides:
|
||||
|
||||
* [Access Control](https://docs.openzeppelin.com/contracts/access-control): decide who can perform each of the actions on your system.
|
||||
* [Tokens](https://docs.openzeppelin.com/contracts/tokens): create tradeable assets or collectives, and distribute them via [Crowdsales](https://docs.openzeppelin.com/contracts/crowdsales).
|
||||
|
||||
20
buidler.config.js
Normal file
20
buidler.config.js
Normal file
@ -0,0 +1,20 @@
|
||||
const fs = require('fs');
|
||||
const path = require('path');
|
||||
|
||||
usePlugin('solidity-coverage');
|
||||
usePlugin('@nomiclabs/buidler-truffle5');
|
||||
|
||||
for (const f of fs.readdirSync(path.join(__dirname, 'buidler'))) {
|
||||
require(path.join(__dirname, 'buidler', f));
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
networks: {
|
||||
buidlerevm: {
|
||||
blockGasLimit: 10000000,
|
||||
},
|
||||
},
|
||||
solc: {
|
||||
version: '0.7.4',
|
||||
},
|
||||
};
|
||||
10
buidler/env-contract.js
Normal file
10
buidler/env-contract.js
Normal file
@ -0,0 +1,10 @@
|
||||
extendEnvironment(env => {
|
||||
const { contract } = env;
|
||||
|
||||
env.contract = function (name, body) {
|
||||
// remove the default account from the accounts list used in tests, in order
|
||||
// to protect tests against accidentally passing due to the contract
|
||||
// deployer being used subsequently as function caller
|
||||
contract(name, accounts => body(accounts.slice(1)));
|
||||
};
|
||||
});
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/*
|
||||
* @dev Provides information about the current execution context, including the
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./IRelayRecipient.sol";
|
||||
import "./IRelayHub.sol";
|
||||
@ -115,7 +115,7 @@ abstract contract GSNRecipient is IRelayRecipient, Context {
|
||||
/**
|
||||
* @dev See `IRelayRecipient.preRelayedCall`.
|
||||
*
|
||||
* This function should not be overriden directly, use `_preRelayedCall` instead.
|
||||
* This function should not be overridden directly, use `_preRelayedCall` instead.
|
||||
*
|
||||
* * Requirements:
|
||||
*
|
||||
@ -138,7 +138,7 @@ abstract contract GSNRecipient is IRelayRecipient, Context {
|
||||
/**
|
||||
* @dev See `IRelayRecipient.postRelayedCall`.
|
||||
*
|
||||
* This function should not be overriden directly, use `_postRelayedCall` instead.
|
||||
* This function should not be overridden directly, use `_postRelayedCall` instead.
|
||||
*
|
||||
* * Requirements:
|
||||
*
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./GSNRecipient.sol";
|
||||
import "../math/SafeMath.sol";
|
||||
@ -30,7 +30,7 @@ contract GSNRecipientERC20Fee is GSNRecipient {
|
||||
/**
|
||||
* @dev The arguments to the constructor are the details that the gas payment token will have: `name` and `symbol`. `decimals` is hard-coded to 18.
|
||||
*/
|
||||
constructor(string memory name, string memory symbol) public {
|
||||
constructor(string memory name, string memory symbol) {
|
||||
_token = new __unstable__ERC20Owned(name, symbol);
|
||||
}
|
||||
|
||||
@ -86,6 +86,8 @@ contract GSNRecipientERC20Fee is GSNRecipient {
|
||||
|
||||
// The maximum token charge is pre-charged from the user
|
||||
_token.safeTransferFrom(from, address(this), maxPossibleCharge);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -116,7 +118,7 @@ contract GSNRecipientERC20Fee is GSNRecipient {
|
||||
contract __unstable__ERC20Owned is ERC20, Ownable {
|
||||
uint256 private constant _UINT256_MAX = 2**256 - 1;
|
||||
|
||||
constructor(string memory name, string memory symbol) public ERC20(name, symbol) { }
|
||||
constructor(string memory name, string memory symbol) ERC20(name, symbol) { }
|
||||
|
||||
// The owner (GSNRecipientERC20Fee) can mint tokens
|
||||
function mint(address account, uint256 amount) public onlyOwner {
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./GSNRecipient.sol";
|
||||
import "../cryptography/ECDSA.sol";
|
||||
@ -23,7 +23,7 @@ contract GSNRecipientSignature is GSNRecipient {
|
||||
/**
|
||||
* @dev Sets the trusted signer that is going to be producing signatures to approve relayed calls.
|
||||
*/
|
||||
constructor(address trustedSigner) public {
|
||||
constructor(address trustedSigner) {
|
||||
require(trustedSigner != address(0), "GSNRecipientSignature: trusted signer is the zero address");
|
||||
_trustedSigner = trustedSigner;
|
||||
}
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Interface for `RelayHub`, the core contract of the GSN. Users should not need to interact with this contract
|
||||
@ -41,7 +41,7 @@ interface IRelayHub {
|
||||
function registerRelay(uint256 transactionFee, string calldata url) external;
|
||||
|
||||
/**
|
||||
* @dev Emitted when a relay is registered or re-registerd. Looking at these events (and filtering out
|
||||
* @dev Emitted when a relay is registered or re-registered. Looking at these events (and filtering out
|
||||
* {RelayRemoved} events) lets a client discover the list of available relays.
|
||||
*/
|
||||
event RelayAdded(address indexed relay, address indexed owner, uint256 transactionFee, uint256 stake, uint256 unstakeDelay, string url);
|
||||
@ -105,7 +105,7 @@ interface IRelayHub {
|
||||
event Deposited(address indexed recipient, address indexed from, uint256 amount);
|
||||
|
||||
/**
|
||||
* @dev Returns an account's deposits. These can be either a contracts's funds, or a relay owner's revenue.
|
||||
* @dev Returns an account's deposits. These can be either a contract's funds, or a relay owner's revenue.
|
||||
*/
|
||||
function balanceOf(address target) external view returns (uint256);
|
||||
|
||||
@ -180,7 +180,7 @@ interface IRelayHub {
|
||||
* - `gasLimit`: gas to forward when calling the encoded function
|
||||
* - `nonce`: client's nonce
|
||||
* - `signature`: client's signature over all previous params, plus the relay and RelayHub addresses
|
||||
* - `approvalData`: dapp-specific data forwared to {acceptRelayedCall}. This value is *not* verified by the
|
||||
* - `approvalData`: dapp-specific data forwarded to {acceptRelayedCall}. This value is *not* verified by the
|
||||
* `RelayHub`, but it still can be used for e.g. a signature.
|
||||
*
|
||||
* Emits a {TransactionRelayed} event.
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Base interface for a contract that will be called via the GSN from {IRelayHub}.
|
||||
@ -53,7 +53,7 @@ interface IRelayRecipient {
|
||||
*
|
||||
* Returns a value to be passed to {postRelayedCall}.
|
||||
*
|
||||
* {preRelayedCall} is called with 100k gas: if it runs out during exection or otherwise reverts, the relayed call
|
||||
* {preRelayedCall} is called with 100k gas: if it runs out during execution or otherwise reverts, the relayed call
|
||||
* will not be executed, but the recipient will still be charged for the transaction's cost.
|
||||
*/
|
||||
function preRelayedCall(bytes calldata context) external returns (bytes32);
|
||||
|
||||
@ -1,5 +1,8 @@
|
||||
= Gas Station Network (GSN)
|
||||
|
||||
[.readme-notice]
|
||||
NOTE: This document is better viewed at https://docs.openzeppelin.com/contracts/api/gsn
|
||||
|
||||
This set of contracts provide all the tools required to make a contract callable via the https://gsn.openzeppelin.com[Gas Station Network].
|
||||
|
||||
TIP: If you're new to the GSN, head over to our xref:learn::sending-gasless-transactions.adoc[overview of the system] and basic guide to xref:ROOT:gsn.adoc[creating a GSN-capable contract].
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/EnumerableSet.sol";
|
||||
import "../utils/Address.sol";
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
/**
|
||||
@ -15,7 +15,7 @@ import "../GSN/Context.sol";
|
||||
* `onlyOwner`, which can be applied to your functions to restrict their use to
|
||||
* the owner.
|
||||
*/
|
||||
contract Ownable is Context {
|
||||
abstract contract Ownable is Context {
|
||||
address private _owner;
|
||||
|
||||
event OwnershipTransferred(address indexed previousOwner, address indexed newOwner);
|
||||
@ -23,7 +23,7 @@ contract Ownable is Context {
|
||||
/**
|
||||
* @dev Initializes the contract setting the deployer as the initial owner.
|
||||
*/
|
||||
constructor () internal {
|
||||
constructor () {
|
||||
address msgSender = _msgSender();
|
||||
_owner = msgSender;
|
||||
emit OwnershipTransferred(address(0), msgSender);
|
||||
|
||||
@ -1,9 +1,101 @@
|
||||
= Access
|
||||
|
||||
Contract modules for authorization and access control mechanisms.
|
||||
[.readme-notice]
|
||||
NOTE: This document is better viewed at https://docs.openzeppelin.com/contracts/api/access
|
||||
|
||||
== Contracts
|
||||
This directory provides ways to restrict who can access the functions of a contract or when they can do it.
|
||||
|
||||
- {AccessControl} provides a general role based access control mechanism. Multiple hierarchical roles can be created and assigned each to multiple accounts.
|
||||
- {Ownable} is a simpler mechanism with a single owner "role" that can be assigned to a single account. This simpler mechanism can be useful for quick tests but projects with production concerns are likely to outgrow it.
|
||||
- {TimelockController} is used in combination with one of the above two mechanisms. By assigning a role to an instance of the `TimelockController` contract, the access to the functions controlled by that role will be delayed by some amount of time.
|
||||
|
||||
== Authorization
|
||||
|
||||
{{Ownable}}
|
||||
|
||||
{{AccessControl}}
|
||||
|
||||
== Timelock
|
||||
|
||||
{{TimelockController}}
|
||||
|
||||
[[timelock-terminology]]
|
||||
==== Terminology
|
||||
|
||||
* *Operation:* A transaction (or a set of transactions) that is the subject of the timelock. It has to be scheduled by a proposer and executed by an executor. The timelock enforces a minimum delay between the proposition and the execution (see xref:access-control.adoc#operation_lifecycle[operation lifecycle]). If the operation contains multiple transactions (batch mode), they are executed atomically. Operations are identified by the hash of their content.
|
||||
* *Operation status:*
|
||||
** *Unset:* An operation that is not part of the timelock mechanism.
|
||||
** *Pending:* An operation that has been scheduled, before the timer expires.
|
||||
** *Ready:* An operation that has been scheduled, after the timer expires.
|
||||
** *Done:* An operation that has been executed.
|
||||
* *Predecessor*: An (optional) dependency between operations. An operation can depend on another operation (its predecessor), forcing the execution order of these two operations.
|
||||
* *Role*:
|
||||
** *Proposer:* An address (smart contract or EOA) that is in charge of scheduling (and cancelling) operations.
|
||||
** *Executor:* An address (smart contract or EOA) that is in charge of executing operations.
|
||||
|
||||
[[timelock-operation]]
|
||||
==== Operation structure
|
||||
|
||||
Operation executed by the xref:api:access.adoc#TimelockController[`TimelockControler`] can contain one or multiple subsequent calls. Depending on whether you need to multiple calls to be executed atomically, you can either use simple or batched operations.
|
||||
|
||||
Both operations contain:
|
||||
|
||||
* *Target*, the address of the smart contract that the timelock should operate on.
|
||||
* *Value*, in wei, that should be sent with the transaction. Most of the time this will be 0. Ether can be deposited before-end or passed along when executing the transaction.
|
||||
* *Data*, containing the encoded function selector and parameters of the call. This can be produced using a number of tools. For example, a maintenance operation granting role `ROLE` to `ACCOUNT` can be encode using web3js as follows:
|
||||
|
||||
```javascript
|
||||
const data = timelock.contract.methods.grantRole(ROLE, ACCOUNT).encodeABI()
|
||||
```
|
||||
|
||||
* *Predecessor*, that specifies a dependency between operations. This dependency is optional. Use `bytes32(0)` if the operation does not have any dependency.
|
||||
* *Salt*, used to disambiguate two otherwise identical operations. This can be any random value.
|
||||
|
||||
In the case of batched operations, `target`, `value` and `data` are specified as arrays, which must be of the same length.
|
||||
|
||||
[[timelock-operation-lifecycle]]
|
||||
==== Operation lifecycle
|
||||
|
||||
Timelocked operations are identified by a unique id (their hash) and follow a specific lifecycle:
|
||||
|
||||
`Unset` -> `Pending` -> `Pending` + `Ready` -> `Done`
|
||||
|
||||
* By calling xref:api:access.adoc#TimelockController-schedule-address-uint256-bytes-bytes32-bytes32-uint256-[`schedule`] (or xref:api:access.adoc#TimelockController-scheduleBatch-address---uint256---bytes---bytes32-bytes32-uint256-[`scheduleBatch`]), a proposer moves the operation from the `Unset` to the `Pending` state. This starts a timer that must be longer than the minimum delay. The timer expires at a timestamp accessible through the xref:api:access.adoc#TimelockController-getTimestamp-bytes32-[`getTimestamp`] method.
|
||||
* Once the timer expires, the operation automatically gets the `Ready` state. At this point, it can be executed.
|
||||
* By calling xref:api:access.adoc#TimelockController-TimelockController-execute-address-uint256-bytes-bytes32-bytes32-[`execute`] (or xref:api:access.adoc#TimelockController-executeBatch-address---uint256---bytes---bytes32-bytes32-[`executeBatch`]), an executor triggers the operation's underlying transactions and moves it to the `Done` state. If the operation has a predecessor, it has to be in the `Done` state for this transition to succeed.
|
||||
* xref:api:access.adoc#TimelockController-TimelockController-cancel-bytes32-[`cancel`] allows proposers to cancel any `Pending` operation. This resets the operation to the `Unset` state. It is thus possible for a proposer to re-schedule an operation that has been cancelled. In this case, the timer restarts when the operation is re-scheduled.
|
||||
|
||||
Operations status can be queried using the functions:
|
||||
|
||||
* xref:api:access.adoc#TimelockController-isOperationPending-bytes32-[`isOperationPending(bytes32)`]
|
||||
* xref:api:access.adoc#TimelockController-isOperationReady-bytes32-[`isOperationReady(bytes32)`]
|
||||
* xref:api:access.adoc#TimelockController-isOperationDone-bytes32-[`isOperationDone(bytes32)`]
|
||||
|
||||
[[timelock-roles]]
|
||||
==== Roles
|
||||
|
||||
[[timelock-admin]]
|
||||
===== Admin
|
||||
|
||||
The admins are in charge of managing proposers and executors. For the timelock to be self-governed, this role should only be given to the timelock itself. Upon deployment, both the timelock and the deployer have this role. After further configuration and testing, the deployer can renounce this role such that all further maintenance operations have to go through the timelock process.
|
||||
|
||||
This role is identified by the *TIMELOCK_ADMIN_ROLE* value: `0x5f58e3a2316349923ce3780f8d587db2d72378aed66a8261c916544fa6846ca5`
|
||||
|
||||
[[timelock-proposer]]
|
||||
===== Proposer
|
||||
|
||||
The proposers are in charge of scheduling (and cancelling) operations. This is a critical role, that should be given to governing entities. This could be an EOA, a multisig, or a DAO.
|
||||
|
||||
WARNING: *Proposer fight:* Having multiple proposers, while providing redundancy in case one becomes unavailable, can be dangerous. As proposer have their say on all operations, they could cancel operations they disagree with, including operations to remove them for the proposers.
|
||||
|
||||
This role is identified by the *PROPOSER_ROLE* value: `0xb09aa5aeb3702cfd50b6b62bc4532604938f21248a27a1d5ca736082b6819cc1`
|
||||
|
||||
[[timelock-executor]]
|
||||
===== Executor
|
||||
|
||||
The executors are in charge of executing the operations scheduled by the proposers once the timelock expires. Logic dictates that multisig or DAO that are proposers should also be executors in order to guarantee operations that have been scheduled will eventually be executed. However, having additional executor can reduce the cost (the executing transaction does not require validation by the multisig or DAO that proposed it), while ensuring whoever is in charge of execution cannot trigger actions that have not been scheduled by the proposers.
|
||||
|
||||
This role is identified by the *EXECUTOR_ROLE* value: `0xd8aa0f3194971a2a116679f7c2090f6939c8d4e01a2a8d7e41d55e5351469e63`
|
||||
|
||||
|
||||
WARNING: A live contract without at least one proposer and one executor is locked. Make sure these roles are filled by reliable entities before the deployer renounces its administrative rights in favour of the timelock contract itself. See the {AccessControl} documentation to learn more about role management.
|
||||
|
||||
281
contracts/access/TimelockController.sol
Normal file
281
contracts/access/TimelockController.sol
Normal file
@ -0,0 +1,281 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
pragma experimental ABIEncoderV2;
|
||||
|
||||
import "./../math/SafeMath.sol";
|
||||
import "./AccessControl.sol";
|
||||
|
||||
/**
|
||||
* @dev Contract module which acts as a timelocked controller. When set as the
|
||||
* owner of an `Ownable` smart contract, it enforces a timelock on all
|
||||
* `onlyOwner` maintenance operations. This gives time for users of the
|
||||
* controlled contract to exit before a potentially dangerous maintenance
|
||||
* operation is applied.
|
||||
*
|
||||
* By default, this contract is self administered, meaning administration tasks
|
||||
* have to go through the timelock process. The proposer (resp executor) role
|
||||
* is in charge of proposing (resp executing) operations. A common use case is
|
||||
* to position this {TimelockController} as the owner of a smart contract, with
|
||||
* a multisig or a DAO as the sole proposer.
|
||||
*/
|
||||
contract TimelockController is AccessControl {
|
||||
|
||||
bytes32 public constant TIMELOCK_ADMIN_ROLE = keccak256("TIMELOCK_ADMIN_ROLE");
|
||||
bytes32 public constant PROPOSER_ROLE = keccak256("PROPOSER_ROLE");
|
||||
bytes32 public constant EXECUTOR_ROLE = keccak256("EXECUTOR_ROLE");
|
||||
uint256 internal constant _DONE_TIMESTAMP = uint256(1);
|
||||
|
||||
mapping(bytes32 => uint256) private _timestamps;
|
||||
uint256 private _minDelay;
|
||||
|
||||
/**
|
||||
* @dev Emitted when a call is scheduled as part of operation `id`.
|
||||
*/
|
||||
event CallScheduled(bytes32 indexed id, uint256 indexed index, address target, uint256 value, bytes data, bytes32 predecessor, uint256 delay);
|
||||
|
||||
/**
|
||||
* @dev Emitted when a call is performed as part of operation `id`.
|
||||
*/
|
||||
event CallExecuted(bytes32 indexed id, uint256 indexed index, address target, uint256 value, bytes data);
|
||||
|
||||
/**
|
||||
* @dev Emitted when operation `id` is cancelled.
|
||||
*/
|
||||
event Cancelled(bytes32 indexed id);
|
||||
|
||||
/**
|
||||
* @dev Emitted when the minimum delay for future operations is modified.
|
||||
*/
|
||||
event MinDelayChange(uint256 oldDuration, uint256 newDuration);
|
||||
|
||||
/**
|
||||
* @dev Initializes the contract with a given `minDelay`.
|
||||
*/
|
||||
constructor(uint256 minDelay, address[] memory proposers, address[] memory executors) {
|
||||
_setRoleAdmin(TIMELOCK_ADMIN_ROLE, TIMELOCK_ADMIN_ROLE);
|
||||
_setRoleAdmin(PROPOSER_ROLE, TIMELOCK_ADMIN_ROLE);
|
||||
_setRoleAdmin(EXECUTOR_ROLE, TIMELOCK_ADMIN_ROLE);
|
||||
|
||||
// deployer + self administration
|
||||
_setupRole(TIMELOCK_ADMIN_ROLE, _msgSender());
|
||||
_setupRole(TIMELOCK_ADMIN_ROLE, address(this));
|
||||
|
||||
// register proposers
|
||||
for (uint256 i = 0; i < proposers.length; ++i) {
|
||||
_setupRole(PROPOSER_ROLE, proposers[i]);
|
||||
}
|
||||
|
||||
// register executors
|
||||
for (uint256 i = 0; i < executors.length; ++i) {
|
||||
_setupRole(EXECUTOR_ROLE, executors[i]);
|
||||
}
|
||||
|
||||
_minDelay = minDelay;
|
||||
emit MinDelayChange(0, minDelay);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Modifier to make a function callable only by a certain role. In
|
||||
* addition to checking the sender's role, `address(0)` 's role is also
|
||||
* considered. Granting a role to `address(0)` is equivalent to enabling
|
||||
* this role for everyone.
|
||||
*/
|
||||
modifier onlyRole(bytes32 role) {
|
||||
require(hasRole(role, _msgSender()) || hasRole(role, address(0)), "TimelockController: sender requires permission");
|
||||
_;
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Contract might receive/hold ETH as part of the maintenance process.
|
||||
*/
|
||||
receive() external payable {}
|
||||
|
||||
/**
|
||||
* @dev Returns whether an operation is pending or not.
|
||||
*/
|
||||
function isOperationPending(bytes32 id) public view returns (bool pending) {
|
||||
return _timestamps[id] > _DONE_TIMESTAMP;
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Returns whether an operation is ready or not.
|
||||
*/
|
||||
function isOperationReady(bytes32 id) public view returns (bool ready) {
|
||||
// solhint-disable-next-line not-rely-on-time
|
||||
return _timestamps[id] > _DONE_TIMESTAMP && _timestamps[id] <= block.timestamp;
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Returns whether an operation is done or not.
|
||||
*/
|
||||
function isOperationDone(bytes32 id) public view returns (bool done) {
|
||||
return _timestamps[id] == _DONE_TIMESTAMP;
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Returns the timestamp at with an operation becomes ready (0 for
|
||||
* unset operations, 1 for done operations).
|
||||
*/
|
||||
function getTimestamp(bytes32 id) public view returns (uint256 timestamp) {
|
||||
return _timestamps[id];
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Returns the minimum delay for an operation to become valid.
|
||||
*/
|
||||
function getMinDelay() public view returns (uint256 duration) {
|
||||
return _minDelay;
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Returns the identifier of an operation containing a single
|
||||
* transaction.
|
||||
*/
|
||||
function hashOperation(address target, uint256 value, bytes calldata data, bytes32 predecessor, bytes32 salt) public pure returns (bytes32 hash) {
|
||||
return keccak256(abi.encode(target, value, data, predecessor, salt));
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Returns the identifier of an operation containing a batch of
|
||||
* transactions.
|
||||
*/
|
||||
function hashOperationBatch(address[] calldata targets, uint256[] calldata values, bytes[] calldata datas, bytes32 predecessor, bytes32 salt) public pure returns (bytes32 hash) {
|
||||
return keccak256(abi.encode(targets, values, datas, predecessor, salt));
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Schedule an operation containing a single transaction.
|
||||
*
|
||||
* Emits a {CallScheduled} event.
|
||||
*
|
||||
* Requirements:
|
||||
*
|
||||
* - the caller must have the 'proposer' role.
|
||||
*/
|
||||
function schedule(address target, uint256 value, bytes calldata data, bytes32 predecessor, bytes32 salt, uint256 delay) public virtual onlyRole(PROPOSER_ROLE) {
|
||||
bytes32 id = hashOperation(target, value, data, predecessor, salt);
|
||||
_schedule(id, delay);
|
||||
emit CallScheduled(id, 0, target, value, data, predecessor, delay);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Schedule an operation containing a batch of transactions.
|
||||
*
|
||||
* Emits one {CallScheduled} event per transaction in the batch.
|
||||
*
|
||||
* Requirements:
|
||||
*
|
||||
* - the caller must have the 'proposer' role.
|
||||
*/
|
||||
function scheduleBatch(address[] calldata targets, uint256[] calldata values, bytes[] calldata datas, bytes32 predecessor, bytes32 salt, uint256 delay) public virtual onlyRole(PROPOSER_ROLE) {
|
||||
require(targets.length == values.length, "TimelockController: length mismatch");
|
||||
require(targets.length == datas.length, "TimelockController: length mismatch");
|
||||
|
||||
bytes32 id = hashOperationBatch(targets, values, datas, predecessor, salt);
|
||||
_schedule(id, delay);
|
||||
for (uint256 i = 0; i < targets.length; ++i) {
|
||||
emit CallScheduled(id, i, targets[i], values[i], datas[i], predecessor, delay);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Schedule an operation that is to becomes valid after a given delay.
|
||||
*/
|
||||
function _schedule(bytes32 id, uint256 delay) private {
|
||||
require(_timestamps[id] == 0, "TimelockController: operation already scheduled");
|
||||
require(delay >= _minDelay, "TimelockController: insufficient delay");
|
||||
// solhint-disable-next-line not-rely-on-time
|
||||
_timestamps[id] = SafeMath.add(block.timestamp, delay);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Cancel an operation.
|
||||
*
|
||||
* Requirements:
|
||||
*
|
||||
* - the caller must have the 'proposer' role.
|
||||
*/
|
||||
function cancel(bytes32 id) public virtual onlyRole(PROPOSER_ROLE) {
|
||||
require(isOperationPending(id), "TimelockController: operation cannot be cancelled");
|
||||
delete _timestamps[id];
|
||||
|
||||
emit Cancelled(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Execute an (ready) operation containing a single transaction.
|
||||
*
|
||||
* Emits a {CallExecuted} event.
|
||||
*
|
||||
* Requirements:
|
||||
*
|
||||
* - the caller must have the 'executor' role.
|
||||
*/
|
||||
function execute(address target, uint256 value, bytes calldata data, bytes32 predecessor, bytes32 salt) public payable virtual onlyRole(EXECUTOR_ROLE) {
|
||||
bytes32 id = hashOperation(target, value, data, predecessor, salt);
|
||||
_beforeCall(predecessor);
|
||||
_call(id, 0, target, value, data);
|
||||
_afterCall(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Execute an (ready) operation containing a batch of transactions.
|
||||
*
|
||||
* Emits one {CallExecuted} event per transaction in the batch.
|
||||
*
|
||||
* Requirements:
|
||||
*
|
||||
* - the caller must have the 'executor' role.
|
||||
*/
|
||||
function executeBatch(address[] calldata targets, uint256[] calldata values, bytes[] calldata datas, bytes32 predecessor, bytes32 salt) public payable virtual onlyRole(EXECUTOR_ROLE) {
|
||||
require(targets.length == values.length, "TimelockController: length mismatch");
|
||||
require(targets.length == datas.length, "TimelockController: length mismatch");
|
||||
|
||||
bytes32 id = hashOperationBatch(targets, values, datas, predecessor, salt);
|
||||
_beforeCall(predecessor);
|
||||
for (uint256 i = 0; i < targets.length; ++i) {
|
||||
_call(id, i, targets[i], values[i], datas[i]);
|
||||
}
|
||||
_afterCall(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Checks before execution of an operation's calls.
|
||||
*/
|
||||
function _beforeCall(bytes32 predecessor) private view {
|
||||
require(predecessor == bytes32(0) || isOperationDone(predecessor), "TimelockController: missing dependency");
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Checks after execution of an operation's calls.
|
||||
*/
|
||||
function _afterCall(bytes32 id) private {
|
||||
require(isOperationReady(id), "TimelockController: operation is not ready");
|
||||
_timestamps[id] = _DONE_TIMESTAMP;
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Execute an operation's call.
|
||||
*
|
||||
* Emits a {CallExecuted} event.
|
||||
*/
|
||||
function _call(bytes32 id, uint256 index, address target, uint256 value, bytes calldata data) private {
|
||||
// solhint-disable-next-line avoid-low-level-calls
|
||||
(bool success,) = target.call{value: value}(data);
|
||||
require(success, "TimelockController: underlying transaction reverted");
|
||||
|
||||
emit CallExecuted(id, index, target, value, data);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dev Changes the timelock duration for future operations.
|
||||
*
|
||||
* Emits a {MinDelayChange} event.
|
||||
*/
|
||||
function updateDelay(uint256 newDelay) external virtual {
|
||||
require(msg.sender == address(this), "TimelockController: caller must be timelock");
|
||||
emit MinDelayChange(_minDelay, newDelay);
|
||||
_minDelay = newDelay;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Elliptic Curve Digital Signature Algorithm (ECDSA) operations.
|
||||
@ -52,13 +52,8 @@ library ECDSA {
|
||||
// with 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 - s1 and flip v from 27 to 28 or
|
||||
// vice versa. If your library also generates signatures with 0/1 for v instead 27/28, add 27 to v to accept
|
||||
// these malleable signatures as well.
|
||||
if (uint256(s) > 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0) {
|
||||
revert("ECDSA: invalid signature 's' value");
|
||||
}
|
||||
|
||||
if (v != 27 && v != 28) {
|
||||
revert("ECDSA: invalid signature 'v' value");
|
||||
}
|
||||
require(uint256(s) <= 0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF5D576E7357A4501DDFE92F46681B20A0, "ECDSA: invalid signature 's' value");
|
||||
require(v == 27 || v == 28, "ECDSA: invalid signature 'v' value");
|
||||
|
||||
// If the signature is valid (and not malleable), return the signer address
|
||||
address signer = ecrecover(hash, v, r, s);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev These functions deal with verification of Merkle trees (hash trees),
|
||||
|
||||
@ -1,5 +1,8 @@
|
||||
= Cryptography
|
||||
|
||||
[.readme-notice]
|
||||
NOTE: This document is better viewed at https://docs.openzeppelin.com/contracts/api/cryptography
|
||||
|
||||
This collection of libraries provides simple and safe ways to use different cryptographic primitives.
|
||||
|
||||
== Libraries
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./IERC165.sol";
|
||||
|
||||
@ -10,7 +10,7 @@ import "./IERC165.sol";
|
||||
* Contracts may inherit from this and call {_registerInterface} to declare
|
||||
* their support of an interface.
|
||||
*/
|
||||
contract ERC165 is IERC165 {
|
||||
abstract contract ERC165 is IERC165 {
|
||||
/*
|
||||
* bytes4(keccak256('supportsInterface(bytes4)')) == 0x01ffc9a7
|
||||
*/
|
||||
@ -21,7 +21,7 @@ contract ERC165 is IERC165 {
|
||||
*/
|
||||
mapping(bytes4 => bool) private _supportedInterfaces;
|
||||
|
||||
constructor () internal {
|
||||
constructor () {
|
||||
// Derived contracts need only register support for their own interfaces,
|
||||
// we register support for ERC165 itself here
|
||||
_registerInterface(_INTERFACE_ID_ERC165);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.2;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Library used to query support of an interface declared via {IERC165}.
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./IERC1820Implementer.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Interface of the ERC165 standard, as defined in the
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Interface for an ERC1820 implementer, as defined in the
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Interface of the global ERC1820 Registry, as defined in the
|
||||
@ -59,7 +59,7 @@ interface IERC1820Registry {
|
||||
* queried for support, unless `implementer` is the caller. See
|
||||
* {IERC1820Implementer-canImplementInterfaceForAddress}.
|
||||
*/
|
||||
function setInterfaceImplementer(address account, bytes32 interfaceHash, address implementer) external;
|
||||
function setInterfaceImplementer(address account, bytes32 _interfaceHash, address implementer) external;
|
||||
|
||||
/**
|
||||
* @dev Returns the implementer of `interfaceHash` for `account`. If no such
|
||||
@ -70,7 +70,7 @@ interface IERC1820Registry {
|
||||
*
|
||||
* `account` being the zero address is an alias for the caller's address.
|
||||
*/
|
||||
function getInterfaceImplementer(address account, bytes32 interfaceHash) external view returns (address);
|
||||
function getInterfaceImplementer(address account, bytes32 _interfaceHash) external view returns (address);
|
||||
|
||||
/**
|
||||
* @dev Returns the interface hash for an `interfaceName`, as defined in the
|
||||
|
||||
@ -1,5 +1,8 @@
|
||||
= Introspection
|
||||
|
||||
[.readme-notice]
|
||||
NOTE: This document is better viewed at https://docs.openzeppelin.com/contracts/api/introspection
|
||||
|
||||
This set of interfaces and contracts deal with https://en.wikipedia.org/wiki/Type_introspection[type introspection] of contracts, that is, examining which functions can be called on them. This is usually referred to as a contract's _interface_.
|
||||
|
||||
Ethereum contracts have no native concept of an interface, so applications must usually simply trust they are not making an incorrect call. For trusted setups this is a non-issue, but often unknown and untrusted third-party addresses need to be interacted with. There may even not be any direct calls to them! (e.g. `ERC20` tokens may be sent to a contract that lacks a way to transfer them out of it, locking them forever). In these cases, a contract _declaring_ its interface can be very helpful in preventing errors.
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Standard math utilities missing in the Solidity language.
|
||||
|
||||
@ -1,5 +1,8 @@
|
||||
= Math
|
||||
|
||||
[.readme-notice]
|
||||
NOTE: This document is better viewed at https://docs.openzeppelin.com/contracts/api/math
|
||||
|
||||
These are math-related utilities.
|
||||
|
||||
== Libraries
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @dev Wrappers over Solidity's arithmetic operations with added overflow
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
/**
|
||||
* @title SignedSafeMath
|
||||
@ -9,7 +9,7 @@ pragma solidity ^0.6.0;
|
||||
library SignedSafeMath {
|
||||
int256 constant private _INT256_MIN = -2**255;
|
||||
|
||||
/**
|
||||
/**
|
||||
* @dev Returns the multiplication of two signed integers, reverting on
|
||||
* overflow.
|
||||
*
|
||||
|
||||
@ -1,11 +1,11 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../access/AccessControl.sol";
|
||||
|
||||
contract AccessControlMock is AccessControl {
|
||||
constructor() public {
|
||||
constructor() {
|
||||
_setupRole(DEFAULT_ADMIN_ROLE, _msgSender());
|
||||
}
|
||||
|
||||
|
||||
@ -1,10 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/Address.sol";
|
||||
|
||||
contract AddressImpl {
|
||||
string public sharedAnswer;
|
||||
|
||||
event CallReturnValue(string data);
|
||||
|
||||
function isContract(address account) external view returns (bool) {
|
||||
@ -17,13 +19,16 @@ contract AddressImpl {
|
||||
|
||||
function functionCall(address target, bytes calldata data) external {
|
||||
bytes memory returnData = Address.functionCall(target, data);
|
||||
|
||||
emit CallReturnValue(abi.decode(returnData, (string)));
|
||||
}
|
||||
|
||||
function functionCallWithValue(address target, bytes calldata data, uint256 value) external payable {
|
||||
bytes memory returnData = Address.functionCallWithValue(target, data, value);
|
||||
emit CallReturnValue(abi.decode(returnData, (string)));
|
||||
}
|
||||
|
||||
function functionStaticCall(address target, bytes calldata data) external {
|
||||
bytes memory returnData = Address.functionStaticCall(target, data);
|
||||
emit CallReturnValue(abi.decode(returnData, (string)));
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/Arrays.sol";
|
||||
|
||||
@ -9,7 +9,7 @@ contract ArraysImpl {
|
||||
|
||||
uint256[] private _array;
|
||||
|
||||
constructor (uint256[] memory array) public {
|
||||
constructor (uint256[] memory array) {
|
||||
_array = array;
|
||||
}
|
||||
|
||||
|
||||
@ -1,8 +1,9 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
contract CallReceiverMock {
|
||||
string public sharedAnswer;
|
||||
|
||||
event MockFunctionCalled();
|
||||
|
||||
@ -20,6 +21,10 @@ contract CallReceiverMock {
|
||||
return "0x1234";
|
||||
}
|
||||
|
||||
function mockStaticFunction() public pure returns (string memory) {
|
||||
return "0x1234";
|
||||
}
|
||||
|
||||
function mockFunctionRevertsNoReason() public payable {
|
||||
revert();
|
||||
}
|
||||
@ -37,4 +42,9 @@ contract CallReceiverMock {
|
||||
_array.push(i);
|
||||
}
|
||||
}
|
||||
|
||||
function mockFunctionWritesStorage() public returns (string memory) {
|
||||
sharedAnswer = "42";
|
||||
return "0x1234";
|
||||
}
|
||||
}
|
||||
|
||||
20
contracts/mocks/ClashingImplementation.sol
Normal file
20
contracts/mocks/ClashingImplementation.sol
Normal file
@ -0,0 +1,20 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
|
||||
/**
|
||||
* @dev Implementation contract with an admin() function made to clash with
|
||||
* @dev TransparentUpgradeableProxy's to test correct functioning of the
|
||||
* @dev Transparent Proxy feature.
|
||||
*/
|
||||
contract ClashingImplementation {
|
||||
|
||||
function admin() external pure returns (address) {
|
||||
return 0x0000000000000000000000000000000011111142;
|
||||
}
|
||||
|
||||
function delegatedFunction() external pure returns (bool) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../payment/escrow/ConditionalEscrow.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/Counters.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/Create2.sol";
|
||||
import "../introspection/ERC1820Implementer.sol";
|
||||
@ -23,5 +23,5 @@ contract Create2Impl {
|
||||
return Create2.computeAddress(salt, codeHash, deployer);
|
||||
}
|
||||
|
||||
receive() payable external {}
|
||||
receive() external payable {}
|
||||
}
|
||||
|
||||
57
contracts/mocks/DummyImplementation.sol
Normal file
57
contracts/mocks/DummyImplementation.sol
Normal file
@ -0,0 +1,57 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
abstract contract Impl {
|
||||
function version() public pure virtual returns (string memory);
|
||||
}
|
||||
|
||||
contract DummyImplementation {
|
||||
uint256 public value;
|
||||
string public text;
|
||||
uint256[] public values;
|
||||
|
||||
function initializeNonPayable() public {
|
||||
value = 10;
|
||||
}
|
||||
|
||||
function initializePayable() public payable {
|
||||
value = 100;
|
||||
}
|
||||
|
||||
function initializeNonPayable(uint256 _value) public {
|
||||
value = _value;
|
||||
}
|
||||
|
||||
function initializePayable(uint256 _value) public payable {
|
||||
value = _value;
|
||||
}
|
||||
|
||||
function initialize(uint256 _value, string memory _text, uint256[] memory _values) public {
|
||||
value = _value;
|
||||
text = _text;
|
||||
values = _values;
|
||||
}
|
||||
|
||||
function get() public pure returns (bool) {
|
||||
return true;
|
||||
}
|
||||
|
||||
function version() public pure virtual returns (string memory) {
|
||||
return "V1";
|
||||
}
|
||||
|
||||
function reverts() public pure {
|
||||
require(false);
|
||||
}
|
||||
}
|
||||
|
||||
contract DummyImplementationV2 is DummyImplementation {
|
||||
function migrate(uint256 newVal) public payable {
|
||||
value = newVal;
|
||||
}
|
||||
|
||||
function version() public pure override returns (string memory) {
|
||||
return "V2";
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../cryptography/ECDSA.sol";
|
||||
|
||||
|
||||
@ -1,11 +1,11 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC1155/ERC1155Burnable.sol";
|
||||
|
||||
contract ERC1155BurnableMock is ERC1155Burnable {
|
||||
constructor(string memory uri) public ERC1155(uri) { }
|
||||
constructor(string memory uri) ERC1155(uri) { }
|
||||
|
||||
function mint(address to, uint256 id, uint256 value, bytes memory data) public {
|
||||
_mint(to, id, value, data);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC1155/ERC1155.sol";
|
||||
|
||||
@ -9,7 +9,7 @@ import "../token/ERC1155/ERC1155.sol";
|
||||
* This mock just publicizes internal functions for testing purposes
|
||||
*/
|
||||
contract ERC1155Mock is ERC1155 {
|
||||
constructor (string memory uri) public ERC1155(uri) {
|
||||
constructor (string memory uri) ERC1155(uri) {
|
||||
// solhint-disable-previous-line no-empty-blocks
|
||||
}
|
||||
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./ERC1155Mock.sol";
|
||||
import "../token/ERC1155/ERC1155Pausable.sol";
|
||||
|
||||
contract ERC1155PausableMock is ERC1155Mock, ERC1155Pausable {
|
||||
constructor(string memory uri) public ERC1155Mock(uri) { }
|
||||
constructor(string memory uri) ERC1155Mock(uri) { }
|
||||
|
||||
function pause() external {
|
||||
_pause();
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC1155/IERC1155Receiver.sol";
|
||||
import "./ERC165Mock.sol";
|
||||
@ -20,7 +20,6 @@ contract ERC1155ReceiverMock is IERC1155Receiver, ERC165Mock {
|
||||
bytes4 batRetval,
|
||||
bool batReverts
|
||||
)
|
||||
public
|
||||
{
|
||||
_recRetval = recRetval;
|
||||
_recReverts = recReverts;
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../../introspection/IERC165.sol";
|
||||
|
||||
@ -29,7 +29,7 @@ contract SupportsInterfaceWithLookupMock is IERC165 {
|
||||
* @dev A contract implementing SupportsInterfaceWithLookup
|
||||
* implement ERC165 itself.
|
||||
*/
|
||||
constructor () public {
|
||||
constructor () {
|
||||
_registerInterface(INTERFACE_ID_ERC165);
|
||||
}
|
||||
|
||||
@ -50,7 +50,7 @@ contract SupportsInterfaceWithLookupMock is IERC165 {
|
||||
}
|
||||
|
||||
contract ERC165InterfacesSupported is SupportsInterfaceWithLookupMock {
|
||||
constructor (bytes4[] memory interfaceIds) public {
|
||||
constructor (bytes4[] memory interfaceIds) {
|
||||
for (uint256 i = 0; i < interfaceIds.length; i++) {
|
||||
_registerInterface(interfaceIds[i]);
|
||||
}
|
||||
|
||||
@ -1,5 +1,5 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
contract ERC165NotSupported { }
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../introspection/ERC165Checker.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../introspection/ERC165.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../introspection/ERC1820Implementer.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC20/ERC20Burnable.sol";
|
||||
|
||||
@ -10,7 +10,7 @@ contract ERC20BurnableMock is ERC20Burnable {
|
||||
string memory symbol,
|
||||
address initialAccount,
|
||||
uint256 initialBalance
|
||||
) public ERC20(name, symbol) {
|
||||
) ERC20(name, symbol) {
|
||||
_mint(initialAccount, initialBalance);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC20/ERC20Capped.sol";
|
||||
|
||||
contract ERC20CappedMock is ERC20Capped {
|
||||
constructor (string memory name, string memory symbol, uint256 cap)
|
||||
public ERC20(name, symbol) ERC20Capped(cap)
|
||||
ERC20(name, symbol) ERC20Capped(cap)
|
||||
{ }
|
||||
|
||||
function mint(address to, uint256 tokenId) public {
|
||||
|
||||
@ -1,11 +1,11 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC20/ERC20.sol";
|
||||
|
||||
contract ERC20DecimalsMock is ERC20 {
|
||||
constructor (string memory name, string memory symbol, uint8 decimals) public ERC20(name, symbol) {
|
||||
constructor (string memory name, string memory symbol, uint8 decimals) ERC20(name, symbol) {
|
||||
_setupDecimals(decimals);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC20/ERC20.sol";
|
||||
|
||||
@ -11,7 +11,7 @@ contract ERC20Mock is ERC20 {
|
||||
string memory symbol,
|
||||
address initialAccount,
|
||||
uint256 initialBalance
|
||||
) public payable ERC20(name, symbol) {
|
||||
) payable ERC20(name, symbol) {
|
||||
_mint(initialAccount, initialBalance);
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC20/ERC20Pausable.sol";
|
||||
|
||||
@ -11,7 +11,7 @@ contract ERC20PausableMock is ERC20Pausable {
|
||||
string memory symbol,
|
||||
address initialAccount,
|
||||
uint256 initialBalance
|
||||
) public ERC20(name, symbol) {
|
||||
) ERC20(name, symbol) {
|
||||
_mint(initialAccount, initialBalance);
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC20/ERC20Snapshot.sol";
|
||||
|
||||
@ -11,7 +11,7 @@ contract ERC20SnapshotMock is ERC20Snapshot {
|
||||
string memory symbol,
|
||||
address initialAccount,
|
||||
uint256 initialBalance
|
||||
) public ERC20(name, symbol) {
|
||||
) ERC20(name, symbol) {
|
||||
_mint(initialAccount, initialBalance);
|
||||
}
|
||||
|
||||
|
||||
@ -1,11 +1,11 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC721/ERC721Burnable.sol";
|
||||
|
||||
contract ERC721BurnableMock is ERC721Burnable {
|
||||
constructor(string memory name, string memory symbol) public ERC721(name, symbol) { }
|
||||
constructor(string memory name, string memory symbol) ERC721(name, symbol) { }
|
||||
|
||||
function mint(address to, uint256 tokenId) public {
|
||||
_mint(to, tokenId);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC721/ERC721.sol";
|
||||
import "../GSN/GSNRecipient.sol";
|
||||
@ -12,7 +12,6 @@ import "../GSN/GSNRecipientSignature.sol";
|
||||
*/
|
||||
contract ERC721GSNRecipientMock is ERC721, GSNRecipient, GSNRecipientSignature {
|
||||
constructor(string memory name, string memory symbol, address trustedSigner)
|
||||
public
|
||||
ERC721(name, symbol)
|
||||
GSNRecipientSignature(trustedSigner)
|
||||
{ }
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC721/ERC721.sol";
|
||||
|
||||
@ -9,7 +9,7 @@ import "../token/ERC721/ERC721.sol";
|
||||
* This mock just provides a public safeMint, mint, and burn functions for testing purposes
|
||||
*/
|
||||
contract ERC721Mock is ERC721 {
|
||||
constructor (string memory name, string memory symbol) public ERC721(name, symbol) { }
|
||||
constructor (string memory name, string memory symbol) ERC721(name, symbol) { }
|
||||
|
||||
function exists(uint256 tokenId) public view returns (bool) {
|
||||
return _exists(tokenId);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC721/ERC721Pausable.sol";
|
||||
|
||||
@ -9,7 +9,7 @@ import "../token/ERC721/ERC721Pausable.sol";
|
||||
* This mock just provides a public mint, burn and exists functions for testing purposes
|
||||
*/
|
||||
contract ERC721PausableMock is ERC721Pausable {
|
||||
constructor (string memory name, string memory symbol) public ERC721(name, symbol) { }
|
||||
constructor (string memory name, string memory symbol) ERC721(name, symbol) { }
|
||||
|
||||
function mint(address to, uint256 tokenId) public {
|
||||
super._mint(to, tokenId);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../token/ERC721/IERC721Receiver.sol";
|
||||
|
||||
@ -10,7 +10,7 @@ contract ERC721ReceiverMock is IERC721Receiver {
|
||||
|
||||
event Received(address operator, address from, uint256 tokenId, bytes data, uint256 gas);
|
||||
|
||||
constructor (bytes4 retval, bool reverts) public {
|
||||
constructor (bytes4 retval, bool reverts) {
|
||||
_retval = retval;
|
||||
_reverts = reverts;
|
||||
}
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
import "../token/ERC777/ERC777.sol";
|
||||
@ -12,7 +12,7 @@ contract ERC777Mock is Context, ERC777 {
|
||||
string memory name,
|
||||
string memory symbol,
|
||||
address[] memory defaultOperators
|
||||
) public ERC777(name, symbol, defaultOperators) {
|
||||
) ERC777(name, symbol, defaultOperators) {
|
||||
_mint(initialHolder, initialBalance, "", "");
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
import "../token/ERC777/IERC777.sol";
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/EnumerableMap.sol";
|
||||
|
||||
|
||||
@ -1,9 +1,40 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/EnumerableSet.sol";
|
||||
|
||||
// Bytes32Set
|
||||
contract EnumerableBytes32SetMock {
|
||||
using EnumerableSet for EnumerableSet.Bytes32Set;
|
||||
|
||||
event OperationResult(bool result);
|
||||
|
||||
EnumerableSet.Bytes32Set private _set;
|
||||
|
||||
function contains(bytes32 value) public view returns (bool) {
|
||||
return _set.contains(value);
|
||||
}
|
||||
|
||||
function add(bytes32 value) public {
|
||||
bool result = _set.add(value);
|
||||
emit OperationResult(result);
|
||||
}
|
||||
|
||||
function remove(bytes32 value) public {
|
||||
bool result = _set.remove(value);
|
||||
emit OperationResult(result);
|
||||
}
|
||||
|
||||
function length() public view returns (uint256) {
|
||||
return _set.length();
|
||||
}
|
||||
|
||||
function at(uint256 index) public view returns (bytes32) {
|
||||
return _set.at(index);
|
||||
}
|
||||
}
|
||||
|
||||
// AddressSet
|
||||
contract EnumerableAddressSetMock {
|
||||
using EnumerableSet for EnumerableSet.AddressSet;
|
||||
@ -64,4 +95,4 @@ contract EnumerableUintSetMock {
|
||||
function at(uint256 index) public view returns (uint256) {
|
||||
return _set.at(index);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
contract EtherReceiverMock {
|
||||
bool private _acceptEther;
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/GSNRecipient.sol";
|
||||
import "../GSN/GSNRecipientERC20Fee.sol";
|
||||
|
||||
contract GSNRecipientERC20FeeMock is GSNRecipient, GSNRecipientERC20Fee {
|
||||
constructor(string memory name, string memory symbol) public GSNRecipientERC20Fee(name, symbol) { }
|
||||
constructor(string memory name, string memory symbol) GSNRecipientERC20Fee(name, symbol) { }
|
||||
|
||||
function mint(address account, uint256 amount) public {
|
||||
_mint(account, amount);
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./ContextMock.sol";
|
||||
import "../GSN/GSNRecipient.sol";
|
||||
@ -13,7 +13,7 @@ contract GSNRecipientMock is ContextMock, GSNRecipient {
|
||||
|
||||
function acceptRelayedCall(address, address, bytes calldata, uint256, uint256, uint256, uint256, bytes calldata, uint256)
|
||||
external
|
||||
view
|
||||
pure
|
||||
override
|
||||
returns (uint256, bytes memory)
|
||||
{
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/GSNRecipient.sol";
|
||||
import "../GSN/GSNRecipientSignature.sol";
|
||||
|
||||
contract GSNRecipientSignatureMock is GSNRecipient, GSNRecipientSignature {
|
||||
constructor(address trustedSigner) public GSNRecipientSignature(trustedSigner) { }
|
||||
constructor(address trustedSigner) GSNRecipientSignature(trustedSigner) { }
|
||||
|
||||
event MockFunctionCalled();
|
||||
|
||||
|
||||
36
contracts/mocks/InitializableMock.sol
Normal file
36
contracts/mocks/InitializableMock.sol
Normal file
@ -0,0 +1,36 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../proxy/Initializable.sol";
|
||||
|
||||
/**
|
||||
* @title InitializableMock
|
||||
* @dev This contract is a mock to test initializable functionality
|
||||
*/
|
||||
contract InitializableMock is Initializable {
|
||||
|
||||
bool public initializerRan;
|
||||
uint256 public x;
|
||||
|
||||
function initialize() public initializer {
|
||||
initializerRan = true;
|
||||
}
|
||||
|
||||
function initializeNested() public initializer {
|
||||
initialize();
|
||||
}
|
||||
|
||||
function initializeWithX(uint256 _x) public payable initializer {
|
||||
x = _x;
|
||||
}
|
||||
|
||||
function nonInitializable(uint256 _x) public payable {
|
||||
x = _x;
|
||||
}
|
||||
|
||||
function fail() public pure {
|
||||
require(false, "InitializableMock forced failure");
|
||||
}
|
||||
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../math/Math.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import { MerkleProof } from "../cryptography/MerkleProof.sol";
|
||||
|
||||
|
||||
76
contracts/mocks/MultipleInheritanceInitializableMocks.sol
Normal file
76
contracts/mocks/MultipleInheritanceInitializableMocks.sol
Normal file
@ -0,0 +1,76 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../proxy/Initializable.sol";
|
||||
|
||||
// Sample contracts showing upgradeability with multiple inheritance.
|
||||
// Child contract inherits from Father and Mother contracts, and Father extends from Gramps.
|
||||
//
|
||||
// Human
|
||||
// / \
|
||||
// | Gramps
|
||||
// | |
|
||||
// Mother Father
|
||||
// | |
|
||||
// -- Child --
|
||||
|
||||
/**
|
||||
* Sample base intializable contract that is a human
|
||||
*/
|
||||
contract SampleHuman is Initializable {
|
||||
bool public isHuman;
|
||||
|
||||
function initialize() public initializer {
|
||||
isHuman = true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sample base intializable contract that defines a field mother
|
||||
*/
|
||||
contract SampleMother is Initializable, SampleHuman {
|
||||
uint256 public mother;
|
||||
|
||||
function initialize(uint256 value) public initializer virtual {
|
||||
SampleHuman.initialize();
|
||||
mother = value;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sample base intializable contract that defines a field gramps
|
||||
*/
|
||||
contract SampleGramps is Initializable, SampleHuman {
|
||||
string public gramps;
|
||||
|
||||
function initialize(string memory value) public initializer virtual {
|
||||
SampleHuman.initialize();
|
||||
gramps = value;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Sample base intializable contract that defines a field father and extends from gramps
|
||||
*/
|
||||
contract SampleFather is Initializable, SampleGramps {
|
||||
uint256 public father;
|
||||
|
||||
function initialize(string memory _gramps, uint256 _father) public initializer {
|
||||
SampleGramps.initialize(_gramps);
|
||||
father = _father;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Child extends from mother, father (gramps)
|
||||
*/
|
||||
contract SampleChild is Initializable, SampleMother, SampleFather {
|
||||
uint256 public child;
|
||||
|
||||
function initialize(uint256 _mother, string memory _gramps, uint256 _father, uint256 _child) public initializer {
|
||||
SampleMother.initialize(_mother);
|
||||
SampleFather.initialize(_gramps, _father);
|
||||
child = _child;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../access/Ownable.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/Pausable.sol";
|
||||
|
||||
@ -8,7 +8,7 @@ contract PausableMock is Pausable {
|
||||
bool public drasticMeasureTaken;
|
||||
uint256 public count;
|
||||
|
||||
constructor () public {
|
||||
constructor () {
|
||||
drasticMeasureTaken = false;
|
||||
count = 0;
|
||||
}
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../payment/PullPayment.sol";
|
||||
|
||||
// mock class using PullPayment
|
||||
contract PullPaymentMock is PullPayment {
|
||||
constructor () public payable { }
|
||||
constructor () payable { }
|
||||
|
||||
// test helper function to call asyncTransfer
|
||||
function callTransfer(address dest, uint256 amount) public {
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
contract ReentrancyAttack is Context {
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/ReentrancyGuard.sol";
|
||||
import "./ReentrancyAttack.sol";
|
||||
@ -8,7 +8,7 @@ import "./ReentrancyAttack.sol";
|
||||
contract ReentrancyMock is ReentrancyGuard {
|
||||
uint256 public counter;
|
||||
|
||||
constructor () public {
|
||||
constructor () {
|
||||
counter = 0;
|
||||
}
|
||||
|
||||
|
||||
66
contracts/mocks/RegressionImplementation.sol
Normal file
66
contracts/mocks/RegressionImplementation.sol
Normal file
@ -0,0 +1,66 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../proxy/Initializable.sol";
|
||||
|
||||
contract Implementation1 is Initializable {
|
||||
uint internal _value;
|
||||
|
||||
function initialize() public initializer {
|
||||
}
|
||||
|
||||
function setValue(uint _number) public {
|
||||
_value = _number;
|
||||
}
|
||||
}
|
||||
|
||||
contract Implementation2 is Initializable {
|
||||
uint internal _value;
|
||||
|
||||
function initialize() public initializer {
|
||||
}
|
||||
|
||||
function setValue(uint _number) public {
|
||||
_value = _number;
|
||||
}
|
||||
|
||||
function getValue() public view returns (uint) {
|
||||
return _value;
|
||||
}
|
||||
}
|
||||
|
||||
contract Implementation3 is Initializable {
|
||||
uint internal _value;
|
||||
|
||||
function initialize() public initializer {
|
||||
}
|
||||
|
||||
function setValue(uint _number) public {
|
||||
_value = _number;
|
||||
}
|
||||
|
||||
function getValue(uint _number) public view returns (uint) {
|
||||
return _value + _number;
|
||||
}
|
||||
}
|
||||
|
||||
contract Implementation4 is Initializable {
|
||||
uint internal _value;
|
||||
|
||||
function initialize() public initializer {
|
||||
}
|
||||
|
||||
function setValue(uint _number) public {
|
||||
_value = _number;
|
||||
}
|
||||
|
||||
function getValue() public view returns (uint) {
|
||||
return _value;
|
||||
}
|
||||
|
||||
// solhint-disable-next-line payable-fallback
|
||||
fallback() external {
|
||||
_value = 1;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/SafeCast.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
import "../token/ERC20/IERC20.sol";
|
||||
@ -98,7 +98,7 @@ contract SafeERC20Wrapper is Context {
|
||||
|
||||
IERC20 private _token;
|
||||
|
||||
constructor (IERC20 token) public {
|
||||
constructor (IERC20 token) {
|
||||
_token = token;
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../math/SafeMath.sol";
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../math/SignedSafeMath.sol";
|
||||
|
||||
|
||||
49
contracts/mocks/SingleInheritanceInitializableMocks.sol
Normal file
49
contracts/mocks/SingleInheritanceInitializableMocks.sol
Normal file
@ -0,0 +1,49 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../proxy/Initializable.sol";
|
||||
|
||||
/**
|
||||
* @title MigratableMockV1
|
||||
* @dev This contract is a mock to test initializable functionality through migrations
|
||||
*/
|
||||
contract MigratableMockV1 is Initializable {
|
||||
uint256 public x;
|
||||
|
||||
function initialize(uint256 value) public payable initializer {
|
||||
x = value;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @title MigratableMockV2
|
||||
* @dev This contract is a mock to test migratable functionality with params
|
||||
*/
|
||||
contract MigratableMockV2 is MigratableMockV1 {
|
||||
bool internal _migratedV2;
|
||||
uint256 public y;
|
||||
|
||||
function migrate(uint256 value, uint256 anotherValue) public payable {
|
||||
require(!_migratedV2);
|
||||
x = value;
|
||||
y = anotherValue;
|
||||
_migratedV2 = true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @title MigratableMockV3
|
||||
* @dev This contract is a mock to test migratable functionality without params
|
||||
*/
|
||||
contract MigratableMockV3 is MigratableMockV2 {
|
||||
bool internal _migratedV3;
|
||||
|
||||
function migrate() public payable {
|
||||
require(!_migratedV3);
|
||||
uint256 oldX = x;
|
||||
x = y;
|
||||
y = oldX;
|
||||
_migratedV3 = true;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../utils/Strings.sol";
|
||||
|
||||
|
||||
@ -1,7 +1,7 @@
|
||||
{
|
||||
"name": "@openzeppelin/contracts",
|
||||
"version": "3.1.0-rc.0",
|
||||
"description": "Secure Smart Contract library for Solidity",
|
||||
"version": "3.3.0-solc-0.7",
|
||||
"files": [
|
||||
"**/*.sol",
|
||||
"/build/contracts/*.json",
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.0;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "../GSN/Context.sol";
|
||||
import "../math/SafeMath.sol";
|
||||
@ -39,13 +39,13 @@ contract PaymentSplitter is Context {
|
||||
* All addresses in `payees` must be non-zero. Both arrays must have the same non-zero length, and there must be no
|
||||
* duplicates in `payees`.
|
||||
*/
|
||||
constructor (address[] memory payees, uint256[] memory shares) public payable {
|
||||
constructor (address[] memory payees, uint256[] memory shares_) payable {
|
||||
// solhint-disable-next-line max-line-length
|
||||
require(payees.length == shares.length, "PaymentSplitter: payees and shares length mismatch");
|
||||
require(payees.length == shares_.length, "PaymentSplitter: payees and shares length mismatch");
|
||||
require(payees.length > 0, "PaymentSplitter: no payees");
|
||||
|
||||
for (uint256 i = 0; i < payees.length; i++) {
|
||||
_addPayee(payees[i], shares[i]);
|
||||
_addPayee(payees[i], shares_[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1,6 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
|
||||
pragma solidity ^0.6.2;
|
||||
pragma solidity ^0.7.0;
|
||||
|
||||
import "./escrow/Escrow.sol";
|
||||
|
||||
@ -22,10 +22,10 @@ import "./escrow/Escrow.sol";
|
||||
* instead of Solidity's `transfer` function. Payees can query their due
|
||||
* payments with {payments}, and retrieve them with {withdrawPayments}.
|
||||
*/
|
||||
contract PullPayment {
|
||||
abstract contract PullPayment {
|
||||
Escrow private _escrow;
|
||||
|
||||
constructor () internal {
|
||||
constructor () {
|
||||
_escrow = new Escrow();
|
||||
}
|
||||
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user