【电路笔记 TMS320C6***DSP】C6748EDMA 初始化函数 EDMA3Init(0x01C00000, 0);的实现细节

  • EDMA3主要包括EDMA3CC(通道控制器)和EDMA3TC(传输控制器),函数EDMA3Init();主要对EDMA3CC进行配置。

C6748的EDMA3 初始化:EDMA3Init(0x01C00000, 0);

  • EDMA3Init(0x01C00000, 0):配置EDMA3控制器的基本参数,如控制寄存器、通道使能等。
  • 如下如0x01C00000为EDMA3控制器的基地址,用于访问其内部寄存器
    在这里插入图片描述

EDMA3Init函数

// https://e2echina.ti.com/support/processors/f/processors-forum/185720/c6654-edma-ipr
/**
 * \file  edma.c
 *
 * \brief This file contains device abstraction layer APIs for the EDMA device.
 *        There are APIs here to enable the EDMA instance, set the required
 *        configurations for communication, transmit or receive data.
 */

/*  Copyright (C) 2011 Texas Instruments Incorporated - http://www.ti.com/
 *  ALL RIGHTS RESERVED. */


/* Driver APIs */
#include "edma.h"

#include "hw_types.h"
#include "hw_edma3cc.h"
#include <c6x.h>

/****************************************************************************/
/*                         GLOBAL VARIABLES                                 */
/****************************************************************************/
unsigned int regionId;

/****************************************************************************/
/*                     API FUNCTION DEFINITIONS                             */
/****************************************************************************/

/**
 *  \brief   EDMA3 Initialization
 *  
 *  This function initializes the EDMA3 Driver
 *  Clears the error specific registers (EMCR/EMCRh, QEMCR, CCERRCLR) &
 *  initialize the Queue Number Registers
 *
 *  \param  baseAdd                  Memory address of the EDMA instance used.\n
 *								     EDMA3控制器的基地址,用于访问其内部寄存器
 *
 *  \param  queNum                   Event Queue Number to which the channel
 *                                   will be mapped (valid only for the
 *                                   Master Channel (DMA/QDMA) request).\n
 *                                   事件队列编号,指定哪个队列将用于映射通道(仅对主通道有效)。
 *
 *  \return None
 *
 *  \note   The regionId is the shadow region(0 or 1) used and the,
 *          Event Queue used is either (0 or 1). There are only four shadow 
 *          regions and only two event Queues
 */
void EDMA3Init(unsigned int baseAdd,
           unsigned int queNum)
{
    unsigned int count = 0;
    unsigned int i = 0;
    
#ifdef _TMS320C6X
    /* For DSP, regionId is assigned here and used globally in the driver */
    regionId = (unsigned int)1u;
#else
    /* FOR ARM, regionId is assigned here and used globally in the driver   */
    regionId = (unsigned int)1u;
#endif

    /* Clear the Event miss Registers 清除了所有与错误相关的寄存器(如事件丢失寄存器和中央控制器错误寄存器),设置为值0xFFFFFFFFu*/
    HWREG(baseAdd + EDMA3CC_EMCR) = EDMA3_SET_ALL_BITS;// #define EDMA3CC_EMCR                 (0x308)
    HWREG(baseAdd + EDMA3CC_EMCRH) = EDMA3_SET_ALL_BITS;// #define EDMA3CC_EMCRH                (0x30C)

    HWREG(baseAdd + EDMA3CC_QEMCR) = EDMA3_SET_ALL_BITS;// #define EDMA3CC_QEMR                 (0x310)

    /* Clear CCERR register                                                 */
    HWREG(baseAdd + EDMA3CC_CCERRCLR) = EDMA3_SET_ALL_BITS;

    /* FOR TYPE EDMA*/ 
    /* Enable the DMA (0 - 64) channels in the DRAE and DRAEH register 
     其中 regionId = 1u;
       #define EDMA3CC_DRAE(n)              (0x340 + (n * 8))
       #define EDMA3CC_DRAEH(n)             (0x344 + (n * 8))
    */ 
    HWREG(baseAdd + EDMA3CC_DRAE(regionId)) = EDMA3_SET_ALL_BITS;
    HWREG(baseAdd + EDMA3CC_DRAEH(regionId)) = EDMA3_SET_ALL_BITS;


    /*AM335X版本特有配置*/
    if((EDMA_REVID_AM335X == EDMAVersionGet()))
    {           
         for(i = 0; i < 64; i++)
         {
              /* All events are one to one mapped with the channels */
              HWREG(baseAdd + EDMA3CC_DCHMAP(i)) = i << 5;
         }

    }
    /* Initialize the DMA Queue Number Registers 初始化DMA队列编号寄存器 
     #define EDMA3CC_DMAQNUM(n)           (0x240 + ((n) * 4))
    */
    for (count = 0;count < SOC_EDMA3_NUM_DMACH; count++)
    {   // 遍历所有DMA通道,设置它们对应的队列编号为queNum
         HWREG(baseAdd + EDMA3CC_DMAQNUM(count >> 3u)) &= 
                                                    EDMA3CC_DMAQNUM_CLR(count);
         HWREG(baseAdd + EDMA3CC_DMAQNUM(count >> 3u)) |= 
                                                    EDMA3CC_DMAQNUM_SET(count,queNum);
    }

    /* FOR TYPE QDMA */
    /* Enable the DMA (0 - 64) channels in the DRAE register  启用QDMA通道并初始化队列编号寄存器(仅适用于QDMA)*/
    HWREG(baseAdd + EDMA3CC_QRAE(regionId)) = EDMA3_SET_ALL_BITS;

    /* Initialize the QDMA Queue Number Registers                           */
    for (count = 0;count < SOC_EDMA3_NUM_QDMACH; count++)
    {
        HWREG(baseAdd + EDMA3CC_QDMAQNUM) &= EDMA3CC_QDMAQNUM_CLR(count);
        HWREG(baseAdd + EDMA3CC_QDMAQNUM) |= 
                       EDMA3CC_QDMAQNUM_SET(count,queNum);
    }
    /*
    * QDMA(Queue-based Direct Memory Access,基于队列的直接内存访问)是一种高级DMA(Direct Memory Access)技术,它扩展了传统DMA的功能,提供* 了更高的灵活性和效率。
    */
}
  • 以上代码中不同的注释部分设置了对应的寄存器值:

在这里插入图片描述

HWREG

//*****************************************************************************
//
// Macros for hardware access, both direct and via the bit-band region.
//
//*****************************************************************************
#define HWREG(x)                                                              \
        (*((volatile unsigned int *)(x)))

EDMA3CC_DMAQNUM 初始化DMA队列编号寄存器

#define EDMA3CC_DMAQNUM(n)           (0x240 + ((n) * 4))
#define SOC_EDMA3_NUM_DMACH                 32
#define SOC_EDMA3_NUM_QDMACH                8
# baseAdd  0x01C00000
for (count = 0;count < SOC_EDMA3_NUM_DMACH; count++)
{   // 遍历所有DMA通道,设置它们对应的队列编号为queNum
     HWREG(baseAdd + EDMA3CC_DMAQNUM(count >> 3u)) = ……
}
// count >> 3u:这个操作将 count 右移3位,相当于 count / 8。因为每个 DMAQNUM 寄存器管理8个通道。
  • 根据宏定义和代码片段,我们可以计算出每个 count 值对应的地址。
countcount >> 3uEDMA3CC_DMAQNUM(count >> 3u)address (hex)
000x2400x01C00240
100x2400x01C00240
200x2400x01C00240
300x2400x01C00240
400x2400x01C00240
500x2400x01C00240
600x2400x01C00240
700x2400x01C00240
810x2440x01C00244
910x2440x01C00244
1010x2440x01C00244
1110x2440x01C00244
1210x2440x01C00244
1310x2440x01C00244
1410x2440x01C00244
1510x2440x01C00244
1620x2480x01C00248
1720x2480x01C00248
1820x2480x01C00248
1920x2480x01C00248
2020x2480x01C00248
2120x2480x01C00248
2220x2480x01C00248
2320x2480x01C00248
2430x24C0x01C0024C
2530x24C0x01C0024C
2630x24C0x01C0024C
2730x24C0x01C0024C
2830x24C0x01C0024C
2930x24C0x01C0024C
3030x24C0x01C0024C
3130x24C0x01C0024C

在这里插入图片描述

EDMA3CC_QDMAQNUM_CLR

  • EDMA3CC_DMAQNUM_CLR(chNum) 宏定义提供了一种简便的方法来生成一个掩码,用于清除指定DMA通道的队列编号。通过这种方式,可以在不影响其他通道的情况下精确地修改单个通道的配置。
/** DMAQNUM bits Clear */
#define EDMA3CC_DMAQNUM_CLR(chNum)            ( ~ (0x7u << (((chNum) % 8u) \
                                                                      * 4u)))
  • EDMA3CC_DMAQNUM_SET进行类似的赋值处理:
/** DMAQNUM bits Set */
#define EDMA3CC_DMAQNUM_SET(chNum,queNum)     ((0x7u & (queNum)) << \
                                                       (((chNum) % 8u) * 4u))
  • QDMA的配置方式省略……
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值