请从官网下载 TD4VM 技术参考手册,地址如下:
TDA4VM 技术参考手册地址
概述
(Mailbox 的介绍在 TRM 的第7.1章节)
Mailbox 使用邮箱中断机制实现了 VM 芯片的核间通信。
Mailbox 是集成在 NAVSS0 域下的一个外设(NAVSS0 的说明可以查看:TDA4VM/VH 芯片 NAVSS0)。
芯片上的 Mailbox 存在一定数量的邮箱实体(mailbox cluster
),整个mailbox 被称作 MAILBOX0
.
功能
MAILBOX0 的功能可以使用下面的图概括:
说明
- 共
12
个邮箱实体,每一个邮箱实体的配置方法一致,且可作为单独的邮箱外设使用(每一个邮箱实体分配的中断号都不一致); - MAILBOX0 的每一个邮箱实体可产生
4个中断号不一致的中断
,也就是说,每一个邮箱实体可实现4个核之间的核间通信
; - 每一个邮箱实体存在
16个队列
,每一个队列最多可保存4个message
,每一个message 宽度为4字节
; - 每一个邮箱可单独产生队列
接收新消息中断
,与队列未满中断
,每一个队列都可单独使能/失能中断;
MAILBOX0 集成实现
MAILBOX0 并不直接作为某一个芯片域的外设,而是集成在 NAVSS0 模块下:
说明:
- MAILBOX0 的时钟与复位由
LPSC0
配置,参考时钟为 MODSS_VBUS_D2_CLK, 来自 MAIN_SYSCLK0;复位信号为 MODSS_RST,由MOD_G_RST控制; - MAILBOX0 存在
12
个邮箱实体,每一个邮箱实体可作为一个单独的邮箱外设,产生4
个不同的中断:CLUSTER[0:11]_PEND_INTR[0:3]
; - MAILBOX0 的12个邮箱产生的
48个中断
,会被INTR_ROUTER0[439:392]
接收,处理器真正接收的中断是INTR_ROUTER0
的输出中断:OUTL_INTR[0:407]
;
注意:INTR_ROUTER0
是 NAVSS0
的一个外设,用于接收不同的中断信号,并路由给不同的处理器核来处理。NAVSS0
与 INTR_ROUTER0
可以查看下面的文章:
TDA4VM/VH 芯片 NAVSS0
邮箱功能描述
MAILBOX0 共实现了12
个邮箱,每一个邮箱都可以产生4个不同的中断,所以,每一个邮箱都可以为4个处理器提供核间通信。
中断使能:置位 MAILBOX_IRQ_ENABLE_SET_[0:3]
寄存器对应的位;
中断失能:置位 MAILBOX_IRQ_ENABLE_CLR_[0:3]
寄存器对应的位;
注意:上述寄存器只配置中断[0:3]的使能与失能,并不设置中断与处理器之间的映射关系,中断与处理器之间的映射关系通过 INTR_ROUTER0 来配置,通过将邮箱产生的中断映射到 INTR_ROUTER0 的输出中断上,实现指定的处理器核处理邮箱中断。
4个中断的状态可以通过 MAILBOX_IRQ_STATUS_RAW_[0:3]
/MAILBOX_IRQ_STATUS_CLR_[0:3]
来查看。
邮箱复位
邮箱可以通过 MAILBOX_SYSCONFIG[0].SOFTRESET
位来实现邮箱外设软复位。
邮箱的中断请求类型
每一个邮箱都实现了两类中断:
- 队列接收消息中断;
- 队列未满中断;
注意:每一个邮箱拥有16个队列,每一个队列可以单独使能或失能上述两类中断.
邮箱分配
接收(建议中断方式,如下):
- 首先通过
MAILBOX_IRQ_ENABLE_SET_[0:3]
使能邮箱的队列接收消息中断,然后通过INTR_ROUTER0
将邮箱中断映射到指定的输出中断
上,实现指定的处理器来处理邮箱的接收中断; - 接收的处理器可以读取
MAILBOX_MESSAGE_[0:15]
, 实现从邮箱的指定队列读取消息。
发送(建议轮询方式,如下):
- 读
MAILBOX_FIFO_STATUS_[0:15]
与MAIL_MSG_STATUS_[0:15]
检查指定队列的 FIFO 状态; - 如果指定的队列 FIFO 未满,则写新消息到
MAILBOX_MESSAGE_[0:15]
。
邮箱通信示例
说明:
User0
与User1
使用邮箱0
进行核间通信,其中,User0 的发送通道为队列0,接收通道为队列1,而User1 的发送通道为队列1,接收通道为队列0;- User0使用邮箱0 的
CLUSTER0_PEND_INTR0
作为队列1消息接收中断, 置位MAILBOX_IRQ_ENABLE_SET_0
的BIT2
。 - User1使用邮箱0的
CLUSTER0_PEND_INTR1
作为队列0消息接收中断, 置位MAILBOX_IRQ_ENABLE_SET_1
的BIT0
。 - User0 通过写
MAILBOX_MESSAGE_0
,实现往队列0中写消息,并触发CLUSTER0_PEND_INTR1
中断给 User1; - User0 通过写
MAILBOX_MESSAGE_1
,实现往队列1中写消息,并触发CLUSTER0_PEND_INTR0
中断给 User1;