diff options
Diffstat (limited to 'backend')
-rw-r--r-- | backend/backend.c | 8 | ||||
-rw-r--r-- | backend/drm/atomic.c | 7 | ||||
-rw-r--r-- | backend/drm/drm.c | 30 | ||||
-rw-r--r-- | backend/drm/properties.c | 13 | ||||
-rw-r--r-- | backend/multi/backend.c | 2 |
5 files changed, 46 insertions, 14 deletions
diff --git a/backend/backend.c b/backend/backend.c index 4b186767..c5dcdb48 100644 --- a/backend/backend.c +++ b/backend/backend.c @@ -217,16 +217,16 @@ struct wlr_backend *wlr_backend_autocreate(struct wl_display *display, backend, &multi->session, name, create_renderer_func); if (subbackend == NULL) { wlr_log(WLR_ERROR, "failed to start backend '%s'", name); - wlr_backend_destroy(backend); wlr_session_destroy(multi->session); + wlr_backend_destroy(backend); free(names); return NULL; } if (!wlr_multi_backend_add(backend, subbackend)) { wlr_log(WLR_ERROR, "failed to add backend '%s'", name); - wlr_backend_destroy(backend); wlr_session_destroy(multi->session); + wlr_backend_destroy(backend); free(names); return NULL; } @@ -272,8 +272,8 @@ struct wlr_backend *wlr_backend_autocreate(struct wl_display *display, multi->session); if (!libinput) { wlr_log(WLR_ERROR, "Failed to start libinput backend"); - wlr_backend_destroy(backend); wlr_session_destroy(multi->session); + wlr_backend_destroy(backend); return NULL; } wlr_multi_backend_add(backend, libinput); @@ -283,8 +283,8 @@ struct wlr_backend *wlr_backend_autocreate(struct wl_display *display, if (!primary_drm) { wlr_log(WLR_ERROR, "Failed to open any DRM device"); wlr_backend_destroy(libinput); - wlr_backend_destroy(backend); wlr_session_destroy(multi->session); + wlr_backend_destroy(backend); return NULL; } diff --git a/backend/drm/atomic.c b/backend/drm/atomic.c index 5c064ac7..ad80f2fd 100644 --- a/backend/drm/atomic.c +++ b/backend/drm/atomic.c @@ -104,7 +104,8 @@ static bool atomic_crtc_pageflip(struct wlr_drm_backend *drm, drmModeDestroyPropertyBlob(drm->fd, crtc->mode_id); } - if (drmModeCreatePropertyBlob(drm->fd, mode, sizeof(*mode), &crtc->mode_id)) { + if (drmModeCreatePropertyBlob(drm->fd, mode, sizeof(*mode), + &crtc->mode_id)) { wlr_log_errno(WLR_ERROR, "Unable to create property blob"); return false; } @@ -120,6 +121,10 @@ static bool atomic_crtc_pageflip(struct wlr_drm_backend *drm, struct atomic atom; atomic_begin(crtc, &atom); atomic_add(&atom, conn->id, conn->props.crtc_id, crtc->id); + if (mode != NULL && conn->props.link_status != 0) { + atomic_add(&atom, conn->id, conn->props.link_status, + DRM_MODE_LINK_STATUS_GOOD); + } atomic_add(&atom, crtc->id, crtc->props.mode_id, crtc->mode_id); atomic_add(&atom, crtc->id, crtc->props.active, 1); set_plane_props(&atom, crtc->primary, crtc->id, fb_id, true); diff --git a/backend/drm/drm.c b/backend/drm/drm.c index 272a168c..0b624717 100644 --- a/backend/drm/drm.c +++ b/backend/drm/drm.c @@ -1,4 +1,4 @@ -#define _POSIX_C_SOURCE 199309L +#define _POSIX_C_SOURCE 200112L #include <assert.h> #include <drm_mode.h> #include <EGL/egl.h> @@ -1083,6 +1083,24 @@ void scan_drm_connectors(struct wlr_drm_backend *drm) { wlr_conn->crtc = NULL; } + // This can only happen *after* hotplug, since we haven't read the + // connector properties yet + if (wlr_conn->props.link_status != 0) { + uint64_t link_status; + if (!get_drm_prop(drm->fd, wlr_conn->id, + wlr_conn->props.link_status, &link_status)) { + wlr_log(WLR_ERROR, "Failed to get link status for '%s'", + wlr_conn->output.name); + continue; + } + + if (link_status == DRM_MODE_LINK_STATUS_BAD) { + // We need to reload our list of modes and force a modeset + wlr_log(WLR_INFO, "Bad link for '%s'", wlr_conn->output.name); + drm_connector_cleanup(wlr_conn); + } + } + if (wlr_conn->state == WLR_DRM_CONN_DISCONNECTED && drm_conn->connection == DRM_MODE_CONNECTED) { wlr_log(WLR_INFO, "'%s' connected", wlr_conn->output.name); @@ -1243,7 +1261,7 @@ static void page_flip_handler(int fd, unsigned seq, int handle_drm_event(int fd, uint32_t mask, void *data) { drmEventContext event = { - .version = DRM_EVENT_CONTEXT_VERSION, + .version = 2, .page_flip_handler = page_flip_handler, }; @@ -1329,7 +1347,13 @@ static void drm_connector_cleanup(struct wlr_drm_connector *conn) { memset(&conn->output.model, 0, sizeof(conn->output.model)); memset(&conn->output.serial, 0, sizeof(conn->output.serial)); - conn->pageflip_pending = false; + if (conn->output.idle_frame != NULL) { + wl_event_source_remove(conn->output.idle_frame); + conn->output.idle_frame = NULL; + } + conn->output.needs_swap = false; + conn->output.frame_pending = false; + /* Fallthrough */ case WLR_DRM_CONN_NEEDS_MODESET: wlr_log(WLR_INFO, "Emitting destruction signal for '%s'", diff --git a/backend/drm/properties.c b/backend/drm/properties.c index 372de232..5ca4c8ac 100644 --- a/backend/drm/properties.c +++ b/backend/drm/properties.c @@ -19,9 +19,10 @@ struct prop_info { static const struct prop_info connector_info[] = { #define INDEX(name) (offsetof(union wlr_drm_connector_props, name) / sizeof(uint32_t)) - { "CRTC_ID", INDEX(crtc_id) }, - { "DPMS", INDEX(dpms) }, - { "EDID", INDEX(edid) }, + { "CRTC_ID", INDEX(crtc_id) }, + { "DPMS", INDEX(dpms) }, + { "EDID", INDEX(edid) }, + { "link-status", INDEX(link_status) }, #undef INDEX }; @@ -87,7 +88,8 @@ static bool scan_properties(int fd, uint32_t id, uint32_t type, uint32_t *result return true; } -bool get_drm_connector_props(int fd, uint32_t id, union wlr_drm_connector_props *out) { +bool get_drm_connector_props(int fd, uint32_t id, + union wlr_drm_connector_props *out) { return scan_properties(fd, id, DRM_MODE_OBJECT_CONNECTOR, out->props, connector_info, sizeof(connector_info) / sizeof(connector_info[0])); } @@ -103,7 +105,8 @@ bool get_drm_plane_props(int fd, uint32_t id, union wlr_drm_plane_props *out) { } bool get_drm_prop(int fd, uint32_t obj, uint32_t prop, uint64_t *ret) { - drmModeObjectProperties *props = drmModeObjectGetProperties(fd, obj, DRM_MODE_OBJECT_ANY); + drmModeObjectProperties *props = + drmModeObjectGetProperties(fd, obj, DRM_MODE_OBJECT_ANY); if (!props) { return false; } diff --git a/backend/multi/backend.c b/backend/multi/backend.c index cefaa361..50851109 100644 --- a/backend/multi/backend.c +++ b/backend/multi/backend.c @@ -1,4 +1,4 @@ -#define _POSIX_C_SOURCE 199309L +#define _POSIX_C_SOURCE 200112L #include <assert.h> #include <stdbool.h> #include <stdlib.h> |