Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit e7778be1 authored by Thomas Daniel's avatar Thomas Daniel Committed by Daniel Vetter
Browse files

drm/i915: Fix startup failure in LRC mode after recent init changes



A previous commit introduced engine init changes:

    commit 372ee59699d9 ("drm/i915: Only init engines once")

This broke execlists as intel_lr_context_render_state_init was trying to emit
commands to the RCS for the default context before the ring->init_hw was called.

Made a new gen8_init_rcs_context function and assign in to render ring
init_context.  Moved call to intel_logical_ring_workarounds_emit into
gen8_init_rcs_context to maintain previous functionality.

Moved call to render_state_init from lr_context_deferred_create into
gen8_init_rcs_context, and modified deferred_create to call ring->init_context
for non-default contexts.

Modified i915_gem_context_enable to call ring->init_context for the default
context.

So init_context will now always be called when the hw is ready - in
i915_gem_context_enable for the default context and in lr_context_deferred_create
for other contexts.

Signed-off-by: default avatarThomas Daniel <thomas.daniel@intel.com>
Signed-off-by: default avatarDaniel Vetter <daniel.vetter@ffwll.ch>
parent d972d6ee
Loading
Loading
Loading
Loading
+18 −7
Original line number Diff line number Diff line
@@ -408,9 +408,20 @@ int i915_gem_context_enable(struct drm_i915_private *dev_priv)

	BUG_ON(!dev_priv->ring[RCS].default_context);

	if (i915.enable_execlists)
		return 0;
	if (i915.enable_execlists) {
		for_each_ring(ring, dev_priv, i) {
			if (ring->init_context) {
				ret = ring->init_context(ring,
						ring->default_context);
				if (ret) {
					DRM_ERROR("ring init context: %d\n",
							ret);
					return ret;
				}
			}
		}

	} else
		for_each_ring(ring, dev_priv, i) {
			ret = i915_switch_context(ring, ring->default_context);
			if (ret)
+19 −11
Original line number Diff line number Diff line
@@ -1336,6 +1336,18 @@ static int gen8_emit_request(struct intel_ringbuffer *ringbuf)
	return 0;
}

static int gen8_init_rcs_context(struct intel_engine_cs *ring,
		       struct intel_context *ctx)
{
	int ret;

	ret = intel_logical_ring_workarounds_emit(ring, ctx);
	if (ret)
		return ret;

	return intel_lr_context_render_state_init(ring, ctx);
}

/**
 * intel_logical_ring_cleanup() - deallocate the Engine Command Streamer
 *
@@ -1409,7 +1421,7 @@ static int logical_render_ring_init(struct drm_device *dev)
		ring->irq_keep_mask |= GT_RENDER_L3_PARITY_ERROR_INTERRUPT;

	ring->init_hw = gen8_init_render_ring;
	ring->init_context = intel_logical_ring_workarounds_emit;
	ring->init_context = gen8_init_rcs_context;
	ring->cleanup = intel_fini_pipe_control;
	ring->get_seqno = gen8_get_seqno;
	ring->set_seqno = gen8_set_seqno;
@@ -1904,21 +1916,17 @@ int intel_lr_context_deferred_create(struct intel_context *ctx,

	if (ctx == ring->default_context)
		lrc_setup_hardware_status_page(ring, ctx_obj);

	if (ring->id == RCS && !ctx->rcs_initialized) {
	else if (ring->id == RCS && !ctx->rcs_initialized) {
		if (ring->init_context) {
			ret = ring->init_context(ring, ctx);
			if (ret)
				DRM_ERROR("ring init context: %d\n", ret);
		}

		ret = intel_lr_context_render_state_init(ring, ctx);
			if (ret) {
			DRM_ERROR("Init render state failed: %d\n", ret);
				DRM_ERROR("ring init context: %d\n", ret);
				ctx->engine[ring->id].ringbuf = NULL;
				ctx->engine[ring->id].state = NULL;
				goto error;
			}
		}

		ctx->rcs_initialized = true;
	}