異常是異常控制流的一種形式,它一部分由硬體實現,一部分由作業系統實現。因為它們有一部分是由硬體實現的,所以具體細節將隨系統的不同而有所不同。然而,對於每個系統而言,基本的思想都是相同的。在這一節中我們的目的是讓你對異常和異常處理有乙個一般性的了解,並且向你揭示現代計算機系統的一乙個經常令人感到迷惑的方面。
異常(exception)就是控制流中的突應用程式異常處理程式變,用來響應處理器狀態中的某些變化。
下圖展示了基本的思想。
在圖中,當處理器狀態中發生乙個重要的變化時,處理器正在執行某個當前指令iurr。 在處理器中,狀態被編碼為不同的位和訊號。狀態變化稱為事件(event)。事件可能和當前指令的執行直接相關。比如,發生虛擬記憶體缺頁、算術溢位,或者一條指令試圖除以零。另一方面,事件也可能和當前指令的執行沒有關係。比如,乙個系統定時器產生訊號或者乙個i/o請求完成。
異常可能會難以理解,因為處理異常需要硬體和軟體緊密合作。很容易搞混哪個部分執行哪個任務。
系統中可能的每種型別的異常都分配了乙個唯一的非負整數的異常號(exceptionnum-ber)。其中一些號碼是由處理器的設計者分配的,其他號碼由作業系統核心(作業系統常駐記憶體的部分)的設計者分配的。前者的示例包括被零除、缺頁、記憶體訪問違例、斷點以及算術運算溢位。後者的示例包括系統呼叫和來自外部i/o裝置的訊號。
在系統啟動時(當計算機重啟或者加電時),作業系統分配和初始化一張稱為異常表的跳轉表,使得表目k包含異常k的處理程式的位址。圖2展示了異常表的格式。
在執行時(當系統在執行某個程式時),處理器檢測到發生了乙個事件,並且確定了相應的異常號k。隨後,處理器觸發異常,方法是執行間接過程呼叫,通過異常表的表目k,轉到相應的處理程式。圖3展示了處理器如何使用異常表來形成適當的異常處理程式的位址。異常號是到異常表中的索引,異常表的起始位址放在乙個叫做異常表基址暫存器(exception table base register)的特殊cpu暫存器裡。
圖3異常類似於過程呼叫,但是有一些重要的不同之處:
●過程呼叫時,在跳轉到處理程式之前,處理器將返回位址壓人棧中。然而,根據異常的型別,返回位址要麼是當前指令(當事件發生時正在執行的指令),要麼是下一條指令(如果事件不發生,將會在當前指令後執行的指令)。
●處理器也把一些額外的處理器狀態壓到棧裡,在處理程式返回時,重新開始執行被中斷的程式會需要這些狀態。比如,x86-64 系統會將包含當前條件碼的eflags暫存器和其他內容壓人棧中。
●如果控制從使用者程式轉移到核心,所有這些專案都被壓到核心棧中,而不是壓到使用者棧中。
●異常處理程式執行在核心模式下,這意味著它們對所有的系統資源都有完全的訪問許可權。
異常可以分為四類:中斷(interrupt)、陷阱(trap)、故障(fault)和終止( abort)。圖4對這些屬性進行了描述
圖4中斷是非同步發生的,是來自處理器外部的i/o裝置的訊號的結果。硬體中斷不是由任何一條專門的指令造成的,從這個意義上來說它是非同步的。硬體中斷的異常處理程式常常稱為中斷處理程式(interrupt handler)。
圖5概述了乙個中斷的處理。i/o 裝置,例如網路介面卡、磁碟控制器和定時器晶元,通過向處理器晶元上的乙個引腳發訊號,並將異常號放到系統匯流排上,來觸發中斷,這個異常號標識了引起中斷的裝置。
圖5在當前指令完成執行之後,處理器注意到中斷引腳的電壓變高了,就從系統匯流排讀取異常號,然後呼叫適當的中斷處理程式。當處理程式返回時,它就將控制返回給下一條指令(也即如果沒有發生中斷,在控制流中會在當前指令之後的那條指令)。結果是程式繼續執行,就好像沒有發生過中斷一樣。剩下的異常型別(陷阱、故障和終止是同步發生的,是執行當前指令的結果。我們把這類指令叫做故障指令(faultinginstruction)。
陷阱是有意的異常,是執行一條指令的結果。就像中斷處理程式-一樣,陷阱處理程式將控制返回到下一條指令。陷阱最重要的用途是在使用者程式和核心之間提供乙個像過程一樣的介面,叫做系統呼叫。
使用者程式經常需要向核心請求服務,比如讀乙個檔案(read)、建立乙個新的程序(fork)、載入乙個新的程式(execve),或者終止當前程序(exit)。為了允許對這些核心服務的受控的訪問,處理器提供了一-條特殊的「syscall n」指令,當使用者程式想要請求服務n時,可以執行這條指令。執行syscall指令會導致乙個到異常處理程式的陷阱,這個處理程式解析引數,並呼叫適當的核心程式。圖6概述了乙個系統呼叫的處理。
故障由錯誤情況引起,它可能能夠被故障處理程式修正。當故障發生時,處理器將控制轉移給故障處理程式。如果處理程式能夠修正這個錯誤情況,它就將控制返回到引起故障的指令,從而重新執行它。否則,處理程式返回到核心中的abort例程,abort 例程會終止引起故障的應用程式。圖7概述了乙個故障的處理。
圖7乙個經典的故障示例是缺頁異常,當指令引用乙個虛擬位址,而與該位址相對應的物理頁面不在記憶體中,因此必須從磁碟中取出時,就會發生故障。就像我們將在虛擬記憶體中看到的那樣,乙個頁面就是虛擬記憶體的乙個連續的塊(典型的是4kb)。缺頁處理程式從磁碟載入適當的頁面,然後將控制返回給引起故障的指令。當指令再次執行時,相應的物理頁面已經駐留在記憶體中了,指令就可以沒有故障地執行完成了。
終止是不可恢復的致命錯誤造成的結果,通常是一些硬體錯誤,比如dram或者sram位被損壞時發生的奇偶錯誤。終止處理程式從不將控制返回給應用程式。如圖8所示,處理程式將控制返回給乙個abort例程,該例程會終止這個應用程式。
圖8
《深入了解計算機系統》,家庭作業2 73 2 74
2.74 寫出具有以下原型的函式 addition that saturates totmin or tmax int saturating add int x,int y 同正常的補碼加法的溢位的方式不同,當正溢位時,飽和加法返回tmax,負溢位時,返回tmin,飽和運算常常用在執行數字訊號處理的...
2021 1 28深入了解計算機系統第2章個人總結
位運算 邏輯and,00 可以通通置零,11.可以用來保留指定位 邏輯或 由於其只能由0 1和1 0得1的性質,所以要想在0和非零數之間找到非零數,用 即可 邏輯異或,感覺有點像 的補集 邏輯非,對於所有位,0取1,1取0,x 1 x 阿貝群 非位運算 類似 但是它不是針對位運算,0取1,非0取0 ...
深入理解計算機系統 異常
異常是異常控制流的一種形式,它一部分是由硬體實現的,一部分是由作業系統實現的。異常就是控制流中的突變,用來響應處理器狀態中的某些變化。在處理器中,狀態被編碼為不同的位和訊號。狀態變化稱為事件event,事件可能與當前指令的執行直接相關。比如發生虛擬儲存器的換頁,算數溢位,或者一條指令試圖除以零。另一...