双核单片机的开发其实并不困难!

2020-05-16 05:12:58
来源:文章来源于网络

多核微控制器(MCU)一直是设计上的一个主要挑战,特别是多核异构设计。早在2011年底,Enzipu半导体公司就率先推出了基于皮层-m4f和皮层-M0的双核MCU--lpc43xx/43sxx系列,主频高达204mhz。以其超强的加工性能,迅速受到业界的好评。四年后,单片机双核简化版lpc5411x系列,在广大lpc爱好者的期待下,终于展现出一代骄傲的天性。

双核单片机:lpc5411x

这lpc5411x系列单片机集成皮质-m4f和皮质-m0+双核与主频率高达100兆赫。由于皮层m4f内核采用哈佛体系结构,三级流水线,支持SIMD,支持单精度浮点运算,单时钟周期可以完成乘法和累加(Mac)指令,因此其处理性能较强,一般用于处理复杂的计算或算法。然而,皮质M0+内核结构简单,只有两级流水线,能量效率高,一般用于实时控制、外围管理、数据通信等任务。

在lpc5411x产品中,corpe-m4f是主核,corpe-m0+是从核。从内核的主要任务是协助主核处理非计算性的杂务,充分释放主核的计算能力,从而实现整个系统的最佳性能。

为了达到最佳的总体性能,lpc5411x采用多层ahb矩阵总线体系结构和多个内存块。下图显示了lpc5411x的内部功能框图,其中可以看到内部的ahb矩阵总线体系结构。在总线上,cor-m4f和m0+都是主总线,可以访问所有的片上资源。总线访问的优先级可以通过寄存器来设置。

Cortex-M4F核在AHB总线上有3个接口:I-code, D-code和System总线。而Cortex-M0+只有一个System总线接口。不同的RAM块可以被不同的AHB master同时访问。

双核MCU的存储区分配

I-code总线用于从CODE内存分区取指令, 地址范围是:0x0000-0000~0x1FFF-FFFF。D-code总线用于从CODE内存分区取操作数,地址范围是:0x0000-0000~0x1FFF-FFFF。

当以上两条总线同时访问同一内存单元时,D-code总线访问优先级比I-code高,所以D-code先访问。对地址范围从0x2000-0000~0xDFFF-FFFF的访问是通过System总线进行的,可用于访问操作数、指令等,数据访问的优先级高于取指令及中断向量。

各个存储区所在的地址区域如下表:

为优化系统整体处理能力,需要让这两个CPU内核同时以最快速度执行各自指令, 比如Cortex-M4F上能执行单周期的的MAC指令,同时Cortex-M0+上能执行单周期的32位乘法。

因此,存储区的合理分配策略是,Flash和RAMX以及SRAM0需要分配给Cortex-M4F内核,分别用于存放指令代码和操作数(见上图红/黄框部分)。而SRAM1/SRAM2这两块需要分给Cortex-M0+(见上图绿色框部分)。 需要注意的是,只要其中一个RAM块分配给某个CPU核,这个RAM块就不能分配给另一个CPU核, 否则这两个CPU核同时访问同一块区域时,就会出现总线争用,而导致另一个CPU核访问出现等待周期,从而降低整个系统处理效率。

双核运行的功耗如何?

在回答这个问题之前,让我们看一下其实测的CoreMark动态功耗图吧:

以代码放在Flash中运行并且主频为48MHz为例,Cortex-M4F动态功耗大约为96uA/MHz,而Cortex-M0+为75uA/MHz。两者之和为171uA/MHz,也就是说双核同时运行时的功耗为8.2mA。这个功耗比许多其他厂家的单Cortex-M4F核的MCU还低,但性能要强很多。

当然如果你比较关心功耗,可以根据应用实际情况让一个CPU内核进入低功耗模式,另一个CPU内核工作,等到一定条件时再唤醒另一个核。

双核之间怎么通信?

下面这张图说明了俩核之间的通信机制。

当一个CPU内核准备好数据之后,通过互锁信号放在共享RAM中,再通过邮箱机制产生中断事件,通知另一个CPU内核来处理。另一个CPU内核处理完数据后,清理相应的中断标志。通过这种方式可以实现实时性很强的双核通信和数据交换。也可以不用互锁信号和共享RAM,直接通过邮箱机制传递最多32位的数据。

另外一种简单的方法叫作消息队列机制:直接在共享RAM中创建循环缓冲器用于消息队列。当一个CPU内核准备好数据之后,就把数据发送到这个队列最后面(队尾),而另一CPU内核每次从这个队列的最前面取数据。对每个队列的访问是单向的,即一个CPU核只能写,而另一个CPU内核只能读。要实现双向,必须创建至少两个队列。 这种方法可以不用互锁信号,但可以使用中断机制通知另一个CPU核,以便实现实时通信和数据交换。

双核的开发很难吗?

针对双核以及多核体系架构,恩智浦提供了多核SDK开发库(称为MCSDK), 以及丰富的例程,包含在相应多核平台的MCUXpresso SDK 开发包中。 下图显示了MCSDK的架构:

eRPC即嵌入式远程过程调用(Embedded Remote Procedure Call),是一套实现调用另一核上远程服务的透明函数调用接口。MCMGR即多核管理器(Multicore Manager),是包含所有CPU内核信息及启动从核的函数调用接口。RPMsg-Lite即远程处理器消息机制精简版(Remote Processor Messaging – Lite),包含了所有处理器间通信的函数库。

这套库支持市面上所有主流ARM Cortex-M软件开发工具,包括IAR、KEIL、GCC,以及MCUXpresso IDE。

有了这套多核SDK开发库,用户可以不用关心硬件底层的通信机制,直接使用相应的例程和调用接口,几分钟内便可以实现双核间的通信和数据交换代码。

下面这个例子说明如何使用RPMsg-Lite,从一个CPU内核发送数据到另一内核:

rpmsg_lite_send(my_rpmsg, my_ept, REMOTE_EPT_ADDR, (char *)&msg, sizeof(msg), …);

其中my_rpmsg是rpmsg_lite_remote_init()或rpmsg_lite_master_init()调用所创建的RPMsg实例;如果是主CPU内核,就用rpmsg_lite_master_init()初始化, 否则就是远程CPU内核,用rpmsg_lite_remote_init()初始化

my_ept是此消息管道的端点,由rpmsg_lite_create_ept()调用创建的:

my_ept = rpmsg_lite_create_ept(my_rpmsg, LOCAL_EPT_ADDR, …);

msg是真正要交换的消息。

REMOTE_EPT_ADDR,LOCAL_EPT_ADDR分别是此消息管道的远程端点和本地端点的逻辑地址。

怎么调试双核应用程序?

在回答这个问题之前,先看一下硬件调试接口图:

上图说明,LPC5411x 系列支持对双核同时调试 ,就像调试单个CPU内核程序一样简单。