Linux init/main.c 初始化中硬件中断向量初始化 trap_init()


/init/main.c部分代码

  1. void main(void)     /* This really IS void, no error here. */  
  2. {           /* The startup routine assumes (well, ...) this */  
  3. /*  
  4.  * Interrupts are still disabled. Do necessary setups, then  
  5.  * enable them  
  6.  */  
  7.     ROOT_DEV = ORIG_ROOT_DEV;   
  8.     drive_info = DRIVE_INFO;   
  9.     memory_end = (1<<20) + (EXT_MEM_K<<10);   
  10.     memory_end &= 0xfffff000;   
  11.     if (memory_end > 16*1024*1024)   
  12.         memory_end = 16*1024*1024;   
  13.     if (memory_end > 12*1024*1024)    
  14.         buffer_memory_end = 4*1024*1024;   
  15.     else if (memory_end > 6*1024*1024)   
  16.         buffer_memory_end = 2*1024*1024;   
  17.     else  
  18.         buffer_memory_end = 1*1024*1024;   
  19.     main_memory_start = buffer_memory_end;   
  20. #ifdef RAMDISK   
  21.     main_memory_start += rd_init(main_memory_start, RAMDISK*1024);   
  22. #endif   
  23.     mem_init(main_memory_start,memory_end);   
  24.     trap_init();   
  25.     blk_dev_init();   
  26.     chr_dev_init();   
  27.     tty_init();   
  28.     time_init();   
  29.     sched_init();   
  30.     buffer_init(buffer_memory_end);   
  31.     hd_init();   
  32.     floppy_init();   
  33.     sti();   
  34.     move_to_user_mode();   
  35.     if (!fork()) {      /* we count on this going ok */  
  36.         init();   
  37.     }  

trap_init()函数位置  /kernel/traps.c

  1. void trap_init(void)   
  2. {   
  3.     int i;   
  4. //设置系统的硬件中断 中断位于kernel/asm.s 或 system_call.s   
  5.     set_trap_gate(0,÷_error);//0中断,位于/kernel/asm.s 19行   
  6.     set_trap_gate(1,&debug);   
  7.     set_trap_gate(2,&nmi);   
  8.     set_system_gate(3,&int3);   /* int3-5 can be called from all */  
  9.     set_system_gate(4,&overflow);   
  10.     set_system_gate(5,&bounds);   
  11.     set_trap_gate(6,&invalid_op);   
  12.     set_trap_gate(7,&device_not_available);   
  13.     set_trap_gate(8,&double_fault);   
  14.     set_trap_gate(9,&coprocessor_segment_overrun);   
  15.     set_trap_gate(10,&invalid_TSS);   
  16.     set_trap_gate(11,&segment_not_present);   
  17.     set_trap_gate(12,&stack_segment);   
  18.     set_trap_gate(13,&general_protection);   
  19.     set_trap_gate(14,&page_fault);   
  20.     set_trap_gate(15,&reserved);   
  21.     set_trap_gate(16,&coprocessor_error);   
  22.     for (i=17;i<48;i++)   
  23.         set_trap_gate(i,&reserved);   
  24.     set_trap_gate(45,&irq13);   
  25.     outb_p(inb_p(0x21)&0xfb,0x21);   
  26.     outb(inb_p(0xA1)&0xdf,0xA1);   
  27.     set_trap_gate(39,¶llel_interrupt);   
  28. }  

set_trap_gate()函数位于/include/asm/system.h

  1. //n为中断向量号,addr中断程序的偏移地址   
  2. //&idt[n]对应中断号在中断描述符表中的偏移值   
  3. //中断描述符的类型是 14,特权级是 0。   
  4. #define set_trap_gate(n,addr) \   
  5.     _set_gate(&idt[n],15,0,addr)   
  6. //设置中断宏函数   
  7. //参数:gate_addr -描述符地址;type -描述符中类型域值;dpl -描述符特权层值;addr -偏移地址   
  8. // %0 - (由 dpl,type 组合成的类型标志字);%1 - (描述符低 4 字节地址);   
  9. // %2 - (描述符高 4 字节地址);%3 - edx(程序偏移地址 addr);%4 - eax(高字中含有段选择符)。   
  10. #define _set_gate(gate_addr,type,dpl,addr) \   
  11. __asm__ ("movw %%dx,%%ax\n\t" \   
  12.     "movw %0,%%dx\n\t" \   
  13.     "movl %%eax,%1\n\t" \   
  14.     "movl %%edx,%2" \   
  15.     : \   
  16.     : "i" ((short) (0x8000+(dpl<<13)+(type<<8))), \   
  17.     "o" (*((char *) (gate_addr))), \   
  18.     "o" (*(4+(char *) (gate_addr))), \   
  19.     "d" ((char *) (addr)),"a" (0x00080000))  

相关内容