Skip to content

Solidity to Syscall Mapping ​

Back to Syscalls

Automatic Lowering ​

The compiler automatically translates standard Solidity constructs to the corresponding NeoVM syscalls. No manual syscall invocation is needed for these patterns.

For a shorter reader guide that separates runtime calls from devpack usage, see Syscalls and Devpack.

Mapping Table ​

Solidity ConstructSyscall / Neo CallNotes
msg.senderSystem.Runtime.GetCallingScriptHashReturns caller's script hash (UInt160)
address(this)System.Runtime.GetExecutingScriptHashReturns current contract's script hash
block.timestampSystem.Runtime.GetTimeMilliseconds, normalized to seconds
block.numberLedger.currentIndex (native call)Not a syscall — uses System.Contract.Call
gasleft()System.Runtime.GasLeftRemaining GAS in current invocation
State variable readSystem.Storage.GetKey derived from variable name via SHA256
State variable writeSystem.Storage.PutKey derived from variable name via SHA256
mapping[key] readSystem.Storage.GetKey = SHA256(serialize(key) || slot)
mapping[key] writeSystem.Storage.PutSame derived key
emit Event(...)System.Runtime.NotifyEvent name + args as notification
require(Runtime.checkWitness(addr))System.Runtime.CheckWitnessWitness verification (200 GAS)
address(target).call(...)System.Contract.CallCross-contract invocation (10 GAS)
address(target).staticcall(...)System.Contract.Call (read-only flags)Read-only cross-contract call
keccak256(...)CryptoLib.keccak256 (native call)Via System.Contract.Call, not a syscall
sha256(...)CryptoLib.sha256 (native call)Via System.Contract.Call, not a syscall

Example Lowering ​

solidity
// What you write:
contract Example {
    mapping(address => uint256) public balances;
    event Transfer(address indexed from, address indexed to, uint256 amount);

    function transfer(address to, uint256 amount) external {
        require(Runtime.checkWitness(msg.sender), "unauthorized");
        balances[msg.sender] -= amount;
        balances[to] += amount;
        emit Transfer(msg.sender, to, amount);
    }
}

// What the compiler emits (pseudocode):
// 1. System.Runtime.CheckWitness(callingScriptHash)  — 200 GAS
// 2. System.Storage.GetContext()                      — 1 GAS
// 3. System.Storage.Get(ctx, derived_key_sender)      — 100 GAS
// 4. System.Storage.Put(ctx, derived_key_sender, new) — 1,000 GAS
// 5. System.Storage.Get(ctx, derived_key_to)          — 100 GAS
// 6. System.Storage.Put(ctx, derived_key_to, new)     — 1,000 GAS
// 7. System.Runtime.Notify("Transfer", [from, to, amount]) — 1 GAS
// Total: ~2,402 GAS units (syscalls only, excludes opcode costs)

MIT Licensed