Unlike other forms of software in which the data is (generally) external to the software that manages it, contract data is stored within a namespace (a key/value store) that is logically "inside" the contract itself.
At a protocol level addresses (including contracts) have balances. Contracts also have code. That code will lay out data organization within its own namespace. All three are included in the idea of "state." In this context, it could be described as the condition or just the data.
Consider this simple, contrived contract:
pragma solidity 0.5.16;
contract State {
uint256 public someVal;
function set(uint v) public payable {
someVal = v;
}
}
There is a getter function (public
) and it will return someVal
. There is a function that can update it AND accept ether. So, there is a uint
stored in the contract, and the contract has a balance that is not necessarily zero. Additionally, the address where the contract bytecode is deployed has code.
All three are established by processing transactions and computing the "state" of the chain.
BTW, we could restrict the allowable state transitions with something like:
require(v > 100, "no small numbers, please.");
That would be in addition to protocol-level restrictions such as not sending more money than one actually has.
In case you are interested in how it is laid out, here is an over-simplified summary. The compiler will read someVal
and assign it "slot 0" because it was first. The EVM will compute (pseudo) a key with hash(contractAddress,0)
. Including the contract address in the hash prevents collisions with other contracts. The key provides a logical location in which to store a 32-byte word (the value). The "State" can be understood as a key/value store where all the contracts manage their own variables as they see fit and the protocol looks after protocol-level concerns such as balances.
As you consider that, keep in mind it is a logical description and doesn't include the Merkle/Patricia tries that help with organization and validation and it is silent on the issues of physical storage, indexing, caching strategies, light client implementations and other client-side implementation concerns.
Hope it helps.