Manages mapping of virtual memory pages.
VirtualMemory | Manages mapping of virtual memory pages. |
Copyright | This program is free software. |
Files | |
C-kern/ | Header file of VirtualMemory. |
C-kern/ | Linux specific implementation VirtualMemory Linux. |
Types | |
struct vmpage_t | Exports vmpage_t into global namespace. |
struct vm_region_t | Exports vm_region_t, describes a single virtual memory region. |
struct vm_mappedregions_t | Exports vm_mappedregions_t, description of all mapped memory. |
struct vm_regionsarray_t | Internal type used by vm_mappedregions_t. |
Functions | |
query | |
log2pagesize_vm | Returns log2_int of pagesize_vm. |
pagesize_vm | Returns the virtual memory page size supported by the underlying system. |
sizephysram_vm | Returns size of all physical memory in bytes. |
sizeavailableram_vm | Returns size of available physical memory in bytes |
sys_pagesize_vm | Returns the virtual memory page size supported by the underlying system. |
ismapped_vm | Returns true is vmpage is mapped whose accessmode equals protection. |
isunmapped_vm | Returns true if memory at vmpage is not mapped. |
test | |
unittest_platform_vm | Unittest for virtual memory module. |
vmpage_t | Type has same structure as memblock_t. |
addr | Points to start (lowest) address of memory. |
size | Size of memory in bytes addr points to. |
lifetime | |
vmpage_FREE | Static initializer. |
vmpage_INIT | Static initializer. |
init_vmpage | Map memory into the virtual address space of the calling process. |
init2_vmpage | Map memory into the virtual address space of the calling process. |
initaligned_vmpage | Map new memory into the virtual address space of the calling process. |
free_vmpage | Invalidates virtual memory address range |
query | |
isfree_vmpage | Returns true if vmpage equals vmpage_FREE. |
change | |
protect_vmpage | Sets protection of memory (e.g. |
tryexpand_vmpage | Tries to grow the upper bound of an already mapped address range. |
movexpand_vmpage | Grows an already mapped virtual memory block. |
shrink_vmpage | Shrinks the size of an already mapped virtual memory block. |
genericcast_vmpage | Casts a pointer to an compatible object into pointer to vmpage_t. |
vm_region_t | Returns information about a mapped memory region and its access permissions. |
addr | Start address or lowest address of mapping. |
endaddr | End address of mapping. |
protection | Gives protection (access rights) of the memory block. |
query | |
compare_vmregion | Returns 0 if left and right regions compare equal. |
vm_mappedregions_t | Buffer which stores a snapshot of all mapped memory regions. |
private variables | |
total_count | Number of stored elements of type vm_region_t. |
element_count | Number of elements element_iterator can access in sequence. |
element_iterator | Points to an array of vm_region_t of size element_count. |
array_iterator | Points to next array of vm_region_t which comes after array element_iterator points to. |
first_array | Points to first array of vm_region_t. |
lifetime | |
vm_mappedregions_FREE | Static initializer: Makes calling free_vmmappedregions safe. |
init_vmmappedregions | Returns in mappedregions the descriptions of all current virtual memory mappings. |
free_vmmappedregions | Free internal memory cache used to store all vm_region_t objects. |
query | |
size_vmmappedregions | Returns the total number of contained vm_region_t. |
compare_vmmappedregions | Returns 0 if all regions stored in left and right container compare equal. |
ismapped_vmmappedregions | Returns true if mappedregions contains a memory region with correct protection. |
isunmapped_vmmappedregions | Returns true if mappedregions contains no memory region which overlaps with mblock. |
iterate | |
gofirst_vmmappedregions | Resets iterator to the first element. |
next_vmmappedregions | Returns the next vm_region_t in the set of all stored elements. |
inline implementation | |
Macros | |
genericcast_vmpage | Implements vmpage_t.genericcast_vmpage. |
init_vmpage | Implements vmpage_t.init_vmpage. |
isfree_vmpage | Implements <vmpage_t.isfree_vmpage>>. |
log2pagesize_vm | Uses cached value from valuecache_maincontext. |
pagesize_vm | Uses cached value from valuecache_maincontext. |
size_vmmappedregions | Returns vm_mappedregions_t->total_count. |
This program is free software. You can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
© 2011 Jörg Seebohn
Header file of VirtualMemory.
Linux specific implementation VirtualMemory Linux.
typedef struct vmpage_t vmpage_t
Exports vmpage_t into global namespace.
typedef struct vm_region_t vm_region_t
Exports vm_region_t, describes a single virtual memory region.
typedef struct vm_mappedregions_t vm_mappedregions_t
Exports vm_mappedregions_t, description of all mapped memory.
typedef struct vm_regionsarray_t vm_regionsarray_t
Internal type used by vm_mappedregions_t.
query | |
log2pagesize_vm | Returns log2_int of pagesize_vm. |
pagesize_vm | Returns the virtual memory page size supported by the underlying system. |
sizephysram_vm | Returns size of all physical memory in bytes. |
sizeavailableram_vm | Returns size of available physical memory in bytes |
sys_pagesize_vm | Returns the virtual memory page size supported by the underlying system. |
ismapped_vm | Returns true is vmpage is mapped whose accessmode equals protection. |
isunmapped_vm | Returns true if memory at vmpage is not mapped. |
test | |
unittest_platform_vm | Unittest for virtual memory module. |
uint8_t log2pagesize_vm( void )
Returns log2_int of pagesize_vm.
struct vmpage_t
Type has same structure as memblock_t. The size of the mapped memory block is always a multiple of pagesize_vm.
addr | Points to start (lowest) address of memory. |
size | Size of memory in bytes addr points to. |
lifetime | |
vmpage_FREE | Static initializer. |
vmpage_INIT | Static initializer. |
init_vmpage | Map memory into the virtual address space of the calling process. |
init2_vmpage | Map memory into the virtual address space of the calling process. |
initaligned_vmpage | Map new memory into the virtual address space of the calling process. |
free_vmpage | Invalidates virtual memory address range |
query | |
isfree_vmpage | Returns true if vmpage equals vmpage_FREE. |
change | |
protect_vmpage | Sets protection of memory (e.g. |
tryexpand_vmpage | Tries to grow the upper bound of an already mapped address range. |
movexpand_vmpage | Grows an already mapped virtual memory block. |
shrink_vmpage | Shrinks the size of an already mapped virtual memory block. |
genericcast_vmpage | Casts a pointer to an compatible object into pointer to vmpage_t. |
size_t size
Size of memory in bytes addr points to. A value of 0 indicates a free memory page. The valid memory region is
addr[ 0 .. size - 1 ]
#define vmpage_FREE vmpage_INIT( 0, )
Static initializer. Sets object of type vmpage_t to NULL. Unmapping (free_vmpage) such a NULL vmpage_t is safe.
#define vmpage_INIT( size, addr ) { addr, size }
Static initializer. Precondition:
int init_vmpage( /*out*/vmpage_t * vmpage, size_t size_in_bytes )
Map memory into the virtual address space of the calling process. The memory size is size_in_bytes rounded up to next multiple of pagesize_vm. It is read and writeable. All the changed content is private to the current processes. A child process can access its content after a fork but see no changes the parent process also see no changes (COPY_ON_WRITE semantics).
int init2_vmpage( /*out*/vmpage_t * vmpage, size_t size_in_bytes, const accessmode_e access_mode )
Map memory into the virtual address space of the calling process. The memory size is size_in_bytes rounded up to next multiple of pagesize_vm. It is accessible as stated in paramter access_mode. A child process can access its content after a fork and a change is shared with the parent process if accessmode_SHARED was specified.
int initaligned_vmpage( /*out*/vmpage_t * vmpage, size_t powerof2_size_in_bytes )
Map new memory into the virtual address space of the calling process. The new memory has size powerof2_size_in_bytes and its description is returned in vmpage. It is read and writeable and not shared between processes. The address of the new memory is aligned to its own size. EINVAL is returned in case powerof2_size_in_bytes < pagesize_vm or if it is not a power of 2.
int free_vmpage( vmpage_t * vmpage )
Invalidates virtual memory address range
vmpage->addr[0 .. vmpage->size - 1 ]
After successull return every access to this memory range will generate a memory exception and vmpage is set to vmpage_FREE. Therefore unmapping an already unmapped memory region does nothing and returns success.
bool isfree_vmpage( vmpage_t * vmpage )
Returns true if vmpage equals vmpage_FREE.
int protect_vmpage( vmpage_t * vmpage, const accessmode_e access_mode )
Sets protection of memory (e.g. if write is possible). See accessmode_e for a list of all supported bits. accessmode_PRIVATE and accessmode_SHARED can not be changed after creation.
int tryexpand_vmpage( vmpage_t * vmpage, size_t size_in_bytes )
Tries to grow the upper bound of an already mapped address range. The new memory size is size_in_bytes rounded up to next multiple of pagesize_vm. If size_in_bytes is lower than vmpage->size EINVAL is returned and nothing is changed. The start address of virtual memory block is not changed. Returns 0 on success else ENOMEM or another system specific error code. In case of success the new address range is
[ old:vmpage->addr .. old:vmpage->addr + (size_in_bytes rounded up to multiple of pagesize_vm()))
If the memory could not be expanded no error logging is done.
int movexpand_vmpage( vmpage_t * vmpage, size_t size_in_bytes )
Grows an already mapped virtual memory block. The new memory size is size_in_bytes rounded up to next multiple of pagesize_vm. If size_in_bytes is lower than vmpage->size EINVAL is returned and nothing is changed. If the block can not be expanded (see tryexpand_vmpage) it is relocated to a new virtual address with sufficient address space. In case of success the new address range is
[ old:vmpage->addr .. old:vmpage->addr + (size_in_bytes rounded up to multiple of pagesize_vm())) or [ NEW_ADDR .. NEW_ADDR + (size_in_bytes rounded up to multiple of pagesize_vm())).
int shrink_vmpage( vmpage_t * vmpage, size_t size_in_bytes )
Shrinks the size of an already mapped virtual memory block. The start address keeps same. The new memory size is size_in_bytes rounded up to next multiple of pagesize_vm. If size_in_bytes is greater than vmpage->size EINVAL is returned and nothing is changed. In case of success the new address range is
[vmpage->addr .. vmpage->addr + (size_in_bytes rounded up to multiple of pagesize_vm())).
struct vm_region_t
Returns information about a mapped memory region and its access permissions.
addr | Start address or lowest address of mapping. |
endaddr | End address of mapping. |
protection | Gives protection (access rights) of the memory block. |
query | |
compare_vmregion | Returns 0 if left and right regions compare equal. |
accessmode_e protection
Gives protection (access rights) of the memory block. See accessmode_e for a list of supported bits.
struct vm_mappedregions_t
Buffer which stores a snapshot of all mapped memory regions. Use init_vmmappedregions to store a snapshot of the current mapping. Do not forget to call free_vmmappedregions after using. To access individual mapping descriptions of type vm_region_t use next_vmmappedregions. With gofirst_vmmappedregions you can reset the internal iterator and scan from the beginning again.
private variables | |
total_count | Number of stored elements of type vm_region_t. |
element_count | Number of elements element_iterator can access in sequence. |
element_iterator | Points to an array of vm_region_t of size element_count. |
array_iterator | Points to next array of vm_region_t which comes after array element_iterator points to. |
first_array | Points to first array of vm_region_t. |
lifetime | |
vm_mappedregions_FREE | Static initializer: Makes calling free_vmmappedregions safe. |
init_vmmappedregions | Returns in mappedregions the descriptions of all current virtual memory mappings. |
free_vmmappedregions | Free internal memory cache used to store all vm_region_t objects. |
query | |
size_vmmappedregions | Returns the total number of contained vm_region_t. |
compare_vmmappedregions | Returns 0 if all regions stored in left and right container compare equal. |
ismapped_vmmappedregions | Returns true if mappedregions contains a memory region with correct protection. |
isunmapped_vmmappedregions | Returns true if mappedregions contains no memory region which overlaps with mblock. |
iterate | |
gofirst_vmmappedregions | Resets iterator to the first element. |
next_vmmappedregions | Returns the next vm_region_t in the set of all stored elements. |
size_t total_count
Number of stored elements of type vm_region_t.
size_t element_count
Number of elements element_iterator can access in sequence. Used to implement internal iterator.
vm_region_t * element_iterator
Points to an array of vm_region_t of size element_count. Used to implement internal iterator.
vm_regionsarray_t * array_iterator
Points to next array of vm_region_t which comes after array element_iterator points to. Used to implement internal iterator.
vm_regionsarray_t * first_array
Points to first array of vm_region_t. The memory is organized as a list of arrays of elements of type vm_region_t. Used to implement internal iterator and to free memory.
#define vm_mappedregions_FREE { 0, 0, 0, 0, 0 }
Static initializer: Makes calling free_vmmappedregions safe.
int init_vmmappedregions( /*out*/vm_mappedregions_t * mappedregions )
Returns in mappedregions the descriptions of all current virtual memory mappings. If changes are made to the mapping of virtual memory pages after the call to init mappedregions still holds the old mapping description. See vm_region_t for a description of the returned information.
int free_vmmappedregions( vm_mappedregions_t * mappedregions )
Free internal memory cache used to store all vm_region_t objects.
size_t size_vmmappedregions( const vm_mappedregions_t * mappedregions )
Returns the total number of contained vm_region_t.
void gofirst_vmmappedregions( vm_mappedregions_t * iterator )
Resets iterator to the first element. The next call to next_vmmappedregions will return the first contained element. See generic <ArrayList Iterator> for a more in deep description.
const vm_region_t * next_vmmappedregions( vm_mappedregions_t * iterator )
Returns the next vm_region_t in the set of all stored elements. NULL is returned if there is no next element. See generic <ArrayList Iterator> for a more in deep description.
Macros | |
genericcast_vmpage | Implements vmpage_t.genericcast_vmpage. |
init_vmpage | Implements vmpage_t.init_vmpage. |
isfree_vmpage | Implements <vmpage_t.isfree_vmpage>>. |
log2pagesize_vm | Uses cached value from valuecache_maincontext. |
pagesize_vm | Uses cached value from valuecache_maincontext. |
size_vmmappedregions | Returns vm_mappedregions_t->total_count. |
#define genericcast_vmpage( obj, nameprefix ) ( __extension__ ({ typeof(obj) _obj = (obj) ; static_assert( sizeof(_obj->nameprefix##addr) == sizeof(((vmpage_t*)0)->addr) && 0 == offsetof(vmpage_t, addr), "addr member is compatible") ; static_assert( sizeof(_obj->nameprefix##size) == sizeof(((vmpage_t*)0)->size) && offsetof(vmpage_t, size) == ((uintptr_t)&_obj->nameprefix##size) -((uintptr_t)&_obj->nameprefix##addr), "size member is compatible") ; if (0) { volatile uint8_t _err ; volatile size_t _size ; _size = _obj->nameprefix##size ; _err = _obj->nameprefix##addr[_size] ; (void) _err ; } (vmpage_t *)(&_obj->nameprefix##addr) ; }))
Implements vmpage_t.genericcast_vmpage.
#define init_vmpage( vmpage, size_in_bytes ) (init2_vmpage((vmpage), (size_in_bytes), accessmode_RDWR|accessmode_PRIVATE))
Implements vmpage_t.init_vmpage.
#define log2pagesize_vm( ) (valuecache_maincontext()->log2pagesize_vm)
Uses cached value from valuecache_maincontext.
#define pagesize_vm( ) (valuecache_maincontext()->pagesize_vm)
Uses cached value from valuecache_maincontext.
#define size_vmmappedregions( mappedregions ) ((mappedregions)->total_count)
Returns vm_mappedregions_t->total_count. Inline implementation of vm_mappedregions_t.size_vmmappedregions.
Exports vmpage_t into global namespace.
typedef struct vmpage_t vmpage_t
Type has same structure as memblock_t.
struct vmpage_t
Exports vm_region_t, describes a single virtual memory region.
typedef struct vm_region_t vm_region_t
Returns information about a mapped memory region and its access permissions.
struct vm_region_t
Exports vm_mappedregions_t, description of all mapped memory.
typedef struct vm_mappedregions_t vm_mappedregions_t
Buffer which stores a snapshot of all mapped memory regions.
struct vm_mappedregions_t
Internal type used by vm_mappedregions_t.
typedef struct vm_regionsarray_t vm_regionsarray_t
Returns log2_int of pagesize_vm.
uint8_t log2pagesize_vm( void )
Returns the virtual memory page size supported by the underlying system.
uint32_t pagesize_vm( void )
Returns size of all physical memory in bytes.
ramsize_t sizephysram_vm( void )
Returns size of available physical memory in bytes
ramsize_t sizeavailableram_vm( void )
Returns the virtual memory page size supported by the underlying system.
uint32_t sys_pagesize_vm( void )
Returns true is vmpage is mapped whose accessmode equals protection.
bool ismapped_vm( const vmpage_t * vmpage, accessmode_e protection )
Returns true if memory at vmpage is not mapped.
bool isunmapped_vm( const vmpage_t * vmpage )
Unittest for virtual memory module.
int unittest_platform_vm( void )
Describes memory block.
struct memblock_t
Points to start (lowest) address of memory.
uint8_t * addr
Size of memory in bytes addr points to.
size_t size
Static initializer.
#define vmpage_FREE vmpage_INIT( 0, )
Static initializer.
#define vmpage_INIT( size, addr ) { addr, size }
Map memory into the virtual address space of the calling process.
int init_vmpage( /*out*/vmpage_t * vmpage, size_t size_in_bytes )
Map memory into the virtual address space of the calling process.
int init2_vmpage( /*out*/vmpage_t * vmpage, size_t size_in_bytes, const accessmode_e access_mode )
Map new memory into the virtual address space of the calling process.
int initaligned_vmpage( /*out*/vmpage_t * vmpage, size_t powerof2_size_in_bytes )
Invalidates virtual memory address range
int free_vmpage( vmpage_t * vmpage )
Returns true if vmpage equals vmpage_FREE.
bool isfree_vmpage( vmpage_t * vmpage )
Sets protection of memory (e.g.
int protect_vmpage( vmpage_t * vmpage, const accessmode_e access_mode )
Tries to grow the upper bound of an already mapped address range.
int tryexpand_vmpage( vmpage_t * vmpage, size_t size_in_bytes )
Grows an already mapped virtual memory block.
int movexpand_vmpage( vmpage_t * vmpage, size_t size_in_bytes )
Shrinks the size of an already mapped virtual memory block.
int shrink_vmpage( vmpage_t * vmpage, size_t size_in_bytes )
Casts a pointer to an compatible object into pointer to vmpage_t.
vmpage_t * genericcast_vmpage( void * obj, IDNAME nameprefix )
Start address or lowest address of mapping.
void * addr
End address of mapping.
void * endaddr
Gives protection (access rights) of the memory block.
accessmode_e protection
Returns 0 if left and right regions compare equal.
int compare_vmregion( const vm_region_t * left, const vm_region_t * right )
Number of stored elements of type vm_region_t.
size_t total_count
Number of elements element_iterator can access in sequence.
size_t element_count
Points to an array of vm_region_t of size element_count.
vm_region_t * element_iterator
Points to next array of vm_region_t which comes after array element_iterator points to.
vm_regionsarray_t * array_iterator
Points to first array of vm_region_t.
vm_regionsarray_t * first_array
Static initializer: Makes calling free_vmmappedregions safe.
#define vm_mappedregions_FREE { 0, 0, 0, 0, 0 }
Free internal memory cache used to store all vm_region_t objects.
int free_vmmappedregions( vm_mappedregions_t * mappedregions )
Returns in mappedregions the descriptions of all current virtual memory mappings.
int init_vmmappedregions( /*out*/vm_mappedregions_t * mappedregions )
Returns the total number of contained vm_region_t.
size_t size_vmmappedregions( const vm_mappedregions_t * mappedregions )
Returns 0 if all regions stored in left and right container compare equal.
int compare_vmmappedregions( const vm_mappedregions_t * left, const vm_mappedregions_t * right )
Returns true if mappedregions contains a memory region with correct protection.
bool ismapped_vmmappedregions( vm_mappedregions_t * mappedregions, const vmpage_t * mblock, accessmode_e protection )
Returns true if mappedregions contains no memory region which overlaps with mblock.
bool isunmapped_vmmappedregions( vm_mappedregions_t * mappedregions, const vmpage_t * mblock )
Resets iterator to the first element.
void gofirst_vmmappedregions( vm_mappedregions_t * iterator )
Returns the next vm_region_t in the set of all stored elements.
const vm_region_t * next_vmmappedregions( vm_mappedregions_t * iterator )
Implements vmpage_t.genericcast_vmpage.
#define genericcast_vmpage( obj, nameprefix ) ( __extension__ ({ typeof(obj) _obj = (obj) ; static_assert( sizeof(_obj->nameprefix##addr) == sizeof(((vmpage_t*)0)->addr) && 0 == offsetof(vmpage_t, addr), "addr member is compatible") ; static_assert( sizeof(_obj->nameprefix##size) == sizeof(((vmpage_t*)0)->size) && offsetof(vmpage_t, size) == ((uintptr_t)&_obj->nameprefix##size) -((uintptr_t)&_obj->nameprefix##addr), "size member is compatible") ; if (0) { volatile uint8_t _err ; volatile size_t _size ; _size = _obj->nameprefix##size ; _err = _obj->nameprefix##addr[_size] ; (void) _err ; } (vmpage_t *)(&_obj->nameprefix##addr) ; }))
Implements vmpage_t.init_vmpage.
#define init_vmpage( vmpage, size_in_bytes ) (init2_vmpage((vmpage), (size_in_bytes), accessmode_RDWR|accessmode_PRIVATE))
Implements <vmpage_t.isfree_vmpage>>.
#define isfree_vmpage( vmpage ) (0 == (vmpage)->addr && 0 == (vmpage)->size)
Inline implementation of maincontext_t.valuecache_maincontext.
#define valuecache_maincontext( ) (pcontext_maincontext()->valuecache)
Returns vm_mappedregions_t->total_count.
#define size_vmmappedregions( mappedregions ) ((mappedregions)->total_count)