BVB Source Codes

mars Show ops_gcc_alpha.hpp Source code

Return Download mars: download ops_gcc_alpha.hpp Source code - Download mars Source code - Type:.hpp
  1. /*
  2.  * Distributed under the Boost Software License, Version 1.0.
  3.  * (See accompanying file LICENSE_1_0.txt or copy at
  4.  * http://www.boost.org/LICENSE_1_0.txt)
  5.  *
  6.  * Copyright (c) 2009 Helge Bahmann
  7.  * Copyright (c) 2013 Tim Blechmann
  8.  * Copyright (c) 2014 Andrey Semashev
  9.  */
  10. /*!
  11.  * \file   atomic/detail/ops_gcc_alpha.hpp
  12.  *
  13.  * This header contains implementation of the \c operations template.
  14.  */
  15.  
  16. #ifndef BOOST_ATOMIC_DETAIL_OPS_GCC_ALPHA_HPP_INCLUDED_
  17. #define BOOST_ATOMIC_DETAIL_OPS_GCC_ALPHA_HPP_INCLUDED_
  18.  
  19. #include <boost/memory_order.hpp>
  20. #include <boost/atomic/detail/config.hpp>
  21. #include <boost/atomic/detail/storage_type.hpp>
  22. #include <boost/atomic/detail/operations_fwd.hpp>
  23. #include <boost/atomic/capabilities.hpp>
  24.  
  25. #ifdef BOOST_HAS_PRAGMA_ONCE
  26. #pragma once
  27. #endif
  28.  
  29. namespace mars_boost {} namespace boost = mars_boost; namespace mars_boost {
  30. namespace atomics {
  31. namespace detail {
  32.  
  33. /*
  34.   Refer to http://h71000.www7.hp.com/doc/82final/5601/5601pro_004.html
  35.   (HP OpenVMS systems documentation) and the Alpha Architecture Reference Manual.
  36.  */
  37.  
  38. /*
  39.     NB: The most natural thing would be to write the increment/decrement
  40.     operators along the following lines:
  41.  
  42.     __asm__ __volatile__
  43.     (
  44.         "1: ldl_l %0,%1 \n"
  45.         "addl %0,1,%0 \n"
  46.         "stl_c %0,%1 \n"
  47.         "beq %0,1b\n"
  48.         : "=&b" (tmp)
  49.         : "m" (value)
  50.         : "cc"
  51.     );
  52.  
  53.     However according to the comments on the HP website and matching
  54.     comments in the Linux kernel sources this defies branch prediction,
  55.     as the cpu assumes that backward branches are always taken; so
  56.     instead copy the trick from the Linux kernel, introduce a forward
  57.     branch and back again.
  58.  
  59.     I have, however, had a hard time measuring the difference between
  60.     the two versions in microbenchmarks -- I am leaving it in nevertheless
  61.     as it apparently does not hurt either.
  62. */
  63.  
  64. struct gcc_alpha_operations_base
  65. {
  66.     static BOOST_FORCEINLINE void fence_before(memory_order order) BOOST_NOEXCEPT
  67.     {
  68.         if ((order & memory_order_release) != 0)
  69.             __asm__ __volatile__ ("mb" ::: "memory");
  70.     }
  71.  
  72.     static BOOST_FORCEINLINE void fence_after(memory_order order) BOOST_NOEXCEPT
  73.     {
  74.         if ((order & (memory_order_consume | memory_order_acquire)) != 0)
  75.             __asm__ __volatile__ ("mb" ::: "memory");
  76.     }
  77.  
  78.     static BOOST_FORCEINLINE void fence_after_store(memory_order order) BOOST_NOEXCEPT
  79.     {
  80.         if (order == memory_order_seq_cst)
  81.             __asm__ __volatile__ ("mb" ::: "memory");
  82.     }
  83. };
  84.  
  85.  
  86. template< bool Signed >
  87. struct operations< 4u, Signed > :
  88.     public gcc_alpha_operations_base
  89. {
  90.     typedef typename make_storage_type< 4u, Signed >::type storage_type;
  91.     typedef typename make_storage_type< 4u, Signed >::aligned aligned_storage_type;
  92.  
  93.     static BOOST_FORCEINLINE void store(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  94.     {
  95.         fence_before(order);
  96.         storage = v;
  97.         fence_after_store(order);
  98.     }
  99.  
  100.     static BOOST_FORCEINLINE storage_type load(storage_type const volatile& storage, memory_order order) BOOST_NOEXCEPT
  101.     {
  102.         storage_type v = storage;
  103.         fence_after(order);
  104.         return v;
  105.     }
  106.  
  107.     static BOOST_FORCEINLINE storage_type exchange(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  108.     {
  109.         storage_type original, tmp;
  110.         fence_before(order);
  111.         __asm__ __volatile__
  112.         (
  113.             "1:\n"
  114.             "mov %3, %1\n"
  115.             "ldl_l %0, %2\n"
  116.             "stl_c %1, %2\n"
  117.             "beq %1, 2f\n"
  118.  
  119.             ".subsection 2\n"
  120.             "2: br 1b\n"
  121.             ".previous\n"
  122.  
  123.             : "=&r" (original),  // %0
  124.               "=&r" (tmp)        // %1
  125.             : "m" (storage),     // %2
  126.               "r" (v)            // %3
  127.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  128.         );
  129.         fence_after(order);
  130.         return original;
  131.     }
  132.  
  133.     static BOOST_FORCEINLINE bool compare_exchange_weak(
  134.         storage_type volatile& storage, storage_type& expected, storage_type desired, memory_order success_order, memory_order failure_order) BOOST_NOEXCEPT
  135.     {
  136.         fence_before(success_order);
  137.         int success;
  138.         storage_type current;
  139.         __asm__ __volatile__
  140.         (
  141.             "1:\n"
  142.             "ldl_l %2, %4\n"                // current = *(&storage)
  143.             "cmpeq %2, %0, %3\n"            // success = current == expected
  144.             "mov %2, %0\n"                  // expected = current
  145.             "beq %3, 2f\n"                  // if (success == 0) goto end
  146.             "stl_c %1, %4\n"                // storage = desired; desired = store succeeded
  147.             "mov %1, %3\n"                  // success = desired
  148.             "2:\n"
  149.             : "+&r" (expected),  // %0
  150.               "+&r" (desired),   // %1
  151.               "=&r" (current),   // %2
  152.               "=&r" (success)    // %3
  153.             : "m" (storage)      // %4
  154.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  155.         );
  156.         if (success)
  157.             fence_after(success_order);
  158.         else
  159.             fence_after(failure_order);
  160.         return !!success;
  161.     }
  162.  
  163.     static BOOST_FORCEINLINE bool compare_exchange_strong(
  164.         storage_type volatile& storage, storage_type& expected, storage_type desired, memory_order success_order, memory_order failure_order) BOOST_NOEXCEPT
  165.     {
  166.         int success;
  167.         storage_type current, tmp;
  168.         fence_before(success_order);
  169.         __asm__ __volatile__
  170.         (
  171.             "1:\n"
  172.             "mov %5, %1\n"                  // tmp = desired
  173.             "ldl_l %2, %4\n"                // current = *(&storage)
  174.             "cmpeq %2, %0, %3\n"            // success = current == expected
  175.             "mov %2, %0\n"                  // expected = current
  176.             "beq %3, 2f\n"                  // if (success == 0) goto end
  177.             "stl_c %1, %4\n"                // storage = tmp; tmp = store succeeded
  178.             "beq %1, 3f\n"                  // if (tmp == 0) goto retry
  179.             "mov %1, %3\n"                  // success = tmp
  180.             "2:\n"
  181.  
  182.             ".subsection 2\n"
  183.             "3: br 1b\n"
  184.             ".previous\n"
  185.  
  186.             : "+&r" (expected),  // %0
  187.               "=&r" (tmp),       // %1
  188.               "=&r" (current),   // %2
  189.               "=&r" (success)    // %3
  190.             : "m" (storage),     // %4
  191.               "r" (desired)      // %5
  192.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  193.         );
  194.         if (success)
  195.             fence_after(success_order);
  196.         else
  197.             fence_after(failure_order);
  198.         return !!success;
  199.     }
  200.  
  201.     static BOOST_FORCEINLINE storage_type fetch_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  202.     {
  203.         storage_type original, modified;
  204.         fence_before(order);
  205.         __asm__ __volatile__
  206.         (
  207.             "1:\n"
  208.             "ldl_l %0, %2\n"
  209.             "addl %0, %3, %1\n"
  210.             "stl_c %1, %2\n"
  211.             "beq %1, 2f\n"
  212.  
  213.             ".subsection 2\n"
  214.             "2: br 1b\n"
  215.             ".previous\n"
  216.  
  217.             : "=&r" (original),  // %0
  218.               "=&r" (modified)   // %1
  219.             : "m" (storage),     // %2
  220.               "r" (v)            // %3
  221.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  222.         );
  223.         fence_after(order);
  224.         return original;
  225.     }
  226.  
  227.     static BOOST_FORCEINLINE storage_type fetch_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  228.     {
  229.         storage_type original, modified;
  230.         fence_before(order);
  231.         __asm__ __volatile__
  232.         (
  233.             "1:\n"
  234.             "ldl_l %0, %2\n"
  235.             "subl %0, %3, %1\n"
  236.             "stl_c %1, %2\n"
  237.             "beq %1, 2f\n"
  238.  
  239.             ".subsection 2\n"
  240.             "2: br 1b\n"
  241.             ".previous\n"
  242.  
  243.             : "=&r" (original),  // %0
  244.               "=&r" (modified)   // %1
  245.             : "m" (storage),     // %2
  246.               "r" (v)            // %3
  247.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  248.         );
  249.         fence_after(order);
  250.         return original;
  251.     }
  252.  
  253.     static BOOST_FORCEINLINE storage_type fetch_and(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  254.     {
  255.         storage_type original, modified;
  256.         fence_before(order);
  257.         __asm__ __volatile__
  258.         (
  259.             "1:\n"
  260.             "ldl_l %0, %2\n"
  261.             "and %0, %3, %1\n"
  262.             "stl_c %1, %2\n"
  263.             "beq %1, 2f\n"
  264.  
  265.             ".subsection 2\n"
  266.             "2: br 1b\n"
  267.             ".previous\n"
  268.  
  269.             : "=&r" (original),  // %0
  270.               "=&r" (modified)   // %1
  271.             : "m" (storage),     // %2
  272.               "r" (v)            // %3
  273.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  274.         );
  275.         fence_after(order);
  276.         return original;
  277.     }
  278.  
  279.     static BOOST_FORCEINLINE storage_type fetch_or(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  280.     {
  281.         storage_type original, modified;
  282.         fence_before(order);
  283.         __asm__ __volatile__
  284.         (
  285.             "1:\n"
  286.             "ldl_l %0, %2\n"
  287.             "bis %0, %3, %1\n"
  288.             "stl_c %1, %2\n"
  289.             "beq %1, 2f\n"
  290.  
  291.             ".subsection 2\n"
  292.             "2: br 1b\n"
  293.             ".previous\n"
  294.  
  295.             : "=&r" (original),  // %0
  296.               "=&r" (modified)   // %1
  297.             : "m" (storage),     // %2
  298.               "r" (v)            // %3
  299.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  300.         );
  301.         fence_after(order);
  302.         return original;
  303.     }
  304.  
  305.     static BOOST_FORCEINLINE storage_type fetch_xor(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  306.     {
  307.         storage_type original, modified;
  308.         fence_before(order);
  309.         __asm__ __volatile__
  310.         (
  311.             "1:\n"
  312.             "ldl_l %0, %2\n"
  313.             "xor %0, %3, %1\n"
  314.             "stl_c %1, %2\n"
  315.             "beq %1, 2f\n"
  316.  
  317.             ".subsection 2\n"
  318.             "2: br 1b\n"
  319.             ".previous\n"
  320.  
  321.             : "=&r" (original),  // %0
  322.               "=&r" (modified)   // %1
  323.             : "m" (storage),     // %2
  324.               "r" (v)            // %3
  325.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  326.         );
  327.         fence_after(order);
  328.         return original;
  329.     }
  330.  
  331.     static BOOST_FORCEINLINE bool test_and_set(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
  332.     {
  333.         return !!exchange(storage, (storage_type)1, order);
  334.     }
  335.  
  336.     static BOOST_FORCEINLINE void clear(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
  337.     {
  338.         store(storage, 0, order);
  339.     }
  340.  
  341.     static BOOST_FORCEINLINE bool is_lock_free(storage_type const volatile&) BOOST_NOEXCEPT
  342.     {
  343.         return true;
  344.     }
  345. };
  346.  
  347.  
  348. template< >
  349. struct operations< 1u, false > :
  350.     public operations< 4u, false >
  351. {
  352.     typedef operations< 4u, false > base_type;
  353.     typedef base_type::storage_type storage_type;
  354.  
  355.     static BOOST_FORCEINLINE storage_type fetch_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  356.     {
  357.         storage_type original, modified;
  358.         fence_before(order);
  359.         __asm__ __volatile__
  360.         (
  361.             "1:\n"
  362.             "ldl_l %0, %2\n"
  363.             "addl %0, %3, %1\n"
  364.             "zapnot %1, #1, %1\n"
  365.             "stl_c %1, %2\n"
  366.             "beq %1, 2f\n"
  367.  
  368.             ".subsection 2\n"
  369.             "2: br 1b\n"
  370.             ".previous\n"
  371.  
  372.             : "=&r" (original),  // %0
  373.               "=&r" (modified)   // %1
  374.             : "m" (storage),     // %2
  375.               "r" (v)            // %3
  376.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  377.         );
  378.         fence_after(order);
  379.         return original;
  380.     }
  381.  
  382.     static BOOST_FORCEINLINE storage_type fetch_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  383.     {
  384.         storage_type original, modified;
  385.         fence_before(order);
  386.         __asm__ __volatile__
  387.         (
  388.             "1:\n"
  389.             "ldl_l %0, %2\n"
  390.             "subl %0, %3, %1\n"
  391.             "zapnot %1, #1, %1\n"
  392.             "stl_c %1, %2\n"
  393.             "beq %1, 2f\n"
  394.  
  395.             ".subsection 2\n"
  396.             "2: br 1b\n"
  397.             ".previous\n"
  398.  
  399.             : "=&r" (original),  // %0
  400.               "=&r" (modified)   // %1
  401.             : "m" (storage),     // %2
  402.               "r" (v)            // %3
  403.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  404.         );
  405.         fence_after(order);
  406.         return original;
  407.     }
  408. };
  409.  
  410. template< >
  411. struct operations< 1u, true > :
  412.     public operations< 4u, true >
  413. {
  414.     typedef operations< 4u, true > base_type;
  415.     typedef base_type::storage_type storage_type;
  416.  
  417.     static BOOST_FORCEINLINE storage_type fetch_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  418.     {
  419.         storage_type original, modified;
  420.         fence_before(order);
  421.         __asm__ __volatile__
  422.         (
  423.             "1:\n"
  424.             "ldl_l %0, %2\n"
  425.             "addl %0, %3, %1\n"
  426.             "sextb %1, %1\n"
  427.             "stl_c %1, %2\n"
  428.             "beq %1, 2f\n"
  429.  
  430.             ".subsection 2\n"
  431.             "2: br 1b\n"
  432.             ".previous\n"
  433.  
  434.             : "=&r" (original),  // %0
  435.               "=&r" (modified)   // %1
  436.             : "m" (storage),     // %2
  437.               "r" (v)            // %3
  438.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  439.         );
  440.         fence_after(order);
  441.         return original;
  442.     }
  443.  
  444.     static BOOST_FORCEINLINE storage_type fetch_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  445.     {
  446.         storage_type original, modified;
  447.         fence_before(order);
  448.         __asm__ __volatile__
  449.         (
  450.             "1:\n"
  451.             "ldl_l %0, %2\n"
  452.             "subl %0, %3, %1\n"
  453.             "sextb %1, %1\n"
  454.             "stl_c %1, %2\n"
  455.             "beq %1, 2f\n"
  456.  
  457.             ".subsection 2\n"
  458.             "2: br 1b\n"
  459.             ".previous\n"
  460.  
  461.             : "=&r" (original),  // %0
  462.               "=&r" (modified)   // %1
  463.             : "m" (storage),     // %2
  464.               "r" (v)            // %3
  465.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  466.         );
  467.         fence_after(order);
  468.         return original;
  469.     }
  470. };
  471.  
  472.  
  473. template< >
  474. struct operations< 2u, false > :
  475.     public operations< 4u, false >
  476. {
  477.     typedef operations< 4u, false > base_type;
  478.     typedef base_type::storage_type storage_type;
  479.  
  480.     static BOOST_FORCEINLINE storage_type fetch_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  481.     {
  482.         storage_type original, modified;
  483.         fence_before(order);
  484.         __asm__ __volatile__
  485.         (
  486.             "1:\n"
  487.             "ldl_l %0, %2\n"
  488.             "addl %0, %3, %1\n"
  489.             "zapnot %1, #3, %1\n"
  490.             "stl_c %1, %2\n"
  491.             "beq %1, 2f\n"
  492.  
  493.             ".subsection 2\n"
  494.             "2: br 1b\n"
  495.             ".previous\n"
  496.  
  497.             : "=&r" (original),  // %0
  498.               "=&r" (modified)   // %1
  499.             : "m" (storage),     // %2
  500.               "r" (v)            // %3
  501.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  502.         );
  503.         fence_after(order);
  504.         return original;
  505.     }
  506.  
  507.     static BOOST_FORCEINLINE storage_type fetch_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  508.     {
  509.         storage_type original, modified;
  510.         fence_before(order);
  511.         __asm__ __volatile__
  512.         (
  513.             "1:\n"
  514.             "ldl_l %0, %2\n"
  515.             "subl %0, %3, %1\n"
  516.             "zapnot %1, #3, %1\n"
  517.             "stl_c %1, %2\n"
  518.             "beq %1, 2f\n"
  519.  
  520.             ".subsection 2\n"
  521.             "2: br 1b\n"
  522.             ".previous\n"
  523.  
  524.             : "=&r" (original),  // %0
  525.               "=&r" (modified)   // %1
  526.             : "m" (storage),     // %2
  527.               "r" (v)            // %3
  528.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  529.         );
  530.         fence_after(order);
  531.         return original;
  532.     }
  533. };
  534.  
  535. template< >
  536. struct operations< 2u, true > :
  537.     public operations< 4u, true >
  538. {
  539.     typedef operations< 4u, true > base_type;
  540.     typedef base_type::storage_type storage_type;
  541.  
  542.     static BOOST_FORCEINLINE storage_type fetch_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  543.     {
  544.         storage_type original, modified;
  545.         fence_before(order);
  546.         __asm__ __volatile__
  547.         (
  548.             "1:\n"
  549.             "ldl_l %0, %2\n"
  550.             "addl %0, %3, %1\n"
  551.             "sextw %1, %1\n"
  552.             "stl_c %1, %2\n"
  553.             "beq %1, 2f\n"
  554.  
  555.             ".subsection 2\n"
  556.             "2: br 1b\n"
  557.             ".previous\n"
  558.  
  559.             : "=&r" (original),  // %0
  560.               "=&r" (modified)   // %1
  561.             : "m" (storage),     // %2
  562.               "r" (v)            // %3
  563.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  564.         );
  565.         fence_after(order);
  566.         return original;
  567.     }
  568.  
  569.     static BOOST_FORCEINLINE storage_type fetch_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  570.     {
  571.         storage_type original, modified;
  572.         fence_before(order);
  573.         __asm__ __volatile__
  574.         (
  575.             "1:\n"
  576.             "ldl_l %0, %2\n"
  577.             "subl %0, %3, %1\n"
  578.             "sextw %1, %1\n"
  579.             "stl_c %1, %2\n"
  580.             "beq %1, 2f\n"
  581.  
  582.             ".subsection 2\n"
  583.             "2: br 1b\n"
  584.             ".previous\n"
  585.  
  586.             : "=&r" (original),  // %0
  587.               "=&r" (modified)   // %1
  588.             : "m" (storage),     // %2
  589.               "r" (v)            // %3
  590.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  591.         );
  592.         fence_after(order);
  593.         return original;
  594.     }
  595. };
  596.  
  597.  
  598. template< bool Signed >
  599. struct operations< 8u, Signed > :
  600.     public gcc_alpha_operations_base
  601. {
  602.     typedef typename make_storage_type< 8u, Signed >::type storage_type;
  603.     typedef typename make_storage_type< 8u, Signed >::aligned aligned_storage_type;
  604.  
  605.     static BOOST_FORCEINLINE void store(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  606.     {
  607.         fence_before(order);
  608.         storage = v;
  609.         fence_after_store(order);
  610.     }
  611.  
  612.     static BOOST_FORCEINLINE storage_type load(storage_type const volatile& storage, memory_order order) BOOST_NOEXCEPT
  613.     {
  614.         storage_type v = storage;
  615.         fence_after(order);
  616.         return v;
  617.     }
  618.  
  619.     static BOOST_FORCEINLINE storage_type exchange(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  620.     {
  621.         storage_type original, tmp;
  622.         fence_before(order);
  623.         __asm__ __volatile__
  624.         (
  625.             "1:\n"
  626.             "mov %3, %1\n"
  627.             "ldq_l %0, %2\n"
  628.             "stq_c %1, %2\n"
  629.             "beq %1, 2f\n"
  630.  
  631.             ".subsection 2\n"
  632.             "2: br 1b\n"
  633.             ".previous\n"
  634.  
  635.             : "=&r" (original),  // %0
  636.               "=&r" (tmp)        // %1
  637.             : "m" (storage),     // %2
  638.               "r" (v)            // %3
  639.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  640.         );
  641.         fence_after(order);
  642.         return original;
  643.     }
  644.  
  645.     static BOOST_FORCEINLINE bool compare_exchange_weak(
  646.         storage_type volatile& storage, storage_type& expected, storage_type desired, memory_order success_order, memory_order failure_order) BOOST_NOEXCEPT
  647.     {
  648.         fence_before(success_order);
  649.         int success;
  650.         storage_type current;
  651.         __asm__ __volatile__
  652.         (
  653.             "1:\n"
  654.             "ldq_l %2, %4\n"                // current = *(&storage)
  655.             "cmpeq %2, %0, %3\n"            // success = current == expected
  656.             "mov %2, %0\n"                  // expected = current
  657.             "beq %3, 2f\n"                  // if (success == 0) goto end
  658.             "stq_c %1, %4\n"                // storage = desired; desired = store succeeded
  659.             "mov %1, %3\n"                  // success = desired
  660.             "2:\n"
  661.             : "+&r" (expected),  // %0
  662.               "+&r" (desired),   // %1
  663.               "=&r" (current),   // %2
  664.               "=&r" (success)    // %3
  665.             : "m" (storage)      // %4
  666.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  667.         );
  668.         if (success)
  669.             fence_after(success_order);
  670.         else
  671.             fence_after(failure_order);
  672.         return !!success;
  673.     }
  674.  
  675.     static BOOST_FORCEINLINE bool compare_exchange_strong(
  676.         storage_type volatile& storage, storage_type& expected, storage_type desired, memory_order success_order, memory_order failure_order) BOOST_NOEXCEPT
  677.     {
  678.         int success;
  679.         storage_type current, tmp;
  680.         fence_before(success_order);
  681.         __asm__ __volatile__
  682.         (
  683.             "1:\n"
  684.             "mov %5, %1\n"                  // tmp = desired
  685.             "ldq_l %2, %4\n"                // current = *(&storage)
  686.             "cmpeq %2, %0, %3\n"            // success = current == expected
  687.             "mov %2, %0\n"                  // expected = current
  688.             "beq %3, 2f\n"                  // if (success == 0) goto end
  689.             "stq_c %1, %4\n"                // storage = tmp; tmp = store succeeded
  690.             "beq %1, 3f\n"                  // if (tmp == 0) goto retry
  691.             "mov %1, %3\n"                  // success = tmp
  692.             "2:\n"
  693.  
  694.             ".subsection 2\n"
  695.             "3: br 1b\n"
  696.             ".previous\n"
  697.  
  698.             : "+&r" (expected),  // %0
  699.               "=&r" (tmp),       // %1
  700.               "=&r" (current),   // %2
  701.               "=&r" (success)    // %3
  702.             : "m" (storage),     // %4
  703.               "r" (desired)      // %5
  704.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  705.         );
  706.         if (success)
  707.             fence_after(success_order);
  708.         else
  709.             fence_after(failure_order);
  710.         return !!success;
  711.     }
  712.  
  713.     static BOOST_FORCEINLINE storage_type fetch_add(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  714.     {
  715.         storage_type original, modified;
  716.         fence_before(order);
  717.         __asm__ __volatile__
  718.         (
  719.             "1:\n"
  720.             "ldq_l %0, %2\n"
  721.             "addq %0, %3, %1\n"
  722.             "stq_c %1, %2\n"
  723.             "beq %1, 2f\n"
  724.  
  725.             ".subsection 2\n"
  726.             "2: br 1b\n"
  727.             ".previous\n"
  728.  
  729.             : "=&r" (original),  // %0
  730.               "=&r" (modified)   // %1
  731.             : "m" (storage),     // %2
  732.               "r" (v)            // %3
  733.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  734.         );
  735.         fence_after(order);
  736.         return original;
  737.     }
  738.  
  739.     static BOOST_FORCEINLINE storage_type fetch_sub(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  740.     {
  741.         storage_type original, modified;
  742.         fence_before(order);
  743.         __asm__ __volatile__
  744.         (
  745.             "1:\n"
  746.             "ldq_l %0, %2\n"
  747.             "subq %0, %3, %1\n"
  748.             "stq_c %1, %2\n"
  749.             "beq %1, 2f\n"
  750.  
  751.             ".subsection 2\n"
  752.             "2: br 1b\n"
  753.             ".previous\n"
  754.  
  755.             : "=&r" (original),  // %0
  756.               "=&r" (modified)   // %1
  757.             : "m" (storage),     // %2
  758.               "r" (v)            // %3
  759.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  760.         );
  761.         fence_after(order);
  762.         return original;
  763.     }
  764.  
  765.     static BOOST_FORCEINLINE storage_type fetch_and(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  766.     {
  767.         storage_type original, modified;
  768.         fence_before(order);
  769.         __asm__ __volatile__
  770.         (
  771.             "1:\n"
  772.             "ldq_l %0, %2\n"
  773.             "and %0, %3, %1\n"
  774.             "stq_c %1, %2\n"
  775.             "beq %1, 2f\n"
  776.  
  777.             ".subsection 2\n"
  778.             "2: br 1b\n"
  779.             ".previous\n"
  780.  
  781.             : "=&r" (original),  // %0
  782.               "=&r" (modified)   // %1
  783.             : "m" (storage),     // %2
  784.               "r" (v)            // %3
  785.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  786.         );
  787.         fence_after(order);
  788.         return original;
  789.     }
  790.  
  791.     static BOOST_FORCEINLINE storage_type fetch_or(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  792.     {
  793.         storage_type original, modified;
  794.         fence_before(order);
  795.         __asm__ __volatile__
  796.         (
  797.             "1:\n"
  798.             "ldq_l %0, %2\n"
  799.             "bis %0, %3, %1\n"
  800.             "stq_c %1, %2\n"
  801.             "beq %1, 2f\n"
  802.  
  803.             ".subsection 2\n"
  804.             "2: br 1b\n"
  805.             ".previous\n"
  806.  
  807.             : "=&r" (original),  // %0
  808.               "=&r" (modified)   // %1
  809.             : "m" (storage),     // %2
  810.               "r" (v)            // %3
  811.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  812.         );
  813.         fence_after(order);
  814.         return original;
  815.     }
  816.  
  817.     static BOOST_FORCEINLINE storage_type fetch_xor(storage_type volatile& storage, storage_type v, memory_order order) BOOST_NOEXCEPT
  818.     {
  819.         storage_type original, modified;
  820.         fence_before(order);
  821.         __asm__ __volatile__
  822.         (
  823.             "1:\n"
  824.             "ldq_l %0, %2\n"
  825.             "xor %0, %3, %1\n"
  826.             "stq_c %1, %2\n"
  827.             "beq %1, 2f\n"
  828.  
  829.             ".subsection 2\n"
  830.             "2: br 1b\n"
  831.             ".previous\n"
  832.  
  833.             : "=&r" (original),  // %0
  834.               "=&r" (modified)   // %1
  835.             : "m" (storage),     // %2
  836.               "r" (v)            // %3
  837.             : BOOST_ATOMIC_DETAIL_ASM_CLOBBER_CC
  838.         );
  839.         fence_after(order);
  840.         return original;
  841.     }
  842.  
  843.     static BOOST_FORCEINLINE bool test_and_set(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
  844.     {
  845.         return !!exchange(storage, (storage_type)1, order);
  846.     }
  847.  
  848.     static BOOST_FORCEINLINE void clear(storage_type volatile& storage, memory_order order) BOOST_NOEXCEPT
  849.     {
  850.         store(storage, 0, order);
  851.     }
  852.  
  853.     static BOOST_FORCEINLINE bool is_lock_free(storage_type const volatile&) BOOST_NOEXCEPT
  854.     {
  855.         return true;
  856.     }
  857. };
  858.  
  859.  
  860. BOOST_FORCEINLINE void thread_fence(memory_order order) BOOST_NOEXCEPT
  861. {
  862.     if (order != memory_order_relaxed)
  863.         __asm__ __volatile__ ("mb" ::: "memory");
  864. }
  865.  
  866. BOOST_FORCEINLINE void signal_fence(memory_order order) BOOST_NOEXCEPT
  867. {
  868.     if (order != memory_order_relaxed)
  869.         __asm__ __volatile__ ("" ::: "memory");
  870. }
  871.  
  872. } // namespace detail
  873. } // namespace atomics
  874. } // namespace mars_boost
  875.  
  876. #endif // BOOST_ATOMIC_DETAIL_OPS_GCC_ALPHA_HPP_INCLUDED_
  877.  
downloadops_gcc_alpha.hpp Source code - Download mars Source code
Related Source Codes/Software:
Hero - Elegant transition library for iOS & tvOS 2017-06-09
deep-photo-styletransfer - Code and data for paper "Deep Photo Style Transfer... 2017-06-09
mastodon - A GNU Social-compatible microblogging server ... 2017-06-09
plyr - A simple HTML5, YouTube and Vimeo player ... 2017-06-08
prepack - Prepack is a partial evaluator for JavaScript. Pre... 2017-06-08
Public-APIs - 2017-06-09
lottie-ios - An iOS library to natively render After Effects ve... 2017-06-09
Awesome-Hacking - A collection of various awesome lists for hackers,... 2017-06-09
algorithms - Minimal examples of data structures and algorithms... 2017-06-10
lectures - Oxford Deep NLP 2017 course 2017-06-10
CRYENGINE - CRYENGINE is a powerful real-time game development... 2017-06-11
postal - 2017-06-11
reactide - Reactide is the first dedicated IDE for React web ... 2017-06-11
rkt - rkt is a pod-native container engine for Linux. It... 2017-06-11
uWebSockets - Tiny WebSockets https://for... 2017-06-11
realworld - TodoMVC for the RealWorld - Exemplary fullstack Me... 2017-06-11
goreplay - GoReplay is an open-source tool for capturing and ... 2017-06-10
pyenv - Simple Python version management 2017-06-10
redux-saga - An alternative side effect model for Redux apps ... 2017-06-10
angular-starter - 2017-06-10

 Back to top