您的位置: OpenADSP社区论坛 -> Blackfin专区 -> 新手上路 -> 新手,求教BF531传输I2S的SPORT和DMA设置参数... 
本帖共有4994个阅读者
发表帖子 发表投票 回复主题
新手,求教BF531传输I2S的SPORT和DMA设置参数问题
bd7bq(论坛新手)
bd7bq
头衔:社区公民
帮派:无帮无派
帖数:25
金钱:329
积分:27
注册时间:2013/7/8
楼主信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
新手,求教BF531传输I2S的SPORT和DMA设置参数问题

用BF531的SPORT0连CS5361.采用的是I2S模式,CS5361是立体声24位的编码器,那么BF531的接收缓冲是不是应该定义为:
unsigned int iRxBuffer[4];]
左右声道为:unsigned long int RightIn,LeftIn;

DMA的设置为:
void Init_DMA(void)
{
    *pDMA1_PERIPHERAL_MAP = 0x1000;                    // Set up DMA1 to receive,Map DMA1 to Sport0 RX    
    *pDMA1_CONFIG = WNR | WDSIZE_32 | DI_EN | FLOW_1;  // 32-bit transfers, Interrupt on completion, Autobuffer mode    
    *pDMA1_START_ADDR = (void *)iRxBuffer;             // Start address of data buffer    
    *pDMA1_X_COUNT = 4;                                // 循环计数器的长度    
    *pDMA1_X_MODIFY = 2;                               // 内部循环地址增量    
}

SPORT0的设置:
void Init_SPORT0(void)
{  
    *pSPORT0_TCLKDIV = 3;                        //配置SPORT 传输接口的时钟频率
    *pSPORT0_TFSDIV = 63;                       //配置SPORT 传输接口的同步频率
    *pSPORT0_RCR1 = RFSR | RCKFE;        
    *pSPORT0_RCR2 = SLEN_24 | RSFSE;              
}

DMA传输中断:
EX_INTERRUPT_HANDLER(Sport0_RX_ISR) //传输DMA 中断函数
{
    *pDMA1_IRQ_STATUS = 0x0001; //清除中断标志位
    // copy input data from dma input buffer into variables    
    LeftIn = iRxBuffer[0]<<16 + iRxBuffer[1];    
    RightIn = iRxBuffer[2]<<16 + iRxBuffer[3];
    // call function that contains user code
}

请大家帮忙看看理解有无问题:
(1) DMA的缓冲区如果定义为unsigned long int iRxBuffer[2],是不是对应的
*pDMA1_X_COUNT = 2;                                // 循环计数器的长度    
*pDMA1_X_MODIFY = 1;                               // 内部循环地址增量  
(2) *pSPORT0_RCR2 中的 SLEN_24或SLEN_32对程序会有什么影响吗?CS5361是24bit的,24位后的数据都是0,传输32位也没有什么影响吧?



「该帖子被 bd7bq 在 2013-08-10 12:05:45 编辑过」

这家伙很懒,什么也没有留下!
等级:论坛新手 参考IP地址:*.*.*.*
2013/8/10 9:35:56
尊贵身份标志
andy(论坛版主)
andy
头衔:社区公民
帮派:无帮无派
帖数:2287
金钱:11132
积分:2263
注册时间:2011/6/8
1信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
*pDMA1_X_MODIFY = 2;
DMA用32位时,若连续采集数据,X_MODIFY 应该为4


unsigned int iRxBuffer[4];
    LeftIn = iRxBuffer[0]<<16 + iRxBuffer[1];    
    RightIn = iRxBuffer[2]<<16 + iRxBuffer[3];
你的数组是int 型,在Blackfin中,int是32位,所以数据不需要再组合移位拼接。

1. DMA的MODIFY与你DMA采集宽度有关,通常8位为1,16位为2,32位为4
2. 通常使用与音频CODEC匹配的数据,如数据不匹配,可能会造成下一组数据拼接在上一组数据的后8位上。具体看CODEC是不是严格按照同步信号开始传输数据



这家伙很懒,什么也没有留下!
等级:论坛版主 参考IP地址:*.*.*.*
2013/8/12 8:57:29
liuhai2200(论坛新手)
liuhai2200
头衔:社区公民
帮派:无帮无派
帖数:69
金钱:636
积分:84
注册时间:2012/8/12
2信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
andy你好,
  现在遇到一个问题:将SPORT口配置成I2S,与AD7980(16位)连接,SPORT接收的数据长度是16位,两个声道就是32位,所以设DMA的宽度为WDSIZE_32,这样每个I2S周期(即采样周期)就得到32位数据,这样理解是否正确?还是像I2S它是每个声道单独传的?
示波器看AD7980的SDO数据是对的(AD7980的时序是没问题的),但是DMA得到的数是错的,而且错的没有任何规律。


「该帖子被 liuhai2200 在 2014-02-27 19:22:27 编辑过」

完成梦想
等级:论坛新手 参考IP地址:*.*.*.*
2014/2/27 9:46:47
尊贵身份标志
OpenADSP(管理员)
OpenADSP
头衔:社区公民
帮派:无帮无派
帖数:5187
金钱:34761
积分:6369
注册时间:2011/6/7
3信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
插播:OpenADSP开源社区长期现货出售BF531/BF532/BF533芯片,开发板,专用仿真器,官方淘宝店:http://dsp-tools.taobao.com/ OP的联系QQ:5516164.

你们继续!

我是OP...
等级:管理员 参考IP地址:*.*.*.*
2014/2/27 10:24:50
liuhai2200(论坛新手)
liuhai2200
头衔:社区公民
帮派:无帮无派
帖数:69
金钱:636
积分:84
注册时间:2012/8/12
4信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
补充一下:
  将SPORT配置成正常的DSP模式进行采样,采样率能到100多k,数据都正常,但是采样率确实不高。

完成梦想
等级:论坛新手 参考IP地址:*.*.*.*
2014/2/27 10:49:35
尊贵身份标志
andy(论坛版主)
andy
头衔:社区公民
帮派:无帮无派
帖数:2287
金钱:11132
积分:2263
注册时间:2011/6/8
5信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
I2S模式下,左右声道的数据是单独传输的,即一个左声道,一个右声道,DMA是搬运数据用的,SPORT DMA的FIFO是32位,所以DMA最多能一次搬运32位数据,如果你的DMA使用32位,DMA会等待左右声道数据都采集完成后搬运一次,你看看SPORT或者DMA的控制寄存器中有没有打包解包相关的使能位,如果有的话需要配置为使能。
数据错误可能是哪里的时序没有配置好,你先查看SPORT的时钟和同步信号,这些信号最好由
AD7980 来提供,因为SPORT接口输出会有误差。
采样率可以由
AD7980 输出,提高AD7980输出的速度,SPORT接口设置为外部的时钟和同步信号模式。




这家伙很懒,什么也没有留下!
等级:论坛版主 参考IP地址:*.*.*.*
2014/2/27 23:49:35
liuhai2200(论坛新手)
liuhai2200
头衔:社区公民
帮派:无帮无派
帖数:69
金钱:636
积分:84
注册时间:2012/8/12
6信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
好的,谢谢andy,但是AD7980应该不能主动提供时钟和帧同步信号吧。
示波器看数据应该是没有问题。
现在我不用DMA,仅使用sport中断,但是SPORT_RX寄存器,里面的值都是0,难道这就是SPORT_RX的FIFO内容吗?
通过看ISR0寄存器,提示SPORT1有错误,这个怎么定位错误原因。
谢谢了。


「该帖子被 liuhai2200 在 2014-02-28 11:50:37 编辑过」

完成梦想
等级:论坛新手 参考IP地址:*.*.*.*
2014/2/28 11:15:16
liuhai2200(论坛新手)
liuhai2200
头衔:社区公民
帮派:无帮无派
帖数:69
金钱:636
积分:84
注册时间:2012/8/12
7信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
另外,问一下,在中断服务函数中是否需要对SPORT1的寄存器进行什么操作?
还有怎么读SPORTRx的FIFO内容呢?
谢谢!
关于ISR0中SPORT1有错误,如果中断完关闭SPORT1的接收,就没有错误了。

完成梦想
等级:论坛新手 参考IP地址:*.*.*.*
2014/2/28 15:20:30
尊贵身份标志
andy(论坛版主)
andy
头衔:社区公民
帮派:无帮无派
帖数:2287
金钱:11132
积分:2263
注册时间:2011/6/8
8信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
你看看芯片数据手册,是否能自动产生时钟,通常音频芯片都会自动产生同步和时钟信号,
SPORT_RX寄存器就是FIFO,你看到的数据就是接收到的数据。你先检查一下硬件上是否有错,我们网站上有个音频环路测试的代码,即采集音频数据,然后实时播放出来,那个代码试用各种音频模块,你只需要把音频芯片的初始化设置好,允许line In输入和耳机输出,采样率任意,代码是以任意采样率采集,然后再以同样采样率播放,你看看用这个代码测试会不会有声音,如果有,再改为你需要的采样率。如果你有我们开发板的代码,可以使用PCM播放和MP3播放来测试音频芯片的输出,通常输出正常,输入部分只需要检查看信号有没有送入到接口,其他的就是找软件问题了

这家伙很懒,什么也没有留下!
等级:论坛版主 参考IP地址:*.*.*.*
2014/3/4 10:01:05
spenser(论坛新手)
spenser
头衔:社区公民
帮派:无帮无派
帖数:3
金钱:122
积分:4
注册时间:2015/7/13
9信息 | 留言 | Email | 主页 | 编辑 | 管理 | 离线
各位,我比你们晚了很久,现在才在学习ADSP,遇到了音频方面的问题,能够进入中断,但是数据SPORT_RX寄存器的值全部为零,希望楼上解决了的给个思路或者解决方案!

这家伙很懒,什么也没有留下!
等级:论坛新手 参考IP地址:*.*.*.*
2015/7/13 16:40:39
11
1
1/2
Powered by OpenADSP Copyright © 2010 www.Openadsp.com. All rights reserved.153990 Call, 1 Queries, Processed in 0.046875 second(s),