久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 3201|回復: 14
收起左側

51單片機開發板串行中斷if語句無法執行問題(看起來很簡單,但程序怎么也調不過去)

[復制鏈接]
ID:30063 發表于 2022-12-5 10:59 | 顯示全部樓層 |閱讀模式
碰到一個看起來很簡單的51單片機串行通信的問題,但折騰了兩天了,怎么也調試不過去

1.目的:
使用郭天祥的開發版,實現串口送入0x01情況下,led燈閃爍的效果


2.代碼如下:
void Usart() interrupt 4
{
unsigned char receiveData;
receiveData=SBUF;//出去接收到的數據
RI = 0;//清除接收中斷標志位

//ledFlash();//放在外面單片機能夠指揮外部小燈閃爍
if(receiveData==0x01)
{
ledFlash();
}

SBUF=receiveData;//將接收到的數據放入到發送寄存器
while(!TI); //等待發送數據完成
TI=0; //清除發送完成標志位
}


3.問題:
1)將實現led閃爍的函數 ledFlash()放在if語句之外直接執行,可以實現當字節到達時,直接閃爍的效果
2)但是,當將ledFlash()移到if 語句中,不知為什么,下載到單片機就無法實現小燈閃爍效果了,但是后面發送到stc-isp的緩沖區的程序仍然正常。如下圖
1.png
4.嘗試:
使用keil串口仿真調試,則當發送0x01時,能夠進入 if 語句,正常執行ledFlash(),如圖 2.png


請教大家,這個到底是怎么回事的,問題該如何解決啊

回復

使用道具 舉報

ID:781832 發表于 2022-12-5 12:00 | 顯示全部樓層
連續發 0x01 看看是否能閃爍
回復

使用道具 舉報

ID:1055764 發表于 2022-12-5 14:05 | 顯示全部樓層
和樓上觀點一樣:連續發 0x01,看是否閃爍。
回復

使用道具 舉報

無效樓層,該帖已經被刪除
ID:30063 發表于 2022-12-5 16:27 | 顯示全部樓層
連續發了,不閃爍
回復

使用道具 舉報

ID:30063 發表于 2022-12-5 19:17 | 顯示全部樓層
northroom 發表于 2022-12-5 12:00
連續發 0x01 看看是否能閃爍

連續發了,還是不行
回復

使用道具 舉報

ID:301191 發表于 2022-12-6 05:48 | 顯示全部樓層
頂一下
回復

使用道具 舉報

ID:213173 發表于 2022-12-6 07:27 | 顯示全部樓層
問題當然在出在ledFlash()函數。放在串口中斷里,每發生一次中斷,if判斷真后 ledFlash()函數只執行一次。放在主循環中就不同了,if判斷真后只要receiveData沒有變化, ledFlash()函數永久重復執行。
回復

使用道具 舉報

ID:308903 發表于 2022-12-6 08:37 | 顯示全部樓層
if(receiveData==0x01)
{
ledFlash();
}
放到 while(!TI); //等待發送數據完成里面呢?
回復

使用道具 舉報

ID:384109 發表于 2022-12-6 08:42 | 顯示全部樓層
代碼不全,這類處理最好是放在主程序處理,而不是在中斷里處理
回復

使用道具 舉報

ID:77589 發表于 2022-12-6 09:22 | 顯示全部樓層
我嚴重懷疑,你是串口調試助手使用問題,可能選擇了ASCII發送(這種情況下,單片機永遠收不到0x01)。
應該切換到十六進制發送。
回復

使用道具 舉報

ID:30063 發表于 2022-12-7 10:05 | 顯示全部樓層
wulin 發表于 2022-12-6 07:27
問題當然在出在ledFlash()函數。放在串口中斷里,每發生一次中斷,if判斷真后 ledFlash()函數只執行一次。 ...

你好,抱歉,沒大看明白,能否解釋一下呢

另外,說一下項目的情況,我是想實現雙機通信,另外一個設備通過串口發送信息,這臺設備通過出口得到信息后進行動作(現在使用的ledFlash()就是這個簡單效果,這個函數在主函數跑以及在沒有if判斷的這個串行接收中斷函數中跑,都正常使得外部led閃爍,但是放到if語句就不執行了,感覺 if 語句中的布爾邏輯是TRUE,不知為什么)
回復

使用道具 舉報

ID:30063 發表于 2022-12-7 10:31 | 顯示全部樓層
  1. #include "reg52.h"                         //此文件中定義了單片機的一些特殊功能寄存器

  2. typedef unsigned int u16;          //對數據類型進行聲明定義
  3. typedef unsigned char u8;



  4. sbit led=P1^0;                 //將單片機的P2.0端口定義為led


  5. sbit beep=P2^3;         //蜂鳴器引腳


  6. /*******************************************************************************
  7. * 函 數 名         : delay
  8. * 函數功能                   : 延時函數,i=1時,大約延時10us
  9. *******************************************************************************/
  10. void delay(u16 i)
  11. {
  12.         while(i--);       
  13. }

  14. void ledFlash()
  15. {
  16.         int i=3;
  17.         while(i--)
  18.         {
  19.                 led=0;
  20.                 delay(50000); //大約延時450ms
  21.                 led=1;
  22.                 delay(50000); //大約延時450ms       
  23.         }               
  24. }


  25. void UsartInit()
  26. {
  27.         SCON=0X50;                        //設置為工作方式1
  28.         TMOD=0X20;                        //設置計數器工作方式2
  29.         PCON=0X80;                        //波特率加倍
  30.         TH1=0XF3;                                //計數器初始值設置,注意波特率是4800的
  31.         TL1=0XF3;
  32.         ES=1;                                                //打開接收中斷
  33.         EA=1;                                                //打開總中斷
  34.         TR1=1;                                        //打開計數器
  35. }


  36. void main()
  37. {       
  38.         UsartInit();  //        串口初始化
  39.         while(1);               
  40. }


  41. void Usart() interrupt 4
  42. {
  43.         u8 receiveData;
  44.         if(RI)
  45.         {
  46.          
  47.         receiveData=SBUF;//出去接收到的數據       
  48.         {
  49.          ledFlash();//
  50.         }
  51.         while(receiveData==0x01)
  52.        

  53.         RI = 0;//清除接收中斷標志位

  54.   }
  55. }
復制代碼

C:\Users\DELL\Pictures\3.png
這個可以執行,不知道為什么?
但是同時出現了2個問題:
1.是ledFlash()函數只讓led閃爍3次,但是在這個函數執行過程中,小燈卻一直閃爍,退不出來了,這是為什么?
2.是while語句放在前面,{}中的flashLed()又不執行了,這個真不懂了
C:\Users\DELL\Pictures\4.png
求教
回復

使用道具 舉報

ID:30063 發表于 2022-12-7 10:34 | 顯示全部樓層
1261867136qq 發表于 2022-12-6 08:37
if(receiveData==0x01)
{
ledFlash();

完整代碼如下:
  1. #include "reg52.h"                         //此文件中定義了單片機的一些特殊功能寄存器

  2. typedef unsigned int u16;          //對數據類型進行聲明定義
  3. typedef unsigned char u8;



  4. sbit led=P1^0;                 //將單片機的P2.0端口定義為led


  5. sbit beep=P2^3;         //蜂鳴器引腳


  6. /*******************************************************************************
  7. * 函 數 名         : delay
  8. * 函數功能                   : 延時函數,i=1時,大約延時10us
  9. *******************************************************************************/
  10. void delay(u16 i)
  11. {
  12.         while(i--);       
  13. }

  14. void ledFlash()
  15. {
  16.         int i=3;
  17.         while(i--)
  18.         {
  19.                 led=0;
  20.                 delay(50000); //大約延時450ms
  21.                 led=1;
  22.                 delay(50000); //大約延時450ms       
  23.         }               
  24. }


  25. void UsartInit()
  26. {
  27.         SCON=0X50;                        //設置為工作方式1
  28.         TMOD=0X20;                        //設置計數器工作方式2
  29.         PCON=0X80;                        //波特率加倍
  30.         TH1=0XF3;                                //計數器初始值設置,注意波特率是4800的
  31.         TL1=0XF3;
  32.         ES=1;                                                //打開接收中斷
  33.         EA=1;                                                //打開總中斷
  34.         TR1=1;                                        //打開計數器
  35. }


  36. void main()
  37. {       
  38.         UsartInit();  //        串口初始化
  39.         while(1);               
  40. }


  41. void Usart() interrupt 4
  42. {
  43.         u8 receiveData;
  44.         if(RI)
  45.         {
  46.          
  47.         receiveData=SBUF;//出去接收到的數據       

  48.          
  49.         {
  50.          ledFlash();//
  51.         }
  52.         while(receiveData==0x01)

  53.         RI = 0;//清除接收中斷標志位

  54.   }
  55. }
復制代碼

代碼可以執行,led閃爍,
但是,出現了2個問題:
1.小燈一直閃爍,停不下來了
2.采用while提前,又不執行了
  1. void Usart() interrupt 4
  2. {
  3.         u8 receiveData;
  4.         if(RI)
  5.         {
  6.          
  7.         receiveData=SBUF;//出去接收到的數據       

  8.            while(receiveData==0x01)
  9.         {
  10.          ledFlash();//
  11.         }
  12.          

  13.         RI = 0;//清除接收中斷標志位

  14.   }
復制代碼

不知道這是怎么回事
回復

使用道具 舉報

ID:213173 發表于 2022-12-7 11:46 | 顯示全部樓層
goodshot 發表于 2022-12-7 10:05
你好,抱歉,沒大看明白,能否解釋一下呢

另外,說一下項目的情況,我是想實現雙機通信,另外一個設備 ...

不知道你的ledFlash()函數的具體代碼,但放在串口中斷中運行肯定是不當的,LED閃爍是需要在一定的時間范圍完成,而串口中斷函數是不能把占用較長時間的LED閃爍函數放進去。串口中斷只能根據收到的信息經判斷輸出一個標志并立即退出函數。主函數根據這個標志調用指定的子函數。
void Usart() interrupt 4
{
        unsigned char receiveData;
        receiveData=SBUF;//獲取接收到的數據
        RI = 0;//清除接收中斷標志位
        if(receiveData==0x01)//判斷是真
        {
                flag=1;//標志置1
        }
        else
        {
                flag=0;//標志清0
        }
}
如果主函數中要持續執行
        if(flag)
        {
                ledFlash();
        }

如果主函數中只要執行1次
        if(flag)
        {
                flag=0;
                ledFlash();
        }
回復

使用道具 舉報

ID:401564 發表于 2022-12-7 17:20 | 顯示全部樓層
在中斷中最好不要使用while
也不要在中斷調用延時時間過長的函數
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 亚洲免费一区二区 | 久久久99国产精品免费 | www.久久精品 | 看av网址 | 91国在线高清视频 | 99久久成人 | 久在草| 中文字幕在线观看视频一区 | 欧美日韩亚洲一区 | 亚洲午夜小视频 | 成人免费视频网 | 日本一二三区高清 | 在线视频91 | 国产精品一区二区视频 | 日韩欧美国产成人一区二区 | 欧美一级做性受免费大片免费 | 欧美日日| 秋霞在线一区二区 | 亚洲欧洲日本国产 | 国产黄色精品在线观看 | jizz在线看片| 亚洲成人在线免费 | 国产综合久久 | 国产中文原创 | 欧美一区二区三区在线看 | 91精品国产乱码久久久久久久久 | 成人在线免费视频 | 欧美a在线看 | 国产精品久久久久久高潮 | 欧美一区二区三区在线观看 | 久久一日本道色综合久久 | 欧美中文字幕在线观看 | 久久99精品久久久久久秒播九色 | 一区在线视频 | 欧美日韩专区 | 亚洲国产精品va在线看黑人 | 亚洲成人精品 | 成av在线 | 天天综合网天天综合色 | com.色.www在线观看 | 美女网站视频免费黄 |