From 78cc612f10addc396d2e5d39c7cc48293028ac56 Mon Sep 17 00:00:00 2001 From: Matt Hoosier Date: Thu, 7 Nov 2019 16:03:41 -0600 Subject: [PATCH] example: improve CRTC search algorithm Add a fallback case for finding an eligible CRTC for the selected connector. The encoder picked may not have been wired up to that connector by the previous DRM master. --- example/common.c | 39 +++++++++++++++++++++++++++++++++++---- 1 file changed, 35 insertions(+), 4 deletions(-) diff --git a/example/common.c b/example/common.c index 00b5cc1..69b206c 100644 --- a/example/common.c +++ b/example/common.c @@ -1,5 +1,6 @@ #include #include +#include #include #include #include @@ -26,13 +27,43 @@ drmModeCrtc *pick_crtc(int drm_fd, drmModeRes *drm_res, { drmModeEncoder *enc; uint32_t crtc_id; + int i; + int j; + bool found; - /* TODO: don't blindly use current CRTC */ enc = drmModeGetEncoder(drm_fd, connector->encoder_id); - crtc_id = enc->crtc_id; - drmModeFreeEncoder(enc); - return drmModeGetCrtc(drm_fd, crtc_id); + if (enc) { + /* Current CRTC happens to be usable on the selected connector */ + crtc_id = enc->crtc_id; + drmModeFreeEncoder(enc); + return drmModeGetCrtc(drm_fd, crtc_id); + } else { + /* Current CRTC used by this encoder can't drive the selected connector. + * Search all of them for a valid combination. */ + for (i = 0, found = false; !found && i < connector->count_encoders; i++) { + enc = drmModeGetEncoder(drm_fd, connector->encoders[i]); + + if (!enc) { + continue; + } + + for (j = 0; !found && j < drm_res->count_crtcs; j++) { + /* Can the CRTC drive the connector? */ + if (enc->possible_crtcs & (1 << j)) { + crtc_id = drm_res->crtcs[j]; + found = true; + } + } + drmModeFreeEncoder(enc); + } + + if (found) { + return drmModeGetCrtc(drm_fd, crtc_id); + } else { + return NULL; + } + } } void disable_all_crtcs_except(int drm_fd, drmModeRes *drm_res, uint32_t crtc_id)