Title: [9719] trunk/arch/blackfin/mach-common: Blackfin/ipipe: fix deferred pipeline sync for the root stage
- Revision
- 9719
- Author
- vapier
- Date
- 2011-03-17 02:19:43 -0400 (Thu, 17 Mar 2011)
Log Message
Blackfin/ipipe: fix deferred pipeline sync for the root stage
From: Philippe Gerum <[email protected]>
This patch makes sure to sync the pipeline for the root stage only
from the outer interrupt level, when resuming kernel code after an
interrupt.
This fixes a bug causing EVT15 to be spuriously popped off upon nested
interrupts, which in turn would cause the preempted kernel code to
resume without supervisor privileges.
Modified Paths
Diff
Modified: trunk/arch/blackfin/mach-common/entry.S (9718 => 9719)
--- trunk/arch/blackfin/mach-common/entry.S 2011-03-17 06:19:21 UTC (rev 9718)
+++ trunk/arch/blackfin/mach-common/entry.S 2011-03-17 06:19:43 UTC (rev 9719)
@@ -952,8 +952,17 @@
#ifdef CONFIG_IPIPE
_resume_kernel_from_int:
+ r1 = LO(~0x8000) (Z);
+ r1 = r0 & r1;
+ r0 = 1;
+ r0 = r1 - r0;
+ r2 = r1 & r0;
+ cc = r2 == 0;
+ /* Sync the root stage only from the outer interrupt level. */
+ if !cc jump .Lnosync;
r0.l = ___ipipe_sync_root;
r0.h = ___ipipe_sync_root;
+ [--sp] = reti;
[--sp] = rets;
[--sp] = ( r7:4, p5:3 );
SP += -12;
@@ -961,6 +970,8 @@
SP += 12;
( r7:4, p5:3 ) = [sp++];
rets = [sp++];
+ reti = [sp++];
+.Lnosync:
rts
#elif defined(CONFIG_PREEMPT)
Modified: trunk/arch/blackfin/mach-common/interrupt.S (9718 => 9719)
--- trunk/arch/blackfin/mach-common/interrupt.S 2011-03-17 06:19:21 UTC (rev 9718)
+++ trunk/arch/blackfin/mach-common/interrupt.S 2011-03-17 06:19:43 UTC (rev 9719)
@@ -274,16 +274,16 @@
* level to EVT14 to prepare the caller for a normal interrupt
* return through RTI.
*
- * We currently use this facility in two occasions:
+ * We currently use this feature in two occasions:
*
- * - to branch to __ipipe_irq_tail_hook as requested by a high
+ * - before branching to __ipipe_irq_tail_hook as requested by a high
* priority domain after the pipeline delivered an interrupt,
* e.g. such as Xenomai, in order to start its rescheduling
* procedure, since we may not switch tasks when IRQ levels are
* nested on the Blackfin, so we have to fake an interrupt return
* so that we may reschedule immediately.
*
- * - to branch to sync_root_irqs, in order to play any interrupt
+ * - before branching to __ipipe_sync_root(), in order to play any interrupt
* pending for the root domain (i.e. the Linux kernel). This lowers
* the core priority level enough so that Linux IRQ handlers may
* never delay interrupts handled by high priority domains; we defer
_______________________________________________
Linux-kernel-commits mailing list
[email protected]
https://blackfin.uclinux.org/mailman/listinfo/linux-kernel-commits