From a549febd805a1a1088c57b8194cd9ccf0f47adf3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 13 Jun 2023 13:16:21 +0200 Subject: [PATCH 01/12] feat: uncouple SLA logic from WitnetRequest implementation --- contracts/UsingWitnet.sol | 15 ++ contracts/data/WitnetRequestFactoryData.sol | 8 +- .../core/WitnetRequestFactoryDefault.sol | 152 +++--------------- .../WitnetRequestBoardTrustableBase.sol | 27 +++- .../IWitnetRequestBoardRequestor.sol | 17 +- contracts/requests/WitnetRequest.sol | 23 +-- package.json | 2 +- 7 files changed, 75 insertions(+), 169 deletions(-) diff --git a/contracts/UsingWitnet.sol b/contracts/UsingWitnet.sol index adb524c2f..6c98af1f8 100644 --- a/contracts/UsingWitnet.sol +++ b/contracts/UsingWitnet.sol @@ -94,6 +94,21 @@ abstract contract UsingWitnet { _id = witnet.postRequest{value: _reward}(_radHash, _slaHash); } + /// @notice Post some data request to be eventually solved by the Witnet decentralized oracle network. + /// @notice The EVM -> Witnet bridge will read the Witnet Data Request bytecode from the WitnetBytecodes + /// @notice registry based on given `_radHash` and `_slaHash` values. + /// @dev Enough ETH needs to be provided as to cover for the implicit fee. + /// @param _radHash Unique hash of some pre-validated Witnet Radon Request. + /// @param _slaParams The SLA params upon which this data request will be solved by Witnet. + /// @return _id The unique identifier of the just posted data request. + /// @return _reward Current reward amount escrowed by the WRB until a result gets reported. + function _witnetPostRequest(bytes32 _radHash, WitnetV2.RadonSLA memory _slaParams) + virtual internal + returns (uint256 _id, uint256 _reward) + { + return _witnetPostRequest(_radHash, witnet.registry().verifyRadonSLA(_slaParams)); + } + /// @notice Read the Witnet-provided result to a previously posted request. /// @dev Reverts if the data request was not yet solved. /// @param _id The unique identifier of some previously posted data request. diff --git a/contracts/data/WitnetRequestFactoryData.sol b/contracts/data/WitnetRequestFactoryData.sol index ca8696d05..b7e04459c 100644 --- a/contracts/data/WitnetRequestFactoryData.sol +++ b/contracts/data/WitnetRequestFactoryData.sol @@ -26,13 +26,9 @@ contract WitnetRequestFactoryData { struct WitnetRequestSlot { /// Array of string arguments passed upon initialization. - string[][] args; - /// Curator's address on settled requests. - address curator; - /// Radon RAD hash. + string[][] args; + /// Radon RAD hash. bytes32 radHash; - /// Radon SLA hash. - bytes32 slaHash; /// Parent WitnetRequestTemplate contract. WitnetRequestTemplate template; } diff --git a/contracts/impls/core/WitnetRequestFactoryDefault.sol b/contracts/impls/core/WitnetRequestFactoryDefault.sol index 06606af99..c13eb0294 100644 --- a/contracts/impls/core/WitnetRequestFactoryDefault.sol +++ b/contracts/impls/core/WitnetRequestFactoryDefault.sol @@ -50,14 +50,6 @@ contract WitnetRequestFactoryDefault _; } - modifier securedRequest { - require( - __witnetRequest().slaHash != bytes32(0), - "WitnetRequest: unsecured" - ); - _; - } - constructor( WitnetBytecodes _registry, bool _upgradable, @@ -94,7 +86,7 @@ contract WitnetRequestFactoryDefault WitnetV2.RadonDataTypes _resultDataType; require( _retrievalsIds.length > 0, - "WitnetRequestTemplate: no retrievals ?" + "WitnetRequestTemplate: no retrievals?" ); // check that all retrievals exist in the registry, // and they all return the same data type @@ -135,32 +127,13 @@ contract WitnetRequestFactoryDefault ) virtual public initializer - returns (WitnetRequest) + returns (address) { WitnetRequestSlot storage __data = __witnetRequest(); __data.args = _args; __data.radHash = _radHash; __data.template = WitnetRequestTemplate(msg.sender); - return WitnetRequest(address(this)); - } - - function forkWitnetRequest( - address _curator, - bytes32 _slaHash - ) - virtual public - initializer - returns (WitnetRequest) - { - WitnetRequestSlot storage __data = __witnetRequest(); - WitnetRequest parent = WitnetRequest(msg.sender); - bytes32 _radHash = parent.radHash(); - __data.args = parent.args(); - __data.curator = _curator; - __data.radHash = _radHash; - __data.slaHash = _slaHash; - __data.template = parent.template(); - return WitnetRequest(address(this)); + return address(this); } @@ -389,51 +362,14 @@ contract WitnetRequestFactoryDefault /// =============================================================================================================== - /// --- IWitnetRequest implementation ----------------------------------------------------------------------------- + /// --- WitnetRequest implementation ------------------------------------------------------------------------------ function bytecode() override external view - securedRequest returns (bytes memory) { - return registry.bytecodeOf( - __witnetRequest().radHash, - __witnetRequest().slaHash - ); - } - - function hash() - override - external view - securedRequest - returns (bytes32) - { - return sha256(abi.encodePacked( - __witnetRequest().radHash, - __witnetRequest().slaHash - )); - } - - /// =============================================================================================================== - /// --- WitnetRequest implementation ------------------------------------------------------------------------------ - - function curator() - override - external view - onlyDelegateCalls - returns (address) - { - return __witnetRequest().curator; - } - - function secured() - override - external view - onlyDelegateCalls - returns (bool) - { - return __witnetRequest().slaHash != bytes32(0); + return registry.bytecodeOf(__witnetRequest().radHash); } function template() @@ -463,62 +399,6 @@ contract WitnetRequestFactoryDefault return __witnetRequest().radHash; } - function slaHash() - override - external view - onlyDelegateCalls - returns (bytes32) - { - return __witnetRequest().slaHash; - } - - function getRadonSLA() - override - external view - onlyDelegateCalls - returns (WitnetV2.RadonSLA memory) - { - return registry.lookupRadonSLA( - __witnetRequest().slaHash - ); - } - - function settleRadonSLA(WitnetV2.RadonSLA memory _sla) - virtual override - external - onlyDelegateCalls - returns (WitnetRequest _settled) - { - WitnetRequestSlot storage __data = __witnetRequest(); - WitnetRequestTemplate _template = __witnetRequest().template; - require( - address(_template) != address(0), - "WitnetRequestFactoryDefault: not a WitnetRequest" - ); - bytes32 _slaHash = registry.verifyRadonSLA(_sla); - if (_slaHash != __data.slaHash) { - if (msg.sender == __witnetRequest().curator) { - __data.slaHash = _slaHash; - _settled = WitnetRequest(address(this)); - } else { - (address _address, bytes32 _salt) = _determineAddress(_slaHash); - if (_address.code.length > 0) { - _settled = WitnetRequest(_address); - } else { - _settled = WitnetRequestFactoryDefault(_cloneDeterministic(_salt)) - .forkWitnetRequest( - msg.sender, - _slaHash - ) - ; - } - } - } else { - _settled = WitnetRequest(address(this)); - } - emit WitnetRequestSettled(_settled, __data.radHash, _slaHash); - } - function version() virtual override(WitnetRequestTemplate, WitnetUpgradableBase) public view @@ -700,7 +580,7 @@ contract WitnetRequestFactoryDefault virtual override public onlyDelegateCalls - returns (WitnetRequest _request) + returns (address _request) { // if called on a WitnetRequest instance: if (address(__witnetRequest().template) != address(0)) { @@ -715,12 +595,11 @@ contract WitnetRequestFactoryDefault __data.resultDataMaxSize, _args ); - // address of unsecured requests (i.e. no slaHash, no curator) built out of a template, - // will be determined by the template's address and the request's radHash: - (address _address, bytes32 _salt) = _determineAddress(_radHash); - if (_address.code.length > 0) { - _request = WitnetRequest(_address); - } else { + // the request address will be determined by the template's address, + // the request's radHash and the factory's implementation version: + bytes32 _salt; + (_request, _salt) = _determineRequestAddressAndSalt(_radHash); + if (_request.code.length == 0) { _request = WitnetRequestFactoryDefault(_cloneDeterministic(_salt)) .initializeWitnetRequest( _radHash, @@ -751,11 +630,16 @@ contract WitnetRequestFactoryDefault ); } - function _determineAddress(bytes32 _hash) + function _determineRequestAddressAndSalt(bytes32 _radHash) internal view returns (address, bytes32) { - bytes32 _salt = keccak256(abi.encodePacked(_hash, bytes4(_WITNET_UPGRADABLE_VERSION))); + bytes32 _salt = keccak256( + abi.encodePacked( + _radHash, + bytes4(_WITNET_UPGRADABLE_VERSION) + ) + ); return ( address(uint160(uint256(keccak256( abi.encodePacked( diff --git a/contracts/impls/core/customs/WitnetRequestBoardTrustableBase.sol b/contracts/impls/core/customs/WitnetRequestBoardTrustableBase.sol index f51347bad..895835aa1 100644 --- a/contracts/impls/core/customs/WitnetRequestBoardTrustableBase.sol +++ b/contracts/impls/core/customs/WitnetRequestBoardTrustableBase.sol @@ -419,9 +419,9 @@ abstract contract WitnetRequestBoardTrustableBase /// @dev Fails if: /// @dev - provided reward is too low. /// @dev - provided address is zero. - /// @param _requestAddr The address of a IWitnetRequest contract, containing the actual Data Request seralized bytecode. + /// @param _requestInterface The address of a IWitnetRequest contract, containing the actual Data Request seralized bytecode. /// @return _queryId An unique query identifier. - function postRequest(IWitnetRequest _requestAddr) + function postRequest(IWitnetRequest _requestInterface) virtual override public payable returns (uint256 _queryId) @@ -434,13 +434,13 @@ abstract contract WitnetRequestBoardTrustableBase require(_value >= _baseReward, "WitnetRequestBoardTrustableBase: reward too low"); // Validates provided script: - require(address(_requestAddr) != address(0), "WitnetRequestBoardTrustableBase: no request"); + require(_requestInterface.hash() != bytes32(0), "WitnetRequestBoardTrustableBase: no precompiled request"); _queryId = ++ __storage().numQueries; __storage().queries[_queryId].from = msg.sender; Witnet.Request storage _request = __request(_queryId); - _request.addr = address(_requestAddr); + _request.addr = address(_requestInterface); _request.gasprice = _gasPrice; _request.reward = _value; @@ -482,6 +482,25 @@ abstract contract WitnetRequestBoardTrustableBase // Let observers know that a new request has been posted emit PostedRequest(_queryId, msg.sender); } + + /// Requests the execution of the given Witnet Data Request in expectation that it will be relayed and solved by the Witnet DON. + /// A reward amount is escrowed by the Witnet Request Board that will be transferred to the reporter who relays back the Witnet-provided + /// result to this request. + /// @dev Fails if: + /// @dev - provided reward is too low. + /// @param _radHash The RAD hash of the data tequest to be solved by Witnet. + /// @param _slaParams The SLA param of the data request to be solved by Witnet. + function postRequest(bytes32 _radHash, WitnetV2.RadonSLA calldata _slaParams) + virtual override + public payable + returns (uint256 _queryId) + { + return postRequest( + _radHash, + registry.verifyRadonSLA(_slaParams) + ); + } + /// Increments the reward of a previously posted request by adding the transaction value to it. /// @dev Updates request `gasPrice` in case this method is called with a higher diff --git a/contracts/interfaces/IWitnetRequestBoardRequestor.sol b/contracts/interfaces/IWitnetRequestBoardRequestor.sol index 8086134ac..2dbb46537 100644 --- a/contracts/interfaces/IWitnetRequestBoardRequestor.sol +++ b/contracts/interfaces/IWitnetRequestBoardRequestor.sol @@ -3,7 +3,7 @@ pragma solidity >=0.7.0 <0.9.0; pragma experimental ABIEncoderV2; -import "../libs/Witnet.sol"; +import "../libs/WitnetV2.sol"; /// @title Witnet Requestor Interface /// @notice It defines how to interact with the Witnet Request Board in order to: @@ -47,11 +47,20 @@ interface IWitnetRequestBoardRequestor { /// @notice A reward amount is escrowed by the Witnet Request Board that will be transferred to the reporter who relays back the Witnet-provided /// @notice result to this request. /// @dev Fails if, provided reward is too low. - /// @param radHash The radHash of the Witnet Data Request. - /// @param slaHash The slaHash of the Witnet Data Request. + /// @param radHash The RAD hash of the data request to be solved by Witnet. + /// @param slaHash The SLA hash of the data request to be solved by Witnet. /// @return _queryId Unique query identifier. function postRequest(bytes32 radHash, bytes32 slaHash) external payable returns (uint256 _queryId); - + + /// @notice Requests the execution of the given Witnet Data Request in expectation that it will be relayed and solved by the Witnet DON. + /// @notice A reward amount is escrowed by the Witnet Request Board that will be transferred to the reporter who relays back the Witnet-provided + /// @notice result to this request. + /// @dev Fails if, provided reward is too low. + /// @param radHash The RAD hash of the data request to be solved by Witnet. + /// @param slaParams The SLA params of the data request to be solved by Witnet. + /// @return _queryId Unique query identifier. + function postRequest(bytes32 radHash, WitnetV2.RadonSLA calldata slaParams) external payable returns (uint256 _queryId); + /// @notice Increments the reward of a previously posted request by adding the transaction value to it. /// @dev Updates request `gasPrice` in case this method is called with a higher /// @dev gas price value than the one used in previous calls to `postRequest` or diff --git a/contracts/requests/WitnetRequest.sol b/contracts/requests/WitnetRequest.sol index 5c91812f4..fb61c5eb6 100644 --- a/contracts/requests/WitnetRequest.sol +++ b/contracts/requests/WitnetRequest.sol @@ -3,14 +3,12 @@ pragma solidity >=0.7.0 <0.9.0; pragma experimental ABIEncoderV2; -import "../interfaces/IWitnetRequest.sol"; - import "../WitnetBytecodes.sol"; import "../WitnetRequestFactory.sol"; abstract contract WitnetRequestTemplate { - event WitnetRequestBuilt(WitnetRequest indexed request, bytes32 indexed radHash, string[][] args); + event WitnetRequestBuilt(address indexed request, bytes32 indexed radHash, string[][] args); function class() virtual external view returns (bytes4); function factory() virtual external view returns (WitnetRequestFactory); @@ -29,36 +27,21 @@ abstract contract WitnetRequestTemplate function getRadonRetrievalsCount() virtual external view returns (uint256); function getRadonTally() virtual external view returns (WitnetV2.RadonReducer memory); - function buildRequest(string[][] calldata args) virtual external returns (WitnetRequest); + function buildRequest(string[][] calldata args) virtual external returns (address); function verifyRadonRequest(string[][] calldata args) virtual external returns (bytes32); } abstract contract WitnetRequest is - IWitnetRequest, WitnetRequestTemplate { event WitnetRequestSettled(IWitnetRequest indexed request, bytes32 radHash, bytes32 slaHash); /// introspection methods - function curator() virtual external view returns (address); - function secured() virtual external view returns (bool); function template() virtual external view returns (WitnetRequestTemplate); /// request-exclusive fields function args() virtual external view returns (string[][] memory); + function bytecode() virtual external view returns (bytes memory); function radHash() virtual external view returns (bytes32); - function slaHash() virtual external view returns (bytes32); - - /// @notice Get request's Radon SLA as verified into the factory's registry. - function getRadonSLA() virtual external view returns (WitnetV2.RadonSLA memory); - - /// @notice Settle request's SLA. Returns address(this) if called from request's curator. - /// @notice Otherwise, returns deterministic IWitnetRequest address based on: - /// @notice - address(this); - /// @notice - hash of provided SLA; - /// @notice - factory's major/mid version. - /// @dev Returned instance will match address(this) only if called from request's curator. - /// @dev Curator of returned instance may be different than caller's address. - function settleRadonSLA(WitnetV2.RadonSLA calldata sla) virtual external returns (WitnetRequest); } \ No newline at end of file diff --git a/package.json b/package.json index aff4fe08b..24e1799c6 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "witnet-solidity-bridge", - "version": "0.7.7", + "version": "0.7.8", "description": "Witnet Solidity Bridge contracts for EVM-compatible chains", "main": "", "scripts": { From 24fd0e6cfbdbeab2f48b68b7fb7f3d0e9235b811 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 13 Jun 2023 14:08:21 +0200 Subject: [PATCH 02/12] refactor: WitnetRequestBase -> WitnetRequestPrecompiled --- .../{WitnetRequestBase.sol => WitnetRequestPrecompiled.sol} | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) rename contracts/requests/{WitnetRequestBase.sol => WitnetRequestPrecompiled.sol} (93%) diff --git a/contracts/requests/WitnetRequestBase.sol b/contracts/requests/WitnetRequestPrecompiled.sol similarity index 93% rename from contracts/requests/WitnetRequestBase.sol rename to contracts/requests/WitnetRequestPrecompiled.sol index ff5d1a864..a638df9dd 100644 --- a/contracts/requests/WitnetRequestBase.sol +++ b/contracts/requests/WitnetRequestPrecompiled.sol @@ -4,7 +4,7 @@ pragma solidity >=0.7.0 <0.9.0; import "../libs/Witnet.sol"; -contract WitnetRequestBase +contract WitnetRequestPrecompiled is IWitnetRequest { From f1a18dfdb8cebc63aaf58ed55043c22fbe5008d7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 13 Jun 2023 14:13:04 +0200 Subject: [PATCH 03/12] refactor: uncouple WitnetRequest, WitnetRequestTemplate --- contracts/requests/WitnetRequest.sol | 30 +------------------ contracts/requests/WitnetRequestTemplate.sol | 31 ++++++++++++++++++++ 2 files changed, 32 insertions(+), 29 deletions(-) create mode 100644 contracts/requests/WitnetRequestTemplate.sol diff --git a/contracts/requests/WitnetRequest.sol b/contracts/requests/WitnetRequest.sol index fb61c5eb6..d63ee9f64 100644 --- a/contracts/requests/WitnetRequest.sol +++ b/contracts/requests/WitnetRequest.sol @@ -3,40 +3,12 @@ pragma solidity >=0.7.0 <0.9.0; pragma experimental ABIEncoderV2; -import "../WitnetBytecodes.sol"; -import "../WitnetRequestFactory.sol"; - -abstract contract WitnetRequestTemplate -{ - event WitnetRequestBuilt(address indexed request, bytes32 indexed radHash, string[][] args); - - function class() virtual external view returns (bytes4); - function factory() virtual external view returns (WitnetRequestFactory); - function registry() virtual external view returns (WitnetBytecodes); - function version() virtual external view returns (string memory); - - function aggregator() virtual external view returns (bytes32); - function parameterized() virtual external view returns (bool); - function resultDataMaxSize() virtual external view returns (uint16); - function resultDataType() virtual external view returns (WitnetV2.RadonDataTypes); - function retrievals() virtual external view returns (bytes32[] memory); - function tally() virtual external view returns (bytes32); - - function getRadonAggregator() virtual external view returns (WitnetV2.RadonReducer memory); - function getRadonRetrievalByIndex(uint256) virtual external view returns (WitnetV2.RadonRetrieval memory); - function getRadonRetrievalsCount() virtual external view returns (uint256); - function getRadonTally() virtual external view returns (WitnetV2.RadonReducer memory); - - function buildRequest(string[][] calldata args) virtual external returns (address); - function verifyRadonRequest(string[][] calldata args) virtual external returns (bytes32); -} +import "./WitnetRequestTemplate.sol"; abstract contract WitnetRequest is WitnetRequestTemplate { - event WitnetRequestSettled(IWitnetRequest indexed request, bytes32 radHash, bytes32 slaHash); - /// introspection methods function template() virtual external view returns (WitnetRequestTemplate); diff --git a/contracts/requests/WitnetRequestTemplate.sol b/contracts/requests/WitnetRequestTemplate.sol new file mode 100644 index 000000000..f180e5060 --- /dev/null +++ b/contracts/requests/WitnetRequestTemplate.sol @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: MIT + +pragma solidity >=0.7.0 <0.9.0; +pragma experimental ABIEncoderV2; + +import "../WitnetRequestFactory.sol"; + +abstract contract WitnetRequestTemplate +{ + event WitnetRequestBuilt(address indexed request, bytes32 indexed radHash, string[][] args); + + function class() virtual external view returns (bytes4); + function factory() virtual external view returns (WitnetRequestFactory); + function registry() virtual external view returns (WitnetBytecodes); + function version() virtual external view returns (string memory); + + function aggregator() virtual external view returns (bytes32); + function parameterized() virtual external view returns (bool); + function resultDataMaxSize() virtual external view returns (uint16); + function resultDataType() virtual external view returns (WitnetV2.RadonDataTypes); + function retrievals() virtual external view returns (bytes32[] memory); + function tally() virtual external view returns (bytes32); + + function getRadonAggregator() virtual external view returns (WitnetV2.RadonReducer memory); + function getRadonRetrievalByIndex(uint256) virtual external view returns (WitnetV2.RadonRetrieval memory); + function getRadonRetrievalsCount() virtual external view returns (uint256); + function getRadonTally() virtual external view returns (WitnetV2.RadonReducer memory); + + function buildRequest(string[][] calldata args) virtual external returns (address); + function verifyRadonRequest(string[][] calldata args) virtual external returns (bytes32); +} \ No newline at end of file From 648c3d41bcbb002f63c6d84d6b301f11c15506a0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Fri, 16 Jun 2023 14:22:58 +0200 Subject: [PATCH 04/12] fix(libs): range checks in WitnetBuffer --- contracts/libs/WitnetBuffer.sol | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/contracts/libs/WitnetBuffer.sol b/contracts/libs/WitnetBuffer.sol index 46a99d953..0c66fdeb1 100644 --- a/contracts/libs/WitnetBuffer.sol +++ b/contracts/libs/WitnetBuffer.sol @@ -22,7 +22,7 @@ library WitnetBuffer { // Ensures we access an existing index in an array modifier withinRange(uint index, uint _range) { - if (index >= _range) { + if (index > _range) { revert IndexOutOfBounds(index, _range); } _; @@ -92,7 +92,7 @@ library WitnetBuffer { bytes memory pokes ) internal pure - withinRange(length, buffer.data.length - buffer.cursor) + withinRange(length, buffer.data.length - buffer.cursor + 1) { bytes[] memory parts = new bytes[](3); parts[0] = peek( @@ -114,7 +114,7 @@ library WitnetBuffer { /// @return The next byte in the buffer counting from the cursor position. function next(Buffer memory buffer) internal pure - withinRange(buffer.cursor, buffer.data.length + 1) + withinRange(buffer.cursor, buffer.data.length) returns (bytes1) { // Return the byte at the position marked by the cursor and advance the cursor all at once @@ -127,7 +127,7 @@ library WitnetBuffer { uint length ) internal pure - withinRange(offset + length, buffer.data.length + 1) + withinRange(offset + length, buffer.data.length) returns (bytes memory) { bytes memory data = buffer.data; @@ -155,7 +155,7 @@ library WitnetBuffer { uint length ) internal pure - withinRange(length, buffer.data.length - buffer.cursor + 1) + withinRange(length, buffer.data.length - buffer.cursor) returns (bytes memory) { return peek( @@ -171,7 +171,7 @@ library WitnetBuffer { /// @return output A `bytes memory` containing the first `length` bytes from the buffer, counting from the cursor position. function read(Buffer memory buffer, uint length) internal pure - withinRange(buffer.cursor + length, buffer.data.length + 1) + withinRange(buffer.cursor + length, buffer.data.length) returns (bytes memory output) { // Create a new `bytes memory destination` value @@ -415,7 +415,7 @@ library WitnetBuffer { /// @return value The `uint16` value of the next 2 bytes in the buffer counting from the cursor position. function readUint16(Buffer memory buffer) internal pure - withinRange(buffer.cursor + 1, buffer.data.length) + withinRange(buffer.cursor + 2, buffer.data.length) returns (uint16 value) { bytes memory data = buffer.data; @@ -431,7 +431,7 @@ library WitnetBuffer { /// @return value The `uint32` value of the next 4 bytes in the buffer counting from the cursor position. function readUint32(Buffer memory buffer) internal pure - withinRange(buffer.cursor + 3, buffer.data.length) + withinRange(buffer.cursor + 4, buffer.data.length) returns (uint32 value) { bytes memory data = buffer.data; @@ -447,7 +447,7 @@ library WitnetBuffer { /// @return value The `uint64` value of the next 8 bytes in the buffer counting from the cursor position. function readUint64(Buffer memory buffer) internal pure - withinRange(buffer.cursor + 7, buffer.data.length) + withinRange(buffer.cursor + 8, buffer.data.length) returns (uint64 value) { bytes memory data = buffer.data; @@ -463,7 +463,7 @@ library WitnetBuffer { /// @return value The `uint128` value of the next 16 bytes in the buffer counting from the cursor position. function readUint128(Buffer memory buffer) internal pure - withinRange(buffer.cursor + 15, buffer.data.length) + withinRange(buffer.cursor + 16, buffer.data.length) returns (uint128 value) { bytes memory data = buffer.data; @@ -479,7 +479,7 @@ library WitnetBuffer { /// @return value The `uint256` value of the next 32 bytes in the buffer counting from the cursor position. function readUint256(Buffer memory buffer) internal pure - withinRange(buffer.cursor + 31, buffer.data.length) + withinRange(buffer.cursor + 32, buffer.data.length) returns (uint256 value) { bytes memory data = buffer.data; @@ -632,7 +632,7 @@ library WitnetBuffer { bool relative ) internal pure - withinRange(offset, buffer.data.length + 1) + withinRange(offset, buffer.data.length) returns (uint) { // Deal with relative offsets From 2817aff96f91d93592d2ec83f6ef8f258f23fb67 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 20 Jun 2023 17:29:23 +0200 Subject: [PATCH 05/12] chore: upgrade WB, WRB, WRF to v0.7.8-648c3d4 on multiple chains --- migrations/witnet.addresses.json | 51 +++++++++++++++++--------------- migrations/witnet.settings.js | 2 -- 2 files changed, 27 insertions(+), 26 deletions(-) diff --git a/migrations/witnet.addresses.json b/migrations/witnet.addresses.json index 41ac14e83..5ee5b3754 100644 --- a/migrations/witnet.addresses.json +++ b/migrations/witnet.addresses.json @@ -73,11 +73,11 @@ "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetErrorsLib": "0x1b91eAB33362f10A5F803Fe3f0d181F42caFaac3", - "WitnetEncodingLib": "0x6395d83C9Aa803498980A5ab78217785d4db7bE7", + "WitnetEncodingLib": "0x49d3f1C57C320f833FF96bd9786Ae7DB8854B680", "WitnetPriceFeedsLib": "0x8684d396366C21AA01B120F69df2070f840aC134", "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", "WitnetProxy": "0xc71A87657b13A370594967A04b4301a3AcEAF007", - "WitnetBytecodesImplementation": "0xFB36b14df6D319A5A7F418C80b0700664A4f9e6a", + "WitnetBytecodesImplementation": "0x17189FaFd8Dda06ccc2086e12A11693ee552B807", "WitnetPriceFeedsImplementation": "0xef978B8CdA6464D0fBaCE5FBC8Ed7A7A8976E094", "WitnetRandomnessImplementation": "0xB4f1f8E27799256ec95C5b5A8d2A5722Bd542E69", "WitnetRequestBoardImplementation": "0x654B79823f244c2476907F21EBD20cFebC04D0A5", @@ -201,31 +201,34 @@ "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "", - "WitnetEncodingLib": "0x6F68A4d58cEd8e094b42511350527Ed628ACB970", - "WitnetBytecodesImplementation": "0x7ab66AB288A143D4e07Aff9b729165bFb71DB73a", - "WitnetPriceFeedsImplementation": "", + "WitnetErrorsLib": "0x88dB6Eb24A8A218B4B676DEC09d19bED7dB1FAA7", + "WitnetEncodingLib": "0x0401E5DdBBb68bB6c8E61d80279F38790CfB07f5", + "WitnetPriceFeedsLib": "0xeD6e685842b347cdB527a8Ad996B14c42fD7ca94", + "WitnetBytecodesImplementation": "0x29E1766C64c93d3ab883749C9f1BBd77e12a497a", + "WitnetPriceFeedsImplementation": "0x950FA00420459C64a02447509aE0a408a2d60A61", "WitnetRandomnessImplementation": "0x9597b5708CDB58fF057ca494574951Fc3d9163f7", - "WitnetRequestBoardImplementation": "", - "WitnetRequestFactoryImplementation": "0xd8875D7D3087DEec0103d47d4cE0C4a5414874E1", + "WitnetRequestBoardImplementation": "0x3C11FFe6A6764B8bbcf62226ca44bc503C697209", + "WitnetRequestFactoryImplementation": "0x692De6368d415469e59B31a2b0895b83Ed6F8a3A", "WitnetRequestRandomness": "0x34fcD46c6D97A534BdC31Eb9d1e5273298CA8034" }, "elastos.mainnet": { "WitnetProxy": "0x0000000e3a3d22d7510B36BdC88994dab11eadc8", "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", "WitnetBytecodes": "0x0000000e3a3d22d7510B36BdC88994dab11eadc8", - "WitnetPriceRouter": "0x9999999d139bdBFbF25923ba39F63bBFc7593400", + "WitnetPriceFeeds": "0x9999999d139bdBFbF25923ba39F63bBFc7593400", + "WitnetPriceRouter": "0x0Aa147F25CE8BfaA4E6B4B2CCa91f595bD732CD4", "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "", - "WitnetEncodingLib": "0x1225A47bC743199dFef9FEEf065b3B76695AaaaC", - "WitnetBytecodesImplementation": "0xF503A52bEcF03d9d5fc85459906a4d280142B1cd", - "WitnetPriceRouterImplementation": "0x0Aa147F25CE8BfaA4E6B4B2CCa91f595bD732CD4", + "WitnetErrorsLib": "0xA99B485363DBAe90D17B10F988C4e1Ae895048e0", + "WitnetEncodingLib": "0xb99FA0430C73E7B82604Aa99d351d6aFdCe46A16", + "WitnetBytecodesImplementation": "0xC467B6E0F700D3E044C9F20BB76957eEC0B33c8C", + "WitnetPriceFeedsImplementation": "0x79c27c0555C95DBfd38e97023c3257376aaa154d", "WitnetRandomnessImplementation": "0x92a68143Ee3C2527C2B07e4354efAF89fd75a359", - "WitnetRequestBoardImplementation": "", - "WitnetRequestFactoryImplementation": "0x49dbaA6eE184Da1bCAba0764B5Daa363d49b3fe5", - "WitnetRequestRandomness": "0x217C32Cf5755aB281809f29F21c107cD0E4652B3" + "WitnetRequestBoardImplementation": "0xc45c93083F7B97Cdb700D4D2ADE6a727E04793ff", + "WitnetRequestFactoryImplementation": "0x7AA219C444f68eDBD5789d89076efA8A3f09996b", + "WitnetRequestRandomness": "0x217C32Cf5755aB281809f29F21c107cD0E4652B3", + "WitnetPriceFeedsLib": "0x62a1b1D6E5bA031846894FC5C3609f586c78D23D" } }, "fuse": { @@ -357,12 +360,12 @@ "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0xb5F3c9Dc6Ca7C1078cE5c51c1cE030D6BEEd57E2", "WitnetErrorsLib": "0x7a56A80A9B169c046EdD1d8f584455a394bc9C71", - "WitnetEncodingLib": "0xB5447342cA17A40e59d410b340ba412E22e36201", + "WitnetEncodingLib": "0xE490b89AfADE571d8Afa158446C603D530608ceA", "WitnetPriceFeedsLib": "0x685528FA605c31aE076e1ee1707041B7Cb356573", - "WitnetBytecodesImplementation": "0x705E076F3387cFd59708D8D8508CECe3e1C65C87", + "WitnetBytecodesImplementation": "0xF58115533e681295CC1F07A135539E72c5116855", "WitnetRandomnessImplementation": "0x65772461641A4A6E8B10c81bae1a132E04e77262", - "WitnetRequestBoardImplementation": "0xb6E0e5a64C7c02Fa477A5254dca35ED967570DF5", - "WitnetRequestFactoryImplementation": "0x364E2b91a4C7563288C3ccF7256BA172935CC550" + "WitnetRequestBoardImplementation": "", + "WitnetRequestFactoryImplementation": "0xA9cC3101735b248964e90fA8506219A9CF0b1091" }, "moonbeam.moonriver": { "WitnetLib": "0x1D9c4a8f8B7b5F9B8e2641D81927f8F8Cc7fF079", @@ -416,12 +419,12 @@ "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0xCFf84e16db3c705aD3C6e96b5575ab9111C874B9", "WitnetErrorsLib": "0x724d8E0a9B83a3Fc1A807b91392cAF5f42233307", - "WitnetEncodingLib": "0x3E4F5AB751F3B7D8953Be20CCc3bD0A7a4dea903", + "WitnetEncodingLib": "0xE929c7Be16CD2F4587A3A6692DDD3D267BEBABa2", "WitnetPriceFeedsLib": "0x83587BcfD1f75B5D08c4e27F098F99783cc693cb", - "WitnetBytecodesImplementation": "0x1a50d6bc99f9a79e8aECFdE71c5A597ef9012C39", + "WitnetBytecodesImplementation": "0xd5Ef8E34a8e459110373eF2f8f141893921d367A", "WitnetRandomnessImplementation": "0x24Cc52D0603F161E16c3DB29Da4c2bCc07d17C4b", - "WitnetRequestBoardImplementation": "0xe0329cad0306dF321CD331C526E6Ccc67ce5c007", - "WitnetRequestFactoryImplementation": "0x4779A692aC089E02FD1301B0b53Fa1a02985a83F" + "WitnetRequestBoardImplementation": "0xfC62b6B0ec3eCF1Fa031B31b468be51E025a36f1", + "WitnetRequestFactoryImplementation": "0x16FEe4c2e8e1A69f31AAD50790015Ffb52F7a88b" }, "polygon.mainnet": { "WitnetLib": "0x1D9c4a8f8B7b5F9B8e2641D81927f8F8Cc7fF079", diff --git a/migrations/witnet.settings.js b/migrations/witnet.settings.js index 2f267a940..c44350041 100644 --- a/migrations/witnet.settings.js +++ b/migrations/witnet.settings.js @@ -329,7 +329,6 @@ module.exports = { verify: { apiUrl: "https://esc-testnet.elastos.io/api", browserURL: "https://esc-testnet.elastos.io/address", - apiKey: "D75NV1MFN41XRSE9SWV9BA3QZKUD1U9RM3", }, }, "elastos.mainnet": { @@ -340,7 +339,6 @@ module.exports = { verify: { apiUrl: "https://esc.elastos.io/api", browserURL: "https://esc.elastos.io/address", - apiKey: "D75NV1MFN41XRSE9SWV9BA3QZKUD1U9RM3", }, }, }, From eeb045bda3ff38f0dc059c1d9f89dee1f924a06a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Fri, 23 Jun 2023 09:10:58 +0200 Subject: [PATCH 06/12] feat: add boba.bnb.mainnet network settings --- migrations/witnet.settings.js | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/migrations/witnet.settings.js b/migrations/witnet.settings.js index c44350041..f8ea79bb3 100644 --- a/migrations/witnet.settings.js +++ b/migrations/witnet.settings.js @@ -205,6 +205,17 @@ module.exports = { apiKey: "MY_API_KEY", }, }, + "boba.bnb.mainnet": { + network_id: 56288, + host: "localhost", + port: 9510, + skipDryRun: true, + verify: { + apiUrl: "https://blockexplorer.bnb.boba.network/api", + browserURL: "https://blockexplorer.bnb.boba.network/", + apiKey: "MY_API_KEY", + }, + }, "boba.moonbeam.bobabase": { network_id: 1297, host: "localhost", From ef859fad4196e60c755e9ea02d80a14648c6ed63 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Fri, 23 Jun 2023 09:11:37 +0200 Subject: [PATCH 07/12] chore: deploy WSB v0.7.8-eeb045b on boba.bnb.mainnet --- README.md | 2 +- migrations/witnet.addresses.json | 19 +++++++++++++++++++ 2 files changed, 20 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 6baeb4572..e55c592f7 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ The repository also provides: - `UsingWitnet`, an inheritable abstract contract that injects methods for conveniently interacting with the WRB. - `WitnetRequest`, used as a means to encapsulate unmodifiable Witnet Data Requests. -- `WitnetRequestBase`, useful as a base contract to implement your own modifiable Witnet Data Requests. +- `WitnetRequestPrecompiled`, useful as a base contract to implement your own modifiable Witnet Data Requests. ## **WitnetProxy** diff --git a/migrations/witnet.addresses.json b/migrations/witnet.addresses.json index 5ee5b3754..47178ccbf 100644 --- a/migrations/witnet.addresses.json +++ b/migrations/witnet.addresses.json @@ -84,6 +84,25 @@ "WitnetRequestFactoryImplementation": "0x2163DBCBdbBeC066EF8d8Adab75Af8b0B9A5cfAA", "WitnetRequestRandomness": "0x620e20d91C9b0e11ecAE439E7b85138DA2a1003F" }, + "boba.bnb.mainnet": { + "WitnetBytecodes": "0x0000000e3a3d22d7510B36BdC88994dab11eadc8", + "WitnetPriceFeeds": "0x9999999d139bdBFbF25923ba39F63bBFc7593400", + "WitnetPriceRouter": "0x62a1b1D6E5bA031846894FC5C3609f586c78D23D", + "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", + "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", + "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", + "WitnetErrorsLib": "0x1225A47bC743199dFef9FEEf065b3B76695AaaaC", + "WitnetEncodingLib": "0xF503A52bEcF03d9d5fc85459906a4d280142B1cd", + "WitnetPriceFeedsLib": "0x7AA219C444f68eDBD5789d89076efA8A3f09996b", + "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", + "WitnetProxy": "0x0Dd81412825b9C3960195ab47F14dFa9Fd70e36e", + "WitnetBytecodesImplementation": "0xa239729c399c9eBae7fdc188A1Dbb2c4a06Cd4Bb", + "WitnetPriceFeedsImplementation": "0xc45c93083F7B97Cdb700D4D2ADE6a727E04793ff", + "WitnetRandomnessImplementation": "0xC467B6E0F700D3E044C9F20BB76957eEC0B33c8C", + "WitnetRequestBoardImplementation": "0xD111C0ef9A8FA71a66E37255d255abd8879D143C", + "WitnetRequestFactoryImplementation": "0x4756097b9184327713D07b3ac4C2a898468220B1", + "WitnetRequestRandomness": "0xA99B485363DBAe90D17B10F988C4e1Ae895048e0" + }, "boba.moonbeam.bobabase": { "WitnetLib": "0x02Cd4089679EAA9431a88170fd784e7dE78A2425", "WitnetPriceRouter": "0xD9465D38f50f364b3263Cb219e58d4dB2D584530", From 8389f70854cedb7d9f23c4add1584ebf8332b794 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Thu, 29 Jun 2023 12:43:57 +0200 Subject: [PATCH 08/12] feat: add settings for gnosis.testnet --- migrations/witnet.settings.js | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/migrations/witnet.settings.js b/migrations/witnet.settings.js index f8ea79bb3..66573e190 100644 --- a/migrations/witnet.settings.js +++ b/migrations/witnet.settings.js @@ -366,6 +366,19 @@ module.exports = { }, }, }, + gnosis: { + "gnosis.testnet": { + host: "localhost", + port: 8509, + network_id: 10200, + skipDryRun: true, + verify: { + apiUrl: "https://blockscout.com/gnosis/chiado/api", + browserURL: "https://blockscout.com/gnosis/chiado/", + apiKey: "MY_API_KEY", + }, + }, + }, harmony: { "harmony.testnet#0": { host: "localhost", From a7f40ec7b839b2566d213f2795fc3b72e0b95ae3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Thu, 29 Jun 2023 12:46:21 +0200 Subject: [PATCH 09/12] chore: deploy WSB 0.7.8 on gnosis.testnet --- migrations/witnet.addresses.json | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/migrations/witnet.addresses.json b/migrations/witnet.addresses.json index 47178ccbf..f000013e3 100644 --- a/migrations/witnet.addresses.json +++ b/migrations/witnet.addresses.json @@ -270,6 +270,27 @@ "WitnetRequestRandomness": "0x6dc0E2AC80550F901cd4d5F5a4C48333A0ca97Ee" } }, + "gnosis": { + "gnosis.testnet": { + "WitnetBytecodes": "0x0000000e3a3d22d7510B36BdC88994dab11eadc8", + "WitnetPriceFeeds": "0x9999999d139bdBFbF25923ba39F63bBFc7593400", + "WitnetPriceRouter": "0xA8767A6EA3099De344499B35f725A38E3cD15562", + "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", + "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", + "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", + "WitnetErrorsLib": "0xf6d52770453166de85B6B6260Cf22196bC460E88", + "WitnetEncodingLib": "0xc71A87657b13A370594967A04b4301a3AcEAF007", + "WitnetPriceFeedsLib": "0x620e20d91C9b0e11ecAE439E7b85138DA2a1003F", + "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", + "WitnetProxy": "0x1b91eAB33362f10A5F803Fe3f0d181F42caFaac3", + "WitnetBytecodesImplementation": "0xa45206cC3Ae76630Cc4D47A730590Ff9B6d8Ee54", + "WitnetPriceFeedsImplementation": "0xB4f1f8E27799256ec95C5b5A8d2A5722Bd542E69", + "WitnetRandomnessImplementation": "0x4874cb1732eE1167A006E0Ab047D940ACF04D771", + "WitnetRequestBoardImplementation": "0x60768ce66aF2f3957e7280c6CfC4ab9c575a7FCF", + "WitnetRequestFactoryImplementation": "0x4374a050f808d1FF18bCcf73270daE3EdF8D0865", + "WitnetRequestRandomness": "0x65772461641A4A6E8B10c81bae1a132E04e77262" + } + }, "harmony": { "harmony.testnet#0": { "WitnetLib": "0x315cfa2F1108d1B490302d79AB4a5A99452e5800", From dc1dd8ba6f1e7a7863801b72b2e42aa2def2cf67 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 25 Jul 2023 12:15:47 +0200 Subject: [PATCH 10/12] fix(libs): string replacements in cbor maps --- contracts/libs/WitnetBuffer.sol | 26 +++++++++++++++++++----- contracts/libs/WitnetEncodingLib.sol | 20 ++++++++++--------- test/TestWitnetBuffer.sol | 30 ++++++++++++++-------------- 3 files changed, 47 insertions(+), 29 deletions(-) diff --git a/contracts/libs/WitnetBuffer.sol b/contracts/libs/WitnetBuffer.sol index 0c66fdeb1..ba3a8037d 100644 --- a/contracts/libs/WitnetBuffer.sol +++ b/contracts/libs/WitnetBuffer.sol @@ -523,13 +523,15 @@ library WitnetBuffer { } } - /// @notice Replace bytecode indexed wildcards by correspondent string. + /// @notice Replace bytecode indexed wildcards by correspondent substrings. /// @dev Wildcard format: "\#\", with # in ["0".."9"]. /// @param input Bytes array containing strings. - /// @param args String values for replacing existing indexed wildcards in input. + /// @param args Array of substring values for replacing indexed wildcards. + /// @return output Resulting bytes array after replacing all wildcards. + /// @return hits Total number of replaced wildcards. function replace(bytes memory input, string[] memory args) internal pure - returns (bytes memory output) + returns (bytes memory output, uint hits) { uint ix = 0; uint lix = 0; uint inputLength; @@ -541,7 +543,7 @@ library WitnetBuffer { uint sourcePointer; if (input.length < 3) { - return input; + return (input, 0); } assembly { @@ -592,6 +594,7 @@ library WitnetBuffer { outputPointer += sourceLength; ix += 3; lix = ix; + hits ++; } else { ix ++; } @@ -615,10 +618,23 @@ library WitnetBuffer { } } else { - return input; + return (input, 0); } } + /// @notice Replace string indexed wildcards by correspondent substrings. + /// @dev Wildcard format: "\#\", with # in ["0".."9"]. + /// @param input String potentially containing wildcards. + /// @param args Array of substring values for replacing indexed wildcards. + /// @return output Resulting string after replacing all wildcards. + function replace(string memory input, string[] memory args) + internal pure + returns (string memory) + { + (bytes memory _outputBytes, ) = replace(bytes(input), args); + return string(_outputBytes); + } + /// @notice Move the inner cursor of the buffer to a relative or absolute position. /// @param buffer An instance of `Buffer`. /// @param offset How many bytes to move the cursor forward. diff --git a/contracts/libs/WitnetEncodingLib.sol b/contracts/libs/WitnetEncodingLib.sol index ef867ced5..081d6d2e5 100644 --- a/contracts/libs/WitnetEncodingLib.sol +++ b/contracts/libs/WitnetEncodingLib.sol @@ -291,8 +291,10 @@ library WitnetEncodingLib { while (!cbor.eof()) { if (cbor.majorType == WitnetCBOR.MAJOR_TYPE_STRING) { _replaceCborWildcards(cbor, args); + cbor = cbor.settle(); + } else { + cbor = cbor.skip().settle(); } - cbor = cbor.skip().settle(); } return cbor.buffer.data; } @@ -300,8 +302,8 @@ library WitnetEncodingLib { function replaceWildcards(WitnetV2.RadonRetrieval memory self, string[] memory args) public pure { - self.url = string (WitnetBuffer.replace(bytes(self.url), args)); - self.body = string(WitnetBuffer.replace(bytes(self.body), args)); + self.url = WitnetBuffer.replace(self.url, args); + self.body = WitnetBuffer.replace(self.body, args); self.script = replaceCborStringsFromBytes(self.script, args); } @@ -482,16 +484,16 @@ library WitnetEncodingLib { uint _rewind = self.len; uint _start = self.buffer.cursor; bytes memory _peeks = bytes(self.readString()); - uint _dataLength = _peeks.length + _rewind; - bytes memory _pokes = WitnetBuffer.replace(_peeks, args); - if (keccak256(_pokes) != keccak256(bytes(_peeks))) { + (bytes memory _pokes, uint _replacements) = WitnetBuffer.replace(_peeks, args); + if (_replacements > 0) { + bytes memory _encodedPokes = encode(string(_pokes)); self.buffer.cursor = _start - _rewind; self.buffer.mutate( - _dataLength, - encode(string(_pokes)) + _peeks.length + _rewind, + _encodedPokes ); + self.buffer.cursor += _encodedPokes.length; } - self.buffer.cursor = _start; } diff --git a/test/TestWitnetBuffer.sol b/test/TestWitnetBuffer.sol index b0c9c5e74..aa0dc5cc5 100644 --- a/test/TestWitnetBuffer.sol +++ b/test/TestWitnetBuffer.sol @@ -88,10 +88,10 @@ contract TestWitnetBuffer { string[] memory args = new string[](2); args[0] = "https://api.whatever.com/"; args[1] = "1"; - bytes memory phrase = WitnetBuffer.replace(bytes(input), args); - emit Log(string(phrase), phrase.length); + string memory phrase = WitnetBuffer.replace(input, args); + emit Log(phrase, bytes(phrase).length); Assert.equal( - keccak256(phrase), + keccak256(bytes(phrase)), keccak256(bytes("https://api.whatever.com//image/1?digest=sha-256")), "String replacement not good :/" ); @@ -101,10 +101,10 @@ contract TestWitnetBuffer { string memory input = "In a village of La Mancha, the name of which I have no desire to call to mind, there lived not long since one of those gentlemen that keep a lance in the lance-rack, an old buckler, a lean hack, and a greyhound for coursing"; string[] memory args = new string[](1); args[0] = "Don Quixote"; - bytes memory phrase = WitnetBuffer.replace(bytes(input), args); - emit Log(string(phrase), phrase.length); + string memory phrase = WitnetBuffer.replace(input, args); + emit Log(phrase, bytes(phrase).length); Assert.equal( - keccak256(phrase), + keccak256(bytes(phrase)), keccak256(bytes(input)), "String replacement not good :/" ); @@ -114,10 +114,10 @@ contract TestWitnetBuffer { string memory input = "\\0\\"; string[] memory args = new string[](1); args[0] = "Hello!"; - bytes memory phrase = WitnetBuffer.replace(bytes(input), args); - emit Log(string(phrase), phrase.length); + string memory phrase = WitnetBuffer.replace(input, args); + emit Log(phrase, bytes(phrase).length); Assert.equal( - keccak256(phrase), + keccak256(bytes(phrase)), keccak256(bytes("Hello!")), "String replacement not good :/" ); @@ -129,10 +129,10 @@ contract TestWitnetBuffer { args[0] = "Hello"; args[1] = "decentralized"; args[2] = "world"; - bytes memory phrase = WitnetBuffer.replace(bytes(input), args); - emit Log(string(phrase), phrase.length); + string memory phrase = WitnetBuffer.replace(input, args); + emit Log(phrase, bytes(phrase).length); Assert.equal( - keccak256(phrase), + keccak256(bytes(phrase)), keccak256(bytes("Test: Hello decentralized world!")), "String replacement not good :/" ); @@ -144,10 +144,10 @@ contract TestWitnetBuffer { args[2] = "Hello"; args[0] = "decentralized"; args[3] = "world"; - bytes memory phrase = WitnetBuffer.replace(bytes(input), args); - emit Log(string(phrase), phrase.length); + string memory phrase = WitnetBuffer.replace(input, args); + emit Log(phrase, bytes(phrase).length); Assert.equal( - keccak256(phrase), + keccak256(bytes(phrase)), keccak256(bytes("Test: Hello decentralized world!")), "String replacement not good :/" ); From 9ca2a05255024c161c803aa115d9d73bcdacad37 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 25 Jul 2023 12:21:32 +0200 Subject: [PATCH 11/12] fix(libs): reading large float16 values --- contracts/libs/WitnetBuffer.sol | 8 ++++---- test/TestWitnetCBOR.sol | 8 ++++---- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/contracts/libs/WitnetBuffer.sol b/contracts/libs/WitnetBuffer.sol index ba3a8037d..f68ec996e 100644 --- a/contracts/libs/WitnetBuffer.sol +++ b/contracts/libs/WitnetBuffer.sol @@ -235,17 +235,17 @@ library WitnetBuffer { } // Compute `2 ^ exponent ยท (1 + fraction / 1024)` if (exponent >= 0) { - result = int32( + result = int32(int( int(1 << uint256(int256(exponent))) * 10000 * fraction - ) >> 10; + ) >> 10); } else { - result = int32( + result = int32(int( int(fraction) * 10000 / int(1 << uint(int(- exponent))) - ) >> 10; + ) >> 10); } // Make the result negative if the sign bit is not 0 if (sign != 0) { diff --git a/test/TestWitnetCBOR.sol b/test/TestWitnetCBOR.sol index 24fe980c3..5d69e2e53 100644 --- a/test/TestWitnetCBOR.sol +++ b/test/TestWitnetCBOR.sol @@ -4,8 +4,8 @@ pragma solidity >=0.7.0 <0.9.0; pragma experimental ABIEncoderV2; import "truffle/Assert.sol"; +import "../contracts/libs/Witnet.sol"; import "../contracts/libs/WitnetCBOR.sol"; -import "../contracts/libs/WitnetLib.sol"; contract TestWitnetCBOR { @@ -123,7 +123,7 @@ contract TestWitnetCBOR { function testBytes32DecodeValueFrom31bytes() external { bytes memory encoded = hex"581f01020304050607080910111213141516171819202122232425262728293031"; - bytes32 decoded = WitnetLib.toBytes32(WitnetCBOR.readBytes(WitnetCBOR.fromBytes(encoded))); + bytes32 decoded = Witnet.toBytes32(WitnetCBOR.readBytes(WitnetCBOR.fromBytes(encoded))); bytes32 expected = 0x0102030405060708091011121314151617181920212223242526272829303100; Assert.equal( decoded, @@ -134,7 +134,7 @@ contract TestWitnetCBOR { function testBytes32DecodeValueFrom32bytes() external { bytes memory encoded = hex"58200102030405060708091011121314151617181920212223242526272829303132"; - bytes32 decoded = WitnetLib.toBytes32(WitnetCBOR.readBytes(WitnetCBOR.fromBytes(encoded))); + bytes32 decoded = Witnet.toBytes32(WitnetCBOR.readBytes(WitnetCBOR.fromBytes(encoded))); bytes32 expected = 0x0102030405060708091011121314151617181920212223242526272829303132; Assert.equal( decoded, @@ -145,7 +145,7 @@ contract TestWitnetCBOR { function testBytes32DecodeValueFrom33bytes() external { bytes memory encoded = hex"5821010203040506070809101112131415161718192021222324252627282930313233"; - bytes32 decoded = WitnetLib.toBytes32(WitnetCBOR.readBytes(WitnetCBOR.fromBytes(encoded))); + bytes32 decoded = Witnet.toBytes32(WitnetCBOR.readBytes(WitnetCBOR.fromBytes(encoded))); bytes32 expected = 0x0102030405060708091011121314151617181920212223242526272829303132; Assert.equal( decoded, From 68936d80623d597555f34920168cefd293691df9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Guillermo=20D=C3=ADaz?= Date: Tue, 25 Jul 2023 12:34:21 +0200 Subject: [PATCH 12/12] chore: bump package version to 0.7.9 --- migrations/witnet.addresses.json | 70 ++++++++++++++++---------------- package.json | 2 +- 2 files changed, 36 insertions(+), 36 deletions(-) diff --git a/migrations/witnet.addresses.json b/migrations/witnet.addresses.json index f000013e3..70e4938da 100644 --- a/migrations/witnet.addresses.json +++ b/migrations/witnet.addresses.json @@ -42,7 +42,7 @@ "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0xF1Aba51c5097487a62DA9c72fb9Aa7B0c98676C1", "WitnetErrorsLib": "", - "WitnetEncodingLib": "0x30e7D86b3DcdC0CC90509b1F7C27eA8e5481FAc5", + "WitnetEncodingLib": "", "WitnetBytecodesImplementation": "0x5832e99368877a63dd1c2cea941C2b43E1F6b16A", "WitnetPriceFeedsImplementation": "", "WitnetRandomnessImplementation": "0xa239729c399c9eBae7fdc188A1Dbb2c4a06Cd4Bb", @@ -72,15 +72,15 @@ "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "0x1b91eAB33362f10A5F803Fe3f0d181F42caFaac3", - "WitnetEncodingLib": "0x49d3f1C57C320f833FF96bd9786Ae7DB8854B680", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", "WitnetPriceFeedsLib": "0x8684d396366C21AA01B120F69df2070f840aC134", "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", "WitnetProxy": "0xc71A87657b13A370594967A04b4301a3AcEAF007", - "WitnetBytecodesImplementation": "0x17189FaFd8Dda06ccc2086e12A11693ee552B807", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "0xef978B8CdA6464D0fBaCE5FBC8Ed7A7A8976E094", "WitnetRandomnessImplementation": "0xB4f1f8E27799256ec95C5b5A8d2A5722Bd542E69", - "WitnetRequestBoardImplementation": "0x654B79823f244c2476907F21EBD20cFebC04D0A5", + "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0x2163DBCBdbBeC066EF8d8Adab75Af8b0B9A5cfAA", "WitnetRequestRandomness": "0x620e20d91C9b0e11ecAE439E7b85138DA2a1003F" }, @@ -91,15 +91,15 @@ "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "0x1225A47bC743199dFef9FEEf065b3B76695AaaaC", - "WitnetEncodingLib": "0xF503A52bEcF03d9d5fc85459906a4d280142B1cd", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", "WitnetPriceFeedsLib": "0x7AA219C444f68eDBD5789d89076efA8A3f09996b", "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", "WitnetProxy": "0x0Dd81412825b9C3960195ab47F14dFa9Fd70e36e", - "WitnetBytecodesImplementation": "0xa239729c399c9eBae7fdc188A1Dbb2c4a06Cd4Bb", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "0xc45c93083F7B97Cdb700D4D2ADE6a727E04793ff", "WitnetRandomnessImplementation": "0xC467B6E0F700D3E044C9F20BB76957eEC0B33c8C", - "WitnetRequestBoardImplementation": "0xD111C0ef9A8FA71a66E37255d255abd8879D143C", + "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0x4756097b9184327713D07b3ac4C2a898468220B1", "WitnetRequestRandomness": "0xA99B485363DBAe90D17B10F988C4e1Ae895048e0" }, @@ -220,13 +220,13 @@ "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "0x88dB6Eb24A8A218B4B676DEC09d19bED7dB1FAA7", - "WitnetEncodingLib": "0x0401E5DdBBb68bB6c8E61d80279F38790CfB07f5", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", "WitnetPriceFeedsLib": "0xeD6e685842b347cdB527a8Ad996B14c42fD7ca94", - "WitnetBytecodesImplementation": "0x29E1766C64c93d3ab883749C9f1BBd77e12a497a", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "0x950FA00420459C64a02447509aE0a408a2d60A61", "WitnetRandomnessImplementation": "0x9597b5708CDB58fF057ca494574951Fc3d9163f7", - "WitnetRequestBoardImplementation": "0x3C11FFe6A6764B8bbcf62226ca44bc503C697209", + "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0x692De6368d415469e59B31a2b0895b83Ed6F8a3A", "WitnetRequestRandomness": "0x34fcD46c6D97A534BdC31Eb9d1e5273298CA8034" }, @@ -239,12 +239,12 @@ "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "0xA99B485363DBAe90D17B10F988C4e1Ae895048e0", - "WitnetEncodingLib": "0xb99FA0430C73E7B82604Aa99d351d6aFdCe46A16", - "WitnetBytecodesImplementation": "0xC467B6E0F700D3E044C9F20BB76957eEC0B33c8C", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "0x79c27c0555C95DBfd38e97023c3257376aaa154d", "WitnetRandomnessImplementation": "0x92a68143Ee3C2527C2B07e4354efAF89fd75a359", - "WitnetRequestBoardImplementation": "0xc45c93083F7B97Cdb700D4D2ADE6a727E04793ff", + "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0x7AA219C444f68eDBD5789d89076efA8A3f09996b", "WitnetRequestRandomness": "0x217C32Cf5755aB281809f29F21c107cD0E4652B3", "WitnetPriceFeedsLib": "0x62a1b1D6E5bA031846894FC5C3609f586c78D23D" @@ -261,8 +261,8 @@ "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetErrorsLib": "", - "WitnetEncodingLib": "0xB5447342cA17A40e59d410b340ba412E22e36201", - "WitnetBytecodesImplementation": "0x705E076F3387cFd59708D8D8508CECe3e1C65C87", + "WitnetEncodingLib": "", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "", "WitnetRandomnessImplementation": "0x7A6C2Aad6b4b08De09477D0F663b8f90b0db9662", "WitnetRequestBoardImplementation": "", @@ -278,15 +278,15 @@ "WitnetRandomness": "0x88888885966F8F77cC6E797aE263C4d091e44A55", "WitnetRequestBoard": "0x777777772C24e6CD34B464D1d71616C444254537", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", - "WitnetErrorsLib": "0xf6d52770453166de85B6B6260Cf22196bC460E88", - "WitnetEncodingLib": "0xc71A87657b13A370594967A04b4301a3AcEAF007", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", "WitnetPriceFeedsLib": "0x620e20d91C9b0e11ecAE439E7b85138DA2a1003F", "Create2Factory": "0xDe312a6f7fA35320E8DD109c8ea42e82806DC45b", "WitnetProxy": "0x1b91eAB33362f10A5F803Fe3f0d181F42caFaac3", - "WitnetBytecodesImplementation": "0xa45206cC3Ae76630Cc4D47A730590Ff9B6d8Ee54", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "0xB4f1f8E27799256ec95C5b5A8d2A5722Bd542E69", "WitnetRandomnessImplementation": "0x4874cb1732eE1167A006E0Ab047D940ACF04D771", - "WitnetRequestBoardImplementation": "0x60768ce66aF2f3957e7280c6CfC4ab9c575a7FCF", + "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0x4374a050f808d1FF18bCcf73270daE3EdF8D0865", "WitnetRequestRandomness": "0x65772461641A4A6E8B10c81bae1a132E04e77262" } @@ -374,8 +374,8 @@ "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0x6dc0E2AC80550F901cd4d5F5a4C48333A0ca97Ee", "WitnetErrorsLib": "", - "WitnetEncodingLib": "0xB5447342cA17A40e59d410b340ba412E22e36201", - "WitnetBytecodesImplementation": "0x705E076F3387cFd59708D8D8508CECe3e1C65C87", + "WitnetEncodingLib": "", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "", "WitnetRandomnessImplementation": "0x7A6C2Aad6b4b08De09477D0F663b8f90b0db9662", "WitnetRequestBoardImplementation": "", @@ -399,10 +399,10 @@ "WitnetRequestBoard": "0x02Cd4089679EAA9431a88170fd784e7dE78A2425", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0xb5F3c9Dc6Ca7C1078cE5c51c1cE030D6BEEd57E2", - "WitnetErrorsLib": "0x7a56A80A9B169c046EdD1d8f584455a394bc9C71", - "WitnetEncodingLib": "0xE490b89AfADE571d8Afa158446C603D530608ceA", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", "WitnetPriceFeedsLib": "0x685528FA605c31aE076e1ee1707041B7Cb356573", - "WitnetBytecodesImplementation": "0xF58115533e681295CC1F07A135539E72c5116855", + "WitnetBytecodesImplementation": "", "WitnetRandomnessImplementation": "0x65772461641A4A6E8B10c81bae1a132E04e77262", "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0xA9cC3101735b248964e90fA8506219A9CF0b1091" @@ -458,12 +458,12 @@ "WitnetRequestBoard": "0x58D8ECe142c60f5707594a7C1D90e46eAE5AF431", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0xCFf84e16db3c705aD3C6e96b5575ab9111C874B9", - "WitnetErrorsLib": "0x724d8E0a9B83a3Fc1A807b91392cAF5f42233307", - "WitnetEncodingLib": "0xE929c7Be16CD2F4587A3A6692DDD3D267BEBABa2", + "WitnetErrorsLib": "", + "WitnetEncodingLib": "", "WitnetPriceFeedsLib": "0x83587BcfD1f75B5D08c4e27F098F99783cc693cb", - "WitnetBytecodesImplementation": "0xd5Ef8E34a8e459110373eF2f8f141893921d367A", + "WitnetBytecodesImplementation": "", "WitnetRandomnessImplementation": "0x24Cc52D0603F161E16c3DB29Da4c2bCc07d17C4b", - "WitnetRequestBoardImplementation": "0xfC62b6B0ec3eCF1Fa031B31b468be51E025a36f1", + "WitnetRequestBoardImplementation": "", "WitnetRequestFactoryImplementation": "0x16FEe4c2e8e1A69f31AAD50790015Ffb52F7a88b" }, "polygon.mainnet": { @@ -483,8 +483,8 @@ "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetRequestRandomness": "0xC768fD0A0EC5B788524227abEBf4Da021e85908c", "WitnetErrorsLib": "", - "WitnetEncodingLib": "0x98DbB216138aA6a0b3ff2ae9bBdeC254398E5B2E", - "WitnetBytecodesImplementation": "0xFB36b14df6D319A5A7F418C80b0700664A4f9e6a", + "WitnetEncodingLib": "", + "WitnetBytecodesImplementation": "", "WitnetPriceFeedsImplementation": "", "WitnetRandomnessImplementation": "0x3f189fAc162d3CC6d84EF72c8177afAd8f3DBeE1", "WitnetRequestBoardImplementation": "", @@ -517,7 +517,7 @@ "WitnetRequestBoardBypassed": "0x0000007F26760C151AC86695D5846D21e7828B67", "WitnetRequestFactory": "0x1111111FDE7dC956E3d7922Bc779D9E2349Afb63", "WitnetErrorsLib": "", - "WitnetEncodingLib": "0xd0f725Bf11bA75D291506d396FbcbeCAb5384e95", + "WitnetEncodingLib": "", "WitnetBytecodesImplementation": "0x71D5D7F2ed2436062946727DB84E44588F765D02", "WitnetPriceFeedsImplementation": "", "WitnetRandomnessImplementation": "0x3caF71061A07A77347d5c01Fb37b53D5B3865B9A", diff --git a/package.json b/package.json index 24e1799c6..2db88b146 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "witnet-solidity-bridge", - "version": "0.7.8", + "version": "0.7.9", "description": "Witnet Solidity Bridge contracts for EVM-compatible chains", "main": "", "scripts": {