打印
[STM32F1]

串口波特率的奇怪现象!(找到原因了)

[复制链接]
4371|10
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
yzzly|  楼主 | 2015-3-20 11:21 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 yzzly 于 2015-3-21 13:33 编辑

103VET6芯片,产品已经生产快1年了,默认9600波特的速率也完全测试过,系统时钟为72M(通过MCO看到),当波特率设置较低(如2400和4800)基本正确,当设置9600及以上时实际输出就不对了(虽然MDK能够看到波特率为要设置的值),头大了!

1.JPG (74.3 KB )

1.JPG

2.JPG (51.71 KB )

2.JPG

3.JPG (52.27 KB )

3.JPG

4.JPG (52.39 KB )

4.JPG
沙发
lvyunhua| | 2015-3-20 11:27 | 只看该作者
应该不至于出现这种情况吧。电路有没有问题呢

使用特权

评论回复
板凳
mmuuss586| | 2015-3-20 12:17 | 只看该作者

程序哪里有问题吧;我用内部晶振,115200波特率都OK;

使用特权

评论回复
地板
yzzly|  楼主 | 2015-3-20 17:22 | 只看该作者
要崩溃了!

使用特权

评论回复
5
mmuuss586| | 2015-3-20 19:45 | 只看该作者
#define                BaudRate        115200
void Uart2_Init(void)
{       
        GPIO_InitTypeDef GPIO_InitStructure;
        USART_InitTypeDef USART_InitStructure;
//----开启Usart1和GPIOA的Rcc时钟,       
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
        RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2, ENABLE);        //开启USART1的Clk,
        RCC_APB1PeriphResetCmd(RCC_APB1Periph_USART2,ENABLE);                //通过对应位设置使Usart1寄存器复位,
        RCC_APB1PeriphResetCmd(RCC_APB1Periph_USART2,DISABLE);        //退出复位,  
//初始化串口1,引脚Pa9,
        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_10MHz;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
  GPIO_Init(GPIOA, &GPIO_InitStructure);
//初始化串口1,引脚Pa10       
        GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_10MHz;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
  GPIO_Init(GPIOA, &GPIO_InitStructure);
//初始化串口1,
        USART_InitStructure.USART_BaudRate = BaudRate;                                        //波特率设置
        USART_InitStructure.USART_WordLength = USART_WordLength_8b;                //字长8bit,
        USART_InitStructure.USART_StopBits = USART_StopBits_1;                                //停止位1,
        USART_InitStructure.USART_Parity = USART_Parity_No;                                        //奇偶校验无,CR1的PCE和PS位,
        USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;                //流控制无,
        USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;                        //收发都使能,
        USART_Init(USART2, &USART_InitStructure);
//使能串口1,
        USART_ITConfig(USART2, USART_IT_RXNE, ENABLE);
        USART_Cmd(USART2, ENABLE);
}

使用特权

评论回复
6
mmuuss586| | 2015-3-20 19:46 | 只看该作者
我的串口初始化程序,仅供参考;

使用特权

评论回复
7
yzzly|  楼主 | 2015-3-21 13:34 | 只看该作者
找到原因了,在完善程序的过程中CPU初始化顺序被本人调整过,奶奶的!

使用特权

评论回复
8
yzzly|  楼主 | 2015-3-21 14:16 | 只看该作者
本帖最后由 yzzly 于 2015-3-21 14:18 编辑

真不明白,这3条语句的顺序怎么影响串口的波特率?
ADC_Configuration();
        TIMx_Configuration();
        DMA_Configuration();



使用特权

评论回复
9
yzzly|  楼主 | 2015-3-23 10:33 | 只看该作者
如果把DMA_Configuration()放在前面发现不但是串口波特率不对,systick的定时周期都增加了近10%,谁给解释是为什么呢?void ConfigDMA1C2(void)                                                                                                                                //
{
        DMA_InitTypeDef                DMA_InitStructure;
        NVIC_InitTypeDef        NVIC_InitStructure;

        RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1,ENABLE);                                                                //ʹÄÜDMA1ʱÖÓ
        DMA_DeInit(DMA1_Channel2);
        if(DMA1_TCIE_C2)
        {
                NVIC_InitStructure.NVIC_IRQChannel = DMA1_Channel2_IRQChannel;
                NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
                NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;
                NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
                NVIC_Init(&NVIC_InitStructure);
        }
        DMA_InitStructure.DMA_PeripheralBaseAddr = (u32)&ADC12_Buf+AdcPrNum*AdcChNum/2*4;                                //Ä¿µÄ»º³åÇø
        DMA_InitStructure.DMA_MemoryBaseAddr = (u32)&ADC1_Buf;                                                //Ô´»º³åÇø
        DMA_InitStructure.DMA_BufferSize = AdcPrNum*AdcChNum/2;                                                        //´«ÊäÊýÁ¿

        DMA_InitStructure.DMA_M2M = DMA1_MTOM_C2;                                                                                //´æ´¢Æ÷µ½´æ´¢Æ÷ģʽ
        DMA_InitStructure.DMA_Priority = DMA1_PL_C2;                                                                        //DMA1ͨµÀÓÅÏȼ¶
        DMA_InitStructure.DMA_MemoryDataSize = DMA1_MSIZE_C2;                                                        //´æ´¢Æ÷Êý¾Ý¿í¶È(Byte¡¢HarfWord¡¢Word)
        DMA_InitStructure.DMA_PeripheralDataSize = DMA1_PSIZE_C2;                                                //ÍâÉèÊý¾Ý¿í¶È(Byte¡¢HarfWord¡¢Word)
        DMA_InitStructure.DMA_MemoryInc = DMA1_MINC_C2;                                                                        //´æ´¢Æ÷µØÖ·ÔöÁ¿Ä£Ê½
        DMA_InitStructure.DMA_PeripheralInc = DMA1_PINC_C2;                                                                //ÍâÉèµØÖ·ÔöÁ¿Ä£Ê½
        DMA_InitStructure.DMA_Mode = DMA1_CIRC_C2;                                                                                //DMA1Ñ­»·Ä£Ê½
        DMA_InitStructure.DMA_DIR = DMA1_DIR_C2;                                                                                //Êý¾Ý´«Êä·½Ïò       
       
        DMA_Init(DMA1_Channel2, &DMA_InitStructure);

        DMA_ITConfig(DMA1_Channel2, DMA_IT_TC , ENABLE);                                                                //ʹÄÜDMA1ͨµÀ2´«ÊäÍê³ÉÖжÏ

        DMA_Cmd(DMA1_Channel2, ENABLE);                                                                                                        //ʹÄÜDMA1ͨµÀ2
}

void ConfigDMA2C1(void)
{
                DMA_InitTypeDef                DMA_InitStructure;
                NVIC_InitTypeDef        NVIC_InitStructure;

                RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA2,ENABLE);                                                                //ʹÄÜDMA2ʱÖÓ
                DMA_DeInit(DMA2_Channel1);
                if(DMA2_TCIE_C1)
                {
                        NVIC_InitStructure.NVIC_IRQChannel = DMA2_Channel1_IRQChannel;
                        NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
                        NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2;
                        NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
                        NVIC_Init(&NVIC_InitStructure);
                }
                DMA_InitStructure.DMA_PeripheralBaseAddr = (u32)&ADC12_Buf;                                //Ä¿µÄ»º³åÇø
                DMA_InitStructure.DMA_MemoryBaseAddr = (u32)&ADC12_Buf+AdcPrNum*AdcChNum/2*4;                                                //Ô´»º³åÇø
                DMA_InitStructure.DMA_BufferSize = AdcPrNum*AdcChNum/2;                                                        //´«ÊäÊýÁ¿

                DMA_InitStructure.DMA_M2M = DMA2_MTOM_C1;                                                                                //´æ´¢Æ÷µ½´æ´¢Æ÷ģʽ
                DMA_InitStructure.DMA_Priority = DMA2_PL_C1;                                                                        //DMA2ͨµÀÓÅÏȼ¶
                DMA_InitStructure.DMA_MemoryDataSize = DMA2_MSIZE_C1;                                                        //´æ´¢Æ÷Êý¾Ý¿í¶È(Byte¡¢HarfWord¡¢Word)
                DMA_InitStructure.DMA_PeripheralDataSize = DMA2_PSIZE_C1;                                                //ÍâÉèÊý¾Ý¿í¶È(Byte¡¢HarfWord¡¢Word)
                DMA_InitStructure.DMA_MemoryInc = DMA2_MINC_C1;                                                                        //´æ´¢Æ÷µØÖ·ÔöÁ¿Ä£Ê½
                DMA_InitStructure.DMA_PeripheralInc = DMA2_PINC_C1;                                                                //ÍâÉèµØÖ·ÔöÁ¿Ä£Ê½
                DMA_InitStructure.DMA_Mode = DMA2_CIRC_C1;                                                                                //DMA2Ñ­»·Ä£Ê½
                DMA_InitStructure.DMA_DIR = DMA2_DIR_C1;                                                                                //Êý¾Ý´«Êä·½Ïò       
               
                DMA_Init(DMA2_Channel1, &DMA_InitStructure);

                DMA_ITConfig(DMA2_Channel1, DMA_IT_TC , ENABLE);                                                                //ʹÄÜDMA2ͨµÀ1´«ÊäÍê³ÉÖжÏ

                DMA_Cmd(DMA2_Channel1, ENABLE);                                                                                                        //ʹÄÜDMA2ͨµÀ1
}

使用特权

评论回复
10
chenyu988| | 2015-3-23 10:38 | 只看该作者
把DMA的中断优先级改低试试

使用特权

评论回复
11
yzzly|  楼主 | 2015-3-23 10:48 | 只看该作者
本系统是定时器定时启动ADC转换,ADC1及ADC2各有5个输入通道。每周期(20毫秒)每个通道转换32次,ADC1每次转换结束DMA1的C1读走,DMA1的C1与C2每10毫秒中断一次。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

428

主题

1183

帖子

3

粉丝