General Memory Pool

Data Structures

struct  pool_statistics


file  pool.h


#define pool_DEBUG   FALSE
#define pool_LIGHTENING   FALSE
#define pool_free_element(ps, eltpointer)   pool_free_elementF((ps),(eltpointer))
#define pool_clear_store(ps)   pool_clear_storeF(ps)


typedef struct pool_store_headerpool_store_t


ASC_DLLSPEC void pool_get_stats (struct pool_statistics *p_stats, pool_store_t ps)
ASC_DLLSPEC pool_store_t pool_create_store (int length, int width, size_t eltsize, int deltalen, int deltapool)
ASC_DLLSPEC void * pool_get_element (pool_store_t ps)
void pool_get_element_list (pool_store_t ps, int len, void **ellist)
ASC_DLLSPEC void pool_free_elementF (pool_store_t ps, void *eltpointer)
ASC_DLLSPEC void pool_clear_storeF (pool_store_t ps)
ASC_DLLSPEC void pool_destroy_store (pool_store_t ps)
void pool_print_store (FILE *fp, pool_store_t ps, unsigned detail)
size_t pool_sizeof_store (pool_store_t ps)

Define Documentation

#define pool_DEBUG   FALSE

Flag controlling extra checking of the pool management routines. Setting pool_DEBUG to TRUE causes the pool_store routines to do some RATHER expensive checking. It should be set to FALSE.

Definition at line 252 of file pool.h.

#define pool_LIGHTENING   FALSE

Flag controlling extent of internal sanity checking. Setting pool_LIGHTENING to TRUE causes pool_store routines to assume the user is perfect: i.e. no sanity checks are at all necessary and most internal accounting can be disabled. No one with an ounce of sanity would ever set this flag to TRUE unless the code using the pool module was proven bug free. It makes the allocator smaller and faster, though, by ~15%.

This flag exists to make it easy to test the theory that the accounting overhead in this code is not of significant cost. Below 1e5 elements it really isn't bad enough to justify the assumption that the user is perfect.

Definition at line 258 of file pool.h.

#define pool_free_element ( ps,
eltpointer   )     pool_free_elementF((ps),(eltpointer))

Releases an element back to the store. If you return the same pointer twice, we will have no qualms about returning it to you twice. We won't necessarily return it to you twice, though.

If pool_DEBUG is TRUE, eltpointer will be checked for belonging to ps. If you call pool_free_element() with a pointer the ps does not recognize, it will not be freed and a message will be sent to ASCERR.

If pool_DEBUG is FALSE, eltpointer will be assumed to belong with the ps in question. The implications of handing pool_free_element() an element of the wrong size or from the wrong ps (bearing in mind the LIFO reuse of elements) should be obvious. If they are not, stop using these routines.

If at any time the number of elements freed exceeds the number handed out, we will whine (unless pool_LIGHTENING). If ps is NULL, and error message is printed and the function returns. If eltpointer is NULL, we will ignore it completely.

ps pool_store_t, the pool store to modify.
eltpointer void*, the element to return to the pool.
No return value.
See also:

Definition at line 277 of file pool.h.

#define pool_clear_store ( ps   )     pool_clear_storeF(ps)

Clears the books in ps. That is, we reset the ps to think that __all__ elements are freshly available and have never been handed out. If ps is NULL, an error message is printed and the function returns.

If pool_DEBUG is TRUE, it first verifies that all elements have been pool_freed first and whines if not. Get and free calls will be balanced to see if spurious elements have been handed in. (This is a heuristic check). The clear process will cause any spurious pointers that were turned in via pool_free_element() to be forgotten about.

Clearing a store is not necessary for pool_destroy_store(). Recycling is faster from the recycle list than from a cleared store, ~2%. Clear is provided for users who want to obtain elements with a higher probability of successive elements being near each other.

ps pool_store_t, the pool store to clear.
No return value.
See also:

Definition at line 322 of file pool.h.

Referenced by gl_destroy_pool(), ppe_destroy_pool(), and RelationIO_destroy_pool().

Typedef Documentation

The token for this memory system. Internal details of the implementation are private. Do not dereference or free this pointer.

Definition at line 114 of file pool.h.

Function Documentation

ASC_DLLSPEC void pool_get_stats ( struct pool_statistics p_stats,
pool_store_t  ps 

Get statistics about a pool store. Stuffs the user's interface structure, p_stats, with info derived from ps given. If pool_LIGHTENING (see below) is TRUE, no statistics except elt_total, elt_taken, elt_onlist, and elt_size are available.

p_stats Pointer to a pool_statistics struct to receive the info. If p_stats is NULL, an error message is printed and the function returns.
ps Pointer to the pool store to query.

Definition at line 293 of file pool.c.

References pool_store_header::active, ASC_PROG_ERR, ascbzero, pool_store_header::curbar, pool_store_header::curelt, pool_statistics::elt_inuse, pool_statistics::elt_onlist, pool_statistics::elt_size, pool_statistics::elt_taken, pool_statistics::elt_total, pool_store_header::eltsize, pool_store_header::eltsize_req, ERROR_REPORTER_HERE, pool_store_header::highwater, pool_store_header::inuse, pool_store_header::len, pool_store_header::onlist, pool_statistics::p_eff, pool_statistics::p_recycle, pool_sizeof_store(), pool_statistics::str_len, pool_statistics::str_wid, pool_store_header::total, and pool_store_header::wid.

ASC_DLLSPEC pool_store_t pool_create_store ( int  length,
int  width,
size_t  eltsize,
int  deltalen,
int  deltapool 

Creates and returns a new pool store. The returned pool_store_t contains all the necessary accounting information, but in particular the eltsize is fixed at creation. All elements requested from ps will be pointers to eltsize bytes of memory. Returns NULL if a store of the requested length*width*eltsize cannot be initially allocated.

The user may request more than length*width elements from the store: this will cause it to grow. It will grow (internally) in chunks of deltalen*width elements. The pool vector above grows in chunks of deltapool, the extra pointers in it being NULL until needed.

length The initial number of width*eltsize blocks that the new pool store will contain. If length < 1, an error message is printed and NULL is returned.
width Number of elements in each block. Width should (for some architectures) be such that width*eltsize = 2^n - 32 for some n fairly large (heuristic: n= 9..13). Widths that are too large may be prone to causing excess page faults, though the process cpu time reported by the clock() can be much better for extremely large sizes. If width < 1, an error message is printed and NULL is returned.

Widths that are too small will result in an excessive number of pool expansions, which may severely limit performance on some VM systems. See deltapool below about pool expansions.

If you know something about the page size of your architecture, fiddling with width may help you reduce your page fault or cache miss count in some uses.
eltsize Element size maintained by the pool. For maximum efficiency, eltsize should be an integer multiple of sizeof(void *). If it is not, elts will be padded so that this is the case. This is to avoid pointer data misalignment. This restriction may or may not help avoid alignment problems with items inside the user's element structure.
deltalen Number of additional pointers in the pool that will be allocated when more elements are needed than are available internally. deltalen must be at least 1 or creation of the new pool will fail.
deltapool Size change of the pool array when expanded. It should be as large as you are willing to tolerate. The pool array starts out completely filled (all pointers allocated). When the pool needs more pointers it gets them in chunks of at least deltapool. These additional pointers will not automatically have elements allocated to them; rather, they will be initialized to NULL and filled in only as the chunks of deltalen*width elements are required.
A pointer to the newly created pool store, NULL if an error occurred.

Definition at line 324 of file pool.c.

References ASC_PROG_ERR, pool_store_header::barsize, CONSOLE_DEBUG, DESTROYED, pool_store_header::eltsize, pool_store_header::eltsize_req, ERROR_REPORTER_HERE, pool_store_header::expand, pool_store_header::growpool, pool_store_header::integrity, pool_store_header::len, pool_store_header::maxlen, NULL, OK, PMEM_calloc, PMEM_free, PMEM_malloc, PMEM_MINBARSIZE, PMEM_MINPOOLGROW, PMEM_MINPOOLSIZE, PMX, pool_store_header::pool, pool_store_header::total, and pool_store_header::wid.

Referenced by gl_init_pool(), InitInstanceNanny(), InitLogRelInstantiator(), InitPendingPool(), InitRelInstantiator(), InitSetManager(), InitValueManager(), ppe_init_pool(), and RelationIO_init_pool().

ASC_DLLSPEC void* pool_get_element ( pool_store_t  ps  ) 

Get a usable element from the pool. Returns a void pointer to a blob of memory of the eltsize set when ps was created. You must cast it appropriately. The blob data is not initialized in any particular way.

ps The pool store from which to retrieve an element. If ps is NULL, then an error message is printed and NULL is returned.
A pointer to the usable element, or NULL iff ps is NULL or store growth is required and the operating system is unable to allocate the required memory.

Definition at line 422 of file pool.c.

References pool_store_header::active, ASC_PROG_ERR, pool_store_header::curbar, pool_store_header::curelt, pool_store_header::eltsize, ERROR_REPORTER_HERE, pool_store_header::highwater, pool_store_header::inuse, pool_store_header::len, pool_store_header::list, pool_element::nextelt, NULL, pool_store_header::onlist, pool_store_header::pool, and pool_store_header::wid.

void pool_get_element_list ( pool_store_t  ps,
int  len,
void **  ellist 


Takes the pointer array, ellist, of length len provided by the user and fills it with pointers to elements from the store. There is not necessarily any relation (memory map wise) between the locations pointed to by successive entries in the ellist returned. Ellist should point to an array with enough space for len pointers. Returns NULL in ellist[0] iff store growth is required and the operating system is unable to allocate the required memory.

The user is reminded that if he knows how many elements he needs ahead of time, he is probably better off mallocing the array himself.

Implement general/pool.c:pool_get_element_list() of remove it from pool.h.

Definition at line 472 of file pool.c.


ASC_DLLSPEC void pool_free_elementF ( pool_store_t  ps,
void *  eltpointer 

Implementation function for pool_free_element(). Do not call this function directly - use pool_free_element() instead.

Definition at line 486 of file pool.c.

References abs, ASC_PROG_ERR, ERROR_REPORTER_HERE, pool_store_header::inuse, pool_store_header::list, pool_element::nextelt, pool_store_header::onlist, and pool_store_header::retned.

ASC_DLLSPEC void pool_clear_storeF ( pool_store_t  ps  ) 
ASC_DLLSPEC void pool_destroy_store ( pool_store_t  ps  ) 

Deallocates everything associated with the ps. If pool_DEBUG is TRUE, it first verifies that all elements have been pool_freed first and whines if not. If pool_DEBUG is FALSE, just nukes everything unconditionally. If ps is NULL, an error message is printed and the function returns.

ps The pool store to destroy.

Definition at line 570 of file pool.c.

References ASC_PROG_ERR, ASC_PROG_WARNING, DESTROYED, ERROR_REPORTER_HERE, pool_store_header::highwater, pool_store_header::integrity, pool_store_header::inuse, pool_store_header::len, OK, pool_store_header::onlist, PMEM_free, and pool_store_header::pool.

Referenced by DestroyInstanceNanny(), DestroyLogRelInstantiator(), DestroyPendingPool(), DestroyRelInstantiator(), DestroySetManager(), DestroyValueManager(), gl_destroy_pool(), ppe_destroy_pool(), and RelationIO_destroy_pool().

void pool_print_store ( FILE *  fp,
pool_store_t  ps,
unsigned  detail 

Prints statistics about a pool_store_t to the file stream given. Which stats get printed depends on detail.

  • If detail 0, displays just summary statistics.
  • If detail 1, just internal statistics.
  • If detail >1, displays both.
fp The open file stream on which to print the report.
ps The pool store on which to report.
detail The level of detail to print: 0 = summary, 1 = internal stats, >1 = both.

Definition at line 600 of file pool.c.

References pool_store_header::active, ASC_PROG_ERR, pool_store_header::barsize, pool_store_header::curbar, pool_store_header::curelt, pool_store_header::eltsize, pool_store_header::eltsize_req, ERROR_REPORTER_HERE, pool_store_header::expand, FPRINTF, pool_store_header::growpool, pool_store_header::highwater, pool_store_header::integrity, pool_store_header::inuse, pool_store_header::len, pool_store_header::maxlen, OK, pool_store_header::onlist, pool_sizeof_store(), pool_store_header::retned, pool_store_header::total, and pool_store_header::wid.

Referenced by gl_report_pool(), ppe_report_pool(), RelationIO_report_pool(), ReportInstanceNanny(), ReportLogRelInstantiator(), ReportPendingPool(), ReportRelInstantiator(), ReportSetManager(), and ReportValueManager().

size_t pool_sizeof_store ( pool_store_t  ps  ) 

Retrieves the current total byte usage of the store. Returns 0 if an invalid pool store is specified.

ps pool_store_t, the pool store to query.
The total bytes currently used by the pool store.

Definition at line 667 of file pool.c.

References pool_store_header::barsize, pool_store_header::len, and pool_store_header::maxlen.

Referenced by pool_get_stats(), and pool_print_store().

Generated on Mon Mar 4 17:48:44 2013 for libascend by  doxygen 1.6.3