完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
扫一扫,分享给好友
本帖最后由 一只耳朵怪 于 2018-5-25 17:30 编辑
RM48L952 可以用CAN中断的方式接收数据, 我想用DMA的方式接收CAN数据. 有没有好的方法和例程.. |
|
相关推荐
44个回答
|
|
Hi Sam,
确实我们的DMA是支持CAN总线的硬件触发的,具体的DAM channel通道你可以在datasheet(不是TRM)里面找得到。 相关的例程我们暂时还没有,不过你可以参考HALCOGEN里面的关于MIBSPI的例程来修改。 谢谢 BR, KEN |
|
|
|
lining870815844 发表于 2018-5-25 06:38 哦。好的。最好能提供一个例程..谢谢。。 |
|
|
|
Hi Ken, 我有查看HALCOGEN里面的关于MIBSPI的例程,当时这几个函数不是太明白,需要一一解释: |
|
|
|
sam, 第一个函数是DMA channel的mapping操作,这里选择的是将DMA的第一个request 1 mapping到channel 0 上面。request 1 是有我们芯片定义的硬件触发MIBSPI的请求,这个可以在我们datasheet的4.16.2 的default DMA request map表格里查到。channel 数也是自己设置的,channel 0的优先级最高。 第二个函数是设置DMA的源地址,终端地址,以及DMA传输数据的长度 第三个函数是配置DMA的package, 里面包括DMA的传输方式,终端盒源端地址的offet 和每次地址跳转的大小,element的大小,frame的大小,读写的具体位数等等。这个DMA配置的重点 第四个函数是这是我们前面定义的channel 0 通道硬件触发。 第五个函数是设置具体的MIBSPI发送和接收的channel。 谢谢 BR, KEN |
|
|
|
lining870815844 发表于 2018-5-25 07:18 Hi Ken, 1.也就是说MIBSPI的硬件触发请求是request 1,那RM48L952 的CAN1的硬件触发请求是request X? .. 能否发份DATASHEET 2. DAM的源地址, 与终端地址配置有什么讲究? |
|
|
|
60user25 发表于 2018-5-25 07:37 Hi Sam, RM48L952的datasheet下载地址如下: http://www.ti.com/lit/ds/symlink/rm48l952.pdf DMA 的源端地址是有点讲究的,特别是选择为硬件触发的时候,你需要将远端地址设为相应的模块的数据寄存器或者类似于发送缓存器,接收缓存器之类的寄存器,这样才能硬件触发。终端地址还好,寄存器或是memory地址都行。 谢谢 BR, KEN |
|
|
|
lining870815844 发表于 2018-5-25 07:55 Hi Ken, 下面是例程但是有问题.不能进入DMA中断。 void main(void) [ /* Enable IRQ interrupt in ARM CPSR register */ _enable_interrupt_(); /* Reset the Flag */ DMA_Comp_Flag = 0xAAAA5555; /* initialize can 1 */ canInit(); // Enable DE3 bit in CTL register to trigger DMA when IF3 receives data // canREG1->CTL |= (1U << 20U); /* At present HALCoGen does not support IF3 configuration, * hence doing it here */ // Read ARB, DATA A & B - 8 bytes */ //canREG1->IF3OBS = 0x1A; // Read DATA A & B - 8 bytes */ canREG1->IF3OBS = 0x18; // Message box 2 configured for auto update canREG1->IF3UEy[0]= 0x0000002A; /* - DMA Configuration */ /* Enable DMA */ dmaEnable(); /* Enable Interrupt after reception of data */ dmaEnableInterrupt(DMA_CH0, FTC); /* assigning dma request: channel-0 with request line - 16 ( DCAN1IF3) */ /* Refer Datasheet DMA request Line connection Table */ dmaReqAssign(DMA_CH0,16); while(1) [ /* - Populate dma control packets structure */ /* Source Address = IF3 Data register * Destination = Receive Buffer in Sys RAM * Length = 1 ( i.e., 64bits = 8 * 8 Bytes) */ dmaConfigCtrlRxPacket((uint32)(&(canREG1->IF3DATx[0])), (uint32)(&RX_DATA1), 1); /* - setting dma control packets for transmit */ dmaSetCtrlPacket(DMA_CH0, g_dmaCTRLPKT); /* - setting the dma channel to trigger on h/w request */ dmaSetChEnable(DMA_CH0, DMA_HW); canEnableloopback(canREG1,Internal_Lbk); dmaEnable(); /* transmit on can1 */ canTransmit(canREG1, canMESSAGE_BOX1, TX_DATA1); /* Wait for the DMA interrupt ISR to set the Flag */ // while(DMA_Comp_Flag != 0x5555AAAA); /* Disable Loopback */ canDisableloopback(canREG1); /* Check the RX_DATA1 for the received message */ ] /* USER CODE END */ ] /* USER CODE BEGIN (4) */ void dmaConfigCtrlRxPacket(uint32 sadd,uint32 dadd,uint32 dsize) [ g_dmaCTRLPKT.SADD = sadd; /* source address */ g_dmaCTRLPKT.DADD = dadd; /* destination address */ g_dmaCTRLPKT.CHCTRL = 0; /* channel control */ g_dmaCTRLPKT.FRCNT = 1; /* frame count */ g_dmaCTRLPKT.ELCNT = dsize; /* element count */ g_dmaCTRLPKT.ELDOFFSET = 0; /* element destination offset */ g_dmaCTRLPKT.ELSOFFSET = 0; /* element source offset */ g_dmaCTRLPKT.FRDOFFSET = 0; /* frame destination offset */ g_dmaCTRLPKT.FRSOFFSET = 0; /* frame source offset */ g_dmaCTRLPKT.PORTASGN = 4; /* port b */ g_dmaCTRLPKT.RDSIZE = ACCESS_64_BIT; /* read size */ g_dmaCTRLPKT.WRSIZE = ACCESS_64_BIT; /* write size */ g_dmaCTRLPKT.TTYPE = FRAME_TRANSFER ; /* transfer type */ g_dmaCTRLPKT.ADDMODERD = ADDR_FIXED; /* address mode read */ g_dmaCTRLPKT.ADDMODEWR = ADDR_FIXED; /* address mode write */ g_dmaCTRLPKT.AUTOINIT = AUTOINIT_ON; /* autoinit */ ] void dmaGroupANotification(dmaInterrupt_t inttype, uint32 channel) [ DMA_Comp_Flag = 0x5555AAAA; ] 请问有什么问题?? |
|
|
|
Hi sam, 你这个程序看着很眼熟啊,应该是我们英文论坛里面一个关于软件触发DMA的实例改过来的吧。 我现在手头上没两块板子,暂时试不了。 要不你先这样吧,先试试没有中断的,简单的软件触发方式,看看DMA能不能工作,后面再去设置硬件触发的,以及想用的带DMA中断的应用。 这样比较容易排排查问题。 谢谢 BR, KEN |
|
|
|
lining870815844 发表于 2018-5-25 08:23 Hi Ken , 的确是从英文论坛里面修改过来的.. 现在CAN1发送数据, DMA能进入中断. 如果将Read and write 配置成64BIT: g_dmaCTRLPKT.RDSIZE = ACCESS_64_BIT; /* read size */ g_dmaCTRLPKT.WRSIZE = ACCESS_64_BIT; /* write size 调试时会出现如下错误: CortexR4: GEL Output: Memory Map Setup for Flash @ Address 0x0CortexR4: Trouble Reading Memory Block at 0x8001584 on Page 0 of Length 0x1: (Error -1170 @ 0x0) Unable to access the DAP. Reset the device, and retry the operation. If error persists, confirm configuration, power-cycle the board, and/or try more reliable JTAG settings (e.g. lower TCLK). (Emulation package 5.0.872.0) 而且RX_DATA1 什么数据都不能收到, 如果将Read and write 配置成32BIT: g_dmaCTRLPKT.RDSIZE = ACCESS_32_BIT; /* read size */ g_dmaCTRLPKT.WRSIZE = ACCESS_32_BIT; /* write size DAM进入中断,当时RX_DATA1只能收到前4byte 数据, 后4byte不能收到。 很疑惑啊,为什么?? |
|
|
|
Hi Ken, 能否给出答案? |
|
|
|
Hi sam, 因为我手上只有一块板子,所以我只能用loopback模式测试CAN接收的DMA功能,我这边测试都是没问题的,接收的数据都是8个字节。 关于DMA的配置如下: void dmaConfigCtrlRxPacket(uint32 sadd,uint32 dadd,uint32 dsize) [ g_dmaCTRLPKT.SADD = sadd; /* source address */ g_dmaCTRLPKT.DADD = dadd; /* destination address */ g_dmaCTRLPKT.CHCTRL = 0; /* channel control */ g_dmaCTRLPKT.FRCNT = 1; /* frame count */ g_dmaCTRLPKT.ELCNT = dsize; /* element count */ g_dmaCTRLPKT.ELDOFFSET = 0; /* element destination offset */ g_dmaCTRLPKT.ELSOFFSET = 0; /* element source offset */ g_dmaCTRLPKT.FRDOFFSET = 0; /* frame destination offset */ g_dmaCTRLPKT.FRSOFFSET = 0; /* frame source offset */ g_dmaCTRLPKT.PORTASGN = 4; /* port b */ g_dmaCTRLPKT.RDSIZE = ACCESS_64_BIT; /* read size */ g_dmaCTRLPKT.WRSIZE = ACCESS_64_BIT; /* write size */ g_dmaCTRLPKT.TTYPE = FRAME_TRANSFER ; /* transfer type */ g_dmaCTRLPKT.ADDMODERD = ADDR_FIXED; /* address mode read */ g_dmaCTRLPKT.ADDMODEWR = ADDR_FIXED; /* address mode write */ g_dmaCTRLPKT.AUTOINIT = AUTOINIT_OFF; /* autoinit */ ] 我觉得你需要把autoinit设为off,然后再测试一下接收情况。 谢谢 BR, KEN |
|
|
|
lining870815844 发表于 2018-5-25 08:47 Hi Ken, 我将设置成 g_dmaCTRLPKT.AUTOINIT = AUTOINIT_OFF; 也试过.. 因为购买RM48L952 开发板有两个CAN,(CAN1 和 CAN2), 是CAN2发送8个Byte , CAN1 DMA接收.. 如果将 g_dmaCTRLPKT.RDSIZE = ACCESS_64_BIT; /* read size */ g_dmaCTRLPKT.WRSIZE = ACCESS_64_BIT; /* write size 设置成这样DEBUG 模式下有时就会出现这样错误提示: CortexR4: GEL Output: Memory Map Setup for Flash @ Address 0x0CortexR4: Trouble Reading Memory Block at 0x8001584 on Page 0 of Length 0x1: (Error -1170 @ 0x0) Unable to access the DAP. Reset the device, and retry the operation. If error persists, confirm configuration, power-cycle the board, and/or try more reliable JTAG settings (e.g. lower TCLK). (Emulation package 5.0.872.0) |
|
|
|
60user25 发表于 2018-5-25 09:03 sam, 明白,我有空找个HDK板测试一下。 谢谢 BR, KEN |
|
|
|
Hi Ken, 希望你能快些回复结果。。 非常感谢。。 |
|
|
|
sam, 方便问一下你们公司具体是做什么产品的吗?汽车还是工业? BR, KEN |
|
|
|
Hi Ken, 公司具体产品是电梯。所以对CAN的要求比较高.. 谢谢! |
|
|
|
Hi Ken, 还有个问题就是, DMA中断只发生一次..很困惑.. |
|
|
|
sam, 我做了一个基于RM48L950 HDK板子的测试例程,里面用DCAN2定时发送三个不同ID的报文信息,然后DCAN1用DMA将IF3中更新的数据搬运到RAM里面。 整个过程中DMA工作正常,中断能一直进去的。你可以参考一下: 有任何问题,我们再交流。 谢谢 BR, KEN |
|
|
|
lining870815844 发表于 2018-5-25 10:29 sam, 另外关于DMA的读写位数,我设置的都是64bit的,编译过程中没有出现你说的报错信息,会不会是你的工程有什么问题呢。 谢谢 BR, KEN |
|
|
|
只有小组成员才能发言,加入小组>>
334 浏览 1 评论
528 浏览 2 评论
NA555DR VCC最低电压需要在5V供电,为什么用3.3V供电搭了个单稳态触发器也使用正常?
773 浏览 3 评论
MSP430F249TPMR出现高温存储后失效了的情况,怎么解决?
649 浏览 1 评论
对于多级放大电路板,在PCB布局中,电源摆放的位置应该注意什么?
1126 浏览 1 评论
AT32F407在USART2 DMA发送数据时,接包接到了要发送的数据,程序还是处于等待传输完成的标识判断中,为什么?
56浏览 29评论
126浏览 23评论
请问下tpa3220实际测试引脚功能和官方资料不符,哪位大佬可以帮忙解答下
251浏览 20评论
请教下关于TAS5825PEVM评估模块原理图中不太明白的地方,寻求答疑
200浏览 14评论
两个TMP117传感器一个可以正常读取温度值,一个读取的值一直是0,为什么?
56浏览 13评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-12-22 22:17 , Processed in 1.332526 second(s), Total 113, Slave 96 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号