网站中使用特殊字体,成品网站nike源码1688免费,网站开发中 倒计时 源码,没有域名装wordpress背景
最近工作中接触到了 Zephyr#xff0c;不由觉得 Zephyr 是个很强大、全面、优秀的实时操作系统#xff0c;但同时是有一定的上手难度的#xff0c;其复杂的构建系统让小编倒吸一口凉气。为了深入研究并完全掌控 Zephyr#xff0c;小编决定把它移植到手头的开发板上…背景
最近工作中接触到了 Zephyr不由觉得 Zephyr 是个很强大、全面、优秀的实时操作系统但同时是有一定的上手难度的其复杂的构建系统让小编倒吸一口凉气。为了深入研究并完全掌控 Zephyr小编决定把它移植到手头的开发板上为后续探究 Zephyr 源码仓库的构建原理、系统启动原理、多种调度机制 打下基础。
基础知识
搭建 Zephyr 环境能够使用基本的 west 命令编译、烧录、调试 bsp
可通过 Zephyr 源码调试 章节验证基础知识的掌握程度。具体 west 工具的细节以及整个 elf 文件链接过程暂时不要深究这是个很深的坑。
移植
Zephyr 仓库下面有很多开发板的基础 bsp我们可以寻找一个与我们开发板上芯片型号类似的 bsp 作为参考。Art-Pi 主控是 Stm32H750XBH6主频高达 480Mhz片上资源非常丰富。
我们可以参考 zephyr/boards/st 目录下的 stm32h750b_dk 该目录树结构如下
stm32h750b_dk
├── Kconfig.stm32h750b_dk
├── arduino_r3_connector.dtsi
├── board.cmake
├── board.yml
├── doc
│ ├── img
│ │ └── stm32h750b_dk.png
│ └── index.rst
├── stm32h750b_dk.dts
├── stm32h750b_dk.yaml
├── stm32h750b_dk_defconfig
└── support└── openocd.cfg各文件描述如下
Kconfig.stm32h750b_dk : 板级 Kconfig 定义用于控制板级资源如使能 HAL 层的各个驱动arduino_r3_connector.dtsi : arduino 扩展引脚设备树定义我们的板子不需要该文件直接删除board.cmake 板级 CMake 配置一般用于配置板子所使用的调试器参数比如使用 openocd 作为调试器 Serverboard.yml : 板级描述文件暂时不清楚有什么用但没有这个文件构建系统会报错doc板子介绍stm32h750b_dk.dts : 板子设备树定义stm32h750b_dk.yaml : 板级测试相关Zephyr 自动化单元测试系统使用stm32h750b_dk_defconfig : 板级 Kconfig 默认值如果在此处配置了默认值就无法通过 menuconfig 或者 App 目录下的 pri.conf 文件中进行修改openocd.cfg : openocd 配置文件如果 board.cmake 中使用 openocd 作为调试器的 server该文件将会被传递给 openocd 使用
主要是板子设备树文件比较重要该文件涉及芯片时钟、外设、内存、flash 配置。其余文件中的内容全部改为自己的开发板Art-Pi 设备树文件最终配置如下
/** Copyright (c) 2023 STMicroelectronics** SPDX-License-Identifier: Apache-2.0*//dts-v1/;
#include st/h7/stm32h750Xb.dtsi
#include st/h7/stm32h750xbhx-pinctrl.dtsi
#include zephyr/dt-bindings/input/input-event-codes.h/ {model STM32H750XBH6 ART PI;compatible st,stm32h750xb-art-pi;chosen {zephyr,console uart4; // uart4 作为控制台输出zephyr,shell-uart uart4; // uart4 作为控制台输入zephyr,sram sram0; // 使用 sram0 作为片内 sramsram0 的定义在 dtsi 文件中zephyr,flash flash0; // 使用 flash0 作为片内 flash这个并不决定链接时各符号的加载地址而是由 CONFIG_FLASH_BASE_ADDRESS 这个宏决定zephyr 构建系统的链接脚本有点复杂暂时不深究};leds {compatible gpio-leds;blue_led: led_1 {gpios gpioi 8 GPIO_ACTIVE_LOW; // 定义板子蓝灯引脚label USER2 LD7;};red_led: led_2 {gpios gpioc 15 GPIO_ACTIVE_LOW; // 定义板子红灯引脚label USER2 LD7;};};gpio_keys {compatible gpio-keys; // 定义板子按键引脚user_button: button {label User;gpios gpioh 4 GPIO_ACTIVE_LOW;zephyr,code INPUT_KEY_0;};};sdram1: sdramc0000000 { // 定义板子片外 sdram 地址使用 fmc 驱动compatible zephyr,memory-region, mmio-sram;device_type memory;reg 0xc0000000 DT_SIZE_M(32); // 定义 sdram 起始地址、尺寸zephyr,memory-region SDRAM1;zephyr,memory-attr ( DT_MEM_ARM(ATTR_MPU_RAM) );};aliases {led0 blue_led;led1 red_led;sw0 user_button;};
};clk_hse { // 外部 hse 定义clock-frequency DT_FREQ_M(25);status okay;
};pll { // pll 配置h750 系列的时钟树比较复杂可通过 cubemx 简化配置div-m 5;mul-n 192;div-p 2;div-q 4;div-r 4;clocks clk_hse;status okay;
};rcc { // 系统各时钟域配置clocks pll;clock-frequency DT_FREQ_M(480);d1cpre 1;hpre 2;d1ppre 2;d2ppre1 2;d2ppre2 2;d3ppre 2;
};uart4 { // uart4 作为 zephyr 控制台pinctrl-0 uart4_tx_pa0 uart4_rx_pi9;pinctrl-names default;current-speed 115200;status okay;
};fmc { // fmc 配置用于驱动 sdram 芯片status okay;pinctrl-0 fmc_nbl0_pe0 fmc_nbl1_pe1fmc_sdclk_pg8 fmc_sdnwe_ph5 fmc_sdcke0_pc3fmc_sdne0_pc2 fmc_sdnras_pf11 fmc_sdncas_pg15fmc_a0_pf0 fmc_a1_pf1 fmc_a2_pf2 fmc_a3_pf3 fmc_a4_pf4fmc_a5_pf5 fmc_a6_pf12 fmc_a7_pf13 fmc_a8_pf14fmc_a9_pf15 fmc_a10_pg0 fmc_a11_pg1 fmc_a12_pg2fmc_a14_pg4 fmc_a15_pg5 fmc_d0_pd14 fmc_d1_pd15fmc_d2_pd0 fmc_d3_pd1 fmc_d4_pe7 fmc_d5_pe8 fmc_d6_pe9fmc_d7_pe10 fmc_d8_pe11 fmc_d9_pe12 fmc_d10_pe13fmc_d11_pe14 fmc_d12_pe15 fmc_d13_pd8 fmc_d14_pd9fmc_d15_pd10;pinctrl-names default;sdram {status okay;power-up-delay 100;num-auto-refresh 8;mode-register 0x221;refresh-rate 0x02A5;bank0 {reg 0;st,sdram-control STM32_FMC_SDRAM_NC_9STM32_FMC_SDRAM_NR_13STM32_FMC_SDRAM_MWID_16STM32_FMC_SDRAM_NB_4STM32_FMC_SDRAM_CAS_2STM32_FMC_SDRAM_SDCLK_PERIOD_2STM32_FMC_SDRAM_RBURST_ENABLESTM32_FMC_SDRAM_RPIPE_0;st,sdram-timing 2 8 6 6 2 2 2;};};
};仅通过如上配置就能够编译并链接通过其背后是 Zephyr 对 stm32 系列芯片 hal 库以及外设驱动的完美适配以至于用户仅通过简单的设备树描述就能让外部设备正常工作起来。最终 Art-Pi 目录结构如下
stm32h750_art_pi
├── Kconfig.defconfig
├── board.cmake
├── board.yml
├── stm32h750_art_pi.dts
├── stm32h750_art_pi_defconfig
└── support└── openocd.cfg // openocd 默认会掉用 openocd.cfg 文件该文件用于描述 openocd 控制的硬件调试器如 stlinkjlink 板级调试
以上步骤全部通过后会面临一个问题如何将固件搞到芯片里面由于我是使用的 stm32 系列同时拥有 stlink 调试器可通过 STM32CubeProgrammer 工具擦除并将固件下载到 flash。但会遇到一个问题固件并没有按照预期执行甚至没跑到 main 线程此时连串口都不能打印日志此时如果拥有调试器那便是如虎添翼。
Zephyr 的构建系统是支持下载以及调试能力的这时候也不需要使用 STM32CubeProgrammer 了。一般调试嵌入式设备需要硬件调试器板子不足以运行 gdb server但 Zephyr 貌似支持 gdb stub这样的话可以不需要硬件调试器、硬件调试器配套的 gdb serverstlink server、jlink server、openocd、gdb。我们选择使用 openocd 作为 gdb server。可通过使用 west flash 命令验证能否下载固件如图 这一命令的背后到底发生了什么其本质是调用 openocd 来将固件下入芯片内但这背后是如何调用起 openocd暂时不深追这个坑很深也正是 Zephyr 构建系统的复杂且神秘之处给人一种知其然不知其所以然的感觉小编决定后续几章来深究 Zephyr 构建系统原理。
此时一般会发现固件跑不起来这时候可以使用 west debugserver 命令来起一个 gdb server这个 gdb server 就是 openocd它在某个端口上起一个 tcp 服务通过 tcp 与 gdb client 交互双方通信是明文传输如图 Openocd 说它监听 3333 端口此时我们便可以通过 gdb 来连接 3333 端口进行调试了如图 使用命令行的方式虽然能进行调试但是很麻烦效率不高这时候可参考 Zephyr 源码调试章节 进行图形化界面调试这样子能大大提高解决问题的效率终极调试界面如图 我的开发环境是 wsl ubuntu使用 wsl 连接 usb 设备需要简单的配置一下可网上搜索 wsl usb 关键字查看相关教程。
应用配置
移植完毕后可通过 Zephyr 仓库 zephyr/samples/basic/blinky 下的应用来验证比如可在 main 函数中翻转 led 灯来验证。但此时Zephyr 的 shell 还不能使用因为 shell 作为 Zephyr 的一个子系统此时还未使能这也是 Zephyr 构建系统的一大优势以搭积木的形式构建系统缺少某一模块仍然能够编译链接通过仅仅是该能力缺失而已。可在 zephyr/samples/basic/blinky 下的 prj.conf 文件中添加如下配置
CONFIG_GPIOy
CONFIG_UART_CONSOLEy //使能 uart console
CONFIG_SHELLy //使能 shell 模块
CONFIG_MEMCy
CONFIG_MEMC_STM32y
CONFIG_MEMC_STM32_SDRAMy 最终就能丝滑的感受 Zephyr 了这才有点操作系统的味道。 最终附上 项目地址 欢迎 Star~~~