anv: Use DRM_XE_VM_BIND_OP_UNMAP_ALL to unbind whole bos

For non-sparse usage there is no difference between
DRM_XE_VM_BIND_OP_UNMAP_ALL and DRM_XE_VM_BIND_OP_UNMAP but for sparse
the same bo can be bound to more than one virtual address.

Then in a case like:
img = vkCreateImage()
mem = vkAllocateMemory()
vkQueueBindSparse(img, mem)
vkFreeMemory(mem)

Note that the sparse VMA bind still points to the closed bo(done in
vkFreeMemory()), but with DRM_XE_VM_BIND_OP_UNMAP_ALL all VMAs
over the bos are removed.

Access to a unbound VMA has a defined behavior(page fault) while
access to a bound VMA without backing gem/bo don't have defined
behavior.

Suggested-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Reviewed-by: Lionel Landwerlin <lionel.g.landwerlin@intel.com>
Signed-off-by: José Roberto de Souza <jose.souza@intel.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/27601>
This commit is contained in:
José Roberto de Souza 2024-02-13 09:05:21 -08:00 committed by Marge Bot
parent 3acb00290d
commit 19439624d9
2 changed files with 14 additions and 3 deletions

View file

@ -42,8 +42,12 @@ struct anv_sparse_submission;
struct anv_trtt_batch_bo;
enum anv_vm_bind_op {
/* bind vma specified in anv_vm_bind */
ANV_VM_BIND,
/* unbind vma specified in anv_vm_bind */
ANV_VM_UNBIND,
/* unbind all vmas of anv_vm_bind::bo, address and size fields must be set to 0 */
ANV_VM_UNBIND_ALL,
};
struct anv_vm_bind {

View file

@ -171,6 +171,13 @@ xe_vm_bind_op(struct anv_device *device,
xe_bind->op = DRM_XE_VM_BIND_OP_MAP;
xe_bind->obj = bo->gem_handle;
}
} else if (bind->op == ANV_VM_UNBIND_ALL) {
xe_bind->op = DRM_XE_VM_BIND_OP_UNMAP_ALL;
xe_bind->obj = bo->gem_handle;
assert(bind->address == 0);
assert(bind->size == 0);
} else {
assert(bind->op == ANV_VM_UNBIND);
}
/* userptr and bo_offset are an union! */
@ -223,10 +230,10 @@ static int xe_vm_unbind_bo(struct anv_device *device, struct anv_bo *bo)
{
struct anv_vm_bind bind = {
.bo = bo,
.address = bo->offset,
.address = 0,
.bo_offset = 0,
.size = bo->actual_size,
.op = ANV_VM_UNBIND,
.size = 0,
.op = ANV_VM_UNBIND_ALL,
};
struct anv_sparse_submission submit = {
.queue = NULL,