1.\" $NetBSD: vmem.9,v 1.17 2017/07/03 21:28:48 wiz Exp $ 2.\" 3.\" Copyright (c)2006 YAMAMOTO Takashi, 4.\" All rights reserved. 5.\" 6.\" Redistribution and use in source and binary forms, with or without 7.\" modification, are permitted provided that the following conditions 8.\" are met: 9.\" 1. Redistributions of source code must retain the above copyright 10.\" notice, this list of conditions and the following disclaimer. 11.\" 2. Redistributions in binary form must reproduce the above copyright 12.\" notice, this list of conditions and the following disclaimer in the 13.\" documentation and/or other materials provided with the distribution. 14.\" 15.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 16.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 17.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 18.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 19.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 20.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 21.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 22.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 23.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 24.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 25.\" SUCH DAMAGE. 26.\" 27.\" ------------------------------------------------------------ 28.Dd February 28, 2016 29.Dt VMEM 9 30.Os 31.\" ------------------------------------------------------------ 32.Sh NAME 33.Nm vmem 34.Nd virtual memory allocator 35.\" ------------------------------------------------------------ 36.Sh SYNOPSIS 37.In sys/vmem.h 38.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 39.Ft vmem_t * 40.Fn vmem_create \ 41"const char *name" "vmem_addr_t base" "vmem_size_t size" "vmem_size_t quantum" \ 42"int (*allocfn)(void *, vmem_size_t, vm_flag_t, vmem_addr_t *)" \ 43"void (*freefn)(void *, vmem_addr_t, vmem_size_t)" \ 44"void *arg" "vmem_size_t qcache_max" "vm_flag_t flags" "int ipl" 45.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 46.Ft vmem_t * 47.Fn vmem_xcreate \ 48"const char *name" "vmem_addr_t base" "vmem_size_t size" "vmem_size_t quantum" \ 49"int (*allocfn)(void *, vmem_size_t, vmem_size_t *, vm_flag_t, vmem_addr_t *)" \ 50"void (*freefn)(void *, vmem_addr_t, vmem_size_t)" \ 51"void *arg" "vmem_size_t qcache_max" "vm_flag_t flags" "int ipl" 52.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 53.Ft int 54.Fn vmem_add \ 55"vmem_t *vm" "vmem_addr_t addr" "vmem_size_t size" "vm_flag_t flags" "vmem_addr_t *addrp" 56.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 57.Ft int 58.Fn vmem_xalloc \ 59"vmem_t *vm" "vmem_size_t size" "vmem_size_t align" \ 60"vmem_size_t phase" "vmem_size_t nocross" "vmem_addr_t minaddr" \ 61"vmem_addr_t maxaddr" "vm_flag_t flags" "vmem_addr_t *addrp" 62.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 63.Ft void 64.Fn vmem_xfree "vmem_t *vm" "vmem_addr_t addr" "vmem_size_t size" 65.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 66.Ft int 67.Fn vmem_alloc "vmem_t *vm" "vmem_size_t size" "vm_flag_t flags" "vmem_addr_t *addrp" 68.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 69.Ft void 70.Fn vmem_free "vmem_t *vm" "vmem_addr_t addr" "vmem_size_t size" 71.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 72.Ft void 73.Fn vmem_destroy "vmem_t *vm" 74.\" ------------------------------------------------------------ 75.Sh DESCRIPTION 76The 77.Nm 78is a general purpose resource allocator. 79Despite its name, it can be used for arbitrary resources 80other than virtual memory. 81.Pp 82.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 83.Fn vmem_create 84creates a new vmem arena. 85.Pp 86.Bl -tag -offset indent -width qcache_max 87.It Fa name 88The string to describe the vmem. 89.It Fa base 90The start address of the initial span. 91Pass 92.Dv 0 93if no initial span is required. 94.It Fa size 95The size of the initial span. 96Pass 97.Dv 0 98if no initial span is required. 99.It Fa quantum 100The smallest unit of allocation. 101.It Fa allocfn 102The callback function used to import spans from the backend arena. 103Set both 104.Fa allocfn 105and 106.Fa freefn 107to 108.Dv NULL 109to disable automatic imports. 110.Nm 111calls 112.Fo "(*allocfn)" 113.Fa arg 114.Fa size 115.Fa flags 116.Fa "&addrp" 117.Fc 118to import a span of size at least 119.Fa size . 120.Fa allocfn 121must accept the same 122.Fa flags 123as 124.Fn vmem_alloc . 125.Fa allocfn 126must return 127.Dv ENOMEM 128to indicate failure, or 0 on success. 129If 130.Fa allocfn 131succeeds, it must write the starting address of the imported span to 132.Fa addrp . 133.It Fa freefn 134The callback function used to free spans to the backend arena. 135.Fa freefn 136may be 137.Dv NULL 138even if 139.Fa allocfn 140is not 141.Dv NULL . 142.Nm 143calls 144.Fn "(*freefn)" arg addr size 145to return to 146.Fa arg 147a span of size 148.Fa size , 149starting at 150.Fa addr , 151that was previously allocated by 152.Fa allocfn . 153.It Fa arg 154The backend arena. 155.Fa arg 156may be 157.Dv NULL . 158.Nm 159passes 160.Fa arg 161as the first argument of 162.Fa allocfn 163and 164.Fa freefn . 165.It Fa qcache_max 166The largest size of allocations which can be served by quantum cache. 167It is merely a hint and can be ignored. 168.It Fa flags 169Either of: 170.Bl -tag -width VM_NOSLEEP 171.It Dv VM_SLEEP 172If the allocation cannot be satisfied immediately, sleep until enough 173resources are available. 174.It Dv VM_NOSLEEP 175Don't sleep. 176Immediately return 177.Dv NULL 178if there are not enough resources available. 179.El 180.It Fa ipl 181Interrupt level to be blocked for allocating from vmem. 182.El 183.Pp 184.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 185.Fn vmem_xcreate 186creates a new vmem arena. 187.Pp 188.Bl -tag -offset indent -width qcache_max 189.It Fa name 190The string to describe the vmem. 191.It Fa base 192The start address of the initial span. 193Pass 194.Dv 0 195if no initial span is required. 196.It Fa size 197The size of the initial span. 198Pass 199.Dv 0 200if no initial span is required. 201.It Fa quantum 202The smallest unit of allocation. 203.It Fa allocfn 204The callback function used to import spans from the backend arena. 205Set both 206.Fa allocfn 207and 208.Fa freefn 209to 210.Dv NULL 211to disable automatic imports. 212.Nm 213calls 214.Fo "(*allocfn)" 215.Fa arg 216.Fa size 217.Fa "&actualsize" 218.Fa flags 219.Fa "&addrp" 220.Fc 221to import a span of size at least 222.Fa size . 223.Fa allocfn 224must accept the same 225.Fa flags 226as 227.Fn vmem_alloc . 228.Fa allocfn 229must return 230.Dv ENOMEM 231to indicate failure, or 0 on success. 232If 233.Fa allocfn 234succeeds, it must write the actual size of the allocation to 235.Fa actualsize 236and the starting address of the imported span to 237.Fa addrp . 238The actual size will always be greater than or equal to the requested size. 239.It Fa freefn 240The callback function used to free spans to the backend arena. 241.Fa freefn 242may be 243.Dv NULL 244even if 245.Fa allocfn 246is not 247.Dv NULL . 248.Nm 249calls 250.Fn "(*freefn)" arg addr size 251to return to 252.Fa arg 253a span of size 254.Fa size , 255starting at 256.Fa addr , 257that was previously allocated by 258.Fa allocfn . 259.It Fa arg 260The backend arena. 261.Fa arg 262may be 263.Dv NULL . 264.Nm 265passes 266.Fa arg 267as the first argument of 268.Fa allocfn 269and 270.Fa freefn . 271.It Fa qcache_max 272The largest size of allocations which can be served by quantum cache. 273It is merely a hint and can be ignored. 274.It Fa flags 275Either of: 276.Bl -tag -width VM_NOSLEEP 277.It Dv VM_SLEEP 278If the allocation cannot be satisfied immediately, sleep until enough 279resources are available. 280.It Dv VM_NOSLEEP 281Don't sleep. 282Immediately return 283.Dv NULL 284if there are not enough resources available. 285.El 286.It Fa ipl 287Interrupt level to be blocked for allocating from vmem. 288.El 289.Pp 290.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 291.Fn vmem_add 292adds a span of size 293.Fa size 294starting at 295.Fa addr 296to the arena. 297Returns 2980 299on success, 300.Dv ENOMEM 301on failure. 302.Bl -tag -offset indent -width flags 303.It Fa flags 304Either of: 305.Bl -tag -width VM_NOSLEEP 306.It Dv VM_SLEEP 307If the allocation cannot be satisfied immediately, sleep until enough 308resources are available. 309.It Dv VM_NOSLEEP 310Don't sleep. 311Immediately return 312.Dv ENOMEM 313if there are not enough resources available. 314.El 315.El 316.Pp 317.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 318.Fn vmem_xalloc 319allocates a resource from the arena. 320.Pp 321.Bl -tag -offset indent -width nocross 322.It Fa vm 323The arena which we allocate from. 324.It Fa size 325Specify the size of the allocation. 326.It Fa align 327If zero, don't care about the alignment of the allocation. 328Otherwise, request a resource segment starting at 329offset 330.Fa phase 331from an 332.Fa align 333aligned boundary. 334.It Fa phase 335See the above description of 336.Fa align . 337If 338.Fa align 339is zero, 340.Fa phase 341must be zero. 342Otherwise, 343.Fa phase 344must be smaller than 345.Fa align . 346.It Fa nocross 347Request a resource which doesn't cross 348.Fa nocross 349aligned boundary. 350.It Fa minaddr 351Specify the minimum address which can be allocated, or 352.Dv VMEM_ADDR_MIN 353if the caller does not care. 354.It Fa maxaddr 355Specify the maximum address which can be allocated, or 356.Dv VMEM_ADDR_MAX 357if the caller does not care. 358.It Fa flags 359A bitwise OR of an allocation strategy and a sleep flag. 360.Pp 361The allocation strategy must be one of: 362.Bl -tag -width VM_INSTANTFIT 363.It Dv VM_BESTFIT 364Prefer space efficiency. 365.It Dv VM_INSTANTFIT 366Prefer performance. 367.El 368.Pp 369The sleep flag must be one of: 370.Bl -tag -width VM_NOSLEEP 371.It Dv VM_SLEEP 372If the allocation cannot be satisfied immediately, sleep until enough 373resources are available. 374.It Dv VM_NOSLEEP 375Don't sleep. 376Immediately return 377.Dv ENOMEM 378if there are not enough resources available. 379.El 380.It Fa addrp 381On success, if 382.Fa addrp 383is not 384.Dv NULL , 385.Fn vmem_xalloc 386overwrites it with the start address of the allocated span. 387.El 388.Pp 389.\" ------------------------------------------------------------ 390.Fn vmem_xfree 391frees resource allocated by 392.Fn vmem_xalloc 393to the arena. 394.Pp 395.Bl -tag -offset indent -width addr 396.It Fa vm 397The arena which we free to. 398.It Fa addr 399The resource being freed. 400It must have been allocated via 401.Fn vmem_xalloc . 402Notably, it must not have been allocated via 403.Fn vmem_alloc . 404Otherwise, the behaviour is undefined. 405.It Fa size 406The size of the resource being freed. 407It must be the same as the 408.Fa size 409argument used for 410.Fn vmem_xalloc . 411.El 412.Pp 413.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 414.Fn vmem_alloc 415allocates a resource from the arena. 416.Pp 417.Bl -tag -offset indent -width flags 418.It Fa vm 419The arena which we allocate from. 420.It Fa size 421Specify the size of the allocation. 422.It Fa flags 423A bitwise OR of an allocation strategy and a sleep flag. 424.Pp 425The allocation strategy must be one of: 426.Bl -tag -width VM_INSTANTFIT 427.It Dv VM_BESTFIT 428Prefer space efficiency. 429.It Dv VM_INSTANTFIT 430Prefer performance. 431.El 432.Pp 433The sleep flag must be one of: 434.Bl -tag -width VM_NOSLEEP 435.It Dv VM_SLEEP 436If the allocation cannot be satisfied immediately, sleep until enough 437resources are available. 438.It Dv VM_NOSLEEP 439Don't sleep. 440Immediately return 441.Dv ENOMEM 442if there are not enough resources available. 443.El 444.It Fa addrp 445On success, if 446.Fa addrp 447is not 448.Dv NULL , 449.Fn vmem_alloc 450overwrites it with the start address of the allocated span. 451.El 452.Pp 453.\" - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 454.Fn vmem_free 455frees resource allocated by 456.Fn vmem_alloc 457to the arena. 458.Pp 459.Bl -tag -offset indent -width addr 460.It Fa vm 461The arena which we free to. 462.It Fa addr 463The resource being freed. 464It must have been allocated via 465.Fn vmem_alloc . 466Notably, it must not have been allocated via 467.Fn vmem_xalloc . 468Otherwise, the behaviour is undefined. 469.It Fa size 470The size of the resource being freed. 471It must be the same as the 472.Fa size 473argument used for 474.Fn vmem_alloc . 475.El 476.Pp 477.\" ------------------------------------------------------------ 478.Fn vmem_destroy 479destroys a vmem arena. 480.Pp 481.Bl -tag -offset indent -width vm 482.It Fa vm 483The vmem arena being destroyed. 484The caller must ensure that no one will use it anymore. 485.El 486.\" ------------------------------------------------------------ 487.Sh RETURN VALUES 488.Fn vmem_create 489return a pointer to the newly allocated vmem_t. 490Otherwise, it returns 491.Dv NULL . 492.Pp 493On success, 494.Fn vmem_xalloc 495and 496.Fn vmem_alloc 497return 0. 498Otherwise, 499.Dv ENOMEM 500is returned. 501.\" ------------------------------------------------------------ 502.Sh CODE REFERENCES 503The 504.Nm 505subsystem is implemented within the file 506.Pa sys/kern/subr_vmem.c . 507.\" ------------------------------------------------------------ 508.Sh SEE ALSO 509.Xr intro 9 , 510.Xr kmem 9 , 511.Xr memoryallocators 9 , 512.Xr uvm 9 513.Rs 514.%A Jeff Bonwick 515.%A Jonathan Adams 516.%T "Magazines and Vmem: Extending the Slab Allocator to Many CPUs and Arbitrary Resources" 517.%J "2001 USENIX Annual Technical Conference" 518.%D 2001 519.Re 520.\" ------------------------------------------------------------ 521.Sh AUTHORS 522This implementation of 523.Nm 524was written by 525.An YAMAMOTO Takashi . 526.Sh BUGS 527.Pp 528.Nm 529relies on 530.Xr malloc 9 , 531.Xr pool 9 , 532and 533.Xr RUN_ONCE 9 , 534so it cannot be used as early during system bootstrap as 535.Xr extent 9 . 536