zoukankan      html  css  js  c++  java
  • 45 内核中的中断处理(下)

    参考

    https://blog.51cto.com/13475106/category6.html及狄泰软件相关课程

     

     主要代码文件

    %include "common.asm"
    
    global _start
    global TimerHandlerEntry
    
    extern TimerHandler
    
    extern gCTaskAddr
    extern gGdtInfo
    extern gIdtInfo
    extern InitInterrupt
    extern EnableTimer
    extern SendEOI
    extern RunTask
    extern KMain
    extern ClearScreen
    
    %macro BeginISR 0
        sub esp, 4
        
        pushad
        
        push ds
        push es
        push fs
        push gs
        
        mov dx, ss
        mov ds, dx
        mov es, dx
        
        mov esp, BaseOfLoader
    %endmacro
    
    %macro EndISR 0
        mov esp, [gCTaskAddr]
        
        pop gs
        pop fs
        pop es
        pop ds
        
        popad
        
        add esp, 4
        
        iret
    %endmacro
    
    [section .text]
    [bits 32]
    _start:
        mov ebp, 0
        
        call InitGlobal
        call ClearScreen
        call KMain
        
        jmp $
        
    ;
    ;    
    InitGlobal:
        push ebp
        mov ebp, esp
        
        mov eax, dword [GdtEntry]
        mov [gGdtInfo], eax
        mov eax, dword [GdtSize]
        mov [gGdtInfo + 4], eax
        
        mov eax, dword [IdtEntry]
        mov [gIdtInfo], eax
        mov eax, dword [IdtSize]
        mov [gIdtInfo + 4], eax
        
        mov eax, dword [RunTaskEntry]
        mov dword [RunTask], eax
        
        mov eax, dword [InitInterruptEntry]
        mov [InitInterrupt], eax
        
        mov eax, dword [EnableTimerEntry]
        mov [EnableTimer], eax
        
        mov eax, dword [SendEOIEntry]
        mov [SendEOI], eax
        
        leave
        
        ret
        
    ;
    ;
    TimerHandlerEntry:
    BeginISR 
        call TimerHandler
    EndISR
        
    
    #include "kernel.h"
    #include "screen.h"
    #include "global.h"
    
    void (* const InitInterrupt)() = NULL;
    void (* const EnableTimer)() = NULL;
    void (* const SendEOI)(uint port) = NULL;
    
    Task* gCTaskAddr = NULL;
    Task p = {0};
    
    void Delay(int n)
    {
        while( n > 0 )
        {
            int i = 0;
            int j = 0;
            
            for(i=0; i<1000; i++)
            {
                for(j=0; j<1000; j++)
                {
                    asm volatile ("nop
    ");
                }
            }
            
            n--;
        }
    }
    
    void TaskA()
    {
        int i = 0;
        
        SetPrintPos(0, 12);
        
        PrintString("Task A: ");
        
        while(1)
        {
            SetPrintPos(8, 12);
            PrintChar('A' + i);
            i = (i + 1) % 26;
            Delay(1);
        }
    }
    
    void TimerHandlerEntry();
    
    void TimerHandler()
    {
        static uint i = 0;
        
        i = (i + 1) % 10;
        
        if( i == 0 )
        {
            static uint j = 0;
            
            SetPrintPos(0, 13);
            
            PrintString("Timer: ");
            
            SetPrintPos(8, 13);
            
            PrintIntDec(j++);
        }
        
        SendEOI(MASTER_EOI_PORT);
    }
    
    void KMain()
    {
        int n = PrintString("D.T.OS
    ");
        uint temp = 0;
        
        PrintString("GDT Entry: ");
        PrintIntHex((uint)gGdtInfo.entry);
        PrintChar('
    ');
        
        PrintString("GDT Size: ");
        PrintIntDec((uint)gGdtInfo.size);
        PrintChar('
    ');
        
        PrintString("IDT Entry: ");
        PrintIntHex((uint)gIdtInfo.entry);
        PrintChar('
    ');
        
        PrintString("IDT Size: ");
        PrintIntDec((uint)gIdtInfo.size);
        PrintChar('
    ');
        
        p.rv.cs = LDT_CODE32_SELECTOR;
        p.rv.gs = LDT_VIDEO_SELECTOR;
        p.rv.ds = LDT_DATA32_SELECTOR;
        p.rv.es = LDT_DATA32_SELECTOR;
        p.rv.fs = LDT_DATA32_SELECTOR;
        p.rv.ss = LDT_DATA32_SELECTOR;
        
        p.rv.esp = (uint)p.stack + sizeof(p.stack);
        p.rv.eip = (uint)TaskA;
        p.rv.eflags = 0x3202;
        
        p.tss.ss0 = GDT_DATA32_FLAT_SELECTOR;
        p.tss.esp0 = (uint)&p.rv + sizeof(p.rv);
        p.tss.iomb = sizeof(p.tss);
        
        SetDescValue(p.ldt + LDT_VIDEO_INDEX,  0xB8000, 0x07FFF, DA_DRWA + DA_32 + DA_DPL3);
        SetDescValue(p.ldt + LDT_CODE32_INDEX, 0x00,    0xFFFFF, DA_C + DA_32 + DA_DPL3);
        SetDescValue(p.ldt + LDT_DATA32_INDEX, 0x00,    0xFFFFF, DA_DRW + DA_32 + DA_DPL3);
        
        p.ldtSelector = GDT_TASK_LDT_SELECTOR;
        p.tssSelector = GDT_TASK_TSS_SELECTOR;
        
        SetDescValue(&gGdtInfo.entry[GDT_TASK_LDT_INDEX], (uint)&p.ldt, sizeof(p.ldt)-1, DA_LDT + DA_DPL0);
        SetDescValue(&gGdtInfo.entry[GDT_TASK_TSS_INDEX], (uint)&p.tss, sizeof(p.tss)-1, DA_386TSS + DA_DPL0);
        
        SetIntHandler(gIdtInfo.entry + 0x20, (uint)TimerHandlerEntry);
        
        InitInterrupt();
        
        EnableTimer();
        
        gCTaskAddr = &p;
        
        RunTask(gCTaskAddr);
    }
    

      

      

  • 相关阅读:
    java 显示当前的时间
    java RandomAccessFile 向文件中写入数据,怎么样不覆盖原来的数据
    NCARG 6.2.0 安装方法
    【转】在Fedora 9下用IFC安装MM5
    Linux下GrADS的安装
    我的博客园
    nyist 2 括号配对问题
    nyist 100 1的个数
    进制(堆栈)
    进制
  • 原文地址:https://www.cnblogs.com/lh03061238/p/14699121.html
Copyright © 2011-2022 走看看