Units and Global Variables
Working with numbers, made easy!
Solidity provides a wide array of predefined units and variables that facilitate both logical and mathematical calculations. In this section we will go over some of the most commonly used ones.
Units
Solidity provides two types of units: ether units and time units.
Ether Units
Recall that the EVM denominates ether in terms of Wei (1 wei = 10**(-18) ether). Therefore, consider the following code that checks if an account has a balance of 1 ether:
Having to specify an exact integer, especially for integers as large as 10**18
, can lead to both bugs and legibility issues. Rather than specifying an exact value, we can utilize units.
In the code above, we are checking if the account has exactly 1 ether. Under the hood, we are still checking if the account has a balance of 10**18
, but it is obvious that using units makes our code easier to read and less prone to bugs. Likewise, we can use units in state/local variables as well:
Solidity provides us with the following ether units:
wei
gwei
ether
Time Units
The EVM (and computers in general) denominate time in terms of seconds. Dealing with seconds might be a headache for some and for this reason, Solidity provides us with time units. As an example, consider the following code:
In the code above, we have a function which performs some logic if it has been more than a hour since the last time it was called; we check this by adding 3600
to lastTimeCalled
. Again, denominating seconds explicitly introduces both legibility issues and the potential for bugs. Instead, we can use time units:
Listed below are the time units that Solidity provides:
seconds
minutes
hours
days
weeks
Again, note that all these units are denominated in terms of seconds.
Global Variables
As the name might suggest, global variables are values that are available at a global level. Listed below are some of the most commonly-used global variables:
block.gaslimit
: the gas limit of the current blockblock.number
: the number of the current blockblock.timestamp
: the time at which the current block was publishedmsg.data
: the data attached with the current messagemsg.sender
: the sender of the current messagemsg.value
: the amount of ether (denominated in wei) that was sent with the current messagetx.gasprice
: the price per gas paid for the current transactiontx.origin
: the account that sent the current transaction
Transactions Vs Messages
Although transactions and messages might seem synonymous, there is a big difference between the two terms. Consider the following transaction:
I call contract A. Halfway through the execution of contract A, contract A calls contract B.
Transaction here refers to the entire execution context. In this scenario, tx.origin
is my address (tx.origin
is always the address of an EOA). Messages, meanwhile, refer to a specific execution environment. In the scenario above, there are two messages:
Message 1: consists of me as the sender and contract A as the recipient.
Message 2: consists of contract A as the sender and contract B as the recipient.
An easy way to think about messages is that a new message is created whenever the from/to values of the execution environment changes.
Resources
Solidity Docs: https://docs.soliditylang.org/en/v0.8.17/units-and-global-variables.html
Last updated