mirror of
https://gitlab.freedesktop.org/wlroots/wlroots.git
synced 2026-03-10 05:34:08 -04:00
Merge branch 'kms-plane-color-pipeline' into 'master'
Draft: backend/drm: add support for plane color pipelines See merge request wlroots/wlroots!5220
This commit is contained in:
commit
268f9e5f37
4 changed files with 121 additions and 0 deletions
|
|
@ -157,6 +157,68 @@ static bool init_plane_cursor_sizes(struct wlr_drm_plane *plane,
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool init_color_pipeline(struct wlr_drm_backend *drm,
|
||||||
|
uint32_t head_id, struct wl_list *list) {
|
||||||
|
uint32_t id = head_id;
|
||||||
|
while (id != 0) {
|
||||||
|
struct wlr_drm_colorop *colorop = calloc(1, sizeof(*colorop));
|
||||||
|
if (colorop == NULL) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
colorop->id = id;
|
||||||
|
wl_list_insert(list->prev, &colorop->link);
|
||||||
|
|
||||||
|
if (!get_drm_colorop_props(drm->fd, id, &colorop->props)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint64_t type = 0, next = 0;
|
||||||
|
if (!get_drm_prop(drm->fd, id, colorop->props.type, &type) ||
|
||||||
|
!get_drm_prop(drm->fd, id, colorop->props.next, &next)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
colorop->type = (uint32_t)type;
|
||||||
|
id = (uint32_t)next;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
static bool init_plane_color_pipelines(struct wlr_drm_backend *drm,
|
||||||
|
struct wlr_drm_plane *plane) {
|
||||||
|
if (plane->props.color_pipeline == 0) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
drmModePropertyRes *prop = drmModeGetProperty(drm->fd, plane->props.color_pipeline);
|
||||||
|
if (prop == NULL) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
plane->color_pipelines = calloc(prop->count_enums, sizeof(plane->color_pipelines[0]));
|
||||||
|
if (plane->color_pipelines == NULL) {
|
||||||
|
goto error;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < prop->count_enums; i++) {
|
||||||
|
wl_list_init(&plane->color_pipelines[i]);
|
||||||
|
plane->color_pipelines_len++;
|
||||||
|
|
||||||
|
if (!init_color_pipeline(drm, prop->enums[i].value, &plane->color_pipelines[i])) {
|
||||||
|
goto error;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
drmModeFreeProperty(prop);
|
||||||
|
return true;
|
||||||
|
|
||||||
|
error:
|
||||||
|
drmModeFreeProperty(prop);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
static bool init_plane(struct wlr_drm_backend *drm,
|
static bool init_plane(struct wlr_drm_backend *drm,
|
||||||
struct wlr_drm_plane *p, const drmModePlane *drm_plane) {
|
struct wlr_drm_plane *p, const drmModePlane *drm_plane) {
|
||||||
uint32_t id = drm_plane->plane_id;
|
uint32_t id = drm_plane->plane_id;
|
||||||
|
|
@ -239,6 +301,10 @@ static bool init_plane(struct wlr_drm_backend *drm,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!init_plane_color_pipelines(drm, p)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
assert(drm->num_crtcs <= 32);
|
assert(drm->num_crtcs <= 32);
|
||||||
for (size_t j = 0; j < drm->num_crtcs; j++) {
|
for (size_t j = 0; j < drm->num_crtcs; j++) {
|
||||||
uint32_t crtc_bit = 1 << j;
|
uint32_t crtc_bit = 1 << j;
|
||||||
|
|
@ -372,6 +438,14 @@ static void drm_plane_finish_surface(struct wlr_drm_plane *plane) {
|
||||||
finish_drm_surface(&plane->mgpu_surf);
|
finish_drm_surface(&plane->mgpu_surf);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void finish_color_pipeline(struct wl_list *list) {
|
||||||
|
struct wlr_drm_colorop *colorop, *tmp;
|
||||||
|
wl_list_for_each_safe(colorop, tmp, list, link) {
|
||||||
|
wl_list_remove(&colorop->link);
|
||||||
|
free(colorop);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void finish_drm_resources(struct wlr_drm_backend *drm) {
|
void finish_drm_resources(struct wlr_drm_backend *drm) {
|
||||||
if (!drm) {
|
if (!drm) {
|
||||||
return;
|
return;
|
||||||
|
|
@ -396,9 +470,15 @@ void finish_drm_resources(struct wlr_drm_backend *drm) {
|
||||||
|
|
||||||
for (size_t i = 0; i < drm->num_planes; ++i) {
|
for (size_t i = 0; i < drm->num_planes; ++i) {
|
||||||
struct wlr_drm_plane *plane = &drm->planes[i];
|
struct wlr_drm_plane *plane = &drm->planes[i];
|
||||||
|
|
||||||
drm_plane_finish_surface(plane);
|
drm_plane_finish_surface(plane);
|
||||||
wlr_drm_format_set_finish(&plane->formats);
|
wlr_drm_format_set_finish(&plane->formats);
|
||||||
free(plane->cursor_sizes);
|
free(plane->cursor_sizes);
|
||||||
|
|
||||||
|
for (size_t j = 0; j < plane->color_pipelines_len; j++) {
|
||||||
|
finish_color_pipeline(&plane->color_pipelines[j]);
|
||||||
|
}
|
||||||
|
free(plane->color_pipelines);
|
||||||
}
|
}
|
||||||
|
|
||||||
free(drm->planes);
|
free(drm->planes);
|
||||||
|
|
|
||||||
|
|
@ -50,6 +50,7 @@ static const struct prop_info crtc_info[] = {
|
||||||
|
|
||||||
static const struct prop_info plane_info[] = {
|
static const struct prop_info plane_info[] = {
|
||||||
#define INDEX(name) (offsetof(struct wlr_drm_plane_props, name) / sizeof(uint32_t))
|
#define INDEX(name) (offsetof(struct wlr_drm_plane_props, name) / sizeof(uint32_t))
|
||||||
|
{ "COLOR_PIPELINE", INDEX(color_pipeline) },
|
||||||
{ "CRTC_H", INDEX(crtc_h) },
|
{ "CRTC_H", INDEX(crtc_h) },
|
||||||
{ "CRTC_ID", INDEX(crtc_id) },
|
{ "CRTC_ID", INDEX(crtc_id) },
|
||||||
{ "CRTC_W", INDEX(crtc_w) },
|
{ "CRTC_W", INDEX(crtc_w) },
|
||||||
|
|
@ -71,6 +72,18 @@ static const struct prop_info plane_info[] = {
|
||||||
#undef INDEX
|
#undef INDEX
|
||||||
};
|
};
|
||||||
|
|
||||||
|
static const struct prop_info colorop_info[] = {
|
||||||
|
#define INDEX(name) (offsetof(struct wlr_drm_colorop_props, name) / sizeof(uint32_t))
|
||||||
|
{ "BYPASS", INDEX(bypass) },
|
||||||
|
{ "CURVE_1D_TYPE", INDEX(curve_1d_type) },
|
||||||
|
{ "DATA", INDEX(data) },
|
||||||
|
{ "MULTIPLIER", INDEX(multiplier) },
|
||||||
|
{ "NEXT", INDEX(next) },
|
||||||
|
{ "SIZE", INDEX(size) },
|
||||||
|
{ "TYPE", INDEX(type) },
|
||||||
|
#undef INDEX
|
||||||
|
};
|
||||||
|
|
||||||
static int cmp_prop_info(const void *arg1, const void *arg2) {
|
static int cmp_prop_info(const void *arg1, const void *arg2) {
|
||||||
const char *key = arg1;
|
const char *key = arg1;
|
||||||
const struct prop_info *elem = arg2;
|
const struct prop_info *elem = arg2;
|
||||||
|
|
@ -121,6 +134,11 @@ bool get_drm_plane_props(int fd, uint32_t id, struct wlr_drm_plane_props *out) {
|
||||||
plane_info, sizeof(plane_info) / sizeof(plane_info[0]));
|
plane_info, sizeof(plane_info) / sizeof(plane_info[0]));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool get_drm_colorop_props(int fd, uint32_t id, struct wlr_drm_colorop_props *out) {
|
||||||
|
return scan_properties(fd, id, DRM_MODE_OBJECT_COLOROP, (uint32_t *)out,
|
||||||
|
colorop_info, sizeof(colorop_info) / sizeof(colorop_info[0]));
|
||||||
|
}
|
||||||
|
|
||||||
bool get_drm_prop(int fd, uint32_t obj, uint32_t prop, uint64_t *ret) {
|
bool get_drm_prop(int fd, uint32_t obj, uint32_t prop, uint64_t *ret) {
|
||||||
drmModeObjectProperties *props =
|
drmModeObjectProperties *props =
|
||||||
drmModeObjectGetProperties(fd, obj, DRM_MODE_OBJECT_ANY);
|
drmModeObjectGetProperties(fd, obj, DRM_MODE_OBJECT_ANY);
|
||||||
|
|
|
||||||
|
|
@ -20,6 +20,14 @@ struct wlr_drm_viewport {
|
||||||
struct wlr_box dst_box;
|
struct wlr_box dst_box;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct wlr_drm_colorop {
|
||||||
|
uint32_t id;
|
||||||
|
uint32_t type;
|
||||||
|
|
||||||
|
struct wlr_drm_colorop_props props;
|
||||||
|
struct wl_list link; // wlr_drm_plane.color_pipelines
|
||||||
|
};
|
||||||
|
|
||||||
struct wlr_drm_plane {
|
struct wlr_drm_plane {
|
||||||
uint32_t type;
|
uint32_t type;
|
||||||
uint32_t id;
|
uint32_t id;
|
||||||
|
|
@ -39,6 +47,9 @@ struct wlr_drm_plane {
|
||||||
struct wlr_output_cursor_size *cursor_sizes;
|
struct wlr_output_cursor_size *cursor_sizes;
|
||||||
size_t cursor_sizes_len;
|
size_t cursor_sizes_len;
|
||||||
|
|
||||||
|
struct wl_list *color_pipelines; // wlr_drm_colorop.link
|
||||||
|
size_t color_pipelines_len;
|
||||||
|
|
||||||
struct wlr_drm_plane_props props;
|
struct wlr_drm_plane_props props;
|
||||||
|
|
||||||
uint32_t initial_crtc_id;
|
uint32_t initial_crtc_id;
|
||||||
|
|
|
||||||
|
|
@ -65,12 +65,24 @@ struct wlr_drm_plane_props {
|
||||||
uint32_t hotspot_x;
|
uint32_t hotspot_x;
|
||||||
uint32_t hotspot_y;
|
uint32_t hotspot_y;
|
||||||
uint32_t in_fence_fd;
|
uint32_t in_fence_fd;
|
||||||
|
uint32_t color_pipeline;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct wlr_drm_colorop_props {
|
||||||
|
uint32_t type;
|
||||||
|
uint32_t next;
|
||||||
|
uint32_t bypass;
|
||||||
|
uint32_t data; // for 1D_LUT, CTM_3X4, 3D_LUT
|
||||||
|
uint32_t size; // for 1D_LUT, 3D_LUT
|
||||||
|
uint32_t curve_1d_type; // for 1D_CURVE
|
||||||
|
uint32_t multiplier; // for MULTIPLIER
|
||||||
};
|
};
|
||||||
|
|
||||||
bool get_drm_connector_props(int fd, uint32_t id,
|
bool get_drm_connector_props(int fd, uint32_t id,
|
||||||
struct wlr_drm_connector_props *out);
|
struct wlr_drm_connector_props *out);
|
||||||
bool get_drm_crtc_props(int fd, uint32_t id, struct wlr_drm_crtc_props *out);
|
bool get_drm_crtc_props(int fd, uint32_t id, struct wlr_drm_crtc_props *out);
|
||||||
bool get_drm_plane_props(int fd, uint32_t id, struct wlr_drm_plane_props *out);
|
bool get_drm_plane_props(int fd, uint32_t id, struct wlr_drm_plane_props *out);
|
||||||
|
bool get_drm_colorop_props(int fd, uint32_t id, struct wlr_drm_colorop_props *out);
|
||||||
|
|
||||||
bool get_drm_prop(int fd, uint32_t obj, uint32_t prop, uint64_t *ret);
|
bool get_drm_prop(int fd, uint32_t obj, uint32_t prop, uint64_t *ret);
|
||||||
void *get_drm_prop_blob(int fd, uint32_t obj, uint32_t prop, size_t *ret_len);
|
void *get_drm_prop_blob(int fd, uint32_t obj, uint32_t prop, size_t *ret_len);
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue