[PATCH 5/8] drm/amdgpu: Add support for resuming SDMA queues w/o HWS

Oded Gabbay oded.gabbay at gmail.com
Thu Nov 2 14:57:08 UTC 2017


On Thu, Nov 2, 2017 at 1:21 AM, Felix Kuehling <Felix.Kuehling at amd.com> wrote:
> Save wptr in hqd_sdma_destroy, restore it in hqd_sdma_load. Also
> read updated wptr from user mode when resuming an SDMA queue.
>
> Signed-off-by: Jay Cornwall <Jay.Cornwall at amd.com>
> Signed-off-by: Yong Zhao <yong.zhao at amd.com>
> Signed-off-by: Felix Kuehling <Felix.Kuehling at amd.com>
> ---
>  drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v7.c | 30 +++++++++++++++--------
>  drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v8.c |  9 ++++---
>  2 files changed, 25 insertions(+), 14 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v7.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v7.c
> index a55d794..14333af 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v7.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v7.c
> @@ -412,10 +412,17 @@ static int kgd_hqd_sdma_load(struct kgd_dev *kgd, void *mqd,
>                 WREG32(mmSDMA0_GFX_CONTEXT_CNTL, data);
>         }
>
> -       WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL,
> -                               m->sdma_rlc_doorbell);
> -       WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR, 0);
> -       WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_WPTR, 0);
> +       data = REG_SET_FIELD(m->sdma_rlc_doorbell, SDMA0_RLC0_DOORBELL,
> +                            ENABLE, 1);
> +       WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL, data);
> +       WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR, m->sdma_rlc_rb_rptr);
> +
> +       if (read_user_wptr(mm, wptr, data))
> +               WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_WPTR, data);
> +       else
> +               WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_WPTR,
> +                      m->sdma_rlc_rb_rptr);
> +
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_VIRTUAL_ADDR,
>                                 m->sdma_rlc_virtual_addr);
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_BASE, m->sdma_rlc_rb_base);
> @@ -425,8 +432,10 @@ static int kgd_hqd_sdma_load(struct kgd_dev *kgd, void *mqd,
>                         m->sdma_rlc_rb_rptr_addr_lo);
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR_ADDR_HI,
>                         m->sdma_rlc_rb_rptr_addr_hi);
> -       WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL,
> -                       m->sdma_rlc_rb_cntl);
> +
> +       data = REG_SET_FIELD(m->sdma_rlc_rb_cntl, SDMA0_RLC0_RB_CNTL,
> +                            RB_ENABLE, 1);
> +       WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL, data);
>
>         return 0;
>  }
> @@ -577,7 +586,7 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
>         struct cik_sdma_rlc_registers *m;
>         uint32_t sdma_base_addr;
>         uint32_t temp;
> -       int timeout = utimeout;
> +       unsigned long end_jiffies = (utimeout * HZ / 1000) + jiffies;
>
>         m = get_sdma_mqd(mqd);
>         sdma_base_addr = get_sdma_base_addr(m);
> @@ -590,10 +599,9 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
>                 temp = RREG32(sdma_base_addr + mmSDMA0_RLC0_CONTEXT_STATUS);
>                 if (temp & SDMA0_STATUS_REG__RB_CMD_IDLE__SHIFT)
>                         break;
> -               if (timeout <= 0)
> +               if (time_after(jiffies, end_jiffies))
>                         return -ETIME;
> -               msleep(20);
> -               timeout -= 20;
> +               usleep_range(500, 1000);
>         }
>
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL, 0);
> @@ -601,6 +609,8 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
>                 RREG32(sdma_base_addr + mmSDMA0_RLC0_RB_CNTL) |
>                 SDMA0_RLC0_RB_CNTL__RB_ENABLE_MASK);
>
> +       m->sdma_rlc_rb_rptr = RREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR);
> +
>         return 0;
>  }
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v8.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v8.c
> index 1017ff5..03c564d 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v8.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gfx_v8.c
> @@ -514,7 +514,7 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
>         struct cik_sdma_rlc_registers *m;
>         uint32_t sdma_base_addr;
>         uint32_t temp;
> -       int timeout = utimeout;
> +       unsigned long end_jiffies = (utimeout * HZ / 1000) + jiffies;
>
>         m = get_sdma_mqd(mqd);
>         sdma_base_addr = get_sdma_base_addr(m);
> @@ -527,10 +527,9 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
>                 temp = RREG32(sdma_base_addr + mmSDMA0_RLC0_CONTEXT_STATUS);
>                 if (temp & SDMA0_STATUS_REG__RB_CMD_IDLE__SHIFT)
>                         break;
> -               if (timeout <= 0)
> +               if (time_after(jiffies, end_jiffies))
>                         return -ETIME;
> -               msleep(20);
> -               timeout -= 20;
> +               usleep_range(500, 1000);
>         }
>
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_DOORBELL, 0);
> @@ -538,6 +537,8 @@ static int kgd_hqd_sdma_destroy(struct kgd_dev *kgd, void *mqd,
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_WPTR, 0);
>         WREG32(sdma_base_addr + mmSDMA0_RLC0_RB_BASE, 0);
>
> +       m->sdmax_rlcx_rb_rptr = RREG32(sdma_base_addr + mmSDMA0_RLC0_RB_RPTR);
> +
>         return 0;
>  }
>
> --
> 2.7.4
>

This patch is:
Acked-by: Oded Gabbay <oded.gabbay at gmail.com>


More information about the amd-gfx mailing list