Module: xenomai-rpm Branch: for-upstream Commit: e144a8c61a6c30febdde5c3ce4bf43a16b13c091 URL: http://git.xenomai.org/?p=xenomai-rpm.git;a=commit;h=e144a8c61a6c30febdde5c3ce4bf43a16b13c091
Author: Philippe Gerum <[email protected]> Date: Thu Nov 11 19:18:42 2010 +0100 powerpc: upgrade I-pipe support to 2.6.35.7-powerpc-2.12-01 --- ... => adeos-ipipe-2.6.35.7-powerpc-2.12-01.patch} | 164 ++++++++++++++------ 1 files changed, 113 insertions(+), 51 deletions(-) diff --git a/ksrc/arch/powerpc/patches/adeos-ipipe-2.6.35.7-powerpc-2.12-00.patch b/ksrc/arch/powerpc/patches/adeos-ipipe-2.6.35.7-powerpc-2.12-01.patch similarity index 99% rename from ksrc/arch/powerpc/patches/adeos-ipipe-2.6.35.7-powerpc-2.12-00.patch rename to ksrc/arch/powerpc/patches/adeos-ipipe-2.6.35.7-powerpc-2.12-01.patch index 68b4458..8200b09 100644 --- a/ksrc/arch/powerpc/patches/adeos-ipipe-2.6.35.7-powerpc-2.12-00.patch +++ b/ksrc/arch/powerpc/patches/adeos-ipipe-2.6.35.7-powerpc-2.12-01.patch @@ -265,10 +265,10 @@ index bd100fc..8fa1901 100644 * or should we not care like we do now ? --BenH. diff --git a/arch/powerpc/include/asm/ipipe.h b/arch/powerpc/include/asm/ipipe.h new file mode 100644 -index 0000000..d06ec57 +index 0000000..9a63df2 --- /dev/null +++ b/arch/powerpc/include/asm/ipipe.h -@@ -0,0 +1,248 @@ +@@ -0,0 +1,245 @@ +/* + * include/asm-powerpc/ipipe.h + * @@ -316,13 +316,16 @@ index 0000000..d06ec57 +#include <asm/paca.h> +#endif + -+#define IPIPE_ARCH_STRING "2.12-00" ++#define IPIPE_ARCH_STRING "2.12-01" +#define IPIPE_MAJOR_NUMBER 2 +#define IPIPE_MINOR_NUMBER 12 -+#define IPIPE_PATCH_NUMBER 0 ++#define IPIPE_PATCH_NUMBER 1 + +#ifdef CONFIG_IPIPE_WANT_PREEMPTIBLE_SWITCH + ++struct mm; ++DECLARE_PER_CPU(struct mm_struct *, ipipe_active_mm); ++ +#define prepare_arch_switch(next) \ + do { \ + local_irq_enable_hw(); \ @@ -367,25 +370,19 @@ index 0000000..d06ec57 +extern cpumask_t __ipipe_dbrk_pending; +#endif + -+#ifdef CONFIG_IPIPE_WANT_PREEMPTIBLE_SWITCH -+struct mm; -+DECLARE_PER_CPU(struct mm_struct *, ipipe_active_mm); +#define ipipe_mm_switch_protect(flags) \ + do { \ -+ preempt_disable(); \ -+ per_cpu(ipipe_active_mm, smp_processor_id()) = NULL; \ ++ __mmactivate_head(); \ + barrier(); \ + (void)(flags); \ + } while(0) ++ +#define ipipe_mm_switch_unprotect(flags) \ + do { \ -+ preempt_enable(); \ ++ barrier(); \ ++ __mmactivate_tail(); \ + (void)(flags); \ + } while(0) -+#else -+#define ipipe_mm_switch_protect(flags) local_irq_save_hw_cond(flags) -+#define ipipe_mm_switch_unprotect(flags) local_irq_restore_hw_cond(flags) -+#endif + +#define __ipipe_hrtimer_irq IPIPE_TIMER_VIRQ +#define __ipipe_hrtimer_freq ppc_tb_freq @@ -933,17 +930,93 @@ index 5f68ecf..5059e59 100644 /* * Most of the CPU's IRQ-state tracing is done from assembly code; we diff --git a/arch/powerpc/include/asm/mmu_context.h b/arch/powerpc/include/asm/mmu_context.h -index 81fb412..a0a2bef 100644 +index 81fb412..cd526ae 100644 --- a/arch/powerpc/include/asm/mmu_context.h +++ b/arch/powerpc/include/asm/mmu_context.h -@@ -32,15 +32,38 @@ extern void __destroy_context(unsigned long context_id); +@@ -32,15 +32,112 @@ extern void __destroy_context(unsigned long context_id); extern void mmu_context_init(void); #endif ++#ifdef CONFIG_IPIPE_WANT_PREEMPTIBLE_SWITCH ++ ++static inline void __mmswitch_head(int cpu) ++{ ++ /* ++ * mmu_context_nohash in SMP mode is tracking an activity ++ * counter into the mm struct. Therefore, we make sure the ++ * kernel always sees the ipipe_active_mm update and the ++ * actual switch as a single atomic operation. Since the ++ * related code already requires to hard disable irqs all ++ * through the switch, there is no additional penalty anyway. ++ */ ++#if defined(CONFIG_PPC_MMU_NOHASH) && defined(CONFIG_SMP) ++ local_irq_disable_hw(); ++#endif ++ per_cpu(ipipe_active_mm, cpu) = NULL; ++} ++ ++static inline void __mmswitch_tail(struct mm_struct *next, int cpu) ++{ ++ per_cpu(ipipe_active_mm, cpu) = next; ++#if defined(CONFIG_PPC_MMU_NOHASH) && defined(CONFIG_SMP) ++ local_irq_enable_hw(); ++#endif ++} ++ ++static inline void __mmactivate_head(void) ++{ ++#if defined(CONFIG_PPC_MMU_NOHASH) && defined(CONFIG_SMP) ++ local_irq_disable_hw(); ++#else ++ preempt_disable(); ++#endif ++ per_cpu(ipipe_active_mm, smp_processor_id()) = NULL; ++} ++ ++static inline void __mmactivate_tail(void) ++{ ++#if defined(CONFIG_PPC_MMU_NOHASH) && defined(CONFIG_SMP) ++ local_irq_enable_hw(); ++#else ++ preempt_enable(); ++#endif ++} ++ ++#else /* !IPIPE_WANT_PREEMPTIBLE_SWITCH */ ++ ++static inline void __mmswitch_head(int cpu) ++{ ++#ifdef CONFIG_IPIPE_DEBUG_INTERNAL ++ WARN_ON_ONCE(!irqs_disabled_hw()); ++#endif ++} ++ ++static inline void __mmswitch_tail(struct mm_struct *next, int cpu) ++{ ++} ++ ++static inline void __mmactivate_head(void) ++{ ++#ifdef CONFIG_IPIPE_DEBUG_INTERNAL ++ WARN_ON_ONCE(irqs_disabled_hw()); ++#endif ++ local_irq_disable_hw_cond(); ++} ++ ++static inline void __mmactivate_tail(void) ++{ ++ local_irq_enable_hw_cond(); ++} ++ ++#endif /* !IPIPE_WANT_PREEMPTIBLE_SWITCH */ ++ +static inline void __do_switch_mm(struct mm_struct *prev, struct mm_struct *next, -+ struct task_struct *tsk) ++ struct task_struct *tsk, int cpu) +{ ++ __mmswitch_head(cpu); ++ barrier(); +#ifdef CONFIG_PPC_STD_MMU_64 ++ /* mm state is undefined. */ + if (cpu_has_feature(CPU_FTR_SLB)) + switch_slb(tsk, next); + else @@ -952,6 +1025,8 @@ index 81fb412..a0a2bef 100644 + /* Out of line for now */ + switch_mmu_context(prev, next); +#endif ++ barrier(); ++ __mmswitch_tail(next, cpu); +} + /* @@ -969,17 +1044,13 @@ index 81fb412..a0a2bef 100644 { + int cpu = ipipe_processor_id(); + -+#if defined(CONFIG_IPIPE_DEBUG_INTERNAL) && \ -+ !defined(CONFIG_IPIPE_WANT_PREEMPTIBLE_SWITCH) -+ WARN_ON_ONCE(!irqs_disabled_hw()); -+#endif /* Mark this context has been used on the new CPU */ - cpumask_set_cpu(smp_processor_id(), mm_cpumask(next)); + cpumask_set_cpu(cpu, mm_cpumask(next)); /* 32-bit keeps track of the current PGDIR in the thread struct */ #ifdef CONFIG_PPC32 -@@ -66,16 +89,34 @@ static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next, +@@ -66,16 +163,29 @@ static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next, /* The actual HW switching method differs between the various * sub architectures. */ @@ -994,18 +1065,13 @@ index 81fb412..a0a2bef 100644 -#endif +#ifdef CONFIG_IPIPE_WANT_PREEMPTIBLE_SWITCH + if (ipipe_root_domain_p) { -+ do { -+ /* mm state is undefined. */ -+ per_cpu(ipipe_active_mm, cpu) = NULL; -+ barrier(); -+ __do_switch_mm(prev, next, tsk); -+ barrier(); -+ per_cpu(ipipe_active_mm, cpu) = next; -+ } while (test_and_clear_thread_flag(TIF_MMSWITCH_INT)); ++ do ++ __do_switch_mm(prev, next, tsk, cpu); ++ while (test_and_clear_thread_flag(TIF_MMSWITCH_INT)); + return; + } /* Falldown wanted for non-root context. */ +#endif /* CONFIG_IPIPE_WANT_PREEMPTIBLE_SWITCH */ -+ __do_switch_mm(prev, next, tsk); ++ __do_switch_mm(prev, next, tsk, cpu); +} +static inline void switch_mm(struct mm_struct *prev, struct mm_struct *next, @@ -1023,7 +1089,7 @@ index 81fb412..a0a2bef 100644 } #define deactivate_mm(tsk,mm) do { } while (0) -@@ -89,7 +130,7 @@ static inline void activate_mm(struct mm_struct *prev, struct mm_struct *next) +@@ -89,7 +199,7 @@ static inline void activate_mm(struct mm_struct *prev, struct mm_struct *next) unsigned long flags; local_irq_save(flags); @@ -4032,7 +4098,7 @@ index 09dffe6..1637d97 100644 #ifdef CONFIG_PPC_SUBPAGE_PROT if (rc == -2) diff --git a/arch/powerpc/mm/mmu_context_nohash.c b/arch/powerpc/mm/mmu_context_nohash.c -index ddfd7ad..a69692a 100644 +index ddfd7ad..4bfd9ad 100644 --- a/arch/powerpc/mm/mmu_context_nohash.c +++ b/arch/powerpc/mm/mmu_context_nohash.c @@ -57,7 +57,7 @@ static unsigned int next_context, nr_free_contexts; @@ -4053,27 +4119,23 @@ index ddfd7ad..a69692a 100644 /* Pick up the victim mm */ mm = context_mm[id]; -@@ -191,9 +191,10 @@ static void context_check_map(void) { } +@@ -191,7 +191,7 @@ static void context_check_map(void) { } void switch_mmu_context(struct mm_struct *prev, struct mm_struct *next) { - unsigned int i, id, cpu = smp_processor_id(); -- unsigned long *map; + unsigned int i, id, cpu = ipipe_processor_id(); -+ unsigned long *map, flags; + unsigned long *map; -+ local_irq_save_hw_cond(flags); /* No lockless fast path .. yet */ - raw_spin_lock(&context_lock); +@@ -201,6 +201,7 @@ void switch_mmu_context(struct mm_struct *prev, struct mm_struct *next) + cpu, next, next->context.active, next->context.id); -@@ -280,6 +281,7 @@ void switch_mmu_context(struct mm_struct *prev, struct mm_struct *next) - pr_hardcont(" -> %d\n", id); - set_context(id, next->pgd); - raw_spin_unlock(&context_lock); -+ local_irq_restore_hw_cond(flags); - } - - /* + #ifdef CONFIG_SMP ++ WARN_ON(!irqs_disabled_hw()); + /* Mark us active and the previous one not anymore */ + next->context.active++; + if (prev) { diff --git a/arch/powerpc/mm/slb.c b/arch/powerpc/mm/slb.c index 1d98ecc..9316b19 100644 --- a/arch/powerpc/mm/slb.c @@ -5399,7 +5461,7 @@ index d5b3876..92b7abe 100644 #endif /* LINUX_HARDIRQ_H */ diff --git a/include/linux/ipipe.h b/include/linux/ipipe.h new file mode 100644 -index 0000000..4e04013 +index 0000000..854f132 --- /dev/null +++ b/include/linux/ipipe.h @@ -0,0 +1,780 @@ @@ -5681,7 +5743,7 @@ index 0000000..4e04013 +#endif + +#ifndef __ipipe_run_irqtail -+#define __ipipe_run_irqtail() do { } while(0) ++#define __ipipe_run_irqtail(irq) do { } while(0) +#endif + +#define __ipipe_pipeline_head_p(ipd) (&(ipd)->p_link == __ipipe_pipeline.next) @@ -7605,7 +7667,7 @@ index 0000000..6257dfa +obj-$(CONFIG_IPIPE_TRACE) += tracer.o diff --git a/kernel/ipipe/core.c b/kernel/ipipe/core.c new file mode 100644 -index 0000000..7f1df1f +index 0000000..9d025b2 --- /dev/null +++ b/kernel/ipipe/core.c @@ -0,0 +1,2149 @@ @@ -8783,7 +8845,7 @@ index 0000000..7f1df1f + __set_bit(IPIPE_STALL_FLAG, &p->status); + barrier(); + head->irqs[irq].handler(irq, head->irqs[irq].cookie); /* Call the ISR. */ -+ __ipipe_run_irqtail(); ++ __ipipe_run_irqtail(irq); + barrier(); + __clear_bit(IPIPE_STALL_FLAG, &p->status); + @@ -8844,7 +8906,7 @@ index 0000000..7f1df1f + + if (likely(ipd != ipipe_root_domain)) { + ipd->irqs[irq].handler(irq, ipd->irqs[irq].cookie); -+ __ipipe_run_irqtail(); ++ __ipipe_run_irqtail(irq); + } else if (ipipe_virtual_irq_p(irq)) { + irq_enter(); + __ipipe_do_root_virq(ipd, irq); _______________________________________________ Xenomai-git mailing list [email protected] https://mail.gna.org/listinfo/xenomai-git
