aboutsummaryrefslogtreecommitdiffstats
path: root/docs
diff options
context:
space:
mode:
Diffstat (limited to 'docs')
-rw-r--r--docs/050-breaking-changes.rst11
-rw-r--r--docs/abi-spec.rst22
-rw-r--r--docs/assembly.rst18
-rw-r--r--docs/common-patterns.rst12
-rw-r--r--docs/contracts.rst65
-rw-r--r--docs/contributing.rst78
-rw-r--r--docs/control-structures.rst24
-rw-r--r--docs/frequently-asked-questions.rst40
-rw-r--r--docs/index.rst13
-rw-r--r--docs/installing-solidity.rst52
-rw-r--r--docs/introduction-to-smart-contracts.rst13
-rw-r--r--docs/layout-of-source-files.rst17
-rw-r--r--docs/metadata.rst28
-rw-r--r--docs/miscellaneous.rst2
-rw-r--r--docs/security-considerations.rst51
-rw-r--r--docs/solidity-by-example.rst10
-rw-r--r--docs/structure-of-a-contract.rst12
-rw-r--r--docs/style-guide.rst28
-rw-r--r--docs/types.rst239
-rw-r--r--docs/using-the-compiler.rst38
-rw-r--r--docs/yul.rst9
21 files changed, 503 insertions, 279 deletions
diff --git a/docs/050-breaking-changes.rst b/docs/050-breaking-changes.rst
index 5a7add5d..9094000e 100644
--- a/docs/050-breaking-changes.rst
+++ b/docs/050-breaking-changes.rst
@@ -53,7 +53,7 @@ Semantic and Syntactic Changes
This section highlights changes that affect syntax and semantics.
-* The functions ``.call()``, ``.delegatecall()`, ``staticcall()``,
+* The functions ``.call()``, ``.delegatecall()``, ``staticcall()``,
``keccak256()``, ``sha256()`` and ``ripemd160()`` now accept only a single
``bytes`` argument. Moreover, the argument is not padded. This was changed to
make more explicit and clear how the arguments are concatenated. Change every
@@ -107,7 +107,10 @@ For most of the topics the compiler will provide suggestions.
other way around is not allowed. Converting ``address`` to ``address
payable`` is possible via conversion through ``uint160``. If ``c`` is a
contract, ``address(c)`` results in ``address payable`` only if ``c`` has a
- payable fallback function.
+ payable fallback function. If you use the :ref:`withdraw pattern<withdrawal_pattern>`,
+ you most likely do not have to change your code because ``transfer``
+ is only used on ``msg.sender`` instead of stored addresses and ``msg.sender``
+ is an ``address payable``.
* Conversions between ``bytesX`` and ``uintY`` of different size are now
disallowed due to ``bytesX`` padding on the right and ``uintY`` padding on
@@ -222,6 +225,8 @@ Variables
* Detecting cyclic dependencies in variables and structs is limited in
recursion to 256.
+* Fixed-size arrays with a length of zero are now disallowed.
+
Syntax
------
@@ -327,7 +332,7 @@ New version:
::
- pragma solidity >0.4.25;
+ pragma solidity >0.4.99 <0.6.0;
contract OtherContract {
uint x;
diff --git a/docs/abi-spec.rst b/docs/abi-spec.rst
index 7b78fad3..f31d9d45 100644
--- a/docs/abi-spec.rst
+++ b/docs/abi-spec.rst
@@ -13,9 +13,9 @@ The Contract Application Binary Interface (ABI) is the standard way to interact
from outside the blockchain and for contract-to-contract interaction. Data is encoded according to its type,
as described in this specification. The encoding is not self describing and thus requires a schema in order to decode.
-We assume the interface functions of a contract are strongly typed, known at compilation time and static. No introspection mechanism will be provided. We assume that all contracts will have the interface definitions of any contracts they call available at compile-time.
+We assume the interface functions of a contract are strongly typed, known at compilation time and static. We assume that all contracts will have the interface definitions of any contracts they call available at compile-time.
-This specification does not address contracts whose interface is dynamic or otherwise known only at run-time. Should these cases become important they can be adequately handled as facilities built within the Ethereum ecosystem.
+This specification does not address contracts whose interface is dynamic or otherwise known only at run-time.
.. _abi_function_selector:
@@ -23,12 +23,12 @@ Function Selector
=================
The first four bytes of the call data for a function call specifies the function to be called. It is the
-first (left, high-order in big-endian) four bytes of the Keccak (SHA-3) hash of the signature of the function. The signature is defined as the canonical expression of the basic prototype, i.e.
+first (left, high-order in big-endian) four bytes of the Keccak-256 (SHA-3) hash of the signature of the function. The signature is defined as the canonical expression of the basic prototype without data location specifier, i.e.
the function name with the parenthesised list of parameter types. Parameter types are split by a single comma - no spaces are used.
.. note::
The return type of a function is not part of this signature. In :ref:`Solidity's function overloading <overload-function>` return types are not considered. The reason is to keep function call resolution context-independent.
- The JSON description of the ABI however contains both inputs and outputs. See (the :ref:`JSON ABI <abi_json>`)
+ The :ref:`JSON description of the ABI<abi_json>` however contains both inputs and outputs.
Argument Encoding
=================
@@ -109,7 +109,7 @@ The encoding is designed to have the following properties, which are especially
1. The number of reads necessary to access a value is at most the depth of the value inside the argument array structure, i.e. four reads are needed to retrieve ``a_i[k][l][r]``. In a previous version of the ABI, the number of reads scaled linearly with the total number of dynamic parameters in the worst case.
- 2. The data of a variable or array element is not interleaved with other data and it is relocatable, i.e. it only uses relative "addresses"
+ 2. The data of a variable or array element is not interleaved with other data and it is relocatable, i.e. it only uses relative "addresses".
Formal Specification of the Encoding
@@ -212,7 +212,7 @@ Given the contract:
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract Foo {
function bar(bytes3[2] memory) public pure {}
@@ -438,8 +438,8 @@ A function description is a JSON object with the fields:
* ``components``: used for tuple types (more below).
- ``outputs``: an array of objects similar to ``inputs``, can be omitted if function doesn't return anything;
-- ``stateMutability``: a string with one of the following values: ``pure`` (:ref:`specified to not read blockchain state <pure-functions>`), ``view`` (:ref:`specified to not modify the blockchain state <view-functions>`), ``nonpayable`` (function does not accept ether) and ``payable`` (function accepts ether);
-- ``payable``: ``true`` if function accepts ether, ``false`` otherwise;
+- ``stateMutability``: a string with one of the following values: ``pure`` (:ref:`specified to not read blockchain state <pure-functions>`), ``view`` (:ref:`specified to not modify the blockchain state <view-functions>`), ``nonpayable`` (function does not accept Ether) and ``payable`` (function accepts Ether);
+- ``payable``: ``true`` if function accepts Ether, ``false`` otherwise;
- ``constant``: ``true`` if function is either ``pure`` or ``view``, ``false`` otherwise.
``type`` can be omitted, defaulting to ``"function"``, likewise ``payable`` and ``constant`` can be omitted, both defaulting to ``false``.
@@ -450,7 +450,7 @@ Constructor and fallback function never have ``name`` or ``outputs``. Fallback f
The fields ``constant`` and ``payable`` are deprecated and will be removed in the future. Instead, the ``stateMutability`` field can be used to determine the same properties.
.. note::
- Sending non-zero ether to non-payable function will revert the transaction.
+ Sending non-zero Ether to non-payable function will revert the transaction.
An event description is a JSON object with fairly similar fields:
@@ -469,7 +469,7 @@ For example,
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract Test {
constructor() public { b = hex"12345678901234567890123456789012"; }
@@ -516,7 +516,7 @@ As an example, the code
::
- pragma solidity ^0.4.19;
+ pragma solidity >=0.4.19 <0.6.0;
pragma experimental ABIEncoderV2;
contract Test {
diff --git a/docs/assembly.rst b/docs/assembly.rst
index 90bfa1f1..c609fa9d 100644
--- a/docs/assembly.rst
+++ b/docs/assembly.rst
@@ -67,7 +67,7 @@ idea is that assembly libraries will be used to enhance the Solidity language.
.. code::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
library GetCode {
function at(address _addr) public view returns (bytes memory o_code) {
@@ -92,7 +92,7 @@ efficient code, for example:
.. code::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
library VectorSum {
// This function is less efficient because the optimizer currently fails to
@@ -271,12 +271,16 @@ In the grammar, opcodes are represented as pre-defined identifiers.
+-------------------------+-----+---+-----------------------------------------------------------------+
| returndatacopy(t, f, s) | `-` | B | copy s bytes from returndata at position f to mem at position t |
+-------------------------+-----+---+-----------------------------------------------------------------+
+| extcodehash(a) | | C | code hash of address a |
++-------------------------+-----+---+-----------------------------------------------------------------+
| create(v, p, s) | | F | create new contract with code mem[p...(p+s)) and send v wei |
| | | | and return the new address |
+-------------------------+-----+---+-----------------------------------------------------------------+
| create2(v, n, p, s) | | C | create new contract with code mem[p...(p+s)) at address |
-| | | | keccak256(<address> . n . keccak256(mem[p...(p+s))) and send v |
-| | | | wei and return the new address |
+| | | | keccak256(0xff . self . n . keccak256(mem[p...(p+s))) |
+| | | | and send v wei and return the new address, where ``0xff`` is a |
+| | | | 8 byte value, ``self`` is the current contract's address |
+| | | | as a 20 byte value and ``n`` is a big-endian 256-bit value |
+-------------------------+-----+---+-----------------------------------------------------------------+
| call(g, a, v, in, | | F | call contract at address a with input mem[in...(in+insize)) |
| insize, out, outsize) | | | providing g gas and v wei and output area |
@@ -381,7 +385,7 @@ Local Solidity variables are available for assignments, for example:
.. code::
- pragma solidity ^0.4.11;
+ pragma solidity >=0.4.11 <0.6.0;
contract C {
uint b;
@@ -420,7 +424,7 @@ be just ``0``, but it can also be a complex functional-style expression.
.. code::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function f(uint x) public view returns (uint b) {
@@ -685,7 +689,7 @@ Example:
We will follow an example compilation from Solidity to assembly.
We consider the runtime bytecode of the following Solidity program::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function f(uint x) public pure returns (uint y) {
diff --git a/docs/common-patterns.rst b/docs/common-patterns.rst
index d26e4377..84c18936 100644
--- a/docs/common-patterns.rst
+++ b/docs/common-patterns.rst
@@ -13,11 +13,11 @@ Withdrawal from Contracts
The recommended method of sending funds after an effect
is using the withdrawal pattern. Although the most intuitive
method of sending Ether, as a result of an effect, is a
-direct ``send`` call, this is not recommended as it
+direct ``transfer`` call, this is not recommended as it
introduces a potential security risk. You may read
more about this on the :ref:`security_considerations` page.
-This is an example of the withdrawal pattern in practice in
+The following is an example of the withdrawal pattern in practice in
a contract where the goal is to send the most money to the
contract in order to become the "richest", inspired by
`King of the Ether <https://www.kingoftheether.com/>`_.
@@ -28,7 +28,7 @@ become the new richest.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract WithdrawalContract {
address public richest;
@@ -65,7 +65,7 @@ This is as opposed to the more intuitive sending pattern:
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract SendContract {
address payable public richest;
@@ -130,7 +130,7 @@ restrictions highly readable.
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract AccessRestriction {
// These will be assigned at the construction
@@ -282,7 +282,7 @@ function finishes.
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract StateMachine {
enum Stages {
diff --git a/docs/contracts.rst b/docs/contracts.rst
index f7ceb950..93f54e4a 100644
--- a/docs/contracts.rst
+++ b/docs/contracts.rst
@@ -42,7 +42,7 @@ This means that cyclic creation dependencies are impossible.
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract OwnedToken {
// TokenCreator is a contract type that is defined below.
@@ -173,7 +173,7 @@ return parameter list for functions.
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function f(uint a) private pure returns (uint b) { return a + 1; }
@@ -187,7 +187,7 @@ In the following example, ``D``, can call ``c.getData()`` to retrieve the value
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
uint private data;
@@ -231,7 +231,7 @@ when they are declared.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
uint public data = 42;
@@ -251,7 +251,7 @@ it evaluates to a state variable. If it is accessed externally
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
uint public data;
@@ -270,7 +270,8 @@ to write a function, for example:
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
+
contract arrayExample {
// public state variable
uint[] public myArray;
@@ -295,7 +296,7 @@ The next example is more complex:
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Complex {
struct Data {
@@ -330,7 +331,7 @@ inheritable properties of contracts and may be overridden by derived contracts.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract owned {
constructor() public { owner = msg.sender; }
@@ -456,7 +457,7 @@ value types and strings.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
uint constant x = 32**22 + 8;
@@ -499,7 +500,7 @@ The following statements are considered modifying the state:
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract C {
function f(uint a, uint b) public view returns (uint) {
@@ -544,7 +545,7 @@ In addition to the list of state modifying statements explained above, the follo
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract C {
function f(uint a, uint b) public pure returns (uint) {
@@ -632,7 +633,7 @@ Like any function, the fallback function can execute complex operations as long
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract Test {
// This function is called for all messages sent to
@@ -683,7 +684,7 @@ The following example shows overloading of the function
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract A {
function f(uint _in) public pure returns (uint out) {
@@ -701,7 +702,7 @@ externally visible functions differ by their Solidity types but not by their ext
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
// This will not compile
contract A {
@@ -734,7 +735,7 @@ candidate, resolution fails.
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract A {
function f(uint8 _in) public pure returns (uint8 out) {
@@ -794,7 +795,7 @@ All non-indexed arguments will be :ref:`ABI-encoded <ABI>` into the data part of
::
- pragma solidity ^0.4.21;
+ pragma solidity >=0.4.21 <0.6.0;
contract ClientReceipt {
event Deposit(
@@ -851,7 +852,7 @@ as topics. The event call above can be performed in the same way as
::
- pragma solidity ^0.4.10;
+ pragma solidity >=0.4.10 <0.6.0;
contract C {
function f() public payable {
@@ -899,7 +900,7 @@ Details are given in the following example.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract owned {
constructor() public { owner = msg.sender; }
@@ -971,7 +972,7 @@ Note that above, we call ``mortal.kill()`` to "forward" the
destruction request. The way this is done is problematic, as
seen in the following example::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract owned {
constructor() public { owner = msg.sender; }
@@ -1000,7 +1001,7 @@ derived override, but this function will bypass
``Base1.kill``, basically because it does not even know about
``Base1``. The way around this is to use ``super``::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract owned {
constructor() public { owner = msg.sender; }
@@ -1059,7 +1060,7 @@ equivalent to ``constructor() public {}``. For example:
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract A {
uint public a;
@@ -1089,7 +1090,7 @@ The constructors of all the base contracts will be called following the
linearization rules explained below. If the base constructors have arguments,
derived contracts need to specify all of them. This can be done in two ways::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract Base {
uint x;
@@ -1130,7 +1131,7 @@ Multiple Inheritance and Linearization
Languages that allow multiple inheritance have to deal with
several problems. One is the `Diamond Problem <https://en.wikipedia.org/wiki/Multiple_inheritance#The_diamond_problem>`_.
Solidity is similar to Python in that it uses "`C3 Linearization <https://en.wikipedia.org/wiki/C3_linearization>`_"
-to force a specific order in the directed acyclic graph of base classes. This
+to force a specific order in the directed acyclic graph (DAG) of base classes. This
results in the desirable property of monotonicity but
disallows some inheritance graphs. Especially, the order in
which the base classes are given in the ``is`` directive is
@@ -1148,7 +1149,7 @@ error "Linearization of inheritance graph impossible".
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract X {}
contract A is X {}
@@ -1179,7 +1180,7 @@ Abstract Contracts
Contracts are marked as abstract when at least one of their functions lacks an implementation as in the following example (note that the function declaration header is terminated by ``;``)::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Feline {
function utterance() public returns (bytes32);
@@ -1187,7 +1188,7 @@ Contracts are marked as abstract when at least one of their functions lacks an i
Such contracts cannot be compiled (even if they contain implemented functions alongside non-implemented functions), but they can be used as base contracts::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Feline {
function utterance() public returns (bytes32);
@@ -1238,7 +1239,7 @@ Interfaces are denoted by their own keyword:
::
- pragma solidity ^0.4.11;
+ pragma solidity >=0.4.11 <0.6.0;
interface Token {
enum TokenType { Fungible, NonFungible }
@@ -1294,13 +1295,13 @@ contract, and a regular ``JUMP`` call will be used instead of a ``DELEGATECALL``
.. index:: using for, set
-The following example illustrates how to use libraries (butmanual method
+The following example illustrates how to use libraries (but manual method
be sure to check out :ref:`using for <using-for>` for a
more advanced example to implement a set).
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
library Set {
// We define a new struct datatype that will be used to
@@ -1374,7 +1375,7 @@ custom types without the overhead of external function calls:
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
library BigInt {
struct bigint {
@@ -1515,7 +1516,7 @@ available without having to add further code.
Let us rewrite the set example from the
:ref:`libraries` in this way::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
// This is the same code as before, just without comments
library Set {
@@ -1565,7 +1566,7 @@ Let us rewrite the set example from the
It is also possible to extend elementary types in that way::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
library Search {
function indexOf(uint[] storage self, uint value)
diff --git a/docs/contributing.rst b/docs/contributing.rst
index d1ed9c6b..361570a0 100644
--- a/docs/contributing.rst
+++ b/docs/contributing.rst
@@ -47,13 +47,14 @@ in addition to *what* you did (unless it is a tiny change).
If you need to pull in any changes from ``develop`` after making your fork (for
example, to resolve potential merge conflicts), please avoid using ``git merge``
-and instead, ``git rebase`` your branch.
+and instead, ``git rebase`` your branch. This will help us review your change
+more easily.
-Additionally, if you are writing a new feature, please ensure you write appropriate
-Boost test cases and place them under ``test/``.
+Additionally, if you are writing a new feature, please ensure you add appropriate
+test cases under ``test/`` (see below).
However, if you are making a larger change, please consult with the `Solidity Development Gitter channel
-<https://gitter.im/ethereum/solidity-dev>`_ (different from the one mentioned above, this on is
+<https://gitter.im/ethereum/solidity-dev>`_ (different from the one mentioned above, this one is
focused on compiler and language development instead of language use) first.
New features and bugfixes should be added to the ``Changelog.md`` file: please
@@ -69,41 +70,47 @@ Thank you for your help!
Running the compiler tests
==========================
-Solidity includes different types of tests. They are included in the application
-called ``soltest``. Some of them require the ``cpp-ethereum`` client in testing mode,
+There is a script at ``scripts/tests.sh`` which executes most of the tests and
+runs ``aleth`` automatically if it is in the path, but does not download it,
+so it most likely will not work right away. Please read on for the details.
+
+Solidity includes different types of tests. Most of them are bundled in the application
+called ``soltest``. Some of them require the ``aleth`` client in testing mode,
some others require ``libz3`` to be installed.
-``soltest`` reads test contracts that are annotated with expected results
-stored in ``./test/libsolidity/syntaxTests``. In order for soltest to find these
-tests the root test directory has to be specified using the ``--testpath`` command
-line option, e.g. ``./build/test/soltest -- --testpath ./test``.
+To run a basic set of tests that neither require ``aleth`` nor ``libz3``, run
+``./scripts/soltest.sh --no-ipc --no-smt``. This script will run ``build/test/soltest``
+internally.
-To disable the z3 tests, use ``./build/test/soltest -- --no-smt --testpath ./test`` and
-to run a subset of the tests that do not require ``cpp-ethereum``, use
-``./build/test/soltest -- --no-ipc --testpath ./test``.
+The option ``--no-smt`` disables the tests that require ``libz3`` and
+``--no-ipc`` disables those that require ``aleth``.
-For all other tests, you need to install `cpp-ethereum <https://github.com/ethereum/cpp-ethereum/releases/download/solidityTester/eth>`_ and run it in testing mode: ``eth --test -d /tmp/testeth``.
+If you want to run the ipc tests (those test the semantics of the generated code),
+you need to install `aleth <https://github.com/ethereum/cpp-ethereum/releases/download/solidityTester/aleth_2018-06-20_artful>`_ and run it in testing mode: ``aleth --test -d /tmp/testeth`` (make sure to rename it).
-Then you run the actual tests: ``./build/test/soltest -- --ipcpath /tmp/testeth/geth.ipc --testpath ./test``.
+Then you run the actual tests: ``./scripts/soltest.sh --ipcpath /tmp/testeth/geth.ipc``.
To run a subset of tests, filters can be used:
-``soltest -t TestSuite/TestName -- --ipcpath /tmp/testeth/geth.ipc --testpath ./test``,
+``./scripts/soltest.sh -t TestSuite/TestName --ipcpath /tmp/testeth/geth.ipc``,
where ``TestName`` can be a wildcard ``*``.
-Alternatively, there is a testing script at ``scripts/tests.sh`` which executes all tests and runs
-``cpp-ethereum`` automatically if it is in the path (but does not download it).
+The script ``scripts/tests.sh`` also runs commandline tests and compilation tests
+in addition to those found in ``soltest``.
-Travis CI even runs some additional tests (including ``solc-js`` and testing third party Solidity frameworks) that require compiling the Emscripten target.
+The CI even runs some additional tests (including ``solc-js`` and testing third party Solidity frameworks) that require compiling the Emscripten target.
.. note ::
- While any version of ``cpp-ethereum`` should be usable, this cannot be guaranteed, and it is suggested to use the same version that is used by the Solidity continuous integration tests.
- Currently the CI uses ``d661ac4fec0aeffbedcdc195f67f5ded0c798278`` of ``cpp-ethereum``.
+ Some versions of ``aleth`` cannot be used for testing. We suggest using the same version that is used by the Solidity continuous integration tests.
+ Currently the CI uses ``d661ac4fec0aeffbedcdc195f67f5ded0c798278`` of ``aleth``.
Writing and running syntax tests
--------------------------------
-As mentioned above, syntax tests are stored in individual contracts. These files must contain annotations, stating the expected result(s) of the respective test.
+Syntax tests check that the compiler generates the correct error messages for invalid code
+and properly accepts valid code.
+They are stored in individual files inside ``tests/libsolidity/syntaxTests``.
+These files must contain annotations, stating the expected result(s) of the respective test.
The test suite will compile and check them against the given expectations.
Example: ``./test/libsolidity/syntaxTests/double_stateVariable_declaration.sol``
@@ -115,10 +122,12 @@ Example: ``./test/libsolidity/syntaxTests/double_stateVariable_declaration.sol``
uint128 variable;
}
// ----
- // DeclarationError: Identifier already declared.
+ // DeclarationError: (36-52): Identifier already declared.
-A syntax test must contain at least the contract under test itself, followed by the separator ``----``. The additional comments above are used to describe the
-expected compiler errors or warnings. This section can be empty in case that the contract should compile without any errors or warnings.
+A syntax test must contain at least the contract under test itself, followed by the separator ``// ----``. The following comments are used to describe the
+expected compiler errors or warnings. The number range denotes the location in the source where the error occurred.
+In case the contract should compile without any errors or warning, the section after the separator has to be empty
+and the separator can be left out completely.
In the above example, the state variable ``variable`` was declared twice, which is not allowed. This will result in a ``DeclarationError`` stating that the identifier was already declared.
@@ -131,7 +140,7 @@ editing of failing contracts using your preferred text editor. Let's try to brea
uint256 variable;
}
// ----
- // DeclarationError: Identifier already declared.
+ // DeclarationError: (36-52): Identifier already declared.
Running ``./test/isoltest`` again will result in a test failure:
@@ -144,16 +153,16 @@ Running ``./test/isoltest`` again will result in a test failure:
}
Expected result:
- DeclarationError: Identifier already declared.
+ DeclarationError: (36-52): Identifier already declared.
Obtained result:
Success
-which prints the expected result next to the obtained result, but also provides a way to change edit / update / skip the current contract or to even quit.
-``isoltest`` offers several options for failing tests:
+``isoltest`` prints the expected result next to the obtained result, but also provides a way to change edit / update / skip the current contract or to even quit.
+It offers several options for failing tests:
-- edit: ``isoltest`` will try to open the editor that was specified before using ``isoltest --editor /path/to/editor``. If no path was set, this will result in a runtime error. In case an editor was specified, this will open it such that the contract can be adjusted.
-- update: Updates the contract under test. This will either remove the annotation which contains the exception not met or will add missing expectations. The test will then be run again.
+- edit: ``isoltest`` tries to open the contract in an editor so you can adjust it. It either uses the editor given on the command line (as ``isoltest --editor /path/to/editor``), in the environment variable ``EDITOR`` or just ``/usr/bin/editor`` (in this order).
+- update: Updates the contract under test. This either removes the annotation which contains the exception not met or adds missing expectations. The test will then be run again.
- skip: Skips the execution of this particular test.
- quit: Quits ``isoltest``.
@@ -176,8 +185,9 @@ and re-run the test. It will now pass again:
.. note::
- Please choose a name for the contract file, that is self-explainatory in the sense of what is been tested, e.g. ``double_variable_declaration.sol``.
- Do not put more than one contract into a single file. ``isoltest`` is currently not able to recognize them individually.
+ Please choose a name for the contract file that explains what it tests, e.g. ``double_variable_declaration.sol``.
+ Do not put more than one contract into a single file, unless you are testing inheritance or cross-contract calls.
+ Each file should test one aspect of your new feature.
Running the Fuzzer via AFL
@@ -276,7 +286,7 @@ use the tool ``scripts/uniqueErrors.sh`` to filter out the unique errors.
Whiskers
========
-*Whiskers* is a templating system similar to `Mustache <https://mustache.github.io>`_. It is used by the
+*Whiskers* is a string templating system similar to `Mustache <https://mustache.github.io>`_. It is used by the
compiler in various places to aid readability, and thus maintainability and verifiability, of the code.
The syntax comes with a substantial difference to Mustache: the template markers ``{{`` and ``}}`` are
diff --git a/docs/control-structures.rst b/docs/control-structures.rst
index ae0abc49..80311a63 100644
--- a/docs/control-structures.rst
+++ b/docs/control-structures.rst
@@ -20,7 +20,7 @@ For example, suppose we want our contract to
accept one kind of external calls with two integers, we would write
something like::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract Simple {
uint sum;
@@ -40,7 +40,7 @@ The output parameters can be declared with the same syntax after the
the sum and the product of the two given integers, then we would
write::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract Simple {
function arithmetic(uint _a, uint _b)
@@ -99,7 +99,7 @@ Internal Function Calls
Functions of the current contract can be called directly ("internally"), also recursively, as seen in
this nonsensical example::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function g(uint a) public pure returns (uint ret) { return a + f(); }
@@ -129,7 +129,7 @@ all function arguments have to be copied to memory.
When calling functions of other contracts, the amount of Wei sent with the call and
the gas can be specified with special options ``.value()`` and ``.gas()``, respectively::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract InfoFeed {
function info() public payable returns (uint ret) { return 42; }
@@ -176,7 +176,7 @@ parameters from the function declaration, but can be in arbitrary order.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
mapping(uint => uint) data;
@@ -199,7 +199,7 @@ Those parameters will still be present on the stack, but they are inaccessible.
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
// omitted name for parameter
@@ -222,7 +222,7 @@ is compiled so recursive creation-dependencies are not possible.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract D {
uint public x;
@@ -345,7 +345,7 @@ the two variables have the same name but disjoint scopes.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract C {
function minimalScoping() pure public {
{
@@ -366,7 +366,7 @@ In any case, you will get a warning about the outer variable being shadowed.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
// This will report a warning
contract C {
function f() pure public returns (uint) {
@@ -386,7 +386,7 @@ In any case, you will get a warning about the outer variable being shadowed.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
// This will not compile
contract C {
function f() pure public returns (uint) {
@@ -433,7 +433,7 @@ a message string for ``require``, but not for ``assert``.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract Sharer {
function sendHalf(address payable addr) public payable returns (uint balance) {
@@ -479,7 +479,7 @@ The following example shows how an error string can be used together with revert
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract VendingMachine {
function buy(uint amount) public payable {
diff --git a/docs/frequently-asked-questions.rst b/docs/frequently-asked-questions.rst
index d2b7de9c..a474f905 100644
--- a/docs/frequently-asked-questions.rst
+++ b/docs/frequently-asked-questions.rst
@@ -43,21 +43,15 @@ Can you return an array or a ``string`` from a solidity function call?
Yes. See `array_receiver_and_returner.sol <https://github.com/fivedogit/solidity-baby-steps/blob/master/contracts/60_array_receiver_and_returner.sol>`_.
-What is problematic, though, is returning any variably-sized data (e.g. a
-variably-sized array like ``uint[]``) from a function **called from within Solidity**.
-This is a limitation of the EVM and will be solved with the next protocol update.
-
-Returning variably-sized data as part of an external transaction or call is fine.
-
Is it possible to in-line initialize an array like so: ``string[] myarray = ["a", "b"];``
=========================================================================================
Yes. However it should be noted that this currently only works with statically sized memory arrays. You can even create an inline memory
-array in the return statement. Pretty cool, huh?
+array in the return statement.
Example::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function f() public pure returns (uint8[5] memory) {
@@ -70,7 +64,7 @@ Example::
Can a contract function return a ``struct``?
============================================
-Yes, but only in ``internal`` function calls.
+Yes, but only in ``internal`` function calls or if ``pragma experimental "ABIEncoderV2";`` is used.
If I return an ``enum``, I only get integer values in web3.js. How to get the named values?
===========================================================================================
@@ -87,7 +81,7 @@ should be noted that you must declare them as static memory arrays.
Examples::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
struct S {
@@ -127,7 +121,7 @@ which will be extended in the future. In addition, Arachnid has written `solidit
For now, if you want to modify a string (even when you only want to know its length),
you should always convert it to a ``bytes`` first::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
string s;
@@ -145,7 +139,17 @@ you should always convert it to a ``bytes`` first::
Can I concatenate two strings?
==============================
-You have to do it manually for now.
+Yes, you can use ``abi.encodePacked``::
+
+ pragma solidity >=0.4.0 <0.6.0;
+
+ library ConcatHelper {
+ function concat(bytes memory a, bytes memory b)
+ internal pure returns (bytes memory) {
+ return abi.encodePacked(a, b);
+ }
+ }
+
Why is the low-level function ``.call()`` less favorable than instantiating a contract with a variable (``ContractB b;``) and executing its functions (``b.doSomething();``)?
=============================================================================================================================================================================
@@ -282,7 +286,7 @@ In the case of a ``contract A`` calling a new instance of ``contract B``, parent
You will need to make sure that you have both contracts aware of each other's presence and that ``contract B`` has a ``payable`` constructor.
In this example::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract B {
constructor() public payable {}
@@ -299,8 +303,8 @@ In this example::
Can a contract function accept a two-dimensional array?
=======================================================
-This is not yet implemented for external calls and dynamic arrays -
-you can only use one level of dynamic arrays.
+If you want to pass two-dimensional arrays across non-internal functions,
+you most likely need to use ``pragma experimental "ABIEncoderV2";``.
What is the relationship between ``bytes32`` and ``string``? Why is it that ``bytes32 somevar = "stringliteral";`` works and what does the saved 32-byte hex value mean?
========================================================================================================================================================================
@@ -330,7 +334,7 @@ Can a contract pass an array (static size) or string or ``bytes`` (dynamic size)
Sure. Take care that if you cross the memory / storage boundary,
independent copies will be created::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
uint[20] x;
@@ -367,7 +371,7 @@ contract level) with ``arrayname.length = <some new length>;``. If you get the
::
- pragma solidity ^0.4.18;
+ pragma solidity >=0.4.18 <0.6.0;
// This will not compile
contract C {
@@ -401,7 +405,7 @@ case in C or Java).
Is it possible to return an array of strings (``string[]``) from a Solidity function?
=====================================================================================
-Not yet, as this requires two levels of dynamic arrays (``string`` is a dynamic array itself).
+Only when ``pragma experimental "ABIEncoderV2";`` is used.
What does the following strange check do in the Custom Token contract?
======================================================================
diff --git a/docs/index.rst b/docs/index.rst
index 20fa1505..0449ff42 100644
--- a/docs/index.rst
+++ b/docs/index.rst
@@ -6,15 +6,18 @@ Solidity
:alt: Solidity logo
:align: center
-Solidity is a contract-oriented, high-level language for implementing smart contracts.
-It was influenced by C++, Python and JavaScript
-and is designed to target the Ethereum Virtual Machine (EVM).
+Solidity is an object-oriented, high-level language for implementing smart
+contracts. Smart contracts are programs which govern the behaviour of accounts
+within the Ethereum state.
+
+Solidity was influenced by C++, Python and JavaScript and is designed to target
+the Ethereum Virtual Machine (EVM).
Solidity is statically typed, supports inheritance, libraries and complex
user-defined types among other features.
-As you will see, it is possible to create contracts for voting,
-crowdfunding, blind auctions, multi-signature wallets and more.
+With Solidity you can create contracts for uses such as voting, crowdfunding, blind auctions,
+and multi-signature wallets.
.. note::
The best way to try out Solidity right now is using
diff --git a/docs/installing-solidity.rst b/docs/installing-solidity.rst
index ba373b8f..9d4be70d 100644
--- a/docs/installing-solidity.rst
+++ b/docs/installing-solidity.rst
@@ -154,28 +154,18 @@ Gentoo Linux also provides a solidity package that can be installed using ``emer
Building from Source
====================
-Clone the Repository
---------------------
-
-To clone the source code, execute the following command:
-
-.. code-block:: bash
-
- git clone --recursive https://github.com/ethereum/solidity.git
- cd solidity
-
-If you want to help developing Solidity,
-you should fork Solidity and add your personal fork as a second remote:
-
-.. code-block:: bash
-
- git remote add personal git@github.com:[username]/solidity.git
+Prerequisites - Linux
+---------------------
-Solidity has git submodules. Ensure they are properly loaded:
+You need to install the following dependencies for Linux builds of Solidity:
-.. code-block:: bash
++-----------------------------------+-------------------------------------------------------+
+| Software | Notes |
++===================================+=======================================================+
+| `Git for Linux`_ | Command-line tool for retrieving source from Github. |
++-----------------------------------+-------------------------------------------------------+
- git submodule update --init --recursive
+.. _Git for Linux: https://git-scm.com/download/linux
Prerequisites - macOS
---------------------
@@ -203,7 +193,7 @@ if you ever want to start again from scratch.
Prerequisites - Windows
-----------------------
-You will need to install the following dependencies for Windows builds of Solidity:
+You need to install the following dependencies for Windows builds of Solidity:
+-----------------------------------+-------------------------------------------------------+
| Software | Notes |
@@ -238,6 +228,28 @@ in Visual Studio 2017 Build Tools or Visual Studio 2017:
.. _Visual Studio 2017: https://www.visualstudio.com/vs/
.. _Visual Studio 2017 Build Tools: https://www.visualstudio.com/downloads/#build-tools-for-visual-studio-2017
+Clone the Repository
+--------------------
+
+To clone the source code, execute the following command:
+
+.. code-block:: bash
+
+ git clone --recursive https://github.com/ethereum/solidity.git
+ cd solidity
+
+If you want to help developing Solidity,
+you should fork Solidity and add your personal fork as a second remote:
+
+.. code-block:: bash
+
+ git remote add personal git@github.com:[username]/solidity.git
+
+Solidity has git submodules. Ensure they are properly loaded:
+
+.. code-block:: bash
+
+ git submodule update --init --recursive
External Dependencies
---------------------
diff --git a/docs/introduction-to-smart-contracts.rst b/docs/introduction-to-smart-contracts.rst
index 5ba7ed12..f5d5f89e 100644
--- a/docs/introduction-to-smart-contracts.rst
+++ b/docs/introduction-to-smart-contracts.rst
@@ -8,15 +8,16 @@ Introduction to Smart Contracts
A Simple Smart Contract
***********************
-Let us begin with the most basic example. It is fine if you do not understand everything
-right now, we will go into more detail later.
+Let us begin with a basic example that sets the value of a variable and exposes
+it for other contracts to access. It is fine if you do not understand
+everything right now, we will go into more detail later.
Storage
=======
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract SimpleStorage {
uint storedData;
@@ -32,9 +33,9 @@ Storage
The first line simply tells that the source code is written for
Solidity version 0.4.0 or anything newer that does not break functionality
-(up to, but not including, version 0.5.0). This is to ensure that the
+(up to, but not including, version 0.6.0). This is to ensure that the
contract is not compilable with a new (breaking) compiler version, where it could behave differently.
-So-called pragmas are common instrutions for compilers about how to treat the
+So-called pragmas are common instructions for compilers about how to treat the
source code (e.g. `pragma once <https://en.wikipedia.org/wiki/Pragma_once>`_).
A contract in the sense of Solidity is a collection of code (its *functions*) and
@@ -80,7 +81,7 @@ registering with username and password — all you need is an Ethereum keypair.
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
contract Coin {
// The keyword "public" makes those variables
diff --git a/docs/layout-of-source-files.rst b/docs/layout-of-source-files.rst
index 11f85aac..fb18f8a9 100644
--- a/docs/layout-of-source-files.rst
+++ b/docs/layout-of-source-files.rst
@@ -13,6 +13,12 @@ and :ref:`pragma directives<pragma>`.
Pragmas
=======
+The ``pragma`` keyword can be used to enable certain compiler features
+or checks. A pragma directive is always local to a source file, so
+you have to add the pragma to all your files if you want enable it
+in all of your project. If you :ref:`import<import>` another file, the pragma
+from that file will not automatically apply to the importing file.
+
.. index:: ! pragma, version
.. _version_pragma:
@@ -43,6 +49,13 @@ the exact version of the compiler, so that bugfix releases are still possible.
It is possible to specify much more complex rules for the compiler version,
the expression follows those used by `npm <https://docs.npmjs.com/misc/semver>`_.
+.. note::
+ Using the version pragma will *not* change the version of the compiler.
+ It will also *not* enable or disable features of the compiler. It will just
+ instruct the compiler to check whether its version matches the one
+ required by the pragma. If it does not match, the compiler will issue
+ an error.
+
.. index:: ! pragma, experimental
.. _experimental_pragma:
@@ -64,6 +77,8 @@ for this part of the code is still under development) and has not
received as much testing as the old encoder. You can activate it
using ``pragma experimental ABIEncoderV2;``.
+.. _smt_checker:
+
SMTChecker
~~~~~~~~~~
@@ -261,7 +276,7 @@ for the two input parameters and two returned values.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
/** @title Shape calculator. */
contract ShapeCalculator {
diff --git a/docs/metadata.rst b/docs/metadata.rst
index 9c4f2574..c0613809 100644
--- a/docs/metadata.rst
+++ b/docs/metadata.rst
@@ -93,15 +93,16 @@ explanatory purposes.
}
}
+.. warning::
+ Since the bytecode of the resulting contract contains the metadata hash, any
+ change to the metadata results in a change of the bytecode. This includes
+ changes to a filename or path, and since the metadata includes a hash of all the
+ sources used, a single whitespace change results in different metadata, and
+ different bytecode.
+
.. note::
Note the ABI definition above has no fixed order. It can change with compiler versions.
-Since the bytecode of the resulting contract contains the metadata hash, any
-change to the metadata results in a change of the bytecode. This includes
-changes to a filename or path, and since the metadata includes a hash of all the
-sources used, a single whitespace change results in different metadata, and
-different bytecode.
-
Encoding of the Metadata Hash in the Bytecode
=============================================
@@ -117,19 +118,28 @@ to the end of the deployed bytecode::
So in order to retrieve the data, the end of the deployed bytecode can be checked
to match that pattern and use the Swarm hash to retrieve the file.
+.. note::
+ The compiler currently uses the "swarm version 0" hash of the metadata,
+ but this might change in the future, so do not rely on this sequence
+ to start with ``0xa1 0x65 'b' 'z' 'z' 'r' '0'``. We might also
+ add additional data to this CBOR structure, so the
+ best option is to use a proper CBOR parser.
+
+
Usage for Automatic Interface Generation and NatSpec
====================================================
The metadata is used in the following way: A component that wants to interact
-with a contract (e.g. Mist) retrieves the code of the contract, from that
+with a contract (e.g. Mist or any wallet) retrieves the code of the contract, from that
the Swarm hash of a file which is then retrieved.
That file is JSON-decoded into a structure like above.
The component can then use the ABI to automatically generate a rudimentary
user interface for the contract.
-Furthermore, Mist can use the userdoc to display a confirmation message to the user
-whenever they interact with the contract.
+Furthermore, the wallet can use the NatSpec user documentation to display a confirmation message to the user
+whenever they interact with the contract, together with requesting
+authorization for the transaction signature.
Additional information about Ethereum Natural Specification (NatSpec) can be found `here <https://github.com/ethereum/wiki/wiki/Ethereum-Natural-Specification-Format>`_.
diff --git a/docs/miscellaneous.rst b/docs/miscellaneous.rst
index 5d2819df..12603f2e 100644
--- a/docs/miscellaneous.rst
+++ b/docs/miscellaneous.rst
@@ -48,7 +48,7 @@ non-elementary type, the positions are found by adding an offset of ``keccak256(
So for the following contract snippet::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
struct s { uint a; uint b; }
diff --git a/docs/security-considerations.rst b/docs/security-considerations.rst
index 8df12b7c..bd06276b 100644
--- a/docs/security-considerations.rst
+++ b/docs/security-considerations.rst
@@ -55,7 +55,7 @@ complete contract):
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// THIS CONTRACT CONTAINS A BUG - DO NOT USE
contract Fund {
@@ -78,7 +78,7 @@ as it uses ``call`` which forwards all remaining gas by default:
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// THIS CONTRACT CONTAINS A BUG - DO NOT USE
contract Fund {
@@ -97,7 +97,7 @@ outlined further below:
::
- pragma solidity ^0.4.11;
+ pragma solidity >=0.4.11 <0.6.0;
contract Fund {
/// Mapping of ether shares of the contract.
@@ -136,15 +136,16 @@ Sending and Receiving Ether
- If a contract receives Ether (without a function being called), the fallback function is executed.
If it does not have a fallback function, the Ether will be rejected (by throwing an exception).
During the execution of the fallback function, the contract can only rely
- on the "gas stipend" it is passed (2300 gas) being available to it at that time. This stipend is not enough to access storage in any way.
+ on the "gas stipend" it is passed (2300 gas) being available to it at that time. This stipend is not enough to modify storage
+ (do not take this for granted though, the stipend might change with future hard forks).
To be sure that your contract can receive Ether in that way, check the gas requirements of the fallback function
(for example in the "details" section in Remix).
- There is a way to forward more gas to the receiving contract using
``addr.call.value(x)("")``. This is essentially the same as ``addr.transfer(x)``,
only that it forwards all remaining gas and opens up the ability for the
- recipient to perform more expensive actions (and it only returns a failure code
- and does not automatically propagate the error). This might include calling back
+ recipient to perform more expensive actions (and it returns a failure code
+ instead of automatically propagating the error). This might include calling back
into the sending contract or other state changes you might not have thought of.
So it allows for great flexibility for honest users but also for malicious actors.
@@ -182,7 +183,7 @@ Never use tx.origin for authorization. Let's say you have a wallet contract like
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
// THIS CONTRACT CONTAINS A BUG - DO NOT USE
contract TxUserWallet {
@@ -202,7 +203,7 @@ Now someone tricks you into sending ether to the address of this attack wallet:
::
- pragma solidity >0.4.24;
+ pragma solidity >0.4.99 <0.6.0;
interface TxUserWallet {
function transferTo(address payable dest, uint amount) external;
@@ -223,6 +224,26 @@ Now someone tricks you into sending ether to the address of this attack wallet:
If your wallet had checked ``msg.sender`` for authorization, it would get the address of the attack wallet, instead of the owner address. But by checking ``tx.origin``, it gets the original address that kicked off the transaction, which is still the owner address. The attack wallet instantly drains all your funds.
+
+Two's Complement / Underflows / Overflows
+=========================================
+
+As in many programming languages, Solidity's integer types are not actually integers.
+They resemble integers when the values are small, but behave differently if the numbers are larger.
+For example, the following is true: ``uint8(255) + uint8(1) == 0``. This situation is called
+an *overflow*. It occurs when an operation is performed that requires a fixed size variable
+to store a number (or piece of data) that is outside the range of the variable's data type.
+An *underflow* is the converse situation: ``uint8(0) - uint8(1) == 255``.
+
+In general, read about the limits of two's complement representation, which even has some
+more special edge cases for signed numbers.
+
+Try to use ``require`` to limit the size of inputs to a reasonable range and use the
+:ref:`SMT checker<smt_checker>` to find potential overflows, or
+use a library like
+`SafeMath<https://github.com/OpenZeppelin/openzeppelin-solidity/blob/master/contracts/math/SafeMath.sol>`
+if you want all overflows to cause a revert.
+
Minor Details
=============
@@ -246,12 +267,8 @@ implications, there might be another issue buried beneath it.
Any compiler warning we issue can be silenced by slight changes to the
code.
-Also try to enable the "0.5.0" safety features as early as possible
-by adding ``pragma experimental "v0.5.0";``. Note that in this case,
-the word ``experimental`` does not mean that the safety features are in any
-way risky, it is just a way to enable some features that are
-not yet part of the latest version of Solidity due to backwards
-compatibility.
+Always use the latest version of the compiler to be notified about all recently
+introduced warnings.
Restrict the Amount of Ether
============================
@@ -305,6 +322,12 @@ of "failsafe" mode, which, for example, disables most of the features, hands ove
control to a fixed and trusted third party or just converts the contract into
a simple "give me back my money" contract.
+Ask for Peer Review
+===================
+
+The more people examine a piece of code, the more issues are found.
+Asking people to review your code also helps as a cross-check to find out whether your code
+is easy to understand - a very important criterion for good smart contracts.
*******************
Formal Verification
diff --git a/docs/solidity-by-example.rst b/docs/solidity-by-example.rst
index d01886f8..0f9a71ab 100644
--- a/docs/solidity-by-example.rst
+++ b/docs/solidity-by-example.rst
@@ -36,7 +36,7 @@ of votes.
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
/// @title Voting with delegation.
contract Ballot {
@@ -225,7 +225,7 @@ activate themselves.
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract SimpleAuction {
// Parameters of the auction. Times are either
@@ -542,7 +542,7 @@ Safe Remote Purchase
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract Purchase {
uint public value;
@@ -793,7 +793,7 @@ The full contract
::
- pragma solidity ^0.4.24;
+ pragma solidity >=0.4.24 <0.6.0;
contract ReceiverPays {
address owner = msg.sender;
@@ -988,7 +988,7 @@ The full contract
::
- pragma solidity ^0.4.24;
+ pragma solidity >=0.4.24 <0.6.0;
contract SimplePaymentChannel {
address payable public sender; // The account sending payments.
diff --git a/docs/structure-of-a-contract.rst b/docs/structure-of-a-contract.rst
index d8bc51b8..582e5338 100644
--- a/docs/structure-of-a-contract.rst
+++ b/docs/structure-of-a-contract.rst
@@ -26,7 +26,7 @@ storage.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract SimpleStorage {
uint storedData; // State variable
@@ -46,7 +46,7 @@ Functions are the executable units of code within a contract.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract SimpleAuction {
function bid() public payable { // Function
@@ -68,7 +68,7 @@ Function modifiers can be used to amend the semantics of functions in a declarat
::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract Purchase {
address public seller;
@@ -95,7 +95,7 @@ Events are convenience interfaces with the EVM logging facilities.
::
- pragma solidity ^0.4.21;
+ pragma solidity >=0.4.21 <0.6.0;
contract SimpleAuction {
event HighestBidIncreased(address bidder, uint amount); // Event
@@ -119,7 +119,7 @@ Structs are custom defined types that can group several variables (see
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Ballot {
struct Voter { // Struct
@@ -140,7 +140,7 @@ Enums can be used to create custom types with a finite set of 'constant values'
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Purchase {
enum State { Created, Locked, Inactive } // Enum
diff --git a/docs/style-guide.rst b/docs/style-guide.rst
index b97beebd..7b48ccad 100644
--- a/docs/style-guide.rst
+++ b/docs/style-guide.rst
@@ -52,7 +52,7 @@ Surround top level declarations in solidity source with two blank lines.
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
// ...
@@ -70,7 +70,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
// ...
@@ -89,7 +89,7 @@ Blank lines may be omitted between groups of related one-liners (such as stub fu
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
function spam() public pure;
@@ -109,7 +109,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
function spam() public pure {
@@ -237,7 +237,7 @@ Import statements should always be placed at the top of the file.
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
import "./Owned.sol";
@@ -251,7 +251,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
// ...
@@ -283,7 +283,7 @@ Within a grouping, place the ``view`` and ``pure`` functions last.
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
constructor() public {
@@ -315,7 +315,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract A {
@@ -411,7 +411,7 @@ should:
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Coin {
struct Bank {
@@ -422,7 +422,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract Coin
{
@@ -723,7 +723,7 @@ manner as modifiers if the function declaration is long or hard to read.
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// Base contracts just to make this compile
contract B {
@@ -755,7 +755,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// Base contracts just to make this compile
contract B {
@@ -955,7 +955,7 @@ As shown in the example below, if the contract name is `Congress` and the librar
Yes::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// Owned.sol
contract Owned {
@@ -984,7 +984,7 @@ Yes::
No::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// owned.sol
contract owned {
diff --git a/docs/types.rst b/docs/types.rst
index ca1bd586..84c448ff 100644
--- a/docs/types.rst
+++ b/docs/types.rst
@@ -51,7 +51,7 @@ Operators:
* Comparisons: ``<=``, ``<``, ``==``, ``!=``, ``>=``, ``>`` (evaluate to ``bool``)
* Bit operators: ``&``, ``|``, ``^`` (bitwise exclusive or), ``~`` (bitwise negation)
* Shift operators: ``<<`` (left shift), ``>>`` (right shift)
-* Arithmetic operators: ``+``, ``-``, unary ``-``, ``*``, ``/``, ``%`` (remainder), ``**`` (exponentiation)
+* Arithmetic operators: ``+``, ``-``, unary ``-``, ``*``, ``/``, ``%`` (modulo), ``**`` (exponentiation)
Comparisons
@@ -82,12 +82,25 @@ Addition, Subtraction and Multiplication
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Addition, subtraction and multiplication have the usual semantics.
-They wrap in two's complement notation, meaning that
+They wrap in two's complement representation, meaning that
for example ``uint256(0) - uint256(1) == 2**256 - 1``. You have to take these overflows
into account when designing safe smart contracts.
-Division and Modulus
-^^^^^^^^^^^^^^^^^^^^
+The expression ``-x`` is equivalent to ``(T(0) - x)`` where
+``T`` is the type of ``x``. This means that ``-x`` will not be negative
+if the type of ``x`` is an unsigned integer type. Also, ``-x`` can be
+positive if ``x`` is negative. There is another caveat also resulting
+from two's complement representation::
+
+ int x = -2**255;
+ assert(-x == x);
+
+This means that even if a number is negative, you cannot assume that
+its negation will be positive.
+
+
+Division
+^^^^^^^^
Since the type of the result of an operation is always the type of one of
the operands, division on integers always results in an integer.
@@ -96,7 +109,23 @@ In Solidity, division rounds towards zero. This mean that ``int256(-5) / int256(
Note that in contrast, division on :ref:`literals<rational_literals>` results in fractional values
of arbitrary precision.
-Division by zero and modulus with zero throws a runtime exception.
+.. note::
+ Division by zero causes a failing assert.
+
+Modulo
+^^^^^^
+
+The modulo operation ``a % n`` yields the remainder ``r`` after the division of the operand ``a``
+by the operand ``n``, where ``q = int(a / n)`` and ``r = a - (n * q)``. This means that modulo
+results in the same sign as its left operand (or zero) and ``a % n == -(abs(a) % n)`` holds for negative ``a``:
+
+ * ``int256(5) % int256(2) == int256(1)``
+ * ``int256(5) % int256(-2) == int256(1)``
+ * ``int256(-5) % int256(2) == int256(-1)``
+ * ``int256(-5) % int256(-2) == int256(-1)``
+
+.. note::
+ Modulo with zero causes a failing assert.
Exponentiation
^^^^^^^^^^^^^^
@@ -104,7 +133,8 @@ Exponentiation
Exponentiation is only available for unsigned types. Please take care that the types
you are using are large enough to hold the result and prepare for potential wrapping behaviour.
-Note that ``0**0`` is defined by the EVM as ``1``.
+.. note::
+ Note that ``0**0`` is defined by the EVM as ``1``.
.. index:: ! ufixed, ! fixed, ! fixed point number
@@ -122,7 +152,7 @@ the type and ``N`` represents how many decimal points are available. ``M`` must
Operators:
* Comparisons: ``<=``, ``<``, ``==``, ``!=``, ``>=``, ``>`` (evaluate to ``bool``)
-* Arithmetic operators: ``+``, ``-``, unary ``-``, unary ``+``, ``*``, ``/``, ``%`` (remainder)
+* Arithmetic operators: ``+``, ``-``, unary ``-``, ``*``, ``/``, ``%`` (modulo)
.. note::
The main difference between floating point (``float`` and ``double`` in many languages, more precisely IEEE 754 numbers) and fixed point numbers is
@@ -159,6 +189,13 @@ has the type ``address payable``, if ``x`` is of integer or fixed bytes type, a
If ``x`` is a contract without payable fallback function, then ``address(x)`` will be of type ``address``.
In external function signatures ``address`` is used for both the ``address`` and the ``address payable`` type.
+.. note::
+ It might very well be that you do not need to care about the distinction between ``address``
+ and ``address payable`` and just use ``address`` everywhere. For example,
+ if you are using the :ref:`withdrawal pattern<withdrawal_pattern>`, you can (and should) store the
+ address itself as ``address``, because you invoke the ``transfer`` function on
+ ``msg.sender``, which is an ``address payable``.
+
Operators:
* ``<=``, ``<``, ``==``, ``!=``, ``>=`` and ``>``
@@ -425,9 +462,37 @@ a non-rational number).
String Literals
---------------
-String literals are written with either double or single-quotes (``"foo"`` or ``'bar'``). They do not imply trailing zeroes as in C; ``"foo"`` represents three bytes not four. As with integer literals, their type can vary, but they are implicitly convertible to ``bytes1``, ..., ``bytes32``, if they fit, to ``bytes`` and to ``string``.
+String literals are written with either double or single-quotes (``"foo"`` or ``'bar'``). They do not imply trailing zeroes as in C; ``"foo"`` represents three bytes, not four. As with integer literals, their type can vary, but they are implicitly convertible to ``bytes1``, ..., ``bytes32``, if they fit, to ``bytes`` and to ``string``.
+
+String literals support the following escape characters:
+
+ - ``\<newline>`` (escapes an actual newline)
+ - ``\\`` (backslash)
+ - ``\'`` (single quote)
+ - ``\"`` (double quote)
+ - ``\b`` (backspace)
+ - ``\f`` (form feed)
+ - ``\n`` (newline)
+ - ``\r`` (carriage return)
+ - ``\t`` (tab)
+ - ``\v`` (vertical tab)
+ - ``\xNN`` (hex escape, see below)
+ - ``\uNNNN`` (unicode escape, see below)
+
+``\xNN`` takes a hex value and inserts the appropriate byte, while ``\uNNNN`` takes a Unicode codepoint and inserts an UTF-8 sequence.
+
+The string in the following example has a length of ten bytes.
+It starts with a newline byte, followed by a double quote, a single
+quote a backslash character and then (without separator) the
+character sequence ``abcdef``.
-String literals support escape characters, such as ``\n``, ``\xNN`` and ``\uNNNN``. ``\xNN`` takes a hex value and inserts the appropriate byte, while ``\uNNNN`` takes a Unicode codepoint and inserts an UTF-8 sequence.
+::
+
+ "\n\"\'\\abc\
+ def"
+
+Any unicode line terminator which is not a newline (i.e. LF, VF, FF, CR, NEL, LS, PS) is considered to
+terminate the string literal. Newline only terminates the string literal if it is not preceded by a ``\``.
.. index:: literal, bytes
@@ -446,8 +511,9 @@ Enums
-----
Enums are one way to create a user-defined type in Solidity. They are explicitly convertible
-to and from all integer types but implicit conversion is not allowed. The explicit conversions
-check the value ranges at runtime and a failure causes an exception. Enums needs at least one member.
+to and from all integer types but implicit conversion is not allowed. The explicit conversion
+from integer checks at runtime that the value lies inside the range of the enum and causes a failing assert otherwise.
+Enums needs at least one member.
The data representation is the same as for enums in C: The options are represented by
subsequent unsigned integer values starting from ``0``.
@@ -455,7 +521,7 @@ subsequent unsigned integer values starting from ``0``.
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract test {
enum ActionChoices { GoLeft, GoRight, GoStraight, SitStill }
@@ -515,6 +581,11 @@ omitted. Note that this only applies to function types. Visibility has
to be specified explicitly for functions defined in contracts, they
do not have a default.
+Conversions:
+
+A value of external function type can be explicitly converted to ``address``
+resulting in the address of the contract of the function.
+
A function type ``A`` is implicitly convertible to a function type ``B`` if and only if
their parameter types are identical, their return types are identical,
their internal/external property is identical and the state mutability of ``A``
@@ -524,7 +595,7 @@ is not more restrictive than the state mutability of ``B``. In particular:
- ``view`` functions can be converted to ``non-payable`` functions
- ``payable`` functions can be converted to ``non-payable`` functions
-No other conversions are possible.
+No other conversions between function types are possible.
The rule about ``payable`` and ``non-payable`` might be a little
confusing, but in essence, if a function is ``payable``, this means that it
@@ -532,8 +603,8 @@ also accepts a payment of zero Ether, so it also is ``non-payable``.
On the other hand, a ``non-payable`` function will reject Ether sent to it,
so ``non-payable`` functions cannot be converted to ``payable`` functions.
-If a function type variable is not initialized, calling it will result
-in an exception. The same happens if you call a function after using ``delete``
+If a function type variable is not initialised, calling it results
+in a failed assertion. The same happens if you call a function after using ``delete``
on it.
If external function types are used outside of the context of Solidity,
@@ -544,10 +615,12 @@ Note that public functions of the current contract can be used both as an
internal and as an external function. To use ``f`` as an internal function,
just use ``f``, if you want to use its external form, use ``this.f``.
-Additionally, public (or external) functions also have a special member called ``selector``,
+Members:
+
+Public (or external) functions also have a special member called ``selector``,
which returns the :ref:`ABI function selector <abi_function_selector>`::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract Selector {
function f() public pure returns (bytes4) {
@@ -557,7 +630,7 @@ which returns the :ref:`ABI function selector <abi_function_selector>`::
Example that shows how to use internal function types::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
library ArrayUtils {
// internal functions can be used in internal library functions because
@@ -608,7 +681,7 @@ Example that shows how to use internal function types::
Another example that uses external function types::
- pragma solidity ^0.4.22;
+ pragma solidity >=0.4.22 <0.6.0;
contract Oracle {
struct Request {
@@ -680,18 +753,18 @@ non-persistent area where function arguments are stored, and behaves mostly like
depending on the kind of variable, function type, etc., but all complex types must now give an explicit
data location.
-Data locations are important because they change how assignments behave:
-assignments between storage and memory and also to a state variable (even from other state variables)
-always create an independent copy.
-Assignments to local storage variables only assign a reference though, and
-this reference always points to the state variable even if the latter is changed
-in the meantime.
-On the other hand, assignments from a memory stored reference type to another
-memory-stored reference type do not create a copy.
+Data locations are not only relevant for persistency of data, but also for the semantics of assignments:
+assignments between storage and memory (or from calldata) always create an independent copy.
+Assignments from memory to memory only create references. This means that changes to one memory variable
+are also visible in all other memory variables that refer to the same data.
+Assignments from storage to a local storage variables also only assign a reference.
+In contrast, all other assignments to storage always copy. Examples for this case
+are assignments to state variables or to members of local variables of storage struct type, even
+if the local variable itself is just a reference.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract C {
uint[] x; // the data location of x is storage
@@ -717,13 +790,6 @@ memory-stored reference type do not create a copy.
function h(uint[] memory) public pure {}
}
-Summary
-^^^^^^^
-
-Forced data location:
- - parameters (not return) of external functions: calldata
- - state variables: storage
-
.. index:: ! array
.. _arrays:
@@ -732,9 +798,10 @@ Arrays
------
Arrays can have a compile-time fixed size or they can be dynamic.
-For storage arrays, the element type can be arbitrary (i.e. also other
-arrays, mappings or structs). For memory arrays, it cannot be a mapping and
-has to be an ABI type if it is an argument of a publicly-visible function.
+The are few restrictions for the element, it can also be
+another array, a mapping or a struct. The general restrictions for
+types apply, though, in that mappings can only be used in storage
+and publicly-visible functions need parameters that are ABI types.
An array of fixed size ``k`` and element type ``T`` is written as ``T[k]``,
an array of dynamic size as ``T[]``. As an example, an array of 5 dynamic
@@ -744,9 +811,13 @@ third dynamic array, you use ``x[2][1]`` (indices are zero-based and
access works in the opposite way of the declaration, i.e. ``x[2]``
shaves off one level in the type from the right).
+Accessing an array past its end causes a revert. If you want to add
+new elements, you have to use ``.push()`` or increase the ``.length``
+member (see below).
+
Variables of type ``bytes`` and ``string`` are special arrays. A ``bytes`` is similar to ``byte[]``,
-but it is packed tightly in calldata. ``string`` is equal to ``bytes`` but does not allow
-length or index access (for now).
+but it is packed tightly in calldata and memory. ``string`` is equal to ``bytes`` but does not allow
+length or index access.
So ``bytes`` should always be preferred over ``byte[]`` because it is cheaper.
As a rule of thumb, use ``bytes`` for arbitrary-length raw byte data and ``string``
for arbitrary-length string (UTF-8) data. If you can limit the length to a certain
@@ -766,14 +837,14 @@ The numeric index will become a required parameter for the getter.
Allocating Memory Arrays
^^^^^^^^^^^^^^^^^^^^^^^^
-Creating arrays with variable length in memory can be done using the ``new`` keyword.
+You can use the ``new`` keyword to create arrays with a runtime-dependent length in memory.
As opposed to storage arrays, it is **not** possible to resize memory arrays (e.g. by assigning to
the ``.length`` member). You either have to calculate the required size in advance
or create a new memory array and copy every element.
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function f(uint len) public pure {
@@ -795,7 +866,7 @@ assigned to a variable right away.
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract C {
function f() public pure {
@@ -809,14 +880,14 @@ assigned to a variable right away.
The type of an array literal is a memory array of fixed size whose base
type is the common type of the given elements. The type of ``[1, 2, 3]`` is
``uint8[3] memory``, because the type of each of these constants is ``uint8``.
-Because of that, it was necessary to convert the first element in the example
+Because of that, it is necessary to convert the first element in the example
above to ``uint``. Note that currently, fixed size memory arrays cannot
be assigned to dynamically-sized memory arrays, i.e. the following is not
possible:
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
// This will not compile.
contract C {
@@ -836,15 +907,31 @@ Members
^^^^^^^
**length**:
- Arrays have a ``length`` member to read their number of elements.
- Dynamically-sized arrays (only available for storage) have a read-write ``length`` member to resize the array. Increasing the length adds uninitialized elements to the array, this has *O(1)* complexity. Reducing the length performs :ref:``delete`` on each removed element and has *O(n)* complexity where *n* is the number of elements being deleted. Please note that calling ``length--`` on an empty array will set the length of the array to 2^256-1 due to ``uint256`` underflow wrapping.
+ Arrays have a ``length`` member that contains their number of elements.
+ The length of memory arrays is fixed (but dynamic, i.e. it can depend on runtime parameters) once they are created.
+ For dynamically-sized arrays (only available for storage), this member can be assigned to resize the array.
+ Accessing elements outside the current length does not automatically resize the array and instead causes a failing assertion.
+ Increasing the length adds new zero-initialised elements to the array.
+ Reducing the length performs an implicit :ref:``delete`` on each of the removed elements.
**push**:
- Dynamic storage arrays and ``bytes`` (not ``string``) have a member function called ``push`` that can be used to append an element at the end of the array. The function returns the new length.
+ Dynamic storage arrays and ``bytes`` (not ``string``) have a member function called ``push`` that you can use to append an element at the end of the array. The element will be zero-initialised. The function returns the new length.
**pop**:
- Dynamic storage arrays and ``bytes`` (not ``string``) have a member function called ``pop`` that can be used to remove an element from the end of the array. This will also implicitly call :ref:``delete`` on the removed element.
+ Dynamic storage arrays and ``bytes`` (not ``string``) have a member function called ``pop`` that you can use to remove an element from the end of the array. This also implicitly calls :ref:``delete`` on the removed element.
.. warning::
- It is not yet possible to use arrays of arrays in external functions.
+ If you use ``.length--`` on an empty array, it causes an underflow and
+ thus sets the length to ``2**256-1``.
+
+.. note::
+ Increasing the length of a storage array has constant gas costs because
+ storage is assumed to be zero-initialised, while decreasing
+ the length has at least linear cost (but in most cases worse than linear),
+ because it includes explicitly clearing the removed
+ elements similar to calling :ref:``delete`` on them.
+
+.. note::
+ It is not yet possible to use arrays of arrays in external functions
+ (but they are supported in public functions).
.. note::
In EVM versions before Byzantium, it was not possible to access
@@ -854,7 +941,7 @@ Members
::
- pragma solidity ^0.4.16;
+ pragma solidity >=0.4.16 <0.6.0;
contract ArrayContract {
uint[2**20] m_aLotOfIntegers;
@@ -862,15 +949,34 @@ Members
// dynamic array of pairs (i.e. of fixed size arrays of length two).
// Because of that, T[] is always a dynamic array of T, even if T
// itself is an array.
+ // Data location for all state variables is storage.
bool[2][] m_pairsOfFlags;
// newPairs is stored in memory - the only possibility
- // for public function arguments
+ // for public contract function arguments
function setAllFlagPairs(bool[2][] memory newPairs) public {
- // assignment to a storage array replaces the complete array
+ // assignment to a storage array performs a copy of ``newPairs`` and
+ // replaces the complete array ``m_pairsOfFlags``.
m_pairsOfFlags = newPairs;
}
+ struct StructType {
+ uint[] contents;
+ uint moreInfo;
+ }
+ StructType s;
+
+ function f(uint[] memory c) public {
+ // stores a reference to ``s`` in ``g``
+ StructType storage g = s;
+ // also changes ``s.moreInfo``.
+ g.moreInfo = 2;
+ // assigns a copy because ``g.contents``
+ // is not a local variable, but a member of
+ // a local variable.
+ g.contents = c;
+ }
+
function setFlagPair(uint index, bool flagA, bool flagB) public {
// access to a non-existing index will throw an exception
m_pairsOfFlags[index][0] = flagA;
@@ -934,7 +1040,7 @@ shown in the following example:
::
- pragma solidity ^0.4.11;
+ pragma solidity >=0.4.11 <0.6.0;
contract CrowdFunding {
// Defines a new type with two fields.
@@ -956,7 +1062,10 @@ shown in the following example:
function newCampaign(address payable beneficiary, uint goal) public returns (uint campaignID) {
campaignID = numCampaigns++; // campaignID is return variable
- // Creates new struct and saves in storage. We leave out the mapping type.
+ // Creates new struct in memory and copies it to storage.
+ // We leave out the mapping type, because it is not valid in memory.
+ // If structs are copied (even from storage to storage), mapping types
+ // are always omitted, because they cannot be enumerated.
campaigns[campaignID] = Campaign(beneficiary, goal, 0, 0);
}
@@ -986,11 +1095,12 @@ Struct types can be used inside mappings and arrays and they can itself
contain mappings and arrays.
It is not possible for a struct to contain a member of its own type,
-although the struct itself can be the value type of a mapping member.
+although the struct itself can be the value type of a mapping member
+or it can contain a dynamically-sized array of its type.
This restriction is necessary, as the size of the struct has to be finite.
Note how in all the functions, a struct type is assigned to a local variable
-(of the default storage data location).
+with data location ``storage``.
This does not copy the struct but only stores a reference so that assignments to
members of the local variable actually write to the state.
@@ -1001,7 +1111,7 @@ assigning it to a local variable, as in
.. index:: !mapping
Mappings
-========
+--------
You declare mapping types with the syntax ``mapping(_KeyType => _ValueType)``.
The ``_KeyType`` can be any elementary type. This means it can be any of
@@ -1010,7 +1120,7 @@ or complex types like contract types, enums, mappings, structs and any array typ
apart from ``bytes`` and ``string`` are not allowed.
``_ValueType`` can be any type, including mappings.
-You can think of mappings as `hash tables <https://en.wikipedia.org/wiki/Hash_table>`_, which are virtually initialized
+You can think of mappings as `hash tables <https://en.wikipedia.org/wiki/Hash_table>`_, which are virtually initialised
such that every possible key exists and is mapped to a value whose
byte-representation is all zeros, a type's :ref:`default value <default-value>`. The similarity ends there, the key data is not stored in a
mapping, only its ``keccak256`` hash is used to look up the value.
@@ -1018,8 +1128,11 @@ mapping, only its ``keccak256`` hash is used to look up the value.
Because of this, mappings do not have a length or a concept of a key or
value being set.
-Mappings are **only** allowed for state variables (or as storage reference types
-in internal functions).
+Mappings can only have a data location of ``storage`` and thus
+are allowed for state variables, as storage reference types
+in functions, or as parameters for library functions.
+They cannot be used as parameters or return parameters
+of contract functions that are publicly visible.
You can mark variables of mapping type as ``public`` and Solidity creates a
:ref:`getter <visibility-and-getters>` for you. The ``_KeyType`` becomes a
@@ -1030,7 +1143,7 @@ each ``_KeyType``, recursively. For example with a mapping:
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract MappingExample {
mapping(address => uint) public balances;
@@ -1075,7 +1188,7 @@ value it referred to previously.
::
- pragma solidity ^0.4.0;
+ pragma solidity >=0.4.0 <0.6.0;
contract DeleteExample {
uint data;
diff --git a/docs/using-the-compiler.rst b/docs/using-the-compiler.rst
index 1e4bbecc..39520bec 100644
--- a/docs/using-the-compiler.rst
+++ b/docs/using-the-compiler.rst
@@ -10,13 +10,17 @@ Using the Commandline Compiler
******************************
.. note::
- This section doesn't apply to :ref:`solcjs <solcjs>`.
+ This section does not apply to :ref:`solcjs <solcjs>`, not even if it is used in commandline mode.
One of the build targets of the Solidity repository is ``solc``, the solidity commandline compiler.
Using ``solc --help`` provides you with an explanation of all options. The compiler can produce various outputs, ranging from simple binaries and assembly over an abstract syntax tree (parse tree) to estimations of gas usage.
If you only want to compile a single file, you run it as ``solc --bin sourceFile.sol`` and it will print the binary. If you want to get some of the more advanced output variants of ``solc``, it is probably better to tell it to output everything to separate files using ``solc -o outputDirectory --bin --ast --asm sourceFile.sol``.
-Before you deploy your contract, activate the optimizer while compiling using ``solc --optimize --bin sourceFile.sol``. By default, the optimizer will optimize the contract for 200 runs. If you want to optimize for initial contract deployment and get the smallest output, set it to ``--runs=1``. If you expect many transactions and don't care for higher deployment cost and output size, set ``--runs`` to a high number.
+Before you deploy your contract, activate the optimizer when compiling using ``solc --optimize --bin sourceFile.sol``.
+By default, the optimizer will optimize the contract assuming it is called 200 times across its lifetime.
+If you want the initial contract deployment to be cheaper and the later function executions to be more expensive,
+set it to ``--runs=1``. If you expect many transactions and do not care for higher deployment cost and
+output size, set ``--runs`` to a high number.
The commandline compiler will automatically read imported files from the filesystem, but
it is also possible to provide path redirects using ``prefix=path`` in the following way:
@@ -43,7 +47,7 @@ Either add ``--libraries "Math:0x12345678901234567890 Heap:0xabcdef0123456"`` to
If ``solc`` is called with the option ``--link``, all input files are interpreted to be unlinked binaries (hex-encoded) in the ``__LibraryName____``-format given above and are linked in-place (if the input is read from stdin, it is written to stdout). All options except ``--libraries`` are ignored (including ``-o``) in this case.
-If ``solc`` is called with the option ``--standard-json``, it will expect a JSON input (as explained below) on the standard input, and return a JSON output on the standard output.
+If ``solc`` is called with the option ``--standard-json``, it will expect a JSON input (as explained below) on the standard input, and return a JSON output on the standard output. This is the recommended interface for more complex and especially automated uses.
.. _evm-version:
.. index:: ! EVM version, compile target
@@ -60,18 +64,23 @@ version to compile for to avoid particular features or behaviours.
behaviour. Please ensure, especially if running a private chain, that you
use matching EVM versions.
-You use the ``--evm-version`` option on the command line:
+On the command line, you can select the EVM version as follows:
.. code-block:: shell
solc --evm-version <VERSION> contract.sol
-Or if using the :ref:`standard JSON interface <compiler-api>`, with the ``evmVersion`` key:
+In the :ref:`standard JSON interface <compiler-api>`, use the ``"evmVersion"``
+key in the ``"settings"`` field:
-.. code-block:: json
+.. code-block:: none
{
- "evmVersion": "<VERSION>"
+ "sources": { ... },
+ "settings": {
+ "optimizer": { ... },
+ "evmVersion": "<VERSION>"
+ }
}
Target options
@@ -80,7 +89,7 @@ Target options
Below is a list of target EVM versions and the compiler-relevant changes introduced
at each version. Backward compatibility is not guaranteed between each version.
-- ``homestead``
+- ``homestead`` (oldest version)
- ``tangerineWhistle``
- gas cost for access to other accounts increased, relevant for gas estimation and the optimizer.
- all gas sent by default for external calls, previously a certain amount had to be retained.
@@ -88,7 +97,7 @@ at each version. Backward compatibility is not guaranteed between each version.
- gas cost for the ``exp`` opcode increased, relevant for gas estimation and the optimizer.
- ``byzantium`` (**default**)
- opcodes ``returndatacopy``, ``returndatasize`` and ``staticcall`` are available in assembly.
- - the ``staticcall`` opcode is used when calling view or pure functions, which prevents the functions from modifying state at the EVM level, i.e., even applies when you use invalid type conversions.
+ - the ``staticcall`` opcode is used when calling non-library view or pure functions, which prevents the functions from modifying state at the EVM level, i.e., even applies when you use invalid type conversions.
- it is possible to access dynamic data returned from function calls.
- ``revert`` opcode introduced, which means that ``revert()`` will not waste gas.
- ``constantinople`` (still in progress)
@@ -100,11 +109,16 @@ at each version. Backward compatibility is not guaranteed between each version.
Compiler Input and Output JSON Description
******************************************
-These JSON formats are used by the compiler API as well as are available through ``solc``. These are subject to change,
-some fields are optional (as noted), but it is aimed at to only make backwards compatible changes.
+The recommended way to interface with the Solidity compiler especially for
+more complex and automated setups is the so-called JSON-input-output interface.
+The same interface is provided by all distributions of the compiler.
+
+The fields are generally subject to change,
+some are optional (as noted), but we try to only make backwards compatible changes.
The compiler API expects a JSON formatted input and outputs the compilation result in a JSON formatted output.
+The following subsections describe the format through an example.
Comments are of course not permitted and used here only for explanatory purposes.
Input Description
@@ -113,7 +127,7 @@ Input Description
.. code-block:: none
{
- // Required: Source code language, such as "Solidity", "serpent", "lll", "assembly", etc.
+ // Required: Source code language, such as "Solidity", "Vyper", "lll", "assembly", etc.
language: "Solidity",
// Required
sources:
diff --git a/docs/yul.rst b/docs/yul.rst
index e010a708..cfeec4db 100644
--- a/docs/yul.rst
+++ b/docs/yul.rst
@@ -83,6 +83,7 @@ Grammar::
FunctionDefinition |
VariableDeclaration |
Assignment |
+ If |
Expression |
Switch |
ForLoop |
@@ -417,6 +418,12 @@ The following functions must be available:
| create(v:u256, p:u256, s:u256) | create new contract with code mem[p..(p+s)) and send v wei |
| | and return the new address |
+---------------------------------------------+-----------------------------------------------------------------+
+| create2(v:u256, n:u256, p:u256, s:u256) | create new contract with code mem[p...(p+s)) at address |
+| | keccak256(0xff . self . n . keccak256(mem[p...(p+s))) |
+| | and send v wei and return the new address, where ``0xff`` is a |
+| | 8 byte value, ``self`` is the current contract's address |
+| | as a 20 byte value and ``n`` is a big-endian 256-bit value |
++---------------------------------------------+-----------------------------------------------------------------+
| call(g:u256, a:u256, v:u256, in:u256, | call contract at address a with input mem[in..(in+insize)) |
| insize:u256, out:u256, | providing g gas and v wei and output area |
| outsize:u256) | mem[out..(out+outsize)) returning 0 on error (eg. out of gas) |
@@ -492,6 +499,8 @@ The following functions must be available:
+---------------------------------------------+-----------------------------------------------------------------+
| extcodecopy(a:u256, t:u256, f:u256, s:u256) | like codecopy(t, f, s) but take code at address a |
+---------------------------------------------+-----------------------------------------------------------------+
+| extcodehash(a:u256) | code hash of address a |
++---------------------------------------------+-----------------------------------------------------------------+
| *Others* |
+---------------------------------------------+-----------------------------------------------------------------+
| discard(unused:bool) | discard value |