• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * IRQ flags handling
3  *
4  * This file gets included from lowlevel asm headers too, to provide
5  * wrapped versions of the local_irq_*() APIs, based on the
6  * raw_local_irq_*() functions from the lowlevel headers.
7  */
8 #ifndef _ASM_IRQFLAGS_H
9 #define _ASM_IRQFLAGS_H
10 
11 #ifndef __ASSEMBLY__
12 
13 #include <asm/core_reg.h>
14 #include <asm/metag_regs.h>
15 
16 #define INTS_OFF_MASK TXSTATI_BGNDHALT_BIT
17 
18 #ifdef CONFIG_SMP
19 extern unsigned int get_trigger_mask(void);
20 #else
21 
22 extern unsigned int global_trigger_mask;
23 
get_trigger_mask(void)24 static inline unsigned int get_trigger_mask(void)
25 {
26 	return global_trigger_mask;
27 }
28 #endif
29 
arch_local_save_flags(void)30 static inline unsigned long arch_local_save_flags(void)
31 {
32 	return __core_reg_get(TXMASKI);
33 }
34 
arch_irqs_disabled_flags(unsigned long flags)35 static inline int arch_irqs_disabled_flags(unsigned long flags)
36 {
37 	return (flags & ~INTS_OFF_MASK) == 0;
38 }
39 
arch_irqs_disabled(void)40 static inline int arch_irqs_disabled(void)
41 {
42 	unsigned long flags = arch_local_save_flags();
43 
44 	return arch_irqs_disabled_flags(flags);
45 }
46 
__irqs_disabled(void)47 static inline unsigned long __irqs_disabled(void)
48 {
49 	/*
50 	 * We shouldn't enable exceptions if they are not already
51 	 * enabled. This is required for chancalls to work correctly.
52 	 */
53 	return arch_local_save_flags() & INTS_OFF_MASK;
54 }
55 
56 /*
57  * For spinlocks, etc:
58  */
arch_local_irq_save(void)59 static inline unsigned long arch_local_irq_save(void)
60 {
61 	unsigned long flags = __irqs_disabled();
62 
63 	asm volatile("SWAP %0,TXMASKI\n" : "=r" (flags) : "0" (flags)
64 		     : "memory");
65 
66 	return flags;
67 }
68 
arch_local_irq_restore(unsigned long flags)69 static inline void arch_local_irq_restore(unsigned long flags)
70 {
71 	asm volatile("MOV TXMASKI,%0\n" : : "r" (flags) : "memory");
72 }
73 
arch_local_irq_disable(void)74 static inline void arch_local_irq_disable(void)
75 {
76 	unsigned long flags = __irqs_disabled();
77 
78 	asm volatile("MOV TXMASKI,%0\n" : : "r" (flags) : "memory");
79 }
80 
81 #ifdef CONFIG_SMP
82 /* Avoid circular include dependencies through <linux/preempt.h> */
83 void arch_local_irq_enable(void);
84 #else
arch_local_irq_enable(void)85 static inline void arch_local_irq_enable(void)
86 {
87 	arch_local_irq_restore(get_trigger_mask());
88 }
89 #endif
90 
91 #endif /* (__ASSEMBLY__) */
92 
93 #endif /* !(_ASM_IRQFLAGS_H) */
94