Compiling C programs with optional flags
This page describes how to compile a C programs that require option flags using Build class from the Python SDK
Sabana allows you to conveniently compile C programs for RISC-V CPUs, saving you the effort of having to install or compile your own toolchain.
We provide a programmatic interface to a gcc based toolchain. Let's go through the steps of getting our first C binary compiled

Creating a Build object

The first step is to create a Build object from the Python SDK. It will provide a handler to define the project and to submit the compilation request to the platform:
from sabana.cc import Build
build = Build(toolchain="riscv64-unknown-elf", version="10.2.0")
At this stage you can select the toolchain that will be used to compile the project and its version.
Currentlyriscv64-unknown-elf is the only toolchain supported

Adding files

The next step of the process is to use the Build object to create a list with all the files that will be sent for compilation. We do this using the file function. Also note how in our examples we use the pathlib module in order to conveniently generate paths that are safe and consistent across operating systems:
from pathlib import Path
...
cwd = Path(__file__).resolve().parent
build.file(cwd.joinpath("cc/main_matrix_mul.c"), flags="-Ofast")
build.file(cwd.joinpath("cc/boot.S"), flags="-Os")
build.file(cwd.joinpath("cc/picorv32.ld"), flags="-Bstatic -T")
The flags parameter is optional, it allows you to declare flags that will be applied to each individual file.
The platform recognizes the .ld extension as belonging to a linker script.
There can only be one linker script file per project

Adding flags

The Build object also allows us to add flags that will be applied globally to all files. We can define global flags for either the compilation or the linking stages:
1
cflags = "-c -Qn --std=c99 -march=rv32im -mabi=ilp32"
2
build.cflags(cflags)
3
ldflags = "-Ofast -ffreestanding -nostdlib -lgcc -march=rv32im -mabi=ilp32"
4
build.ldflags(ldflags)

Compiling the C program

After we have defined the files and parameters we can then request the project to be compiled:
result = build.compile()

Compilation results

If the compilation is successful the results variable will contain a Python dictionary with the following elements:
  • binarray: This is a numpy array of int8 elements containing the executable binary for the CPU
  • objdump: This is a string containing the dis-assembly of the program compiled, as it would be output by objdump.
Typically the binarray will be used as a direct input to a program buffer write request, in order to write this binary in the memory used by a CPU implemented in a Sabana image.
Alternatively it can also be written to a file for it to be used in some other way.
You can use Sabana's compilation service to compile C programs for any RISC-V CPU. Any CPU! not only those hosted as an image in the platform
1
with open(binary, "wb") as f:
2
f.write(result["binarray"])
3
python
4
with open(objdump, "w") as f:
5
f.write(result["objdump"])

Next steps

You may want to check out the reference page for the Build class in case you need further details.
Now that we know how to conveniently compile C programs we can go ahead and take a look at integrating a RISC-V CPU in an image to be deployed with Sabana:
Copy link
On this page
Creating a Build object
Adding files
Adding flags
Compiling the C program
Compilation results
Next steps