8 %include "sconst.inc" 9 10 _NR_get_ticks equ 0 ; 要跟 global.c 中 sys_call_table 的定义相对应! 11 INT_VECTOR_SYS_CALL equ 0x90 12 13 14 ; 导出符号 15 global get_ticks 16 17 18 bits 32 19 [section .text] 20 21 ; ==================================================================================== 22 ; get_ticks 23 ; ==================================================================================== 24 get_ticks: 25 mov eax, _NR_get_ticks;用eax传递系统调用参数 26 int INT_VECTOR_SYS_CALL 27 ret
61 PUBLIC void init_prot()
62 {
63 init_8259A();
64
65 // 全部初始化成中断门(没有陷阱门)
......
98 init_idt_desc(INT_VECTOR_SYS_CALL, DA_386IGate, sys_call, PRIVILEGE_USER);
}因为我们使用了eax来传递系统调用的参数,但是eax又被用于保存进程上下文中的运算,所以我们修改save函数,其中的eax换成esi:
save:
...
325 mov esi, esp ; esi = 进程表起始地址
326
327 inc dword [k_reenter] ; k_reenter++;
328 cmp dword [k_reenter], 0 ; if(k_reenter ==0)
329 jne .1 ; {
330 mov esp, StackTop ; mov esp, StackTop <-- 切换到内核栈
331 push restart ; push restart
332 jmp [esi + RETADR - P_STACKBASE] ; return;
333 .1: ; } else { 已经在内核栈,不需要再切换
334 push restart_reenter ; push restart_reenter
335 jmp [esi + RETADR - P_STACKBASE] ; return;
336 ; }
...
ret
342 sys_call: 343 call save 344 345 sti 346 347 call [sys_call_table + eax * 4] 348 mov [esi + EAXREG - P_STACKBASE], eax 349 350 cli 351 352 ret
28 PUBLIC t_sys_call sys_call_table[NR_SYS_CALL] = {sys_get_ticks};
23 typedef void* t_sys_call;注意,这是一个指针,不是一个函数指针45 PUBLIC int sys_get_ticks()
46 {
disp_str("+");
47 return ticks;
48 }47 /* proc.c */ 48 PUBLIC int sys_get_ticks(); /* t_sys_call */ 49 50 /* syscall.asm */ 51 PUBLIC void sys_call(); /* t_pf_int_handler */ 52 PUBLIC int get_ticks();我们来理清调用关系:get_tricks >>sys_call(eax=!!) >> sys_get_tricks
70 void TestA()
71 {
72 while(1){
get_tricks();
73 disp_str("A");
74 disp_int(i++);
75 disp_str(".");
76 delay(1);
77 }
78 } 然后编译运行即可。
59 /* 初始化 8253 PIT */ 60 out_byte(TIMER_MODE, RATE_GENERATOR); 61 out_byte(TIMER0, (t_8) (TIMER_FREQ/HZ) ); 62 out_byte(TIMER0, (t_8) ((TIMER_FREQ/HZ) >> 8)); 63 /* 初始化 8253 PIT 完毕 */
40 PUBLIC void milli_delay(int milli_sec)
41 {
42 int t = get_ticks();
43
44 while(((get_ticks() - t) * 1000 / HZ) < milli_sec) {}
45 }
76 void TestA()
77 {
78 while(1){
79 disp_str("A");
80 disp_int(get_ticks());
81 disp_str(".");
82 milli_delay(1000);
83 }
84 }《自己动手写操作系统》 第六章 系统调用的实现,布布扣,bubuko.com
原文:http://blog.csdn.net/trochiluses/article/details/21988205