To build software for RISC-V you need a cross-compiler β a toolchain that runs on your x86 or ARM machine but emits RISC-V code. The good news in 2026 is that this is mostly a solved problem. This guide covers the fast path (install a prebuilt toolchain) and the full path (build one from source for a custom ISA configuration).

Fast Path: Install a Prebuilt Toolchain
For most work, your distroβs package is all you need.
Debian / Ubuntu (Linux glibc target):
sudo apt update
sudo apt install -y gcc-riscv64-linux-gnu g++-riscv64-linux-gnu
riscv64-linux-gnu-gcc --versionBare-metal / embedded (newlib target):
sudo apt install -y gcc-riscv64-unknown-elf # package name varies by distroFedora:
sudo dnf install -y gcc-riscv64-linux-gnu binutils-riscv64-linux-gnuLLVM/Clang (one Clang targets every architecture):
sudo apt install -y clang lld
clang --target=riscv64-linux-gnu --versionCompile and run a quick test (with QEMU user mode):
echo 'int main(){return 42;}' > t.c
riscv64-linux-gnu-gcc -static t.c -o t
qemu-riscv64 ./t; echo $? # 42Understanding the Toolchain Triple
The prefix encodes a target triple: riscv64-linux-gnu = 64-bit RISC-V, Linux OS, GNU (glibc) C library. The bare-metal variant riscv64-unknown-elf means βno OS, ELF output, newlib.β Picking the right one is the single most common beginner mistake:
- Linux applications β
riscv64-linux-gnu(glibc) - Microcontrollers / firmware / bootloaders β
riscv64-unknown-elf(newlib)
Full Path: Build From Source
Build from source when you need a specific -march (e.g. enabling vector or crypto), a multilib toolchain, or the latest compiler. The official riscv-gnu-toolchain repo automates everything.
# Dependencies (Debian/Ubuntu)
sudo apt install -y autoconf automake autotools-dev curl python3 \
libmpc-dev libmpfr-dev libgmp-dev gawk build-essential bison flex \
texinfo gperf libtool patchutils bc zlib1g-dev libexpat-dev ninja-build git
git clone https://github.com/riscv/riscv-gnu-toolchain
cd riscv-gnu-toolchainConfigure for Your Target
Pick the ABI and ISA you want. For a Linux RV64GC glibc toolchain:
./configure --prefix=/opt/riscv --with-arch=rv64gc --with-abi=lp64d
make linux -j$(nproc) # builds the glibc/Linux toolchainFor a bare-metal newlib toolchain (e.g. for an embedded RV32IMC core):
./configure --prefix=/opt/riscv32 --with-arch=rv32imc --with-abi=ilp32
make -j$(nproc) # default target builds newlibThen add it to your PATH:
export PATH=/opt/riscv/bin:$PATH
riscv64-unknown-linux-gnu-gcc --versionBuilding from source takes a while (it compiles binutils, GCC, and the C library). Use
-j$(nproc)and be patient.
Key Configure Flags
--with-archβ the ISA string, e.g.rv64gcvto enable vectors.--with-abiβlp64d(64-bit, hardware double) orilp32(32-bit). The ABI must be compatible with the arch.--enable-multilibβ build libraries for multiple arch/ABI combos in one toolchain.make linuxvsmakeβ glibc/Linux vs newlib/bare-metal.
Matching -march to Your Target
The -march you compile with must be a subset of what your target hardware (or QEMU CPU) supports, or the binary will hit an illegal instruction. Examples:
# General Linux SBC
riscv64-linux-gnu-gcc -march=rv64gc -mabi=lp64d app.c -o app
# Vector-capable chip (SpacemiT K1, QEMU -cpu rv64,v=true)
riscv64-linux-gnu-gcc -march=rv64gcv -mabi=lp64d app.c -o app
# Tiny embedded MCU
riscv64-unknown-elf-gcc -march=rv32imc -mabi=ilp32 firmware.c -o fw.elfCheck what a target supports via /proc/cpuinfo on the device, or -cpu help in QEMU.
LLVM for RISC-V
Clang shares the GNU sysroot, so you can mix and match. To build vector code with Clang:
clang --target=riscv64-linux-gnu -march=rv64gcv -O3 \
--sysroot=/usr/riscv64-linux-gnu -fuse-ld=lld app.c -o appLLVMβs RISC-V backend is mature in 2026, including auto-vectorization for RVV β useful if you want a single compiler across all your target architectures.
Verifying Your Build
riscv64-linux-gnu-gcc -march=rv64gc hello.c -o hello
file hello # ELF 64-bit LSB ... UCB RISC-V
riscv64-linux-gnu-readelf -A hello | grep arch # confirms ISA attributes
qemu-riscv64 -L /usr/riscv64-linux-gnu ./hello # run dynamic binaryThe readelf -A step is worth knowing: it prints the recorded ISA attributes so you can confirm the binary really targets what you intended.
The Bottom Line
For everyday RISC-V development, install your distroβs gcc-riscv64-linux-gnu (or Clang) and you are done. Build from source only when you need a custom -march, a bare-metal newlib toolchain, or cutting-edge compiler features β and when you do, riscv-gnu-toolchain makes it a one-command affair. Either way, pair it with QEMU to test before you touch hardware.
Part of my RISC-V series. Next up: RISC-V Vector Programming and RISC-V Profiles and RVA23.



