19 #include <my_atomic.h> 
   28 #define lock_wrap(f, t, proto_args, args, lock) \ 
   29 t _ ## f proto_args;                            \ 
   30 static inline t f  proto_args                   \ 
   33   my_atomic_rwlock_wrlock(lock);                \ 
   35   my_atomic_rwlock_wrunlock(lock);              \ 
   39 #define lock_wrap_void(f, proto_args, args, lock) \ 
   40 void _ ## f proto_args;                         \ 
   41 static inline void f proto_args                 \ 
   43   my_atomic_rwlock_wrlock(lock);                \ 
   45   my_atomic_rwlock_wrunlock(lock);              \ 
   48 #define nolock_wrap(f, t, proto_args, args)     \ 
   49 t _ ## f proto_args;                            \ 
   50 static inline t f  proto_args                   \ 
   55 #define nolock_wrap_void(f, proto_args, args)   \ 
   56 void _ ## f proto_args;                         \ 
   57 static inline void f proto_args                 \ 
   68 #define LF_DYNARRAY_LEVEL_LENGTH 256 
   69 #define LF_DYNARRAY_LEVELS       4 
   72   void * 
volatile level[LF_DYNARRAY_LEVELS];
 
   77 typedef int (*lf_dynarray_func)(
void *, 
void *);
 
   79 void lf_dynarray_init(
LF_DYNARRAY *array, uint element_size);
 
   82 nolock_wrap(lf_dynarray_value, 
void *,
 
   85 lock_wrap(lf_dynarray_lvalue, 
void *,
 
   89 nolock_wrap(lf_dynarray_iterate, 
int,
 
   90             (
LF_DYNARRAY *array, lf_dynarray_func func, 
void *arg),
 
   97 #define LF_PINBOX_PINS 4 
   98 #define LF_PURGATORY_SIZE 10 
  100 typedef void lf_pinbox_free_func(
void *, 
void *, 
void*);
 
  104   lf_pinbox_free_func *free_func;
 
  106   uint free_ptr_offset;
 
  107   uint32 
volatile pinstack_top_ver;         
 
  108   uint32 
volatile pins_in_array;            
 
  112   void * 
volatile pin[LF_PINBOX_PINS];
 
  114   void  **stack_ends_here;
 
  116   uint32 purgatory_count;
 
  117   uint32 
volatile link;
 
  119 #if SIZEOF_INT*2+SIZEOF_CHARP*(LF_PINBOX_PINS+3) != 64 
  120   char pad[64-
sizeof(uint32)*2-
sizeof(
void*)*(LF_PINBOX_PINS+3)];
 
  128 #define lf_rwlock_by_pins(PINS)   \ 
  129   my_atomic_rwlock_wrlock(&(PINS)->pinbox->pinarray.lock) 
  130 #define lf_rwunlock_by_pins(PINS) \ 
  131   my_atomic_rwlock_wrunlock(&(PINS)->pinbox->pinarray.lock) 
  138 #if defined(__GNUC__) && defined(MY_LF_EXTRA_DEBUG) 
  139 #define LF_REQUIRE_PINS(N)                                      \ 
  140   static const char require_pins[LF_PINBOX_PINS-N]              \ 
  141                              __attribute__ ((unused));          \ 
  142   static const int LF_NUM_PINS_IN_THIS_FILE= N; 
  143 #define _lf_pin(PINS, PIN, ADDR)                                \ 
  145     assert(PIN < LF_NUM_PINS_IN_THIS_FILE),                     \ 
  146     my_atomic_storeptr(&(PINS)->pin[PIN], (ADDR))               \ 
  149 #define LF_REQUIRE_PINS(N) 
  150 #define _lf_pin(PINS, PIN, ADDR)  my_atomic_storeptr(&(PINS)->pin[PIN], (ADDR)) 
  153 #define _lf_unpin(PINS, PIN)      _lf_pin(PINS, PIN, NULL) 
  154 #define lf_pin(PINS, PIN, ADDR)   \ 
  156     lf_rwlock_by_pins(PINS);      \ 
  157     _lf_pin(PINS, PIN, ADDR);     \ 
  158     lf_rwunlock_by_pins(PINS);    \ 
  160 #define lf_unpin(PINS, PIN)  lf_pin(PINS, PIN, NULL) 
  161 #define _lf_assert_pin(PINS, PIN) assert((PINS)->pin[PIN] != 0) 
  162 #define _lf_assert_unpin(PINS, PIN) assert((PINS)->pin[PIN] == 0) 
  164 void lf_pinbox_init(
LF_PINBOX *pinbox, uint free_ptr_offset,
 
  165                     lf_pinbox_free_func *free_func, 
void * free_func_arg);
 
  166 void lf_pinbox_destroy(
LF_PINBOX *pinbox);
 
  168 lock_wrap(lf_pinbox_get_pins, 
LF_PINS *,
 
  171           &pinbox->pinarray.lock)
 
  172 lock_wrap_void(lf_pinbox_put_pins,
 
  175                &pins->pinbox->pinarray.lock)
 
  176 lock_wrap_void(lf_pinbox_free,
 
  179                &pins->pinbox->pinarray.lock)
 
  185 typedef struct st_lf_allocator {
 
  187   uchar * 
volatile top;
 
  189   uint32 
volatile mallocs;
 
  190   void (*constructor)(uchar *); 
 
  191   void (*destructor)(uchar *);  
 
  194 void lf_alloc_init(LF_ALLOCATOR *allocator, uint 
size, uint free_ptr_offset);
 
  195 void lf_alloc_destroy(LF_ALLOCATOR *allocator);
 
  196 uint lf_alloc_pool_count(LF_ALLOCATOR *allocator);
 
  201 #define _lf_alloc_free(PINS, PTR)     _lf_pinbox_free((PINS), (PTR)) 
  202 #define lf_alloc_free(PINS, PTR)       lf_pinbox_free((PINS), (PTR)) 
  203 #define _lf_alloc_get_pins(A)         _lf_pinbox_get_pins(&(A)->pinbox) 
  204 #define lf_alloc_get_pins(A)           lf_pinbox_get_pins(&(A)->pinbox) 
  205 #define _lf_alloc_put_pins(PINS)      _lf_pinbox_put_pins(PINS) 
  206 #define lf_alloc_put_pins(PINS)        lf_pinbox_put_pins(PINS) 
  207 #define lf_alloc_direct_free(ALLOC, ADDR) my_free((ADDR)) 
  209 lock_wrap(lf_alloc_new, 
void *,
 
  212           &pins->pinbox->pinarray.lock)
 
  223 #define LF_HASH_UNIQUE 1 
  226 extern const int LF_HASH_OVERHEAD;
 
  231   my_hash_get_key get_key;              
 
  233   uint key_offset, key_length;          
 
  237   int32 
volatile count;                 
 
  240 void lf_hash_init(
LF_HASH *hash, uint element_size, uint 
flags,
 
  241                   uint key_offset, uint key_length, my_hash_get_key get_key,
 
  243 void lf_hash_destroy(
LF_HASH *hash);
 
  244 int lf_hash_insert(
LF_HASH *hash, 
LF_PINS *pins, 
const void *data);
 
  245 void *lf_hash_search(
LF_HASH *hash, 
LF_PINS *pins, 
const void *key, uint keylen);
 
  246 int lf_hash_delete(
LF_HASH *hash, 
LF_PINS *pins, 
const void *key, uint keylen);
 
  251 #define _lf_hash_get_pins(HASH)     _lf_alloc_get_pins(&(HASH)->alloc) 
  252 #define lf_hash_get_pins(HASH)       lf_alloc_get_pins(&(HASH)->alloc) 
  253 #define _lf_hash_put_pins(PINS)     _lf_pinbox_put_pins(PINS) 
  254 #define lf_hash_put_pins(PINS)       lf_pinbox_put_pins(PINS) 
  255 #define lf_hash_search_unpin(PINS)   lf_unpin((PINS), 2) 
  260 #undef lock_wrap_void 
  262 #undef nolock_wrap_void