Commit 269af5d7 by Michael Schmid

atomic functions imlemented like arm versions

parent 302cef3c
......@@ -128,14 +128,16 @@ EMBB_DEFINE_AND_ASSIGN(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
// scm34681: add atomic methods (all headers)
#define EMBB_DEFINE_AND_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX)\
#define EMBB_DEFINE_AND_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX)\
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_and_assign_, \
EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) value) { \
__asm__ __volatile__("and" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[value], %[value_p]\n\t" \
"dsync" \
: [value]"+r" (value) \
: [value_p]"r" (*pointer_to_value)\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) result=0; \
__asm__ __volatile__("dsync\n\t" \
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[result], %[pointer_to_value]\n\t" \
"and %[result], %[value]\n\t" \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[pointer_to_value], %[result]\n\t" \
: [pointer_to_value]"+m" (*pointer_to_value), [result]"+d" (result) \
: [value]"d" (value)\
: "memory"); \
}
#else
......
......@@ -128,19 +128,25 @@ EMBB_DEFINE_COMPARE_AND_SWAP(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
// scm34681: use aurix instruction set
#define EMBB_DEFINE_COMPARE_AND_SWAP(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
#define EMBB_DEFINE_COMPARE_AND_SWAP(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE int EMBB_CAT2(embb_internal__atomic_compare_and_swap_, \
EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* expected, \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) desired) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) result = 0; \
__asm__ __volatile__ ( \
"eq" EMBB_ATOMIC_X86_SIZE_SUFFIX " %%d15, %[expected], %[pointer_to_value]\n\t" \
"cmov" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[pointer_to_value], %%d15, %[desired]\n\t" \
"cmovn" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[expected], %%d15, %[pointer_to_value]\n\t" \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) oldval = 0; \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) exp_val = 0; \
__asm__ __volatile__ ("dsync\n\t" \
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[oldval], %[pointer_to_value]\n\t" \
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[exp_val], %[expected]\n\t" \
"eq %%d15, %[exp_val], %[oldval]\n\t" \
"cmov %[oldval], %%d15, %[desired]\n\t" \
"cmovn %[exp_val], %%d15, %[oldval]\n\t" \
"mov %[result], %%d15\n\t" \
: [result]"+r" (result), [expected]"+r" (*expected), [pointer_to_value]"+r"(*pointer_to_value)\
: [desired]"r" (desired) \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[pointer_to_value], %[oldval]\n\t" \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[expected], %[exp_val]\n\t" \
"dsync\n\t" \
: [result]"+d" (result), [expected]"+m" (*expected), [exp_val]"+d" (exp_val),[oldval]"+d" (oldval), [pointer_to_value]"+m"(*pointer_to_value)\
: [desired]"d" (desired) \
: "%d15", "memory", "cc"); \
return result; \
}
......@@ -148,9 +154,9 @@ EMBB_DEFINE_COMPARE_AND_SWAP(4, "")
#error "No atomic fetch and store implementation found"
#endif
EMBB_DEFINE_COMPARE_AND_SWAP(1, "")
EMBB_DEFINE_COMPARE_AND_SWAP(2, "")
EMBB_DEFINE_COMPARE_AND_SWAP(4, "")
EMBB_DEFINE_COMPARE_AND_SWAP(1, ".b")
EMBB_DEFINE_COMPARE_AND_SWAP(2, ".h")
EMBB_DEFINE_COMPARE_AND_SWAP(4, ".w")
#else
#error "Unknown architecture"
......
......@@ -124,13 +124,14 @@ EMBB_DEFINE_FETCH_AND_ADD(4, "")
EMBB_PLATFORM_INLINE EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) EMBB_CAT2(embb_internal__atomic_fetch_and_add_, EMBB_PARAMETER_SIZE_BYTE) \
(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) new_value) { \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) \
result,tmp1; \
__asm__ __volatile__ ("ld" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[result], %[pointer_to_value]\n\t" \
result=0,tmp1=0; \
__asm__ __volatile__ ("dsync\n\t" \
"ld" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[result], %[pointer_to_value]\n\t" \
"add %[tmp1],%[new_value], %[result]\n\t" \
"st" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[pointer_to_value], %[tmp1]\n\t" \
"dsync" \
: [result] "+r" (result), [tmp1]"+r" (tmp1), [pointer_to_value]"+m" (*pointer_to_value) \
: [new_value]"r" (new_value) \
"dsync\n\t" \
: [result] "+d" (result), [tmp1]"+d" (tmp1), [pointer_to_value]"+m" (*pointer_to_value) \
: [new_value]"d" (new_value) \
: "memory", "cc" ); \
return result; \
}
......
......@@ -112,13 +112,13 @@ EMBB_DEFINE_LOAD(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
#define EMBB_DEFINE_LOAD(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
#define EMBB_DEFINE_LOAD(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) \
EMBB_CAT2(embb_internal__atomic_load_, EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value) { \
/* no fence required for loads */ \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) result; \
__asm__ __volatile__("ld" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[result], %[value]\n\t" \
"dsync"\
__asm__ __volatile__("dsync\n\t"\
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[result], %[value]\n\t" \
"dsync\n\t"\
: [result]"=r" (result) \
: [value]"m" (*pointer_to_value) \
: "memory"); \
......
......@@ -64,7 +64,7 @@ EMBB_PLATFORM_INLINE void embb_atomic_memory_barrier() {
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
// Read/write barrier
EMBB_PLATFORM_INLINE void embb_atomic_memory_barrier() {
__asm__ __volatile__ ("isync" : : : "memory");
__asm__ __volatile__ ("dsync" : : : "memory");
}
#else
#error "No atomic fetch and store implementation found"
......
......@@ -113,13 +113,17 @@ EMBB_DEFINE_OR_ASSIGN(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
#define EMBB_DEFINE_OR_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
#define EMBB_DEFINE_OR_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_or_assign_, EMBB_PARAMETER_SIZE_BYTE)(\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) value) { \
__asm__ __volatile__("or" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[value], %[value_p]\n\t" \
"dsync" \
: [value]"+r" (value) \
: [value_p]"r" (*pointer_to_value) \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) result=0; \
__asm__ __volatile__( \
"dsync\n\t" \
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[result], %[pointer_to_value]\n\t"\
"or %[result], %[value]\n\t" \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[pointer_to_value], %[result]\n\t" \
: [result]"+d" (result), [pointer_to_value]"+m" (*pointer_to_value) \
: [value]"d" (value) \
: "memory"); \
}
......
......@@ -108,15 +108,16 @@ EMBB_DEFINE_STORE(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
#define EMBB_DEFINE_STORE(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX)\
#define EMBB_DEFINE_STORE(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX)\
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_store_, EMBB_PARAMETER_SIZE_BYTE)(EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) new_value) {\
__asm__ __volatile__("st" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[result], %[value]\n\t" \
"dsync" \
: [result]"=m" (*pointer_to_value)\
: [value]"r" (new_value)\
__asm__ __volatile__( \
"dsync\n\t" \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[pointer_to_value], %[value]\n\t" \
: [pointer_to_value]"=m" (*pointer_to_value)\
: [value]"d" (new_value)\
: "memory"); \
} // scm34681: check correct implementation
}
#else
#error "No atomic fetch and store implementation found"
......
......@@ -116,24 +116,28 @@ EMBB_DEFINE_SWAP(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
#define EMBB_DEFINE_SWAP(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
#define EMBB_DEFINE_SWAP(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) EMBB_CAT2(embb_internal__atomic_swap_, EMBB_PARAMETER_SIZE_BYTE)(\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) new_value)\
{ \
__asm__ __volatile__("swap.w" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[pointer_to_value], %[new_value]" \
: [pointer_to_value]"+m" (*pointer_to_value), [new_value]"+q" (new_value) \
: \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) \
result=0; \
__asm__ __volatile__("dsync\n\t" \
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX "%[result], %[pointer_to_value]" \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX "%[pointer_to_value], %[new_value]" \
: [result]"+d"(result), [pointer_to_value]"+m" (*pointer_to_value) \
: [new_value]"d" (new_value) \
: "memory"); \
return new_value; \
return result; \
}
#else
#error "No atomic fetch and store implementation found"
#endif
EMBB_DEFINE_SWAP(1, "")
EMBB_DEFINE_SWAP(2, "")
EMBB_DEFINE_SWAP(4, "")
EMBB_DEFINE_SWAP(1, ".b")
EMBB_DEFINE_SWAP(2, ".h")
EMBB_DEFINE_SWAP(4, ".w")
#else
#error "Unknown architecture"
......
......@@ -115,14 +115,18 @@ EMBB_DEFINE_XOR_ASSIGN(4, "")
#elif defined(EMBB_PLATFORM_ARCH_TC)
#if defined(EMBB_PLATFORM_COMPILER_GNUC)
#define EMBB_DEFINE_XOR_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_X86_SIZE_SUFFIX) \
#define EMBB_DEFINE_XOR_ASSIGN(EMBB_PARAMETER_SIZE_BYTE, EMBB_ATOMIC_TC_SIZE_SUFFIX) \
EMBB_PLATFORM_INLINE void EMBB_CAT2(embb_internal__atomic_xor_assign_, EMBB_PARAMETER_SIZE_BYTE)(\
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) volatile* pointer_to_value, \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) value) { \
__asm__ __volatile__("xor" EMBB_ATOMIC_X86_SIZE_SUFFIX " %[value], %[value_p]\n\t" \
"dsync" \
: [value]"+r" (value) \
: [value_p]"r" (*pointer_to_value) \
EMBB_CAT2(EMBB_BASE_BASIC_TYPE_SIZE_, EMBB_PARAMETER_SIZE_BYTE) result=0; \
__asm__ __volatile__( \
"dsync\n\t" \
"ld" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[result], %[pointer_to_value]\n\t" \
"xor %[result], %[value]\n\t" \
"st" EMBB_ATOMIC_TC_SIZE_SUFFIX " %[pointer_to_value], %[result]\n\t" \
: [value]"+d" (value), [result]"+d" (result) \
: [pointer_to_value]"m" (*pointer_to_value) \
: "memory"); \
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or sign in to comment