solc:solidity的编译器
solidity编写的以太坊智能合约可通过命令行编译工具solc来进行编译,成为以太坊虚拟机中的代码。solc编译后最终部署到链上形成我们所见到的各种智能合约。
作为一个solidity命令行编译工具,我们来看看官网都怎么说solc。
solc的安装很简单:
npm install -g solc
//或者
npm install -g solc-cli
//或者
sudo apt-get install solc
安装完成后我们来看,solc --help
,solc –help命令显示所有的solc命令选项。编译器可以生成各种输出,比如最终的二进制合约文件、语法树的汇编或者需要预计的要花费的gas等。solc --bin sourceFile.sol
,可以编译后输出一个名为sourceFile.sol的智能合约文件。如果你想从solc
获得更丰富的一些输出变量,你可以使用solc -o outputDirectory --bin --ast --asm sourceFile.sol
。
你在部署以太坊智能合约之前可以用solc --optimize --bin sourceFile.sol
优化一下。默认情况下solc编译器会帮你优化200次。你也可以设置 --runs=1
,这样就按照最小化的方式进行编译,如果你希望多次交易不太在乎成本,那你可以设置成你想要的次数:)。
命令行编译器会自动读取需要导入的文件,也可以通过使用prefix = path
来指定路径,例如:
solc github.com/ethereum/dapp-bin/=/usr/local/lib/dapp-bin/ =/usr/local/lib/fallback file.sol
这样编译器就会从指定目录github.com/ethereum/dapp-bin/
下的/usr/local/lib/dapp-bin/
目录开始搜索,如果没有找到文件,它将查看/usr/local/lib/fallback
。solc将只读取你指定的这两个路径的,因此像import "/etc/passwd";
必须要通过/=
重新映射才起作用。如果有多个匹配,则选择具有最长公共前缀的进行匹配。
出于安全上的考虑,编译器限制了它可以访问的一些目录。在命令行中指定的源文件的路径(及其子目录)和命令行指定的路径外其他所有内容都会被拒绝。--allow-paths /sample/path,/another/sample/path
来切换。
如果智能合约使用了libraries,你会注意到字节码包含了__LibraryName______
的子字符串。您可以使用solc作为链接器,这意味着它将在这些点为您插入库地址。
可以通过添加库--libraries "Math:0x12345678901234567890 Heap:0xabcdef0123456"
到您的命令,以提供每个库的地址,或者使用文件中的说明字符串(每行一个库),并使用--libraries fileName
运行solc。
如果用选项--link
调用Solc,则所有输入文件都被解释为未链接的二进制文件(HEX编码),在上面给出的__LibraryName____
格式中,将其链接到适当地址(如果从stdin读取输入,则将其写入stdout)。在这种情况下,除了库外,所有选项都被忽略(包括-o
)。
如果用--standard-json
调用SOLC,它就将标准的JSON输入(如下所述),并返回JSON输出。
solc编译器输入输出JSON描述
这些JSON格式通过编译器API使用,可以通过SOLC获得。内容都是可以修改的,一些对象是可选的(如前所述),其目的是向后兼容。
编译器的API需要一个JSON格式的输入,然后以JSON格式输出编译结果。
注意不允许注释。下面示例中的注释,是官网为了学习者更好的理解标注的。
- 输入格式说明:
{
// Required: Source code language, such as "Solidity", "serpent", "lll", "assembly", etc.
language: "Solidity",
// Required
sources:
{
// The keys here are the "global" names of the source files,
// imports can use other files via remappings (see below).
"myFile.sol":
{
// Optional: keccak256 hash of the source file
// It is used to verify the retrieved conten