From d650209479c4344078cab5589132557e56609ce1 Mon Sep 17 00:00:00 2001 From: matt Date: Sat, 10 Aug 2013 19:59:21 +0000 Subject: [PATCH] Make these under Thumb2 --- .../lib/libc/arch/arm/atomic/atomic_add_32.S | 24 +++++----- .../lib/libc/arch/arm/atomic/atomic_add_64.S | 44 ++++++------------- .../lib/libc/arch/arm/atomic/atomic_and_32.S | 21 ++++----- .../lib/libc/arch/arm/atomic/atomic_and_64.S | 40 +++++------------ .../lib/libc/arch/arm/atomic/atomic_cas_32.S | 22 ++++++---- .../lib/libc/arch/arm/atomic/atomic_cas_64.S | 27 +++++++----- .../lib/libc/arch/arm/atomic/atomic_cas_8.S | 20 +++++---- .../lib/libc/arch/arm/atomic/atomic_cas_up.S | 3 +- .../lib/libc/arch/arm/atomic/atomic_dec_32.S | 29 ++++++------ .../lib/libc/arch/arm/atomic/atomic_dec_64.S | 38 +++++++--------- .../lib/libc/arch/arm/atomic/atomic_inc_32.S | 23 +++++----- .../lib/libc/arch/arm/atomic/atomic_inc_64.S | 38 +++++++--------- .../lib/libc/arch/arm/atomic/atomic_or_32.S | 27 ++++++------ .../lib/libc/arch/arm/atomic/atomic_or_64.S | 40 +++++------------ common/lib/libc/arch/arm/atomic/atomic_swap.S | 26 +++++++---- .../lib/libc/arch/arm/atomic/atomic_swap_64.S | 13 +++--- 16 files changed, 195 insertions(+), 240 deletions(-) diff --git a/common/lib/libc/arch/arm/atomic/atomic_add_32.S b/common/lib/libc/arch/arm/atomic/atomic_add_32.S index 79eb006ea681..d725184cf2ec 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_add_32.S +++ b/common/lib/libc/arch/arm/atomic/atomic_add_32.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_add_32.S,v 1.3 2012/08/31 23:41:52 matt Exp $ */ +/* $NetBSD: atomic_add_32.S,v 1.4 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. @@ -34,19 +34,19 @@ #ifdef _ARM_ARCH_6 ENTRY_NP(_atomic_add_32) - mov r3, r0 /* need r0 for return value */ -1: ldrex r0, [r3] /* load old value (to be returned) */ - add r2, r0, r1 /* calculate new value */ - strex ip, r2, [r3] /* try to store */ - cmp ip, #0 /* succeed? */ +1: ldrex r3, [r0] /* load old value */ + add r3, r3, r1 /* calculate new value */ + strex r2, r3, [r0] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return old value */ - END(_atomic_add_32) +END(_atomic_add_32) + ATOMIC_OP_ALIAS(atomic_add_32,_atomic_add_32) ATOMIC_OP_ALIAS(atomic_add_int,_atomic_add_32) ATOMIC_OP_ALIAS(atomic_add_long,_atomic_add_32) @@ -56,16 +56,16 @@ STRONG_ALIAS(_atomic_add_long,_atomic_add_32) STRONG_ALIAS(_atomic_add_ptr,_atomic_add_32) ENTRY_NP(_atomic_add_32_nv) - mov r3, r0 /* need r0 for return value */ -1: ldrex r0, [r3] /* load old value */ + mov ip, r0 /* need r0 for return value */ +1: ldrex r0, [ip] /* load old value */ add r0, r0, r1 /* calculate new value (return value) */ - strex r2, r0, [r3] /* try to store */ + strex r2, r0, [ip] /* try to store */ cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ END(_atomic_add_32_nv) diff --git a/common/lib/libc/arch/arm/atomic/atomic_add_64.S b/common/lib/libc/arch/arm/atomic/atomic_add_64.S index db816e365852..94f9a341cd8e 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_add_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_add_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_add_64.S,v 1.5 2013/08/10 19:02:22 matt Exp $ */ +/* $NetBSD: atomic_add_64.S,v 1.6 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -32,50 +32,34 @@ #ifdef _ARM_ARCH_6 -ENTRY_NP(_atomic_add_64) - push {r4} /* save temporary */ - mov r4, r0 /* need r0 for return value */ -#ifndef __ARM_EABI__ - mov r3, r2 - mov r2, r1 -#endif -1: ldrexd r0, [r4] /* load old value (to be returned) */ - adds LO, LO, NLO /* calculate new value */ - adc HI, HI, NHI /* calculate new value */ - strexd ip, r0, [r4] /* try to store */ - cmp ip, #0 /* succeed? */ - bne 1b /* no, try again */ -#ifdef _ARM_ARCH_7 - dmb -#else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ -#endif - pop {r4} /* restore temporary */ - RET - END(_atomic_add_64) -ATOMIC_OP_ALIAS(atomic_add_64,_atomic_add_64) - ENTRY_NP(_atomic_add_64_nv) push {r4} /* save temporary */ - mov r4, r0 /* need r0 for return value */ + mov ip, r0 /* need r0 for return value */ #ifndef __ARM_EABI__ mov r3, r2 mov r2, r1 #endif -1: ldrexd r0, [r4] /* load old value */ +1: ldrexd r0, [ip] /* load old value */ +#ifdef __thumb__ + add LO, LO, NLO /* calculate new value lo */ +#else adds LO, LO, NLO /* calculate new value lo */ +#endif adc HI, HI, NHI /* calculate new value hi */ - strexd ip, r0, [r4] /* try to store */ - cmp ip, #0 /* succeed? */ + strexd r4, r0, [ip] /* try to store */ + cmp r4, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r4, c7, c10, 5 /* data memory barrier */ #endif pop {r4} /* restore temporary */ RET /* return new value */ - END(_atomic_add_64_nv) +END(_atomic_add_64_nv) + +STRONG_ALIAS(_atomic_add_64,_atomic_add_64_nv) ATOMIC_OP_ALIAS(atomic_add_64_nv,_atomic_add_64_nv) +ATOMIC_OP_ALIAS(atomic_add_64,_atomic_add_64) #endif /* _ARM_ARCH_6 */ diff --git a/common/lib/libc/arch/arm/atomic/atomic_and_32.S b/common/lib/libc/arch/arm/atomic/atomic_and_32.S index d55440cdab0b..1c20b7e14bd3 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_and_32.S +++ b/common/lib/libc/arch/arm/atomic/atomic_and_32.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_and_32.S,v 1.3 2012/08/31 23:41:52 matt Exp $ */ +/* $NetBSD: atomic_and_32.S,v 1.4 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. @@ -34,19 +34,19 @@ #ifdef _ARM_ARCH_6 ENTRY_NP(_atomic_and_32) - mov r3, r0 /* need r0 for return value */ -1: ldrex r0, [r3] /* load old value (to be returned) */ - and r2, r0, r1 /* calculate new value */ - strex ip, r2, [r3] /* try to store */ - cmp ip, #0 /* succeed? */ +1: ldrex r3, [r0] /* load old value (to be returned) */ + and r3, r3, r1 /* calculate new value */ + strex r2, r3, [r0] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return old value */ - END(_atomic_and_32) +END(_atomic_and_32) + ATOMIC_OP_ALIAS(atomic_and_32,_atomic_and_32) ATOMIC_OP_ALIAS(atomic_and_uint,_atomic_and_32) ATOMIC_OP_ALIAS(atomic_and_ulong,_atomic_and_32) @@ -63,10 +63,11 @@ ENTRY_NP(_atomic_and_32_nv) #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ - END(_atomic_and_32_nv) +END(_atomic_and_32_nv) + ATOMIC_OP_ALIAS(atomic_and_32_nv,_atomic_and_32_nv) ATOMIC_OP_ALIAS(atomic_and_uint_nv,_atomic_and_32_nv) ATOMIC_OP_ALIAS(atomic_and_ulong_nv,_atomic_and_32_nv) diff --git a/common/lib/libc/arch/arm/atomic/atomic_and_64.S b/common/lib/libc/arch/arm/atomic/atomic_and_64.S index 2b5d5e65e91f..edca1747206d 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_and_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_and_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_and_64.S,v 1.4 2013/08/10 19:02:22 matt Exp $ */ +/* $NetBSD: atomic_and_64.S,v 1.5 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -32,50 +32,30 @@ #ifdef _ARM_ARCH_6 -ENTRY_NP(_atomic_and_64) - push {r4} /* save temporary */ -#ifndef __ARM_EABI__ - mov r3, r2 - mov r2, r1 -#endif - mov r4, r0 /* need r0 for return value */ -1: ldrexd r0, [r4] /* load old value (to be returned) */ - and r0, r0, r2 /* calculate new value */ - and r1, r1, r3 /* calculate new value */ - strexd ip, r0, [r4] /* try to store */ - cmp ip, #0 /* succeed? */ - bne 1b /* no, try again */ -#ifdef _ARM_ARCH_7 - dmb -#else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ -#endif - pop {r4} /* restore temporary */ - RET - END(_atomic_and_64) -ATOMIC_OP_ALIAS(atomic_and_64,_atomic_and_64) - ENTRY_NP(_atomic_and_64_nv) push {r4} /* save temporary */ #ifndef __ARM_EABI__ mov r3, r2 mov r2, r1 #endif - mov r4, r0 /* need r0 for return value */ -1: ldrexd r0, [r4] /* load old value */ + mov ip, r0 /* need r0 for return value */ +1: ldrexd r0, [ip] /* load old value */ and r0, r0, r2 /* calculate new value */ and r1, r1, r3 /* calculate new value */ - strexd ip, r0, [r4] /* try to store */ - cmp ip, #0 /* succeed? */ + strexd r4, r0, [ip] /* try to store */ + cmp r4, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r4, c7, c10, 5 /* data memory barrier */ #endif pop {r4} /* restore temporary */ RET /* return new value */ - END(_atomic_and_64_nv) +END(_atomic_and_64_nv) + +STRONG_ALIAS(_atomic_and_64,_atomic_and_64_nv) ATOMIC_OP_ALIAS(atomic_and_64_nv,_atomic_and_64_nv) +ATOMIC_OP_ALIAS(atomic_and_64,_atomic_and_64_nv) #endif /* _ARM_ARCH_6 */ diff --git a/common/lib/libc/arch/arm/atomic/atomic_cas_32.S b/common/lib/libc/arch/arm/atomic/atomic_cas_32.S index 43f6e69cf1a9..85e281ae175d 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_cas_32.S +++ b/common/lib/libc/arch/arm/atomic/atomic_cas_32.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_cas_32.S,v 1.4 2012/10/29 14:09:38 chs Exp $ */ +/* $NetBSD: atomic_cas_32.S,v 1.5 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -36,21 +36,25 @@ * and kernel. */ ENTRY_NP(_atomic_cas_32) - mov r3, r0 /* we need r0 for return value */ + mov ip, r0 /* we need r0 for return value */ 1: - ldrex r0, [r3] /* load old value */ - teq r0, r1 /* compare? */ + ldrex r0, [ip] /* load old value */ + cmp r0, r1 /* compare? */ +#ifdef __thumb__ + bne 2f /* return if different */ +#else RETc(ne) /* return if different */ - strex ip, r2, [r3] /* store new value */ - cmp ip, #0 /* succeed? */ +#endif + strex r3, r2, [ip] /* store new value */ + cmp r3, #0 /* succeed? */ bne 1b /* nope, try again. */ #ifdef _ARM_ARCH_7 dsb #else - mcr p15, 0, ip, c7, c10, 4 /* data synchronization barrier */ + mcr p15, 0, r3, c7, c10, 4 /* data synchronization barrier */ #endif - RET /* return. */ - END(_atomic_cas_32) +2: RET /* return. */ +END(_atomic_cas_32) ATOMIC_OP_ALIAS(atomic_cas_32,_atomic_cas_32) ATOMIC_OP_ALIAS(atomic_cas_uint,_atomic_cas_32) diff --git a/common/lib/libc/arch/arm/atomic/atomic_cas_64.S b/common/lib/libc/arch/arm/atomic/atomic_cas_64.S index a3bd758f45c4..05fc6b53a623 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_cas_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_cas_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_cas_64.S,v 1.2 2012/10/29 14:09:38 chs Exp $ */ +/* $NetBSD: atomic_cas_64.S,v 1.3 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -36,23 +36,28 @@ * and kernel. */ ENTRY_NP(_atomic_cas_64) - stmfd sp!, {r4, r5, r6} /* save temporaries */ - mov r6, r0 /* we need r0 for return value */ + push {r4, r5, r6} /* save temporaries */ + mov ip, r0 /* we need r0 for return value */ #ifdef __ARM_EABI__ ldrd r4, [sp] /* fetch new value */ #else - ldr r5, [sp, #4] /* fetch new value */ ldr r4, [sp, #0] /* fetch new value */ + ldr r5, [sp, #4] /* fetch new value */ mov r3, r2 /* r2 will be overwritten by r1 which ... */ mov r2, r1 /* r1 will be overwritten by ldrexd */ #endif 1: - ldrexd r0, [r6] /* load current value */ - teq r0, r2 /* compare to old? 1st half */ - teqeq r1, r3 /* compare to old? 2nd half */ + ldrexd r0, [ip] /* load current value */ + cmp r0, r2 /* compare to old? 1st half */ +#ifdef __thumb__ bne 2f /* jump to return if different */ - strexd ip, r4, [r6] /* store new value */ - cmp ip, #0 /* succeed? */ + cmp r1, r3 /* compare to old? 2nd half */ +#else + cmpeq r1, r3 /* compare to old? 2nd half */ +#endif + bne 2f /* jump to return if different */ + strexd r6, r4, [ip] /* store new value */ + cmp r6, #0 /* succeed? */ bne 1b /* nope, try again. */ #ifdef _ARM_ARCH_7 dsb @@ -60,9 +65,9 @@ ENTRY_NP(_atomic_cas_64) mcr p15, 0, ip, c7, c10, 4 /* data synchronization barrier */ #endif 2: - ldmfd sp!, {r4, r5, r6} /* restore temporaries */ + pop {r4, r5, r6} /* restore temporaries */ RET /* return. */ - END(_atomic_cas_64) +END(_atomic_cas_64) ATOMIC_OP_ALIAS(atomic_cas_64,_atomic_cas_64) diff --git a/common/lib/libc/arch/arm/atomic/atomic_cas_8.S b/common/lib/libc/arch/arm/atomic/atomic_cas_8.S index a02c499708f7..e0d7bc35f61f 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_cas_8.S +++ b/common/lib/libc/arch/arm/atomic/atomic_cas_8.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_cas_8.S,v 1.4 2012/10/29 14:09:38 chs Exp $ */ +/* $NetBSD: atomic_cas_8.S,v 1.5 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -36,20 +36,24 @@ * and kernel. */ ENTRY_NP(_atomic_cas_8) - mov r3, r0 /* we need r0 for return value */ + mov ip, r0 /* we need r0 for return value */ 1: - ldrexb r0, [r3] /* load old value */ - teq r0, r1 /* compare? */ + ldrexb r0, [ip] /* load old value */ + cmp r0, r1 /* compare? */ +#ifdef __thumb__ + bne 2f +#else RETc(ne) /* return if different */ - strexb ip, r2, [r3] /* store new value */ - cmp ip, #0 /* succeed? */ +#endif + strexb r3, r2, [ip] /* store new value */ + cmp r3, #0 /* succeed? */ bne 1b /* nope, try again. */ #ifdef _ARM_ARCH_7 dsb /* data synchronization barrier */ #else - mcr p15, 0, ip, c7, c10, 4 /* data synchronization barrier */ + mcr p15, 0, r3, c7, c10, 4 /* data synchronization barrier */ #endif - RET /* return. */ +2: RET /* return. */ END(_atomic_cas_8) ATOMIC_OP_ALIAS(atomic_cas_8,_atomic_cas_8) diff --git a/common/lib/libc/arch/arm/atomic/atomic_cas_up.S b/common/lib/libc/arch/arm/atomic/atomic_cas_up.S index 9fe854ea2f87..8f45cf85444c 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_cas_up.S +++ b/common/lib/libc/arch/arm/atomic/atomic_cas_up.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_cas_up.S,v 1.2 2008/05/25 15:56:11 chs Exp $ */ +/* $NetBSD: atomic_cas_up.S,v 1.3 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. @@ -41,3 +41,4 @@ RAS_START_ASM_HIDDEN(_atomic_cas) streq r2, [r3] RAS_END_ASM_HIDDEN(_atomic_cas) RET +END(_atomic_cas_up) diff --git a/common/lib/libc/arch/arm/atomic/atomic_dec_32.S b/common/lib/libc/arch/arm/atomic/atomic_dec_32.S index 5d8b3d2494ce..484efe959b30 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_dec_32.S +++ b/common/lib/libc/arch/arm/atomic/atomic_dec_32.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_dec_32.S,v 1.3 2012/08/31 23:41:52 matt Exp $ */ +/* $NetBSD: atomic_dec_32.S,v 1.4 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -33,19 +33,19 @@ #ifdef _ARM_ARCH_6 ENTRY_NP(_atomic_dec_32) - mov r2, r0 /* need r0 for return value */ -1: ldrex r0, [r2] /* load old value (return value) */ - sub r1, r0, #1 /* calculate new value */ - strex r3, r1, [r2] /* try to store */ - cmp r3, #0 /* succeed? */ +1: ldrex r3, [r0] /* load old value (return value) */ + sub r3, r3, #1 /* calculate new value */ + strex r2, r3, [r0] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ - END(_atomic_dec_32) +END(_atomic_dec_32) + ATOMIC_OP_ALIAS(atomic_dec_32,_atomic_dec_32) ATOMIC_OP_ALIAS(atomic_dec_uint,_atomic_dec_32) ATOMIC_OP_ALIAS(atomic_dec_ulong,_atomic_dec_32) @@ -55,19 +55,20 @@ STRONG_ALIAS(_atomic_dec_ulong,_atomic_dec_32) STRONG_ALIAS(_atomic_dec_ptr,_atomic_dec_32) ENTRY_NP(_atomic_dec_32_nv) - mov r2, r0 /* need r0 for return value */ -1: ldrex r0, [r2] /* load old value */ + mov ip, r0 /* need r0 for return value */ +1: ldrex r0, [ip] /* load old value */ sub r0, r0, #1 /* calculate new value (return value) */ - strex r1, r0, [r2] /* try to store */ - cmp r1, #0 /* succeed? */ + strex r2, r0, [ip] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ - END(_atomic_dec_32_nv) +END(_atomic_dec_32_nv) + ATOMIC_OP_ALIAS(atomic_dec_32_nv,_atomic_dec_32_nv) ATOMIC_OP_ALIAS(atomic_dec_uint_nv,_atomic_dec_32_nv) ATOMIC_OP_ALIAS(atomic_dec_ulong_nv,_atomic_dec_32_nv) diff --git a/common/lib/libc/arch/arm/atomic/atomic_dec_64.S b/common/lib/libc/arch/arm/atomic/atomic_dec_64.S index 0f6a4acf0a48..6624b874f8cc 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_dec_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_dec_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_dec_64.S,v 1.4 2013/08/10 18:45:12 matt Exp $ */ +/* $NetBSD: atomic_dec_64.S,v 1.5 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -32,29 +32,20 @@ #ifdef _ARM_ARCH_6 -ENTRY_NP(_atomic_dec_64) - mov r3, r0 /* need r0 for return value */ -1: ldrexd r0, [r3] /* load old value (return value) */ - subs LO, LO, #1 /* calculate new value */ - sbc HI, HI, #0 /* calculate new value */ - strexd r2, r0, [r3] /* try to store */ - cmp r2, #0 /* succeed? */ - bne 1b /* no, try again? */ -#ifdef _ARM_ARCH_7 - dmb -#else - mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ -#endif - RET - END(_atomic_dec_64) -ATOMIC_OP_ALIAS(atomic_dec_64,_atomic_dec_64) - ENTRY_NP(_atomic_dec_64_nv) - mov r3, r0 /* need r0 for return value */ -1: ldrexd r0, [r3] /* load old value */ + mov ip, r0 /* need r0 for return value */ +#ifdef __thumb__ + mov r2, #0 +#endif +1: ldrexd r0, [ip] /* load old value */ +#ifdef __thumb__ + sub LO, LO, #1 /* calculate new value */ + sbc HI, HI, r2 /* calculate new value */ +#else subs LO, LO, #1 /* calculate new value */ sbc HI, HI, #0 /* calculate new value */ - strexd r2, r0, [r3] /* try to store */ +#endif + strexd r2, r0, [ip] /* try to store */ cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 @@ -63,7 +54,10 @@ ENTRY_NP(_atomic_dec_64_nv) mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ - END(_atomic_dec_64_nv) +END(_atomic_dec_64_nv) + +STRONG_ALIAS(_atomic_dec_64,_atomic_dec_64_nv) ATOMIC_OP_ALIAS(atomic_dec_64_nv,_atomic_dec_64_nv) +ATOMIC_OP_ALIAS(atomic_dec_64,_atomic_dec_64) #endif /* _ARM_ARCH_6 */ diff --git a/common/lib/libc/arch/arm/atomic/atomic_inc_32.S b/common/lib/libc/arch/arm/atomic/atomic_inc_32.S index 9710b700bfb4..efd63ca4145a 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_inc_32.S +++ b/common/lib/libc/arch/arm/atomic/atomic_inc_32.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_inc_32.S,v 1.4 2012/10/29 14:09:38 chs Exp $ */ +/* $NetBSD: atomic_inc_32.S,v 1.5 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -33,16 +33,15 @@ #ifdef _ARM_ARCH_6 ENTRY_NP(_atomic_inc_32) - mov r2, r0 /* need r0 for return value */ -1: ldrex r0, [r2] /* load old value (return value) */ - add r1, r0, #1 /* calculate new value */ - strex r3, r1, [r2] /* try to store */ - cmp r3, #0 /* succeed? */ +1: ldrex r3, [r0] /* load old value (return value) */ + add r3, r3, #1 /* calculate new value */ + strex r2, r3, [r0] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ END(_atomic_inc_32) @@ -55,16 +54,16 @@ STRONG_ALIAS(_atomic_inc_ulong,_atomic_inc_32) STRONG_ALIAS(_atomic_inc_ptr,_atomic_inc_32) ENTRY_NP(_atomic_inc_32_nv) - mov r2, r0 /* need r0 for return value */ -1: ldrex r0, [r2] /* load old value */ + mov ip, r0 /* need r0 for return value */ +1: ldrex r0, [ip] /* load old value */ add r0, r0, #1 /* calculate new value (return value) */ - strex r1, r0, [r2] /* try to store */ - cmp r1, #0 /* succeed? */ + strex r2, r0, [ip] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ END(_atomic_inc_32_nv) diff --git a/common/lib/libc/arch/arm/atomic/atomic_inc_64.S b/common/lib/libc/arch/arm/atomic/atomic_inc_64.S index 18b2fb458b8b..4b5ad02834ec 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_inc_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_inc_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_inc_64.S,v 1.6 2013/08/10 18:45:12 matt Exp $ */ +/* $NetBSD: atomic_inc_64.S,v 1.7 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -32,29 +32,20 @@ #ifdef _ARM_ARCH_6 -ENTRY_NP(_atomic_inc_64) - mov r3, r0 /* need r0 for return value */ -1: ldrexd r0, [r3] /* load old value (return value) */ - adds LO, LO, #1 /* calculate new value */ - adc HI, HI, #0 /* zero means we carried */ - strexd r2, r0, [r3] /* try to store */ - cmp r2, #0 /* succeed? */ - bne 1b /* no, try again? */ -#ifdef _ARM_ARCH_7 - dmb -#else - mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ -#endif - RET - END(_atomic_inc_64) -ATOMIC_OP_ALIAS(atomic_inc_64,_atomic_inc_64) - ENTRY_NP(_atomic_inc_64_nv) - mov r3, r0 /* need r0 for return value */ -1: ldrexd r0, [r3] /* load old value */ + mov ip, r0 /* need r0 for return value */ +#ifdef __thumb__ + mov r2, #0 +#endif +1: ldrexd r0, [ip] /* load old value */ +#ifdef __thumb__ + add LO, LO, #1 /* calculate new value */ + adc HI, HI, r2 /* zero means we carried */ +#else adds LO, LO, #1 /* calculate new value (return value) */ adc HI, HI, #0 /* fold carry into high */ - strexd r2, r0, [r3] /* try to store */ +#endif + strexd r2, r0, [ip] /* try to store */ cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 @@ -63,7 +54,10 @@ ENTRY_NP(_atomic_inc_64_nv) mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ - END(_atomic_inc_64_nv) +END(_atomic_inc_64_nv) + +STRONG_ALIAS(_atomic_inc_64,_atomic_inc_64_nv) ATOMIC_OP_ALIAS(atomic_inc_64_nv,_atomic_inc_64_nv) +ATOMIC_OP_ALIAS(atomic_inc_64,_atomic_inc_64) #endif /* _ARM_ARCH_6 */ diff --git a/common/lib/libc/arch/arm/atomic/atomic_or_32.S b/common/lib/libc/arch/arm/atomic/atomic_or_32.S index 9a64a54f69a9..fedc550bf91c 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_or_32.S +++ b/common/lib/libc/arch/arm/atomic/atomic_or_32.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_or_32.S,v 1.3 2012/08/31 23:41:52 matt Exp $ */ +/* $NetBSD: atomic_or_32.S,v 1.4 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2008 The NetBSD Foundation, Inc. * All rights reserved. @@ -33,19 +33,19 @@ #ifdef _ARM_ARCH_6 ENTRY_NP(_atomic_or_32) - mov r3, r0 /* need r0 for return value */ -1: ldrex r0, [r3] /* load old value (to be returned) */ - orr r2, r0, r1 /* calculate new value */ - strex ip, r2, [r3] /* try to store */ - cmp ip, #0 /* succeed? */ +1: ldrex r3, [r0] /* load old value (to be returned) */ + orr r3, r3, r1 /* calculate new value */ + strex r2, r3, [r0] /* try to store */ + cmp r2, #0 /* succeed? */ bne 1b /* no, try again */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return old value */ - END(_atomic_or_32) +END(_atomic_or_32) + ATOMIC_OP_ALIAS(atomic_or_32,_atomic_or_32) ATOMIC_OP_ALIAS(atomic_or_uint,_atomic_or_32) ATOMIC_OP_ALIAS(atomic_or_ulong,_atomic_or_32) @@ -53,19 +53,20 @@ STRONG_ALIAS(_atomic_or_uint,_atomic_or_32) STRONG_ALIAS(_atomic_or_ulong,_atomic_or_32) ENTRY_NP(_atomic_or_32_nv) - mov r3, r0 /* need r0 for return value */ -1: ldrex r0, [r3] /* load old value */ + mov ip, r0 /* need r0 for return value */ +1: ldrex r0, [ip] /* load old value */ orr r0, r0, r1 /* calculate new value (return value) */ - strex r2, r0, [r3] /* try to store */ + strex r2, r0, [ip] /* try to store */ cmp r2, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r2, c7, c10, 5 /* data memory barrier */ #endif RET /* return new value */ - END(_atomic_or_32_nv) +END(_atomic_or_32_nv) + ATOMIC_OP_ALIAS(atomic_or_32_nv,_atomic_or_32_nv) ATOMIC_OP_ALIAS(atomic_or_uint_nv,_atomic_or_32_nv) ATOMIC_OP_ALIAS(atomic_or_ulong_nv,_atomic_or_32_nv) diff --git a/common/lib/libc/arch/arm/atomic/atomic_or_64.S b/common/lib/libc/arch/arm/atomic/atomic_or_64.S index 35b193b68d5a..710e56382d76 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_or_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_or_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_or_64.S,v 1.4 2013/08/10 19:02:22 matt Exp $ */ +/* $NetBSD: atomic_or_64.S,v 1.5 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -32,31 +32,8 @@ #ifdef _ARM_ARCH_6 -ENTRY_NP(_atomic_or_64) - push {r4} /* save temporary */ -#ifndef __ARM_EABI__ - mov r3, r2 - mov r2, r1 -#endif - mov r4, r0 /* need r0 for return value */ -1: ldrexd r0, [r4] /* load old value (to be returned) */ - orr r0, r0, r2 /* calculate new value */ - orr r1, r1, r3 /* calculate new value */ - strexd ip, r0, [r4] /* try to store */ - cmp ip, #0 /* succeed? */ - bne 1b /* no, try again */ -#ifdef _ARM_ARCH_7 - dmb -#else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ -#endif - pop {r4} /* restore temporary */ - RET - END(_atomic_or_64) -ATOMIC_OP_ALIAS(atomic_or_64,_atomic_or_64) - ENTRY_NP(_atomic_or_64_nv) - push {r4} /* save temporary */ + push {r4,r5} /* save temporary */ #ifndef __ARM_EABI__ mov r3, r2 mov r2, r1 @@ -65,17 +42,20 @@ ENTRY_NP(_atomic_or_64_nv) 1: ldrexd r0, [r4] /* load old value */ orr r0, r0, r2 /* calculate new value (return value) */ orr r1, r1, r3 /* calculate new value (return value) */ - strexd ip, r0, [r4] /* try to store */ - cmp ip, #0 /* succeed? */ + strexd r5, r0, [r4] /* try to store */ + cmp r5, #0 /* succeed? */ bne 1b /* no, try again? */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r5, c7, c10, 5 /* data memory barrier */ #endif - pop {r4} /* restore temporary */ + pop {r4,r5} /* restore temporary */ RET /* return new value */ - END(_atomic_or_64_nv) +END(_atomic_or_64_nv) + +STRONG_ALIAS(_atomic_or_64,_atomic_or_64_nv) ATOMIC_OP_ALIAS(atomic_or_64_nv,_atomic_or_64_nv) +ATOMIC_OP_ALIAS(atomic_or_64,_atomic_or_64) #endif /* _ARM_ARCH_6 */ diff --git a/common/lib/libc/arch/arm/atomic/atomic_swap.S b/common/lib/libc/arch/arm/atomic/atomic_swap.S index d960db044f26..4e9d90aced66 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_swap.S +++ b/common/lib/libc/arch/arm/atomic/atomic_swap.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_swap.S,v 1.5 2013/01/28 06:22:34 matt Exp $ */ +/* $NetBSD: atomic_swap.S,v 1.6 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2007,2012 The NetBSD Foundation, Inc. @@ -45,24 +45,32 @@ */ ENTRY_NP(_atomic_swap_32) - mov r2, r0 + mov ip, r0 1: #ifdef _ARM_ARCH_6 - ldrex r0, [r2] + ldrex r0, [ip] cmp r0, r1 - strexne ip, r1, [r2] +#ifdef __thumb__ + beq 99f + strex r3, r1, [ip] + cmp r3, #0 #else - swp r0, r1, [r2] - cmp r0, r1 - movnes ip, #0 + strexne r3, r1, [ip] + cmpne r3, #0 +#endif +#else + swp r0, r1, [ip] + cmp r0, r1 + movnes r3, #0 + cmpne r3, #0 #endif - cmpne ip, #0 bne 1b #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r3, c7, c10, 5 /* data memory barrier */ #endif +99: RET END(_atomic_swap_32) ATOMIC_OP_ALIAS(atomic_swap_32,_atomic_swap_32) diff --git a/common/lib/libc/arch/arm/atomic/atomic_swap_64.S b/common/lib/libc/arch/arm/atomic/atomic_swap_64.S index 4d3ae2c7fc75..133cfc146943 100644 --- a/common/lib/libc/arch/arm/atomic/atomic_swap_64.S +++ b/common/lib/libc/arch/arm/atomic/atomic_swap_64.S @@ -1,4 +1,4 @@ -/* $NetBSD: atomic_swap_64.S,v 1.3 2013/08/10 18:38:33 matt Exp $ */ +/* $NetBSD: atomic_swap_64.S,v 1.4 2013/08/10 19:59:21 matt Exp $ */ /*- * Copyright (c) 2012 The NetBSD Foundation, Inc. * All rights reserved. @@ -32,20 +32,19 @@ ENTRY_NP(_atomic_swap_64) push {r4} /* save temporary */ - mov r4, r0 /* return value will be in r0 */ + mov ip, r0 /* return value will be in r0 */ #ifndef __ARM_EABI__ mov r3, r2 /* r2 will be overwriten by r1 */ mov r2, r1 /* and r1 will be overwritten by ldrexd */ #endif -1: - ldrexd r0, [r4] /* load old value */ - strexd ip, r2, [r4] /* store new value */ - cmp ip, #0 /* succeed? */ +1: ldrexd r0, [ip] /* load old value */ + strexd r4, r2, [ip] /* store new value */ + cmp r4, #0 /* succeed? */ bne 1b /* no, try again */ #ifdef _ARM_ARCH_7 dmb #else - mcr p15, 0, ip, c7, c10, 5 /* data memory barrier */ + mcr p15, 0, r4, c7, c10, 5 /* data memory barrier */ #endif pop {r4} /* restore temporary */ RET