vm: controller: add an auto-detach flag for vm-objects
This commit is contained in:
@@ -7,6 +7,7 @@
|
||||
#include <kernel/sched.h>
|
||||
#include <kernel/task.h>
|
||||
#include <kernel/util.h>
|
||||
#include <kernel/vm-controller.h>
|
||||
#include <kernel/vm-object.h>
|
||||
#include <mango/status.h>
|
||||
|
||||
@@ -721,6 +722,9 @@ kern_status_t address_space_map(
|
||||
}
|
||||
|
||||
tracek("address_space_map(%zx, %zx)", map_address, length);
|
||||
if (map_address == 0xc6a55000) {
|
||||
printk("break");
|
||||
}
|
||||
|
||||
if (!root || !object) {
|
||||
tracek("null pointer");
|
||||
@@ -838,7 +842,7 @@ static kern_status_t split_area(
|
||||
|
||||
put_entry(&root->s_mappings, right);
|
||||
for (size_t i = unmap_base; i < unmap_limit; i += VM_PAGE_SIZE) {
|
||||
tracek("unmapping %zx", i);
|
||||
tracek("pmap_remove %zx", i);
|
||||
pmap_remove(root->s_pmap, i);
|
||||
}
|
||||
|
||||
@@ -875,7 +879,7 @@ static kern_status_t left_reduce_area(
|
||||
return KERN_OK;
|
||||
}
|
||||
|
||||
tracek(" unmapping %zx-%zx (%zx bytes)", base, base + length, length);
|
||||
tracek(" pmap_remove %zx-%zx (%zx bytes)", base, base + length, length);
|
||||
for (size_t i = base; i < limit; i += VM_PAGE_SIZE) {
|
||||
pmap_remove(root->s_pmap, i);
|
||||
}
|
||||
@@ -912,7 +916,7 @@ static kern_status_t right_reduce_area(
|
||||
return KERN_OK;
|
||||
}
|
||||
|
||||
tracek(" unmapping %zx-%zx (%zx bytes)", base, base + length, length);
|
||||
tracek(" pmap_remove %zx-%zx (%zx bytes)", base, base + length, length);
|
||||
for (size_t i = base; i < limit; i += VM_PAGE_SIZE) {
|
||||
pmap_remove(root->s_pmap, i);
|
||||
}
|
||||
@@ -930,9 +934,10 @@ static kern_status_t delete_area(
|
||||
return KERN_OK;
|
||||
}
|
||||
|
||||
tracek("delete mapping [%zx-%zx]",
|
||||
tracek("delete mapping [%zx-%zx] (%zx bytes)",
|
||||
mapping->vma_base,
|
||||
mapping->vma_limit);
|
||||
mapping->vma_limit,
|
||||
mapping->vma_limit - mapping->vma_base);
|
||||
|
||||
for (size_t i = mapping->vma_base; i < mapping->vma_limit;
|
||||
i += VM_PAGE_SIZE) {
|
||||
@@ -946,7 +951,23 @@ static kern_status_t delete_area(
|
||||
&mapping->vma_object->vo_mappings,
|
||||
&mapping->vma_object_entry);
|
||||
mapping->vma_object = NULL;
|
||||
/* if the object is attached to a controller and the ref-count is 2,
|
||||
* then the only other remaining reference to this object is held by
|
||||
* the controller. */
|
||||
struct vm_controller *ctrl = object->vo_ctrl;
|
||||
bool detach = ctrl != NULL && object->vo_base.ob_refcount == 2
|
||||
&& (object->vo_flags & VMO_AUTO_DETACH);
|
||||
vm_object_unlock_irqrestore(object, flags);
|
||||
|
||||
if (detach) {
|
||||
/* TODO find a better way to achieve this, and/or give the
|
||||
* server that created the object more control over when it
|
||||
* should be detached */
|
||||
vm_controller_lock_irqsave(ctrl, &flags);
|
||||
vm_controller_detach_object(ctrl, object);
|
||||
vm_controller_unlock_irqrestore(ctrl, flags);
|
||||
}
|
||||
|
||||
object_unref(&object->vo_base);
|
||||
|
||||
/* don't actually delete the mapping yet. that will be done by
|
||||
|
||||
Reference in New Issue
Block a user