• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            隨筆-80  評論-24  文章-0  trackbacks-0

            int.s文件的核心功能是對中斷進行設置,不過這里把一些中斷處理程序也放進來,而且還把其他文件中用到的一些庫函數放到這兒,目的是為了方便,不需再在lib/目錄下重新建立asmlib.s類似的文件。由于該文件比較長,所有分兩部分解析。

             

              1 %include "asm/int.sh"
              2 
              3 extern boot_heartbeat
              4 extern pre_schedule
              5 extern validate_buffer
              6 extern sys_call_table
              7 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
              8 ; 到處中斷向量表和中斷描述符表寄存器
              9 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
             10 global idt
             11 global idtr
             12 
             13 global set_idt
             14 global sys_call
             15 
             16 global out_byte
             17 global in_byte
             18 global read_port
             19 global write_port
             20 global install_int_handler
             21 global uninstall_int_handler
             22 global install_sys_call_handler
             23 global enable_hwint
             24 global disable_hwint
             25 
             26 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
             27 ; 處理器能夠處理的默認中斷和異常
             28 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
             29 global divide_error
             30 global debug_exception
             31 global nmi
             32 global breakpoint_exception
             33 global overflow
             34 global bounds_check
             35 global inval_opcode
             36 global copr_not_available
             37 global double_fault
             38 global copr_seg_overrun
             39 global inval_tss
             40 global segment_not_present
             41 global stack_exception
             42 global general_protection
             43 global page_fault
             44 global copr_error
             45 global exception
             46 
             47 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
             48 ; 可屏蔽的硬件中斷
             49 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
             50 global int_clock
             51 global int_keyboard
             52 global int_serial_port2
             53 global int_serial_port1
             54 global int_lpt2
             55 global int_floppy
             56 global int_lpt1
             57 global int_rtc
             58 global int_ps_2_mouse
             59 global int_fpu_fault
             60 global int_at_win
             61 global int_default
             62 
             63 [SECTION .text]
             64 set_idt:
             65     ; 對8259A主片寫入ICW1
             66     push 0x11
             67     push MASTER_CTL_8259
             68     call out_byte
             69     add esp, 4 * 2
             70 
             71     ; 對8259A從片寫入ICW1
             72     push 0x11
             73     push SLAVE_CTL_8259
             74     call out_byte
             75     add esp, 4 * 2
             76 
             77     ; 設置8259A主片的中斷入口地址,為IRQ0_IV
             78     push IRQ0_IV
             79     push MASTER_CTL_MASK_8259
             80     call out_byte
             81     add esp, 4 * 2
             82 
             83     ; 設置8259A從片的中斷入口地址,為IRQ8_IV
             84     push IRQ8_IV
             85     push SLAVE_CTL_MASK_8259
             86     call out_byte
             87     add esp, 4 * 2
             88 
             89     ; 向8259A主片寫入ICW3,表明IR2處級聯了從片
             90     push 0x4
             91     push MASTER_CTL_MASK_8259
             92     call out_byte
             93     add esp, 4 * 2
             94 
             95     ; 向8259A從片寫入ICW3,表明從片是連接在主片的IR2處
             96     push 0x2
             97     push SLAVE_CTL_MASK_8259
             98     call out_byte
             99     add esp, 4 * 2
            100 
            101     ; 向8259A主片寫入ICW4
            102     push 0x1
            103     push MASTER_CTL_MASK_8259
            104     call out_byte
            105     add esp, 4 * 2
            106 
            107     ; 向8259A從片寫入ICW4
            108     push 0x1
            109     push SLAVE_CTL_MASK_8259
            110     call out_byte
            111     add esp, 4 * 2
            112 
            113     ; 屏蔽8259A主片的所有硬件中斷
            114     push 0xff
            115     push MASTER_CTL_MASK_8259
            116     call out_byte
            117     add esp, 4 * 2
            118 
            119     ; 屏蔽8259A從片的所有硬件中斷
            120     push 0xff
            121     push SLAVE_CTL_MASK_8259
            122     call out_byte
            123     add esp, 4 * 2
            124 
            125     ; 除零錯誤(內核態允許的中斷)
            126     ; 指令div or idiv
            127     push PRIVILEGE_KERNEL
            128     push divide_error
            129     push INT_GATE_386
            130     push DIVIDE_IV
            131     call init_idt
            132     add esp, 4 * 4
            133 
            134     ; 調試異常(內核態允許的中斷)
            135     push PRIVILEGE_KERNEL
            136     push debug_exception
            137     push INT_GATE_386
            138     push DEBUG_IV
            139     call init_idt
            140     add esp, 4 * 4
            141 
            142     ; 非屏蔽中斷(內核態允許的中斷)
            143     push PRIVILEGE_KERNEL
            144     push nmi
            145     push INT_GATE_386
            146     push NMI_IV
            147     call init_idt
            148     add esp, 4 * 4
            149 
            150     ; 調試斷點異常(用戶態允許的中斷)
            151     ; 指令int3
            152     push PRIVILEGE_USER
            153     push breakpoint_exception
            154     push INT_GATE_386
            155     push BREAKPOINT_IV
            156     call init_idt
            157     add esp, 4 * 4
            158 
            159     ; 溢出異常(用戶態允許的中斷)
            160     ; 指令into
            161     push PRIVILEGE_USER
            162     push overflow
            163     push INT_GATE_386
            164     push OVERFLOW_IV
            165     call init_idt
            166     add esp, 4 * 4
            167 
            168     ; 越界錯誤(內核態允許的中斷)
            169     ; linux將其設置為用戶態也允許的中斷
            170     ; 指令bound
            171     push PRIVILEGE_KERNEL
            172     push bounds_check
            173     push INT_GATE_386
            174     push BOUNDS_IV
            175     call init_idt
            176     add esp, 4 * 4
            177 
            178     ; 無效操作碼錯誤(內核態允許的中斷)
            179     ; 主要由ud2或無效指令引起
            180     push PRIVILEGE_KERNEL
            181     push inval_opcode
            182     push INT_GATE_386
            183     push INVAL_OP_IV
            184     call init_idt
            185     add esp, 4 * 4
            186 
            187     ; 設備不可用/無數學協處理器(內核態允許的中斷)
            188     ; 浮點數或wait/fwait指令
            189     push PRIVILEGE_KERNEL
            190     push copr_not_available
            191     push INT_GATE_386
            192     push COPROC_NOT_IV
            193     call init_idt
            194     add esp, 4 * 4
            195 
            196     ; 雙重錯誤(內核態允許的中斷)
            197     ; 所有能產生異?;騈MI或intr的指令
            198     push PRIVILEGE_KERNEL
            199     push double_fault
            200     push INT_GATE_386
            201     push DOUBLE_FAULT_IV
            202     call init_idt
            203     add esp, 4 * 4
            204 
            205     ; 386機器不再產生此種異常
            206     push PRIVILEGE_KERNEL
            207     push copr_seg_overrun
            208     push INT_GATE_386
            209     push COPROC_SEG_IV
            210     call init_idt
            211     add esp, 4 * 4
            212 
            213     ; 無效TSS錯誤(內核態允許的中斷)
            214     ; 任務切換或訪問TSS段時
            215     push PRIVILEGE_KERNEL
            216     push inval_tss
            217     push INT_GATE_386
            218     push INVAL_TSS_IV
            219     call init_idt
            220     add esp, 4 * 4
            221 
            222     ; 段不存在錯誤(內核態允許的中斷)
            223     ; 加載段寄存器或訪問系統段時
            224     push PRIVILEGE_KERNEL
            225     push segment_not_present
            226     push INT_GATE_386
            227     push SEG_NOT_IV
            228     call init_idt
            229     add esp, 4 * 4
            230 
            231     ; 堆棧段錯誤(內核態允許的中斷)
            232     ; 堆棧段操作或加載ss時
            233     push PRIVILEGE_KERNEL
            234     push stack_exception
            235     push INT_GATE_386
            236     push STACK_FAULT_IV
            237     call init_idt
            238     add esp, 4 * 4
            239 
            240     ; 常規保護錯誤(內核態允許的中斷)
            241     ; 內存或其他保護檢驗時
            242     push PRIVILEGE_KERNEL
            243     push general_protection
            244     push INT_GATE_386
            245     push PROTECTION_IV
            246     call init_idt
            247     add esp, 4 * 4
            248 
            249     ; 頁錯誤(內核態允許的中斷)
            250     ; 內存訪問時
            251     push PRIVILEGE_KERNEL
            252     push page_fault
            253     push INT_GATE_386
            254     push PAGE_FAULT_IV
            255     call init_idt
            256     add esp, 4 * 4
            257 
            258 
            259     ;;;;;;;;;;;;;;;;注意這里0x0f號中斷保留,未使用
            260 
            261 
            262     ; x87FPU浮點錯誤(內核態允許的中斷)
            263     ; x87FPU浮點指令或WAIT/FWAIT指令
            264     push PRIVILEGE_KERNEL
            265     push copr_error
            266     push INT_GATE_386
            267     push COPROC_ERR_IV
            268     call init_idt
            269     add esp, 4 * 4


            以上代碼雖然比較長,但是任務很簡單主要完成的有:
            1、設置8259A,80X86架構里面內置有兩片8259A,通過設置達到如下效果:分為主8259A和從8259A,從片連接在主片的IRQ2引腳上;設置主片的IRQ0引腳(時鐘中斷)的中斷號為IRQ0_IV(0x20),從8259A的IRQ0引腳的中斷號為IRQ8_IV;然后設置默認屏蔽所有的主片和從片的中斷(這樣是為了在初始化對應的硬件的時候再打開對應中斷);
            2、設置0~15號中斷向量,這些中斷向量都是Intel規定的中斷;設置中斷的核心函數是init_idt,該函數稍后會講解。

              1     ; 從0x20開始到中斷向量表尾部,統一初始化成默認的中斷處理程序
              2     mov ecx, IRQ0_IV
              3     push PRIVILEGE_KERNEL
              4     push int_default
              5     push INT_GATE_386
              6 init_rest:
              7     push ecx
              8     call init_idt
              9     pop ecx
             10     inc ecx
             11     cmp ecx, 255
             12     jna init_rest
             13     add esp, 4 * 3
             14 
             15     ; 全部中斷向量入口程序加載完成之后便加載中斷描述符表
             16     lidt [idtr] ; 加載中斷描述符表
             17     ret
             18 
             19 init_idt:
             20     mov eax, [esp + 4 * 1] ; 中斷向量號
             21     mov ebx, [esp + 4 * 2] ; 描述符類型(中斷門/調用門/陷阱門)
             22     mov ecx, [esp + 4 * 3] ; 中斷處理程序入口
             23     mov edx, [esp + 4 * 4] ; 特權級
             24     mov esi, idt
             25     shl eax, 3
             26     add esi, eax ; 中斷向量號乘以8然后加上idt基地址就能找到對用中斷向量號的idt描述符
             27     mov word [esi], cx
             28     add esi, 2
             29     mov word [esi], 0x8 ; CS段描述符
             30     add esi, 2
             31     mov byte [esi], 0x0
             32     add esi, 1
             33     shl edx, 5
             34     and bl, 0x0f
             35     or bl, 0x80
             36     or bl, dl
             37     mov byte [esi], bl
             38     add esi, 1
             39     shr ecx, 16
             40     mov word [esi], cx
             41     ret
             42     
             43 ; 在發生中斷時,eflags、cs、eip將自動被壓入棧中
             44 ; 如果有出錯碼的話,那么出錯碼緊接著繼續被壓入棧中(同樣被自動壓入棧中)
             45 ; 如果有堆棧切換,也就是說有特權級變化,那么原ss和esp將被壓入內層堆棧,之后才是eflags、cs、eip
             46 ; 從中斷或者異常中返回時必須用iretd,它與ret不同的時它會改變eflags的值
             47 divide_error:
             48     push 0xffffffff
             49     push DIVIDE_IV
             50     jmp exception
             51 
             52 debug_exception:
             53     push 0xffffffff
             54     push DEBUG_IV
             55     jmp exception
             56 
             57 nmi:
             58     push 0xffffffff
             59     push NMI_IV
             60     jmp exception
             61 
             62 breakpoint_exception:
             63     push 0xffffffff
             64     push BREAKPOINT_IV
             65     jmp exception
             66 
             67 overflow:
             68     push 0xffffffff
             69     push OVERFLOW_IV
             70     jmp exception
             71 
             72 bounds_check:
             73     push 0xffffffff
             74     push BOUNDS_IV
             75     jmp exception
             76 
             77 inval_opcode:
             78     push 0xffffffff
             79     push INVAL_OP_IV
             80     jmp exception
             81 
             82 copr_not_available:
             83     push 0xffffffff
             84     push COPROC_NOT_IV
             85     jmp exception
             86 
             87 double_fault:
             88     push DOUBLE_FAULT_IV
             89     jmp exception
             90 
             91 copr_seg_overrun:
             92     push 0xffffffff
             93     push COPROC_SEG_IV
             94     jmp exception
             95 
             96 inval_tss: ; 系統將出錯碼自動壓棧
             97     push INVAL_TSS_IV
             98     jmp exception
             99 
            100 segment_not_present: ; 系統將出錯碼自動壓棧
            101     push SEG_NOT_IV
            102     jmp exception
            103 
            104 stack_exception: ; 系統將出錯碼自動壓棧
            105     push STACK_FAULT_IV
            106     jmp exception
            107 
            108 general_protection: ; 系統將出錯碼自動壓棧
            109     push PROTECTION_IV
            110     jmp $
            111     jmp exception
            112 
            113 page_fault: ; 系統將出錯碼自動壓棧
            114     push PAGE_FAULT_IV
            115     jmp exception
            116 
            117 copr_error:
            118     push 0xffffffff
            119     push COPROC_ERR_IV
            120     jmp exception
            121 
            122 exception:
            123     add esp, 4 * 2 ; 跳過出錯碼和向量號
            124     cli
            125     hlt ; 我們目前不處理錯誤,只要出錯就讓機器hlt
            126     ;iretd
            127 


            上面這段代碼主要完成的工作有:
            1、初始化從0x20-0xff的所有中斷向量,使得這些中斷向量均指向默認的中斷處理函數int_default;
            2、init_idt函數的實現,該函數有如下形式:void init_idt(int iv, int privil, void *fun, int descr_type); 接受的四個參數依次是中斷向量號,該中斷特權級,中斷處理函數,描述符類型(是中斷門or調用門or陷阱門);該函數通過設置對應IDT中的描述符項的屬性完成設置。
            3、0x00-0x0f的中斷處理函數的實現,其實這些函數都跳轉到(不是調用,是直接跳轉)exception函數,該函數直接將系統hlt,意思是我們的系統目前不支持例如除零錯誤等的異常中斷。

            posted on 2012-02-14 00:21 myjfm 閱讀(538) 評論(0)  編輯 收藏 引用 所屬分類: 操作系統
            麻豆精品久久久久久久99蜜桃 | 国产欧美久久久精品影院| 久久久久亚洲AV无码去区首| 久久亚洲国产精品123区| 亚洲欧美国产精品专区久久| 日韩精品无码久久久久久| 青青青国产成人久久111网站| 亚洲欧美一区二区三区久久| 久久久精品2019免费观看| 久久无码国产| 亚洲国产精品热久久| 色综合久久久久无码专区| 久久WWW免费人成—看片| 久久成人国产精品| 久久亚洲国产精品成人AV秋霞| 女人香蕉久久**毛片精品| 久久一日本道色综合久久| 久久午夜综合久久| 99久久99久久精品国产片果冻 | 久久精品日日躁夜夜躁欧美| 日本精品久久久久中文字幕8| 久久久老熟女一区二区三区| 国产成人综合久久精品红| 久久夜色精品国产www| 一级做a爰片久久毛片人呢| 69SEX久久精品国产麻豆| 2021国内久久精品| 国产精品乱码久久久久久软件| 久久综合九色综合久99| 久久久青草久久久青草| 精品久久久久中文字幕日本| 久久亚洲精品国产精品| 久久一日本道色综合久久| 亚洲中文字幕无码久久2020| 亚洲综合伊人久久综合| 亚洲综合日韩久久成人AV| 久久夜色精品国产噜噜亚洲AV| 色欲综合久久躁天天躁蜜桃| 亚洲人成伊人成综合网久久久| 日韩久久久久久中文人妻| 久久精品国产亚洲av水果派|