[Kos-dev] double fault fonctionnel !

Christophe Avoinne (Club-Internet) kos-dev@enix.org
Fri, 6 Apr 2001 22:48:36 +0200


----- Original Message -----
From: "Thomas Petazzoni" <thomas.petazzoni@ifrance.com>
To: <kos-dev@enix.org>
Sent: Thursday, April 05, 2001 5:55 PM
Subject: Re: [Kos-dev] double fault fonctionnel !


>
> voici le code de notre thread de test :
>
> void test_lost_of_irq(void *data)
> {
>   asm("0: movl $0xDEADBEEF, %esp\n\t
>        hlt\n\t
>        jmp 0b");
> }
>
>
> voici le code de notre handler de double fault, la partie
> interessante...
>
>   printk("coucou generated by task gate handler\n");
>
>   asm("movl %%esp, %0":"=r"(esp0));
>   __bochs_printk("ESP seems to be 0x%x\n", esp0);
>   asm("pushf\n
>        pop %%eax\n
>        movl %%eax, %0":"=r"(esp0));
>   __bochs_printk("Real EFLAGS is 0x%x\n", esp0);
>
>   dump_cpu_context(cpu_context);
>   printk("Eflags is 0x%x (esp=0x%x)\n", cpu_context->eflags,
> (unsigned)cpu_context);
>
>   double_fault_tss = get_double_fault_tss();
>   system_tss = get_system_tss();
>   __bochs_printk("old esp system tss addr is 0x%x\n", system_tss->esp);
>
>
>   new_stack_addr = get_physical_page();
>   new_stack_addr += PAGE_SIZE-1;
>

Euh évite ça, tu n'as pas une infinté de pages physiques à allouer !
j'aimerais mieux que tu le places en "else { ... }" juste après le "if" qui
suit :

>
>   show_all_thread_info();
>   if (system_tss->esp == 0xDEADBEEF)
>     {
>       *(screen +1) = 6;
>       (*screen)++;
>       __bochs_printk("irq lost.. or not ?\n");
>        system_tss->esp =  double_fault_tss->esp0 - 512;
>        system_tss->eip++; // saute l'instruction "hlt"
>        return cpu_context;
>     }
>

>
> > 1°) la barre tournante du timer 0 continue de tourner : l'IRQ est bien
> > exécuté après ou pendant un #DF ! ca signifie que le signal IRQ a été
> > maintenu jusqu'à ce qu'il puisse avoir lieu.
> > 2°) la barre tournante du timer 0 ne bouge plus : les IRQ sont
> > irrémédiablement perdus. Il faut envisager un système plus compliqué
pour
> > compenser.
>
> voici ce qui se passe : le double fault est bien execute une fois, et le
> caractere est bien incremente a l'ecran (*screen)++; ainsi que le
> message affiche via bochs_printk. mais apres cette premiere fois, plus
> rien ne se passe... les twiddles ne tournent plus :(((
>

Humm... ça signifie que tu n'appelles qu'une fois le #DF ?! pas bon ça ! le
but est qu'il appelle justement le #DF pour chaque IRQ0 !

Cela dit, comme le démasquage des interuptions n'est pas automatique
(nécessité de faire : "mov $0x20h,%al; out %al,$0x20"), on ne peut pas avoir
plusieurs interruptions timer 0. D'où peut-être une deuxième exécution du
"hlt" qui lui tourne à l'infini à cause du fait que l'on n'a libéré pas le
premier IRQ 0. A mon avis c'est sûrement ça !

Rajoute donc un genre : " mov $0x20,%al; out %al,$0x20 " dans le " if " du
handler #DF. Ca devrait débloquer la situation.

> bref d'apres les premiers tests, il va falloir tester si un IRQ a genere
> le double fault... et reparer ce qu'il faut si besoin est.
>

Trop tôt pour conclure ça.

> Hlide au secours ...

:)

Hlide.