guest_ram: add custom iterator
Add a function that initialises ram with a
custom iterator. This is used for mapping vm
memory onto a dataport.
diff --git a/libsel4vm/include/sel4vm/guest_ram.h b/libsel4vm/include/sel4vm/guest_ram.h
index f2a4c5f..be8cf5e 100644
--- a/libsel4vm/include/sel4vm/guest_ram.h
+++ b/libsel4vm/include/sel4vm/guest_ram.h
@@ -102,6 +102,19 @@
int vm_ram_register_at(vm_t *vm, uintptr_t start, size_t bytes, bool untyped);
/***
+ * @function vm_ram_register_at(vm, start, bytes, untyped)
+ * Reserve a region of memory for RAM in the guest VM at a starting guest physical address with a custom memory iterator
+ * @param {vm_t *} vm A handle to the VM that ram needs to be allocated for
+ * @param {uintptr_t} start Starting guest physical address of the ram region being allocated
+ * @param {size_t} size The size of the RAM region to be allocated
+ * @param {memory_map_iterator_fn} map_iterator Iterator function
+ * @param {void *} cookie Iterator cookie
+ * @return 0 on success, -1 on error
+ */
+int vm_ram_register_at_custom_iterator(vm_t *vm, uintptr_t start, size_t bytes, memory_map_iterator_fn map_iterator,
+ void *cookie);
+
+/***
* @function vm_ram_mark_allocated(vm, start, bytes)
* Mark a registered region of RAM as allocated
* @param {vm_t *} vm A handle to the VM
diff --git a/libsel4vm/src/guest_ram.c b/libsel4vm/src/guest_ram.c
index 22d0da4..9b7887b 100644
--- a/libsel4vm/src/guest_ram.c
+++ b/libsel4vm/src/guest_ram.c
@@ -375,6 +375,32 @@
return 0;
}
+int vm_ram_register_at_custom_iterator(vm_t *vm, uintptr_t start, size_t bytes, memory_map_iterator_fn map_iterator,
+ void *cookie)
+{
+ vm_memory_reservation_t *ram_reservation;
+ int err;
+
+ ram_reservation = vm_reserve_memory_at(vm, start, bytes, default_ram_fault_callback,
+ NULL);
+ if (!ram_reservation) {
+ ZF_LOGE("Unable to reserve ram region at addr 0x%x of size 0x%x", start, bytes);
+ return -1;
+ }
+ err = map_vm_memory_reservation(vm, ram_reservation, map_iterator, cookie);
+ if (err) {
+ ZF_LOGE("failed to map vm memory reservation to dataport\n");
+ return -1;
+ }
+ err = expand_guest_ram_region(vm, start, bytes);
+ if (err) {
+ ZF_LOGE("Failed to register new ram region");
+ vm_free_reserved_memory(vm, ram_reservation);
+ return -1;
+ }
+ return 0;
+}
+
void vm_ram_free(vm_t *vm, uintptr_t start, size_t bytes)
{
return;