This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] TMS320C6748:EDMA3

Guru**** 2539500 points


请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/processors-group/processors/f/processors-forum/824566/tms320c6748-edma3

器件型号:TMS320C6748

最后、我们将尝试 QDMA。  不起作用:(

我的计划如下:

使用 QDMA 通道0从16位 GPIO 端口读取16次、并将读数保存在一组16位字中。

在 POR 之后、我按如下方式对其进行设置:

//参数块

#define PARAM_START 0x01c04000
#define PARAM_SET_0 0x4000
#define param_set_1 (param_set_0 + 32)
#define param_set_2 (param_set_1 + 32)
#define RF_IN (SOC_GPIO_0_regs + 0x70)
#define NO_LINK 0xFFFF

#define QCHMAP0 0x01c00200
#define QER 0x01c01080
#define QEER 0x01c01084
#define QEECR 0x01c01088
#define QEESR 0x01c0108c

#define IER 0x01c01050
#define IECR 0x01c01058
#define IESR 0x01c01060
#define IPR 0x01c01068
#define ICR 0x01c01070
#define RFDMA_READY (HWREG (IPR)& 0x00000001)

struct __attribute__(__packed__) T_Param {
//在下方保留声明顺序!
uint32 op;
uint32 src;
uint16 acnt;
uint16位;
uint32 dst;
uint16 srcbidx;
uint16 dstbidx;
uint16链接;
uint16 bcntrld;
uint16 srccidx;
uint16 dstcidx;
uint16 ccnt;
uint16 rsvd;
};

int16 rf_readings[16];

#pragma LOCATION (DATA_PARARAM、PARAM_START)
struct __attribute__(__packed__) T_param data_param;
//====================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================

bool QDMA_DONE(){
返回(RFDMA_READY);

//====================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================

空 InitQDMA(){


int i;
对于(i=0;i<16;i++){
RF_readings[i]= 0;

//启用 QDMA 通道0
HWREG (QEESR)= 0x00000001;
//清除中断状态
HWREG (ICR)= 0x00000001;
//设置中断使能
HWREG (IESR)= 0x00000001;
//初始化参数集0
DATA_PARAM.src = RF_IN;
DATA_PARAM.acnt = 2;
DATA_PARAM.bcnt = 16;
DATA_PARAM.srcbidx = 0;
data_param.dstbidx = 2;
DATA_PARAM.bcntrld = 0;
DATA_PARAM.srccidx = 0;
DATA_PARAM.dstcidx = 0;
DATA_PARAM.ccnt = 1;
DATA_PARAM.DST =(uint32)&Rf_readings;
data_param.link = no_link;
//触发字;必须是函数中的最后一条赋值语句
DATA_PARAM.OPT = 0x00100008;//TCINTEN = 1、STATIC = 1
然后、在 while (1)循环中、我调用 QDMA_DONE()以检查 IPR 的位0。  如果该位置位、我将处理数据。  然后,调用 InitQDMA()来重复该过程。  它似乎不起作用-未观察到数据传输。  什么似乎缺失或不正确?
  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    我想您从固定地址(GPIO 端口)读取数据、然后将数据移动到具有增量目标地址的缓冲区中。 在最简单的情况下、只需读取一次 GPIO 16位、因此 ACNT=2、BCNT=1、这是否适合您? 也就是说、您是否会看到 IPR 位设置? 您的 QDMA 触发字是什么? 如果没有发生任何情况、您是否看到 EDMA 传输的任何错误? 例如在 ERRSTAT 寄存器中?

    在读取的16次中、我认为您需要在 opt 字段中使用 SAM=0、DAM=1。

    此致、Eric

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    很高兴有人最后回复!!  谢谢!!

    出于学习目的、我简化了代码、使其成为8字节数组的 memcpy。  当我运行它时,它会导致错误。  ERRSTAT 和 ERRDET。  可能会发生什么情况?

    ERRSTAT 0x00000001错误状态[内存映射]
    _RESV_1 保留
    MMRAERR 0 -无 MMR 地址错误事件
    TRERR 0 -无 TR 错误事件
    _RESV_4 *保留
    BUSERR 1 -错误总线错误事件
    ERREN 0x00000000错误使能[存储器映射]
    ERRCLR 0x00000000错误清除寄存器[存储器映射]
    ERRDET 0x00010001错误详细信息[存储器映射]
    _RESV_1******** 保留
    TCCHEN 0传输完成链使能
    TCINTEN 1传输完成中断使能
    _RESV_4**保留
    TCC 000000传输完成代码
    _RESV_6****保留
    STAT 0001 - READ_ADDRESS 转换状态
    ERRCMD 0x00000000错误命令[存储器映射]

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    以下是新的代码片段:

    bool QDMA_DONE(){
    uint32 x = RFDMA_READY;
    bool TB =(x!= 0)? true:false;
    退还(TB);

    //====================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================================

    空 InitQDMA(){

    //清除中断状态
    HWREG (ICR)= 0x00000001;

    int i;
    对于(i=0;i<8;i++){
    dstdata[i]= 0;

    //初始化参数集0
    HWREG (QCHMAP0)= 0x0000000c;
    HWREG (QEESR)= 0x00000001;
    DATA_PARAM.src =(uint32) srcdata;
    DATA_PARAM.acnt = 1;
    DATA_PARAM.bcnt = 8;
    DATA_PARAM.srcbidx = 1;
    data_param.dstbidx = 1;
    DATA_PARAM.bcntrld = 1;
    DATA_PARAM.srccidx = 0;
    DATA_PARAM.dstcidx = 0;
    DATA_PARAM.ccnt = 1;
    DATA_PARAM.OPT = 0x0010000c;//TCINTEN = 1、静态= 1、SYNCDIM=1
    data_param.link = no_link;
    //触发字;必须是函数中的最后一条赋值语句
    //设置中断使能
    //启用 QDMA 通道0
    HWREG (IESR)= 0x00000001;
    DATA_PARAM.DST =(uint32) dstdata;

    /* int i;
    对于(i=0;i<16;i++){
    RF_readings[i]= 0;

    //清除中断状态
    HWREG (ICR)= 0x00000001;
    //启用 QDMA 通道0
    HWREG (QEESR)= 0x00000001;
    //初始化参数集0
    DATA_PARAM.src = RF_IN;
    DATA_PARAM.acnt = 2;
    DATA_PARAM.bcnt = 16;
    DATA_PARAM.srcbidx = 0;
    data_param.dstbidx = 2;
    DATA_PARAM.bcntrld = 0;
    DATA_PARAM.srccidx = 0;
    DATA_PARAM.dstcidx = 0;
    DATA_PARAM.ccnt = 1;
    DATA_PARAM.DST =(uint32)&Rf_readings;
    data_param.link = no_link;
    //触发字;必须是函数中的最后一条赋值语句
    //设置中断使能
    HWREG (IESR)= 0x00000001;
    DATA_PARAM.OPT = 0x00100008;//TCINTEN = 1、STATIC = 1
    *

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    取得了一些进展。  参数中源和目标的地址调整使其工作。  我从其他 e2e 文章中发现、L2 RAM 的寻址方式与 EDMA3不同。

    进入 GPIO 到 L2 RAM 中的16个样本存储... 如果我只尝试一个采样-也就是说、将一个16位 GPIO 读取传输到一个16位存储器位置、它就会起作用。  但是、一到16方案不起作用。  基本而言、我正在等待 IPR 中的中断位永久置位。  参数是

    DATA_PARAM.acnt = 2;
    DATA_PARAM.bcnt = 16;
    DATA_PARAM.srcbidx = 0;
    data_param.dstbidx = 2;
    DATA_PARAM.bcntrld = 0;
    DATA_PARAM.srccidx = 0;
    DATA_PARAM.dstcidx = 0;
    DATA_PARAM.ccnt = 1;

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    很高兴你取得了进步--把一个16位 GPIO 读数转移到一个16位内存位置,它工作正常。 对于"但一到16方案不起作用。"、即您读取 FIFO 16次、每次都将读取保存到不同的位置。 如果 data_param.dstbidx = 4有用、您可以尝试。 此外、在 OPT 字段中、位设置为 :中间传输完成中断使能和 传输完成中断使能、 以及传输同步维度。 尝试查看是否仅使用 A-SYNC 并同时启用中间中断和传输完成中断、您可以达到多远。 您是否在缓冲区中看到了 GPIO 数据? 以及接收到多少个缓冲器数据?

    此外、我不确定您需要连续读取16个 QDMA 的原因。 DMA 读取速度如此之快、GPIO 可能未填充新数据。 因此、您可能将16个相同的 GPIO 数据放入16个不同的目的缓冲区中。 为什么不是每次只将一个16位 GPIO 读取到存储器中、那么应用需要知道下一个 GPIO 数据何时进入并安排另一个 QDMA 读取。

    此致、Eric   

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    在为 AB 同步设置它之后、它最终会起作用。

    问题:

    如果轮询代码很慢、无法及时响应活动 IPR 位、假设 QDMA 使用链接、则可能会错过中断。 我的问题是错过的中断不可恢复?  IPR 位被覆盖、前一位未被保留?  

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好!

    我尝试了 IPR 未被清除的情况(通过写入 ICR)、但另一个 DMA 传输来自同一 DMA 通道。 我发现第二次传输仍然发生、IPR 位被覆盖、并且错过了前一个中断、无法恢复。

    此致、Eric  

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    谢谢。  好消息。

    我肯定会详细了解 EDMA3。  仍然不清楚为什么同步不起作用、但 AB 同步会起作用。

    再次感谢后续行动。

    Peter