Deployment of FreeRTOS on UET RV P-Core
The deployment of FreeRTOS on the UET RV P-Core platform demonstrates the seamless integration
of a real-time operating system (RTOS) with the RISC-V architecture. This blog shows how the
Port_FreeRTOS_RV_PCORE project is designed to run FreeRTOS on RISC-V cores, specifically
with a demonstration on the UET RV P-Core platform.
Introduction to FreeRTOS
FreeRTOS is an open-source real-time operating system designed for embedded systems. It provides
efficient multitasking and low-latency scheduling for time-critical applications. Lightweight and
flexible, FreeRTOS can be tailored to various microcontroller and processor architectures, including
RISC-V, allowing developers to take full advantage of RISC-V’s extensible instruction set while
maintaining real-time capabilities.
Introduction to UETRV-PCORE:
UETRV_Pcore is a RISC-V based application class SoC integrating a 5-stage pipelined processor with
memory and peripherals.. Integrating FreeRTOS with UETRV-Pcore enhances its real-time
multitasking capabilities, ensuring efficient task scheduling and resource management for embedded
applications on the RISC-V architecture.
Complete Guide to Deploy FreeRTOS on UETRV-PCORE:
Now that you have a basic understanding of what FreeRTOS is, let's dive into the steps to deploy it on
UETRV-Pcore. The process follows these key steps:
● Clone the Port_FreeRTOS_RV_PCORE repository, configure the toolchain with
Crosstool-NG, and build the GNU RISC-V toolchain.
● Add the RISC-V toolchain to the environment path and build the project using make.
● Use make run-freertos to deploy the project on UETRV-Pcore.
● Run the simulation and enable VCD generation with adjusted simulation parameters.
● Check uart_logdata.log for simulation results and debug outputs.
● Use GTKWave to visualize VCD output files and analyze the system’s performance.
● Define new tasks with specific priorities and frequencies, and integrate them into the
FreeRTOS scheduler by modifying the main_blinky.c file.
Detailed Information
Clone the project repository
git clone https://github.com/MujtabaRawn65/Port_FreeRTOS_RV_PCORE.git
cd Port_FreeRTOS_RV_PCORE
Building the Toolchain Using Crosstool-NG
To run the project, you can build your own RISC-V toolchain, such as riscv32-unknown-elf. Below
are the steps to build your own toolchain, tailored to your architecture:
Step 1: Clone the Crosstool-NG Repository
Clone the Crosstool-NG and configure Crosstool-NG.
cd FreeRTOS/Demo
git clone https://github.com/crosstool-ng/crosstool-ng
cd crosstool-ng
./bootstrap
./configure --enable-local
make
Step 2: Generate Toolchain Configuration
Create a configuration file to define the architecture. Depending on your target architecture (RV32 or
RV64).
For RV32 builds: Create a file name as "defconfig" ( should be exactly the same, no file extension )
with the below content:
CT_EXPERIMENTAL=y
CT_ARCH_RISCV=y
CT_ARCH_64=n
CT_ARCH_ARCH="rv32ima"
CT_ARCH_ABI="ilp32"
CT_TARGET_CFLAGS="-mcmodel=medany"
CT_TARGET_LDFLAGS="-mcmodel=medany"
CT_MULTILIB=y
CT_DEBUG_GDB=y
For RV64 builds: Create a file name as "defconfig" ( should be exactly the same, no file extension )
with the below content:
CT_EXPERIMENTAL=y
CT_ARCH_RISCV=y
CT_ARCH_64=y
CT_ARCH_ARCH="rv64ima"
CT_ARCH_ABI="lp64"
CT_TARGET_CFLAGS="-mcmodel=medany"
CT_TARGET_LDFLAGS="-mcmodel=medany"
CT_MULTILIB=y
CT_DEBUG_GDB=y
Run the below command. The configurations will be save to .config file.:
./ct-ng defconfig
Step 4: Build the Toolchain
Run the following command to build GNU toolchain for RISC-V:
./ct-ng build
This will generate the toolchain in the ~/x-tools/riscv32-unknown-elf or ~/x-tools/riscv64-unknown-elf
directory depending on your target architecture.
Set the RISC-V Toolchain Path
Make sure to add the toolchain's bin directory to your PATH:
export PATH=~/x-tools/{YOUR_TOOLCHAIN}/bin:$PATH
Adding More Tasks in FreeRTOS
If you wish to add more tasks to the FreeRTOS system, edit the main_blinky.c file in
FreeRTOS/Demo folder following the steps as given below:
Step 1: Define Task Priority and Frequency
Define macros for the task's priority and execution frequency:
#define mainNAME_TASK_PRIORITY ( tskIDLE_PRIORITY + 2 )
#define mainNAME_TASK_FREQUENCY_MS pdMS_TO_TICKS( 3000 ) // 3 seconds
Step 2: Define the Task Function
Implement the task function according to FreeRTOS' requirements:
static void prvNewTask( void * pvParameters )
{
( void ) pvParameters;
for( ; ; )
{
// Task-specific operations
// Add a delay to control the execution frequency
vTaskDelay( mainNAME_TASK_FREQUENCY_MS );
}
}
Step 3: Create the New Task
Add the new task using xTaskCreate:
xTaskCreate( prvNewTask, "New-Task", configMINIMAL_STACK_SIZE * 2U, NULL,
mainNAME_TASK_PRIORITY, NULL );
This creates the new task in the FreeRTOS scheduler.
Step 4: Rebuild the Project
After adding the task, rebuild the project using the make run-freertos command as shown below.
Currently Running Tasks on Demo:
The Port_FreeRTOS_RV_PCORE project includes several tasks, each demonstrating different
FreeRTOS functionalities:
Running the FreeRTOS Demo on UET RV P-Core
Navigate to the main UETRV-PCore directory and run following commands
cd ../../
make run-freertos
The run-freertos command initiates the deployment of FreeRTOS on the UETRV-Pcore platform by
first navigating to the FreeRTOS/Demo folder, where it builds the FreeRTOS project with defined
tasks, compiling all instructions into an executable .axf file named RTOSDemo.axf. The build process
sets up cross-compilation for the RISC-V architecture using the riscv32-unknown-elf toolchain. Once
the .axf file is generated, it is converted to a .hex file (RTOSDemo.hex) for use in simulation.
Afterward, the command returns to the main folder and copies the .hex file to the required directory
(sdk/example-uart/hello.hex). It then runs the Verilator simulation, capturing the output in
uart_logdata.log for debugging and performance analysis. If run with vcd=1, the simulation can also
generate a trace VCD file for further analysis.
Configure Simulation Cycles (Optional)
If you want to modify the simulation cycle count in the Makefile, use the max_cycles flag:
make max_cycles=<desired_number_of_cycles>
Expected Output
After the simulation is complete, check the output in the uart_logdata.log file. You should see
the UART output, which confirms that the FreeRTOS demo is running successfully.
Expected UART Output:
This output shows that the tasks are executing correctly in FreeRTOS.