diff -Naur protobuf-3.3.0/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h protobuf-3.3.0-m/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h --- protobuf-3.3.0/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h 2017-04-27 07:32:21.000000000 +0800 +++ protobuf-3.3.0-m/src/google/protobuf/stubs/atomicops_internals_arm_gcc.h 2020-09-11 11:47:46.820000000 +0800 @@ -69,6 +69,31 @@ return prev_value; } +inline Atomic64 NoBarrier_CompareAndSwap(volatile Atomic64* ptr, + Atomic64 old_value, + Atomic64 new_value) { + Atomic64 prev; + int32_t temp; + + __asm__ __volatile__ ( // NOLINT + "0: \n\t" + "ldxr %[prev], %[ptr] \n\t" + "cmp %[prev], %[old_value] \n\t" + "bne 1f \n\t" + "stxr %w[temp], %[new_value], %[ptr] \n\t" + "cbnz %w[temp], 0b \n\t" + "1: \n\t" + : [prev]"=&r" (prev), + [temp]"=&r" (temp), + [ptr]"+Q" (*ptr) + : [old_value]"IJr" (old_value), + [new_value]"r" (new_value) + : "cc", "memory" + ); // NOLINT + + return prev; +} + inline Atomic32 NoBarrier_AtomicExchange(volatile Atomic32* ptr, Atomic32 new_value) { Atomic32 old_value; @@ -105,6 +130,15 @@ return NoBarrier_CompareAndSwap(ptr, old_value, new_value); } +inline Atomic64 Acquire_CompareAndSwap(volatile Atomic64* ptr, + Atomic64 old_value, + Atomic64 new_value) { + Atomic64 prev = NoBarrier_CompareAndSwap(ptr, old_value, new_value); + MemoryBarrier(); + + return prev; +} + inline Atomic32 Release_CompareAndSwap(volatile Atomic32* ptr, Atomic32 old_value, Atomic32 new_value) { @@ -115,15 +149,29 @@ *ptr = value; } -inline void MemoryBarrierInternal() { +/*inline void MemoryBarrierInternal() { pLinuxKernelMemoryBarrier(); } +*/ + +inline void MemoryBarrierInternal() { + __asm__ __volatile__ ("dmb ish" ::: "memory"); // NOLINT + } inline void Acquire_Store(volatile Atomic32* ptr, Atomic32 value) { *ptr = value; MemoryBarrierInternal(); } +inline void Release_Store(volatile Atomic64* ptr, Atomic64 value) { + __asm__ __volatile__ ( // NOLINT + "stlr %x[value], %[ptr] \n\t" + : [ptr]"=Q" (*ptr) + : [value]"r" (value) + : "memory" + ); // NOLINT +} + inline void Release_Store(volatile Atomic32* ptr, Atomic32 value) { MemoryBarrierInternal(); *ptr = value; @@ -133,6 +181,19 @@ return *ptr; } +inline Atomic64 Acquire_Load(volatile const Atomic64* ptr) { + Atomic64 value; + + __asm__ __volatile__ ( // NOLINT + "ldar %x[value], %[ptr] \n\t" + : [value]"=r" (value) + : [ptr]"Q" (*ptr) + : "memory" + ); // NOLINT + + return value; +} + inline Atomic32 Acquire_Load(volatile const Atomic32* ptr) { Atomic32 value = *ptr; MemoryBarrierInternal(); diff -Naur protobuf-3.3.0/src/google/protobuf/stubs/platform_macros.h protobuf-3.3.0-m/src/google/protobuf/stubs/platform_macros.h --- protobuf-3.3.0/src/google/protobuf/stubs/platform_macros.h 2017-04-27 07:32:21.000000000 +0800 +++ protobuf-3.3.0-m/src/google/protobuf/stubs/platform_macros.h 2020-09-11 11:48:01.230000000 +0800 @@ -76,6 +76,9 @@ #elif defined(__PPC__) #define GOOGLE_PROTOBUF_ARCH_PPC 1 #define GOOGLE_PROTOBUF_ARCH_32_BIT 1 +#elif defined(__aarch64__) +#define GOOGLE_PROTOBUF_ARCH_ARM 1 +#define GOOGLE_PROTOBUF_ARCH_64_BIT 1 #elif defined(__GNUC__) # if (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 7)) || (__GNUC__ > 4)) // We fallback to the generic Clang/GCC >= 4.7 implementation in atomicops.h