modesetting: Consider RandR primary output for selectioh of sync crtc.

The "sync crtc" is the crtc used to drive the display timing of a
drawable under DRI2 and DRI3/Present. If a drawable intersects
multiple video outputs, then normally the crtc is chosen which has
the largest intersection area with the drawable.

If multiple outputs / crtc's have exacty the same intersection
area then the crtc chosen was simply the first one with maximum
intersection. Iow. the choice was random, depending on plugging
order of displays.

This adds the ability to choose a preferred output in such a tie
situation. The RandR output marked as "primary output" is chosen
on such a tie.

This new behaviour and its implementation is consistent with other
video ddx drivers. See amdgpu-ddx, ati-ddx and nouveau-ddx for
reference. This commit is a straightforward port from amdgpu-ddx.

Signed-off-by: Mario Kleiner <mario.kleiner.de@gmail.com>
(cherry picked from commit 4b75e65766)
This commit is contained in:
Mario Kleiner 2021-10-01 09:47:41 +02:00 committed by Povilas Kanapickas
parent 22f4ff1026
commit fbc690ccaf

View File

@ -120,7 +120,8 @@ static RRCrtcPtr
rr_crtc_covering_box(ScreenPtr pScreen, BoxPtr box, Bool screen_is_xf86_hint)
{
rrScrPrivPtr pScrPriv;
RRCrtcPtr crtc, best_crtc;
RROutputPtr primary_output;
RRCrtcPtr crtc, best_crtc, primary_crtc;
int coverage, best_coverage;
int c;
BoxRec crtc_box, cover_box;
@ -136,6 +137,11 @@ rr_crtc_covering_box(ScreenPtr pScreen, BoxPtr box, Bool screen_is_xf86_hint)
if (!pScrPriv)
return NULL;
primary_crtc = NULL;
primary_output = RRFirstOutput(pScreen);
if (primary_output)
primary_crtc = primary_output->crtc;
for (c = 0; c < pScrPriv->numCrtcs; c++) {
crtc = pScrPriv->crtcs[c];
@ -146,7 +152,8 @@ rr_crtc_covering_box(ScreenPtr pScreen, BoxPtr box, Bool screen_is_xf86_hint)
rr_crtc_box(crtc, &crtc_box);
box_intersect(&cover_box, &crtc_box, box);
coverage = box_area(&cover_box);
if (coverage > best_coverage) {
if ((coverage > best_coverage) ||
(coverage == best_coverage && crtc == primary_crtc)) {
best_crtc = crtc;
best_coverage = coverage;
}