专栏中心

EEPW首页 > 专栏 > stm32 使用printf +DMA增加3个打印缓冲

stm32 使用printf +DMA增加3个打印缓冲

发布人:mayer 时间:2009-08-11 来源:工程师 发布文章
stm32 使用printf +DMA增加3个打印缓冲

 

实现了使用3个打印缓冲组连续打印的功能,如果3个缓冲组全满了就在前一个组打印完成后打印:printf buffer is full!剩下的2个缓冲组继续打印。

初步实现了该功能,显示效果如下:

DMA1 transmission successful!successful,successful,successful
print buffer is full!

DMA2 transmission successful!successful,successful,successful

DMA3 transmission successful!successful,successful,successful


DMA1 transmission successful!successful,successful,successful
print buffer is full!

DMA2 transmission successful!successful,successful,successful

DMA3 transmission successful!successful,successful,successful


DMA1 transmission successful!successful,successful,successful
print buffer is full!

DMA2 transmission successful!successful,successful,successful

DMA3 transmission successful!successful,successful,successful


DMA1 transmission successful!successful,successful,successful
print buffer is full!

DMA2 transmission successful!successful,successful,successful

DMA3 transmission successful!successful,successful,successful

宏:

#define UART_BUFFLEN 256

#define PRINTFBUF_NUM 3

#define PRINTFULL ("print buffer is full!\r\n")


typedef enum
{
    BUFF_EMPTY = 0,
    BUFF_HAS_DATA,
    BUFF_FULL
}BUFF_FLAG;
typedef struct
{
    u16 sPriority;
    u16 sLength ;
    BUFF_FLAG iFullFlag;
    u8 ucBuffer[UART_BUFFLEN];
}ST_UARTBUFFER;

 

函数:

中断:

 


/*******************************************************************************
* Function Name  : DMA1_Channel4_IRQHandler
* Description    : This function handles DMA1 Channel 4 interrupt request.
* Input          : None
* Output         : None
* Return         : None
*******************************************************************************/
void DMA1_Channel4_IRQHandler(void)
{
    u8 ucIndex;
    ST_UARTBUFFER *pUart1SendBuffer;
    volatile ST_PRINTFBUFFER *pPrintfBuffer;

   
    if(DMA_GetITStatus(DMA1_IT_TC4))
    {
        DMA_ClearITPendingBit(DMA1_IT_TC4);
        pUart1SendBuffer = GetUART1SendBufferAddr();
        pPrintfBuffer = GetPrintfBufferAddr ();
        (pUart1SendBuffer + pPrintfBuffer->ucIndex)->iFullFlag = BUFF_EMPTY;
        if (pPrintfBuffer->iFullFlag == BUFF_FULL)
        {
            DMAUART1_Configuration(PRINTFULL,strlen(PRINTFULL));
           
            pPrintfBuffer->iFullFlag = BUFF_HAS_DATA;
        }
        else
        {
            for (ucIndex = 0 ; ucIndex < PRINTFBUF_NUM ;ucIndex++)
            {
                if ( (pUart1SendBuffer + ucIndex)->iFullFlag== BUFF_FULL)
                {
                    pPrintfBuffer->ucIndex = ucIndex;
                    DMAUART1_Configuration((pUart1SendBuffer + pPrintfBuffer->ucIndex)->ucBuffer,(pUart1SendBuffer + pPrintfBuffer->ucIndex)->sLength);

                    break;
                }
            }
            if (ucIndex == PRINTFBUF_NUM)
            {
                pPrintfBuffer->iFullFlag == BUFF_EMPTY;
            }
        }
       
       
       
       
    }
    if(DMA_GetITStatus(DMA1_IT_HT4))
    {
        DMA_ClearITPendingBit(DMA1_IT_HT4);

    }
    if(DMA_GetITStatus(DMA1_IT_TE4))
    {
        DMA_ClearITPendingBit(DMA1_IT_TE4);

    }
    if(DMA_GetITStatus(DMA1_IT_GL4))
    {
        DMA_ClearITPendingBit(DMA1_IT_GL4);

    }
}

 

每次打印的数据长度不能超过UART_BUFFLEN个
int printf(const char *format ,... )
{
    va_list arg;
    int rv;
    u8 ucIndex;
    static u8 ucCounter = 0;
   

    for (ucIndex = 0 ; ucIndex < PRINTFBUF_NUM ;ucIndex++)
    {
        if ( g_acUART1SendBuffer[ucIndex].iFullFlag == BUFF_EMPTY)
        {
            g_acUART1SendBuffer[ucIndex].iFullFlag = BUFF_FULL;
            va_start(arg, format);
            rv = vsprintf(g_acUART1SendBuffer[ucIndex].ucBuffer, format, arg);
            g_acUART1SendBuffer[ucIndex].sLength = rv;
            va_end(arg);
            break;
        }
        else
        {

        }
    }

    if (ucIndex == PRINTFBUF_NUM)
    {
        g_stPrintBuffer.iFullFlag = BUFF_FULL;
        ucCounter ++;
    }
    else
    {
        if (g_stPrintBuffer.iFullFlag != BUFF_FULL)
        {
            for (ucIndex = 0 ; ucIndex < PRINTFBUF_NUM ;ucIndex++)
            {
                if ( g_acUART1SendBuffer[ucIndex].iFullFlag == BUFF_FULL)
                {
                    g_stPrintBuffer.ucIndex = ucIndex;
                    break;
                }
            }
            if (ucIndex == PRINTFBUF_NUM)
            {
                g_stPrintBuffer.iFullFlag = BUFF_FULL;
            }
            else
            {
                DMAUART1_Configuration(g_acUART1SendBuffer[g_stPrintBuffer.ucIndex].ucBuffer,g_acUART1SendBuffer[g_stPrintBuffer.ucIndex].sLength);
                g_stPrintBuffer.iFullFlag = BUFF_HAS_DATA;
            }
           
        }
        else
        {

        }
    }
   
   
    return rv;
}


void DMAUART1_Configuration(u8 *uiSendBuf,u32 uiLength)
{
    DMA_InitTypeDef DMA_InitStructure;
    DMA_DeInit ((DMA_Channel_TypeDef*)DMA1_Channel4_BASE);
    DMA_InitStructure.DMA_PeripheralBaseAddr = 0x40013804;//&(USART1.DR);
    DMA_InitStructure.DMA_MemoryBaseAddr = (u32)uiSendBuf;
    DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralDST;
    DMA_InitStructure.DMA_BufferSize = uiLength;
    DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
    DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
    DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;
    DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;
    DMA_InitStructure.DMA_Mode = DMA_Mode_Normal;
    DMA_InitStructure.DMA_Priority = DMA_Priority_Medium;
    DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
    DMA_Init(DMA1_Channel4, &DMA_InitStructure);

     DMA_ITConfig(DMA1_Channel4, DMA_IT_TC, ENABLE);
     DMA_Cmd(DMA1_Channel4, ENABLE);
}
测试方法:

            printf("\r\nDMA1 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA2 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA3 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA4 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA5 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA6 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA7 transmission successful!successful,successful,successful\r\n");
            printf("\r\nDMA8 transmission successful!successful,successful,successful\r\n");
只有3个缓冲组,所以4,5,6,7,8均来不及打印,

专栏文章内容及配图由作者撰写发布,仅供工程师学习之用,如有侵权或者其他违规问题,请联系本站处理。 联系我们

关键词:

相关推荐

无线RF解决方案 - 结合 ZigBee, RF4CE, 智能能源及IP

视频 2010-01-14

现代地空导弹关键技术

视频 2010-01-14

ZLG500A 器件读卡模块简介

2026年广州国际智能制造技术与装备展览会,大湾区智能制造年度盛

2025-11-19

功率二极管与整流:从器件到半波整流电路的完整解析

EDA/PCB 2025-11-19

“智行万象 生态共生” 第三届英飞凌汽车创新峰会举行

无人机是用四旋翼好还是六旋翼好

了解低功耗蓝牙协议栈的架构

新型两栖船坞运输舰技术特点概述

视频 2010-01-14

U盘伴侣―EasyUDisk读写U盘模块

TDR时域反射技术:硬件工程师的“听诊器”

内阻很小的MOS管为什么会发热?

USBCAN接口卡数据手册V2.0

为什么越小的去耦电容越靠近电源管脚放置?

内卷红海突围!全志以 “性价比利刃” 斩获36.76%业绩增长,全志T536实力解码

网口为什么需要有一个变压器?

新世纪的攻击型核潜艇技术发展趋势

视频 2010-01-14

新一代舰艇隐身技术研制特点

视频 2010-01-14
更多 培训课堂
更多 焦点
更多 视频

技术专区