drm/amd/display: make dc_commit_surfaces_to_stream() re-entrant
dc_commit_surfaces_to_stream() function currently is handle's only one plane at a time. This will not work if multiple planes have to be set to a crtc. The functionality of dc_commit_surfaces_to_stream() with this patch is slit into 1. Accumulate and initialise all the surfaces that needs to be set to a crtc. 2. Update the intialised set of surfaces to the steam in one go. Hence dc_commit_surfaces_to_stream() is renamed to init_surfaces(). Once all the planes requested by user space are initialised, dc_commit_surfaces_to_stream() shall sequentially populates *updates, *flip_addr, *plane_info and *scaling_info for all surfaces. BUG: SWDEV-119421 TEST: (On Chromium OS for Stoney Only) * Chromium UI comes up, on both eDP & DP. * 'new_surface_count' now changes as per user input for e.g for all below run tests its 2, without this patch for the below tests it used to be 1 * Executed below tests to see YUV(underlay) & RGB planes on eDP plane_test --format XR24 --size 500x100 -p --format YV12 --size 500x500 plane_test --format AR24 --size 500x50 -p --format YV12 --size 150x150 plane_test --format AR24 --size 500x50 -p --format YV12 --size 1366x768 Signed-off-by: Harry Wentland <Harry.Wentland@amd.com> Signed-off-by: Shirish S <shirish.s@amd.com> Signed-off-by: Alex Deucher <alexander.deucher@amd.com>
This commit is contained in:
parent
110ff5439a
commit
0430d52b76
|
@ -730,19 +730,20 @@ static void update_stream_scaling_settings(
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dm_dc_surface_commit(
|
static void add_surface(struct dc *dc,
|
||||||
struct dc *dc,
|
struct drm_crtc *crtc,
|
||||||
struct drm_crtc *crtc)
|
struct drm_plane *plane,
|
||||||
|
const struct dc_surface **dc_surfaces)
|
||||||
{
|
{
|
||||||
struct dc_surface *dc_surface;
|
struct dc_surface *dc_surface;
|
||||||
const struct dc_surface *dc_surfaces[1];
|
|
||||||
struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc);
|
struct amdgpu_crtc *acrtc = to_amdgpu_crtc(crtc);
|
||||||
const struct dc_stream *dc_stream = acrtc->stream;
|
const struct dc_stream *dc_stream = acrtc->stream;
|
||||||
unsigned long flags;
|
unsigned long flags;
|
||||||
|
|
||||||
spin_lock_irqsave(&crtc->dev->event_lock, flags);
|
spin_lock_irqsave(&crtc->dev->event_lock, flags);
|
||||||
if (acrtc->pflip_status != AMDGPU_FLIP_NONE) {
|
if (acrtc->pflip_status != AMDGPU_FLIP_NONE) {
|
||||||
DRM_ERROR("dm_dc_surface_commit: acrtc %d, already busy\n", acrtc->crtc_id);
|
DRM_ERROR("add_surface: acrtc %d, already busy\n",
|
||||||
|
acrtc->crtc_id);
|
||||||
spin_unlock_irqrestore(&crtc->dev->event_lock, flags);
|
spin_unlock_irqrestore(&crtc->dev->event_lock, flags);
|
||||||
/* In comit tail framework this cannot happen */
|
/* In comit tail framework this cannot happen */
|
||||||
BUG_ON(0);
|
BUG_ON(0);
|
||||||
|
@ -770,22 +771,11 @@ static void dm_dc_surface_commit(
|
||||||
fill_plane_attributes(
|
fill_plane_attributes(
|
||||||
crtc->dev->dev_private,
|
crtc->dev->dev_private,
|
||||||
dc_surface,
|
dc_surface,
|
||||||
crtc->primary->state,
|
plane->state,
|
||||||
true);
|
true);
|
||||||
|
|
||||||
dc_surfaces[0] = dc_surface;
|
*dc_surfaces = dc_surface;
|
||||||
|
|
||||||
if (false == dc_commit_surfaces_to_stream(
|
|
||||||
dc,
|
|
||||||
dc_surfaces,
|
|
||||||
1,
|
|
||||||
dc_stream)) {
|
|
||||||
dm_error(
|
|
||||||
"%s: Failed to attach surface!\n",
|
|
||||||
__func__);
|
|
||||||
}
|
|
||||||
|
|
||||||
dc_surface_release(dc_surface);
|
|
||||||
fail:
|
fail:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -2385,11 +2375,16 @@ static void amdgpu_dm_do_flip(
|
||||||
}
|
}
|
||||||
|
|
||||||
void dc_commit_surfaces(struct drm_atomic_state *state,
|
void dc_commit_surfaces(struct drm_atomic_state *state,
|
||||||
struct drm_device *dev, struct amdgpu_display_manager *dm)
|
struct drm_device *dev,
|
||||||
|
struct amdgpu_display_manager *dm,
|
||||||
|
struct drm_crtc *pcrtc)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
uint32_t i;
|
||||||
struct drm_plane *plane;
|
struct drm_plane *plane;
|
||||||
struct drm_plane_state *old_plane_state;
|
struct drm_plane_state *old_plane_state;
|
||||||
|
const struct dc_stream *dc_stream_attach;
|
||||||
|
const struct dc_surface *dc_surfaces_constructed[MAX_SURFACES];
|
||||||
|
int planes_count = 0;
|
||||||
|
|
||||||
/* update planes when needed */
|
/* update planes when needed */
|
||||||
for_each_plane_in_state(state, plane, old_plane_state, i) {
|
for_each_plane_in_state(state, plane, old_plane_state, i) {
|
||||||
|
@ -2398,6 +2393,7 @@ void dc_commit_surfaces(struct drm_atomic_state *state,
|
||||||
struct drm_framebuffer *fb = plane_state->fb;
|
struct drm_framebuffer *fb = plane_state->fb;
|
||||||
struct drm_connector *connector;
|
struct drm_connector *connector;
|
||||||
struct dm_connector_state *dm_state = NULL;
|
struct dm_connector_state *dm_state = NULL;
|
||||||
|
struct amdgpu_crtc *acrtc_attach;
|
||||||
enum dm_commit_action action;
|
enum dm_commit_action action;
|
||||||
bool pflip_needed;
|
bool pflip_needed;
|
||||||
|
|
||||||
|
@ -2439,10 +2435,27 @@ void dc_commit_surfaces(struct drm_atomic_state *state,
|
||||||
*/
|
*/
|
||||||
if (!dm_state)
|
if (!dm_state)
|
||||||
continue;
|
continue;
|
||||||
|
if (crtc == pcrtc) {
|
||||||
dm_dc_surface_commit(dm->dc, crtc);
|
add_surface(dm->dc, crtc, plane,
|
||||||
|
&dc_surfaces_constructed[planes_count]);
|
||||||
|
acrtc_attach = to_amdgpu_crtc(crtc);
|
||||||
|
dc_stream_attach = acrtc_attach->stream;
|
||||||
|
planes_count++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (planes_count) {
|
||||||
|
if (false == dc_commit_surfaces_to_stream(dm->dc,
|
||||||
|
dc_surfaces_constructed,
|
||||||
|
planes_count,
|
||||||
|
dc_stream_attach)) {
|
||||||
|
dm_error("%s: Failed to attach surface!\n", __func__);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
for (i = 0; i < planes_count; i++)
|
||||||
|
dc_surface_release(dc_surfaces_constructed[i]);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void amdgpu_dm_atomic_commit_tail(
|
void amdgpu_dm_atomic_commit_tail(
|
||||||
|
@ -2453,10 +2466,10 @@ void amdgpu_dm_atomic_commit_tail(
|
||||||
struct amdgpu_display_manager *dm = &adev->dm;
|
struct amdgpu_display_manager *dm = &adev->dm;
|
||||||
struct drm_plane *plane;
|
struct drm_plane *plane;
|
||||||
struct drm_plane_state *old_plane_state;
|
struct drm_plane_state *old_plane_state;
|
||||||
uint32_t i;
|
uint32_t i, j;
|
||||||
uint32_t commit_streams_count = 0;
|
uint32_t commit_streams_count = 0;
|
||||||
uint32_t new_crtcs_count = 0;
|
uint32_t new_crtcs_count = 0;
|
||||||
struct drm_crtc *crtc;
|
struct drm_crtc *crtc, *pcrtc;
|
||||||
struct drm_crtc_state *old_crtc_state;
|
struct drm_crtc_state *old_crtc_state;
|
||||||
const struct dc_stream *commit_streams[MAX_STREAMS];
|
const struct dc_stream *commit_streams[MAX_STREAMS];
|
||||||
struct amdgpu_crtc *new_crtcs[MAX_STREAMS];
|
struct amdgpu_crtc *new_crtcs[MAX_STREAMS];
|
||||||
|
@ -2615,8 +2628,9 @@ void amdgpu_dm_atomic_commit_tail(
|
||||||
dc_stream_get_status(acrtc->stream)->primary_otg_inst;
|
dc_stream_get_status(acrtc->stream)->primary_otg_inst;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* update planes when needed */
|
/* update planes when needed per crtc*/
|
||||||
dc_commit_surfaces(state, dev, dm);
|
for_each_crtc_in_state(state, pcrtc, old_crtc_state, j)
|
||||||
|
dc_commit_surfaces(state, dev, dm, pcrtc);
|
||||||
|
|
||||||
for (i = 0; i < new_crtcs_count; i++) {
|
for (i = 0; i < new_crtcs_count; i++) {
|
||||||
/*
|
/*
|
||||||
|
@ -2793,15 +2807,18 @@ static uint32_t add_val_sets_surface(
|
||||||
const struct dc_stream *stream,
|
const struct dc_stream *stream,
|
||||||
const struct dc_surface *surface)
|
const struct dc_surface *surface)
|
||||||
{
|
{
|
||||||
uint32_t i = 0;
|
uint32_t i = 0, j = 0;
|
||||||
|
|
||||||
while (i < set_count) {
|
while (i < set_count) {
|
||||||
if (val_sets[i].stream == stream)
|
if (val_sets[i].stream == stream) {
|
||||||
|
while (val_sets[i].surfaces[j])
|
||||||
|
j++;
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
++i;
|
++i;
|
||||||
}
|
}
|
||||||
|
|
||||||
val_sets[i].surfaces[val_sets[i].surface_count] = surface;
|
val_sets[i].surfaces[j] = surface;
|
||||||
val_sets[i].surface_count++;
|
val_sets[i].surface_count++;
|
||||||
|
|
||||||
return val_sets[i].surface_count;
|
return val_sets[i].surface_count;
|
||||||
|
|
Loading…
Reference in New Issue