📄 int.asm
字号:
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Snixos Project version 1.0, 2003.6; (C) Copyright 2003,2004,2005 Jockeyson,KeqiangGao <Snallie@tom.com>; All Rights Reserved.; Distributed under the terms of the GNU General Public License.;; This program is a free and open source software and you can redistribute ; it and/or modify it under the terms of the GNU General Public License as; published by the Free Software Foundation. As no any liability is assumed ; for any incidental or consequential damages in connection with the ; information or program fragments contained herein,so any exception arised; is at your own risk. It is ABSOLUTELY WITHOUT ANY WARRANTY.; Bug report please send to Snallie@tom.com .;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; int.asm : Interrupt Handlers for SNIXOS; Author : snallie@tom.com; Time : 2003.6;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;bits 32; GLOBAL symbol definitionGLOBAL initInterrupts, tickcountGLOBAL eax_reg, ebx_reg, ecx_reg, edx_reg, esi_reg, edi_regGLOBAL eflag_reg, cs_reg, eip_reg, esp_reg, ebp_regGLOBAL ds_reg, es_reg, ss_reg, fs_reg, gs_reg ; ExceptionsGLOBAL int0x0 ,int0x1 ,int0x2 ,int0x3 ,int0x4 ,int0x5 ,int0x6 ,int0x7 GLOBAL int0x8 ,int0x9 ,int0xA ,int0xB ,int0xC ,int0xD ,int0xE ,int0xFGLOBAL int0x10,int0x11,int0x12,int0x13; IRQsGLOBAL int0x20,int0x21,int0x22,int0x23,int0x24,int0x25,int0x26,int0x27GLOBAL int0x30,int0x31,int0x32,int0x33,int0x34,int0x35,int0x36,int0x37; Imported symbolEXTERN scheduler ; in kernel.cEXTERN exceptionHandle ; in kernel.c EXTERN keyBdHandle ; in keyboard.c%macro saveCPUregs 0 push cs push ds push es push ss push fs push gs push eax push ebx push ecx push ebx push esi push edi push ebp push eax mov eax,esp add eax,15*4 xchg eax,[esp] ; value of esp send to stack when int occured push eax mov eax,cr0 xchg eax,[esp] ; push dword cr0 push eax mov eax,cr2 xchg eax,[esp] ; push dword cr2 push eax mov eax,cr3 xchg eax,[esp] ; push dword cr3%endmacro;; Intel Exception handlers; Divide By Zeroint0x0: ; pushad ;FLG,ECS,EIP,||,EAX,ECX,EDX,EBX,ESP,EBP,ESI,EDI ; prepare parameters for c function exceptionHandle() push dword 0x00expHdl: saveCPUregs call exceptionHandle ; c function defined in kernel.c ; Debug Trapint0x1: push dword 0X01 jmp expHdl ; NMI Interruptint0x2: push dword 0X02 jmp expHdl ; Breakpointint0x3: push dword 0X03 jmp expHdl ; Overflowint0x4: push dword 0X04 jmp expHdl ; BOUND Range Exceededint0x5: push dword 0X05 jmp expHdl ; Invalid Opcodeint0x6: push dword 0X06 jmp expHdl ; Device Not Availableint0x7: push dword 0X07 jmp expHdl ; Double Faultint0x8: push dword 0X08 jmp expHdl ; Coprocessor Segment Overrunint0x9: push dword 0X09 jmp expHdl ; Invalid TSSint0xA: push dword 0X0A jmp expHdl ; Segment Not Presentint0xB: push dword 0X0B jmp expHdl ; Stack-Segment Faultint0xC: push dword 0X0C jmp expHdl ; General Protection Faultint0xD: push dword 0X0D jmp expHdl ; Page Faultint0xE: push dword 0X0E jmp expHdl ; Int F reservedint0xF: push dword 0X0F jmp expHdl; Floating Point Error (Math Fault)int0x10: push dword 0X10 jmp expHdl ; Alignment Checkint0x11: push dword 0X11 jmp expHdl ; Machine Checkint0x12: push dword 0X12 jmp expHdl ; Streaming SIMD Extensionsint0x13: push dword 0X13 jmp expHdl ;; Interrupt Handlers (0x20-0x27) (0x30-0x37); IRQ0 System Timerint0x20: cli ; force to cli add dword [tickcount], 1 ; tickcount++ each time clock interrupt occured inc dword [TICK] cmp dword [TICK],SCHED_INTERVAL ; schedual interval reached jz dispatcher jmp quitInt20dispatcher: mov word [TICK], 0 ; reset TICK ; Save old general purpose regs mov dword [eax_reg], eax mov dword [ebx_reg], ebx mov dword [ecx_reg], ecx mov dword [edx_reg], edx ; Save old index regs mov dword [esi_reg], esi mov dword [edi_reg], edi mov dword [ebp_reg], ebp ; Save old flag register & PC pop dword [eip_reg] pop dword [cs_reg] pop dword [eflag_reg] mov dword [esp_reg], esp call scheduler ; Restore new general purpose regs mov dword eax, [eax_reg] mov dword ebx, [ebx_reg] mov dword ecx, [ecx_reg] mov dword edx, [edx_reg] ; Restore new index regs mov dword esi, [esi_reg] mov dword edi, [edi_reg] ; switch to the desired stack mov dword esp, [esp_reg] mov dword ebp, [ebp_reg] ; Restore new flag register & PC push dword [eflag_reg] push dword [cs_reg] push dword [eip_reg] quitInt20: call SendEOI sti iret ; end of int0x20 Interrupt Handler SCHED_INTERVAL EQU 1000/10/5tickcount dd 0 ; Ticks since boot timeTICK dd 0 ; for scheduling ; IRQ1 Keyboard;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; keybdIntRoutine; keyboard interrupt service routine; nothing but call C routine keyBdHandle in keyboard.c for ; further process ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;keybdIntRoutine: int0x21: pusha ; !!no pusha when enter keybd and no popa when ; exit keybd may emit exceptional behavior!! cli call keyBdHandle ; in keyboard.c -fno-frame-pointer popa sti iret ; keyboard interrupt done ;; dummy IRQ handler for IRQ2~IRQ7 int0x22: ; IRQ2 PIC2 (not needed), Do nothing hereint0x23: ; IRQ3 Serial Port (com1 usually) int0x24: ; IRQ4 Serial Port (com2 usually)int0x25: ; IRQ5 Reserved/Sound Cardint0x26: ; IRQ6 Floppy Disk Controllerint0x27: ; IRQ7 Parallel Port cli call SendEOI sti iret;; dummy IRQ handler for IRQ8~IRQ15int0x30: ; IRQ8 Real Time Clock, Do nothing here for nowint0x31: ; IRQ9 Redirect from PIC1int0x32: ; IRQ10 Reservedint0x33: ; IRQ11 Reservedint0x34: ; IRQ12 PS/2 Mouseint0x35: ; IRQ13 Math Co-processorint0x36: ; IRQ14 Hard Diskint0x37: ; IRQ15 Reserved cli call SendEOI call SendEOI2 sti iret;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; initInterrupts;; Sets up the IDT for the exception & IRQs handlers;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Each entry is a protected mode gate descriptor: ; byte in IDT entry usage ; 0 byte 0 (LSB) of handler offset (EIP 7:0) ; 1 byte 1 of handler offset (EIP 15:8) ; 2 LSB of handler selector (CS 7:0) ; 3 MSB of handler selector (CS 15:8) ; 4 (not used, set to 0) ; 5 access byte (8Eh, 8Fh, 0EEh, or 0EFh) ; 6 byte 2 of handler offset (EIP 23:16) ; 7 byte 3 (MSB) of handler offset (EIP 31:24) EXTERN doInitInts ; a C function defined in kerenel.c used to fill IDTinitInterrupts: call doInitInts lidt [IDTR] ; Now load the IDTR call _delay call InitPic ; Redirect the IRQs ret; End of initInterrupts ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; InitPic (local function);; ARGUMENTS: None;; Initializes the PIC and IRQ0-IRQ15 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; The 8259 chips can mask (enable and disable) individual IRQs. ; Zeroing a bit at port 21h or A1h enables the corresponding IRQ:; ; Bits at I/O port 21h; (1st 8259) IRQ ; ; b0 IRQ 0 (timer) ; b1 IRQ 1 (keyboard) ; b2 IRQ 2 (cascade; reserved for 2nd 8259) ; b3 IRQ 3 (COM2,4) ; b4 IRQ 4 (COM1,3) ; b5 IRQ 5 (LPT) ; b6 IRQ 6 (floppy) ; b7 IRQ 7 ; ; Bits at I/O port A1h; (2nd 8259) IRQ ; b0 IRQ 8 (realtime clock) ; b1 IRQ 9 ; b2 IRQ 10 ; b3 IRQ 11 ; b4 IRQ 12 (PS/2 mouse) ; b5 IRQ 13 ('386 coprocessor) ; b6 IRQ 14 (primary IDE drives) ; b7 IRQ 15 (secondary IDE drives) InitPic: push eax push ebx ;; Initialize PIC 1 mov al, 0x11 out 0x20, al call _delay ; Remap IRQs 0-7 mov al, 0x20 ; IRQ0 starts at INT 0x20 out 0x21, al call _delay mov al, 0x4 ; Slave attached to IRQ2 out 0x21, al call _delay mov al, 0x01 ; Last command byte out 0x21, al call _delay ;; Initialize PIC 2 mov al, 0x11 out 0xa0, al call _delay ; Remap IRQs 8-15 mov al, 0x30 ; IRQ8 starts at INT 0x30 out 0xa1, al call _delay mov al, 0x2 out 0xa1, al call _delay mov al, 0x01 ; Last command byte out 0xa1, al call _delay ;; Unmask all interrupts xor al, al out 0x21, al out 0xa1, al pop ebx pop eax ret;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; SendEOI (Sends end of interrupt signal to the PIC);; Just call this function at the end of every IRQ handler to signal;; to the PIC that it can service another IRQ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;SendEOI: push eax mov al, 0x20 ; EOI Signal out 0x20, al ; Send it! pop eax ret; End SendEOI ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; SendEOI2 (sends end of interrupt signal to PIC2);; the ame as SendEOI, but for PIC2;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;SendEOI2: push eax mov al, 0x20 ; EOI Signal out 0xa0, al ; Send it! pop eax ret; End of SendEOI2;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; _delay;; just for delay for a little more CPU cycles ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;_delay: nop nop jmp .next.next: ret;; Data Area; The IDT Register, 6 BytesIDTR dw 0x800 ; Size (256 entries times 8 Bytes/entry) dd 0x1000 ; Base 0x1000 per our memory map ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; SYSTEM PCB ; data exchange area for task scheduler ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; pcb: eax_reg dd 0 ebx_reg dd 0 ecx_reg dd 0 edx_reg dd 0 esi_reg dd 0 edi_reg dd 0 esp_reg dd 0 ebp_reg dd 0 eflag_reg dd 0 cs_reg dw 0 ds_reg dw 0 es_reg dw 0 ss_reg dw 0 fs_reg dw 0 gs_reg dw 0 eip_reg dd 0pcb_end:
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -