summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHarry Wentland <harry.wentland@amd.com>2017-03-30 11:55:56 -0400
committerHarry Wentland <harry.wentland@amd.com>2017-04-19 20:57:52 -0400
commit64f569b5df205b1bb77bbca8b2b7e313e420915c (patch)
treea0a5b7b1ae92b789a24fbcbe0e4d78748014b72b
parent258e6a91fc6139f1de864606bbbc3bdf1d4bb5d9 (diff)
drm/amd/display: Use validate_context from atomic_check in commitdc-drm-next-atomic-wip
With this we're now using the exact state that was validated in atomic_check in atomic_commit. Change-Id: Ia46a4f80e162934b71ce2aa59845b1bfac55c924 Signed-off-by: Harry Wentland <harry.wentland@amd.com>
-rw-r--r--drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_types.c46
-rw-r--r--drivers/gpu/drm/amd/display/dc/core/dc.c83
-rw-r--r--drivers/gpu/drm/amd/display/dc/core/dc_stream.c6
-rw-r--r--drivers/gpu/drm/amd/display/dc/dc.h5
-rw-r--r--drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c6
5 files changed, 76 insertions, 70 deletions
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_types.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_types.c
index aa4ee6b83438..d88e88c875a3 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_types.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_types.c
@@ -2674,6 +2674,7 @@ void amdgpu_dm_atomic_commit_tail(
new_stream = dm_state->set[j].stream;
break;
}
+
/*
* this loop saves set mode crtcs
* we needed to enable vblanks once all
@@ -2691,16 +2692,30 @@ void amdgpu_dm_atomic_commit_tail(
}
case DM_COMMIT_ACTION_NOTHING: {
- struct dm_connector_state *dm_state = NULL;
+ struct dm_connector_state *dm_conn_state = NULL;
if (!aconnector)
break;
- dm_state = to_dm_connector_state(aconnector->base.state);
+ dm_conn_state = to_dm_connector_state(aconnector->base.state);
+
+ /* TODO clean this stupid hack
+ * probably needs some cleanup in atomic_check first */
+ for (j = 0; j < dm_state->set_count; j++)
+ if (dm_state->set[j].stream->priv == acrtc) {
+ if (acrtc->stream)
+ mod_freesync_remove_stream(adev->dm.freesync_module,
+ acrtc->stream);
+ acrtc->stream = dm_state->set[j].stream;
+ mod_freesync_add_stream(adev->dm.freesync_module,
+ acrtc->stream,
+ &aconnector->caps);
+ break;
+ }
/* Scaling update */
update_stream_scaling_settings(&crtc->state->mode,
- dm_state, acrtc->stream);
+ dm_conn_state, acrtc->stream);
break;
}
@@ -2708,8 +2723,9 @@ void amdgpu_dm_atomic_commit_tail(
case DM_COMMIT_ACTION_RESET:
DRM_INFO("Atomic commit: RESET. crtc id %d:[%p]\n", acrtc->crtc_id, acrtc);
/* i.e. reset mode */
- if (acrtc->stream)
+ if (acrtc->stream) {
remove_stream(adev, acrtc);
+ }
break;
} /* switch() */
} /* for_each_crtc_in_state() */
@@ -2742,19 +2758,23 @@ void amdgpu_dm_atomic_commit_tail(
}
/* DC is optimized not to do anything if 'streams' didn't change. */
- WARN_ON(!dc_commit_validation_set(dm->dc, dm_state->set,
- dm_state->set_count));
+ WARN_ON(!dc_commit_context(dm->dc, dm_state->context));
+
+ /* update planes when needed */
+ dc_commit_surfaces(state, dev, dm);
list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc);
- if (acrtc->stream != NULL)
- acrtc->otg_inst =
- dc_stream_get_status(acrtc->stream)->primary_otg_inst;
- }
+ if (acrtc->stream != NULL) {
+ const struct dc_stream_status *status = dc_stream_get_status(acrtc->stream);
- /* update planes when needed */
- dc_commit_surfaces(state, dev, dm);
+ if (!status)
+ DC_ERR("got no status for stream %p on acrtc%p\n", acrtc->stream, acrtc);
+ else
+ acrtc->otg_inst = status->primary_otg_inst;
+ }
+ }
for (i = 0; i < new_crtcs_count; i++) {
/*
@@ -2970,6 +2990,7 @@ static uint32_t update_in_val_sets_stream(
} else {
/* update. relase old stream */
dc_stream_release(old_stream);
+
}
return set_count;
@@ -3137,6 +3158,7 @@ int amdgpu_dm_atomic_check(struct drm_device *dev,
__func__, acrtc->base.base.id);
break;
}
+ new_stream->priv = acrtc;
new_streams[new_stream_count] = new_stream;
dm_state->set_count = update_in_val_sets_stream(
diff --git a/drivers/gpu/drm/amd/display/dc/core/dc.c b/drivers/gpu/drm/amd/display/dc/core/dc.c
index e5ec359b3830..2c86a6309074 100644
--- a/drivers/gpu/drm/amd/display/dc/core/dc.c
+++ b/drivers/gpu/drm/amd/display/dc/core/dc.c
@@ -792,18 +792,17 @@ static void program_timing_sync(
}
}
-static bool set_changed(
+static bool context_changed(
struct core_dc *dc,
- const struct dc_validation_set set[],
- uint8_t set_count)
+ struct validate_context *context)
{
uint8_t i;
- if (set_count != dc->current_context->stream_count)
+ if (context->stream_count != dc->current_context->stream_count)
return true;
for (i = 0; i < dc->current_context->stream_count; i++) {
- if (&dc->current_context->streams[i]->public != set[i].stream)
+ if (&dc->current_context->streams[i]->public != &context->streams[i]->public)
return true;
}
@@ -829,46 +828,36 @@ static bool streams_changed(
}
/* TODO operate on validation set (or something like it) */
-bool dc_commit_validation_set(
- const struct dc *dc,
- const struct dc_validation_set set[],
- uint8_t set_count)
+bool dc_commit_context(struct dc *dc, struct validate_context *context)
{
struct core_dc *core_dc = DC_TO_CORE(dc);
struct dc_bios *dcb = core_dc->ctx->dc_bios;
enum dc_status result = DC_ERROR_UNEXPECTED;
- struct validate_context *context;
int i, j, k;
- /* TODO check validation set changed */
- if (false == set_changed(core_dc, set, set_count))
+ if (!context)
+ dm_logger_write(core_dc->ctx->logger, LOG_ERROR,
+ "%s: dc_commit_context with no context!\n",
+ __func__);
+
+ if (false == context_changed(core_dc, context))
return DC_OK;
dm_logger_write(core_dc->ctx->logger, LOG_DC, "%s: %d streams\n",
- __func__, set_count);
+ __func__, context->stream_count);
- context = dm_alloc(sizeof(struct validate_context));
- if (context == NULL)
- goto context_alloc_fail;
+ for (i = 0; i < context->stream_count; i++) {
+ const struct dc_stream *stream = &context->streams[i]->public;
- /* TODO no need for validation. just rebuild context */
- /* TODO check context is created deterministically */
- result = core_dc->res_pool->funcs->validate_with_context(core_dc, set, set_count, context);
- if (result != DC_OK) {
- dm_logger_write(core_dc->ctx->logger, LOG_ERROR,
- "%s: Context validation failed! dc_status:%d\n",
- __func__,
- result);
- BREAK_TO_DEBUGGER();
- dc_resource_validate_ctx_destruct(context);
- goto fail;
+ dc_stream_log(stream,
+ core_dc->ctx->logger,
+ LOG_DC);
}
if (!dcb->funcs->is_accelerated_mode(dcb))
core_dc->hwss.enable_accelerated_mode(core_dc);
- if (result == DC_OK)
- result = core_dc->hwss.apply_ctx_to_hw(core_dc, context);
+ result = core_dc->hwss.apply_ctx_to_hw(core_dc, context);
program_timing_sync(core_dc, context);
@@ -898,17 +887,8 @@ bool dc_commit_validation_set(
context->streams[i]->public.timing.pix_clk_khz);
}
- dc_resource_validate_ctx_destruct(core_dc->current_context);
- dm_free(core_dc->current_context);
-
- core_dc->current_context = context;
-
- return (result == DC_OK);
-
-fail:
- dm_free(context);
+ dc_resource_validate_ctx_copy_construct(context, core_dc->current_context);
-context_alloc_fail:
return (result == DC_OK);
}
@@ -1028,24 +1008,27 @@ bool dc_post_update_surfaces_to_stream(struct dc *dc)
dc_resource_validate_ctx_copy_construct(core_dc->current_context, context);
post_surface_trace(dc);
+
for (i = 0; i < context->res_ctx.pool->pipe_count; i++)
if (context->res_ctx.pipe_ctx[i].stream == NULL) {
context->res_ctx.pipe_ctx[i].pipe_idx = i;
core_dc->hwss.power_down_front_end(
core_dc, &context->res_ctx.pipe_ctx[i]);
}
-
if (!core_dc->res_pool->funcs->validate_bandwidth(core_dc, context)) {
BREAK_TO_DEBUGGER();
+ dc_resource_validate_ctx_destruct(context);
+ dm_free(context);
return false;
}
core_dc->hwss.set_bandwidth(core_dc, context, true);
- dc_resource_validate_ctx_copy_construct(context, core_dc->current_context);
-
- dc_resource_validate_ctx_destruct(context);
- dm_free(context);
+ if (core_dc->current_context) {
+ dc_resource_validate_ctx_destruct(core_dc->current_context);
+ dm_free(core_dc->current_context);
+ }
+ core_dc->current_context = context;
return true;
}
@@ -1494,8 +1477,10 @@ void dc_update_surfaces_and_stream(struct dc *dc,
if (cur_pipe_ctx->surface == pipe_ctx->surface)
is_new_pipe_surface = false;
- if (is_new_pipe_surface ||
- srf_updates[i].in_transfer_func)
+ /* TODO find out why check is false */
+ /* TODO with this still not programming some color stuff... panel is dark-ish */
+ /*if (is_new_pipe_surface ||
+ srf_updates[i].in_transfer_func)*/
core_dc->hwss.set_input_transfer_func(
pipe_ctx, pipe_ctx->surface);
@@ -1539,10 +1524,8 @@ void dc_update_surfaces_and_stream(struct dc *dc,
return;
fail:
- if (core_dc->current_context != context) {
- dc_resource_validate_ctx_destruct(context);
- dm_free(context);
- }
+ dc_resource_validate_ctx_destruct(context);
+ dm_free(context);
}
uint8_t dc_get_current_stream_count(const struct dc *dc)
diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_stream.c b/drivers/gpu/drm/amd/display/dc/core/dc_stream.c
index 3dbd6c0885d8..454107b27db0 100644
--- a/drivers/gpu/drm/amd/display/dc/core/dc_stream.c
+++ b/drivers/gpu/drm/amd/display/dc/core/dc_stream.c
@@ -164,9 +164,11 @@ const struct dc_stream_status *dc_stream_get_status(
struct core_stream *stream = DC_STREAM_TO_CORE(dc_stream);
struct core_dc *dc = DC_TO_CORE(stream->ctx->dc);
- for (i = 0; i < dc->current_context->stream_count; i++)
- if (stream == dc->current_context->streams[i])
+ for (i = 0; i < dc->current_context->stream_count; i++) {
+ if (stream == dc->current_context->streams[i]) {
return &dc->current_context->stream_status[i];
+ }
+ }
return NULL;
}
diff --git a/drivers/gpu/drm/amd/display/dc/dc.h b/drivers/gpu/drm/amd/display/dc/dc.h
index cc725c54f9f1..0863e44be550 100644
--- a/drivers/gpu/drm/amd/display/dc/dc.h
+++ b/drivers/gpu/drm/amd/display/dc/dc.h
@@ -544,10 +544,7 @@ void dc_resource_validate_ctx_destruct(struct validate_context *context);
* Phy, Encoder, Timing Generator are programmed and enabled.
* New streams are enabled with blank stream; no memory read.
*/
-bool dc_commit_validation_set(
- const struct dc *dc,
- const struct dc_validation_set set[],
- uint8_t set_count);
+bool dc_commit_context(struct dc *dc, struct validate_context *context);
/*
* Set up streams and links associated to drive sinks
diff --git a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c
index 2fbf6ddcf3be..1329106261a3 100644
--- a/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c
+++ b/drivers/gpu/drm/amd/display/dc/dce110/dce110_hw_sequencer.c
@@ -2347,9 +2347,11 @@ static void dce110_program_front_end_for_pipe(
pipe_ctx->xfm->funcs->transform_set_gamut_remap(pipe_ctx->xfm, &adjust);
pipe_ctx->scl_data.lb_params.alpha_en = pipe_ctx->bottom_pipe != 0;
- if (old_pipe && memcmp(&old_pipe->scl_data,
+
+ /* TODO check why this skips scaler calll now */
+ /*if (old_pipe && memcmp(&old_pipe->scl_data,
&pipe_ctx->scl_data,
- sizeof(struct scaler_data)) != 0)
+ sizeof(struct scaler_data)) != 0)*/
program_scaler(dc, pipe_ctx);
mi->funcs->mem_input_program_surface_config(