1 项目介绍
本项目,基于eetree提供的i.MX RT1021开发板,适配了zephyr rtos,并适配了lcd驱动进行lvgl显示。不同于常见的rt-thread、freerots等rtos,zephyr驱动是以类linux的设备树方式进行管理的,因此本项目的大部分适配工作是建立针对eetree rt1021开发板的设备树。同时通过适配过程,也能体现出zephyr rtos基于设备树管理的优越性。
2 zephyr及设备树简介
2.1 zephyr
Zephyr是一个小型的实时操作系统,用于资源受限的嵌入式互联设备(主要是微控制器),支持多种架构,使用Apache许可证 2.0发行。Zephyr最初是风河系统公司在2015年11月推出的为物联网(IoT)设备开发的“Rocket内核”,更早时称为“Microkernel Profile for VxWorks”,代码移植于2001年并购Eonic Systems得来的Virtuoso DSP RTOS。在2016年2月,它成为Linux基金会的项目而改称现名。
2.1 设备树
设备树是一种描述特定硬件的数据结构,以便于操作系统更高的使用和管理硬件外设,它是一种树状的形态结构。
对应的描述语言:
/dts-v1/;
/ {
soc {
i2c-bus-controller {
i2c-peripheral-1 {
};
i2c-peripheral-2 {
};
i2c-peripheral-3 {
};
};
};
};
3 硬件介绍
eetree的i.MX RT1021开发板由核心板和底板两部分组成,基于恩智浦i.MX RT1020系列MIMXRT1021CAG4A芯片设计,有如下特点:
- 高性能 Arm Cortex-M7
- 2517 CoreMark/1070 DMIPS@500 MHz
- 高达 256KB 片内RAM
- 外扩8MB FLASH用于存储程序
- 丰富的接口UART、SPI、I2C、USB、USDHC等
- 丰富的外设:温湿度传感器、三轴磁场传感器、加速度角速度传感器、环境光传感器,一个RGB彩灯、一块128*160分辨率的电阻式触摸屏,一个旋钮,一个双轴电位计摇杆等
4 设备树适配
要让一个rtos正常运行,通常需要适配ram、flash、内核任务调度、uart这几个基础的方面。zephyr对于内核的支持已经非常完善,已经完成了目前绝大多数的内核适配,因此这部分我们可以不用关心。并且,nxp官方在zephyr提供了基于其官方开发板的设备树支持,我们可以作为参考,并主要关心不同开发板硬件差异的ram、flash、uart部分。同时为了运行lvgl,我们还需适配spi lcd驱动。
4.1 建立开发板dts文件
基于nxp 开发板dts进行修改,删除与我们无关的dts信息
4.2 ram设备树描述
&itcm {
reg = <0x00000000 DT_SIZE_K(64)>;
};
&dtcm {
reg = <0x20000000 DT_SIZE_K(64)>;
};
&ocram {
reg = <0x20200000 DT_SIZE_K(128)>;
};
4.3 flash设备树描述
&flexspi {
status = "okay";
reg = <0x402a8000 0x4000>, <0x60000000 DT_SIZE_M(8)>;
w25q64: w25q64@0 {
compatible = "nxp,imx-flexspi-nor";
size = <67108864>;
reg = <0>;
spi-max-frequency = <133000000>;
status = "okay";
jedec-id = [9d 70 17];
erase-block-size = <4096>;
write-block-size = <1>;
...
};
};
4.4 uart设备树描述
&lpuart1 {
status = "okay";
current-speed = <115200>;
pinctrl-0 = <&pinmux_lpuart1>;
pinctrl-1 = <&pinmux_lpuart1_sleep>;
pinctrl-names = "default", "sleep";
};
uart管脚适配:
pinmux_lpuart1: pinmux_lpuart1 {
group0 {
pinmux = <&iomuxc_gpio_ad_b0_07_lpuart1_rx>,
<&iomuxc_gpio_ad_b0_06_lpuart1_tx>;
drive-strength = "r0-6";
slew-rate = "slow";
nxp,speed = "100-mhz";
};
};
4.5 spi lcd设备树描述:
&lpspi4 {
status = "okay";
pinctrl-0 = <&pinmux_lpspi4>;
pinctrl-names = "default";
cs-gpios = <&gpio3 1 GPIO_ACTIVE_LOW>;
st7735r_st7735r_ada_160x128: st7735r@0 {
compatible = "sitronix,st7735r";
spi-max-frequency = <20000000>;
reg = <0>;
cmd-data-gpios = <&gpio3 4 GPIO_ACTIVE_LOW>; /* D9 */
reset-gpios = <&gpio3 7 GPIO_ACTIVE_LOW>; /* D8 */
width = <160>;
height = <128>;
x-offset = <0>;
y-offset = <0>;
madctl = <0x60>;
colmod = <0x55>;
vmctr1 = <0x0e>;
pwctr1 = [a2 02 84];
pwctr2 = [c5];
pwctr3 = [0a 00];
pwctr4 = [8a 2a];
pwctr5 = [8a ee];
frmctr1 = [01 2c 2d];
frmctr2 = [01 2c 2d];
frmctr3 = [01 2c 2d 01 2c 2d];
gamctrp1 = [02 1c 07 12 37 32 29 2d 29 25 2b 39 00 01 03 10];
gamctrn1 = [03 1d 07 06 2e 2c 29 2d 2e 2e 37 3f 00 00 02 10];
};
};
spi管脚适配:
pinmux_lpspi4: pinmux_lpspi4 {
group0 {
pinmux = <&iomuxc_gpio_emc_32_lpspi4_sck>,
<&iomuxc_gpio_emc_33_lpspi4_pcs0>,
<&iomuxc_gpio_emc_34_lpspi4_sdo>,
<&iomuxc_gpio_emc_35_lpspi4_sdi>;
drive-strength = "r0-6";
slew-rate = "fast";
nxp,speed = "100-mhz";
};
};
4.6 zephyr选定外设
chosen {
zephyr,flash-controller = &w25q64;
zephyr,flash = &w25q64;
zephyr,code-partition = &slot0_partition;
zephyr,sram = &ocram;
zephyr,itcm = &itcm;
zephyr,dtcm = &dtcm;
zephyr,console = &lpuart1;
zephyr,shell-uart = &lpuart1;
zephyr,display = &st7735r_st7735r_ada_160x128;
};
5 代码展示
工程代码位于:\samples\modules\lvgl\demos\目录
5.1 主线程代码
int main(void)
{
const struct device *display_dev;
display_dev = DEVICE_DT_GET(DT_CHOSEN(zephyr_display));
if (!device_is_ready(display_dev)) {
LOG_ERR("Device not ready, aborting test");
return 0;
}
printk("eetree i.MX RT1021 board\n");
#if defined(CONFIG_LV_USE_DEMO_MUSIC)
lv_demo_music();
#elif defined(CONFIG_LV_USE_DEMO_BENCHMARK)
lv_demo_benchmark();
#elif defined(CONFIG_LV_USE_DEMO_STRESS)
lv_demo_stress();
#else
#error Enable one of the demos CONFIG_LV_USE_DEMO_MUSIC, CONFIG_LV_USE_DEMO_BENCHMARK \
or CONFIG_LV_USE_DEMO_STRESS.
#endif
lv_task_handler();
display_blanking_off(display_dev);
while (1) {
int32_t time = lv_task_handler();
if(time>0)
k_msleep(lv_task_handler());
else
k_msleep(100);
}
return 0;
}
5.2 针对eetree硬件添加工程关键配置:
CONFIG_LV_COLOR_16_SWAP=y
CONFIG_MAIN_STACK_SIZE=32768
CONFIG_LV_Z_MEM_POOL_SIZE=65536
6 编译运行
west build -p auto -b mimxrt1020_evk samples\modules\lvgl\demos
7 小结
本文完成了在zephyr上对eetree board的基础功能适配,并可进行lvgl显示,代码通过gitee进行开源,为该板子的生态支持提供了基础贡献,未来可以在zephyr上基于该硬件探索更多的可能性。