OpenEdv-开源电子网

 找回密码
 立即注册
正点原子全套STM32/Linux/FPGA开发资料,上千讲STM32视频教程免费下载...
查看: 4061|回复: 3

UCOS+STemWIN 加入两个串口任务,任务无法正常调度,求解答!!

[复制链接]

5

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
127
金钱
127
注册时间
2016-1-21
在线时间
17 小时
发表于 2016-3-22 17:20:01 | 显示全部楼层 |阅读模式
20金钱
       最近在做ZigBee+GPRS与STM32网关通信实验,用的是战舰V3开发板。要实现的功能是:串口1与GPRS串口通信(GPRS暂时用PC模拟收发数据),接收PC端的命令并通过串口3发送给ZigBee协调器;串口3与ZigBee串口通信,接收ZigBee汇集的数据包并通过串口1发送给PC(GPRS)。      两个串口的中断函数照搬的SIM900A GPRS通信实验的例程,串口1的中断函数如下:
      [mw_shl_code=c,true]void USART1_IRQHandler(void)
{
        u8 res;       
        OSIntEnter();      //进入OS中断       
        if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)//接收到数据
        {         
                res =USART_ReceiveData(USART1);                 
                if((USART1_RX_STA&(1<<15))==0)//接收完的一批数据,还没有被处理,则不再接收其他数据
                {
                        if(USART1_RX_STA<USART1_REC_LEN)        //还可以接收数据
                        {
                                TIM_SetCounter(TIM3,0);//计数器清空                                         
                                if(USART1_RX_STA==0)                                 //使能定时器3的中断
                                {
                                        TIM_Cmd(TIM3,ENABLE);//使能定时器3
                                }
                                USART1_RX_BUF[USART1_RX_STA++]=res;        //记录接收到的值         
                        }else
                        {
                                USART1_RX_STA|=1<<15;                                //强制标记接收完成
                        }
                }
                USART_ClearITPendingBit(USART1, USART_IT_RXNE);//清除接收中断
        }  
        OSIntExit();     //退出OS中断        
} [/mw_shl_code]      考虑到任务的实时性,在主程序中加入了UCOS-III操作系统,按照任务优先级先后顺序写了TOUCH任务、GPRS串口通信任务、触摸屏显示任务与LED闪烁任务。GPRS串口通信任务在任务死循环内判断USART1是否接收到PC发送的数据,然后将数据通过串口3发送出去;触摸屏显示任务也同样在任务死循环内判断USART3是否接收到ZigBee协调器发来的数据,然后将数据包进行解析、显示。
      GPRS串口通信任务如下:
      [mw_shl_code=c,true]void GPRS_USART1_task(void *pdata)
{
        u8 i,rxlen;
        OS_ERR err;
       
        while(1)
        {
                if(USART1_RX_STA&0x8000)  //USART1接收到GPRS发送的数据
                {
                        rxlen=USART1_RX_STA&0X7FFF;        //得到数据长度
                        for(i=0;i<rxlen;i++) USART3_TX_BUF=USART1_RX_BUF;       
                     
                        USART1_RX_STA=0;                           //启动下一次接收
                        USART3_TX_BUF=0;                        //自动添加结束符
                        printf("%s",USART3_TX_BUF);//发送接收到的数据通过串口3发送给ZigBee协调器
                }
                OSTimeDlyHMSM(0,0,0,20,OS_OPT_TIME_PERIODIC,&err);//延时20ms
        }
}[/mw_shl_code]       触摸屏显示任务部分代码如下:
[mw_shl_code=c,true]void emwindemo_task(void *p_arg){
while(1)
        {
        if((USART3_RX_STA&0x8000) && (USART3_RX_BUF[0]=='&'))   //接收到从协调器传送的一帧数据
                {
//。。。。。数据解析处理、显示(祥见附件)
                        USART3_RX_STA=0;

                }
        GUI_Exec();
        }
}
[/mw_shl_code]
      但下载后的现象是:
      1)用串口助手先给串口1发数据能收到,再给串口3发却始终不能收到且界面也无数据显示,而且LED始终不闪烁;
      2)用串口助手先给串口3发数据能收到且界面数据显示正常,但每发一下LED就闪一下,再给串口1发这时也能收到,但再换给串口3发却又不能收到;
      我对第1个现象的理解就是:由于串口1的任务优先级最高,一旦串口1发生接收中断后始终执行串口1任务(我把它解释为任务死锁),从而导致UCOS无法发生任务调度,从而串口3和LED任务都不能运行;第2个现象,串口1的任务(优先级高)可以打断串口3(优先级低)的任务,但为什么优先级最低的LED任务只执行一次没明白。
      求教原子哥和大神们,如何解决串口通信任务死锁的问题,保证UCOS各任务正常调度?希望给与小弟指点,谢谢!




正点原子逻辑分析仪DL16劲爆上市
回复

使用道具 举报

5

主题

17

帖子

0

精华

初级会员

Rank: 2

积分
127
金钱
127
注册时间
2016-1-21
在线时间
17 小时
 楼主| 发表于 2016-3-22 17:25:04 | 显示全部楼层
忘了附上源程序了

网关程序.rar

12.56 MB, 下载次数: 308

回复

使用道具 举报

530

主题

11万

帖子

34

精华

管理员

Rank: 12Rank: 12Rank: 12

积分
165371
金钱
165371
注册时间
2010-12-1
在线时间
2110 小时
发表于 2016-3-22 20:25:11 | 显示全部楼层
帮顶
回复

使用道具 举报

3

主题

15

帖子

0

精华

初级会员

Rank: 2

积分
129
金钱
129
注册时间
2013-3-24
在线时间
19 小时
发表于 2016-3-24 23:58:53 | 显示全部楼层
在重要的地方 加入代码临界段保护 试试  还有如果有多个任务都使用同一个外设 那么试试用互斥信号量。
玩了STM32彻底上瘾
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则



关闭

原子哥极力推荐上一条 /2 下一条

正点原子公众号

QQ|手机版|OpenEdv-开源电子网 ( 粤ICP备12000418号-1 )

GMT+8, 2025-2-23 04:37

Powered by OpenEdv-开源电子网

© 2001-2030 OpenEdv-开源电子网

快速回复 返回顶部 返回列表