From 610b0493ac4a3bbde44378adf855c7202b1e59c4 Mon Sep 17 00:00:00 2001 From: Scott Anderson Date: Sat, 30 Sep 2017 19:03:34 +1300 Subject: Rename files to remove pointless drm prefix --- backend/drm/properties.c | 145 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 145 insertions(+) create mode 100644 backend/drm/properties.c (limited to 'backend/drm/properties.c') diff --git a/backend/drm/properties.c b/backend/drm/properties.c new file mode 100644 index 00000000..5bec3243 --- /dev/null +++ b/backend/drm/properties.c @@ -0,0 +1,145 @@ +#include +#include +#include +#include +#include +#include +#include +#include "backend/drm/properties.h" + +/* + * Creates a mapping between property names and an array index where to store + * the ids. The prop_info arrays must be sorted by name, as bsearch is used to + * search them. + */ +struct prop_info { + const char *name; + size_t index; +}; + +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) }, +#undef INDEX +}; + +static const struct prop_info crtc_info[] = { +#define INDEX(name) (offsetof(union wlr_drm_crtc_props, name) / sizeof(uint32_t)) + { "ACTIVE", INDEX(active) }, + { "MODE_ID", INDEX(mode_id) }, + { "rotation", INDEX(rotation) }, + { "scaling mode", INDEX(scaling_mode) }, +#undef INDEX +}; + +static const struct prop_info plane_info[] = { +#define INDEX(name) (offsetof(union wlr_drm_plane_props, name) / sizeof(uint32_t)) + { "CRTC_H", INDEX(crtc_h) }, + { "CRTC_ID", INDEX(crtc_id) }, + { "CRTC_W", INDEX(crtc_w) }, + { "CRTC_X", INDEX(crtc_x) }, + { "CRTC_Y", INDEX(crtc_y) }, + { "FB_ID", INDEX(fb_id) }, + { "SRC_H", INDEX(src_h) }, + { "SRC_W", INDEX(src_w) }, + { "SRC_X", INDEX(src_x) }, + { "SRC_Y", INDEX(src_y) }, + { "type", INDEX(type) }, +#undef INDEX +}; + +static int cmp_prop_info(const void *arg1, const void *arg2) { + const char *key = arg1; + const struct prop_info *elem = arg2; + + return strcmp(key, elem->name); +} + +static bool scan_properties(int fd, uint32_t id, uint32_t type, uint32_t *result, + const struct prop_info *info, size_t info_len) { + drmModeObjectProperties *props = drmModeObjectGetProperties(fd, id, type); + if (!props) { + wlr_log_errno(L_ERROR, "Failed to get DRM object properties"); + return false; + } + + for (uint32_t i = 0; i < props->count_props; ++i) { + drmModePropertyRes *prop = drmModeGetProperty(fd, props->props[i]); + if (!prop) { + wlr_log_errno(L_ERROR, "Failed to get DRM object property"); + continue; + } + + const struct prop_info *p = + bsearch(prop->name, info, info_len, sizeof(info[0]), cmp_prop_info); + if (p) { + result[p->index] = prop->prop_id; + } + + drmModeFreeProperty(prop); + } + + drmModeFreeObjectProperties(props); + return true; +} + +bool wlr_drm_get_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])); +} + +bool wlr_drm_get_crtc_props(int fd, uint32_t id, union wlr_drm_crtc_props *out) { + return scan_properties(fd, id, DRM_MODE_OBJECT_CRTC, out->props, + crtc_info, sizeof(crtc_info) / sizeof(crtc_info[0])); +} + +bool wlr_drm_get_plane_props(int fd, uint32_t id, union wlr_drm_plane_props *out) { + return scan_properties(fd, id, DRM_MODE_OBJECT_PLANE, out->props, + plane_info, sizeof(plane_info) / sizeof(plane_info[0])); +} + +bool wlr_drm_get_prop(int fd, uint32_t obj, uint32_t prop, uint64_t *ret) { + drmModeObjectProperties *props = drmModeObjectGetProperties(fd, obj, DRM_MODE_OBJECT_ANY); + if (!props) { + return false; + } + + bool found = false; + + for (uint32_t i = 0; i < props->count_props; ++i) { + if (props->props[i] == prop) { + *ret = props->prop_values[i]; + found = true; + break; + } + } + + drmModeFreeObjectProperties(props); + return found; +} + +void *wlr_drm_get_prop_blob(int fd, uint32_t obj, uint32_t prop, size_t *ret_len) { + uint64_t blob_id; + if (!wlr_drm_get_prop(fd, obj, prop, &blob_id)) { + return NULL; + } + + drmModePropertyBlobRes *blob = drmModeGetPropertyBlob(fd, blob_id); + if (!blob) { + return NULL; + } + + void *ptr = malloc(blob->length); + if (!ptr) { + drmModeFreePropertyBlob(blob); + return NULL; + } + + memcpy(ptr, blob->data, blob->length); + *ret_len = blob->length; + + drmModeFreePropertyBlob(blob); + return ptr; +} -- cgit v1.2.3