*This content has been reposted with the approval of the original author.
Foreword
This is a guide for porting Zephyr to the G32R501.
About Zephyr
I would call this the hottest RTOS project in the world right now. Its official website is: https://www.zephyrproject.org. The following is a self-description from the official site:
What is the Zephyr Project?The Zephyr® Project is an open source scalable real-time operating system (RTOS) supporting multiple hardware architectures including ARC, ARM, RISC-V and X86. The Zephyr OS is a proven RTOS used in products today.Zephyr OS is modular and supports multiple architectures, developers can easily tailor an optimal solution to meet their needs. Zephyr OS is used in a broad spectrum of applications from simple connected sensors to complex edge systems.As an open source project, the community contributes to the evolution of Zephyr by adding support for new hardware, developer tools, sensors and device drivers. Enhancements in security, device management capabilities, connectivity stacks and file systems are easily implemented.
This project is currently an open-source RTOS project hosted by the Apache Foundation. Project members include many well-known semiconductor vendors such as Intel, Nordic, NXP, Renesas, Infineon, TI, and ST, as well as famous tech companies like Meta and Google. I even saw Honda on the member page—yes, that Honda.
With so many companies involved, it’s clear they see great potential in the Zephyr project. So, what are its advantages? Here is my summary:
- Open Source: Project participants can contribute through code. This allows them to leverage the community while also exerting their own influence and increasing exposure for their products.
- Devicetree + Kconfig Development Model: Similar to Linux development, this model allows for flexible and maximum compatibility across different MCU models.
- Rich Ecosystem: It supports eight processor architectures, over 750 development boards, and more than 220 sensor drivers. It also comes with officially integrated cryptography libraries, graphics libraries, and various protocol stacks—covering almost everything commonly used.
Based on the last point alone, I would strongly recommend this RTOS.
About the G32R501
This is the latest real-time control MCU from Geehy, based on the Cortex-M52 core. Official website: https://www.geehy.com. Here is the MCU’s description from the website:
The G32R5 series of real-time control MCUs is equipped with an Arm® Cortex®-M52 core featuring the Arm v8.1-M architecture and a proprietary Zidian math instruction extension unit. It supports Arm Helium™ technology based on the MVE (M-Profile Vector Extension) solution. It integrates high-performance sensing, control peripherals, and a flexible peripheral interconnect system. It supports a wide operating temperature range of -40°C to 105°/125°C, making it suitable for a broad range of applications including new energy inverters, commercial power supplies, industrial automation, and new energy vehicles.
The G32R5 series of real-time control MCUs is equipped with an Arm® Cortex®-M52 core featuring the Arm v8.1-M architecture and a proprietary Zidian math instruction extension unit. It supports Arm Helium™ technology based on the MVE (M-Profile Vector Extension) solution. It integrates high-performance sensing, control peripherals, and a flexible peripheral interconnect system. It supports a wide operating temperature range of -40°C to 105°/125°C, making it suitable for a broad range of applications including new energy inverters, commercial power supplies, industrial automation, and new energy vehicles.
The goal of this porting effort is to bring Zephyr to the G32R501, allowing Geehy’s new MCU to benefit from this global momentum.
Notes Before Porting
This article is a porting guide. While it will touch upon Zephyr concepts, it cannot provide a comprehensive introduction to the fundamentals of Zephyr development. For that, please refer to the official documentation, which can be accessed directly here.
Build Tools
Zephyr uses west and CMake as its build tools, so developers will need to be familiar with them. west is a companion tool for the Zephyr project, also detailed in the official documentation. For CMake, please learn it on your own~
Compiler
There are a few important points regarding the compiler:
- The ARM GCC compiler has relatively complete support in the Zephyr project. For the Cortex-M52 core, the latest version, 14.2, is required. You can download it here: https://developer.arm.com/downloads/-/arm-gnu-toolchain-downloads.
- The ARM Clang compiler is also supported by Zephyr, but I encountered some issues during the porting process. Although they can be resolved, debugging is a hassle. I personally do not recommend it.
- IAR’s toolchain is also supported by Zephyr, but I also ran into some trouble while porting to the G32R501. It’s important to note that Zephyr uses the IAR Build Tools for Arm, not the common Workbench. You can download it from https://github.com/iarsystems/arm/releases.
Basic Concepts
Next, let’s introduce some basic concepts of Zephyr development to facilitate the subsequent porting work.
SoC First, let’s cover Zephyr’s conventions regarding MCU architecture. In Zephyr, the following concepts are relevant to a specific MCU and require the porting engineer’s attention:
- SoC
- SoC series
- SoC family
- CPU Cluster
- CPU core
- Architecture
For details, refer to the SoC Porting Guide section in the official documentation. The official docs also have a diagram and a table that help in understanding these concepts, linked here:

For our target, the G32R501, the mapping should be as follows:

The G32R501 is based on the Cortex-M52, which Zephyr does not yet support. Porting from this level would be a massive undertaking that is beyond my current abilities. We know that the Cortex-M52 belongs to the Armv8.1-M family, and within the same family, Zephyr supports the Cortex-M55. We will use this as a basis for our modifications and will not port the processor architecture aspects.
ModuleA Module can be understood as a relatively complete “package, ” such as a library or an SDK. Modules follow specific rules to provide configuration and compilation rules. They can be added to a build project using the west tool and can provide Kconfig options if necessary. For details, refer to the official documentation on Modules (External projects).
Preparation
Conventions
To facilitate the description of the porting work, let’s establish some conventions first.
Working Directory: All source code-related directories will be placed in this directory. Set the environment variable WORK_DIR to the path of this directory. You can use a different directory, but it is strongly recommended that the path does not contain spaces or Chinese characters. On my machine, this directory is D:\zephyrproject.
Required Python Environment: We will use a virtual environment. The steps for this will be explained later.
Python Virtual Environment and Other Assets: These will be placed in D:\zephyrproject.asset. Keeping this separate from the working directory helps maintain a clean workspace. This directory is also not mandatory and can be changed according to your setup.
Preparation Steps
The preparation involves setting up the development environment, with the following steps:
Install required software tools.
Create a Python virtual environment.
Install west.
Initialize the working directory.
Productivity tips.
Verify the development environment.
Let’s detail these steps:
First, install the required software tools.You can refer to the official documentation’s “Install dependencies” section. It’s particularly important to note that if you have a Python version lower than 3.12, it is recommended to install version 3.12. We will use a virtual environment, so multiple Python versions will not cause conflicts.
Second, create a Python virtual environment.Open a command line window (cmd or PowerShell, whichever you prefer—hereafter referred to as the command line) and execute the following command, then wait for it to complete:
python -m venv D:\zephyrproject.asset.venv
D:\zephyrproject.asset.venv is the directory where the virtual environment is located. Its parent directory is D:\zephyrproject.asset, as agreed upon earlier.
When using Python, you’ll install packages. Using a domestic mirror can be more convenient. In the command line, execute:
pip config set global.index-url https://mirrors.tuna.tsinghua.edu.cn/pypi/web/simple
The above is the Tsinghua University mirror address. You can replace it with others:
Alibaba Cloud Mirror: http://mirrors.aliyun.com/pypi/simple
USTC Mirror: https://mirrors.ustc.edu.cn/pypi/simple
Huawei Cloud Mirror: https://repo.huaweicloud.com/repository/pypi/simple
Tencent Cloud Mirror: https://mirrors.cloud.tencent.com/pypi/simple
Third, install west.The porting work needs to be done within the Python virtual environment, so first, you need to activate it in your command line tool. If you are using cmd, execute:D:\zephyrproject.asset.venv\Scripts\activate.bat
If you are using PowerShell, execute:D:\zephyrproject.asset.venv\Scripts\Activate.ps1
After successful execution in either cmd or PowerShell, the command prompt will be prefixed with (.venv). For example, this is what it looks like in my PowerShell:
181419necwqnayb87kkh5w.png
(Note the green text. The cmd window will not have colors, nor the “PS” letters.)
Once the virtual environment is activated, you can use pip to install west. In the command line window, execute:
pip install west
After installation, you can run west -V to check the version. A normal version number output indicates a successful installation. Now, let’s use west to initialize the working directory.
Fourth, initialize the working directory.
west init D:\zephyrproject
D:\zephyrproject is our designated working directory. If your directory is different, please use your path.The command above will pull the Zephyr source code from GitHub, so please ensure your network connection is stable.
After this command completes successfully, we will have the Zephyr source code. We also need other modules, so execute the following commands:
cd D:\zephyrproject
west update
This command will also pull module source code from GitHub. Once it’s finished, the working directory initialization is complete.
Fifth, productivity tips.Before we officially start, we need to set some environment variables and activate the virtual environment. Typing many commands each time is cumbersome. So, I have prepared a script to configure the development environment when launching the command line. It comes in two versions, for cmd and PowerShell. Please choose one based on your command line tool.
First, the cmd method:Create a script D:\zephyrproject.asset\setup_env.bat:
@echo off
REM Set environment variables, make sure to use your actual paths
set “ZEPHYR_BASE=D:\zephyrproject\zephyr”
set “ZEPHYR_TOOLCHAIN_VARIANT=gnuarmemb”
set “GNUARMEMB_TOOLCHAIN_PATH=D:\apps\arm-gnu-toolchain-13.2.Rel1-mingw-w64-i686-arm-none-eabi”
REM Add tool executable paths to PATH if they are not already there
set Path=C:\Program Files\Git\cmd;C:\Program Files\CMake\bin;C:\ProgramData\chocolatey\bin;%GNUARMEMB_TOOLCHAIN_PATH%\bin;C:\Program Files\SEGGER\JLink;%Path%
REM Activate the virtual environment, note the actual path
call D:\zephyrproject.asset.venv\Scripts\activate.bat
REM Display tool versions to confirm they are available
cmake –version
ninja –version
python -V
west –version
Having to type the script path every time you start is also not convenient. There’s another trick: “One-click development environment creation.” Please follow these steps:
Open File Explorer and navigate to the D:\zephyrproject.asset directory.
Right-click on an empty space in the directory, select New → Shortcut.
In "Type the location of the item", enter cmd, and click Next.
In "Type a name for this shortcut", enter zephyrproject, and click Finish.
Back in the folder, you will see a shortcut. Select it.
Right-click and choose Properties. In the "Target" field, enter C:\Windows\System32\cmd.exe /K D:\zephyrproject.asset\setup_env.bat. In the "Start in" field, enter D:\zephyrproject. Click OK.
It should look like this when done:
181510m1se147pil4lledc.png
Now, double-clicking this shortcut will open a fully configured Zephyr development environment. This shortcut can be copied to other locations, like your desktop.
Next, the PowerShell method:PowerShell script D:\zephyrproject.asset\setup_env.ps1:
Set environment variables, make sure to use your actual paths
$env:ZEPHYR_BASE = “D:\zephyrproject\zephyr”
$env:ZEPHYR_TOOLCHAIN_VARIANT = “gnuarmemb”
$env:GNUARMEMB_TOOLCHAIN_PATH = “D:\apps\arm-gnu-toolchain-13.2.Rel1-mingw-w64-i686-arm-none-eabi”
Add tool executable paths to PATH if they are not already there
$env:Path = “C:\Program Files\Git\cmd;C:\Program Files\CMake\bin;C:\ProgramData\chocolatey\bin;$env:GNUARMEMB_TOOLCHAIN_PATH\bin;C:\Program Files\SEGGER\JLink;$env:Path”
Activate the virtual environment, note the actual path
$venvPath = “D:\zephyrproject.asset.venv\Scripts”
$activateScript = Join-Path -Path $venvPath -ChildPath “Activate.ps1”
& $activateScript
Display tool versions to confirm they are available
cmake –version
ninja –version
python -V
west –version
Steps to create the shortcut:
Open File Explorer and navigate to the D:\zephyrproject.asset directory.
Right-click on an empty space, select New → Shortcut.
In "Type the location of the item", enter powershell, and click Next.
In "Type a name for this shortcut", enter zephyrproject_ps, and click Finish.
Back in the folder, select the new shortcut.
Right-click and choose Properties. In the "Target" field, enter C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe -ExecutionPolicy Bypass -NoExit -File "D:\zephyrproject.asset\setup_env.ps1". In the "Start in" field, enter D:\zephyrproject. Click OK.
It should look like this when done:
181609qe04qoy1qb4z9dsy.png
Double-clicking the two shortcuts should open windows similar to this:
181652gglge43kf93yesg5.png
(Left is cmd, right is PowerShell. A note of caution: my system has Windows Terminal installed, which “contains” both cmd and PowerShell in one window, which may look different from traditional command line windows. Please ignore this difference.)
Sixth, verify the development environment.Now that the environment is set up, besides checking the software versions as the script does, we can also try to compile a project to see if all the necessary components are in place. [15]Open the command line (you can use the shortcuts we just created) and execute:
west build -p -b stm32_min_dev@blue zephyr\samples\hello_world
If everything is normal, you should see a compilation result similar to this:
181840k5d35hnmnvddirvl.png
This command compiles a program: an LED blinker for a common APM32F103XB development board.
图片.png
Once the compilation is successful, you can flash it to see it run. To flash using a J-Link:
west flash -r jlink
Porting - Part 1
Based on my development experience, porting Zephyr to a completely new MCU generally follows this process:
1. Create the basic file and folder structure.
2. Modify the files and ensure they compile successfully.
3. Add necessary drivers.
4. Continue to refine the drivers until they meet project requirements.
The first step is particularly difficult because building a Zephyr project involves many steps and tools, each with different input requirements, making the build system quite complex. I hope my experience can help engineers who need it to get started with porting quickly.
Here's a small tip: The "porting cycle" of "modify" → "compile and verify" → "modify again" → "verify again" is essential. It means you should compile and verify as soon as possible after each relatively complete modification.
After adding the necessary drivers in step three, we can perform simple tasks like blinking an LED. The rest is testing and refinement.
The entire porting process will be managed with Git and will be made public for any interested engineers to use. I must state in advance: this porting guide and the related code are the result of my personal time and effort outside of work, and not all content has been fully validated. If you intend to use this content in product development, please perform your own verification to ensure all functions are complete. I provide no guarantees and assume no liability for any direct or indirect damages resulting from the use of this software.
Getting Started
This is the first part of the porting work: creating the basic file and folder structure. As it involves a lot of content, please follow the steps carefully.
As mentioned earlier, this porting effort is organized as a module, so the first step is to create a file structure that conforms to the module standard. In the working directory (mine is `D:\zephyrproject`, which I won't repeat), create a folder named `g32r5_zephyr`. The porting code will be developed in this folder, which we will call the "porting directory". The initial file structure is:
D:\zephyrproject
└─g32r5_zephyr
└─zephyr
└─module.yml
For now, the file `D:\zephyrproject\g32r5_zephyr\zephyr\module.yml` only needs one line of content:
name: hal_g32r5
Following the "porting cycle, " let's first verify if this module is valid. Enter the development environment (i.e., open one of the two shortcuts from before), switch to the working directory, and run a compilation:
west build -p -b stm32_min_dev@blue zephyr\samples\hello_world -- -DZEPHYR_EXTRA_MODULES="D:\zephyrproject\g32r5_zephyr"
This build command is similar to the one in "Sixth, verify the development environment, " but with the addition of -- -DZEPHYR_EXTRA_MODULES="D:\zephyrproject\g32r5_zephyr". This addition tells the build tool (west) that there is an extra module to process.
If everything is normal, after the command executes, there will be a zephyr_modules.txt file in the build directory. You should find a line similar to this in the file:"hal_g32r5":"D:/zephyrproject/g32r5_zephyr":""
This content indicates that we have successfully created a complete module that west can recognize, even though this module has no substantial content yet :)A successful first step! Worth celebrating.
Create a Simple Test Program
To facilitate the porting process, let's add a simple program that we can modify at any time during porting without altering the Zephyr source code.In the porting directory, create a test folder and copy all the contents from zephyr\samples\hello_world into it.
Additionally, most of the subsequent modifications will require cleaning the existing build and re-configuring/re-building. To avoid typing long build commands every time, I will create a script do_build.bat in the porting directory specifically for re-building:
@echo off
setlocal enabledelayedexpansion
set "CURRENT_PATH=%~dp0"
set "PARENT_PATH=!CURRENT_PATH:~0,-1!"
set "PARENT_PATH=!parent_path:\=/!"
set "PROJECT_ROOT=%parent_path%/test"
set "BOARD=stm32_min_dev@blue"
echo ZEPHYR_EXTRA_MODULES: !PARENT_PATH!
echo ZEPHYR_TOOLCHAIN_VARIANT: !ZEPHYR_TOOLCHAIN_VARIANT!
REM Delete build directory
del build /q /f /s >NUL 2>&1
west build -p -b stm32_min_dev@blue !PROJECT_ROOT! -- -DZEPHYR_EXTRA_MODULES=!PARENT_PATH!
endlocal
Now, in the working directory, you just need to execute:
g32r5_zephyr\do_build.bat
to perform a fresh configuration and build. Later in the porting process, when we add support for the target development board, we will only need to modify the
BOARD line in do_build.bat to rebuild.
Add SoC-related Content
This is the most difficult step in the porting process, requiring many files of various types and formats. Because it's a cohesive part of the port, compiling and debugging after every single file change would make the article too lengthy. Therefore, this section will present all the content first and then proceed with a compilation test.I will number the steps in this stage for better readability.
1. Modify g32r5_zephyr\zephyr\module.yml
The purpose of modifying this file is to let the west build tool know that the porting directory contains a new SoC to be included in the build. The modified file should look like this:
name: hal_g32r5
build:
cmake: .
kconfig: Kconfig
settings:
board_root: .
dts_root: .
soc_root: .
Compared to the previous content, the build section and subsequent lines are new. This tells the west tool that the current directory (which is critically the porting directory!) contains board and SoC related content that needs to be processed along with the Zephyr source directory during the build.
2. Add the soc Directory
In the porting directory, create the soc directory. Do not change the file/folder names, or west will not be able to find them.The complete file/folder structure under the soc directory is as follows:
│ CMakeLists.txt
│
└─geehy
└─g2r5
│ CMakeLists.txt
│ Kconfig
│ Kconfig.defconfig
│ Kconfig.soc
│ linker.ld
│ soc.yml
│
├─common
│ CMakeLists.txt
│ pinctrl_soc.h
│
└─g32r501
CMakeLists.txt
Kconfig.soc
soc.c
soc.h
That's a lot of files. The following will focus on the purpose and key content of these files. For the full content, please refer to the source code directly.
→ g32r5_zephyr\soc\CMakeLists.txtThis file specifies how the soc directory is included in the build. The purpose of other CMakeLists.txt files is the same and will not be repeated.
→ g32r5_zephyr\geehy\g32r5This directory structure corresponds to the knowledge from the "Basic Concepts" section. If you don't understand, please go back and read it.
→ g32r5_zephyr\geehy\g32r5\KconfigThis file defines the configuration item for the SOC-Family and also selects its dependencies. Key content is as follows:
config SOC_FAMILY_G32R5
bool
select BUILD_OUTPUT_HEX
select USE_G32R5_HAL
select CPU_HAS_ARM_MPU
select CPU_HAS_MPU
select CPU_HAS_FPU
select ARMV8_M_DSP
The purpose of this content is to define SOC_FAMILY_G32R5 and its dependencies. This means that if you use the G32R5 SOC_FAMILY, you must also select all items listed in the select statements. It's important to note that all items except USE_G32R5_HAL are defined by Zephyr itself. USE_G32R5_HAL is part of our port.
→ g32r5_zephyr\geehy\g32r5\Kconfig.defconfigThis file is optional. Its purpose is to select some options related to the G32R5. It can be an empty file for now.
→ g32r5_zephyr\geehy\g32r5\Kconfig.socThe main content of this file is:
config SOC_FAMILY
default "g32r5" if SOC_FAMILY_G32R5
config SYS_CLOCK_HW_CYCLES_PER_SEC
int
default 240000000 if SOC_FAMILY_G32R5
rsource "*/Kconfig.soc"
The config SOC_FAMILY line provides a string-type configuration item, primarily to provide a global CONFIG_SOC_FAMILY macro definition, which will be used during configuration and build processes.The config SYS_CLOCK_HW_CYCLES_PER_SEC line defines the hardware system clock frequency. We'll use a fixed value for now, which can later be modified to be obtained from the DeviceTree.The last line traverses all subdirectories for Kconfig.soc files, if any. For this project, it will only find g32r5_zephyr\geehy\g32r5\g32r501\Kconfig.soc.
→ g32r5_zephyr\geehy\commonThis directory contains common resources for the G32R5 Family.
→ g32r5_zephyr\geehy\g32r5\g32r501The content of this directory corresponds to the g32r501 soc-series.
→ g32r5_zephyr\soc\geehy\g32r5\g32r501\Kconfig.socThis defines the g32r501 soc-series and the specific socs under this series. The main content is:
config SOC_SERIES_G32R501
bool "G32R501 Series MCU"
select ARM
select SOC_FAMILY_G32R5
select CPU_HAS_FPU
select CPU_CORTEX_M55
select ARMV8_1_M_MVEI
select ARMV8_1_M_MVEF
help
Enable support for Geehy G32R501 MCU series
config SOC_SERIES
default "g32r501" if SOC_SERIES_G32R501
config SOC_G32R501DVXT
bool "G32R501DVXT"
select SOC_SERIES_G32R501
config SOC_G32R501DRXT
bool "G32R501DRXT"
select SOC_SERIES_G32R501
# ...
config SOC
default "g32r501dvxt" if SOC_G32R501DVXT
default "g32r501drxt" if SOC_G32R501DRXT
default "g32r501dmxt" if SOC_G32R501DMXT
default "g32r501dnxt" if SOC_G32R501DNXU
config FLASH_SIZE
default 256
config SRAM_SIZE
default 16
config FLASH_BASE_ADDRESS
default 0x08000000
config SRAM_BASE_ADDRESS
default 0x20000000
config NUM_IRQS
default 227
config SOC_SERIES_G32R501 defines the G32R501 SOC-SERIES (please review the concept earlier). Here you can see we are basing it on the Cortex-M55 core instead of the Cortex-M52. The reason for this was mentioned earlier: Zephyr does not yet support Cortex-M52, and the difficulty of an architecture port is beyond my current skill level. Since the M52 and M55 are in the same family with only some feature differences that do not affect the current porting work, we are proceeding with the M55 as a base. The rest of the file defines specific MCU models and necessary information like Flash size.
→ g32r5_zephyr\soc\geehy\g32r5\g32r501\soc.c/.hThese two source files are the essential base source code for this SoC series. soc.h in particular cannot be omitted, as many low-level Zephyr codes will include this header file.The soc.h file cannot be missing, but its content can be very simple:
#ifndef SOC_H_
#define SOC_H_
#include <g32r501.h>
#endif /* SOC_H_ */
Yes, just one effective line, including the corresponding header file for the G32R501 from the SDK.This concludes the introduction to the soc directory. The content is quite complex, and you can deepen your understanding by examining the actual files in the code repository.
3. Add the dts Directory
The dts related files are the "ingredients list" for the DeviceTree. The dtc tool will process a series of dts files to generate a complete DeviceTree and related header files for subsequent compilation.Besides files with the .dts extension, there are also .dtsi files, which are analogous to .h files for .c files.
In the porting directory, create the multi-level folder: dts\geehy\g32r5, and in this folder, create the file g32r501.dtsi with the following main content:
#include <arm/armv8.1-m.dtsi>
#include <zephyr/dt-bindings/i2c/i2c.h>
#include <zephyr/dt-bindings/gpio/gpio.h>
#include <zephyr/dt-bindings/adc/adc.h>
#include <freq.h>
#include <mem.h>
/ {
cpus {
#address-cells = <1>;
#size-cells = <0>;
cpu0: cpu@0 {
compatible = "arm,cortex-m52";
reg = <0>;
#address-cells = <1>;
#size-cells = <1>;
clock-frequency = <DT_FREQ_M(168)>;
mpu: mpu@e000ed90 {
compatible = "arm,armv8m-mpu";
reg = <0xe000ed90 0x40>;
};
};
};
};
&nvic {
arm,num-irq-priority-bits = <4>;
};
The content is very concise and only specifies some information about the core.
4. Add the SDK
This step adds the official SDK for the G32R501 to the project. Since I couldn't find an official code repository, I'm referencing a repository on Gitee.
I should add that the porting project is managed using Git. You can create a Git repository in the porting directory by running the command:
git init .
Then, use this command to add the SDK:
git submodule add https://gitee.com/quincyzh/hal_geehy_g32r501.git sdk/g32r501
After successfully pulling the code, the sdk\g32r501 directory will appear in the porting directory.
To enable the SDK to be included in the compilation, we need to add two CMakeLists.txt files and two Kconfig files. One set of files is in the porting directory, and the other is in the sdk directory.
CMakeLists.txt in the porting directory:
# G32R5
add_subdirectory_ifdef(CONFIG_SOC_FAMILY_G32R5 sdk)
zephyr_include_directories_ifdef(CONFIG_SOC_FAMILY_G32R5 include)
Kconfig
in the porting directory:
# Kconfig
rsource "sdk/Kconfig"
The effective content is to source sdk/Kconfig.
CMakeLists.txt in the sdk directory:
# sdk/CMakeLists.txt
zephyr_library()
zephyr_compile_definitions(
-D__ARM_ARCH_8_1M_MAIN___
-D__ARM_TARGET_COPROC
-D__G32R501__
-D__G32R501XX__
-D__CORE_CPU0__
)
zephyr_include_directories(g32r501/device_support/g32r501/common/device/Geehy)
zephyr_include_directories(g32r501/device_support/g32r501/common/device/CMSIS/Core/Include)
zephyr_include_directories(g32r501/device_support/g32r501/common/device/Geehy/system_eval/include)
zephyr_include_directories(g32r501/driverlib/g32r501/driverlib)
zephyr_include_directories(g32r501/device_support/g32r501/headers/include)
file(GLOB_RECURSE HAL_SOURCES
g32r501/driverlib/g32r501/driverlib/*.c
)
# Remove some files
set(BLACKLIST_HAL_SOURCES
"${CMAKE_CURRENT_SOURCE_DIR}/g32r501/driverlib/g32r501/driverlib/interrupt.c"
)
list(REMOVE_ITEM HAL_SOURCES ${BLACKLIST_HAL_SOURCES})
zephyr_library_sources(${HAL_SOURCES})
The `Kconfig` file under the SDK is an empty file. It's kept mainly for adding functionality later.
These two `CMakeLists.txt` files add the relevant files from the SDK directory to the build and also add necessary macro definitions. Two points to note here:
* Functions starting with `zephyr_` are extensions provided by Zephyr, not built-in CMake functions.
* Functions ending with `_ifdef` are checked during the build process and are only executed if the variable represented by the first parameter is defined. This parameter is generated by the Kconfig tool based on the Kconfig option files.
5. Add Development Board-related Content
The development board we are porting is the G32R501 Micro-EVB:
182316yxfu7emu5cvye7dv.png
The documentation is here. The main resources on this board are:
* On-board CMSIS-DAP compatible emulator: Geehy-Link debugger x1
* Peripheral resources:
* RESET KEY x1
* LED x2
* 40-pin ExpandPack interface x1
Porting steps:
In the porting folder, create the directory `boards\geehy\g32r501_micro_evb`, and create the following text files:
board.yml
g32r501_micro_evb.dts
g32r501_micro_evb.yaml
g32r501_micro_evb_defconfig
Kconfig.defconfig
Kconfig.g32r501_micro_evb
For the specific content of each file, please refer to the code repository. Here, I'll introduce `g32r501_micro_evb.dts`:
/dts-v1/;
#include <geehy/g32r5/g32r501.dtsi>
/ {
model = "Geehy G32R501 Eval";
compatible = "geehy,g32r501";
chosen {
zephyr,flash = &flash0;
};
};
The include line in the file includes the dtsi file we wrote earlier. With this, we can now proceed to compile.
6. SoC Initialization
Every MCU has some necessary initialization tasks to ensure the software system is in a deterministic state after a reset.For the G32R501 SoC, the most basic initialization must include:
Enabling the CP12 coprocessor function: The G32R501's "write register protection (WRPRT)" feature depends on the coprocessor.
Disabling the watchdog: The G32G501's watchdog is enabled by default, so we'll disable it for now.You can refer to the G32R501 user manual for details.
Find the file soc\geehy\g32r5\g32r501\soc.c. It's currently empty. Let's add the following content:
#include <zephyr/kernel.h>
#include <zephyr/init.h>
#include "soc.h"
#if defined(CONFIG_SOC_PREP_HOOK)
// execute before z_bss_zero and z_data_copy(C runtime initialize)
void soc_prep_hook(void)
{
// Enable CP0 Full Access and CP0 Non-secure Access
SCB->CPACR |= (3U << 0U*2U);
SCB->NSACR |= (3U << 0U*2U);
// Enable WRPRT Protection COP
SCB->CPACR |= 0xC;
__DSB();
__ISB();
// Disable the Watchdog Timer
__wrprt_disable();
WD->WDCR = (0x5U << WD_WDCR_WDCHK_Pos) |
(0x1U << WD_WDCR_WDDIS_Pos);
__wrprt_enable();
}
#endif /* CONFIG_SOC_PREP_HOOK */
The main function of soc.c is the two points mentioned above.
Also, as you can see from the source code, this function is only compiled if the macro CONFIG_SOC_PREP_HOOK is defined. As mentioned before, macros of the CONFIG_ type are generated by the Kconfig tool, so we need to handle this in a Kconfig file. There are two ways to enable this macro:
Enable this option in the project-level Kconfig file.
Directly enable this option in the SoC-level Kconfig file.
Since this feature is SoC-related, we will enable it directly in the SoC-related file. The specific method is to modify the soc\geehy\g32r5\g32r501\Kconfig.soc file:
config SOC_SERIES_G32R501
bool "G32R501 Series MCU"
select ARM
select SOC_FAMILY_G32R5
select CPU_HAS_FPU
select CPU_CORTEX_M55
select ARMV8_1_M_MVEI
select ARMV8_1_M_MVEF
select SOC_PREP_HOOK
Add select SOC_PREP_HOOK under the SOC_SERIES_G32R501 option, and that's it.The simplest SoC initialization work is now complete. Let's compile and test.
6. Simple TestModify the BOARD in the do_build.bat file in the porting directory:
@echo off
setlocal enabledelayedexpansion
set "CURRENT_PATH=%~dp0"
set "PARENT_PATH=!CURRENT_PATH:~0,-1!"
set "PARENT_PATH=!parent_path:\=/!"
set "PROJECT_ROOT=%parent_path%/test"
set "BOARD=g32r501_micro_evb"
echo ZEPHYR_EXTRA_MODULES: !PARENT_PATH!
echo ZEPHYR_TOOLCHAIN_VARIANT: !ZEPHYR_TOOLCHAIN_VARIANT!
REM Delete build directory
del build /q /f /s >NUL 2>&1
west build -p -b !BOARD! !PROJECT_ROOT! -- -DZEPHYR_EXTRA_MODULES=!PARENT_PATH!
endlocal
Yes, change BOARD to our defined development board name: g32r501_micro_evb.Then, execute this script:
182402hb7847bdhhnr8bya.png
The image above shows my compilation result, which was clearly successful. The two red boxes show that the newly defined development board has been used.This successfully compiled program can be downloaded and executed, although you won't see any visible activity.
Starting a debug session, you can see the code running to the main function. Don't underestimate the process of reaching main. The Zephyr system's startup process is actually quite complex, and the main function is a built-in task of the system. Reaching the main function already indicates that the system has been initialized, including the C runtime environment, the Zephyr kernel, and the defined drivers. Therefore, being able to enter main during debugging proves that our porting work so far has been successful.
Summary
At this point, the most basic porting work is complete.This part was also quite difficult: we borrowed content from the Cortex-M55 architecture to port the Zephyr kernel to the new G32R501 MCU. Although the clock is not yet correctly initialized and the system tick frequency is certainly inaccurate, it is actually running. Next, we need to port more drivers: clock, GPIO, UART, etc., which we will cover in the second part.
Finally, the porting content has been made public in a Gitee code repository. You can view the "add soc driver" commit in the repository. Code repository: https://gitee.com/quincyzh/g32r5_zephyr
This is the end of Part 1. Please look forward to Part 2.