Commit 51235849 authored by Christian König's avatar Christian König Committed by Alex Deucher
Browse files

drm/amdgpu: fix sdma v4 startup under SRIOV



Under SRIOV we were enabling the ring buffer before it was initialized.

Signed-off-by: default avatarChristian König <christian.koenig@amd.com>
Reviewed-by: default avatarHuang Rui <ray.huang@amd.com>
Signed-off-by: default avatarAlex Deucher <alexander.deucher@amd.com>
parent 105f2070
Loading
Loading
Loading
Loading
+116 −118
Original line number Diff line number Diff line
@@ -675,13 +675,14 @@ static void sdma_v4_0_enable(struct amdgpu_device *adev, bool enable)
 * sdma_v4_0_gfx_resume - setup and start the async dma engines
 *
 * @adev: amdgpu_device pointer
 * @i: instance to resume
 *
 * Set up the gfx DMA ring buffers and enable them (VEGA10).
 * Returns 0 for success, error for failure.
 */
static int sdma_v4_0_gfx_resume(struct amdgpu_device *adev)
static void sdma_v4_0_gfx_resume(struct amdgpu_device *adev, unsigned int i)
{
	struct amdgpu_ring *ring;
	struct amdgpu_ring *ring = &adev->sdma.instance[i].ring;
	u32 rb_cntl, ib_cntl, wptr_poll_cntl;
	u32 rb_bufsz;
	u32 wb_offset;
@@ -689,10 +690,7 @@ static int sdma_v4_0_gfx_resume(struct amdgpu_device *adev)
	u32 doorbell_offset;
	u32 temp;
	u64 wptr_gpu_addr;
	int i, r;

	for (i = 0; i < adev->sdma.num_instances; i++) {
		ring = &adev->sdma.instance[i].ring;
	wb_offset = (ring->rptr_offs * 4);

	WREG32(sdma_v4_0_get_reg_offset(adev, i, mmSDMA0_SEM_WAIT_FAIL_TIMER_CNTL), 0);
@@ -794,24 +792,6 @@ static int sdma_v4_0_gfx_resume(struct amdgpu_device *adev)
	WREG32(sdma_v4_0_get_reg_offset(adev, i, mmSDMA0_GFX_IB_CNTL), ib_cntl);

	ring->ready = true;

		if (amdgpu_sriov_vf(adev)) { /* bare-metal sequence doesn't need below to lines */
			sdma_v4_0_ctx_switch_enable(adev, true);
			sdma_v4_0_enable(adev, true);
		}

		r = amdgpu_ring_test_ring(ring);
		if (r) {
			ring->ready = false;
			return r;
		}

		if (adev->mman.buffer_funcs_ring == ring)
			amdgpu_ttm_set_buffer_funcs_status(adev, true);

	}

	return 0;
}

static void
@@ -943,16 +923,13 @@ static int sdma_v4_0_load_microcode(struct amdgpu_device *adev)
 */
static int sdma_v4_0_start(struct amdgpu_device *adev)
{
	int r = 0;
	struct amdgpu_ring *ring;
	int i, r;

	if (amdgpu_sriov_vf(adev)) {
		sdma_v4_0_ctx_switch_enable(adev, false);
		sdma_v4_0_enable(adev, false);

		/* set RB registers */
		r = sdma_v4_0_gfx_resume(adev);
		return r;
	}
	} else {

		if (adev->firmware.load_type != AMDGPU_FW_LOAD_PSP) {
			r = sdma_v4_0_load_microcode(adev);
@@ -964,12 +941,33 @@ static int sdma_v4_0_start(struct amdgpu_device *adev)
		sdma_v4_0_enable(adev, true);
		/* enable sdma ring preemption */
		sdma_v4_0_ctx_switch_enable(adev, true);
	}

	/* start the gfx rings and rlc compute queues */
	r = sdma_v4_0_gfx_resume(adev);
	for (i = 0; i < adev->sdma.num_instances; i++)
		sdma_v4_0_gfx_resume(adev, i);

	if (amdgpu_sriov_vf(adev)) {
		sdma_v4_0_ctx_switch_enable(adev, true);
		sdma_v4_0_enable(adev, true);
	} else {
		r = sdma_v4_0_rlc_resume(adev);
		if (r)
			return r;
	r = sdma_v4_0_rlc_resume(adev);
	}

	for (i = 0; i < adev->sdma.num_instances; i++) {
		ring = &adev->sdma.instance[i].ring;

		r = amdgpu_ring_test_ring(ring);
		if (r) {
			ring->ready = false;
			return r;
		}

		if (adev->mman.buffer_funcs_ring == ring)
			amdgpu_ttm_set_buffer_funcs_status(adev, true);
	}

	return r;
}