بلاگ
Ethereum: getting different binaries for the same Solidity source code when compiling with Solc and Remix
Ethereum: Debugging Binary Differences Between Local and Remix
As a Solidity developer, you are not the only one who notices differences in the binary output between compiling locally with Truffle’s solc compiler and deploying to the Ethereum network using Remix. In this article, we will explore the causes of these discrepancies and provide tips on how to troubleshoot and resolve them.
The Problem: Different Binary Formats
When you compile your Solidity code using solc (Solidity Compiler) locally, it produces a binary file with a specific format that is only compatible with the architecture of the local machine. However, when you deploy your contract to the Ethereum network using Remix, the same source code is compiled into different binaries due to differences between the Solana blockchain’s native compiler and the Ethereum Virtual Machine (EVM) requirements.
The problem: solc compiler version
A potential cause of these binary differences is an incompatibility between the solc compiler version used locally and the one used by Remix. The solc
compiler version may not be compatible with your local setup, resulting in different binary outputs when compiled and deployed on the two platforms.
Testing with Remix
To verify this hypothesis, we can test the scenario with Remix, which has its own native Solana compiler (solana
). We will create a new contract and deploy it using Remix, and then compare the binary output to what is produced locally.
Here is an updated version of your code:
pragma solidity 0.8.20;
contract HelloWorld {
function test() public pure returns (bool) {}
}
// Deploying with Remix
function main() public payable {
HelloWorld memory hello = Hello();
require(hello.test() == true, "hello");
}
Deploying to Remix
We will use the web3.js
library in Remix to interact with the local machine blockchain and deploy our contract using a new account. The deployment process may produce different binaries depending on the Solana compiler used.
Testing with solc compiler version
Now, let’s test this scenario by comparing the binary output produced locally to the one produced when we use Remix.
Local Build
cd ~/Truffle
solc -v solidity-0.8.20.js --bin HelloWorld.js
Remix Deployment (with solana)
To deploy our contract using Remix, we will create a new account on the Solana blockchain and interact with it to test our deployment.
const { Web3 } = require('web3');
const web3 = new Web3();
async function main() {
const networkName = 'mainnet';
const accountAddress = '0x...'; // Replace with your own Solana address
try {
const transactionCount = await web3.eth.getTransactionCount(accountAddress);
const tx = wait web3.eth.sendTransaction({
from: accountAddress,
to: '0x...', // Replace with the recipient address
value: web3.utils.toWei('1', 'ether'),
gas: 200000,
gasPrice: 20,
});
console.log(tx);
} catch (error) {
console.error(error);
}
}
main();
Comparing Binary Outputs
We can compare the binary output produced locally and when we use Remix to identify the differences.
Output Comparison
When we run the code locally, we can see a different binary format than the one we deploy with Remix. Let’s look at the potential differences:
$ objdump -h HelloWorld_0x12345678.bin
bin file format
We’ll compare the output of objdump
for both scenarios.
In this example, the locally produced HelloWorld_0x12345678.bin
binary has a different structure and layout than the one deployed with Remix. This difference may be due to the Solana compiler used in Remix versus the solc compiler used locally.