mirror of
https://github.com/ethereum/solidity
synced 2023-10-03 13:03:40 +00:00
Merge pull request #8843 from ethereum/deprecate-now
[BREAKING] Deprecate keyword now
This commit is contained in:
commit
5566cd9f74
@ -3,6 +3,7 @@
|
||||
Breaking changes:
|
||||
* Type Checker: Disallow virtual for library functions.
|
||||
* Deprecated dot syntax for `value` and `gas`.
|
||||
* Deprecated the identifier `now`.
|
||||
|
||||
Language Features:
|
||||
|
||||
|
@ -15,3 +15,4 @@ This section gives detailed instructions on how to update prior code for every b
|
||||
|
||||
* Change ``f.value(...)()`` to ``f{value: ...}()``. Similarly ``(new C).value(...)()`` to
|
||||
``(new C){value: ...}()`` and ``f.gas(...)()`` to ``f{gas: ...}()``.
|
||||
* Change ``now`` to ``block.timestamp``.
|
||||
|
@ -67,7 +67,7 @@ The following is the order of precedence for operators, listed in order of evalu
|
||||
| *15* | Comma operator | ``,`` |
|
||||
+------------+-------------------------------------+--------------------------------------------+
|
||||
|
||||
.. index:: assert, block, coinbase, difficulty, number, block;number, timestamp, block;timestamp, msg, data, gas, sender, value, now, gas price, origin, revert, require, keccak256, ripemd160, sha256, ecrecover, addmod, mulmod, cryptography, this, super, selfdestruct, balance, send
|
||||
.. index:: assert, block, coinbase, difficulty, number, block;number, timestamp, block;timestamp, msg, data, gas, sender, value, gas price, origin, revert, require, keccak256, ripemd160, sha256, ecrecover, addmod, mulmod, cryptography, this, super, selfdestruct, balance, send
|
||||
|
||||
Global Variables
|
||||
================
|
||||
@ -91,7 +91,6 @@ Global Variables
|
||||
- ``msg.data`` (``bytes``): complete calldata
|
||||
- ``msg.sender`` (``address payable``): sender of the message (current call)
|
||||
- ``msg.value`` (``uint``): number of wei sent with the message
|
||||
- ``now`` (``uint``): current block timestamp (alias for ``block.timestamp``)
|
||||
- ``tx.gasprice`` (``uint``): gas price of the transaction
|
||||
- ``tx.origin`` (``address payable``): sender of the transaction (full call chain)
|
||||
- ``assert(bool condition)``: abort execution and revert state changes if condition is ``false`` (use for internal error)
|
||||
@ -124,7 +123,7 @@ Global Variables
|
||||
- ``type(I).interfaceId`` (``bytes4``): value containing the EIP-165 interface identifier of the given interface, see :ref:`Type Information<meta-type>`.
|
||||
|
||||
.. note::
|
||||
Do not rely on ``block.timestamp``, ``now`` and ``blockhash`` as a source of randomness,
|
||||
Do not rely on ``block.timestamp`` or ``blockhash`` as a source of randomness,
|
||||
unless you know what you are doing.
|
||||
|
||||
Both the timestamp and the block hash can be influenced by miners to some degree.
|
||||
@ -144,6 +143,8 @@ Global Variables
|
||||
In version 0.5.0, the following aliases were removed: ``suicide`` as alias for ``selfdestruct``,
|
||||
``msg.gas`` as alias for ``gasleft``, ``block.blockhash`` as alias for ``blockhash`` and
|
||||
``sha3`` as alias for ``keccak256``.
|
||||
.. note::
|
||||
In version 0.7.0, the alias ``now`` (for ``block.timestamp``) was removed.
|
||||
|
||||
.. index:: visibility, public, private, external, internal
|
||||
|
||||
|
@ -128,7 +128,7 @@ restrictions highly readable.
|
||||
// phase, where `msg.sender` is the account
|
||||
// creating this contract.
|
||||
address public owner = msg.sender;
|
||||
uint public creationTime = now;
|
||||
uint public creationTime = block.timestamp;
|
||||
|
||||
// Modifiers can be used to change
|
||||
// the body of a function.
|
||||
@ -159,7 +159,7 @@ restrictions highly readable.
|
||||
|
||||
modifier onlyAfter(uint _time) {
|
||||
require(
|
||||
now >= _time,
|
||||
block.timestamp >= _time,
|
||||
"Function called too early."
|
||||
);
|
||||
_;
|
||||
@ -287,7 +287,7 @@ function finishes.
|
||||
// This is the current stage.
|
||||
Stages public stage = Stages.AcceptingBlindedBids;
|
||||
|
||||
uint public creationTime = now;
|
||||
uint public creationTime = block.timestamp;
|
||||
|
||||
modifier atStage(Stages _stage) {
|
||||
require(
|
||||
@ -306,10 +306,10 @@ function finishes.
|
||||
// will not take the new stage into account.
|
||||
modifier timedTransitions() {
|
||||
if (stage == Stages.AcceptingBlindedBids &&
|
||||
now >= creationTime + 10 days)
|
||||
block.timestamp >= creationTime + 10 days)
|
||||
nextStage();
|
||||
if (stage == Stages.RevealBids &&
|
||||
now >= creationTime + 12 days)
|
||||
block.timestamp >= creationTime + 12 days)
|
||||
nextStage();
|
||||
// The other stages transition by transaction
|
||||
_;
|
||||
|
@ -44,7 +44,7 @@ Constant
|
||||
|
||||
For ``constant`` variables, the value has to be a constant at compile time and it has to be
|
||||
assigned where the variable is declared. Any expression
|
||||
that accesses storage, blockchain data (e.g. ``now``, ``address(this).balance`` or
|
||||
that accesses storage, blockchain data (e.g. ``block.timestamp``, ``address(this).balance`` or
|
||||
``block.number``) or
|
||||
execution data (``msg.value`` or ``gasleft()``) or makes calls to external contracts is disallowed. Expressions
|
||||
that might have a side-effect on memory allocation are allowed, but those that
|
||||
|
@ -146,7 +146,7 @@ The following statements are considered modifying the state:
|
||||
|
||||
contract C {
|
||||
function f(uint a, uint b) public view returns (uint) {
|
||||
return a * (b + 42) + now;
|
||||
return a * (b + 42) + block.timestamp;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -61,7 +61,7 @@ to receive their money - contracts cannot activate themselves.
|
||||
address payable _beneficiary
|
||||
) public {
|
||||
beneficiary = _beneficiary;
|
||||
auctionEndTime = now + _biddingTime;
|
||||
auctionEndTime = block.timestamp + _biddingTime;
|
||||
}
|
||||
|
||||
/// Bid on the auction with the value sent
|
||||
@ -78,7 +78,7 @@ to receive their money - contracts cannot activate themselves.
|
||||
// Revert the call if the bidding
|
||||
// period is over.
|
||||
require(
|
||||
now <= auctionEndTime,
|
||||
block.timestamp <= auctionEndTime,
|
||||
"Auction already ended."
|
||||
);
|
||||
|
||||
@ -140,7 +140,7 @@ to receive their money - contracts cannot activate themselves.
|
||||
// external contracts.
|
||||
|
||||
// 1. Conditions
|
||||
require(now >= auctionEndTime, "Auction not yet ended.");
|
||||
require(block.timestamp >= auctionEndTime, "Auction not yet ended.");
|
||||
require(!ended, "auctionEnd has already been called.");
|
||||
|
||||
// 2. Effects
|
||||
@ -211,8 +211,8 @@ invalid bids.
|
||||
/// functions. `onlyBefore` is applied to `bid` below:
|
||||
/// The new function body is the modifier's body where
|
||||
/// `_` is replaced by the old function body.
|
||||
modifier onlyBefore(uint _time) { require(now < _time); _; }
|
||||
modifier onlyAfter(uint _time) { require(now > _time); _; }
|
||||
modifier onlyBefore(uint _time) { require(block.timestamp < _time); _; }
|
||||
modifier onlyAfter(uint _time) { require(block.timestamp > _time); _; }
|
||||
|
||||
constructor(
|
||||
uint _biddingTime,
|
||||
@ -220,7 +220,7 @@ invalid bids.
|
||||
address payable _beneficiary
|
||||
) public {
|
||||
beneficiary = _beneficiary;
|
||||
biddingEnd = now + _biddingTime;
|
||||
biddingEnd = block.timestamp + _biddingTime;
|
||||
revealEnd = biddingEnd + _revealTime;
|
||||
}
|
||||
|
||||
@ -326,4 +326,4 @@ invalid bids.
|
||||
highestBidder = bidder;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -351,7 +351,7 @@ The full contract
|
||||
{
|
||||
sender = msg.sender;
|
||||
recipient = _recipient;
|
||||
expiration = now + duration;
|
||||
expiration = block.timestamp + duration;
|
||||
}
|
||||
|
||||
/// the recipient can close the channel at any time by presenting a
|
||||
@ -376,7 +376,7 @@ The full contract
|
||||
/// if the timeout is reached without the recipient closing the channel,
|
||||
/// then the Ether is released back to the sender.
|
||||
function claimTimeout() public {
|
||||
require(now >= expiration);
|
||||
require(block.timestamp >= expiration);
|
||||
selfdestruct(sender);
|
||||
}
|
||||
|
||||
|
@ -47,7 +47,7 @@ These suffixes cannot be applied to variables. For example, if you want to
|
||||
interpret a function parameter in days, you can in the following way::
|
||||
|
||||
function f(uint start, uint daysAfter) public {
|
||||
if (now >= start + daysAfter * 1 days) {
|
||||
if (block.timestamp >= start + daysAfter * 1 days) {
|
||||
// ...
|
||||
}
|
||||
}
|
||||
@ -61,7 +61,7 @@ There are special variables and functions which always exist in the global
|
||||
namespace and are mainly used to provide information about the blockchain
|
||||
or are general-use utility functions.
|
||||
|
||||
.. index:: abi, block, coinbase, difficulty, encode, number, block;number, timestamp, block;timestamp, msg, data, gas, sender, value, now, gas price, origin
|
||||
.. index:: abi, block, coinbase, difficulty, encode, number, block;number, timestamp, block;timestamp, msg, data, gas, sender, value, gas price, origin
|
||||
|
||||
|
||||
Block and Transaction Properties
|
||||
@ -78,7 +78,6 @@ Block and Transaction Properties
|
||||
- ``msg.sender`` (``address payable``): sender of the message (current call)
|
||||
- ``msg.sig`` (``bytes4``): first four bytes of the calldata (i.e. function identifier)
|
||||
- ``msg.value`` (``uint``): number of wei sent with the message
|
||||
- ``now`` (``uint``): current block timestamp (alias for ``block.timestamp``)
|
||||
- ``tx.gasprice`` (``uint``): gas price of the transaction
|
||||
- ``tx.origin`` (``address payable``): sender of the transaction (full call chain)
|
||||
|
||||
@ -88,7 +87,7 @@ Block and Transaction Properties
|
||||
This includes calls to library functions.
|
||||
|
||||
.. note::
|
||||
Do not rely on ``block.timestamp``, ``now`` and ``blockhash`` as a source of randomness,
|
||||
Do not rely on ``block.timestamp`` or ``blockhash`` as a source of randomness,
|
||||
unless you know what you are doing.
|
||||
|
||||
Both the timestamp and the block hash can be influenced by miners to some degree.
|
||||
@ -112,6 +111,9 @@ Block and Transaction Properties
|
||||
The function ``gasleft`` was previously known as ``msg.gas``, which was deprecated in
|
||||
version 0.4.21 and removed in version 0.5.0.
|
||||
|
||||
.. note::
|
||||
In version 0.7.0, the alias ``now`` (for ``block.timestamp``) was removed.
|
||||
|
||||
.. index:: abi, encoding, packed
|
||||
|
||||
ABI Encoding and Decoding Functions
|
||||
@ -327,4 +329,3 @@ for an interface type ``I``:
|
||||
A ``bytes4`` value containing the `EIP-165 <https://eips.ethereum.org/EIPS/eip-165>`_
|
||||
interface identifier of the given interface ``I``. This identifier is defined as the ``XOR`` of all
|
||||
function selectors defined within the interface itself - excluding all inherited functions.
|
||||
|
||||
|
@ -580,6 +580,9 @@ Available upgrade modules
|
||||
| | | ``f{gas: ..., value: ...}()`` and |
|
||||
| | | ``(new C){value: ...}()``. |
|
||||
+-----------------+---------+--------------------------------------------------+
|
||||
| ``now`` | 0.7.0 | The ``now`` keyword is deprecated. Use |
|
||||
| | | ``block.timestamp`` instead. |
|
||||
+-----------------+---------+--------------------------------------------------+
|
||||
|
||||
Please read :doc:`0.5.0 release notes <050-breaking-changes>`,
|
||||
:doc:`0.6.0 release notes <060-breaking-changes>` and
|
||||
|
@ -2908,6 +2908,20 @@ bool TypeChecker::visit(Identifier const& _identifier)
|
||||
);
|
||||
}
|
||||
|
||||
if (
|
||||
MagicVariableDeclaration const* magicVar =
|
||||
dynamic_cast<MagicVariableDeclaration const*>(annotation.referencedDeclaration)
|
||||
)
|
||||
if (magicVar->type()->category() == Type::Category::Integer)
|
||||
{
|
||||
solAssert(_identifier.name() == "now", "");
|
||||
m_errorReporter
|
||||
.typeError(
|
||||
_identifier.location(),
|
||||
"\"now\" has been deprecated. Use \"block.timestamp\" instead."
|
||||
);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -69,8 +69,8 @@ contract MultiSigWalletWithDailyLimit is MultiSigWallet {
|
||||
internal
|
||||
returns (bool)
|
||||
{
|
||||
if (now > lastDay + 24 hours) {
|
||||
lastDay = now;
|
||||
if (block.timestamp > lastDay + 24 hours) {
|
||||
lastDay = block.timestamp;
|
||||
spentToday = 0;
|
||||
}
|
||||
if (spentToday + amount > dailyLimit || spentToday + amount < spentToday)
|
||||
@ -88,7 +88,7 @@ contract MultiSigWalletWithDailyLimit is MultiSigWallet {
|
||||
view
|
||||
returns (uint)
|
||||
{
|
||||
if (now > lastDay + 24 hours)
|
||||
if (block.timestamp > lastDay + 24 hours)
|
||||
return dailyLimit;
|
||||
if (dailyLimit < spentToday)
|
||||
return 0;
|
||||
|
@ -256,7 +256,7 @@ contract provider is module, safeMath, announcementTypes {
|
||||
providers[msg.sender].data[currHeight].country = country;
|
||||
providers[msg.sender].data[currHeight].info = info;
|
||||
providers[msg.sender].data[currHeight].currentRate = rate;
|
||||
providers[msg.sender].data[currHeight].create = now;
|
||||
providers[msg.sender].data[currHeight].create = block.timestamp;
|
||||
providers[msg.sender].data[currHeight].lastPaidRate = rate;
|
||||
providers[msg.sender].data[currHeight].priv = priv;
|
||||
providers[msg.sender].data[currHeight].lastSupplyID = currentSchellingRound;
|
||||
@ -436,7 +436,7 @@ contract provider is module, safeMath, announcementTypes {
|
||||
clients[msg.sender].lastSupplyID = currentSchellingRound;
|
||||
clients[msg.sender].paidUpTo = currentSchellingRound;
|
||||
clients[msg.sender].lastRate = providers[provider].data[currHeight].currentRate;
|
||||
clients[msg.sender].providerConnected = now;
|
||||
clients[msg.sender].providerConnected = block.timestamp;
|
||||
emit ENewClient(msg.sender, provider, currHeight, bal);
|
||||
}
|
||||
function partProvider() isReady external {
|
||||
|
@ -55,7 +55,7 @@ contract Campaign {
|
||||
}
|
||||
|
||||
modifier timedTransitions() {
|
||||
if (stage == Stages.AuctionStarted && deadline < now)
|
||||
if (stage == Stages.AuctionStarted && deadline < block.timestamp)
|
||||
stage = Stages.AuctionFailed;
|
||||
_;
|
||||
}
|
||||
@ -86,7 +86,7 @@ contract Campaign {
|
||||
&& address(_marketMaker) != address(0)
|
||||
&& _fee < FEE_RANGE
|
||||
&& _funding > 0
|
||||
&& now < _deadline);
|
||||
&& block.timestamp < _deadline);
|
||||
eventContract = _eventContract;
|
||||
marketFactory = _marketFactory;
|
||||
marketMaker = _marketMaker;
|
||||
|
@ -71,7 +71,7 @@ contract FutarchyOracle is Oracle {
|
||||
public
|
||||
{
|
||||
// Deadline is in the future
|
||||
require(_deadline > now);
|
||||
require(_deadline > block.timestamp);
|
||||
// Create decision event
|
||||
categoricalEvent = eventFactory.createCategoricalEvent(collateralToken, this, outcomeCount);
|
||||
// Create outcome events
|
||||
@ -131,7 +131,7 @@ contract FutarchyOracle is Oracle {
|
||||
public
|
||||
{
|
||||
// Outcome is not set yet and deadline has passed
|
||||
require(!isSet && deadline <= now);
|
||||
require(!isSet && deadline <= block.timestamp);
|
||||
// Find market with highest marginal price for long outcome tokens
|
||||
uint highestMarginalPrice = markets[0].marketMaker().calcMarginalPrice(markets[0], LONG);
|
||||
uint highestIndex = 0;
|
||||
|
@ -80,7 +80,7 @@ contract UltimateOracle is Oracle {
|
||||
&& forwardedOutcomeSetTimestamp == 0
|
||||
&& forwardedOracle.isOutcomeSet());
|
||||
forwardedOutcome = forwardedOracle.getOutcome();
|
||||
forwardedOutcomeSetTimestamp = now;
|
||||
forwardedOutcomeSetTimestamp = block.timestamp;
|
||||
emit ForwardedOracleOutcomeAssignment(forwardedOutcome);
|
||||
}
|
||||
|
||||
@ -97,7 +97,7 @@ contract UltimateOracle is Oracle {
|
||||
totalOutcomeAmounts[_outcome] = challengeAmount;
|
||||
totalAmount = challengeAmount;
|
||||
frontRunner = _outcome;
|
||||
frontRunnerSetTimestamp = now;
|
||||
frontRunnerSetTimestamp = block.timestamp;
|
||||
emit OutcomeChallenge(msg.sender, _outcome);
|
||||
}
|
||||
|
||||
@ -120,7 +120,7 @@ contract UltimateOracle is Oracle {
|
||||
if (_outcome != frontRunner && totalOutcomeAmounts[_outcome] > totalOutcomeAmounts[frontRunner])
|
||||
{
|
||||
frontRunner = _outcome;
|
||||
frontRunnerSetTimestamp = now;
|
||||
frontRunnerSetTimestamp = block.timestamp;
|
||||
}
|
||||
emit OutcomeVote(msg.sender, _outcome, amount);
|
||||
}
|
||||
@ -147,7 +147,7 @@ contract UltimateOracle is Oracle {
|
||||
view
|
||||
returns (bool)
|
||||
{
|
||||
return forwardedOutcomeSetTimestamp != 0 && now.sub(forwardedOutcomeSetTimestamp) > challengePeriod;
|
||||
return forwardedOutcomeSetTimestamp != 0 && (block.timestamp).sub(forwardedOutcomeSetTimestamp) > challengePeriod;
|
||||
}
|
||||
|
||||
/// @dev Checks if time to overbid the front runner is over
|
||||
@ -157,7 +157,7 @@ contract UltimateOracle is Oracle {
|
||||
view
|
||||
returns (bool)
|
||||
{
|
||||
return frontRunnerSetTimestamp != 0 && now.sub(frontRunnerSetTimestamp) > frontRunnerPeriod;
|
||||
return frontRunnerSetTimestamp != 0 && (block.timestamp).sub(frontRunnerSetTimestamp) > frontRunnerPeriod;
|
||||
}
|
||||
|
||||
/// @dev Checks if outcome was challenged
|
||||
|
@ -264,10 +264,10 @@ contract MilestoneTracker {
|
||||
&&(msg.sender != recipient))
|
||||
revert();
|
||||
if (milestone.status != MilestoneStatus.AcceptedAndInProgress) revert();
|
||||
if (now < milestone.minCompletionDate) revert();
|
||||
if (now > milestone.maxCompletionDate) revert();
|
||||
if (block.timestamp < milestone.minCompletionDate) revert();
|
||||
if (block.timestamp > milestone.maxCompletionDate) revert();
|
||||
milestone.status = MilestoneStatus.Completed;
|
||||
milestone.doneTime = now;
|
||||
milestone.doneTime = block.timestamp;
|
||||
emit ProposalStatusChanged(_idMilestone, milestone.status);
|
||||
}
|
||||
|
||||
@ -312,7 +312,7 @@ contract MilestoneTracker {
|
||||
&&(msg.sender != recipient))
|
||||
revert();
|
||||
if ((milestone.status != MilestoneStatus.Completed) ||
|
||||
(now < milestone.doneTime + milestone.reviewTime))
|
||||
(block.timestamp < milestone.doneTime + milestone.reviewTime))
|
||||
revert();
|
||||
|
||||
authorizePayment(_idMilestone);
|
||||
|
@ -38,7 +38,6 @@ namespace solidity::frontend::test
|
||||
|
||||
namespace
|
||||
{
|
||||
|
||||
static char const* registrarCode = R"DELIMITER(
|
||||
pragma solidity >=0.4.0 <0.8.0;
|
||||
|
||||
@ -68,7 +67,7 @@ abstract contract AuctionSystem {
|
||||
|
||||
function bid(string memory _name, address payable _bidder, uint _value) internal {
|
||||
Auction storage auction = m_auctions[_name];
|
||||
if (auction.endDate > 0 && now > auction.endDate)
|
||||
if (auction.endDate > 0 && block.timestamp > auction.endDate)
|
||||
{
|
||||
emit AuctionEnded(_name, auction.highestBidder);
|
||||
onAuctionEnd(_name);
|
||||
@ -82,7 +81,7 @@ abstract contract AuctionSystem {
|
||||
auction.sumOfBids += _value;
|
||||
auction.highestBid = _value;
|
||||
auction.highestBidder = _bidder;
|
||||
auction.endDate = now + c_biddingTime;
|
||||
auction.endDate = block.timestamp + c_biddingTime;
|
||||
|
||||
emit NewBid(_name, _bidder, _value);
|
||||
}
|
||||
@ -120,7 +119,7 @@ contract GlobalRegistrar is Registrar, AuctionSystem {
|
||||
Auction storage auction = m_auctions[_name];
|
||||
Record storage record = m_toRecord[_name];
|
||||
address previousOwner = record.owner;
|
||||
record.renewalDate = now + c_renewalInterval;
|
||||
record.renewalDate = block.timestamp + c_renewalInterval;
|
||||
record.owner = auction.highestBidder;
|
||||
emit Changed(_name);
|
||||
if (previousOwner != 0x0000000000000000000000000000000000000000) {
|
||||
@ -138,7 +137,7 @@ contract GlobalRegistrar is Registrar, AuctionSystem {
|
||||
bool needAuction = requiresAuction(_name);
|
||||
if (needAuction)
|
||||
{
|
||||
if (now < m_toRecord[_name].renewalDate)
|
||||
if (block.timestamp < m_toRecord[_name].renewalDate)
|
||||
revert();
|
||||
bid(_name, msg.sender, msg.value);
|
||||
} else {
|
||||
|
@ -40,7 +40,6 @@ using namespace solidity::util;
|
||||
|
||||
namespace solidity::frontend::test
|
||||
{
|
||||
|
||||
static char const* walletCode = R"DELIMITER(
|
||||
//sol Wallet
|
||||
// Multi-sig, daily-limited account proxy/wallet.
|
||||
@ -317,7 +316,7 @@ abstract contract daylimit is multiowned {
|
||||
return false;
|
||||
}
|
||||
// determines today's index.
|
||||
function today() private view returns (uint) { return now / 1 days; }
|
||||
function today() private view returns (uint) { return block.timestamp / 1 days; }
|
||||
|
||||
// FIELDS
|
||||
|
||||
|
@ -34,7 +34,7 @@ function colony_test
|
||||
FORCE_ABIv2=false
|
||||
CONFIG="truffle.js"
|
||||
|
||||
truffle_setup https://github.com/solidity-external-tests/colonyNetwork.git develop_060
|
||||
truffle_setup https://github.com/solidity-external-tests/colonyNetwork.git develop_070
|
||||
run_install install_fn
|
||||
|
||||
cd lib
|
||||
|
@ -33,7 +33,7 @@ function gnosis_safe_test
|
||||
OPTIMIZER_LEVEL=1
|
||||
CONFIG="truffle.js"
|
||||
|
||||
truffle_setup https://github.com/solidity-external-tests/safe-contracts.git development_060
|
||||
truffle_setup https://github.com/solidity-external-tests/safe-contracts.git development_070
|
||||
|
||||
force_truffle_version
|
||||
sed -i 's|github:gnosis/mock-contract#sol_0_5_0|github:solidity-external-tests/mock-contract#master_070|g' package.json
|
||||
|
@ -381,7 +381,7 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
revert();
|
||||
if (address(DAOrewardAccount) == 0x0000000000000000000000000000000000000000)
|
||||
revert();
|
||||
lastTimeMinQuorumMet = now;
|
||||
lastTimeMinQuorumMet = block.timestamp;
|
||||
minQuorumDivisor = 5; // sets the minimal quorum to 20%
|
||||
proposals.push(); // avoids a proposal with ID 0 because it is used
|
||||
|
||||
@ -390,7 +390,7 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
}
|
||||
|
||||
receive() external payable override(DAOInterface, TokenCreation) {
|
||||
if (now < closingTime + creationGracePeriod && msg.sender != address(extraBalance))
|
||||
if (block.timestamp < closingTime + creationGracePeriod && msg.sender != address(extraBalance))
|
||||
createTokenProxy(msg.sender);
|
||||
else
|
||||
receiveEther();
|
||||
@ -430,13 +430,13 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
revert();
|
||||
|
||||
if (!isFueled
|
||||
|| now < closingTime
|
||||
|| block.timestamp < closingTime
|
||||
|| (msg.value < proposalDeposit && !_newCurator)) {
|
||||
|
||||
revert();
|
||||
}
|
||||
|
||||
if (now + _debatingPeriod < now) // prevents overflow
|
||||
if (block.timestamp + _debatingPeriod < block.timestamp) // prevents overflow
|
||||
revert();
|
||||
|
||||
// to prevent a 51% attacker to convert the ether into deposit
|
||||
@ -445,7 +445,7 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
|
||||
// to prevent curator from halving quorum before first proposal
|
||||
if (proposals.length == 1) // initial length is 1 (see constructor)
|
||||
lastTimeMinQuorumMet = now;
|
||||
lastTimeMinQuorumMet = block.timestamp;
|
||||
|
||||
Proposal storage p = proposals.push();
|
||||
_proposalID = proposals.length - 1;
|
||||
@ -453,7 +453,7 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
p.amount = _amount;
|
||||
p.description = _description;
|
||||
p.proposalHash = keccak256(abi.encodePacked(_recipient, _amount, _transactionData));
|
||||
p.votingDeadline = now + _debatingPeriod;
|
||||
p.votingDeadline = block.timestamp + _debatingPeriod;
|
||||
p.open = true;
|
||||
//p.proposalPassed = False; // that's default
|
||||
p.newCurator = _newCurator;
|
||||
@ -493,7 +493,7 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
Proposal storage p = proposals[_proposalID];
|
||||
if (p.votedYes[msg.sender]
|
||||
|| p.votedNo[msg.sender]
|
||||
|| now >= p.votingDeadline) {
|
||||
|| block.timestamp >= p.votingDeadline) {
|
||||
|
||||
revert();
|
||||
}
|
||||
@ -529,13 +529,13 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
? splitExecutionPeriod
|
||||
: executeProposalPeriod;
|
||||
// If we are over deadline and waiting period, assert proposal is closed
|
||||
if (p.open && now > p.votingDeadline + waitPeriod) {
|
||||
if (p.open && block.timestamp > p.votingDeadline + waitPeriod) {
|
||||
closeProposal(_proposalID);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check if the proposal can be executed
|
||||
if (now < p.votingDeadline // has the voting deadline arrived?
|
||||
if (block.timestamp < p.votingDeadline // has the voting deadline arrived?
|
||||
// Have the votes been counted?
|
||||
|| !p.open
|
||||
|| p.proposalPassed // anyone trying to call us recursively?
|
||||
@ -573,7 +573,7 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
if (!p.creator.send(p.proposalDeposit))
|
||||
revert();
|
||||
|
||||
lastTimeMinQuorumMet = now;
|
||||
lastTimeMinQuorumMet = block.timestamp;
|
||||
// set the minQuorum to 20% again, in the case it has been reached
|
||||
if (quorum > totalSupply / 5)
|
||||
minQuorumDivisor = 5;
|
||||
@ -628,9 +628,9 @@ contract DAO is DAOInterface, Token, TokenCreation {
|
||||
|
||||
// Sanity check
|
||||
|
||||
if (now < p.votingDeadline // has the voting deadline arrived?
|
||||
if (block.timestamp < p.votingDeadline // has the voting deadline arrived?
|
||||
//The request for a split expires XX days after the voting deadline
|
||||
|| now > p.votingDeadline + splitExecutionPeriod
|
||||
|| block.timestamp > p.votingDeadline + splitExecutionPeriod
|
||||
// Does the new Curator address match?
|
||||
|| p.recipient != _newCurator
|
||||
// Is it a new curator proposal?
|
||||
@ -759,7 +759,7 @@ override returns (bool _success) {
|
||||
|
||||
function transfer(address _to, uint256 _value) public override returns (bool success) {
|
||||
if (isFueled
|
||||
&& now > closingTime
|
||||
&& block.timestamp > closingTime
|
||||
&& !isBlocked(msg.sender)
|
||||
&& _to != address(this)
|
||||
&& transferPaidOut(msg.sender, _to, _value)
|
||||
@ -782,7 +782,7 @@ override returns (bool _success) {
|
||||
function transferFrom(address _from, address _to, uint256 _value) public
|
||||
override returns (bool success) {
|
||||
if (isFueled
|
||||
&& now > closingTime
|
||||
&& block.timestamp > closingTime
|
||||
&& !isBlocked(_from)
|
||||
&& _to != address(this)
|
||||
&& transferPaidOut(_from, _to, _value)
|
||||
@ -869,11 +869,11 @@ override returns (bool _success) {
|
||||
// this can only be called after `quorumHalvingPeriod` has passed or at anytime after
|
||||
// fueling by the curator with a delay of at least `minProposalDebatePeriod`
|
||||
// between the calls
|
||||
if ((lastTimeMinQuorumMet < (now - quorumHalvingPeriod) || msg.sender == curator)
|
||||
&& lastTimeMinQuorumMet < (now - minProposalDebatePeriod)
|
||||
&& now >= closingTime
|
||||
if ((lastTimeMinQuorumMet < (block.timestamp - quorumHalvingPeriod) || msg.sender == curator)
|
||||
&& lastTimeMinQuorumMet < (block.timestamp - minProposalDebatePeriod)
|
||||
&& block.timestamp >= closingTime
|
||||
&& proposals.length > 1) {
|
||||
lastTimeMinQuorumMet = now;
|
||||
lastTimeMinQuorumMet = block.timestamp;
|
||||
minQuorumDivisor *= 2;
|
||||
return true;
|
||||
} else {
|
||||
@ -887,7 +887,7 @@ override returns (bool _success) {
|
||||
_newCurator,
|
||||
0,
|
||||
0,
|
||||
now + splitExecutionPeriod,
|
||||
block.timestamp + splitExecutionPeriod,
|
||||
name,
|
||||
symbol,
|
||||
decimals
|
||||
@ -907,7 +907,7 @@ override returns (bool _success) {
|
||||
if (blocked[_account] == 0)
|
||||
return false;
|
||||
Proposal storage p = proposals[blocked[_account]];
|
||||
if (now > p.votingDeadline) {
|
||||
if (block.timestamp > p.votingDeadline) {
|
||||
blocked[_account] = 0;
|
||||
return false;
|
||||
} else {
|
||||
|
@ -102,7 +102,7 @@ contract TokenCreation is TokenCreationInterface, Token {
|
||||
|
||||
function createTokenProxy(address payable _tokenHolder) payable public
|
||||
override returns (bool success) {
|
||||
if (now < closingTime && msg.value > 0
|
||||
if (block.timestamp < closingTime && msg.value > 0
|
||||
&& (privateCreation == 0x0000000000000000000000000000000000000000 || privateCreation == msg.sender)) {
|
||||
|
||||
uint token = (msg.value * 20) / divisor();
|
||||
@ -121,7 +121,7 @@ override returns (bool success) {
|
||||
}
|
||||
|
||||
function refund() public override {
|
||||
if (now > closingTime && !isFueled) {
|
||||
if (block.timestamp > closingTime && !isFueled) {
|
||||
// Get extraBalance - will only succeed when called for the first time
|
||||
if (address(extraBalance).balance >= extraBalance.accumulatedInput())
|
||||
extraBalance.payOut(address(this), extraBalance.accumulatedInput());
|
||||
@ -141,11 +141,11 @@ override returns (bool success) {
|
||||
// The number of (base unit) tokens per wei is calculated
|
||||
// as `msg.value` * 20 / `divisor`
|
||||
// The fueling period starts with a 1:1 ratio
|
||||
if (closingTime - 2 weeks > now) {
|
||||
if (closingTime - 2 weeks > block.timestamp) {
|
||||
return 20;
|
||||
// Followed by 10 days with a daily creation rate increase of 5%
|
||||
} else if (closingTime - 4 days > now) {
|
||||
return (20 + (now - (closingTime - 2 weeks)) / (1 days));
|
||||
} else if (closingTime - 4 days > block.timestamp) {
|
||||
return (20 + (block.timestamp - (closingTime - 2 weeks)) / (1 days));
|
||||
// The last 4 days there is a constant creation rate ratio of 1:1.5
|
||||
} else {
|
||||
return 30;
|
||||
|
@ -1025,29 +1025,6 @@ BOOST_AUTO_TEST_CASE(blockchain)
|
||||
ABI_CHECK(callContractFunctionWithValue("someInfo()", 28), encodeArgs(28, u256("0x1212121212121212121212121212121212121212"), 7));
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE(now)
|
||||
{
|
||||
char const* sourceCode = R"(
|
||||
contract test {
|
||||
function someInfo() public returns (bool equal, uint val) {
|
||||
equal = block.timestamp == now;
|
||||
val = now;
|
||||
}
|
||||
}
|
||||
)";
|
||||
ALSO_VIA_YUL(
|
||||
compileAndRun(sourceCode);
|
||||
u256 startBlock = blockNumber();
|
||||
size_t startTime = blockTimestamp(startBlock);
|
||||
auto ret = callContractFunction("someInfo()");
|
||||
u256 endBlock = blockNumber();
|
||||
size_t endTime = blockTimestamp(endBlock);
|
||||
BOOST_CHECK(startBlock != endBlock);
|
||||
BOOST_CHECK(startTime != endTime);
|
||||
ABI_CHECK(ret, encodeArgs(true, endTime));
|
||||
)
|
||||
}
|
||||
|
||||
BOOST_AUTO_TEST_CASE(send_ether)
|
||||
{
|
||||
char const* sourceCode = R"(
|
||||
|
@ -346,9 +346,9 @@ BOOST_AUTO_TEST_CASE(incorrect_storage_access_bug)
|
||||
mapping(uint => uint) data;
|
||||
function f() public returns (uint)
|
||||
{
|
||||
if (data[now] == 0)
|
||||
if (data[block.timestamp] == 0)
|
||||
data[uint(-7)] = 5;
|
||||
return data[now];
|
||||
return data[block.timestamp];
|
||||
}
|
||||
}
|
||||
)";
|
||||
|
@ -10,7 +10,7 @@ contract C
|
||||
assert(tx.origin == msg.sender);
|
||||
uint x = block.number;
|
||||
assert(x + 2 > block.number);
|
||||
assert(now > 10);
|
||||
assert(block.timestamp > 10);
|
||||
assert(gasleft() > 100);
|
||||
}
|
||||
}
|
||||
@ -22,5 +22,5 @@ contract C
|
||||
// Warning: (244-275): Assertion violation happens here
|
||||
// Warning: (311-316): Overflow (resulting value larger than 2**256 - 1) happens here
|
||||
// Warning: (304-332): Assertion violation happens here
|
||||
// Warning: (336-352): Assertion violation happens here
|
||||
// Warning: (356-379): Assertion violation happens here
|
||||
// Warning: (336-364): Assertion violation happens here
|
||||
// Warning: (368-391): Assertion violation happens here
|
||||
|
@ -0,0 +1,7 @@
|
||||
contract C {
|
||||
function f() public {
|
||||
now;
|
||||
}
|
||||
}
|
||||
// ----
|
||||
// TypeError: (38-41): "now" has been deprecated. Use "block.timestamp" instead.
|
@ -0,0 +1,8 @@
|
||||
contract C {
|
||||
function f() public view {
|
||||
uint now = block.timestamp;
|
||||
now;
|
||||
}
|
||||
}
|
||||
// ----
|
||||
// Warning: (43-51): This declaration shadows a builtin symbol.
|
@ -1,7 +1,7 @@
|
||||
contract C {
|
||||
uint x;
|
||||
function g() pure public {}
|
||||
function f() view public returns (uint) { return now; }
|
||||
function f() view public returns (uint) { return block.timestamp; }
|
||||
function h() public { x = 2; }
|
||||
function i() payable public { x = 2; }
|
||||
}
|
||||
|
@ -267,6 +267,11 @@ public:
|
||||
|
||||
return "";
|
||||
}
|
||||
|
||||
static std::string nowUpdate(langutil::SourceLocation const& _location)
|
||||
{
|
||||
return regex_replace(_location.text(), std::regex{"now"}, "block.timestamp");
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
@ -196,6 +196,8 @@ Allowed options)",
|
||||
m_suite.activateModule(Module::VirtualFunction);
|
||||
else if (module == "dotsyntax")
|
||||
m_suite.activateModule(Module::DotSyntax);
|
||||
else if (module == "now")
|
||||
m_suite.activateModule(Module::NowKeyword);
|
||||
else
|
||||
{
|
||||
error() << "Unknown upgrade module \"" + module + "\"" << endl;
|
||||
|
@ -58,7 +58,8 @@ private:
|
||||
AbstractContract,
|
||||
OverridingFunction,
|
||||
VirtualFunction,
|
||||
DotSyntax
|
||||
DotSyntax,
|
||||
NowKeyword
|
||||
};
|
||||
|
||||
/// Upgrade suite that hosts all available modules.
|
||||
@ -84,6 +85,8 @@ private:
|
||||
/// Solidity 0.7.0
|
||||
if (isActivated(Module::DotSyntax))
|
||||
DotSyntax{m_changes}.analyze(_sourceUnit);
|
||||
if (isActivated(Module::NowKeyword))
|
||||
NowKeyword{m_changes}.analyze(_sourceUnit);
|
||||
}
|
||||
|
||||
void activateModule(Module _module) { m_modules.insert(_module); }
|
||||
@ -103,7 +106,8 @@ private:
|
||||
Module::AbstractContract,
|
||||
Module::OverridingFunction,
|
||||
Module::VirtualFunction,
|
||||
Module::DotSyntax
|
||||
Module::DotSyntax,
|
||||
Module::NowKeyword
|
||||
};
|
||||
};
|
||||
|
||||
|
@ -40,3 +40,22 @@ void DotSyntax::endVisit(FunctionCall const& _functionCall)
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
void NowKeyword::endVisit(Identifier const& _identifier)
|
||||
{
|
||||
IdentifierAnnotation& annotation = _identifier.annotation();
|
||||
|
||||
if (
|
||||
MagicVariableDeclaration const* magicVar =
|
||||
dynamic_cast<MagicVariableDeclaration const*>(annotation.referencedDeclaration)
|
||||
)
|
||||
if (magicVar->type()->category() == Type::Category::Integer)
|
||||
{
|
||||
solAssert(_identifier.name() == "now", "");
|
||||
m_changes.emplace_back(
|
||||
UpgradeChange::Level::Safe,
|
||||
_identifier.location(),
|
||||
SourceTransform::nowUpdate(_identifier.location())
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -32,4 +32,13 @@ private:
|
||||
void endVisit(frontend::FunctionCall const& _expression) override;
|
||||
};
|
||||
|
||||
class NowKeyword: public AnalysisUpgrade
|
||||
{
|
||||
public:
|
||||
using AnalysisUpgrade::AnalysisUpgrade;
|
||||
void analyze(frontend::SourceUnit const& _sourceUnit) { _sourceUnit.accept(*this); }
|
||||
private:
|
||||
void endVisit(frontend::Identifier const& _expression) override;
|
||||
};
|
||||
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user