硬汉嵌入式论坛

 找回密码
 立即注册
查看: 1289|回复: 3
收起左侧

硬汉哥,有一处while死循环不理解,求指导!!!

[复制链接]

7

主题

7

回帖

28

积分

新手上路

积分
28
发表于 2023-3-3 09:26:35 | 显示全部楼层 |阅读模式
硬汉哥,有一处while死循环不理解。

就是这个while(1)死循环,没找到退出这个循环的条件啊。虽然它是被freertos任务等级最低的vTaskGUI调用,但是如果卡在死循环里,其他任务就没法执行了啊,不是很理解,请执教,谢谢硬汉哥!!!

static void DSO_Graph(void)
{
        uint32_t t0, t1;
        uint8_t uKeyCode;
        WM_HWIN hTouchWin;
       
       
        /* 创建桌面窗口所需的定时器,用触发电压参考线的短暂显示 */
        hTimer = WM_CreateTimer(WM_HBKWIN,  /* 接受信息的窗口的句柄 */
                                   0,                                 /* 用户定义的Id。如果不对同一窗口使用多个定时器,此值可以设置为零。 */
                                   1050,                        /* 周期,此周期过后指定窗口应收到消息*/
                                   0);                                       /* 留待将来使用,应为0 */       
       
        while(1)
        {
                /* 记录刷新前的时刻 */
                t0 = GUI_GetTime();
               
                /* 给信号处理任务发消息,做波形的处理和FFT */
                /* 继续发消息,启动歌曲播放 */
                g_Flag->ucDsoMsg = DspFFT2048Pro_15;
                xEventGroupSetBits(xCreatedEventGroup, g_Flag->ucDsoMsg);
               
                /*
                   g_Flag->hWinRunStop = 0 表示运行态,= 1表示暂停。
                   g_ucWaveRefreshFlag 等于0:表示不执行波形区域的刷新,等于1:表示执行波形区域的刷新。
                */
                if((g_Flag->hWinRunStop == 0)||(g_Flag->ucWaveRefresh == 1))
                {
                        _DrawWave();
                        g_Flag->ucWaveRefresh = 0;
                }
               
                /* 求差值,根据不同的执行时间差,执行不同的延迟时间 */
                t1 = GUI_GetTime() - t0;
                if (t1 < g_RefreshDelay[TimeBaseId])
                {  
                        GUI_Delay(g_RefreshDelay[TimeBaseId] - t1);
                }
               
                /////////////////////////////////////////////////////////////////////////////////////////////////
                /////////////////////////////////////////////////////////////////////////////////////////////////
               
                /* 按键消息处理 */
                uKeyCode = bsp_GetKey();
               
                /* 判断是否有按键按下 */
                if(uKeyCode != KEY_NONE)
                {
                        switch (uKeyCode)
                        {
                            /* 按键K1 用于实现屏幕截图功能 ********************************************************/       
                                case KEY_1_DOWN:
                                        /************由于按键不够用,将截图功能取消***********/
                                        #if 1
                                                hTouchWin = WM_CreateWindowAsChild(0,
                                                                           0,
                                                                           800,
                                                                           480,
                                                                           WM_HBKWIN,
                                                                           WM_CF_SHOW,
                                                                           _cbTouchCalibration,
                                                                           0);
                                                WM_Exec();
                                                WM_SelectWindow(hTouchWin);
                               
                                                /* 执行触摸校准 */
                                                TOUCH_Calibration();
                               
                                                WM_SelectWindow(0);
                               
                                                WM_DeleteWindow(hTouchWin);
                                                WM_Exec();
                               
                                                /* 自动触发暂停状态 */
                                                if(g_Flag->hWinRunStop == 1)
                                                {
                                                        g_Flag->ucWaveRefresh = 1;
                                                }
                                       
                                                /* 普通触发暂停状态 */
                                                if(TriggerFlag == 1)
                                                {
                                                        TriggerFlag = 2;
                                                }
                                        #endif
                                       
                                        /* 用于截图 */
                                        #if 0
                                                xTaskNotifyGive(xHandleTaskMsgPro);
                                        #endif
                                       
                                        /* 打印任务的执行情况 */                                               
                                        #if 0
                                                g_Flag->ucDsoMsg = DspTaskInfo_13;
                                                xEventGroupSetBits(xCreatedEventGroup, g_Flag->ucDsoMsg);
                                        #endif       
                                               
                                        break;
                               
                                /* 按键K2 用于实现波形的暂停和运行 ***************************************************/
                                case KEY_2_DOWN:
                                        /* TriggerFlag = 0 表示当前用的是自动触发模式进行暂停和运行操作 */
                                        if(TriggerFlag == 0)
                                        {
                                                if(g_Flag->hWinRunStop == 0)
                                                {
                                                        g_Flag->hWinRunStop = 1;
                                                        ADC_DMA_Close();
                                                }
                                                else
                                                {
                                                        g_Flag->hWinRunStop = 0;                                               
                                                        ADC_DMA_Open();
                                                }
                                        }
                                        /* TriggerFlag = 2或3表示当前用的是正常触发模式进行暂停和运行操作 */
                                        else
                                        {
                                                if(g_Flag->ucTrig == 0)
                                                {
                                                        g_Flag->ucTrig = 1;
                                                        ADC_DMA_Close();
                                                }
                                                else
                                                {
                                                        g_Flag->ucTrig = 0;                                               
                                                        ADC_DMA_Open();
                                                }
                                               
                                                /* 设置更新一次 */
                                                TriggerFlag = 2;
                                        }
                                        g_Flag->ucWaveRefresh = 1;
                                        WM_InvalidateArea(&rRunMode);
                                        break;
                               
                                /* 按键K3用于切换自动触发和普通触发 **********************************************/
                case KEY_3_DOWN:               
                                        /* TriggerFlag = 0 表示当前用的是自动触发模式 */
                                        if(TriggerFlag == 0)
                                        {
                                                /* 从自动触发切换到普通触发 */
                                                TriggerFlag = 1;
                                                g_Flag->ucTrig = g_Flag->hWinRunStop;
                                                g_DSO1->sCurTriStep = 0;
                                               
                                                /* 更新触发位置 */
                                                WM_InvalidateArea(&rTrigPos);
                                               
                                                /*  进入触发后重新设置ADC触发值为1V,切换后重新设置采样率位2Msps */
                                                WM_SendMessageNoPara(hDlgScale, WM_TextUpDate);
                                               
                                                /* 进入触发界面后,默认设置触发是1V,也就是1241 */
                                                ADC_AnalogWatchdogThresholdsConfig(ADC3, 1241, 0);
                                        }
                                        /* TriggerFlag = 2或3表示当前用的是正常触发模式 */
                                        else
                                        {
                                                /* TriggerFlag = 0 表示当前用的是自动触发模式 */
                                                TriggerFlag = 0;
                                               
                                                /* 更新状态 */
                                                g_Flag->hWinRunStop = g_Flag->ucTrig;
                                               
                                                /* 返回后,不再需要看门狗设置触发 */
                                                ADC_AnalogWatchdogThresholdsConfig(ADC3, 4095, 0);
                                        }
                                       
                                        /* 两种触发模式切换后,都将数值设置为默认 */
                                        g_TrigVol->usPos = 190;     
                                        g_TrigVol->usTrigValue = 1241;
                                        WM_InvalidateArea(&rTrigValue);
                                        WM_InvalidateArea(&rTrigMode);
                                       
                                        /* 刚切换到普通触发模式显示一次波形 */
                                        if(TriggerFlag == 1)
                                        {
                                                TriggerFlag = 2;
                                        }
                                        break;

                                /* 摇杆上键按下 *************************************************************/
                case JOY_DOWN_U:       
                                        /* 调节幅度放大 */
                                        if(g_Flag->hWinButState == 1) /* 幅度调节 */
                                        {
                                                Ch1AmpId++;
                                                if(Ch1AmpId == ATT_COUNT)
                                                {
                                                        Ch1AmpId = ATT_COUNT - 1;
                                                }
                                                WM_SendMessageNoPara(hDlgAmp, WM_TextUpDate);
                                        }
                                        /* 调节参考电压的上移 */
                                        else if(g_Flag->hWinButState == 2)
                                        {
                                                g_DSO1->usRefPos -= 10;
                                                if(g_DSO1->usRefPos<= 40)
                                                {
                                                        g_DSO1->usRefPos = 40;
                                                }
                                                WM_InvalidateArea(&rRefPos);
                                        }
                                        /* 调节水平横线A上移 */
                                        else if(g_Flag->hWinButState == 5)
                                        {
                                                g_Cursors->sCursorHA -= g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorHA <= 40)
                                                {
                                                        g_Cursors->sCursorHA = 40;
                                                }
                                        }
                                        /* 调节水平横线B上移  */
                                        else if(g_Flag->hWinButState == 6)
                                        {
                                                g_Cursors->sCursorHB -= g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorHB <= g_Cursors->sCursorHA)
                                                {
                                                        g_Cursors->sCursorHB = g_Cursors->sCursorHA;
                                                }
                                        }
                                        /* 调节自动触发和普通触发的触发值 */
                                        else if(g_Flag->hWinButState == 7)
                                        {
                                                /* 调整触发箭头的位置,方便查看 */
                                                g_TrigVol->usPos -= g_TrigVol->usTriStep;
                                                if(g_TrigVol->usPos <= DSOSCREEN_STARTY)
                                                {
                                                        g_TrigVol->usPos = DSOSCREEN_STARTY;
                                                }
                                               
                                                /* 根据调节的触发箭头位置获得触发值 */
                                                g_TrigVol->ufTrigValue = 240 - g_TrigVol->usPos;
                                                g_TrigVol->ufTrigValue = g_TrigVol->ufTrigValue * g_AttTable[Ch1AmpId][1] / 50000;
                                                g_TrigVol->ufTrigValue = g_TrigVol->ufTrigValue * 4095 / 3.3f;
                                                g_TrigVol->usTrigValue = g_TrigVol->ufTrigValue;
                                               
                                                /* 更新触发值 */
                                                WM_InvalidateArea(&rTrigValue);
                                               
                                                /* 更新后,更新一下波形显示,仅限普通触发方式 */
                                                if(TriggerFlag != 0)
                                                {
                                                        TriggerFlag = 2;
                                                       
                                                        /* 如果是普通触发模式,更新ADC3的看门狗阀值 */
                                                        ADC_AnalogWatchdogThresholdsConfig(ADC3, g_TrigVol->usTrigValue, 0);
                                                }
                                               
                                                /* 更新触发值的显示并获得当前的时间,从而实现调节触发值后,显现一条水平的直线,时长1s */
                                                g_TrigVol->ulTrigTimeLine = GUI_GetTime();
                                                WM_RestartTimer(hTimer, 1050);       
                                        }
                                       
                                        /* 使用K2按键将波形暂停后,通过变量g_ucWaveRefreshFlag置1进行波形刷新 */
                                        if(g_Flag->hWinRunStop == 1)
                                        {
                                                g_Flag->ucWaveRefresh = 1;  
                                        }
                                        break;
                                       
                                /* 摇杆下键按下 *************************************************************/
                                case JOY_DOWN_D:       
                                        /* 调节幅度衰减 */
                                        if(g_Flag->hWinButState == 1)
                                        {
                                                Ch1AmpId--;
                                                if(Ch1AmpId < 0)
                                                {
                                                        Ch1AmpId = 0;
                                                }
                                                WM_SendMessageNoPara(hDlgAmp, WM_TextUpDate);
                                        }
                                        /* 调节参考电压的下移 */
                                        else if(g_Flag->hWinButState == 2)
                                        {
                                                g_DSO1->usRefPos += 10;
                                                if(g_DSO1->usRefPos >= 440)
                                                {
                                                        g_DSO1->usRefPos = 440;
                                                }
                                                WM_InvalidateArea(&rRefPos);
                                        }
                                        /* 调节水平横线A下移 */
                                        if(g_Flag->hWinButState == 5)
                                        {
                                                g_Cursors->sCursorHA += g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorHA >= g_Cursors->sCursorHB)
                                                {
                                                        g_Cursors->sCursorHA = g_Cursors->sCursorHB;
                                                }
                                        }
                                         /* 调节水平横线B下移  */
                                        else if(g_Flag->hWinButState == 6)
                                        {
                                                g_Cursors->sCursorHB += g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorHB >= 440)
                                                {
                                                        g_Cursors->sCursorHB = 440;
                                                }
                                        }
                                        /* 调节自动触发和普通触发的触发值 */
                                        else if(g_Flag->hWinButState == 7)
                                        {
                                                /* 调整触发箭头的位置,方便查看 */
                                                g_TrigVol->usPos += g_TrigVol->usTriStep;
                                                if(g_TrigVol->usPos >= DSOSCREEN_ENDY)
                                                {
                                                        g_TrigVol->usPos = DSOSCREEN_ENDY;
                                                }
                                               
                                                /* 根据调节的触发箭头位置获得触发值 */
                                                g_TrigVol->ufTrigValue = 240 - g_TrigVol->usPos;
                                                g_TrigVol->ufTrigValue = g_TrigVol->ufTrigValue * g_AttTable[Ch1AmpId][1] / 50000;
                                                g_TrigVol->ufTrigValue = g_TrigVol->ufTrigValue * 4095 / 3.3f;
                                                g_TrigVol->usTrigValue = g_TrigVol->ufTrigValue;
                                               
                                                WM_InvalidateArea(&rTrigValue);
                                               
                                                /* 更新后,更新一下波形显示,仅限普通触发方式 */
                                                if(TriggerFlag != 0)
                                                {
                                                        TriggerFlag = 2;
                                                        /* 如果是普通触发模式,更新ADC3的看门狗阀值 */
                                                        ADC_AnalogWatchdogThresholdsConfig(ADC3, g_TrigVol->usTrigValue, 0);
                                                }
                                               
                                                /* 更新触发值的显示并获得当前的时间,从而实现调节触发值后,显现一条水平的直线,时长1s */
                                                g_TrigVol->ulTrigTimeLine = GUI_GetTime();
                                                WM_RestartTimer(hTimer, 1050);       
                                        }
                                       
                                        /* 使用K2按键将波形暂停后,通过变量g_Flag->ucWaveRefresh置1进行波形刷新 */
                                        if(g_Flag->hWinRunStop == 1)
                                        {
                                                g_Flag->ucWaveRefresh = 1;  
                                        }
                                        break;
                                       
                                /* 摇杆左键按下 *************************************************************/
                                case JOY_DOWN_L:
                                        /* 调节ADC的采样率 */
                                        if(g_Flag->hWinButState == 0)
                                        {
                                                TimeBaseId++;
                                                if(TimeBaseId == TIME_COUNT)
                                                {
                                                        TimeBaseId = TIME_COUNT - 1;
                                                }
                                                ADC_DMA_Close();
                                                ADC_DMA_Open();
                                               
                                                /* 如果是低频的慢速显示需要记录当前的DMA出传输位置 */
                                                g_DSO1->ulSlowRefresh0 = 10240 - DMA2_Stream1->NDTR;
                                                g_DSO2->ulSlowRefresh0 = 10240 - DMA2_Stream0->NDTR;
                                                g_DSO1->ulSlowRefresh1 = 0;
                                                g_DSO2->ulSlowRefresh1 = 0;                                               
                                               
                                                /* 更新当前采样时基显示 */
                                                WM_SendMessageNoPara(hDlgScale, WM_TextUpDate);
                                               
                                                /*
                                                   g_DSO1->ucSlowWaveFlag和g_DSO2->ucSlowWaveFlag = 0 表示启动慢速显示模式,
                                                   也就是滚动显示在低频采样时,设置其等于0才有效。这里为了方便直接设置为0;
                                                */
                                                g_DSO1->ucSlowWaveFlag = 0;
                                                g_DSO2->ucSlowWaveFlag = 0;
                                        }
                                        /* 调节垂直线A左移 */
                                        else if(g_Flag->hWinButState == 3)
                                        {
                                                g_Cursors->sCursorVA -= g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorVA <= 40)
                                                {
                                                        g_Cursors->sCursorVA = 40;
                                                }
                                        }
                                        /* 调节垂直线B左移 */
                                        else if(g_Flag->hWinButState == 4)
                                        {
                                                g_Cursors->sCursorVB -= g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorVB <= g_Cursors->sCursorVA)
                                                {
                                                        g_Cursors->sCursorVB = g_Cursors->sCursorVA;
                                                }
                                        }
                                        /* 自动触发模式和普通触发模式2K数据的显示起始位置设定 */
                                        else if(g_Flag->hWinButState == 7)
                                        {
                                                /* 自动触发模式:2K数据的显示起始位置设定 */
                                                if(TriggerFlag == 0)
                                                {
                                                        /* 左移100个数据 */
                                                        g_DSO1->sCurTriStep -= 100;       
                                                }
                                                /* 普通触发模式:6K数据的显示起始位置设定 */
                                                else
                                                {
                                                        /* 左移100个数据 */
                                                        g_DSO1->sCurTriStep -= 100;
                                                        /*
                                                           正常触发模式支持的数据显示是2K=2048,默认显示屏的正中间位置对应数据的
                                                           正中间位置,由于一屏可以显示600字节,所以向右最大偏移-(1024-300) = -724字节。
                                                        */
                                                        if(g_DSO1->sCurTriStep <= -724)
                                                        {
                                                                g_DSO1->sCurTriStep = -724;
                                                        }
                                                       
                                                        /* 通过设置为2来更新波形显示 */
                                                        TriggerFlag = 2;
                                                }
                                       
                                                /* 更新当前的数据位置的箭头 */
                                                WM_InvalidateArea(&rTrigPos);
                                        }
                       
                                        /* 使用K2按键将波形暂停后,通过变量g_Flag->ucWaveRefresh置1进行波形刷新 */
                                        if(g_Flag->hWinRunStop == 1)
                                        {
                                                g_Flag->ucWaveRefresh = 1;  
                                        }
                                        break;
                                       
                                /* 摇杆右键按下 *************************************************************/
                                case JOY_DOWN_R:
                                        /* 调节ADC的采样率 */
                                        if(g_Flag->hWinButState == 0)
                                        {
                                                TimeBaseId--;
                                                if(TimeBaseId < 0)
                                                {
                                                        TimeBaseId = 0;
                                                }
                                               
                                                ADC_DMA_Close();
                                                ADC_DMA_Open();
                                               
                                                /* 如果是低频的慢速显示需要记录当前的DMA出传输位置 */
                                                g_DSO1->ulSlowRefresh0 = 10240 - DMA2_Stream1->NDTR;
                                                g_DSO2->ulSlowRefresh0 = 10240 - DMA2_Stream0->NDTR;
                                                g_DSO1->ulSlowRefresh1 = 0;
                                                g_DSO2->ulSlowRefresh1 = 0;
                                               
                                                /* 更新当前采样时基显示 */
                                                WM_SendMessageNoPara(hDlgScale, WM_TextUpDate);
                                               
                                                /*
                                                   g_DSO1->ucSlowWaveFlag和g_DSO2->ucSlowWaveFlag = 0 表示启动慢速显示模式,
                                                   也就是滚动显示在低频采样时,设置其等于0才有效。这里为了方便直接设置为0;
                                                */
                                                g_DSO1->ucSlowWaveFlag = 0;
                                                g_DSO2->ucSlowWaveFlag = 0;
                                        }
                                        /* 调节垂直线A右移 */
                                        else if(g_Flag->hWinButState == 3)
                                        {
                                                g_Cursors->sCursorVA += g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorVA >= g_Cursors->sCursorVB)
                                                {
                                                        g_Cursors->sCursorVA = g_Cursors->sCursorVB;
                                                }
                                        }
                                        /* 调节垂直线B右移 */
                                        else if(g_Flag->hWinButState == 4)
                                        {
                                                g_Cursors->sCursorVB += g_Cursors->usCursorStep;
                                                if(g_Cursors->sCursorVB >= 640)
                                                {
                                                        g_Cursors->sCursorVB = 640;
                                                }
                                        }
                                        /* 自动触发模式和普通触发模式6K数据的显示起始位置设定 */
                                        else if(g_Flag->hWinButState == 7)
                                        {
                                                /* 自动触发模式:6K数据的显示起始位置设定 */
                                                if(TriggerFlag == 0)
                                                {
                                                        /* 右移100个数据 */
                                                        g_DSO1->sCurTriStep += 100;                                               
                                                }
                                                /* 普通触发模式:2K数据的显示起始位置设定 */
                                                else
                                                {
                                                        /* 右移100个数据 */
                                                        g_DSO1->sCurTriStep += 100;
                                                       
                                                        /*
                                                           正常触发模式支持的数据显示是2K=2048,默认显示屏的正中间位置对应数据的
                                                           正中间位置,由于一屏可以显示600字节,所以向右最大偏移1024-300 =724字节。
                                                        */
                                                        if(g_DSO1->sCurTriStep >= 724)
                                                        {
                                                                g_DSO1->sCurTriStep = 724;
                                                        }
                                                       
                                                        /* 通过设置为2来更新波形显示 */
                                                        TriggerFlag = 2;
                                                }
                                               
                                                /* 更新当前的数据位置的箭头 */
                                                WM_InvalidateArea(&rTrigPos);
                                        }
                                       
                                        /* 使用K2按键将波形暂停后,通过变量g_Flag->ucWaveRefresh置1进行波形刷新 */
                                        if(g_Flag->hWinRunStop == 1)
                                        {
                                                g_Flag->ucWaveRefresh = 1;  
                                        }
                                        break;

                                /* 摇杆OK键按下 *************************************************************/
                                case JOY_DOWN_OK:
                                        /* OK键用于实现8种功能的切换 */
                                        g_Flag->hWinButState++;
                                        if(g_Flag->hWinButState == 8)
                                        {
                                                g_Flag->hWinButState = 0;
                                        }
                                        WM_InvalidateArea(&rButState);
                                        break;
                        }               
                }
        }
}



捕获.PNG
回复

使用道具 举报

1万

主题

6万

回帖

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
106660
QQ
发表于 2023-3-3 17:06:43 | 显示全部楼层
DSO_Graph函数是GUI任务的实体,全部都在这个里面执行的。
然后他是最低优先级任务,其它任务优先级都比它高,比他优先级高的任务都可以抢占他执行。


回复

使用道具 举报

7

主题

7

回帖

28

积分

新手上路

积分
28
 楼主| 发表于 2023-3-3 18:38:53 来自手机 | 显示全部楼层
eric2013 发表于 2023-3-3 17:06
DSO_Graph函数是GUI任务的实体,全部都在这个里面执行的。
然后他是最低优先级任务,其它任务优先级都比 ...

感谢硬汉,感谢硬汉,紫薯布丁
回复

使用道具 举报

7

主题

7

回帖

28

积分

新手上路

积分
28
 楼主| 发表于 2023-3-3 18:52:34 来自手机 | 显示全部楼层
eric2013 发表于 2023-3-3 17:06
DSO_Graph函数是GUI任务的实体,全部都在这个里面执行的。
然后他是最低优先级任务,其它任务优先级都比 ...

硬汉哥,那我的理解就是while外的代码应该只执行一次,当进入while后,被其他任务抢占,再回来也是循环执行while里的任务吧。
回复

使用道具 举报

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

本版积分规则

QQ|小黑屋|Archiver|手机版|硬汉嵌入式论坛

GMT+8, 2024-4-28 14:11 , Processed in 0.172575 second(s), 28 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2023, Tencent Cloud.

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