From: Lang Yu <[email protected]>

Implement proper front door loading for vpe 6.1.

Signed-off-by: Lang Yu <[email protected]>
Signed-off-by: Alex Deucher <[email protected]>
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c   |  3 ++
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  1 +
 drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.c   | 38 +++++++++++++++++++++++
 drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.h   |  5 +++
 drivers/gpu/drm/amd/amdgpu/psp_gfx_if.h   |  1 +
 drivers/gpu/drm/amd/amdgpu/vpe_v6_1.c     | 15 +++++++++
 6 files changed, 63 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index 0eef555e3ef8..bd70715d329f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -2396,6 +2396,9 @@ static int psp_get_fw_type(struct amdgpu_firmware_info 
*ucode,
        case AMDGPU_UCODE_ID_VPE_CTL:
                *type = GFX_FW_TYPE_VPEC_FW2;
                break;
+       case AMDGPU_UCODE_ID_VPE:
+               *type = GFX_FW_TYPE_VPE;
+               break;
        case AMDGPU_UCODE_ID_MAXIMUM:
        default:
                return -EINVAL;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
index 0b601efa2944..4db6d0090893 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -489,6 +489,7 @@ enum AMDGPU_UCODE_ID {
        AMDGPU_UCODE_ID_DMCUB,
        AMDGPU_UCODE_ID_VPE_CTX,
        AMDGPU_UCODE_ID_VPE_CTL,
+       AMDGPU_UCODE_ID_VPE,
        AMDGPU_UCODE_ID_MAXIMUM,
 };
 
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.c
index a84e03a9b0fc..ae070072705a 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.c
@@ -37,6 +37,17 @@
 
 static void vpe_set_ring_funcs(struct amdgpu_device *adev);
 
+int amdgpu_vpe_psp_update_sram(struct amdgpu_device *adev)
+{
+       struct amdgpu_firmware_info ucode = {
+               .ucode_id = AMDGPU_UCODE_ID_VPE,
+               .mc_addr = adev->vpe.cmdbuf_gpu_addr,
+               .ucode_size = 8,
+       };
+
+       return psp_execute_ip_fw_load(&adev->psp, &ucode);
+}
+
 int amdgpu_vpe_init_microcode(struct amdgpu_vpe *vpe)
 {
        struct amdgpu_device *adev = vpe->ring.adev;
@@ -126,12 +137,35 @@ static int vpe_early_init(void *handle)
        return 0;
 }
 
+
+static int vpe_common_init(struct amdgpu_vpe *vpe)
+{
+       struct amdgpu_device *adev = container_of(vpe, struct amdgpu_device, 
vpe);
+       int r;
+
+       r = amdgpu_bo_create_kernel(adev, PAGE_SIZE, PAGE_SIZE,
+                                   AMDGPU_GEM_DOMAIN_GTT,
+                                   &adev->vpe.cmdbuf_obj,
+                                   &adev->vpe.cmdbuf_gpu_addr,
+                                   (void **)&adev->vpe.cmdbuf_cpu_addr);
+       if (r) {
+               dev_err(adev->dev, "VPE: failed to allocate cmdbuf bo %d\n", r);
+               return r;
+       }
+
+       return 0;
+}
+
 static int vpe_sw_init(void *handle)
 {
        struct amdgpu_device *adev = (struct amdgpu_device *)handle;
        struct amdgpu_vpe *vpe = &adev->vpe;
        int ret;
 
+       ret = vpe_common_init(vpe);
+       if (ret)
+               goto out;
+
        ret = vpe_irq_init(vpe);
        if (ret)
                goto out;
@@ -157,6 +191,10 @@ static int vpe_sw_fini(void *handle)
 
        vpe_ring_fini(vpe);
 
+       amdgpu_bo_free_kernel(&adev->vpe.cmdbuf_obj,
+                             &adev->vpe.cmdbuf_gpu_addr,
+                             (void **)&adev->vpe.cmdbuf_cpu_addr);
+
        return 0;
 }
 
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.h
index 010fa7f308fd..b590205d6a28 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vpe.h
@@ -59,8 +59,13 @@ struct amdgpu_vpe {
        const struct firmware           *fw;
        uint32_t                        fw_version;
        uint32_t                        feature_version;
+
+       struct amdgpu_bo                *cmdbuf_obj;
+       uint64_t                        cmdbuf_gpu_addr;
+       uint32_t                        *cmdbuf_cpu_addr;
 };
 
+int amdgpu_vpe_psp_update_sram(struct amdgpu_device *adev);
 int amdgpu_vpe_init_microcode(struct amdgpu_vpe *vpe);
 int amdgpu_vpe_ring_init(struct amdgpu_vpe *vpe);
 int amdgpu_vpe_ring_fini(struct amdgpu_vpe *vpe);
diff --git a/drivers/gpu/drm/amd/amdgpu/psp_gfx_if.h 
b/drivers/gpu/drm/amd/amdgpu/psp_gfx_if.h
index fd11115429c8..dfd60db97012 100644
--- a/drivers/gpu/drm/amd/amdgpu/psp_gfx_if.h
+++ b/drivers/gpu/drm/amd/amdgpu/psp_gfx_if.h
@@ -295,6 +295,7 @@ enum psp_gfx_fw_type {
        GFX_FW_TYPE_RS64_MEC_P3_STACK               = 97,   /* RS64 MEC stack 
P3        SOC21   */
        GFX_FW_TYPE_VPEC_FW1                        = 100,  /* VPEC FW1 To Save 
        VPE     */
        GFX_FW_TYPE_VPEC_FW2                        = 101,  /* VPEC FW2 To Save 
        VPE     */
+       GFX_FW_TYPE_VPE                             = 102,
        GFX_FW_TYPE_MAX
 };
 
diff --git a/drivers/gpu/drm/amd/amdgpu/vpe_v6_1.c 
b/drivers/gpu/drm/amd/amdgpu/vpe_v6_1.c
index 1a483d38e70d..1259b150dc96 100644
--- a/drivers/gpu/drm/amd/amdgpu/vpe_v6_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/vpe_v6_1.c
@@ -84,6 +84,21 @@ static int vpe_v6_1_load_microcode(struct amdgpu_vpe *vpe)
        ret = REG_SET_FIELD(ret, VPEC_CNTL, UMSCH_INT_ENABLE, 0);
        WREG32(vpe_get_reg_offset(vpe, 0, regVPEC_CNTL), ret);
 
+       if (adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) {
+               uint32_t f32_offset, f32_cntl;
+
+               f32_offset = vpe_get_reg_offset(vpe, 0, regVPEC_F32_CNTL);
+               f32_cntl = RREG32(f32_offset);
+               f32_cntl = REG_SET_FIELD(f32_cntl, VPEC_F32_CNTL, HALT, 0);
+               f32_cntl = REG_SET_FIELD(f32_cntl, VPEC_F32_CNTL, TH1_RESET, 0);
+
+               adev->vpe.cmdbuf_cpu_addr[0] = f32_offset;
+               adev->vpe.cmdbuf_cpu_addr[1] = f32_cntl;
+
+               amdgpu_vpe_psp_update_sram(adev);
+               return 0;
+       }
+
        vpe_hdr = (const struct vpe_firmware_header_v1_0 *)adev->vpe.fw->data;
 
        /* Thread 0(command thread) ucode offset/size */
-- 
2.41.0

Reply via email to