"Fossies" - the Fresh Open Source Software Archive

Member "openpa-1.0.4/src/primitives/opa_emulated.h" (5 Dec 2012, 4090 Bytes) of package /linux/misc/openpa-1.0.4.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "opa_emulated.h" see the Fossies "Dox" file reference documentation.

    1 /* -*- Mode: C; c-basic-offset:4 ; indent-tabs-mode:nil ; -*- */
    2 /*
    3  *  (C) 2008 by Argonne National Laboratory.
    4  *      See COPYRIGHT in top-level directory.
    5  */
    6 
    7 #ifndef OPA_EMULATED_H_INCLUDED
    8 #define OPA_EMULATED_H_INCLUDED
    9 
   10 /* Functions emulated using other atomics
   11 
   12    This header should be included at the bottom of any atomic
   13    primitives header that needs to implement an atomic op in terms of
   14    another atomic.
   15 */
   16 
   17 /* Emulating using LL/SC */
   18 #if defined(OPA_LL_SC_SUPPORTED)
   19 static _opa_inline int OPA_fetch_and_add_int_by_llsc(OPA_int_t *ptr, int val)
   20 {
   21     int prev;
   22     do {
   23         prev = OPA_LL_int(ptr);
   24     } while (!OPA_SC_int(ptr, prev + val));
   25     return prev;
   26 }
   27 
   28 
   29 static _opa_inline void OPA_add_int_by_llsc(OPA_int_t *ptr, int val)
   30 {
   31     OPA_fetch_and_add_int_by_llsc(ptr, val);
   32 }
   33 
   34 static _opa_inline void OPA_incr_int_by_llsc(OPA_int_t *ptr)
   35 {
   36     OPA_add_int_by_llsc(ptr, 1);
   37 }
   38 
   39 static _opa_inline void OPA_decr_int_by_llsc(OPA_int_t *ptr)
   40 {
   41     OPA_add_int_by_llsc(ptr, -1);
   42 }
   43 
   44 
   45 static _opa_inline int OPA_fetch_and_decr_int_by_llsc(OPA_int_t *ptr)
   46 {
   47     return OPA_fetch_and_add_int_by_llsc(ptr, -1);
   48 }
   49 
   50 static _opa_inline int OPA_fetch_and_incr_int_by_llsc(OPA_int_t *ptr)
   51 {
   52     return OPA_fetch_and_add_int_by_llsc(ptr, 1);
   53 }
   54 
   55 static _opa_inline int OPA_decr_and_test_int_by_llsc(OPA_int_t *ptr)
   56 {
   57     int prev = OPA_fetch_and_decr_int_by_llsc(ptr);
   58     return prev == 1;
   59 }
   60 
   61 static _opa_inline void *OPA_cas_ptr_by_llsc(OPA_ptr_t *ptr, void *oldv, void *newv)
   62 {
   63     void *prev;
   64     do {
   65         prev = OPA_LL_ptr(ptr);
   66     } while (prev == oldv && !OPA_SC_ptr(ptr, newv));
   67     return prev;
   68 }
   69 
   70 static _opa_inline int OPA_cas_int_by_llsc(OPA_int_t *ptr, int oldv, int newv)
   71 {
   72     int prev;
   73     do {
   74         prev = OPA_LL_int(ptr);
   75     } while (prev == oldv && !OPA_SC_int(ptr, newv));
   76     return prev;
   77 }
   78 
   79 
   80 static _opa_inline void *OPA_swap_ptr_by_llsc(OPA_ptr_t *ptr, void *val)
   81 {
   82     void *prev;
   83     do {
   84         prev = OPA_LL_ptr(ptr);
   85     } while (!OPA_SC_ptr(ptr, val));
   86     return prev;
   87 }
   88 
   89 static _opa_inline int OPA_swap_int_by_llsc(OPA_int_t *ptr, int val)
   90 {
   91     int prev;
   92     do {
   93         prev = OPA_LL_int(ptr);
   94     } while (!OPA_SC_int(ptr, val));
   95     return prev;
   96 }
   97 
   98 #endif /* OPA_LL_SC_SUPPORTED */
   99 
  100 static _opa_inline int OPA_fetch_and_add_int_by_cas(OPA_int_t *ptr, int val)
  101 {
  102     int cmp;
  103     int prev = OPA_load_int(ptr);
  104 
  105     do {
  106         cmp = prev;
  107         prev = OPA_cas_int(ptr, cmp, prev + val);
  108     } while (prev != cmp);
  109 
  110     return prev;
  111 }
  112 
  113 static _opa_inline int OPA_fetch_and_incr_int_by_faa(OPA_int_t *ptr)
  114 {
  115     return OPA_fetch_and_add_int(ptr, 1);
  116 }
  117 
  118 static _opa_inline int OPA_fetch_and_decr_int_by_faa(OPA_int_t *ptr)
  119 {
  120     return OPA_fetch_and_add_int(ptr, -1);
  121 }
  122 
  123 static _opa_inline int OPA_decr_and_test_int_by_fad(OPA_int_t *ptr)
  124 {
  125     return OPA_fetch_and_decr_int(ptr) == 1;
  126 }
  127 
  128 static _opa_inline void OPA_add_int_by_faa(OPA_int_t *ptr, int val)
  129 {
  130     OPA_fetch_and_add_int(ptr, val);
  131 }
  132 
  133 static _opa_inline int OPA_incr_int_by_faa(OPA_int_t *ptr)
  134 {
  135     return OPA_fetch_and_add_int(ptr, 1);
  136 }
  137 
  138 static _opa_inline void OPA_incr_int_by_add(OPA_int_t *ptr)
  139 {
  140     OPA_add_int(ptr, 1);
  141 }
  142 
  143 static _opa_inline void OPA_incr_int_by_fai(OPA_int_t *ptr)
  144 {
  145     OPA_fetch_and_incr_int(ptr);
  146 }
  147 
  148 static _opa_inline int OPA_decr_int_by_faa(OPA_int_t *ptr)
  149 {
  150     return OPA_fetch_and_add_int(ptr, -1);
  151 }
  152 
  153 static _opa_inline void OPA_decr_int_by_add(OPA_int_t *ptr)
  154 {
  155     OPA_add_int(ptr, -1);
  156 }
  157 
  158 static _opa_inline void OPA_decr_int_by_fad(OPA_int_t *ptr)
  159 {
  160     OPA_fetch_and_decr_int(ptr);
  161 }
  162 
  163 
  164 /* Swap using CAS */
  165 
  166 static _opa_inline void *OPA_swap_ptr_by_cas(OPA_ptr_t *ptr, void *val)
  167 {
  168     void *cmp;
  169     void *prev = OPA_load_ptr(ptr);
  170 
  171     do {
  172         cmp = prev;
  173         prev = OPA_cas_ptr(ptr, cmp, val);
  174     } while (prev != cmp);
  175 
  176     return prev;
  177 }
  178 
  179 static _opa_inline int OPA_swap_int_by_cas(OPA_int_t *ptr, int val)
  180 {
  181     int cmp;
  182     int prev = OPA_load_int(ptr);
  183 
  184     do {
  185         cmp = prev;
  186         prev = OPA_cas_int(ptr, cmp, val);
  187     } while (prev != cmp);
  188 
  189     return prev;
  190 }
  191 
  192 #endif /* OPA_EMULATED_H_INCLUDED */