[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: f499ed192819b17d7e933d31d7739061a8a2927d URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=f499ed192819b17d7e933d31d7739061a8a2927d Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 42d137fca23021da0aef8222cc0146d11913464d URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=42d137fca23021da0aef8222cc0146d11913464d Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 210dd59c9160a91d3452a69db5ebb9c4e051b926 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=210dd59c9160a91d3452a69db5ebb9c4e051b926 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 866480ef10b406969298d8b1494dddf7e487dda4 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=866480ef10b406969298d8b1494dddf7e487dda4 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 4ac3f53947669ee9190e81ccd3df4d2908021f43 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=4ac3f53947669ee9190e81ccd3df4d2908021f43 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: ef9c66572512b1cb1fc7b7b8d0014e75ed695b49 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=ef9c66572512b1cb1fc7b7b8d0014e75ed695b49 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: e3da159beec50736863c3270b65b01a4392a599b URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=e3da159beec50736863c3270b65b01a4392a599b Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 6259a2ac1b83b74bcd87d5da9507c252e5f9b1f9 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=6259a2ac1b83b74bcd87d5da9507c252e5f9b1f9 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 752661710da82c8435f259a2c26281a2355d28f4 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=752661710da82c8435f259a2c26281a2355d28f4 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 71b4401fc6e01c0006fd7ccf35781e38867acc42 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=71b4401fc6e01c0006fd7ccf35781e38867acc42 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 9848284dfc20ae70f672ff3db3b8df60b331f799 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=9848284dfc20ae70f672ff3db3b8df60b331f799 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: fecda8676719b4aa39df266a3088713a10c80760 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=fecda8676719b4aa39df266a3088713a10c80760 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: fcf98c7dceea8f6a891127540e9452ac8f3d384b URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=fcf98c7dceea8f6a891127540e9452ac8f3d384b Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 38d109a137a3cd36d024051c04bfafb0970dedd1 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=38d109a137a3cd36d024051c04bfafb0970dedd1 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 629c602d67433e9220881c83326eb35754f6ac56 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=629c602d67433e9220881c83326eb35754f6ac56 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: 29bf6e13adbd7d15e4be7f20aaac1d7c6fabee6b URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=29bf6e13adbd7d15e4be7f20aaac1d7c6fabee6b Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,
[Xenomai-git] Gilles Chanteperdrix : cobalt/arm64: attempt at fixing fpu switch
Module: xenomai-3 Branch: next Commit: a8682f4883728fee0b19c87814cce50bad6adfd7 URL: http://git.xenomai.org/?p=xenomai-3.git;a=commit;h=a8682f4883728fee0b19c87814cce50bad6adfd7 Author: Gilles ChanteperdrixDate: Fri Oct 30 17:14:00 2015 +0100 cobalt/arm64: attempt at fixing fpu switch Return to eager switching, since user-space applications use FPU registers even when not using the FPU, but use an auxiliary backup area when the "TIF_FOREIGN_FPSTATE" bit is set, in order to avoid clobbering the saved FPU state. --- .../cobalt/arch/arm64/include/asm/xenomai/thread.h | 14 +++-- kernel/cobalt/arch/arm64/thread.c | 54 +--- 2 files changed, 25 insertions(+), 43 deletions(-) diff --git a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h index 9055e58..4b247ac 100644 --- a/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h +++ b/kernel/cobalt/arch/arm64/include/asm/xenomai/thread.h @@ -24,6 +24,7 @@ struct xnarchtcb { struct xntcb core; #ifdef CONFIG_XENO_ARCH_FPU + struct fpsimd_state xnfpsimd_state; struct fpsimd_state *fpup; #define xnarch_fpu_ptr(tcb) ((tcb)->fpup) #endif @@ -67,7 +68,10 @@ static inline void xnarch_init_root_tcb(struct xnthread *thread) void xnarch_init_shadow_tcb(struct xnthread *thread); -int xnarch_fault_fpu_p(struct ipipe_trap_data *d); +static inline int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +{ + return xnarch_fault_trap(d) == IPIPE_TRAP_FPU_ACC; +} void xnarch_leave_root(struct xnthread *root); @@ -75,8 +79,12 @@ void xnarch_save_fpu(struct xnthread *thread); void xnarch_switch_fpu(struct xnthread *from, struct xnthread *thread); -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d); +static inline int +xnarch_handle_fpu_fault(struct xnthread *from, + struct xnthread *to, struct ipipe_trap_data *d) +{ + return 0; +} #else /* !CONFIG_XENO_ARCH_FPU */ diff --git a/kernel/cobalt/arch/arm64/thread.c b/kernel/cobalt/arch/arm64/thread.c index 2238751..b987e09 100644 --- a/kernel/cobalt/arch/arm64/thread.c +++ b/kernel/cobalt/arch/arm64/thread.c @@ -6,6 +6,7 @@ * * ARM64 port * Copyright (C) 2015 Dmitriy Cherkasov + * Copyright (C) 2015 Gilles Chanteperdrix * * Xenomai is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by @@ -41,7 +42,7 @@ static inline unsigned long get_cpacr(void) { unsigned long result; - __asm__ __volatile__("mrs %0, cpacr_el1": "=r"(result)); + __asm__ ("mrs %0, cpacr_el1": "=r"(result)); return result; } @@ -53,21 +54,20 @@ static inline void set_cpacr(long val) : /* */ : "r"(val)); } -static void enable_fpsimd(void) +static inline void enable_fpsimd(void) { - unsigned long cpacr = get_cpacr(); - cpacr |= FPSIMD_EN; - set_cpacr(cpacr); + set_cpacr(get_cpacr() | FPSIMD_EN); } -int xnarch_fault_fpu_p(struct ipipe_trap_data *d) +static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *rootcb) { - return (d->exception == IPIPE_TRAP_FPU_ACC); -} + struct task_struct *curr = rootcb->core.host_task; -static inline struct fpsimd_state *get_fpu_owner(struct xnarchtcb *tcb) -{ - return &(tcb->core.tsp->fpsimd_state); + if (test_ti_thread_flag(task_thread_info(curr), TIF_FOREIGN_FPSTATE)) + /* Foreign fpu state, use auxiliary backup area */ + return >xnfpsimd_state; + + return >thread.fpsimd_state; } void xnarch_leave_root(struct xnthread *root) @@ -76,13 +76,6 @@ void xnarch_leave_root(struct xnthread *root) rootcb->fpup = get_fpu_owner(rootcb); } -void xnarch_save_fpu(struct xnthread *thread) -{ - struct xnarchtcb *tcb = &(thread->tcb); - if (xnarch_fpu_ptr(tcb)) - fpsimd_save_state(tcb->fpup); -} - void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) { struct fpsimd_state *const from_fpup = from ? from->tcb.fpup : NULL; @@ -93,35 +86,16 @@ void xnarch_switch_fpu(struct xnthread *from, struct xnthread *to) if (from_fpup == to_fpup) return; - if (from_fpup) - fpsimd_save_state(from_fpup); + fpsimd_save_state(from_fpup); fpsimd_load_state(to_fpup); -} - -int xnarch_handle_fpu_fault(struct xnthread *from, - struct xnthread *to, struct ipipe_trap_data *d) -{ - spl_t s; - - /* FPU should already be enabled for XNFPU tasks. */ - if (xnthread_test_state(to, XNFPU)) - BUG(); - - xnlock_get_irqsave(, s); - xnthread_set_state(to, XNFPU); - xnlock_put_irqrestore(, s); - - xnarch_switch_fpu(from,