EOS合约虚拟机架构
EOS操作系统软件的目的是可以支持多种虚拟机,同时可以按需求增加新的虚拟机。
以太虚拟机(EVM)
这个虚拟机已经被用于大多数现有的智能合约,并且可以在EOS系统区块链上使用。可以想象,在EOS操作系统区块链上,EVM合约可以在内部沙箱中运行,只需要少量适配就可以与其他EOS应用程序交互。
Wren
Wren(http://wren.io)是一种小型的、快速的、基于类别的编程语言。短小精悍、易于文档记录和理解的代码库。具有非常好的性能,并且可以很容易地嵌入C++应用程序中。
Web Assembly(WASM)
WASM是构建高性能Web应用程序的新兴Web标准,通过少量适配就可以被明确定义和沙箱化。WASM的好处在于业界广泛支持,因此可以用熟悉的语言开发开发智能合约,例如C或C++/Rust。
以太发人员已经开始适配WASM,以提供适当的沙箱并使用以太坊WASM定义(https://github.com/ewasm/design)。这种方法很容易改编后用于EOS系统软件集成。
性能原因
开始使用WREN, 1000 TPS, 达不到EOS的性能要求。WASM的测试达到 50000 TPS。实际主网运行,3996 TPS,一般100左右。https://eosnetworkmonitor.io/开发友好多语言兼容
当前主要使用cpp工具集。
https://steemit.com/eos/@dantheman/web-assembly-on-eos-50-000-transfers-per-second
EOS的账户设计
比特币/以太坊使用私钥和地址概念的账户系统。
EOS使用一个可读的12个字符来创建账户。
➜ eos-contracts kcleos get account hellomykey11
created: 2018-11-16T06:54:10.500
permissions:
owner 1: 1 EOS7ijWCBmoXBi3CgtK7DJxentZZeTkeUnaSDvyro9dq7Sd1C3dC4
active 1: 1 EOS58idArYhygKSaT6i9q4PjXoaSYC5bv93NEfWh5qipASzpAMxyG, 1 [email protected]
memory:
quota: 539.8 KiB used: 521.8 KiB
net bandwidth:
delegated: 1.0000 EOS (total staked delegated to account from others)
used: 268.2 KiB
available: 437.9 KiB
limit: 706 KiB
cpu bandwidth:
delegated: 1.0000 EOS (total staked delegated to account from others)
used: 54.73 ms
available: 78.12 ms
limit: 132.8 ms
EOS balances:
liquid: 307.9120 EOS
staked: 0.0000 EOS
unstaking: 0.0000 EOS
total: 307.9120 EOS
账户的消息处理
- 每个账户都可以发送结构化消息到其他账户
- 账户可以定义消息被接收后的处理脚本(合约)
- 每个账户有自己独有的数据库
- 账户的消息处理程序可以向其他账户发送消息
消息和自动的消息处理程序的组合是EOS定义智能合约的方式
mykey创建账户:
https://eosq.app/tx/f99f8057290488bd6c11b9fdab70197a8a50efcccada62acc6b0b18a4988a1bb
ETH EOS 合约升级设计差异
"code is law" vs "intent of code is law"
李嘉图合约,社区治理
https://medium.com/@bytemaster/the-intent-of-code-is-law-c0e0cd318032
EOS合约开发
- Action handler and Action Apply Context
Smart contracts provide action handlers to do the work of requested actions. Each time an action runs, i.e., the action is "applied" by running the apply method in the contract implementation, EOSIO creates a new action "apply" context within which the action runs. The diagram below illustrates key elements of the action "apply" context.
helloworld合约
#include
class hello : public eosio::contract {
public:
using contract::contract;
/// @abi action
void hi( account_name user ) {
print( "Hello, ", name{user} );
}
};
extern "C" {
void apply( uint64_t receiver, uint64_t code, uint64_t action ) {
auto self = receiver;
if( action == N(onerror)) {
/* onerror is only valid if it is for the "eosio" code account and authorized by "eosio"'s "active permission */
eosio_assert(code == N(eosio), "onerror action's are only valid from the \"eosio\" system account");
}
if( code == self || action == N(onerror) ) {
hello thiscontract( self );
switch( action ) {
EOSIO_API( hello, (hi) )
}
}
}
}
- 合约数据持久化存储 Multi-Index API
EOS中引入了Multi-Index多索引容器,Multi-Index基于boost中的Multi-Index开发。Multi-Index API 提供了EOSIO数据库的C++接口,它可以存储任意数据类型。通过API能够读取和修改EOSIO数据库中的持久状态。
eosio::multi_index
在概念上被视为传统数据库中的表格,其中行是容器中的单个对象,列是容器中对象的成员属性,并且索引通过与一个键兼容的键提供对对象的快速查找对象成员属性。
https://github.com/EOSIO/eos/blob/v1.6.0/contracts/eosiolib/multi_index.hpp
https://www.boost.org/doc/libs/1_66_0/libs/multi_index/doc/index.html
class token : public contract {
...
struct account {
asset balance;
uint64_t primary_key()const { return balance.symbol.name(); }
};
struct currency_stats {
asset supply;
asset max_supply;
account_name issuer;
uint64_t primary_key()const { return supply.symbol.name(); }
};
typedef eosio::multi_index accounts;
typedef eosio::multi_index stats;
...
};
- EOSIO合约基础库eosiolib
智能合约开发最重要的eosiolib库,现在已经整合到eosio.cdt项目中了。
https://github.com/EOSIO/eosio.cdt
eosiolib库,位于eosio.cdt/libraries/eosiolib目录,共有40个C/C++文件,下面这张图描述了这些文件之间的引用关系:
- db.h
- action.h
- crypto.h
- system.h
- wasm_interface.cpp
https://github.com/EOSIO/eos/blob/v1.7.1/libraries/chain/wasm_interface.cpp
- 开发环境
vscode + cpp plugin
EOS Studio, https://www.eosstudio.io/
开发库不成熟,对比以太openzeppelin。
开发测试组件缺乏,合约测试麻烦。缺乏想truffle一样的轻量级的开发环境。(mykey的开发主要是js/shell脚本在kylin测试网测试。本地的测试使用docker。)
基础工具待完善,交易的资源费用预估等。
https://github.com/OpenZeppelin/openzeppelin-solidity
https://hub.docker.com/r/eosio/eos-dev
https://github.com/eostea/eos-wiki