diff -Npur dbf-sos-9_5/hwcore/cpu_context.c dbf-sos-9_5-modif/hwcore/cpu_context.c --- dbf-sos-9_5/hwcore/cpu_context.c 2006-06-10 09:18:00.000000000 +0200 +++ dbf-sos-9_5-modif/hwcore/cpu_context.c 2006-06-12 18:22:41.000000000 +0200 @@ -24,6 +24,8 @@ #include #include #include +#include +#include #include #include "cpu_context.h" @@ -214,6 +216,8 @@ struct x86_tss { static struct x86_tss kernel_tss; static struct x86_tss double_fault_tss; +extern unsigned int double_fault_alternate_stack; +#define ALTERNATE_DOUBLE_FAULT_STACK_SIZE 512 sos_ret_t sos_cpu_context_subsystem_setup() { @@ -236,6 +240,17 @@ sos_ret_t sos_cpu_context_subsystem_setu kernel_tss.ss0 = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); double_fault_tss.ss0 = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); + double_fault_tss.esp0 = double_fault_alternate_stack + ALTERNATE_DOUBLE_FAULT_STACK_SIZE; + double_fault_tss.cr3 = sos_paging_get_current_PD_paddr(); + double_fault_tss.eip = (sos_vaddr_t) sos_exception_get_routine(SOS_EXCEPT_DOUBLE_FAULT); + asm ("pushf ; popl %0" + : "=r" (double_fault_tss.eflags)); + double_fault_tss.es = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); + double_fault_tss.cs = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KCODE); + double_fault_tss.ss = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); + double_fault_tss.ds = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); + double_fault_tss.fs = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); + double_fault_tss.gs = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KDATA); /* Register the double fault TSS into the GDT */ sos_gdt_register_double_fault_tss((sos_vaddr_t) &double_fault_tss); diff -Npur dbf-sos-9_5/hwcore/exception.c dbf-sos-9_5-modif/hwcore/exception.c --- dbf-sos-9_5/hwcore/exception.c 2006-01-22 12:48:00.000000000 +0100 +++ dbf-sos-9_5-modif/hwcore/exception.c 2006-06-12 18:11:21.000000000 +0200 @@ -167,7 +167,7 @@ sos_exception_handler_t sos_exception_ge /* Double fault not supported */ if (exception_number == SOS_EXCEPT_DOUBLE_FAULT) - return NULL; + return sos_exception_wrapper_array[SOS_EXCEPT_DOUBLE_FAULT]; /* Expected to be atomic */ return sos_exception_handler_array[exception_number]; diff -Npur dbf-sos-9_5/hwcore/exception_wrappers.S dbf-sos-9_5-modif/hwcore/exception_wrappers.S --- dbf-sos-9_5/hwcore/exception_wrappers.S 2006-01-22 12:48:00.000000000 +0100 +++ dbf-sos-9_5-modif/hwcore/exception_wrappers.S 2006-06-12 18:20:00.000000000 +0200 @@ -30,6 +30,8 @@ with exception.c */ .globl sos_exception_wrapper_array +.globl double_fault_alternate_stack + /** Update the kernel TSS in case we are switching to a thread in user mode in order to come back into the correct kernel stack */ .extern sos_cpu_context_update_kernel_tss diff -Npur dbf-sos-9_5/hwcore/idt.c dbf-sos-9_5-modif/hwcore/idt.c --- dbf-sos-9_5/hwcore/idt.c 2006-06-10 09:31:00.000000000 +0200 +++ dbf-sos-9_5-modif/hwcore/idt.c 2006-06-12 17:45:08.000000000 +0200 @@ -82,7 +82,14 @@ sos_ret_t sos_idt_subsystem_setup() /* Setup an empty IDTE interrupt gate, see figure 5-2 in Intel x86 doc, vol 3 */ - idte->seg_sel = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KCODE); + if (i == 8) + { + idte->seg_sel = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_DBL_FAULT_TSS); + } + else + { + idte->seg_sel = SOS_BUILD_SEGMENT_REG_VALUE(0, FALSE, SOS_SEG_KCODE); + } idte->reserved = 0; idte->flags = 0; if(i == 8) /* Double fault gate */ diff -Npur dbf-sos-9_5/sos/main.c dbf-sos-9_5-modif/sos/main.c --- dbf-sos-9_5/sos/main.c 2006-06-10 10:03:00.000000000 +0200 +++ dbf-sos-9_5-modif/sos/main.c 2006-06-13 11:50:53.000000000 +0200 @@ -201,6 +201,7 @@ void Toto(void) char Tab[] = "Message a afficher !"; I = ((I + 1) % 20); sos_x86_videomem_printf(I, 0, SOS_X86_VIDEO_FG_YELLOW | SOS_X86_VIDEO_BG_BLUE, "Toto %d %s ", I, Tab); + sos_thread_yield(); Toto(); }