Go to the documentation of this file.00001 #ifndef BOOST_DETAIL_ATOMIC_GCC_ARMV6P_HPP
00002 #define BOOST_DETAIL_ATOMIC_GCC_ARMV6P_HPP
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037 #define BOOST_ATOMIC_CHAR_LOCK_FREE 2
00038 #define BOOST_ATOMIC_CHAR16_T_LOCK_FREE 2
00039 #define BOOST_ATOMIC_CHAR32_T_LOCK_FREE 2
00040 #define BOOST_ATOMIC_WCHAR_T_LOCK_FREE 2
00041 #define BOOST_ATOMIC_SHORT_LOCK_FREE 2
00042 #define BOOST_ATOMIC_INT_LOCK_FREE 2
00043 #define BOOST_ATOMIC_LONG_LOCK_FREE 2
00044 #define BOOST_ATOMIC_LLONG_LOCK_FREE 0
00045 #define BOOST_ATOMIC_ADDRESS_LOCK_FREE 2
00046 #define BOOST_ATOMIC_BOOL_LOCK_FREE 2
00047
00048 namespace boost {
00049 namespace detail {
00050 namespace atomic {
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072 #if defined(__thumb__) && !defined(__ARM_ARCH_7A__)
00073
00074 #define BOOST_ATOMIC_ARM_ASM_START(TMPREG) "adr " #TMPREG ", 1f\n" "bx " #TMPREG "\n" ".arm\n" ".align 4\n" "1: "
00075 #define BOOST_ATOMIC_ARM_ASM_END(TMPREG) "adr " #TMPREG ", 1f + 1\n" "bx " #TMPREG "\n" ".thumb\n" ".align 2\n" "1: "
00076
00077 #else
00078
00079 #define BOOST_ATOMIC_ARM_ASM_START(TMPREG)
00080 #define BOOST_ATOMIC_ARM_ASM_END(TMPREG)
00081 #endif
00082
00083 #if defined(__ARM_ARCH_7A__)
00084
00085 #define BOOST_ATOMIC_ARM_DMB "dmb\n"
00086 #else
00087 #define BOOST_ATOMIC_ARM_DMB "mcr\tp15, 0, r0, c7, c10, 5\n"
00088 #endif
00089
00090 static inline void
00091 arm_barrier(void)
00092 {
00093 int brtmp;
00094 __asm__ __volatile__ (
00095 BOOST_ATOMIC_ARM_ASM_START(%0)
00096 BOOST_ATOMIC_ARM_DMB
00097 BOOST_ATOMIC_ARM_ASM_END(%0)
00098 : "=&l" (brtmp) :: "memory"
00099 );
00100 }
00101
00102 static inline void
00103 platform_fence_before(memory_order order)
00104 {
00105 switch(order) {
00106 case memory_order_release:
00107 case memory_order_acq_rel:
00108 case memory_order_seq_cst:
00109 arm_barrier();
00110 case memory_order_consume:
00111 default:;
00112 }
00113 }
00114
00115 static inline void
00116 platform_fence_after(memory_order order)
00117 {
00118 switch(order) {
00119 case memory_order_acquire:
00120 case memory_order_acq_rel:
00121 case memory_order_seq_cst:
00122 arm_barrier();
00123 default:;
00124 }
00125 }
00126
00127 static inline void
00128 platform_fence_before_store(memory_order order)
00129 {
00130 platform_fence_before(order);
00131 }
00132
00133 static inline void
00134 platform_fence_after_store(memory_order order)
00135 {
00136 if (order == memory_order_seq_cst)
00137 arm_barrier();
00138 }
00139
00140 static inline void
00141 platform_fence_after_load(memory_order order)
00142 {
00143 platform_fence_after(order);
00144 }
00145
00146 template<typename T>
00147 bool
00148 platform_cmpxchg32(T & expected, T desired, volatile T * ptr)
00149 {
00150 int success;
00151 int tmp;
00152 __asm__ (
00153 BOOST_ATOMIC_ARM_ASM_START(%2)
00154 "mov %1, #0\n"
00155 "ldrex %0, %3\n"
00156 "teq %0, %4\n"
00157 "ittt eq\n"
00158 "strexeq %2, %5, %3\n"
00159 "teqeq %2, #0\n"
00160 "moveq %1, #1\n"
00161 BOOST_ATOMIC_ARM_ASM_END(%2)
00162 : "=&r" (expected),
00163 "=&r" (success),
00164 "=&l" (tmp),
00165 "+Q" (*ptr)
00166 : "r" (expected),
00167 "r" (desired)
00168 : "cc"
00169 );
00170 return success;
00171 }
00172
00173
00174 }
00175 }
00176
00177 #define BOOST_ATOMIC_THREAD_FENCE 2
00178 static inline void
00179 atomic_thread_fence(memory_order order)
00180 {
00181 switch(order) {
00182 case memory_order_acquire:
00183 case memory_order_release:
00184 case memory_order_acq_rel:
00185 case memory_order_seq_cst:
00186 detail::atomic::arm_barrier();
00187 default:;
00188 }
00189 }
00190
00191 #define BOOST_ATOMIC_SIGNAL_FENCE 2
00192 static inline void
00193 atomic_signal_fence(memory_order)
00194 {
00195 __asm__ __volatile__ ("" ::: "memory");
00196 }
00197
00198 }
00199
00200 #undef BOOST_ATOMIC_ARM_ASM_START
00201 #undef BOOST_ATOMIC_ARM_ASM_END
00202
00203 #include <boost/atomic/detail/cas32weak.hpp>
00204
00205 #endif