API GUIDE / CAN / OVERVIEW
G32S10 CAN API 概述
模块概述:本文档描述 G32S10 SDK 当前提供的 CAN 硬件驱动层:
1. 文档范围
本文档描述 G32S10 SDK 当前提供的 CAN 硬件驱动层:
| 层级 | 职责 |
|---|---|
| LL | 直接访问 CAN 寄存器和位域,不维护软件状态 |
| HAL | 管理 CPM 时钟/复位、原始位时序和 filter 配置、帧寄存器访问、控制器状态、外设中断源、callback 以及 CAN 寄存器窗口 DMA 地址 |
CAN 帧协议语义、DLC 转换、bitrate 查表、SoC IRQ 所有权、DMA 通道申请、waiter、
队列、超时、恢复策略和统计信息属于可选的 CAN middleware,详见code/middleware/can/example/README.md。
HAL 会检查寄存器访问所需的前置条件,包括句柄、实例、filter index 和控制器状态
是否合法。HAL 可以在逻辑帧字段与 TFIR/RFIR/RXID 原始字段之间转换,但不负责
DLC/应用长度换算、完整 CAN 帧语义校验或 im_can_frame_t 转换,也不维护完整的
收发策略。
2. 编译配置与文件
直接使用 HAL/LL 时需要使能:
CONFIG_DRIVER_CAN=y
DRIVER_CAN 会选择 CAN HAL 及其 CPM 依赖,不会自动选择 OS、DMA 驱动或 CAN
middleware。
可选的寄存器 dump helper 还需要同时使能:
CONFIG_SDK_ENABLE_DEBUG_HELPERS=y CONFIG_CAN_ENABLE_DEBUG_HELPERS=y
未同时使能这两个选项时,hal_can_regs_dump() 保留公开符号,但返回IM_ERR_UNSUPPORTED,不会读取或打印寄存器。
相关源文件如下:
| 文件 | 职责 |
|---|---|
code/include/drivers/g32s10/can/hal_can.h | HAL 公开类型和函数 |
code/drivers/g32s10/can/hal_can.c | HAL 实现及 CPM 集成 |
code/include/drivers/g32s10/can/ll_can.h | LL 寄存器和位域辅助接口 |
code/include/drivers/g32s10/can/can_regs.h | 寄存器布局、实例和 PM 位定义 |
code/drivers/g32s10/can/Kconfig | DRIVER_CAN 配置 |
code/drivers/g32s10/can/CMakeLists.txt | HAL 源文件注册 |
当前支持 CAN0 和 CAN1 两个寄存器块实例。板级 pinmux 和外部 CAN 收发器
配置仍由 BSP 和硬件设计负责。
3. 位时序字段
HAL 接收已经编码的寄存器字段,不根据目标 bitrate 自动计算时序:
typedef struct {
uint32_t tseg1;
uint32_t tseg2;
uint32_t sjw;
uint32_t divider;
} hal_can_bit_timing_t;实际值计算如下:
TSEG1 = tseg1 + 1 TSEG2 = tseg2 + 1 SJW = sjw + 1 BRP = divider + 1 bitrate = CANCLK / (BRP * (1 + TSEG1 + TSEG2))
PM 定义的编码字段范围如下:
| 字段 | 编码范围 |
|---|---|
tseg1 | 0..15 |
tseg2 | 0..7 |
sjw | 0..3,同时受 PM 中与 tseg2 的关系约束 |
divider | 0..63 |
HAL 在写寄存器前校验每个字段是否位于上述编码范围,但不会根据物理 bitrate 选择
timing profile,也不校验 sjw <= tseg2 等协议层时序关系。hal_can_set_timing() 仅可在控制器处于 reset 时调用。
4. 原始帧镜像与 Filter
HAL 对外提供控制器原始 TX/RX 寄存器窗口镜像:
typedef struct {
uint32_t frame_info;
uint32_t id;
uint32_t data[HAL_CAN_DATA_REG_COUNT];
} hal_can_frame_image_t;镜像共 18 个 word,即 72 byte。frame_info、id 和 data 保存 PM 定义的原始
寄存器值。HAL 还提供不暴露寄存器 bit 位置的逻辑字段结构:
typedef struct {
uint32_t dlc;
uint32_t filter_match;
bool is_extended;
bool is_remote;
bool is_fd;
bool brs;
bool esi;
} hal_can_frame_info_t;dlc、帧格式、remote、FD 和 BRS 可用于 TX 编码及 RX 解码;filter_match 和esi 来自 RX 帧信息。该结构描述寄存器字段的逻辑值,不等同于应用层 CAN 帧。
HAL 仍然不负责:
根据 payload byte 长度计算 DLC;
校验标准标识符或扩展标识符范围;
校验 remote、FD、BRS 与 payload 长度组合;
判断 data 窗口中有多少 byte 有效。
hal_can_tx_frame_info_encode() 把逻辑字段编码为原始 TFIR,hal_can_rx_frame_info_decode() 解码原始 RFIR,hal_can_rx_id_decode() 从原始
RXID 中提取有效标识符。寄存器 bit 位置和 RXID mask 因而由 HAL 维护。
hal_can_tx_image_write() 将镜像复制到 TX 寄存器窗口。hal_can_tx_header_get() 在不修改窗口的情况下读回原始 TFIR/TXID header,使
DMA owner 可以通过 HAL 验证写入可见性。hal_can_tx_request() 请求发送,hal_can_tx_abort() 取消当前发送请求。hal_can_rx_image_read() 复制一个可用
RX 镜像,调用方随后必须调用 hal_can_rx_release() 释放硬件 RX buffer。
这些接口均为立即操作,不实现软件 timeout 或 retry loop。
Acceptance filter 使用:
typedef struct {
uint32_t id;
uint32_t mask;
} hal_can_filter_t;mask bit 为 0 时比较对应标识符 bit,为 1 时忽略该 bit。id 和 mask 均为 29 位硬件字段,HAL 会拒绝超过 0x1FFFFFFF 的值。HAL_CAN_FILTER_ACCEPT_ALL 表示全部 bit 均忽略。配置、使能或关闭 filter 时,
控制器必须处于 reset。
5. 已移除的旧版策略接口
重构后的 HAL 不再提供:
内置模块时钟或 baud-rate 查找表;
hal_can_set_baud();独立的
hal_can_set_module_clock();hal_can_config_t.bus_rate或manual_timing_enable;HAL_CAN_DMA_REQUEST_TX;HAL 所有的
hal_can_frame_t和帧/DLC 校验 helper;独立的
hal_can_frame.c或im_can_timing.c源文件。
应用需要基于 bitrate 配置和应用级 im_can_frame_t 收发时,应使用可选的 CAN
middleware。应用自行管理原始硬件 timing、帧镜像编码、IRQ 路由和传输策略时,
可以直接使用 HAL。