atomic_count_gcc_x86.hpp 1.5 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677
  1. #ifndef BOOST_SMART_PTR_DETAIL_ATOMIC_COUNT_GCC_X86_HPP_INCLUDED
  2. #define BOOST_SMART_PTR_DETAIL_ATOMIC_COUNT_GCC_X86_HPP_INCLUDED
  3. //
  4. // boost/detail/atomic_count_gcc_x86.hpp
  5. //
  6. // atomic_count for g++ on 486+/AMD64
  7. //
  8. // Copyright 2007 Peter Dimov
  9. //
  10. // Distributed under the Boost Software License, Version 1.0. (See
  11. // accompanying file LICENSE_1_0.txt or copy at
  12. // http://www.boost.org/LICENSE_1_0.txt)
  13. //
  14. namespace boost
  15. {
  16. namespace detail
  17. {
  18. class atomic_count
  19. {
  20. public:
  21. explicit atomic_count( long v ) : value_( static_cast< int >( v ) ) {}
  22. long operator++()
  23. {
  24. return atomic_exchange_and_add( &value_, +1 ) + 1;
  25. }
  26. long operator--()
  27. {
  28. return atomic_exchange_and_add( &value_, -1 ) - 1;
  29. }
  30. operator long() const
  31. {
  32. return atomic_exchange_and_add( &value_, 0 );
  33. }
  34. private:
  35. atomic_count(atomic_count const &);
  36. atomic_count & operator=(atomic_count const &);
  37. mutable int value_;
  38. private:
  39. static int atomic_exchange_and_add( int * pw, int dv )
  40. {
  41. // int r = *pw;
  42. // *pw += dv;
  43. // return r;
  44. int r;
  45. __asm__ __volatile__
  46. (
  47. "lock\n\t"
  48. "xadd %1, %0":
  49. "+m"( *pw ), "=r"( r ): // outputs (%0, %1)
  50. "1"( dv ): // inputs (%2 == %1)
  51. "memory", "cc" // clobbers
  52. );
  53. return r;
  54. }
  55. };
  56. } // namespace detail
  57. } // namespace boost
  58. #endif // #ifndef BOOST_SMART_PTR_DETAIL_ATOMIC_COUNT_GCC_X86_HPP_INCLUDED