From: Saleemkhan Jamadar <[email protected]>
User queue fence driver handles the interrupts received
from the VCN firmware in case of user queue submissions,
changes are done in VCN interrupt handler to process the
received interrupt and pass to appropriate fence driver.
v2 - handle the case when kernel and usermode queues are active
to service the interrrupt. (Alex)
Signed-off-by: Saleemkhan Jamadar <[email protected]>
Reviewed-by: Alex Deucher <[email protected]>
---
drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c | 37 +++++++++++++++++--------
1 file changed, 26 insertions(+), 11 deletions(-)
diff --git a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
index d2744cd4c865..c246a932a4e6 100644
--- a/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
+++ b/drivers/gpu/drm/amd/amdgpu/vcn_v4_0_5.c
@@ -32,6 +32,7 @@
#include "vcn_v2_0.h"
#include "mmsch_v4_0.h"
#include "vcn_v4_0_5.h"
+#include "amdgpu_userq_fence.h"
#include "vcn/vcn_4_0_5_offset.h"
#include "vcn/vcn_4_0_5_sh_mask.h"
@@ -1666,6 +1667,7 @@ static int vcn_v4_0_5_set_pg_state(struct amdgpu_vcn_inst
*vinst,
static int vcn_v4_0_5_process_interrupt(struct amdgpu_device *adev, struct
amdgpu_irq_src *source,
struct amdgpu_iv_entry *entry)
{
+ u32 doorbell_offset = entry->src_data[0];
uint32_t ip_instance;
switch (entry->client_id) {
@@ -1682,17 +1684,30 @@ static int vcn_v4_0_5_process_interrupt(struct
amdgpu_device *adev, struct amdgp
DRM_DEBUG("IH: VCN TRAP\n");
- switch (entry->src_id) {
- case VCN_4_0__SRCID__UVD_ENC_GENERAL_PURPOSE:
- amdgpu_fence_process(&adev->vcn.inst[ip_instance].ring_enc[0]);
- break;
- case VCN_4_0__SRCID_UVD_POISON:
- amdgpu_vcn_process_poison_irq(adev, source, entry);
- break;
- default:
- DRM_ERROR("Unhandled interrupt: %d %d\n",
- entry->src_id, entry->src_data[0]);
- break;
+ if (doorbell_offset) {
+ struct xarray *xa = &adev->userq_xa;
+ struct amdgpu_userq_fence_driver *fence_drv;
+ unsigned long flags;
+
+ xa_lock_irqsave(xa, flags);
+ fence_drv = xa_load(xa, doorbell_offset);
+ if (fence_drv)
+ amdgpu_userq_fence_driver_process(fence_drv);
+
+ xa_unlock_irqrestore(xa, flags);
+ } else {
+ switch (entry->src_id) {
+ case VCN_4_0__SRCID__UVD_ENC_GENERAL_PURPOSE:
+
amdgpu_fence_process(&adev->vcn.inst[ip_instance].ring_enc[0]);
+ break;
+ case VCN_4_0__SRCID_UVD_POISON:
+ amdgpu_vcn_process_poison_irq(adev, source, entry);
+ break;
+ default:
+ DRM_ERROR("Unhandled interrupt: %d %d\n",
+ entry->src_id, entry->src_data[0]);
+ break;
+ }
}
return 0;
--
2.43.0