diff options
author | Balazs Kilvady <kilvadyb@homejinni.com> | 2013-02-26 18:55:12 +0000 |
---|---|---|
committer | The Qt Project <gerrit-noreply@qt-project.org> | 2013-05-23 13:39:23 +0200 |
commit | dfd49c6f90bbe10a4e0c0e74768b3696f60b796c (patch) | |
tree | dfb605db83d5dba27c1739018dbbe02e4cc85d17 | |
parent | 765fd0c6ebdfbd1a0540211bc8b58e46076b41a3 (diff) |
Fix the atomicIncrement implementation for MIPS GCC
https://bugs.webkit.org/show_bug.cgi?id=106739
Patch by Balazs Kilvady <kilvadyb@homejinni.com> on 2013-02-26
Reviewed by Oliver Hunt.
Implementation of missing __sync_[add|sub]_and_fetch_8 functions.
Some architectures, like MIPS32, don't have GCC implementation for
builtin __sync_* functions with 64 bits variable size. GCC answer
for the problem: If a target doesn't support atomic operations on
certain variable sizes, you are out of luck with atomicity in that
case (http://gcc.gnu.org/bugzilla/show_bug.cgi?id=56296). GCC >= 4.8
will support __atomic_* builtin functions for this purpose for all
the GCC targets, but for current compilers we have to include our
own implementation.
* GNUmakefile.list.am:
* WTF.pro:
* wtf/Atomics.cpp: Added.
(WTF):
(WTF::getSwapLock):
(WTF::atomicStep):
* wtf/CMakeLists.txt:
git-svn-id: http://svn.webkit.org/repository/webkit/trunk@144077 268f45cc-cd09-0410-ab3c-d52691b4dbfc
Conflicts:
Source/WTF/ChangeLog
Change-Id: I98ce0ccd6747253ae6fa36fe9d338e155945a043
Reviewed-by: Allan Sandfeld Jensen <allan.jensen@digia.com>
Reviewed-by: Jocelyn Turcotte <jocelyn.turcotte@digia.com>
-rw-r--r-- | Source/WTF/ChangeLog | 26 | ||||
-rw-r--r-- | Source/WTF/GNUmakefile.list.am | 1 | ||||
-rw-r--r-- | Source/WTF/WTF.pro | 1 | ||||
-rw-r--r-- | Source/WTF/wtf/Atomics.cpp | 111 | ||||
-rw-r--r-- | Source/WTF/wtf/CMakeLists.txt | 1 |
5 files changed, 140 insertions, 0 deletions
diff --git a/Source/WTF/ChangeLog b/Source/WTF/ChangeLog index 0f8b6debe..fe3005dc0 100644 --- a/Source/WTF/ChangeLog +++ b/Source/WTF/ChangeLog @@ -1,3 +1,29 @@ +2013-02-26 Balazs Kilvady <kilvadyb@homejinni.com> + + Fix the atomicIncrement implementation for MIPS GCC + https://bugs.webkit.org/show_bug.cgi?id=106739 + + Reviewed by Oliver Hunt. + + Implementation of missing __sync_[add|sub]_and_fetch_8 functions. + + Some architectures, like MIPS32, don't have GCC implementation for + builtin __sync_* functions with 64 bits variable size. GCC answer + for the problem: If a target doesn't support atomic operations on + certain variable sizes, you are out of luck with atomicity in that + case (http://gcc.gnu.org/bugzilla/show_bug.cgi?id=56296). GCC >= 4.8 + will support __atomic_* builtin functions for this purpose for all + the GCC targets, but for current compilers we have to include our + own implementation. + + * GNUmakefile.list.am: + * WTF.pro: + * wtf/Atomics.cpp: Added. + (WTF): + (WTF::getSwapLock): + (WTF::atomicStep): + * wtf/CMakeLists.txt: + 2013-02-18 Balazs Kilvady <kilvadyb@homejinni.com> MIPS DFG implementation. diff --git a/Source/WTF/GNUmakefile.list.am b/Source/WTF/GNUmakefile.list.am index 88cce1398..0955a0587 100644 --- a/Source/WTF/GNUmakefile.list.am +++ b/Source/WTF/GNUmakefile.list.am @@ -11,6 +11,7 @@ wtf_sources += \ Source/WTF/wtf/ArrayBufferView.h \ Source/WTF/wtf/Assertions.cpp \ Source/WTF/wtf/Assertions.h \ + Source/WTF/wtf/Atomics.cpp \ Source/WTF/wtf/Atomics.h \ Source/WTF/wtf/BitArray.h \ Source/WTF/wtf/BitVector.cpp \ diff --git a/Source/WTF/WTF.pro b/Source/WTF/WTF.pro index 366194bbd..8725afb08 100644 --- a/Source/WTF/WTF.pro +++ b/Source/WTF/WTF.pro @@ -196,6 +196,7 @@ SOURCES += \ ArrayBuffer.cpp \ ArrayBufferView.cpp \ Assertions.cpp \ + Atomics.cpp \ BitVector.cpp \ CryptographicallyRandomNumber.cpp \ CurrentTime.cpp \ diff --git a/Source/WTF/wtf/Atomics.cpp b/Source/WTF/wtf/Atomics.cpp new file mode 100644 index 000000000..bcaedf740 --- /dev/null +++ b/Source/WTF/wtf/Atomics.cpp @@ -0,0 +1,111 @@ +/* + * Copyright (C) 2007, 2008, 2010, 2012 Apple Inc. All rights reserved. + * Copyright (C) 2007 Justin Haygood (jhaygood@reaktix.com) + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of + * its contributors may be used to endorse or promote products derived + * from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY + * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * + * Note: The implementations of InterlockedIncrement and InterlockedDecrement are based + * on atomic_increment and atomic_exchange_and_add from the Boost C++ Library. The license + * is virtually identical to the Apple license above but is included here for completeness. + * + * Boost Software License - Version 1.0 - August 17th, 2003 + * + * Permission is hereby granted, free of charge, to any person or organization + * obtaining a copy of the software and accompanying documentation covered by + * this license (the "Software") to use, reproduce, display, distribute, + * execute, and transmit the Software, and to prepare derivative works of the + * Software, and to permit third-parties to whom the Software is furnished to + * do so, all subject to the following: + * + * The copyright notices in the Software and this entire statement, including + * the above license grant, this restriction and the following disclaimer, + * must be included in all copies of the Software, in whole or in part, and + * all derivative works of the Software, unless such copies or derivative + * works are solely in the form of machine-executable object code generated by + * a source language processor. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT + * SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE + * FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER + * DEALINGS IN THE SOFTWARE. + */ + +#include "config.h" + +// Some architectures, like MIPS32, don't have GCC implementation for builtin __sync_* functions +// with 64 bits variable size. Official GCC answer for the problem: If a target doesn't support +// atomic operations on certain variable sizes, you are out of luck with atomicity in that case +// (http://gcc.gnu.org/bugzilla/show_bug.cgi?id=56296). GCC >= 4.8 will support __atomic_* builtin +// functions for this purpose for all the GCC targets, but for current compilers we have to include +// our own implementation. +#if COMPILER(GCC) && !defined(__GCC_HAVE_SYNC_COMPARE_AND_SWAP_8) && USE(LOCKFREE_THREADSAFEREFCOUNTED) && USE(PTHREADS) + +#include "Atomics.h" + +#include "ThreadingPrimitives.h" + +namespace WTF { + +static const size_t kSwapLockCount = 32; +static Mutex s_swapLocks[kSwapLockCount]; + +static inline Mutex& getSwapLock(const volatile int64_t* addr) +{ + return s_swapLocks[(reinterpret_cast<intptr_t>(addr) >> 3U) % kSwapLockCount]; +} + +static int64_t atomicStep(int64_t volatile* addend, int64_t step) +{ + Mutex& mutex = getSwapLock(addend); + + mutex.lock(); + int64_t value = *addend + step; + *addend = value; + mutex.unlock(); + + return value; +} + +extern "C" { + +int64_t __sync_add_and_fetch_8(int64_t volatile* addend, int64_t value) +{ + return atomicStep(addend, value); +} + +int64_t __sync_sub_and_fetch_8(int64_t volatile* addend, int64_t value) +{ + return atomicStep(addend, -value); +} + +} // extern "C" + +} // namespace WTF + +#endif diff --git a/Source/WTF/wtf/CMakeLists.txt b/Source/WTF/wtf/CMakeLists.txt index 9ba49504b..b7f437c64 100644 --- a/Source/WTF/wtf/CMakeLists.txt +++ b/Source/WTF/wtf/CMakeLists.txt @@ -157,6 +157,7 @@ SET(WTF_SOURCES ArrayBuffer.cpp ArrayBufferView.cpp Assertions.cpp + Atomics.cpp BitVector.cpp CryptographicallyRandomNumber.cpp CurrentTime.cpp |