1fc76f6aeSSascha Wildner.\" 2fc76f6aeSSascha Wildner.\" Copyright (c) 2009 3fc76f6aeSSascha Wildner.\" The DragonFly Project. All rights reserved. 4fc76f6aeSSascha Wildner.\" 5fc76f6aeSSascha Wildner.\" Redistribution and use in source and binary forms, with or without 6fc76f6aeSSascha Wildner.\" modification, are permitted provided that the following conditions 7fc76f6aeSSascha Wildner.\" are met: 8fc76f6aeSSascha Wildner.\" 9fc76f6aeSSascha Wildner.\" 1. Redistributions of source code must retain the above copyright 10fc76f6aeSSascha Wildner.\" notice, this list of conditions and the following disclaimer. 11fc76f6aeSSascha Wildner.\" 2. Redistributions in binary form must reproduce the above copyright 12fc76f6aeSSascha Wildner.\" notice, this list of conditions and the following disclaimer in 13fc76f6aeSSascha Wildner.\" the documentation and/or other materials provided with the 14fc76f6aeSSascha Wildner.\" distribution. 15fc76f6aeSSascha Wildner.\" 3. Neither the name of The DragonFly Project nor the names of its 16fc76f6aeSSascha Wildner.\" contributors may be used to endorse or promote products derived 17fc76f6aeSSascha Wildner.\" from this software without specific, prior written permission. 18fc76f6aeSSascha Wildner.\" 19fc76f6aeSSascha Wildner.\" THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 20fc76f6aeSSascha Wildner.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 21fc76f6aeSSascha Wildner.\" LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 22fc76f6aeSSascha Wildner.\" FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 23fc76f6aeSSascha Wildner.\" COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 24fc76f6aeSSascha Wildner.\" INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING, 25fc76f6aeSSascha Wildner.\" BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 26fc76f6aeSSascha Wildner.\" LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 27fc76f6aeSSascha Wildner.\" AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 28fc76f6aeSSascha Wildner.\" OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT 29fc76f6aeSSascha Wildner.\" OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30fc76f6aeSSascha Wildner.\" SUCH DAMAGE. 31fc76f6aeSSascha Wildner.\" 32*550c09d2SAaron LI.Dd January 25, 2024 33fc76f6aeSSascha Wildner.Dt OBJCACHE 9 34fb5b3747SSascha Wildner.Os 35fc76f6aeSSascha Wildner.Sh NAME 36fc76f6aeSSascha Wildner.Nm objcache_create , 37fc76f6aeSSascha Wildner.Nm objcache_create_mbacked , 38fc76f6aeSSascha Wildner.Nm objcache_create_simple , 39fc76f6aeSSascha Wildner.Nm objcache_destroy , 40fc76f6aeSSascha Wildner.Nm objcache_dtor , 41fc76f6aeSSascha Wildner.Nm objcache_get , 42fc76f6aeSSascha Wildner.Nm objcache_malloc_alloc , 43fc76f6aeSSascha Wildner.Nm objcache_malloc_free , 44fc76f6aeSSascha Wildner.Nm objcache_nop_alloc , 45fc76f6aeSSascha Wildner.Nm objcache_nop_free , 46fc76f6aeSSascha Wildner.\" .Nm objcache_populate_linear , 47fc76f6aeSSascha Wildner.Nm objcache_put , 485f861a3bSSascha Wildner.Nm objcache_reclaimlist 49fc76f6aeSSascha Wildner.Nd "object caching facility" 50fc76f6aeSSascha Wildner.Sh SYNOPSIS 51fc76f6aeSSascha Wildner.In sys/objcache.h 52*550c09d2SAaron LI.Bd -literal 53*550c09d2SAaron LItypedef boolean_t (objcache_ctor_fn)(void *obj, void *privdata, int ocflags); 54*550c09d2SAaron LI 55*550c09d2SAaron LItypedef void (objcache_dtor_fn)(void *obj, void *privdata); 56*550c09d2SAaron LI 57*550c09d2SAaron LItypedef void *(objcache_alloc_fn)(void *allocator_args, int ocflags); 58*550c09d2SAaron LI 59*550c09d2SAaron LItypedef void (objcache_free_fn)(void *obj, void *allocator_args); 60*550c09d2SAaron LI 61*550c09d2SAaron LIstruct objcache_malloc_args { 62*550c09d2SAaron LI size_t objsize; 63*550c09d2SAaron LI malloc_type_t mtype; 64*550c09d2SAaron LI}; 65*550c09d2SAaron LI.Ed 66fc76f6aeSSascha Wildner.Ft struct objcache * 67fc76f6aeSSascha Wildner.Fo objcache_create 68fc76f6aeSSascha Wildner.Fa "const char *name" 69d91f660cSStathis Kamperis.Fa "int cluster_limit" 70fc76f6aeSSascha Wildner.Fa "int mag_capacity" 71fc76f6aeSSascha Wildner.Fa "objcache_ctor_fn *ctor" 72fc76f6aeSSascha Wildner.Fa "objcache_dtor_fn *dtor" 73fc76f6aeSSascha Wildner.Fa "void *privdata" 74fc76f6aeSSascha Wildner.Fa "objcache_alloc_fn *alloc" 75fc76f6aeSSascha Wildner.Fa "objcache_free_fn *free" 76fc76f6aeSSascha Wildner.Fa "void *allocator_args" 77fc76f6aeSSascha Wildner.Fc 78fc76f6aeSSascha Wildner.Ft struct objcache * 79fc76f6aeSSascha Wildner.Fo objcache_create_mbacked 80fc76f6aeSSascha Wildner.Fa "malloc_type_t mtype" 81fc76f6aeSSascha Wildner.Fa "size_t objsize" 82d91f660cSStathis Kamperis.Fa "int cluster_limit" 83fc76f6aeSSascha Wildner.Fa "int mag_capacity" 84fc76f6aeSSascha Wildner.Fa "objcache_ctor_fn *ctor" 85fc76f6aeSSascha Wildner.Fa "objcache_dtor_fn *dtor" 86fc76f6aeSSascha Wildner.Fa "void *privdata" 87fc76f6aeSSascha Wildner.Fc 88fc76f6aeSSascha Wildner.Ft struct objcache * 89fc76f6aeSSascha Wildner.Fn objcache_create_simple "malloc_type_t mtype" "size_t objsize" 90fc76f6aeSSascha Wildner.Ft void 91fc76f6aeSSascha Wildner.Fn objcache_destroy "struct objcache *oc" 92fc76f6aeSSascha Wildner.Ft void 93fc76f6aeSSascha Wildner.Fn objcache_dtor "struct objcache *oc" "void *obj" 94fc76f6aeSSascha Wildner.Ft void * 95fc76f6aeSSascha Wildner.Fn objcache_get "struct objcache *oc" "int ocflags" 96fc76f6aeSSascha Wildner.Ft void * 97fc76f6aeSSascha Wildner.Fn objcache_malloc_alloc "void *allocator_args" "int ocflags" 98fc76f6aeSSascha Wildner.Ft void 99fc76f6aeSSascha Wildner.Fn objcache_malloc_free "void *obj" "void *allocator_args" 100fc76f6aeSSascha Wildner.Ft void * 101fc76f6aeSSascha Wildner.Fn objcache_nop_alloc "void *allocator_args" "int ocflags" 102fc76f6aeSSascha Wildner.Ft void 103fc76f6aeSSascha Wildner.Fn objcache_nop_free "void *obj" "void *allocator_args" 104fc76f6aeSSascha Wildner.\" .Ft void 105fc76f6aeSSascha Wildner.\" .Fo objcache_populate_linear 106fc76f6aeSSascha Wildner.\" .Fa "struct objcache *oc" 107fc76f6aeSSascha Wildner.\" .Fa "void *elts" 108fc76f6aeSSascha Wildner.\" .Fa "int nelts" 109fc76f6aeSSascha Wildner.\" .Fa "int size" 110fc76f6aeSSascha Wildner.\" .Fc 111fc76f6aeSSascha Wildner.Ft void 112fc76f6aeSSascha Wildner.Fn objcache_put "struct objcache *oc" "void *obj" 113fc76f6aeSSascha Wildner.Ft boolean_t 1148a7a7510SAaron LI.Fn objcache_reclaimlist "struct objcache *oc[]" "int nlist" 115fc76f6aeSSascha Wildner.Sh DESCRIPTION 116fc76f6aeSSascha WildnerObject caching is a technique for manipulating objects that are frequently 117fc76f6aeSSascha Wildnerallocated and freed. 118fc76f6aeSSascha WildnerThe idea behind caching is to preserve the invariant portion of an object's 119fc76f6aeSSascha Wildnerinitial state between uses, so it does not have to be destroyed and reborn 120fc76f6aeSSascha Wildnerevery time the object is used. 121fc76f6aeSSascha Wildner.Pp 122fc76f6aeSSascha Wildner.Fn objcache_create 123fc76f6aeSSascha Wildnercreates a new object cache. 124fc76f6aeSSascha WildnerIt is identified by 125fc76f6aeSSascha Wildner.Fa name , 126fc76f6aeSSascha Wildnerwhich is used to distinguish the object in diagnostic output. 127fc76f6aeSSascha WildnerThe 128d91f660cSStathis Kamperis.Fa cluster_limit 129fc76f6aeSSascha Wildnerdetermines the number of available magazines in the depot layer. 130fc76f6aeSSascha WildnerIt must be at least 131e61925a5SAaron LI.Fa ( mag_capacity 132e61925a5SAaron LI* ncpus * 8). 133fc76f6aeSSascha WildnerIf 0 is given, then there is no limit to the number of magazines the depot 134fc76f6aeSSascha Wildnercan have (aside from the inherent limitation imposed by the restricted nature 135fc76f6aeSSascha Wildnerof the back end allocator). 136fc76f6aeSSascha WildnerThe 137fc76f6aeSSascha Wildner.Fa mag_capacity 138fc76f6aeSSascha Wildnerdescribes the capacity of the magazine, that is the largest number of objects 139fc76f6aeSSascha Wildnerit can hold. 140fc76f6aeSSascha WildnerIf set to 0, the default value is used as defined in 1410280bae0SSascha Wildner.Pa sys/kern/kern_objcache.c . 142fc76f6aeSSascha WildnerCurrently, the default value is 64. 143fc76f6aeSSascha WildnerThe object caching system itself may adjust the cluster limit and/or 144fc76f6aeSSascha Wildnermagazines' capacity based on the number of available CPUs. 145fc76f6aeSSascha Wildner.Fa ctor 146fc76f6aeSSascha Wildnerspecifies a function that constructs (i.e., performs the one-time 147fc76f6aeSSascha Wildnerinitialization of) an object in the cache. 148fc76f6aeSSascha WildnerIt is defined as: 149fc76f6aeSSascha Wildner.Bd -literal 150fc76f6aeSSascha Wildnerboolean_t foo_ctor(void *obj, void *privdata, int ocflags); 151fc76f6aeSSascha Wildner.Ed 152fc76f6aeSSascha Wildner.Pp 153fc76f6aeSSascha WildnerIf no constructor is needed, it must be set to 154fc76f6aeSSascha Wildner.Dv NULL . 155fc76f6aeSSascha Wildner.Fa dtor 1568bd03982SAaron LIspecifies a destructor function that destroys the cached object, before it 157fc76f6aeSSascha Wildneris released to the back end that manages the flow of real memory. 158fc76f6aeSSascha WildnerIt is defined as: 159fc76f6aeSSascha Wildner.Bd -literal 160fc76f6aeSSascha Wildnervoid foo_dtor(void *obj, void *privdata); 161fc76f6aeSSascha Wildner.Ed 162fc76f6aeSSascha Wildner.Pp 1638bd03982SAaron LIIf no destructor is needed, it must be set to 164fc76f6aeSSascha Wildner.Dv NULL . 165fc76f6aeSSascha WildnerThe interface to underlying allocator is provided by 166fc76f6aeSSascha Wildner.Fa alloc , 167fc76f6aeSSascha Wildner.Fa free 168fc76f6aeSSascha Wildnerand 169fc76f6aeSSascha Wildner.Fa allocator_args . 170fc76f6aeSSascha WildnerIt must adhere to the following form: 171fc76f6aeSSascha Wildner.Bd -literal 172fc76f6aeSSascha Wildnervoid *foo_alloc(void *allocator_args, int ocflags); 173fc76f6aeSSascha Wildnervoid foo_free(void *obj, void *allocator_args); 174fc76f6aeSSascha Wildner.Ed 175fc76f6aeSSascha Wildner.Pp 176fc76f6aeSSascha Wildner.Fn objcache_malloc_alloc 177fc76f6aeSSascha Wildnerand 178fc76f6aeSSascha Wildner.Fn objcache_malloc_free 179fc76f6aeSSascha Wildnerare wrappers for 180fc76f6aeSSascha Wildner.Xr kmalloc 9 181fc76f6aeSSascha Wildnerallocation functions. 182fc76f6aeSSascha WildnerWhereas, 183fc76f6aeSSascha Wildner.Fn objcache_nop_alloc 184fc76f6aeSSascha Wildnerand 185fc76f6aeSSascha Wildner.Fn objcache_nop_free 186fc76f6aeSSascha Wildnerare wrappers for allocation policies that pre-allocate at initialization time 187fc76f6aeSSascha Wildnerinstead of doing run-time allocation. 188fc76f6aeSSascha Wildner.Pp 189fc76f6aeSSascha Wildner.Fn objcache_create_mbacked 190fc76f6aeSSascha Wildnercreates a new object cache of size 191fc76f6aeSSascha Wildner.Fa objsize , 192fc76f6aeSSascha Wildnerbacked with a 193fc76f6aeSSascha Wildner.Vt malloc_type_t 194fc76f6aeSSascha Wildnerargument. 195fc76f6aeSSascha WildnerThe latter is used to perform statistics in memory usage and for basic sanity 196fc76f6aeSSascha Wildnerchecks. 197fc76f6aeSSascha WildnerFor the underlying allocator, 198fc76f6aeSSascha Wildner.Xr kmalloc 9 199fc76f6aeSSascha Wildnerfunctions are employed. 200fc76f6aeSSascha Wildner.Pp 201fc76f6aeSSascha Wildner.Fn objcache_create_simple 202fc76f6aeSSascha Wildnercreates a new object cache of size 203fc76f6aeSSascha Wildner.Fa objsize , 204fc76f6aeSSascha Wildnerbacked with a 2054a77bba4SSascha Wildner.Vt malloc_type_t 206fc76f6aeSSascha Wildnerargument. 207fc76f6aeSSascha WildnerThe 208d91f660cSStathis Kamperis.Fa cluster_limit 209fc76f6aeSSascha Wildneris set to 0 and the default value for magazines' capacity is used. 210fc76f6aeSSascha Wildner.Fa ctor 211fc76f6aeSSascha Wildnerand 212fc76f6aeSSascha Wildner.Fa dtor 213fc76f6aeSSascha Wildnerare set to 214fc76f6aeSSascha Wildner.Dv NULL . 215fc76f6aeSSascha Wildner.Fa privdata 216fc76f6aeSSascha Wildneris set to 217fc76f6aeSSascha Wildner.Dv NULL 218fc76f6aeSSascha Wildneras well. 219fc76f6aeSSascha WildnerFor the underlying allocator, 220fc76f6aeSSascha Wildner.Xr kmalloc 9 221fc76f6aeSSascha Wildnerfunctions are employed. 222fc76f6aeSSascha Wildner.Pp 223fc76f6aeSSascha Wildner.Fn objcache_get 224fc76f6aeSSascha Wildnerreturns an object from the 225fc76f6aeSSascha Wildner.Fa oc 226fc76f6aeSSascha Wildnerobject cache. 227fc76f6aeSSascha WildnerThe object is in its initialized state. 228fc76f6aeSSascha WildnerNewly allocated objects are subjected to the object cache's constructor 229fc76f6aeSSascha Wildnerfunction, if not 230fc76f6aeSSascha Wildner.Dv NULL , 231fc76f6aeSSascha Wildnerprior to being returned. 232fc76f6aeSSascha Wildner.Fa ocflags 233fc76f6aeSSascha Wildneris only used when the depot does not have any non-empty magazines and a new 234fc76f6aeSSascha Wildnerobject needs to be allocated using the back end allocator. 235fc76f6aeSSascha WildnerIn this case we cannot depend on flags such as 236fc76f6aeSSascha Wildner.Dv M_ZERO . 237fc76f6aeSSascha WildnerIf the back end allocator fails, or if the depot's object limit has been 238fc76f6aeSSascha Wildnerreached and 239fc76f6aeSSascha Wildner.Dv M_WAITOK 240fc76f6aeSSascha Wildneris not specified, 241fc76f6aeSSascha Wildner.Dv NULL 242fc76f6aeSSascha Wildneris returned. 243fc76f6aeSSascha Wildner.Pp 244fc76f6aeSSascha Wildner.Fn objcache_put 245fc76f6aeSSascha Wildnerreturns 246fc76f6aeSSascha Wildner.Fa obj 247fc76f6aeSSascha Wildnerto the 248fc76f6aeSSascha Wildner.Fa oc 249fc76f6aeSSascha Wildnerobject cache. 250fc76f6aeSSascha WildnerThe object must be in its initialized state prior to this call. 2518bd03982SAaron LIIf there is no empty magazine, the object destructor is called and 252fc76f6aeSSascha Wildnerthe object is freed. 253fc76f6aeSSascha Wildner.Pp 254fc76f6aeSSascha Wildner.Fn objcache_dtor 255fc76f6aeSSascha Wildnerputs 256fc76f6aeSSascha Wildner.Fa obj 257fc76f6aeSSascha Wildnerback into the 258fc76f6aeSSascha Wildner.Fa oc 259fc76f6aeSSascha Wildnerobject cache, indicating that the object is not in any shape to be reused and 2608bd03982SAaron LIshould be destructed and freed immediately. 261fc76f6aeSSascha Wildner.Pp 262fc76f6aeSSascha Wildner.Fn objcache_reclaimlist 263fc76f6aeSSascha Wildneriterates over the 264fc76f6aeSSascha Wildner.Fa oclist[] 265fc76f6aeSSascha Wildnerlist with 266fc76f6aeSSascha Wildner.Fa nlist 267fc76f6aeSSascha Wildnerelements and tries to free up some memory. 268fc76f6aeSSascha WildnerFor each object cache in the reclaim list, the current per-CPU cache is tried 269fc76f6aeSSascha Wildnerfirst and then the full magazine depot. 270fc76f6aeSSascha WildnerThe function returns 271fc76f6aeSSascha Wildner.Dv TRUE 272fc76f6aeSSascha Wildneras soon as some free memory is found 273fc76f6aeSSascha Wildnerand 274fc76f6aeSSascha Wildner.Dv FALSE 275fc76f6aeSSascha Wildnerotherwise. 276fc76f6aeSSascha Wildner.Pp 277fc76f6aeSSascha Wildner.Fn objcache_destroy 278fc76f6aeSSascha Wildnerdestroys the 279fc76f6aeSSascha Wildner.Fa oc 280fc76f6aeSSascha Wildnerobject cache. 281fc76f6aeSSascha WildnerThe object must have no existing references. 282fc76f6aeSSascha Wildner.\" .Pp 283fc76f6aeSSascha Wildner.\" .Fn objcache_populate_linear 284fc76f6aeSSascha Wildner.\" populates the per-cluster depot with elements from a linear block of memory. 285fc76f6aeSSascha Wildner.\" Must be called for individually for each cluster. 286fc76f6aeSSascha Wildner.\" Populated depots should not be destroyed. 287fc76f6aeSSascha Wildner.\" Currently this function is unimplemented. 288fc76f6aeSSascha Wildner.Sh IMPLEMENTATION NOTES 289fc76f6aeSSascha Wildner.Ss Magazine 290fc76f6aeSSascha WildnerA magazine is the very basic functional unit of the object caching scheme. 291fc76f6aeSSascha WildnerThe number of objects it can hold is fixed and determined by its capacity. 292fc76f6aeSSascha WildnerThe term magazine is used as an analogy with automatic weapon 293fc76f6aeSSascha Wildner(a firearm that can fire several rounds without reloading). 294fc76f6aeSSascha Wildner.Ss Per-CPU object cache 295fc76f6aeSSascha WildnerThe reasoning behind per-CPU caches is to allow CPUs to perform their 296fc76f6aeSSascha Wildnertransactions (i.e., allocations, frees) in a parallel, yet lockless manner. 297fc76f6aeSSascha Wildner.Pp 298fc76f6aeSSascha WildnerEach CPU is given two magazines, an active and a backup. 299fc76f6aeSSascha WildnerThis is done in order to avoid a situation where a tight loop of 300fc76f6aeSSascha Wildnertwo allocations followed by two frees can cause thrashing at the 301fc76f6aeSSascha Wildnermagazine boundary. 302fc76f6aeSSascha Wildner.Pp 303fc76f6aeSSascha WildnerIf we need to add an object to the cache and the active magazine is full, 304fc76f6aeSSascha Wildnerroom is searched in the backup magazine. 305fc76f6aeSSascha WildnerIf the backup has room, we swap active with backup and add the object. 306fc76f6aeSSascha WildnerIf both magazines are full, we get an empty magazine from the depot 307fc76f6aeSSascha Wildnerand move a fully loaded magazine to the depot. 308fc76f6aeSSascha Wildner.Ss Magazine depot 309fc76f6aeSSascha WildnerEach object cache manages a global supply of magazines, the depot, that is 310fc76f6aeSSascha Wildneravailable across all CPUs. 311fc76f6aeSSascha WildnerThe depot maintains two lists of magazines. 312fc76f6aeSSascha WildnerOne for completely full and one for completely free magazines. 313fc76f6aeSSascha WildnerThe per-CPU object caches only exchange completely full or 314fc76f6aeSSascha Wildnercompletely empty magazines with the depot layer. 315fc76f6aeSSascha Wildner.Sh EXAMPLES 316fc76f6aeSSascha Wildner.Bd -literal 317fc76f6aeSSascha Wildner/* This is the data structure we are going to cache. */ 318fc76f6aeSSascha Wildnerstruct foo { 319fc76f6aeSSascha Wildner int x; 320fc76f6aeSSascha Wildner char str[32]; 321fc76f6aeSSascha Wildner}; 322fc76f6aeSSascha Wildner 323fc76f6aeSSascha WildnerMALLOC_DEFINE(M_FOOBUF, "foobuf", "Buffer to my little precious data"); 324fc76f6aeSSascha Wildner 325fc76f6aeSSascha Wildnerstruct objcache_malloc_args foo_malloc_args = { 326fc76f6aeSSascha Wildner sizeof(struct foo), M_FOOBUF }; 327fc76f6aeSSascha Wildner 328fc76f6aeSSascha Wildnerstruct objcache *foo_cache; 329fc76f6aeSSascha Wildner 330fc76f6aeSSascha Wildner/* 331fc76f6aeSSascha Wildner * Object cache constructor. 332fc76f6aeSSascha Wildner */ 333fc76f6aeSSascha Wildnerstatic boolean_t 334fc76f6aeSSascha Wildnerfoo_cache_ctor(void *obj, void *privdata, int ocflags) 335fc76f6aeSSascha Wildner{ 336fc76f6aeSSascha Wildner struct foo *myfoo = obj; 337fc76f6aeSSascha Wildner 338fc76f6aeSSascha Wildner /* 339fc76f6aeSSascha Wildner * Do any initialization of the object here. Let's just zero out 340fc76f6aeSSascha Wildner * the data structure for the fun of it. 341fc76f6aeSSascha Wildner */ 342fc76f6aeSSascha Wildner bzero(myfoo, sizeof(*myfoo)); 343fc76f6aeSSascha Wildner 344fc76f6aeSSascha Wildner return (TRUE); 345fc76f6aeSSascha Wildner} 346fc76f6aeSSascha Wildner 347fc76f6aeSSascha Wildner/* 3488bd03982SAaron LI * Object cache destructor. 349fc76f6aeSSascha Wildner */ 350fc76f6aeSSascha Wildnerstatic void 351fc76f6aeSSascha Wildnerfoo_cache_dtor(void *obj, void *privdata) 352fc76f6aeSSascha Wildner{ 353fc76f6aeSSascha Wildner struct foo *myfoo = obj; 354fc76f6aeSSascha Wildner 355fc76f6aeSSascha Wildner /* 356fc76f6aeSSascha Wildner * Do any clean up here. E.g., if you have kmalloc'ed() inside 357fc76f6aeSSascha Wildner * the constructor, this is the right place and time to kfree(). 358fc76f6aeSSascha Wildner */ 359fc76f6aeSSascha Wildner} 360fc76f6aeSSascha Wildner 361fc76f6aeSSascha Wildner/* 362fc76f6aeSSascha Wildner * Initialize our subsystem. 363fc76f6aeSSascha Wildner */ 364fc76f6aeSSascha Wildnerstatic void 365fc76f6aeSSascha Wildnerfoo_init(void) 366fc76f6aeSSascha Wildner{ 367fc76f6aeSSascha Wildner /* Create the object cache. */ 368fc76f6aeSSascha Wildner foo_cache = objcache_create("foo", 369fc76f6aeSSascha Wildner 0, /* infinite depot's capacity */ 370fc76f6aeSSascha Wildner 0, /* default magazine's capacity */ 371fc76f6aeSSascha Wildner foo_ctor, foo_dtor, NULL, 372fc76f6aeSSascha Wildner objcache_malloc_alloc, 373fc76f6aeSSascha Wildner objcache_malloc_free, 374fc76f6aeSSascha Wildner &foo_malloc_args); 375fc76f6aeSSascha Wildner} 376fc76f6aeSSascha Wildner 377fc76f6aeSSascha Wildner/* 378fc76f6aeSSascha Wildner * Random function. 379fc76f6aeSSascha Wildner */ 380fc76f6aeSSascha Wildnerstatic void 381fc76f6aeSSascha Wildnerfoo_random(...) 382fc76f6aeSSascha Wildner{ 383fc76f6aeSSascha Wildner struct foo *myfoo; 384fc76f6aeSSascha Wildner 385fc76f6aeSSascha Wildner /* Get a `foo' object from the object cache. */ 386fc76f6aeSSascha Wildner myfoo = objcache_get(foo_cache, M_WAITOK); 387fc76f6aeSSascha Wildner 388fc76f6aeSSascha Wildner /* Do stuff with it. */ 389fc76f6aeSSascha Wildner /* ... */ 390fc76f6aeSSascha Wildner 391fc76f6aeSSascha Wildner /* We don't need it anymore. Put it back in object cache. */ 392fc76f6aeSSascha Wildner objcache_put(foo_cache, myfoo); 393fc76f6aeSSascha Wildner} 394fc76f6aeSSascha Wildner 395fc76f6aeSSascha Wildner/* 396fc76f6aeSSascha Wildner * Shutdown our subsystem. 397fc76f6aeSSascha Wildner */ 398fc76f6aeSSascha Wildnerstatic void 399fc76f6aeSSascha Wildnerfoo_uninit(void) 400fc76f6aeSSascha Wildner{ 401fc76f6aeSSascha Wildner /* Destroy the object cache. */ 402fc76f6aeSSascha Wildner objcache_destroy(foo_cache); 403fc76f6aeSSascha Wildner} 404fc76f6aeSSascha Wildner.Ed 405fc76f6aeSSascha Wildner.Sh SEE ALSO 406ae03fd51SSascha Wildner.Xr memory 9 407fc76f6aeSSascha Wildner.Rs 408fc76f6aeSSascha Wildner.%A "Jeff Bonwick" 409fc76f6aeSSascha Wildner.%T "The Slab Allocator: An Object-Caching Kernel Memory Allocator" 410fc76f6aeSSascha Wildner.%R "USENIX Summer 1994 Technical Conference" 411fc76f6aeSSascha Wildner.Re 412fc76f6aeSSascha Wildner.Rs 413fc76f6aeSSascha Wildner.%A "Jeff Bonwick" 414fc76f6aeSSascha Wildner.%A "Jonathan Adams" 415fc76f6aeSSascha Wildner.%T "Magazines and Vmem: Extending the Slab Allocator to Many CPUs and Arbitrary Resources" 416fc76f6aeSSascha Wildner.%R "USENIX 2001 Technical Conference" 417fc76f6aeSSascha Wildner.Re 418fc76f6aeSSascha Wildner.Sh HISTORY 419fc76f6aeSSascha WildnerThe object caching system appeared in 420fc76f6aeSSascha Wildner.Dx 1.3 . 421fc76f6aeSSascha Wildner.Sh AUTHORS 422fc76f6aeSSascha WildnerThe object caching system was written by 423fc76f6aeSSascha Wildner.An -nosplit 424c616d378SFranco Fichtner.An Jeffrey M. Hsu Aq Mt hsu@freebsd.org . 425fc76f6aeSSascha WildnerThis manual page was written by 426c616d378SFranco Fichtner.An Stathis Kamperis Aq Mt ekamperi@gmail.com . 427