Read this article on BlocSec’s blog
Introduction
In 2024, Solana emerged dramatically, with its Total Value Locked (TVL) soaring from one billion USD at the beginning of the year to nearly five billion USD, making it the fourth-largest public blockchain.
Compared to Ethereum, Solana offers users a superior experience with faster speeds and lower costs. The Proof of History-based consensus mechanism and the asynchronous transaction processing model offer developers high transaction throughput and low latency, making it a favored platform for all kinds of decentralized applications.
BlockSec has specially planned the “Solana Simplified” series, covering basic concepts of Solana, practical guides on analyzing Solana transactions, and tutorials on writing Solana smart contracts.
As the first article in this series, this text will delve into the key concepts within the Solana network, including its operating mechanisms, account model, and transactions, laying the foundation for writing correct and efficient smart contracts in Solana.
eBPF: The Keystone of Solana Transaction Execution
To write and execute smart contracts, blockchains typically require a programming language and a Turing-complete computational environment.
Smart contracts on Ethereum are usually written in a high-level language called Solidity. The compiler translates them into bytecode, which is then executed in the Ethereum Virtual Machine (EVM). Instead of developing an entirely new virtual environment and language, Solana has chosen to fully utilize existing advanced technologies. The eBPF (extended Berkeley Packet Filter) virtual machine, initially designed for expanding Linux kernel functionalities, has been selected by Solana to serve as its underlying execution environment.
So, what advantages does eBPF offer over the EVM?
Unlike the EVM, which is limited to interpreted execution, eBPF supports Just-In-Time (JIT) compilation, enabling it to translate bytecode into machine instructions that the processor can execute directly. Such capability significantly increases program efficiency.
Furthermore, eBPF features an efficient instruction set and a mature infrastructure. Developers can craft smart contracts using the Rust language. Leveraging the eBPF backend of the LLVM compiler framework, the Rust programs can be directly compiled into eBPF bytecode.
Solana’s Account Model
Solana Account Structure
Data is stored in the form of accounts on Solana. As illustrated below, all data within Solana can be conceptualized as a vast key-value database. The keys in this database are the account addresses. For “wallet” accounts (i.e., accounts directly controlled by Solana users via public-private key pairs), these addresses are public keys generated using the Ed25519 signature system. The values in the database consist of specific details of each account, including the balance and other relevant information.
Solana utilizes the following structure known as AccountInfo
to describe an account.
The AccountInfo
for each account contains four fields. Here is an explanation of each:
Data
Field: This field stores the data related to the account. If the account is a program (i.e., a smart contract), it stores the eBPF bytecode. Otherwise, the format of data is generally defined by the account creator.Executable
Field: This field is used to indicate whether the account is a program. It is important to note that, unlike Ethereum, programs in Solana can be updated.Lamports
Field: This field records the balance of Solana tokens in the account. Lamports are actually the smallest unit of the SOL Token (1 SOL = 1 billion Lamports).Owner
Field: This field indicates the owner of the account. In Solana, every account has an "Owner". For instance, the owner of all "wallet" accounts is the System Program, a special account on the Solana network responsible for functions such as account creation. The account owner is the only one who can modify account data and deduct Lamports from the balance (however anyone can increase Lamports by transferring funds to the account).
Predefined Solana Accounts
Solana has a set of predefined executable programs known as Native Programs
, which are deployed at fixed addresses. As the Solana network is upgraded, these predefined programs can also be updated. They serve as APIs and library functions, offering specific functionalities within the Solana network.
Within Native Programs, one that developers often interact with is the System Program
. The System Program provides developers with a set of instructions, each of which performs an independent task. For example, developers can use the CreateAccount
instruction to create new accounts, or the Transfer
instruction to transfer Lamports to other accounts.
Another common Native Programs is the BPF Loader
program. It is the owner of all other program accounts and is responsible for deploying, updating, and executing custom programs. When a "wallet" account needs to update a program it has deployed, it is actually done by delegating to the BPF Loader program, since only the owner of a program has the direct authority to modify data.
In addition to Native Programs, Solana also offers a set of accounts known as Sysvars
. These accounts provide programs on Solana with information and global variables related to the current state of the Solana network, such as the current clock and the most recent block hash.
Account Rent
On the Solana blockchain, each account has to maintain a certain number of Lamports as a minimum balance, known as rent. Unlike the rent in real life, rent on Solana is reclaimable. To ensure that the data in an account is available on the chain, the account must hold an appropriate amount of Lamports. The amount of rent is related to the size of the data occupied by the account.
Any transaction that attempts to reduce the account balance below the amount of rent will fail, unless it reduces the balance to exactly zero. Dropping the balance to zero indicates that the account’s rent has been reclaimed, and at the end of the transaction, Solana will clear the corresponding account’s data in the garbage collection process.
🧐 Viewing Solana Accounts in Solana Scans
To better understand the aforementioned concepts, we used Solana’s “Hello World” project to deploy a program account, which can be viewed using Solana’s blockchain explorer, Solscan.
As shown in the image above, we can first see that the account has been labeled as “Program”. A portion of Lamports was deducted from the sender’s balance as rent for this account, hence the SOL Balance
field is not empty. Furthermore, since the account we created is a program, its Executable
field is set to Yes. You might be confused that the Executable Data
field stores an address, instead of an eBPF program. As mentioned earlier, Solana allows for program updates, and it is actually implemented through a "proxy" pattern. Since direct modifications to the program account are not permitted initially, Solana creates a separate data account to store the eBPF program, while the Data field in the program account only stores the address of this data account.
Whenever an update to the program is needed, only the Data field of the data account needs to be modified. Using Solscan to view the data account, we can find that it is marked as “Program Executable Data Account,” and its Data
field stores the actual program.
The Owner
field in the "More Info" section is the BPF Loader, consistent with what was mentioned earlier.
Someone might notice that the last field of “Overview” is Upgrade Authority
, which is not present in the AccountInfo. What does it mean?
As mentioned earlier, the “wallet” account delegates program updates to the BPF Loader. Before updating, the BPF Loader verifies whether the delegator is the account that originally deployed the program. Since the Owner of the program account is already set to BPF Loader, it has no space to store this information. Thus Solana puts it into the Data field of the data account. That’s why there is an Upgrade Authority
field in "Overview", and it is actually the wallet address that deployed the program. The image below shows the relationship between the program account and the data account. Note that the Data field of the data account consists of both the wallet address and the eBPF code.
Transactions and Instructions in Solana
In Solana, users execute programs by issuing transactions. A unique aspect of Solana is its ability to execute these transactions in parallel, which is a key reason behind its blazing-fast transaction speeds. Now let’s take a closer look at how transactions are designed in Solana.
A Solana transaction consists of signatures and a message. A transaction can include multiple signatures. The message of a transaction is composed of four parts, as illustrated below.
The Header
and the Compact Array of Account Addresses
specify all the accounts involved in a transaction and their characteristics during the transaction, including whether the account is a signer and whether it is writable during execution. With this information, Solana can verify the signatures provided by the signer accounts and process transactions in parallel, as long as these transactions do not include any accounts that write to the same state.
The Recent Blockhash
acts as a timestamp for the transaction. If a transaction's blockhash is 150 blocks older than the latest blockhash, it is considered expired and will not be executed.
The Compact Array of Instructions
is the most important part of the transaction, containing one or more instructions. An instruction essentially triggers the execution of a routine provided by a program account. Each instruction consists of three fields, as illustrated below.
The first field, Program ID Index, specifies the receiver of the instruction, which is the on-chain program that needs to process the instruction. Rather than storing a 32-byte address, this address is placed within the Compact Array of Account Addresses of the transaction message, and the field only stores an u8 index pointing to the address in the array.
Similar to the first field, the second field stores account address indexes, known as Compact Array of Account Address Indexes
. This array specifies all the accounts involved in this instruction.
The last field is a byte array containing the additional data required by the program to process the instruction, such as function arguments.
It is important to note that Solana processes all instructions within a transaction in the order and guarantees the atomic execution of the transaction. This means it either fully completes with all instructions successfully processed, or fails altogether. There will not be a situation where some instructions are processed and others are not.
🧐 Viewing Solana Transactions in Solana Scans
We use another Solana explorer to view the transaction that created the program account earlier. In the Overview section, you can see the Solana transaction signature, the recent blockhash, and other information:
In the Account Input section, all the accounts involved in the current transaction are listed, along with their characteristics in the transaction. We can see that, in addition to the sender and program account addresses, two Native Programs
and Sysvar
accounts have also been included.
Since it is a simple program creation transaction, it contains only two instructions. The receiver of the first instruction is the System Program, responsible for creating the program account. The receiver of the second instruction is the BPF Loader, which creates a data account to store the deployed eBPF code and writes its address into the Data field of the program account.
Conclusion
Smart contracts on Solana are developed in Rust and run on the eBPF virtual machine. Solana follows the account model, where on-chain accounts need to maintain enough rent to avoid data being removed. A transaction consists of one or more instructions that define all required accounts, enabling parallel processing and enhancing throughput while reducing response latency. These features together have contributed to the rapid development of Solana, making it one of the favored blockchains.
Related Reading
- How to Make One Million in Two Minutes: Using MetaSleuth to Track “Smart” Money on Solana
- Lead in: Secure the Solana Ecosystem
- MetaSuites 5.0 Extends Full Support to Solana Scans
About BlockSec
BlockSec is a full-stack Web3 security service provider. The company is committed to enhancing security and usability for the emerging Web3 world in order to facilitate its mass adoption. To this end, BlockSec provides smart contract and EVM chain security auditing services, the Phalcon platform for security development and blocking threats proactively, the MetaSleuth platform for fund tracking and investigation, and MetaSuites extension for web3 builders surfing efficiently in the crypto world.
To date, the company has served over 300 clients such as Uniswap Foundation, Compound, Forta, and PancakeSwap, and received tens of millions of US dollars in two rounds of financing from preeminent investors, including Matrix Partners, Vitalbridge Capital, and Fenbushi Capital.
- Website: https://blocksec.com/
- Email: contact@blocksec.com
- Twitter:https://twitter.com/BlockSecTeam
- MetaSleuth: https://metasleuth.io/