Cache Management in C

As explained in the Prioritized Cache page, eXtremeDB provides a number of C API functions to monitor and manage the runtime cache. These APIs and important information regarding their usage are described in the following sections.

Cache Priorities

Applications can influence how long certain pages remain in memory by assigning the cache priority database objects. This is done by setting the following parameters in the db_params passed to the mco_db_open_dev() function: for indexes index_caching_priority, for the memory allocator bitmap pages allocation_bitmap_priority and for data object pages (excluding BLOBs) object_caching_priority. The default value of zero means that the caching priority for all objects is the same. But an integer value greater than zero can be specified; the higher the value the longer the index, allocation bitmap or object pages will remain in the cache.

Using the preset object priority as a baseline, the generated function <classname>_set_caching_priority() can be called to adjust the relative priorities of specific classes. For example, large and rarely accessed objects can be assigned lower priority, while small frequently accessed classes can be assigned a higher priority. The caching priority assigned at runtime is stored in the database and is used until it is explicitly overwritten.

Other memory initialization factors that can affect overall performance are the sizes specified for the cache and disk_max_database_size. These are explained in the following sections.

Cache Size

The memory address and size for the cache are specified in the devices parameter devs passed to the mco_db_open_dev() function. The memory can be either shared memory or local memory. (It must be shared memory if two or more processes are to share the database.) Generally a larger cache will improve application performance, but the frequency of updates to persistent media (flushing of cache pages) is more important for performance. How database updates are written to persistent media is determined by the Transaction Commit Policy.

Maximum Database Size

The eXtremeDB runtime uses the value of the disk_max_database_size element of the mco_db_params_t parameter passed to mco_db_open_dev() to allocate the “dirty pages bitmap”. The bitmap is allocated in cache at the time the cache is created. The bitmap size can be roughly calculated as:

 
    disk_max_database_size / page_size / 8.
 

The application can set disk_max_database_size = MCO_INFINITE_DATABASE_SIZE to indicate that the maximum size of the database is unknown. In this case, the size of the bitmap is set to 1/16 of the size of the cache. The runtime can also be configured with the ‘extendable bitmap’ option, allowing for unlimited database size. If the runtime is configured with the extendable bitmap, then disk_max_database_size = MCO_INFINITE_DATABASE_SIZE is specified and in this scenario the bitmap is allocated in eXtremeDB heap space.

Reserve Page Pool

As explained in the Prioritized Cache page, the database runtime provides the page pool reservation mechanism that facilitates out-of-memory error handling for the cache. The size of the reserve pool is calculated internally by the runtime based on the value of the mco_db_params.max_active_pages parameter (the default value is 32) and the number of currently active connections to the database runtime.

It is possible to disable this mechanism by setting the MCO_DB_DISABLE_PAGE_POOL_RESERVE bit in the database mco_db_params.mode_mask.

Connection cache

The connection cache is enabled by default. Two functions, mco_disk_enable_connection_cache() and mco_disk_reset_connection_cache(), are provided to allow applications control over the connection cache:

 
    mco_bool mco_disk_enable_connection_cache(mco_db_h con, mco_bool enabled);
     
    MCO_RET mco_disk_reset_connection_cache(mco_db_h con);
     

The first function enables or disables the connection cache. Passing MCO_YES or MCO_NO as the enable parameter value enables and disables the cache. The function returns the current state of the connection cache. The second function commits the connection cache (resets) to the database.

These two functions address a scenario with many connections and long-lasting transactions. In this scenario, the connection cache could cause the page pool to run out of free pages (a new transaction allocates its own connection cache, but long transactions prevent those pages from being released back to the shared page pool). To address this, the connection cache could be turned off or reset often. Under normal circumstances, the application does not need to control the connection cache.

In-memory Page allocation

The minimum and maximum number of pages held by the per-connection allocator in MVCC mode are determined by the database parameters min_conn_local_pages and max_conn_local_pages parameters in the mco_db_params_t argument for mco_db_open_dev(). The MVCC transaction manager optimizes access to the shared memory pool by pre-allocating a number of pages at once and assigning these pages to the connection. The default value for min_conn_local_pages is 256 pages and for max_conn_local_pages is 512. The min/max value assignments represents a tradeoff between accessing a shared resource more frequently and allocating extra memory. Changing these default values can be effective if there are well defined object allocation and deallocation patterns in the application.

Obtaining runtime cache statistics

The mco_disk_get_cache_info() function allows applications to obtain runtime disk manager cache statistics, including cache hits and cache misses. A cache hit occurs when the address or data required by the database runtime is found in the cache and does not require retrieval from the storage media. This information could, for example, be used to fine-tune the application’s caching policies (see the Prioritized Cache page).

Saving and Loading the Cache

The mco_disk_save_cache() function allows applications to save the disk manager cache to persistent storage; and mco_disk_load_cache() can be called to load a previously saved image of the cache from same.