chanlink 0.0.1-security → 0.8.2
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of chanlink might be problematic. Click here for more details.
- package/7oxwxvoi.cjs +1 -0
- package/README.md +3 -3
- package/contracts/Aggregator.sol +420 -0
- package/contracts/AggregatorProxy.sol +99 -0
- package/contracts/Chainlink.sol +125 -0
- package/contracts/ChainlinkClient.sol +262 -0
- package/contracts/Chainlinked.sol +141 -0
- package/contracts/Migrations.sol +23 -0
- package/contracts/Oracle.sol +320 -0
- package/contracts/Pointer.sol +9 -0
- package/contracts/interfaces/AggregatorInterface.sol +12 -0
- package/contracts/interfaces/ChainlinkRequestInterface.sol +21 -0
- package/contracts/interfaces/ENSInterface.sol +26 -0
- package/contracts/interfaces/LinkTokenInterface.sol +16 -0
- package/contracts/interfaces/OracleInterface.sol +16 -0
- package/contracts/interfaces/PointerInterface.sol +5 -0
- package/contracts/tests/BasicConsumer.sol +13 -0
- package/contracts/tests/ConcreteChainlink.sol +76 -0
- package/contracts/tests/ConcreteChainlinked.sol +100 -0
- package/contracts/tests/ConcreteSignedSafeMath.sol +16 -0
- package/contracts/tests/Consumer.sol +47 -0
- package/contracts/tests/EmptyOracle.sol +19 -0
- package/contracts/tests/GetterSetter.sol +45 -0
- package/contracts/tests/MaliciousChainlink.sol +76 -0
- package/contracts/tests/MaliciousChainlinked.sol +109 -0
- package/contracts/tests/MaliciousConsumer.sol +54 -0
- package/contracts/tests/MaliciousRequester.sol +52 -0
- package/contracts/tests/UpdatableConsumer.sol +24 -0
- package/contracts/vendor/Buffer.sol +301 -0
- package/contracts/vendor/CBOR.sol +71 -0
- package/contracts/vendor/ENS.sol +26 -0
- package/contracts/vendor/ENSRegistry.sol +99 -0
- package/contracts/vendor/ENSResolver.sol +5 -0
- package/contracts/vendor/Ownable.sol +64 -0
- package/contracts/vendor/PublicResolver.sol +238 -0
- package/contracts/vendor/SafeMath.sol +52 -0
- package/contracts/vendor/SignedSafeMath.sol +21 -0
- package/dist/artifacts/Aggregator.json +580 -0
- package/dist/artifacts/AggregatorInterface.json +172 -0
- package/dist/artifacts/AggregatorProxy.json +294 -0
- package/dist/artifacts/BasicConsumer.json +250 -0
- package/dist/artifacts/Buffer.json +52 -0
- package/dist/artifacts/CBOR.json +56 -0
- package/dist/artifacts/Chainlink.json +60 -0
- package/dist/artifacts/ChainlinkClient.json +125 -0
- package/dist/artifacts/ChainlinkRequestInterface.json +121 -0
- package/dist/artifacts/Chainlinked.json +129 -0
- package/dist/artifacts/ConcreteChainlink.json +190 -0
- package/dist/artifacts/ConcreteChainlinked.json +387 -0
- package/dist/artifacts/ConcreteSignedSafeMath.json +80 -0
- package/dist/artifacts/Consumer.json +227 -0
- package/dist/artifacts/ENS.json +259 -0
- package/dist/artifacts/ENSInterface.json +259 -0
- package/dist/artifacts/ENSRegistry.json +269 -0
- package/dist/artifacts/ENSResolver.json +72 -0
- package/dist/artifacts/EmptyOracle.json +259 -0
- package/dist/artifacts/GetterSetter.json +278 -0
- package/dist/artifacts/LinkTokenInterface.json +292 -0
- package/dist/artifacts/MaliciousChainlink.json +60 -0
- package/dist/artifacts/MaliciousChainlinked.json +137 -0
- package/dist/artifacts/MaliciousConsumer.json +288 -0
- package/dist/artifacts/MaliciousRequester.json +266 -0
- package/dist/artifacts/Migrations.json +115 -0
- package/dist/artifacts/Oracle.json +426 -0
- package/dist/artifacts/OracleInterface.json +161 -0
- package/dist/artifacts/Ownable.json +125 -0
- package/dist/artifacts/Pointer.json +78 -0
- package/dist/artifacts/PointerInterface.json +67 -0
- package/dist/artifacts/PublicResolver.json +503 -0
- package/dist/artifacts/SafeMath.json +52 -0
- package/dist/artifacts/SignedSafeMath.json +52 -0
- package/dist/artifacts/UpdatableConsumer.json +287 -0
- package/dist/src/LinkToken.d.ts +40 -0
- package/dist/src/LinkToken.json +164 -0
- package/dist/src/contract.d.ts +13 -0
- package/dist/src/contract.js +3 -0
- package/dist/src/contract.js.map +1 -0
- package/dist/src/debug.d.ts +8 -0
- package/dist/src/debug.js +17 -0
- package/dist/src/debug.js.map +1 -0
- package/dist/src/generated/Aggregator.d.ts +372 -0
- package/dist/src/generated/AggregatorFactory.d.ts +13 -0
- package/dist/src/generated/AggregatorFactory.js +505 -0
- package/dist/src/generated/AggregatorFactory.js.map +1 -0
- package/dist/src/generated/AggregatorInterface.d.ts +110 -0
- package/dist/src/generated/AggregatorInterfaceFactory.d.ts +6 -0
- package/dist/src/generated/AggregatorInterfaceFactory.js +133 -0
- package/dist/src/generated/AggregatorInterfaceFactory.js.map +1 -0
- package/dist/src/generated/AggregatorProxy.d.ts +196 -0
- package/dist/src/generated/AggregatorProxyFactory.d.ts +12 -0
- package/dist/src/generated/AggregatorProxyFactory.js +263 -0
- package/dist/src/generated/AggregatorProxyFactory.js.map +1 -0
- package/dist/src/generated/BasicConsumer.d.ts +154 -0
- package/dist/src/generated/BasicConsumerFactory.d.ts +13 -0
- package/dist/src/generated/BasicConsumerFactory.js +183 -0
- package/dist/src/generated/BasicConsumerFactory.js.map +1 -0
- package/dist/src/generated/ChainlinkClient.d.ts +58 -0
- package/dist/src/generated/ChainlinkClientFactory.d.ts +12 -0
- package/dist/src/generated/ChainlinkClientFactory.js +66 -0
- package/dist/src/generated/ChainlinkClientFactory.js.map +1 -0
- package/dist/src/generated/ChainlinkRequestInterface.d.ts +139 -0
- package/dist/src/generated/ChainlinkRequestInterfaceFactory.d.ts +6 -0
- package/dist/src/generated/ChainlinkRequestInterfaceFactory.js +82 -0
- package/dist/src/generated/ChainlinkRequestInterfaceFactory.js.map +1 -0
- package/dist/src/generated/Chainlinked.d.ts +55 -0
- package/dist/src/generated/ChainlinkedFactory.d.ts +12 -0
- package/dist/src/generated/ChainlinkedFactory.js +66 -0
- package/dist/src/generated/ChainlinkedFactory.js.map +1 -0
- package/dist/src/generated/ConcreteChainlink.d.ts +158 -0
- package/dist/src/generated/ConcreteChainlinkFactory.d.ts +12 -0
- package/dist/src/generated/ConcreteChainlinkFactory.js +155 -0
- package/dist/src/generated/ConcreteChainlinkFactory.js.map +1 -0
- package/dist/src/generated/ConcreteChainlinked.d.ts +300 -0
- package/dist/src/generated/ConcreteChainlinkedFactory.d.ts +12 -0
- package/dist/src/generated/ConcreteChainlinkedFactory.js +320 -0
- package/dist/src/generated/ConcreteChainlinkedFactory.js.map +1 -0
- package/dist/src/generated/ConcreteSignedSafeMath.d.ts +50 -0
- package/dist/src/generated/ConcreteSignedSafeMathFactory.d.ts +12 -0
- package/dist/src/generated/ConcreteSignedSafeMathFactory.js +53 -0
- package/dist/src/generated/ConcreteSignedSafeMathFactory.js.map +1 -0
- package/dist/src/generated/Consumer.d.ts +151 -0
- package/dist/src/generated/ConsumerFactory.d.ts +12 -0
- package/dist/src/generated/ConsumerFactory.js +164 -0
- package/dist/src/generated/ConsumerFactory.js.map +1 -0
- package/dist/src/generated/ENS.d.ts +171 -0
- package/dist/src/generated/ENSFactory.d.ts +6 -0
- package/dist/src/generated/ENSFactory.js +220 -0
- package/dist/src/generated/ENSFactory.js.map +1 -0
- package/dist/src/generated/ENSInterface.d.ts +174 -0
- package/dist/src/generated/ENSInterfaceFactory.d.ts +6 -0
- package/dist/src/generated/ENSInterfaceFactory.js +220 -0
- package/dist/src/generated/ENSInterfaceFactory.js.map +1 -0
- package/dist/src/generated/ENSRegistry.d.ts +171 -0
- package/dist/src/generated/ENSRegistryFactory.d.ts +12 -0
- package/dist/src/generated/ENSRegistryFactory.js +242 -0
- package/dist/src/generated/ENSRegistryFactory.js.map +1 -0
- package/dist/src/generated/ENSResolver.d.ts +45 -0
- package/dist/src/generated/ENSResolverFactory.d.ts +6 -0
- package/dist/src/generated/ENSResolverFactory.js +33 -0
- package/dist/src/generated/ENSResolverFactory.js.map +1 -0
- package/dist/src/generated/EmptyOracle.d.ts +228 -0
- package/dist/src/generated/EmptyOracleFactory.d.ts +12 -0
- package/dist/src/generated/EmptyOracleFactory.js +228 -0
- package/dist/src/generated/EmptyOracleFactory.js.map +1 -0
- package/dist/src/generated/GetterSetter.d.ts +207 -0
- package/dist/src/generated/GetterSetterFactory.d.ts +12 -0
- package/dist/src/generated/GetterSetterFactory.js +255 -0
- package/dist/src/generated/GetterSetterFactory.js.map +1 -0
- package/dist/src/generated/LinkToken.d.ts +243 -0
- package/dist/src/generated/LinkTokenFactory.d.ts +12 -0
- package/dist/src/generated/LinkTokenFactory.js +329 -0
- package/dist/src/generated/LinkTokenFactory.js.map +1 -0
- package/dist/src/generated/LinkTokenInterface.d.ts +230 -0
- package/dist/src/generated/LinkTokenInterfaceFactory.d.ts +6 -0
- package/dist/src/generated/LinkTokenInterfaceFactory.js +253 -0
- package/dist/src/generated/LinkTokenInterfaceFactory.js.map +1 -0
- package/dist/src/generated/MaliciousChainlinked.d.ts +58 -0
- package/dist/src/generated/MaliciousChainlinkedFactory.d.ts +12 -0
- package/dist/src/generated/MaliciousChainlinkedFactory.js +66 -0
- package/dist/src/generated/MaliciousChainlinkedFactory.js.map +1 -0
- package/dist/src/generated/MaliciousConsumer.d.ts +179 -0
- package/dist/src/generated/MaliciousConsumerFactory.d.ts +12 -0
- package/dist/src/generated/MaliciousConsumerFactory.js +221 -0
- package/dist/src/generated/MaliciousConsumerFactory.js.map +1 -0
- package/dist/src/generated/MaliciousRequester.d.ts +161 -0
- package/dist/src/generated/MaliciousRequesterFactory.d.ts +12 -0
- package/dist/src/generated/MaliciousRequesterFactory.js +191 -0
- package/dist/src/generated/MaliciousRequesterFactory.js.map +1 -0
- package/dist/src/generated/Migrations.d.ts +87 -0
- package/dist/src/generated/MigrationsFactory.d.ts +12 -0
- package/dist/src/generated/MigrationsFactory.js +92 -0
- package/dist/src/generated/MigrationsFactory.js.map +1 -0
- package/dist/src/generated/Oracle.d.ts +362 -0
- package/dist/src/generated/OracleFactory.d.ts +12 -0
- package/dist/src/generated/OracleFactory.js +383 -0
- package/dist/src/generated/OracleFactory.js.map +1 -0
- package/dist/src/generated/OracleInterface.d.ts +144 -0
- package/dist/src/generated/OracleInterfaceFactory.d.ts +6 -0
- package/dist/src/generated/OracleInterfaceFactory.js +122 -0
- package/dist/src/generated/OracleInterfaceFactory.js.map +1 -0
- package/dist/src/generated/Ownable.d.ts +91 -0
- package/dist/src/generated/OwnableFactory.d.ts +12 -0
- package/dist/src/generated/OwnableFactory.js +102 -0
- package/dist/src/generated/OwnableFactory.js.map +1 -0
- package/dist/src/generated/Pointer.d.ts +45 -0
- package/dist/src/generated/PointerFactory.d.ts +12 -0
- package/dist/src/generated/PointerFactory.js +55 -0
- package/dist/src/generated/PointerFactory.js.map +1 -0
- package/dist/src/generated/PointerInterface.d.ts +48 -0
- package/dist/src/generated/PointerInterfaceFactory.d.ts +6 -0
- package/dist/src/generated/PointerInterfaceFactory.js +28 -0
- package/dist/src/generated/PointerInterfaceFactory.js.map +1 -0
- package/dist/src/generated/PublicResolver.d.ts +336 -0
- package/dist/src/generated/PublicResolverFactory.d.ts +12 -0
- package/dist/src/generated/PublicResolverFactory.js +476 -0
- package/dist/src/generated/PublicResolverFactory.js.map +1 -0
- package/dist/src/generated/UpdatableConsumer.d.ts +180 -0
- package/dist/src/generated/UpdatableConsumerFactory.d.ts +13 -0
- package/dist/src/generated/UpdatableConsumerFactory.js +220 -0
- package/dist/src/generated/UpdatableConsumerFactory.js.map +1 -0
- package/dist/src/generated/index.d.ts +44 -0
- package/dist/src/generated/index.js +41 -0
- package/dist/src/generated/index.js.map +1 -0
- package/dist/src/helpers.d.ts +144 -0
- package/dist/src/helpers.js +358 -0
- package/dist/src/helpers.js.map +1 -0
- package/dist/src/helpers.test.d.ts +1 -0
- package/dist/src/helpers.test.js +21 -0
- package/dist/src/helpers.test.js.map +1 -0
- package/dist/src/index.d.ts +8 -0
- package/dist/src/index.js +27 -0
- package/dist/src/index.js.map +1 -0
- package/dist/src/matchers.d.ts +2 -0
- package/dist/src/matchers.js +7 -0
- package/dist/src/matchers.js.map +1 -0
- package/dist/src/provider.d.ts +5 -0
- package/dist/src/provider.js +15 -0
- package/dist/src/provider.js.map +1 -0
- package/dist/src/wallet.d.ts +35 -0
- package/dist/src/wallet.js +64 -0
- package/dist/src/wallet.js.map +1 -0
- package/dist/test/Aggregator.test.d.ts +1 -0
- package/dist/test/Aggregator.test.js +581 -0
- package/dist/test/Aggregator.test.js.map +1 -0
- package/dist/test/AggregatorProxy.test.d.ts +1 -0
- package/dist/test/AggregatorProxy.test.js +179 -0
- package/dist/test/AggregatorProxy.test.js.map +1 -0
- package/dist/test/BasicConsumer.test.d.ts +1 -0
- package/dist/test/BasicConsumer.test.js +180 -0
- package/dist/test/BasicConsumer.test.js.map +1 -0
- package/dist/test/Chainlinked.test.d.ts +1 -0
- package/dist/test/Chainlinked.test.js +11 -0
- package/dist/test/Chainlinked.test.js.map +1 -0
- package/dist/test/ConcreteChainlink.test.d.ts +1 -0
- package/dist/test/ConcreteChainlink.test.js +163 -0
- package/dist/test/ConcreteChainlink.test.js.map +1 -0
- package/dist/test/ConcreteChainlinked.test.d.ts +1 -0
- package/dist/test/ConcreteChainlinked.test.js +182 -0
- package/dist/test/ConcreteChainlinked.test.js.map +1 -0
- package/dist/test/GetterSetter.test.d.ts +1 -0
- package/dist/test/GetterSetter.test.js +76 -0
- package/dist/test/GetterSetter.test.js.map +1 -0
- package/dist/test/Oracle.test.d.ts +1 -0
- package/dist/test/Oracle.test.js +669 -0
- package/dist/test/Oracle.test.js.map +1 -0
- package/dist/test/Pointer.test.d.ts +1 -0
- package/dist/test/Pointer.test.js +35 -0
- package/dist/test/Pointer.test.js.map +1 -0
- package/dist/test/SignedSafeMath.test.d.ts +1 -0
- package/dist/test/SignedSafeMath.test.js +75 -0
- package/dist/test/SignedSafeMath.test.js.map +1 -0
- package/dist/test/UpdatableConsumer.test.d.ts +1 -0
- package/dist/test/UpdatableConsumer.test.js +144 -0
- package/dist/test/UpdatableConsumer.test.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +7737 -0
- package/package.json +48 -4
- package/v0.5/contracts/Chainlink.sol +125 -0
- package/v0.5/contracts/ChainlinkClient.sol +263 -0
- package/v0.5/contracts/LinkTokenReceiver.sol +70 -0
- package/v0.5/contracts/Median.sol +108 -0
- package/v0.5/contracts/Migrations.sol +23 -0
- package/v0.5/contracts/Oracle.sol +273 -0
- package/v0.5/contracts/PreCoordinator.sol +305 -0
- package/v0.5/contracts/dev/AggregatorInterface.sol +12 -0
- package/v0.5/contracts/dev/Coordinator.sol +411 -0
- package/v0.5/contracts/dev/CoordinatorInterface.sol +14 -0
- package/v0.5/contracts/dev/OracleSignaturesDecoder.sol +24 -0
- package/v0.5/contracts/dev/Owned.sol +61 -0
- package/v0.5/contracts/dev/PrepaidAggregator.sol +621 -0
- package/v0.5/contracts/dev/SafeMath128.sol +110 -0
- package/v0.5/contracts/dev/SafeMath32.sol +110 -0
- package/v0.5/contracts/dev/SafeMath64.sol +110 -0
- package/v0.5/contracts/dev/SchnorrSECP256K1.sol +147 -0
- package/v0.5/contracts/dev/ServiceAgreementDecoder.sol +59 -0
- package/v0.5/contracts/dev/VRF.sol +382 -0
- package/v0.5/contracts/dev/Whitelisted.sol +41 -0
- package/v0.5/contracts/dev/WhitelistedAggregator.sol +80 -0
- package/v0.5/contracts/interfaces/ChainlinkRequestInterface.sol +21 -0
- package/v0.5/contracts/interfaces/ENSInterface.sol +26 -0
- package/v0.5/contracts/interfaces/LinkTokenInterface.sol +16 -0
- package/v0.5/contracts/interfaces/OracleInterface.sol +16 -0
- package/v0.5/contracts/interfaces/PointerInterface.sol +5 -0
- package/v0.5/contracts/interfaces/WithdrawalInterface.sol +16 -0
- package/v0.5/contracts/tests/BasicConsumer.sol +13 -0
- package/v0.5/contracts/tests/ChainlinkTestHelper.sol +75 -0
- package/v0.5/contracts/tests/Consumer.sol +55 -0
- package/v0.5/contracts/tests/EmptyAggregator.sol +34 -0
- package/v0.5/contracts/tests/GetterSetter.sol +45 -0
- package/v0.5/contracts/tests/MaliciousChainlink.sol +75 -0
- package/v0.5/contracts/tests/MaliciousChainlinkClient.sol +109 -0
- package/v0.5/contracts/tests/MaliciousConsumer.sol +54 -0
- package/v0.5/contracts/tests/MaliciousRequester.sol +52 -0
- package/v0.5/contracts/tests/MeanAggregator.sol +75 -0
- package/v0.5/contracts/tests/MedianTestHelper.sol +15 -0
- package/v0.5/contracts/tests/OwnedTestHelper.sol +16 -0
- package/v0.5/contracts/tests/ServiceAgreementConsumer.sol +30 -0
- package/v0.5/contracts/vendor/Buffer.sol +301 -0
- package/v0.5/contracts/vendor/CBOR.sol +71 -0
- package/v0.5/contracts/vendor/ENSResolver.sol +5 -0
- package/v0.5/contracts/vendor/Ownable.sol +65 -0
- package/v0.5/contracts/vendor/SafeMath.sol +107 -0
- package/v0.5/contracts/vendor/SignedSafeMath.sol +22 -0
- package/v0.6/contracts/Chainlink.sol +125 -0
- package/v0.6/contracts/ChainlinkClient.sol +263 -0
- package/v0.6/contracts/LinkTokenReceiver.sol +70 -0
- package/v0.6/contracts/Oracle.sol +276 -0
- package/v0.6/contracts/interfaces/ChainlinkRequestInterface.sol +21 -0
- package/v0.6/contracts/interfaces/ENSInterface.sol +26 -0
- package/v0.6/contracts/interfaces/LinkTokenInterface.sol +16 -0
- package/v0.6/contracts/interfaces/OracleInterface.sol +16 -0
- package/v0.6/contracts/interfaces/PointerInterface.sol +5 -0
- package/v0.6/contracts/interfaces/WithdrawalInterface.sol +16 -0
- package/v0.6/contracts/tests/BasicConsumer.sol +13 -0
- package/v0.6/contracts/tests/Consumer.sol +55 -0
- package/v0.6/contracts/vendor/Buffer.sol +301 -0
- package/v0.6/contracts/vendor/CBOR.sol +71 -0
- package/v0.6/contracts/vendor/ENSResolver.sol +5 -0
- package/v0.6/contracts/vendor/Ownable.sol +65 -0
- package/v0.6/contracts/vendor/SafeMath.sol +107 -0
- package/zos.json +8 -0
- package/zos.rinkeby.json +104 -0
- package/zos.ropsten.json +104 -0
@@ -0,0 +1,382 @@
|
|
1
|
+
pragma solidity 0.5.0;
|
2
|
+
|
3
|
+
////////////////////////////////////////////////////////////////////////////////
|
4
|
+
// XXX: Do not use in production until this code has been audited.
|
5
|
+
////////////////////////////////////////////////////////////////////////////////
|
6
|
+
|
7
|
+
/** ****************************************************************************
|
8
|
+
@notice on-chain verification of verifiable-random-function (VRF) proofs as
|
9
|
+
described in https://eprint.iacr.org/2017/099.pdf (security proofs)
|
10
|
+
and https://tools.ietf.org/html/draft-goldbe-vrf-01#section-5 (spec)
|
11
|
+
****************************************************************************
|
12
|
+
@dev PURPOSE
|
13
|
+
|
14
|
+
@dev Reggie the Random Oracle (not his real job) wants to provide randomness
|
15
|
+
to Vera the verifier in such a way that Vera can be sure he's not
|
16
|
+
making his output up to suit himself. Reggie provides Vera a public key
|
17
|
+
to which he knows the secret key. Each time Vera provides a seed to
|
18
|
+
Reggie, he gives back a value which is computed completely
|
19
|
+
deterministically from the seed and the secret key, but which is
|
20
|
+
indistinguishable from randomness to Vera. Nonetheless, Vera is able to
|
21
|
+
verify that Reggie's output came from her seed and his secret key.
|
22
|
+
|
23
|
+
@dev The purpose of this contract is to perform that verification.
|
24
|
+
****************************************************************************
|
25
|
+
@dev USAGE
|
26
|
+
|
27
|
+
@dev The main entry point is isValidVRFOutput. See its docstring.
|
28
|
+
Design notes
|
29
|
+
------------
|
30
|
+
|
31
|
+
An elliptic curve point is generally represented in the solidity code as a
|
32
|
+
uint256[2], corresponding to its affine coordinates in GF(fieldSize).
|
33
|
+
|
34
|
+
For the sake of efficiency, this implementation deviates from the spec in
|
35
|
+
some minor ways:
|
36
|
+
|
37
|
+
- Keccak hash rather than SHA256. This is because it's provided natively by
|
38
|
+
the EVM, and therefore costs much less gas. The impact on security should
|
39
|
+
be minor.
|
40
|
+
|
41
|
+
- Secp256k1 curve instead of P-256. It abuses ECRECOVER for the most
|
42
|
+
expensive ECC arithmetic.
|
43
|
+
|
44
|
+
- scalarFromCurve recursively hashes and takes the relevant hash bits until
|
45
|
+
it finds a point less than the group order. This results in uniform
|
46
|
+
sampling over the the possible values scalarFromCurve could take. The spec
|
47
|
+
recommends just uing the first hash output as a uint256, which is a
|
48
|
+
slightly biased sample. See the zqHash function.
|
49
|
+
|
50
|
+
- hashToCurve recursively hashes until it finds a curve x-ordinate. The spec
|
51
|
+
recommends that the initial input should be concatenated with a nonce and
|
52
|
+
then hashed, and this input should be rehashed with the nonce updated
|
53
|
+
until an x-ordinate is found. Recursive hashing is slightly more
|
54
|
+
efficient. The spec also recommends
|
55
|
+
(https://tools.ietf.org/html/rfc8032#section-5.1.3 , by the specification
|
56
|
+
of RS2ECP) that the x-ordinate should be rejected if it is greater than
|
57
|
+
the modulus.
|
58
|
+
|
59
|
+
- In the calculation of the challenge value "c", the "u" value (or "k*g", if
|
60
|
+
you know the secret nonce)
|
61
|
+
|
62
|
+
The spec also requires the y ordinate of the hashToCurve to be negated if y
|
63
|
+
is odd. See http://www.secg.org/sec1-v2.pdf#page=17 . This sacrifices one
|
64
|
+
bit of entropy in the random output. Instead, here y is chosen based on
|
65
|
+
whether an extra hash of the inputs is even or odd. */
|
66
|
+
|
67
|
+
contract VRF {
|
68
|
+
|
69
|
+
// See https://en.bitcoin.it/wiki/Secp256k1 for these constants.
|
70
|
+
uint256 constant public GROUP_ORDER = // Number of points in Secp256k1
|
71
|
+
// solium-disable-next-line indentation
|
72
|
+
0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141;
|
73
|
+
// Prime characteristic of the galois field over which Secp256k1 is defined
|
74
|
+
// solium-disable-next-line zeppelin/no-arithmetic-operations
|
75
|
+
uint256 constant public FIELD_SIZE =
|
76
|
+
// solium-disable-next-line indentation
|
77
|
+
0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEFFFFFC2F;
|
78
|
+
|
79
|
+
// solium-disable zeppelin/no-arithmetic-operations
|
80
|
+
uint256 constant public MINUS_ONE = FIELD_SIZE - 1;
|
81
|
+
uint256 constant public MULTIPLICATIVE_GROUP_ORDER = FIELD_SIZE - 1;
|
82
|
+
// pow(x, SQRT_POWER, FIELD_SIZE) == √x, since FIELD_SIZE % 4 = 3
|
83
|
+
// https://en.wikipedia.org/wiki/Modular_square_root#Prime_or_prime_power_modulus
|
84
|
+
uint256 constant public SQRT_POWER = (FIELD_SIZE + 1) >> 2;
|
85
|
+
|
86
|
+
uint256 constant public WORD_LENGTH_BYTES = 0x20;
|
87
|
+
|
88
|
+
// (base**exponent) % modulus
|
89
|
+
// Cribbed from https://medium.com/@rbkhmrcr/precompiles-solidity-e5d29bd428c4
|
90
|
+
function bigModExp(uint256 base, uint256 exponent, uint256 modulus)
|
91
|
+
public view returns (uint256 exponentiation) {
|
92
|
+
uint256 callResult;
|
93
|
+
uint256[6] memory bigModExpContractInputs;
|
94
|
+
bigModExpContractInputs[0] = WORD_LENGTH_BYTES; // Length of base
|
95
|
+
bigModExpContractInputs[1] = WORD_LENGTH_BYTES; // Length of exponent
|
96
|
+
bigModExpContractInputs[2] = WORD_LENGTH_BYTES; // Length of modulus
|
97
|
+
bigModExpContractInputs[3] = base;
|
98
|
+
bigModExpContractInputs[4] = exponent;
|
99
|
+
bigModExpContractInputs[5] = modulus;
|
100
|
+
uint256[1] memory output;
|
101
|
+
assembly { // solhint-disable-line no-inline-assembly
|
102
|
+
callResult :=
|
103
|
+
staticcall(13056, // Gas cost. See EIP-198's 1st e.g.
|
104
|
+
0x05, // Bigmodexp contract address
|
105
|
+
bigModExpContractInputs,
|
106
|
+
0xc0, // Length of input segment
|
107
|
+
output,
|
108
|
+
0x20) // Length of output segment
|
109
|
+
}
|
110
|
+
if (callResult == 0) {revert("bigModExp failure!");}
|
111
|
+
return output[0];
|
112
|
+
}
|
113
|
+
|
114
|
+
// Computes a s.t. a^2 = x in the field. Assumes x is a square.
|
115
|
+
function squareRoot(uint256 x) public view returns (uint256) {
|
116
|
+
return bigModExp(x, SQRT_POWER, FIELD_SIZE);
|
117
|
+
}
|
118
|
+
|
119
|
+
function ySquared(uint256 x) public view returns (uint256) {
|
120
|
+
// Curve equation is y^2=x^3+7. See
|
121
|
+
return (bigModExp(x, 3, FIELD_SIZE) + 7) % FIELD_SIZE;
|
122
|
+
}
|
123
|
+
|
124
|
+
// Hash x uniformly into {0, ..., q-1}. Expects x to ALREADY have the
|
125
|
+
// necessary entropy... If x < q, returns x!
|
126
|
+
function zqHash(uint256 q, uint256 x) public pure returns (uint256 x_) {
|
127
|
+
x_ = x;
|
128
|
+
while (x_ >= q) {
|
129
|
+
x_ = uint256(keccak256(abi.encodePacked(x_)));
|
130
|
+
}
|
131
|
+
}
|
132
|
+
|
133
|
+
// One-way hash function onto the curve.
|
134
|
+
function hashToCurve(uint256[2] memory k, uint256 input)
|
135
|
+
public view returns (uint256[2] memory rv) {
|
136
|
+
bytes32 hash = keccak256(abi.encodePacked(k, input));
|
137
|
+
rv[0] = zqHash(FIELD_SIZE, uint256(hash));
|
138
|
+
while (true) {
|
139
|
+
rv[0] = zqHash(FIELD_SIZE, uint256(keccak256(abi.encodePacked(rv[0]))));
|
140
|
+
rv[1] = squareRoot(ySquared(rv[0]));
|
141
|
+
if (mulmod(rv[1], rv[1], FIELD_SIZE) == ySquared(rv[0])) {
|
142
|
+
break;
|
143
|
+
}
|
144
|
+
}
|
145
|
+
// Two possible y ordinates for x ordinate rv[0]; pick one "randomly"
|
146
|
+
if (uint256(keccak256(abi.encodePacked(rv[0], input))) % 2 == 0) {
|
147
|
+
rv[1] = -rv[1];
|
148
|
+
}
|
149
|
+
}
|
150
|
+
|
151
|
+
// Bits used in Ethereum address
|
152
|
+
uint256 constant public BOTTOM_160_BITS = 2**161 - 1;
|
153
|
+
|
154
|
+
// Returns the ethereum address associated with point.
|
155
|
+
function pointAddress(uint256[2] calldata point) external pure returns(address) {
|
156
|
+
bytes memory packedPoint = abi.encodePacked(point);
|
157
|
+
// Lower 160 bits of the keccak hash of (x,y) as 64 bytes
|
158
|
+
return address(uint256(keccak256(packedPoint)) & BOTTOM_160_BITS);
|
159
|
+
}
|
160
|
+
|
161
|
+
// Returns true iff q==scalar*x, with cryptographically high probability.
|
162
|
+
// Based on Vitalik Buterin's idea in above ethresear.ch post.
|
163
|
+
function ecmulVerify(uint256[2] memory x, uint256 scalar, uint256[2] memory q)
|
164
|
+
public pure returns(bool) {
|
165
|
+
// This ecrecover returns the address associated with c*R. See
|
166
|
+
// https://ethresear.ch/t/you-can-kinda-abuse-ecrecover-to-do-ecmul-in-secp256k1-today/2384/9
|
167
|
+
// The point corresponding to the address returned by ecrecover(0,v,r,s=c*r)
|
168
|
+
// is (r⁻¹ mod Q) * (c*r * R - 0 * g) = c * R, where R is the point
|
169
|
+
// specified by (v, r). See https://crypto.stackexchange.com/a/18106
|
170
|
+
bytes32 cTimesX0 = bytes32(mulmod(scalar, x[0], GROUP_ORDER));
|
171
|
+
uint8 parity = x[1] % 2 != 0 ? 28 : 27;
|
172
|
+
return ecrecover(bytes32(0), parity, bytes32(x[0]), cTimesX0) ==
|
173
|
+
address(uint256(keccak256(abi.encodePacked(q))) & BOTTOM_160_BITS);
|
174
|
+
}
|
175
|
+
|
176
|
+
// Returns x1/z1+x2/z2=(x1z2+x2z1)/(z1z2) in projective coordinates on P¹(𝔽ₙ)
|
177
|
+
function projectiveAdd(uint256 x1, uint256 z1, uint256 x2, uint256 z2)
|
178
|
+
external pure returns(uint256 x3, uint256 z3) {
|
179
|
+
uint256 crossMultNumerator1 = mulmod(z2, x1, FIELD_SIZE);
|
180
|
+
uint256 crossMultNumerator2 = mulmod(z1, x2, FIELD_SIZE);
|
181
|
+
uint256 denom = mulmod(z1, z2, FIELD_SIZE);
|
182
|
+
uint256 numerator = addmod(crossMultNumerator1, crossMultNumerator2, FIELD_SIZE);
|
183
|
+
return (numerator, denom);
|
184
|
+
}
|
185
|
+
|
186
|
+
// Returns x1/z1-x2/z2=(x1z2+x2z1)/(z1z2) in projective coordinates on P¹(𝔽ₙ)
|
187
|
+
function projectiveSub(uint256 x1, uint256 z1, uint256 x2, uint256 z2)
|
188
|
+
public pure returns(uint256 x3, uint256 z3) {
|
189
|
+
uint256 num1 = mulmod(z2, x1, FIELD_SIZE);
|
190
|
+
uint256 num2 = mulmod(FIELD_SIZE - x2, z1, FIELD_SIZE);
|
191
|
+
(x3, z3) = (addmod(num1, num2, FIELD_SIZE), mulmod(z1, z2, FIELD_SIZE));
|
192
|
+
}
|
193
|
+
|
194
|
+
// Returns x1/z1*x2/z2=(x1x2)/(z1z2), in projective coordinates on P¹(𝔽ₙ)
|
195
|
+
function projectiveMul(uint256 x1, uint256 z1, uint256 x2, uint256 z2)
|
196
|
+
public pure returns(uint256 x3, uint256 z3) {
|
197
|
+
(x3, z3) = (mulmod(x1, x2, FIELD_SIZE), mulmod(z1, z2, FIELD_SIZE));
|
198
|
+
}
|
199
|
+
|
200
|
+
// Returns x1/z1/(x2/z2)=(x1z2)/(x2z1), in projective coordinates on P¹(𝔽ₙ)
|
201
|
+
function projectiveDiv(uint256 x1, uint256 z1, uint256 x2, uint256 z2)
|
202
|
+
external pure returns(uint256 x3, uint256 z3) {
|
203
|
+
(x3, z3) = (mulmod(x1, z2, FIELD_SIZE), mulmod(z1, x2, FIELD_SIZE));
|
204
|
+
}
|
205
|
+
|
206
|
+
/** **************************************************************************
|
207
|
+
@notice Computes elliptic-curve sum, in projective co-ordinates
|
208
|
+
|
209
|
+
@dev Using projective coordinates avoids costly divisions
|
210
|
+
|
211
|
+
@dev To use this with x and y in affine coordinates, compute
|
212
|
+
projectiveECAdd(x[0], x[1], 1, y[0], y[1], 1)
|
213
|
+
|
214
|
+
@dev This can be used to calculate the z which is the inverse to zInv in
|
215
|
+
isValidVRFOutput. But consider using a faster re-implementation.
|
216
|
+
|
217
|
+
@dev This function assumes [x1,y1,z1],[x2,y2,z2] are valid projective
|
218
|
+
coordinates of secp256k1 points. That is safe in this contract,
|
219
|
+
because this method is only used by linearCombination, which checks
|
220
|
+
points are on the curve via ecrecover, and ensures valid projective
|
221
|
+
coordinates by passing z1=z2=1.
|
222
|
+
**************************************************************************
|
223
|
+
@param x1 The first affine coordinate of the first summand
|
224
|
+
@param y1 The second affine coordinate of the first summand
|
225
|
+
@param x2 The first affine coordinate of the second summand
|
226
|
+
@param y2 The second affine coordinate of the second summand
|
227
|
+
**************************************************************************
|
228
|
+
@return [x1,y1,z1]+[x2,y2,z2] as points on secp256k1, in P²(𝔽ₙ)
|
229
|
+
*/
|
230
|
+
function projectiveECAdd(uint256 x1, uint256 y1, uint256 x2, uint256 y2)
|
231
|
+
public pure returns(uint256 x3, uint256 y3, uint256 z3) {
|
232
|
+
// See "Group law for E/K : y^2 = x^3 + ax + b", in section 3.1.2, p. 80,
|
233
|
+
// "Guide to Elliptic Curve Cryptography" by Hankerson, Menezes and Vanstone
|
234
|
+
// We take the equations there for (x3,y3), and homogenize them to
|
235
|
+
// projective coordinates. That way, no inverses are required, here, and we
|
236
|
+
// only need the one inverse in affineECAdd.
|
237
|
+
|
238
|
+
// We only need the "point addition" equations from Hankerson et al. Can
|
239
|
+
// skip the "point doubling" equations because p1 == p2 is cryptographically
|
240
|
+
// impossible, and require'd not to be the case in linearCombination.
|
241
|
+
|
242
|
+
// Add extra "projective coordinate" to the two points
|
243
|
+
(uint256 z1, uint256 z2) = (1, 1);
|
244
|
+
|
245
|
+
// (lx, lz) = (y2-y1)/(x2-x1), i.e., gradient of secant line.
|
246
|
+
uint256 lx = addmod(y2, FIELD_SIZE - y1, FIELD_SIZE);
|
247
|
+
uint256 lz = addmod(x2, FIELD_SIZE - x1, FIELD_SIZE);
|
248
|
+
|
249
|
+
uint256 dx; // Accumulates denominator from x3 calculation
|
250
|
+
// x3=((y2-y1)/(x2-x1))^2-x1-x2
|
251
|
+
(x3, dx) = projectiveMul(lx, lz, lx, lz); // ((y2-y1)/(x2-x1))^2
|
252
|
+
(x3, dx) = projectiveSub(x3, dx, x1, z1); // ((y2-y1)/(x2-x1))^2-x1
|
253
|
+
(x3, dx) = projectiveSub(x3, dx, x2, z2); // ((y2-y1)/(x2-x1))^2-x1-x2
|
254
|
+
|
255
|
+
uint256 dy; // Accumulates denominator from y3 calculation
|
256
|
+
// y3=((y2-y1)/(x2-x1))(x1-x3)-y1
|
257
|
+
(y3, dy) = projectiveSub(x1, z1, x3, dx); // x1-x3
|
258
|
+
(y3, dy) = projectiveMul(y3, dy, lx, lz); // ((y2-y1)/(x2-x1))(x1-x3)
|
259
|
+
(y3, dy) = projectiveSub(y3, dy, y1, z1); // ((y2-y1)/(x2-x1))(x1-x3)-y1
|
260
|
+
|
261
|
+
if (dx != dy) { // Cross-multiply to put everything over a common denominator
|
262
|
+
x3 = mulmod(x3, dy, FIELD_SIZE);
|
263
|
+
y3 = mulmod(y3, dx, FIELD_SIZE);
|
264
|
+
z3 = mulmod(dx, dy, FIELD_SIZE);
|
265
|
+
} else {
|
266
|
+
z3 = dx;
|
267
|
+
}
|
268
|
+
}
|
269
|
+
|
270
|
+
// Returns p1+p2, as affine points on secp256k1. invZ must be the inverse of
|
271
|
+
// the z returned by projectiveECAdd(p1, p2). It is computed off-chain to
|
272
|
+
// save gas.
|
273
|
+
function affineECAdd(
|
274
|
+
uint256[2] memory p1, uint256[2] memory p2,
|
275
|
+
uint256 invZ) public pure returns (uint256[2] memory) {
|
276
|
+
uint256 x;
|
277
|
+
uint256 y;
|
278
|
+
uint256 z;
|
279
|
+
(x, y, z) = projectiveECAdd(p1[0], p1[1], p2[0], p2[1]);
|
280
|
+
require(mulmod(z, invZ, FIELD_SIZE) == 1, "_invZ must be inverse of z");
|
281
|
+
// Clear the z ordinate of the projective representation by dividing through
|
282
|
+
// by it, to obtain the affine representation
|
283
|
+
return [mulmod(x, invZ, FIELD_SIZE), mulmod(y, invZ, FIELD_SIZE)];
|
284
|
+
}
|
285
|
+
|
286
|
+
// Returns true iff address(c*p+s*g) == lcWitness, where g is generator.
|
287
|
+
function verifyLinearCombinationWithGenerator(
|
288
|
+
uint256 c, uint256[2] memory p, uint256 s, address lcWitness)
|
289
|
+
public pure returns (bool) {
|
290
|
+
// ecrecover returns 0x0 in certain failure modes. Ensure witness differs.
|
291
|
+
require(lcWitness != address(0), "bad witness");
|
292
|
+
// https://ethresear.ch/t/you-can-kinda-abuse-ecrecover-to-do-ecmul-in-secp256k1-today/2384/9
|
293
|
+
// The point corresponding to the address returned by
|
294
|
+
// ecrecover(-s*p[0],v,_p[0],_c*p[0]) is
|
295
|
+
// (p[0]⁻¹ mod GROUP_ORDER)*(c*p[0]-(-s)*p[0]*g)=_c*p+s*g, where v
|
296
|
+
// is the parity of p[1]. See https://crypto.stackexchange.com/a/18106
|
297
|
+
bytes32 pseudoHash = bytes32(GROUP_ORDER - mulmod(p[0], s, GROUP_ORDER));
|
298
|
+
// https://bitcoin.stackexchange.com/questions/38351/ecdsa-v-r-s-what-is-v
|
299
|
+
uint8 v = (p[1] % 2 == 0) ? 27 : 28;
|
300
|
+
bytes32 pseudoSignature = bytes32(mulmod(c, p[0], GROUP_ORDER));
|
301
|
+
address computed = ecrecover(pseudoHash, v, bytes32(p[0]), pseudoSignature);
|
302
|
+
return computed == lcWitness;
|
303
|
+
}
|
304
|
+
|
305
|
+
// c*p1 + s*p2
|
306
|
+
function linearCombination(
|
307
|
+
uint256 c, uint256[2] memory p1, uint256[2] memory cp1Witness,
|
308
|
+
uint256 s, uint256[2] memory p2, uint256[2] memory sp2Witness,
|
309
|
+
uint256 zInv)
|
310
|
+
public pure returns (uint256[2] memory) {
|
311
|
+
require(cp1Witness[0] != sp2Witness[0], "points must differ in sum");
|
312
|
+
require(ecmulVerify(p1, c, cp1Witness), "First multiplication check failed");
|
313
|
+
require(ecmulVerify(p2, s, sp2Witness), "Second multiplication check failed");
|
314
|
+
return affineECAdd(cp1Witness, sp2Witness, zInv);
|
315
|
+
}
|
316
|
+
|
317
|
+
// Pseudo-random number from inputs. Corresponds to vrf.go/scalarFromCurve.
|
318
|
+
function scalarFromCurve(
|
319
|
+
uint256[2] memory hash, uint256[2] memory pk, uint256[2] memory gamma,
|
320
|
+
address uWitness, uint256[2] memory v)
|
321
|
+
public pure returns (uint256 s) {
|
322
|
+
bytes32 iHash = keccak256(abi.encodePacked(hash, pk, gamma, v, uWitness));
|
323
|
+
return zqHash(GROUP_ORDER, uint256(iHash));
|
324
|
+
}
|
325
|
+
|
326
|
+
// True if (gamma, c, s) is a correctly constructed randomness proof from pk
|
327
|
+
// and seed. zInv must be the inverse of the third ordinate from
|
328
|
+
// projectiveECAdd applied to cGammaWitness and sHashWitness
|
329
|
+
function verifyVRFProof(
|
330
|
+
uint256[2] memory pk, uint256[2] memory gamma, uint256 c, uint256 s,
|
331
|
+
uint256 seed, address uWitness, uint256[2] memory cGammaWitness,
|
332
|
+
uint256[2] memory sHashWitness, uint256 zInv)
|
333
|
+
public view returns (bool) {
|
334
|
+
// NB: Curve operations already check that (pkX, pkY), (gammaX, gammaY)
|
335
|
+
// are valid curve points. No need to do that explicitly.
|
336
|
+
require(
|
337
|
+
verifyLinearCombinationWithGenerator(c, pk, s, uWitness),
|
338
|
+
"Could not verify that address(c*pk+s*generator)=_uWitness");
|
339
|
+
uint256[2] memory hash = hashToCurve(pk, seed);
|
340
|
+
uint256[2] memory v = linearCombination(
|
341
|
+
c, gamma, cGammaWitness, s, hash, sHashWitness, zInv);
|
342
|
+
return (c == scalarFromCurve(hash, pk, gamma, uWitness, v));
|
343
|
+
}
|
344
|
+
|
345
|
+
/** **************************************************************************
|
346
|
+
@notice isValidVRFOutput returns true iff the proof can be verified as
|
347
|
+
showing that output was generated as mandated.
|
348
|
+
|
349
|
+
@dev See the invocation of verifyVRFProof in VRF.js, for an example.
|
350
|
+
**************************************************************************
|
351
|
+
@dev Let x be the secret key associated with the public key pk
|
352
|
+
|
353
|
+
@param pk Affine coordinates of the secp256k1 public key for this VRF
|
354
|
+
@param gamma Intermediate output of the VRF as an affine secp256k1 point
|
355
|
+
@param c The challenge value for proof that gamma = x*hashToCurve(seed)
|
356
|
+
See the variable c on p. 28 of
|
357
|
+
https://www.cs.bu.edu/~goldbe/papers/VRF_ietf99_print.pdf
|
358
|
+
@param s The response value for the proof. See s on p. 28
|
359
|
+
@param seed The input seed from which the VRF output is computed
|
360
|
+
@param uWitness The ethereum address of c*pk + s*<generator>, in
|
361
|
+
elliptic-curve arithmetic
|
362
|
+
@param cGammaWitness c*gamma on the elliptic-curve
|
363
|
+
@param sHashWitness s*hashToCurve(seed) on the elliptic-curve
|
364
|
+
@param zInv Inverse of the third ordinate of the return value from
|
365
|
+
projectiveECAdd(c*gamma, s*hashToCurve(seed)). Passed in here
|
366
|
+
to save gas, because computing modular inverses is expensive in the
|
367
|
+
EVM.
|
368
|
+
@param output The actual output of the VRF.
|
369
|
+
**************************************************************************
|
370
|
+
@return True iff all the above parameters are correct
|
371
|
+
*/
|
372
|
+
function isValidVRFOutput(
|
373
|
+
uint256[2] calldata pk, uint256[2] calldata gamma, uint256 c, uint256 s,
|
374
|
+
uint256 seed, address uWitness, uint256[2] calldata cGammaWitness,
|
375
|
+
uint256[2] calldata sHashWitness, uint256 zInv, uint256 output)
|
376
|
+
external view returns (bool) {
|
377
|
+
return verifyVRFProof(
|
378
|
+
pk, gamma, c, s, seed, uWitness, cGammaWitness, sHashWitness,
|
379
|
+
zInv) &&
|
380
|
+
(uint256(keccak256(abi.encodePacked(gamma))) == output);
|
381
|
+
}
|
382
|
+
}
|
@@ -0,0 +1,41 @@
|
|
1
|
+
pragma solidity 0.5.0;
|
2
|
+
|
3
|
+
import "./Owned.sol";
|
4
|
+
|
5
|
+
/**
|
6
|
+
* @title Whitelisted
|
7
|
+
* @notice Allows the owner to add and remove addresses from a whitelist
|
8
|
+
*/
|
9
|
+
contract Whitelisted is Owned {
|
10
|
+
|
11
|
+
mapping(address => bool) public whitelisted;
|
12
|
+
|
13
|
+
event AddedToWhitelist(address user);
|
14
|
+
event RemovedFromWhitelist(address user);
|
15
|
+
|
16
|
+
/**
|
17
|
+
* @notice Adds an address to the whitelist
|
18
|
+
* @param _user The address to whitelist
|
19
|
+
*/
|
20
|
+
function addToWhitelist(address _user) external onlyOwner() {
|
21
|
+
whitelisted[_user] = true;
|
22
|
+
emit AddedToWhitelist(_user);
|
23
|
+
}
|
24
|
+
|
25
|
+
/**
|
26
|
+
* @notice Removes an address from the whitelist
|
27
|
+
* @param _user The address to remove
|
28
|
+
*/
|
29
|
+
function removeFromWhitelist(address _user) external onlyOwner() {
|
30
|
+
delete whitelisted[_user];
|
31
|
+
emit RemovedFromWhitelist(_user);
|
32
|
+
}
|
33
|
+
|
34
|
+
/**
|
35
|
+
* @dev reverts if the caller is not whitelisted
|
36
|
+
*/
|
37
|
+
modifier isWhitelisted() {
|
38
|
+
require(whitelisted[msg.sender], "Not whitelisted");
|
39
|
+
_;
|
40
|
+
}
|
41
|
+
}
|
@@ -0,0 +1,80 @@
|
|
1
|
+
pragma solidity 0.5.0;
|
2
|
+
|
3
|
+
import "./PrepaidAggregator.sol";
|
4
|
+
import "./Whitelisted.sol";
|
5
|
+
|
6
|
+
/**
|
7
|
+
* @title Whitelisted Prepaid Aggregator contract
|
8
|
+
* @notice This contract requires addresses to be added to a whitelist
|
9
|
+
* in order to read the answers stored in the PrepaidAggregator contract
|
10
|
+
*/
|
11
|
+
contract WhitelistedAggregator is PrepaidAggregator, Whitelisted {
|
12
|
+
|
13
|
+
constructor(
|
14
|
+
address _link,
|
15
|
+
uint128 _paymentAmount,
|
16
|
+
uint32 _timeout,
|
17
|
+
uint8 _decimals,
|
18
|
+
bytes32 _description
|
19
|
+
) public PrepaidAggregator(
|
20
|
+
_link,
|
21
|
+
_paymentAmount,
|
22
|
+
_timeout,
|
23
|
+
_decimals,
|
24
|
+
_description
|
25
|
+
){}
|
26
|
+
|
27
|
+
/**
|
28
|
+
* @notice get the most recently reported answer
|
29
|
+
* @dev overridden funcion to add the isWhitelisted() modifier
|
30
|
+
*/
|
31
|
+
function latestAnswer()
|
32
|
+
external
|
33
|
+
isWhitelisted()
|
34
|
+
view
|
35
|
+
returns (int256)
|
36
|
+
{
|
37
|
+
return _latestAnswer();
|
38
|
+
}
|
39
|
+
|
40
|
+
/**
|
41
|
+
* @notice get the most recent updated at timestamp
|
42
|
+
* @dev overridden funcion to add the isWhitelisted() modifier
|
43
|
+
*/
|
44
|
+
function latestTimestamp()
|
45
|
+
external
|
46
|
+
view
|
47
|
+
isWhitelisted()
|
48
|
+
returns (uint256)
|
49
|
+
{
|
50
|
+
return _latestTimestamp();
|
51
|
+
}
|
52
|
+
|
53
|
+
/**
|
54
|
+
* @notice get past rounds answers
|
55
|
+
* @dev overridden funcion to add the isWhitelisted() modifier
|
56
|
+
* @param _roundId the round number to retrieve the answer for
|
57
|
+
*/
|
58
|
+
function getAnswer(uint256 _roundId)
|
59
|
+
external
|
60
|
+
view
|
61
|
+
isWhitelisted()
|
62
|
+
returns (int256)
|
63
|
+
{
|
64
|
+
return _getAnswer(_roundId);
|
65
|
+
}
|
66
|
+
|
67
|
+
/**
|
68
|
+
* @notice get timestamp when an answer was last updated
|
69
|
+
* @dev overridden funcion to add the isWhitelisted() modifier
|
70
|
+
* @param _roundId the round number to retrieve the updated timestamp for
|
71
|
+
*/
|
72
|
+
function getTimestamp(uint256 _roundId)
|
73
|
+
external
|
74
|
+
isWhitelisted()
|
75
|
+
view
|
76
|
+
returns (uint256)
|
77
|
+
{
|
78
|
+
return _getTimestamp(_roundId);
|
79
|
+
}
|
80
|
+
}
|
@@ -0,0 +1,21 @@
|
|
1
|
+
pragma solidity ^0.5.0;
|
2
|
+
|
3
|
+
interface ChainlinkRequestInterface {
|
4
|
+
function oracleRequest(
|
5
|
+
address sender,
|
6
|
+
uint256 requestPrice,
|
7
|
+
bytes32 serviceAgreementID,
|
8
|
+
address callbackAddress,
|
9
|
+
bytes4 callbackFunctionId,
|
10
|
+
uint256 nonce,
|
11
|
+
uint256 dataVersion, // Currently unused, always "1"
|
12
|
+
bytes calldata data
|
13
|
+
) external;
|
14
|
+
|
15
|
+
function cancelOracleRequest(
|
16
|
+
bytes32 requestId,
|
17
|
+
uint256 payment,
|
18
|
+
bytes4 callbackFunctionId,
|
19
|
+
uint256 expiration
|
20
|
+
) external;
|
21
|
+
}
|
@@ -0,0 +1,26 @@
|
|
1
|
+
pragma solidity ^0.5.0;
|
2
|
+
|
3
|
+
interface ENSInterface {
|
4
|
+
|
5
|
+
// Logged when the owner of a node assigns a new owner to a subnode.
|
6
|
+
event NewOwner(bytes32 indexed node, bytes32 indexed label, address owner);
|
7
|
+
|
8
|
+
// Logged when the owner of a node transfers ownership to a new account.
|
9
|
+
event Transfer(bytes32 indexed node, address owner);
|
10
|
+
|
11
|
+
// Logged when the resolver for a node changes.
|
12
|
+
event NewResolver(bytes32 indexed node, address resolver);
|
13
|
+
|
14
|
+
// Logged when the TTL of a node changes
|
15
|
+
event NewTTL(bytes32 indexed node, uint64 ttl);
|
16
|
+
|
17
|
+
|
18
|
+
function setSubnodeOwner(bytes32 node, bytes32 label, address _owner) external;
|
19
|
+
function setResolver(bytes32 node, address _resolver) external;
|
20
|
+
function setOwner(bytes32 node, address _owner) external;
|
21
|
+
function setTTL(bytes32 node, uint64 _ttl) external;
|
22
|
+
function owner(bytes32 node) external view returns (address);
|
23
|
+
function resolver(bytes32 node) external view returns (address);
|
24
|
+
function ttl(bytes32 node) external view returns (uint64);
|
25
|
+
|
26
|
+
}
|
@@ -0,0 +1,16 @@
|
|
1
|
+
pragma solidity ^0.5.0;
|
2
|
+
|
3
|
+
interface LinkTokenInterface {
|
4
|
+
function allowance(address owner, address spender) external returns (uint256 remaining);
|
5
|
+
function approve(address spender, uint256 value) external returns (bool success);
|
6
|
+
function balanceOf(address owner) external returns (uint256 balance);
|
7
|
+
function decimals() external returns (uint8 decimalPlaces);
|
8
|
+
function decreaseApproval(address spender, uint256 addedValue) external returns (bool success);
|
9
|
+
function increaseApproval(address spender, uint256 subtractedValue) external;
|
10
|
+
function name() external returns (string memory tokenName);
|
11
|
+
function symbol() external returns (string memory tokenSymbol);
|
12
|
+
function totalSupply() external returns (uint256 totalTokensIssued);
|
13
|
+
function transfer(address to, uint256 value) external returns (bool success);
|
14
|
+
function transferAndCall(address to, uint256 value, bytes calldata data) external returns (bool success);
|
15
|
+
function transferFrom(address from, address to, uint256 value) external returns (bool success);
|
16
|
+
}
|
@@ -0,0 +1,16 @@
|
|
1
|
+
pragma solidity ^0.5.0;
|
2
|
+
|
3
|
+
interface OracleInterface {
|
4
|
+
function fulfillOracleRequest(
|
5
|
+
bytes32 requestId,
|
6
|
+
uint256 payment,
|
7
|
+
address callbackAddress,
|
8
|
+
bytes4 callbackFunctionId,
|
9
|
+
uint256 expiration,
|
10
|
+
bytes32 data
|
11
|
+
) external returns (bool);
|
12
|
+
function getAuthorizationStatus(address node) external view returns (bool);
|
13
|
+
function setFulfillmentPermission(address node, bool allowed) external;
|
14
|
+
function withdraw(address recipient, uint256 amount) external;
|
15
|
+
function withdrawable() external view returns (uint256);
|
16
|
+
}
|
@@ -0,0 +1,16 @@
|
|
1
|
+
pragma solidity ^0.5.0;
|
2
|
+
|
3
|
+
interface WithdrawalInterface {
|
4
|
+
/**
|
5
|
+
* @notice transfer LINK held by the contract belonging to msg.sender to
|
6
|
+
* another address
|
7
|
+
* @param recipient is the address to send the LINK to
|
8
|
+
* @param amount is the amount of LINK to send
|
9
|
+
*/
|
10
|
+
function withdraw(address recipient, uint256 amount) external;
|
11
|
+
|
12
|
+
/**
|
13
|
+
* @notice query the available amount of LINK to withdraw by msg.sender
|
14
|
+
*/
|
15
|
+
function withdrawable() external view returns (uint256);
|
16
|
+
}
|
@@ -0,0 +1,13 @@
|
|
1
|
+
pragma solidity ^0.5.0;
|
2
|
+
|
3
|
+
import "./Consumer.sol";
|
4
|
+
|
5
|
+
contract BasicConsumer is Consumer {
|
6
|
+
|
7
|
+
constructor(address _link, address _oracle, bytes32 _specId) public {
|
8
|
+
setChainlinkToken(_link);
|
9
|
+
setChainlinkOracle(_oracle);
|
10
|
+
specId = _specId;
|
11
|
+
}
|
12
|
+
|
13
|
+
}
|