Best Practices While Writing Smart Contracts
With every new appliance there comes a user manual elaborating the dos and don’ts of that specific appliance. Why not a user manual for writing smart contracts?
Developer handbooks are every new developer’s best friend. Any dev would agree. You’ll find the nitty-gritty details of a new language, the security measures, the terminology, the formatting, the common errors, etc., all in one single handbook. And, that’s what we’re here for today.
I usually have the habit of thinking about all possible issues I might encounter in a certain project before I start, and I know you do too. We’re going to talk about the security of smart contracts, the vulnerabilities, and how they’re tackled.
Security Vulnerabilities, and how they’re solved.
Re-entrancy
When an attacker takes control of an untrustworthy contract using an external call function, they can perform a recursive call back to the original function, unexpectedly repeating transactions that would not have run otherwise and finally consuming all the gas. This reentrancy attack has the potential to drain a smart contract’s ether and enable infiltration into its code.
Here’s how a re-entrancy vulnerability is exploited:
- The Attacker starts by calling the withdrawal function of the Victim.
- The Victim transfers the money and calls the fallback function of the Attacker.
- Re-entrancy is the result of the fallback function recursively calling the withdraw function.
- Within the iteration limit of the function, additional ether will be transferred several times to the Attacker.
Here’s what you can do to prevent Reentrancy:
- This certain vulnerability can be prevented by the state changing logic of the statement is committed before ether is sent out of the contract through an external call.
- It’s also good coding practice to place any logic that makes external calls to unknown addresses at the end of a program’s execution. It’s called the checks-effects-interactions pattern.
Running out of gas.
When sending ether across contracts, the primitive function send may generate an unexpected out-of-gas exception. There are prefixed units of gas available to allow execution of a limited set of bytecode instructions, and if not enough gas units are available, the call function will throw an out-of-gas exception.
Gas is the transaction execution cost of smart contracts and products on the blockchain.
Here’s what you can do to prevent the Out-of-Gas exception:
- This issue can be avoided by utilizing the transfer() function rather than the send() function, as the former would revert the local transactions if the external transaction is reverted.
- However, if send() is required, the function’s return value must be kept track of.
- Another method is to utilize a withdrawal pattern, in which each user is obliged to call an isolated function that manages ether transactions while leaving the rest of the contract execution alone. As a result, transaction management is no longer affected by the failure of send() transactions.
Exceptions can be mishandled.
Exception handling is always a crucial point when it comes to writing any code/logic. In Solidity, exceptions can be raised in various situations, but they are not all handled in the same manner. Usually, exception handling is based on the interaction between the contracts. This makes the contracts vulnerable because programmers will be ignorant of any ether lost if these exceptions are not correctly handled and transactions are reverted.
Here’s what you can do to prevent Mishandling Exceptions:
- By using external calls throughout, this vulnerability can be avoided. However, this is not an ideal solution to this issue as different variations of an external call can be a necessity.
- Hence, this vulnerability needs a fix from the Solidity language itself to make the consequences of a thrown exception uniform.
Randomness and Private Information not being so private.
Smart contracts being on blockchain mean that everything is public and for everyone to see. This can be a big drawback, as even local variables and state variables marked as private are publicly visible.
Even while using values, using a random number generator can be pretty tricky. This is because you do not want miners to cheat.
Here’s what you can do to prevent these issues:
- There are roundabouts you can use while assigning values to variables. For example, you can use global private counters for each group of variables to store the variable’s value without letting anyone see it, as these counters are not visible.
If you’re looking to include randomness in your smart contract, let me explain how Chainlink handles these unique issues:
Verifiable randomness is a cryptographic notion that has been around for more than two decades but has just lately been used to smart contracts. In its most basic definition, verifiable randomness is randomness with cryptographic proof attached. For example, an asymmetric key pair proof is generated in Chainlink so that the requester may verify that the randomness was not tampered with in any way.
A few more basic tips to begin with:
- Define the purpose of your smart contract.
- Don’t reinvent the wheel: Do not spend time rewriting something which already exists. There are multiple sources providing libraries of already existing contracts which you can utilize by extending their functionalities.
- Choose a clear, descriptive name.
- Choose the Development Environment you’re comfortable with: Now, if you’re an already seasoned coder, you must have an IDE that you’re comfortable with. But if you’re less experienced, Ethereum provides a marvellous online IDE called Remix.
- Choose the latest stable version of Solidity: This is to be able to use new features and make use of multiple libraries that support the version.
- Reduce Complexity.
- Test Thoroughly.
- Consult your peers.
Starting something is always the most daunting activity. The fear of not knowing what to do next can often be the thing that holds one back from taking the leap. However, with the help of a helping hand from an experienced professional, it seems a little doable, mainly because they’ve already done it. We aim to provide you with that exact sense of safety with this blog, and we’re here to help you in every step of the process.