Steven Seeger wrote:
> It is being called a lot. Running my test with the break in both loops
> yields approximately 60 calls to it. Half of those are called even
> before i387.c's init_fpu().

For the records: we found a solution to this FPU issue. The issue was
two-fold:
- when xenomai was preempting some linux kernel code which has called
kernel_fpu_begin, it was saving the current FPU context over the current
thread user-space FPU backup area, erasing its value previously saved by
kernel_fpu_begin();
- xenomai could preempt the linux kernel anywhere within the
kernel_fpu_begin function, which caused it to observe an incoherent
state (namely incoherent values of
current_thread_info()->status & TS_USEDFPU and TS bit in CR0).

These issues were easy to observe on Geode, because Linux on these
processors use MMX, thus kernel_fpu_begin routinely.

So, the following patch should be integrated into the I-pipe patch:

diff --git a/include/asm-x86/i387.h b/include/asm-x86/i387.h
index 56d00e3..e850fa1 100644
--- a/include/asm-x86/i387.h
+++ b/include/asm-x86/i387.h
@@ -222,11 +222,14 @@ static inline void __clear_fpu(struct task_struct
*tsk)
 static inline void kernel_fpu_begin(void)
 {
        struct thread_info *me = current_thread_info();
+       unsigned long flags;
        preempt_disable();
+       local_irq_save_hw_cond(flags);
        if (me->status & TS_USEDFPU)
                __save_init_fpu(me->task);
        else
                clts();
+       local_irq_restore_hw_cond(flags);
 }

 static inline void kernel_fpu_end(void)


And the following patch should be applied to Xenomai:

Index: include/asm-x86/bits/pod_32.h
===================================================================
--- include/asm-x86/bits/pod_32.h       (revision 4572)
+++ include/asm-x86/bits/pod_32.h       (working copy)
@@ -63,7 +63,12 @@ static inline void xnarch_leave_root(xna
        rootcb->ts_usedfpu = wrap_test_fpu_used(current) != 0;
        rootcb->cr0_ts = (read_cr0() & 8) != 0;
        /* So that xnarch_save_fpu() will operate on the right FPU area. */
-       rootcb->fpup = x86_fpustate_ptr(&rootcb->user_task->thread);
+       if (rootcb->cr0_ts || rootcb->ts_usedfpu)
+               rootcb->fpup = x86_fpustate_ptr(&rootcb->user_task->thread);
+       else
+               /* the kernel is currently using fpu in kernel-space, do not
+                  clobber the user-space fpu backup area. */
+               rootcb->fpup = &rootcb->i387;
 }

 #define xnarch_enter_root(rootcb)  do { } while(0)





-- 
                                                 Gilles.

_______________________________________________
Adeos-main mailing list
[email protected]
https://mail.gna.org/listinfo/adeos-main

Reply via email to