#include <MyProject.h>

/**
    @function     Conf_DMA
    @brief        DMA配置
    @param[in]    DMAx: DMA通道
**           DMAPipe: DMA管道，可选参数如下
                    UART1_XDATA    UART1-->XDATA
                    XDATA_UART1    UART1<--XDATA
                    I2C_XDATA      I2C  -->XDATA
                    XDATA_I2C      I2C  <--XDATA
                    SPI_XDATA      SPI  -->XDATA
                    XDATA_SPI      SPI  <--XDATA
                    UART2_XDATA    UART2-->XDATA
                    XDATA_UART2    UART2<--XDATA
**           DMAAddr: 传输首地址，可取地址范围：0x0000~0x0317
**           DMALen: DMALen    数据包大小(1~64)
    @return       None
    @date         2025-11-05
*/
void Conf_DMA(uint8_t DMAx, uint8_t DMAPipe, uint16_t DMAAddr, uint8_t DMALen)
{
    // 等待DMAx传输结束
    Wait_DMA(DMAx);
    // 禁止DMAx的传输
    ClrBit(*(&DMA0_CR0 + DMAx), DMAEN);
    // 设置DMAx的传输管道
    SetReg(*(&DMA0_CR0 + DMAx), DMA_PIPE, DMAPipe);
    // 设置DMAx传输数量
    *(&DMA0_LEN + DMAx) = DMALen - 1;
    // 设置DMAx传输首地址
    *(&DMA0_BA + DMAx) = DMAAddr & 0x07ff;
}

/**
    @function     Set_DMA_Pipe
    @brief        配置DMA传输通道

    @param[in]    DMAx: [输入/出]
**           DMAPipe: [输入/出]
    @date         2025-11-05
*/
void Set_DMA_Pipe(uint8_t DMAx, uint8_t DMAPipe)
{
    bool bTmp = false;
    
    if (ReadBit(*(&DMA0_CR0 + DMAx), DMAEN))
    {
        bTmp = true;
        
        while (ReadBit(*(&DMA0_CR0 + DMAx), DMABSY));
        
        ClrBit(*(&DMA0_CR0 + DMAx), DMAEN);
    }
    
    SetReg(*(&DMA0_CR0 + DMAx), DMACFG2 | DMACFG1 | DMACFG0, DMAPipe);
    
    if (bTmp)
    { SetBit(*(&DMA0_CR0 + DMAx), DMAEN); }
}

/**
    @function     Set_DMA_Data_Package
    @brief        配置DMA传输数据
    @param[in]    DMAx: [输入/出]
**           ulAddr: [输入/出]
**           cLen: [输入/出]
    @date         2025-11-05
*/
void Set_DMA_Data_Package(uint8_t DMAx, uint16_t ulAddr, uint8_t cLen)
{
    bool bTmp = false;
    
    if (ReadBit(*(&DMA0_CR0 + DMAx), DMAEN))
    {
        bTmp = true;
        
        while (ReadBit(*(&DMA0_CR0 + DMAx), DMABSY));
        
        ClrBit(*(&DMA0_CR0 + DMAx), DMAEN);
    }
    
    *(&DMA0_LEN + DMAx) =  cLen - 1;
    *(&DMA0_BA + 2 * DMAx)  =  ulAddr;
    
    if (bTmp)
    { SetBit(*(&DMA0_CR0 + DMAx), DMAEN); }
}


/**
    @function     Start_DMA
    @brief        启动DMA传输
    @param[in]    DMAx: [输入/出]
    @date         2025-11-05
*/
void Start_DMA(uint8_t DMAx)
{
    SetBit(*(&DMA0_CR0 + DMAx), DMAEN | DMABSY);
}

/**
    @function     Get_DMA_Status
    @brief        获取DMA状态
    @param[in]    DMAx: [输入/出]
**           DMAStatus: [输入/出]
    @return       状态
    @date         2025-11-05
*/
bool Get_DMA_Status(uint8_t DMAx, uint8_t DMAStatus)
{
    return ReadBit(*(&DMA0_CR0 + DMAx), DMAStatus);
}

/**
    @function     Set_IRQ_DMA
    @brief        使能中断 配置中断优先级
    @param[in]    DMA_IRQ: [输入/出]
    @date         2025-11-05
*/
void Set_IRQ_DMA(uint8_t DMA_IRQ_Priority)
{
    // 使能DMA中断
    SetBit(DMA0_CR0, DMAIE);
    
    if (!EA)
    {
        EA = 1;
    }
    
    // 配置中断优先级
    SetReg(IP1, PDMA1 | PDMA0, DMA_IRQ_Priority);
}





