How to Install the Solidity Compiler via Source Code Compilation?

5/5 - (4 votes)
How to Install the Solidity Compiler via Source Code Compilation?

In this article, we’ll produce, i.e., compile a Solidity compiler from its source code. Platform compilation is not an operation regular computer users explicitly do very often, if ever. However, in some unusual situations, we need specific software in terms of its (previous) version, or it should run in our exotic environment, etc.

Regardless of the reason, we’ll go through the listing and explanations of each software prerequisite before compiling the Solidity compiler.

Even more, we’ll follow detailed steps of how to install all prerequisites, check their state after installation, and finally perform the main show: compile the Solidity compiler (by following a shorter and a longer approach).

This is the third way of installing the Solidity compiler. For the other ways, feel free to check out those tutorials on the Finxter blog:

🌍 Related Tutorials:

We cannot guarantee this will work on your machine. Do it at your own risk. We only share what worked for us but running these commands can pose security risks due to the dependency of many external (third-party) libraries.

If in doubt, we recommend you use the tutorials referenced before or after:

👉 If you want to find out more ways to install the Solidity compiler, check out our full guide on the Finxter blog.

Prerequisites for Compiling the Solidity Compiler

Here is the approach of building the Solidity compiler from the source code. Before we proceed with it, we’ll have to check if we meet the prerequisites (for the article needs, on Ubuntu 20.04):

  1. Cmake v3.13+, a cross-platform build file generator;
  2. Boost v1.65+, C++ libraries;
  3. Git; a command-line tool for retrieving source code;
  4. z3 v4.8+, an SMT solver for use with SMT checker (optional);
  5. cvc4, an SMT solver for use with SMT checker (optional);
  6. ccache, speeds up repeated C/C++ builds;
  7. python, for z3 source compilation;

There are a lot of new elements and terms, so let’s explore what they are and what their role is in compiling our Solidity compiler.

💡 Note: we will assume that the Solidity compiler we’re working with is above 0.5.10 to avoid errors during the linking process.

ℹ️ Info: Linking is a phase in the linking process where the linker takes the object files produced by a compiler and generates a library or an executable file.

ℹ️ Info: “CMake is an open-source, cross-platform family of tools designed to build, test, and package software. CMake is used to control the software compilation process using simple platform and compiler-independent configuration files…”

Cmake is a set of tools that enables us to generate our Solidity compiler from its source code.

ℹ️ Info: Boost is an organization and a collection of C++ peer-reviewed libraries that greatly simplify development by providing support for various algorithms, data structures, and many more useful facilities. We have to install Boost C++ libraries because Solidity compiler source code depends on it. I deliberately chose the term “dependency” because it is commonly used when describing source code hierarchy.

ℹ️ Info: “Git is a DevOps tool used for source code management. It is a free and open-source distributed version control system used to handle small to very large projects efficiently. Git is used to tracking changes in the source code, enabling multiple developers to work together on non-linear development.”

Git is our tool of choice for downloading Solidity compiler source code.

The following few info blocks are a bit more technical at the moment. I also gave an explanation in simpler and more general words to ease our understanding.

ℹ️ Info: “Solidity implements a formal verification approach based on SMT (Satisfiability Modulo Theories) and Horn solving. The SMTChecker module automatically tries to prove that the code satisfies the specification given by require and assert statements.” (source).

In simpler words, formal verification is a process in which we mathematically check if the behavior of a system, i.e., a code statement satisfies a specific property, i.e. a condition.

We’ll dig more into the topic of SMTChecker in one of the following articles. Until then, just think of it as checking if a key fits the lock.

ℹ️ Info: Z3 Theorem Prover is a cross-platform SMT solver by Microsoft. Going into more detail might be too technical and redundant at the moment, but let’s just look at it from a practical point of view: it is a supporting tool for SMT checking.

ℹ️ Info: CVC4 is “…an efficient open-source automatic theorem prover for satisfiability modulo theories (SMT) problems. It can be used to prove the validity (or, dually, the satisfiability) of first-order formulas in a large number of built-in logical theories and their combination.”

CVC4 is also a supporting tool for SMT checking.

Installing the Prerequisites

As we’ve covered the basics, let’s check and install (install command) or upgrade (upgrade command) the prerequisites:

Step 1: Install cmake and check version

Install the cmake utility

$ sudo apt install -y cmake

Check the installed version:

$ cmake – version
cmake version 3.16.3

Step 2: Install Boost library:

Install the boost library:

$ sudo apt install -y libboost-all-dev

Check the installed version; dpkg is a packet manager for Debian/Ubuntu, and grep is a search utility that will filter out the line containing the search criteria.

The pipe symbol “|” sends the output of one command to the other command; check the quote symbols when pasting the commands in the command line:

$ dpkg -s libboost-dev | grep "Version"
Version: 1.71.0.0ubuntu2

Step 3: Install Git

Install the Git source control software:

$ sudo apt install -y git

Check the installed version:

$ git – version
git version 2.25.1

Step 4: Install Python and check version

Install Python:

$ sudo apt install -y python

Check the installed version:

$ python – version
Python 2.7.18

Step 5: Install z3 SMT checker

Install the z3 SMT checker tool:

$ sudo apt install -y z3 libz3-dev

Check the installed version:

$ z3 – version
Z3 version 4.8.7 - 64 bit

The build process will report the inability to run several tests with z3 versions different than 4.8.17. It’s not mandatory to run the tests, but if we want to, we’ll first have to remove the previous version and compile z3 from its source files:

🛑 Warning: z3 compilation can be very costly in terms of time and machine performance!

Remove the installed z3:

$ sudo apt remove -y z3

Download and unzip z3 from the Git repository:

$ cd ~ && wget \
https://github.com/Z3Prover/z3/archive/refs/tags/z3-4.8.17.zip \
&& unzip z3-4.8.17.zip

Pre-installation procedure generates the build files:

$ cd z3-z3-4.8.17 && python scripts/mk_make.py

Use the build files, compile the source and install z3:

$ cd build && make && sudo make install

Check the z3 version:

$ z3 –-version
Z3 version 4.8.17 - 64 bit

Just a little bit of housekeeping:

$ cd ~ && rm -rf z3-z3-4.8.17 z3-4.8.17.zip

Now that we’re equipped with z3 v4.8.17, we can continue with the rest of the installation.

Install the CVC4 SMT checker tool:

$ sudo apt install -y cvc4 libcvc4-dev

Check the installed version; the head command limits the output (listing) to the top -n lines:

$ cvc4 – version | head -n 1

This is CVC4 version 1.6

Install the ccache, a fast C/C++ compiler cache tool useful for speeding up repeated builds:

$ sudo apt install -y ccache

Check the installed version:

$ ccache – version | grep "version" | head -n 1
ccache version 3.7.7

Compiling the Solidity Compiler

Now we can start with fetching and compiling the Solidity compiler. There is a longer and shorter approach to our task. We’ll do a longer approach first:

Fetch the Solidity compiler source code from the Git repository; --recursive flag initialize all submodules within the cloned module, using their default settings:

$ git clone – recursive https://github.com/ethereum/solidity.git && cd solidity

💡 Note: if we want to proceed with the compilation of the Solidity compiler without the SMT checkers, the syntax for step 2. is:

# disables only Z3 SMT Solver.
cmake .. -DUSE_Z3=OFF

# disables only CVC4 SMT Solver.
cmake .. -DUSE_CVC4=OFF

# disables both Z3 and CVC4
cmake .. -DUSE_CVC4=OFF -DUSE_Z3=OFF

Create the build directory, descend into it, create the build files, use the build files and start the compilation:

mkdir build && cd build && cmake .. && make

The Solidity compiler compilation took almost 1h 45min on my machine.

Install the Solidity compiler at usr/local/bin:

cd solc && make install

And now, we’ll do a shorter approach:

Run the script ~/solidity/scripts/build.sh, which will install binaries solc and soltest at usr/local/bin:

Either approach will make solc globally available:

$ solc – version
solc, the solidity compiler commandline interface
Version: 0.8.17-develop.2022.8.26+commit.f802eafc.Linux.g++

Let’s run our classic example and check if the compiler works as planned:

$ solc ~/solidity_src/1_Storage.sol – abi – bin -o ~/solidity_src/output
Compiler run successful. Artifact(s) can be found in directory "~/solidity_src/output".

Conclusion

In this article, we showed how to prepare the environment and compile a Solidity compiler.

First, we listed and explained the software prerequisites needed for compiling a Solidity compiler. In some cases, we reached a complete explanation, and in others, we just gave a brief introductory explanation and announced an entire topic, such as in the case of the Satisfiability Modulo Theorem, SMT.

Second, we installed the prerequisites by following the first part of a step-by-step tutorial. All the examples have been checked and validated at the time of writing the article, so I expect that we’ll be able to follow them without issues. We also concluded that a compilation process can in some cases take a substantial amount of time; it took almost 40 minutes to compile the z3 SMT solver on my machine.

Third, we compiled a Solidity compiler following a step-by-step tutorial. I explained for each command example to broaden our learning process even outside of the strict scope of Solidity, to Linux (as far as we needed to go). Finally, when the compilation ended, we confirmed that our home-compiled Solidity compiler works at least as charming as the ones we’ve simply downloaded or installed in a precompiled state.