move new files out from platform support patch
[openwrt/staging/yousong.git] / target / linux / ubicom32 / files / arch / ubicom32 / include / asm / ubicom32-common.h
1 /*
2 * arch/ubicom32/include/asm/ubicom32-common.h
3 * Ubicom32 atomic lock operations.
4 *
5 * (C) Copyright 2009, Ubicom, Inc.
6 *
7 * This file is part of the Ubicom32 Linux Kernel Port.
8 *
9 * The Ubicom32 Linux Kernel Port is free software: you can redistribute
10 * it and/or modify it under the terms of the GNU General Public License
11 * as published by the Free Software Foundation, either version 2 of the
12 * License, or (at your option) any later version.
13 *
14 * The Ubicom32 Linux Kernel Port is distributed in the hope that it
15 * will be useful, but WITHOUT ANY WARRANTY; without even the implied
16 * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
17 * the GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License
20 * along with the Ubicom32 Linux Kernel Port. If not,
21 * see <http://www.gnu.org/licenses/>.
22 *
23 * Ubicom32 implementation derived from (with many thanks):
24 * arch/m68knommu
25 * arch/blackfin
26 * arch/parisc
27 */
28
29 #ifndef _ASM_UBICOM32_UBICOM32_COMMON_H
30 #define _ASM_UBICOM32_UBICOM32_COMMON_H
31
32 #define S(arg) #arg
33 #define D(arg) S(arg)
34 /*
35 * scratchpad1 is owned by the LDSR.
36 *
37 * The upper bits provide 16 global spinlocks. Acquiring one of these
38 * global spinlocks synchornizes across multiple threads and prevents
39 * the LDSR from delivering any interrupts while the lock is held.
40 * Use these locks only when absolutely required.
41 *
42 * The lower 16 bits of scratchpad1 are used as per thread interrupt
43 * enable/disable bits. These bits will prevent a thread from receiving
44 * any interrupts.
45 *
46 * Bit Usage:
47 * - MT_EN_LOCK_BIT - Protects writes to MT_EN, so code can read current value
48 * then write a new value atomically (profiler for example)
49 * - ATOMIC_LOCK_BIT - Used to provide general purpose atomic handling.
50 * - LDSR_LOCK_BIT - Used by the LDSR exclusively to provide protection.
51 * - DCCR_LOCK_BIT - Used to limit access to the DCCR cache control peripheral
52 * - ICCR_LOCK_BIT - Used to limit access to the ICCR cache control peripheral
53 * - LSB 16 bits - Used by the LDSR to represent thread enable/disable bits.
54 */
55 #define MT_EN_LOCK_BIT 31
56 #define ATOMIC_LOCK_BIT 30
57 #define LDSR_LOCK_BIT 29
58 #define PCI_LOCK_BIT 28
59 #define ICCR_LOCK_BIT 27
60 #define DCCR_LOCK_BIT 26
61
62 #if !defined(__ASSEMBLY__)
63
64 #define UBICOM32_TRYLOCK(bit) \
65 asm volatile ( \
66 " move.4 %0, #0 \n\t" \
67 " bset scratchpad1, scratchpad1, #"D(bit)" \n\t" \
68 " jmpne.f 1f \n\t" \
69 " move.4 %0, #1 \n\t" \
70 "1: \n\t" \
71 : "=r" (ret) \
72 : \
73 : "cc", "memory" \
74 ) \
75
76 #define UBICOM32_UNLOCK(bit) \
77 asm volatile ( \
78 " bclr scratchpad1, scratchpad1, #"D(bit)" \n\t" \
79 : \
80 : \
81 : "cc", "memory" \
82 ) \
83
84 #define UBICOM32_LOCK(bit) \
85 asm volatile ( \
86 "1: bset scratchpad1, scratchpad1, #"D(bit)" \n\t" \
87 " jmpne.f 1b \n\t" \
88 : \
89 : \
90 : "cc", "memory" \
91 ) \
92
93 /*
94 * __atomic_lock_trylock()
95 * Attempt to acquire the lock, return TRUE if acquired.
96 */
97 static inline int __atomic_lock_trylock(void)
98 {
99 int ret;
100 UBICOM32_TRYLOCK(ATOMIC_LOCK_BIT);
101 return ret;
102 }
103
104 /*
105 * __atomic_lock_release()
106 * Release the global atomic lock.
107 *
108 * Note: no one is suspended waiting since this lock is a spinning lock.
109 */
110 static inline void __atomic_lock_release(void)
111 {
112 UBICOM32_UNLOCK(ATOMIC_LOCK_BIT);
113 }
114
115 /*
116 * __atomic_lock_acquire()
117 * Acquire the global atomic lock, spin if not available.
118 */
119 static inline void __atomic_lock_acquire(void)
120 {
121 UBICOM32_LOCK(ATOMIC_LOCK_BIT);
122 }
123 #else /* __ASSEMBLY__ */
124
125 #include <asm/ubicom32-common-asm.h>
126
127 #endif /* __ASSEMBLY__ */
128 #endif /* _ASM_UBICOM32_UBICOM32_COMMON_H */