drm/amdgpu: merge VM manager and VM context ID structure
authorChristian König <christian.koenig@amd.com>
Tue, 8 Mar 2016 14:40:11 +0000 (15:40 +0100)
committerAlex Deucher <alexander.deucher@amd.com>
Thu, 5 May 2016 00:19:13 +0000 (20:19 -0400)
No need to have two of them any more.

Signed-off-by: Christian König <christian.koenig@amd.com>
Acked-by: Alex Deucher <alexander.deucher@amd.com>
Reviewed-by: Chunming Zhou <david1.zhou@amd.com>
Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
drivers/gpu/drm/amd/amdgpu/amdgpu.h
drivers/gpu/drm/amd/amdgpu/amdgpu_vm.c

index b9a6fe9a2a31b2c4b6bd447698c161c8928bb179..c1b10046317ed3733599163baff421201f9c4be4 100644 (file)
@@ -839,13 +839,6 @@ struct amdgpu_vm_pt {
        uint64_t                        addr;
 };
 
-struct amdgpu_vm_id {
-       struct amdgpu_vm_manager_id     *mgr_id;
-       uint64_t                        pd_gpu_addr;
-       /* last flushed PD/PT update */
-       struct fence                    *flushed_updates;
-};
-
 struct amdgpu_vm {
        /* tree of virtual addresses mapped */
        struct rb_root          va;
@@ -871,7 +864,7 @@ struct amdgpu_vm {
        struct amdgpu_vm_pt     *page_tables;
 
        /* for id and flush management per ring */
-       struct amdgpu_vm_id     ids[AMDGPU_MAX_RINGS];
+       struct amdgpu_vm_id     *ids[AMDGPU_MAX_RINGS];
 
        /* protecting freed */
        spinlock_t              freed_lock;
@@ -880,11 +873,15 @@ struct amdgpu_vm {
        struct amd_sched_entity entity;
 };
 
-struct amdgpu_vm_manager_id {
+struct amdgpu_vm_id {
        struct list_head        list;
        struct fence            *active;
        atomic_long_t           owner;
 
+       uint64_t                pd_gpu_addr;
+       /* last flushed PD/PT update */
+       struct fence            *flushed_updates;
+
        uint32_t                gds_base;
        uint32_t                gds_size;
        uint32_t                gws_base;
@@ -898,7 +895,7 @@ struct amdgpu_vm_manager {
        struct mutex                            lock;
        unsigned                                num_ids;
        struct list_head                        ids_lru;
-       struct amdgpu_vm_manager_id             ids[AMDGPU_NUM_VM];
+       struct amdgpu_vm_id                     ids[AMDGPU_NUM_VM];
 
        uint32_t                                max_pfn;
        /* vram base address for page table entry  */
index 0c92e0450694f01de80db59e8c61cdf9a60267cf..8a758b4fb3a9caa0c01f65e0df2a5e53c0c21a37 100644 (file)
@@ -166,43 +166,41 @@ int amdgpu_vm_grab_id(struct amdgpu_vm *vm, struct amdgpu_ring *ring,
 {
        uint64_t pd_addr = amdgpu_bo_gpu_offset(vm->page_directory);
        struct amdgpu_device *adev = ring->adev;
-       struct amdgpu_vm_id *id = &vm->ids[ring->idx];
+       struct amdgpu_vm_id *id = vm->ids[ring->idx];
        struct fence *updates = sync->last_vm_update;
        int r;
 
        mutex_lock(&adev->vm_manager.lock);
 
        /* check if the id is still valid */
-       if (id->mgr_id) {
+       if (id) {
                struct fence *flushed = id->flushed_updates;
-               bool is_later;
-               long owner;
+               long owner = atomic_long_read(&id->owner);
+               bool usable = pd_addr == id->pd_gpu_addr;
 
-               if (!flushed)
-                       is_later = true;
+               if (owner != (long)&vm->ids[ring->idx])
+                       usable = false;
+               else if (!flushed)
+                       usable = false;
                else if (!updates)
-                       is_later = false;
+                       usable = true;
                else
-                       is_later = fence_is_later(updates, flushed);
+                       usable = !fence_is_later(updates, flushed);
 
-               owner = atomic_long_read(&id->mgr_id->owner);
-               if (!is_later && owner == (long)id &&
-                   pd_addr == id->pd_gpu_addr) {
+               if (usable) {
 
-                       r = amdgpu_sync_fence(ring->adev, sync,
-                                             id->mgr_id->active);
+                       r = amdgpu_sync_fence(ring->adev, sync, id->active);
                        if (r) {
                                mutex_unlock(&adev->vm_manager.lock);
                                return r;
                        }
 
-                       fence_put(id->mgr_id->active);
-                       id->mgr_id->active = fence_get(fence);
+                       fence_put(id->active);
+                       id->active = fence_get(fence);
 
-                       list_move_tail(&id->mgr_id->list,
-                                      &adev->vm_manager.ids_lru);
+                       list_move_tail(&id->list, &adev->vm_manager.ids_lru);
 
-                       *vm_id = id->mgr_id - adev->vm_manager.ids;
+                       *vm_id = id - adev->vm_manager.ids;
                        *vm_pd_addr = AMDGPU_VM_NO_FLUSH;
                        trace_amdgpu_vm_grab_id(vm, ring->idx, *vm_id,
                                                *vm_pd_addr);
@@ -212,38 +210,41 @@ int amdgpu_vm_grab_id(struct amdgpu_vm *vm, struct amdgpu_ring *ring,
                }
        }
 
-       id->mgr_id = list_first_entry(&adev->vm_manager.ids_lru,
-                                     struct amdgpu_vm_manager_id,
-                                     list);
+       id = list_first_entry(&adev->vm_manager.ids_lru,
+                             struct amdgpu_vm_id,
+                             list);
 
-       if (id->mgr_id->active && !fence_is_signaled(id->mgr_id->active)) {
-               struct amdgpu_vm_manager_id *mgr_id, *tmp;
+       if (id->active && !fence_is_signaled(id->active)) {
+               struct amdgpu_vm_id *tmp;
                struct list_head *head = &adev->vm_manager.ids_lru;
-               list_for_each_entry_safe(mgr_id, tmp, &adev->vm_manager.ids_lru, list) {
-                       if (mgr_id->active && fence_is_signaled(mgr_id->active)) {
-                               list_move(&mgr_id->list, head);
-                               head = &mgr_id->list;
+
+               list_for_each_entry_safe(id, tmp, &adev->vm_manager.ids_lru,
+                                        list) {
+                       if (id->active && fence_is_signaled(id->active)) {
+                               list_move(&id->list, head);
+                               head = &id->list;
                        }
                }
-               id->mgr_id = list_first_entry(&adev->vm_manager.ids_lru,
-                                             struct amdgpu_vm_manager_id,
-                                             list);
+               id = list_first_entry(&adev->vm_manager.ids_lru,
+                                     struct amdgpu_vm_id,
+                                     list);
        }
 
-       r = amdgpu_sync_fence(ring->adev, sync, id->mgr_id->active);
+       r = amdgpu_sync_fence(ring->adev, sync, id->active);
        if (!r) {
-               fence_put(id->mgr_id->active);
-               id->mgr_id->active = fence_get(fence);
+               fence_put(id->active);
+               id->active = fence_get(fence);
 
                fence_put(id->flushed_updates);
                id->flushed_updates = fence_get(updates);
 
                id->pd_gpu_addr = pd_addr;
 
-               list_move_tail(&id->mgr_id->list, &adev->vm_manager.ids_lru);
-               atomic_long_set(&id->mgr_id->owner, (long)id);
+               list_move_tail(&id->list, &adev->vm_manager.ids_lru);
+               atomic_long_set(&id->owner, (long)&vm->ids[ring->idx]);
+               vm->ids[ring->idx] = id;
 
-               *vm_id = id->mgr_id - adev->vm_manager.ids;
+               *vm_id = id - adev->vm_manager.ids;
                *vm_pd_addr = pd_addr;
                trace_amdgpu_vm_grab_id(vm, ring->idx, *vm_id, *vm_pd_addr);
        }
@@ -268,14 +269,14 @@ void amdgpu_vm_flush(struct amdgpu_ring *ring,
                     uint32_t oa_base, uint32_t oa_size)
 {
        struct amdgpu_device *adev = ring->adev;
-       struct amdgpu_vm_manager_id *mgr_id = &adev->vm_manager.ids[vm_id];
+       struct amdgpu_vm_id *id = &adev->vm_manager.ids[vm_id];
        bool gds_switch_needed = ring->funcs->emit_gds_switch && (
-               mgr_id->gds_base != gds_base ||
-               mgr_id->gds_size != gds_size ||
-               mgr_id->gws_base != gws_base ||
-               mgr_id->gws_size != gws_size ||
-               mgr_id->oa_base != oa_base ||
-               mgr_id->oa_size != oa_size);
+               id->gds_base != gds_base ||
+               id->gds_size != gds_size ||
+               id->gws_base != gws_base ||
+               id->gws_size != gws_size ||
+               id->oa_base != oa_base ||
+               id->oa_size != oa_size);
 
        if (ring->funcs->emit_pipeline_sync && (
            pd_addr != AMDGPU_VM_NO_FLUSH || gds_switch_needed))
@@ -287,12 +288,12 @@ void amdgpu_vm_flush(struct amdgpu_ring *ring,
        }
 
        if (gds_switch_needed) {
-               mgr_id->gds_base = gds_base;
-               mgr_id->gds_size = gds_size;
-               mgr_id->gws_base = gws_base;
-               mgr_id->gws_size = gws_size;
-               mgr_id->oa_base = oa_base;
-               mgr_id->oa_size = oa_size;
+               id->gds_base = gds_base;
+               id->gds_size = gds_size;
+               id->gws_base = gws_base;
+               id->gws_size = gws_size;
+               id->oa_base = oa_base;
+               id->oa_size = oa_size;
                amdgpu_ring_emit_gds_switch(ring, vm_id,
                                            gds_base, gds_size,
                                            gws_base, gws_size,
@@ -310,14 +311,14 @@ void amdgpu_vm_flush(struct amdgpu_ring *ring,
  */
 void amdgpu_vm_reset_id(struct amdgpu_device *adev, unsigned vm_id)
 {
-       struct amdgpu_vm_manager_id *mgr_id = &adev->vm_manager.ids[vm_id];
-
-       mgr_id->gds_base = 0;
-       mgr_id->gds_size = 0;
-       mgr_id->gws_base = 0;
-       mgr_id->gws_size = 0;
-       mgr_id->oa_base = 0;
-       mgr_id->oa_size = 0;
+       struct amdgpu_vm_id *id = &adev->vm_manager.ids[vm_id];
+
+       id->gds_base = 0;
+       id->gds_size = 0;
+       id->gws_base = 0;
+       id->gws_size = 0;
+       id->oa_base = 0;
+       id->oa_size = 0;
 }
 
 /**
@@ -1345,10 +1346,8 @@ int amdgpu_vm_init(struct amdgpu_device *adev, struct amdgpu_vm *vm)
        struct amd_sched_rq *rq;
        int i, r;
 
-       for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-               vm->ids[i].mgr_id = NULL;
-               vm->ids[i].flushed_updates = NULL;
-       }
+       for (i = 0; i < AMDGPU_MAX_RINGS; ++i)
+               vm->ids[i] = NULL;
        vm->va = RB_ROOT;
        spin_lock_init(&vm->status_lock);
        INIT_LIST_HEAD(&vm->invalidated);
@@ -1443,12 +1442,12 @@ void amdgpu_vm_fini(struct amdgpu_device *adev, struct amdgpu_vm *vm)
        fence_put(vm->page_directory_fence);
 
        for (i = 0; i < AMDGPU_MAX_RINGS; ++i) {
-               struct amdgpu_vm_id *id = &vm->ids[i];
+               struct amdgpu_vm_id *id = vm->ids[i];
 
-               if (id->mgr_id)
-                       atomic_long_cmpxchg(&id->mgr_id->owner,
-                                           (long)id, 0);
-               fence_put(id->flushed_updates);
+               if (!id)
+                       continue;
+
+               atomic_long_cmpxchg(&id->owner, (long)&vm->ids[i], 0);
        }
 }
 
@@ -1486,6 +1485,10 @@ void amdgpu_vm_manager_fini(struct amdgpu_device *adev)
 {
        unsigned i;
 
-       for (i = 0; i < AMDGPU_NUM_VM; ++i)
-               fence_put(adev->vm_manager.ids[i].active);
+       for (i = 0; i < AMDGPU_NUM_VM; ++i) {
+               struct amdgpu_vm_id *id = &adev->vm_manager.ids[i];
+
+               fence_put(id->active);
+               fence_put(id->flushed_updates);
+       }
 }