舉例說明下,中斷何時會被丟棄與不會被丟棄:
假設正在執行INT0中斷服務程序中,程序執行時間很長,還未結束(遇RETI指令視為結束!)
而外設正通過串口向CPU發送數據1,2,3,4……
這時收到發來了【1】,RI被置位,由于INT0未結束,而串口無法響應中斷;
須臾【2】又收到了,RI再次置位,不過RI原本已是1,置位也是白置,SBUF中的【1】,被【2】擠掉了。
這時INT0結束了,RI=1的申請被執行,于是轉串口中斷服務,也就收到了【2】,這樣【1】就丟失了。
這時【3】又發來了,RI又被硬件置1。由于程序寫的很糟糕,應在開始就清RI,結果,在中斷服務程序結束前才清RI。這樣【3】也丟了。
然后【4】來了,當然就收到了。
【關鍵點】記住:
1、每個中斷源有一個IF標記,中斷源動作(起效)時,IF被硬件置1,但它只是【申請】中斷,是否被被批準【響應】,還取決于其它條件(被允許、已打開、無更高、同級在執行、CPU當前指令執行完畢……)。
2、由于一個中斷源只有一個標記IF,會出現以下三種情況:
2.1、中斷源動作了,IF被置1,但未被響應(如串口收到【1】未被響應),又來了N次動作(如串口又陸續收到【2】……【N】),那么只有中斷響應前的一個【N】會被收到,在N之前的全部丟失。
2.2、中斷響應后IF未被清除保持1,在中斷服務退出后,會再次進入中斷。也即數據【1】被無限次當作串入的數據。
所以必須及時清除中斷標記IF。提示:注意看手冊,有的IF在中斷響應后會由硬件自動清除。
2.3、中斷源動作讓IF=1,在未被響應之前,誤將IF清成0,則中斷申請取消,無法響應,即丟失。這在共用一個中斷入口的中斷源中時易發生。
例如,串行中斷服務程序:先看了TI=0無發送中斷,于是轉至查看RI=1,就在處理接收數據過程中,TI變1了、之后服務程序也結束了,不過程序寫的比較差,在退出中斷前,才清除了RI、TI。這樣就丟失了一個TI。
|