@@ -132,11 +132,22 @@ static inline void arch_local_irq_disable(void)
irq_soft_mask_set(IRQ_SOFT_MASK_STD);
}
-extern void arch_local_irq_restore(unsigned long);
+extern void __arch_local_irq_enable(void);
static inline void arch_local_irq_enable(void)
{
- arch_local_irq_restore(0);
+ __irq_soft_mask_clear(IRQ_SOFT_MASK_ALL);
+ if (unlikely(local_r14 & R14_BIT_IRQ_HAPPENED_MASK))
+ __arch_local_irq_enable();
+}
+
+static inline void arch_local_irq_restore(unsigned long flags)
+{
+ __irq_soft_mask_insert(flags);
+ if (!flags) {
+ if (unlikely(local_r14 & R14_BIT_IRQ_HAPPENED_MASK))
+ __arch_local_irq_enable();
+ }
}
static inline unsigned long arch_local_irq_save(void)
@@ -97,11 +97,6 @@ extern int tau_interrupts(int);
int distribute_irqs = 1;
-static inline notrace unsigned long get_irq_happened(void)
-{
- return local_r14 & R14_BIT_IRQ_HAPPENED_MASK;
-}
-
static inline notrace int decrementer_check_overflow(void)
{
u64 now = get_tb_or_rtc();
@@ -210,19 +205,10 @@ notrace unsigned int __check_irq_replay(void)
return 0;
}
-notrace void arch_local_irq_restore(unsigned long mask)
+notrace void __arch_local_irq_enable(void)
{
- unsigned char irq_happened;
unsigned int replay;
- /* Write the new soft-enabled value */
- __irq_soft_mask_insert(mask);
- /* any bits still disabled */
- if (mask)
- return;
-
- barrier();
-
/*
* From this point onward, we can take interrupts, preempt,
* etc... unless we got hard-disabled. We check if an event
@@ -236,9 +222,6 @@ notrace void arch_local_irq_restore(unsigned long mask)
* be hard-disabled, so there is no problem, we
* cannot have preempted.
*/
- irq_happened = get_irq_happened();
- if (!irq_happened)
- return;
/*
* We need to hard disable to get a trusted value from
@@ -252,10 +235,11 @@ notrace void arch_local_irq_restore(unsigned long mask)
* (expensive) mtmsrd.
* XXX: why not test & IRQ_HARD_DIS?
*/
- if (unlikely(irq_happened != PACA_IRQ_HARD_DIS))
+ if (unlikely((local_r14 & R14_BIT_IRQ_HAPPENED_MASK) !=
+ PACA_IRQ_HARD_DIS)) {
__hard_irq_disable();
#ifdef CONFIG_PPC_IRQ_SOFT_MASK_DEBUG
- else {
+ } else {
/*
* We should already be hard disabled here. We had bugs
* where that wasn't the case so let's dbl check it and
@@ -264,8 +248,8 @@ notrace void arch_local_irq_restore(unsigned long mask)
*/
if (WARN_ON(mfmsr() & MSR_EE))
__hard_irq_disable();
- }
#endif
+ }
__irq_soft_mask_set(IRQ_SOFT_MASK_ALL);
trace_hardirqs_off();
@@ -293,7 +277,7 @@ notrace void arch_local_irq_restore(unsigned long mask)
/* Finally, let's ensure we are hard enabled */
__hard_irq_enable();
}
-EXPORT_SYMBOL(arch_local_irq_restore);
+EXPORT_SYMBOL(__arch_local_irq_enable);
/*
* This is specifically called by assembly code to re-enable interrupts