mirror of
https://github.com/mpv-player/mpv.git
synced 2025-12-28 05:33:14 +00:00
drm/atomic: refactor planes names
We are currently using primary / overlay planes drm objects, assuming that primary plane is osd and overlay plane is video. This commit is doing two things : - replace the primary / overlay planes members with osd and video planes member without the assumption - Add two more options to determine which one of the primary / overlay is associated to osd / video. - It will default osd to overlay and video to primary if unspecified
This commit is contained in:
@@ -488,6 +488,20 @@ Available video output drivers are:
|
||||
Mode ID to use (resolution and frame rate).
|
||||
(default: 0)
|
||||
|
||||
``--drm-osd-plane-id=<number>``
|
||||
Select the DRM planed index to use for OSD (or OSD and video).
|
||||
Index is zero based, and related to crtc.
|
||||
When using this option with drm_prime renderer, it will only affect
|
||||
the OSD contents. Otherwise it will set OSD & video plane.
|
||||
(default: primary plane)
|
||||
|
||||
``--drm-video-plane-id=<number>``
|
||||
Select the DRM planed index to use for video layer.
|
||||
Index is zero based, and related to crtc.
|
||||
This option only has effect when using the drm_prime renderer (which
|
||||
supports several layers) together with ``vo=gpu`` and ``gpu-context=drm``.
|
||||
(default: first overlay plane)
|
||||
|
||||
``--drm-format=<xrgb8888,xrgb2101010>``
|
||||
Select the DRM format to use (default: xrgb8888). This allows you to
|
||||
choose the bit depth of the DRM mode. xrgb8888 is your usual 24 bit per
|
||||
|
||||
@@ -137,8 +137,8 @@ void drm_object_print_info(struct mp_log *log, struct drm_object *object)
|
||||
(long long)object->props->prop_values[i]);
|
||||
}
|
||||
|
||||
struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd,
|
||||
int crtc_id, int connector_id, int overlay_id)
|
||||
struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd, int crtc_id,
|
||||
int connector_id, int osd_plane_id, int video_plane_id)
|
||||
{
|
||||
drmModePlane *drmplane = NULL;
|
||||
drmModePlaneRes *plane_res = NULL;
|
||||
@@ -146,7 +146,10 @@ struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd,
|
||||
struct drm_object *plane = NULL;
|
||||
struct drm_atomic_context *ctx;
|
||||
int crtc_index = -1;
|
||||
int layercount = 0;
|
||||
int layercount = -1;
|
||||
int primary_id = 0;
|
||||
int overlay_id = 0;
|
||||
|
||||
uint64_t value;
|
||||
|
||||
res = drmModeGetResources(fd);
|
||||
@@ -206,20 +209,26 @@ struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd,
|
||||
mp_err(log, "Unable to retrieve type property from plane %d\n", j);
|
||||
goto fail;
|
||||
} else {
|
||||
if ((value == DRM_PLANE_TYPE_OVERLAY) &&
|
||||
(layercount == overlay_id)) {
|
||||
ctx->overlay_plane = plane;
|
||||
}
|
||||
else if (value == DRM_PLANE_TYPE_PRIMARY) {
|
||||
ctx->primary_plane = plane;
|
||||
}
|
||||
else {
|
||||
drm_object_free(plane);
|
||||
plane = NULL;
|
||||
layercount++;
|
||||
|
||||
if ((!primary_id) && (value == DRM_PLANE_TYPE_PRIMARY))
|
||||
primary_id = drmplane->plane_id;
|
||||
|
||||
if ((!overlay_id) && (value == DRM_PLANE_TYPE_OVERLAY))
|
||||
overlay_id = drmplane->plane_id;
|
||||
|
||||
if (layercount == osd_plane_id) {
|
||||
ctx->osd_plane = plane;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (value == DRM_PLANE_TYPE_OVERLAY)
|
||||
layercount++;
|
||||
if (layercount == video_plane_id) {
|
||||
ctx->video_plane = plane;
|
||||
continue;
|
||||
}
|
||||
|
||||
drm_object_free(plane);
|
||||
plane = NULL;
|
||||
}
|
||||
} else {
|
||||
mp_err(log, "Failed to create Plane object from plane ID %d\n",
|
||||
@@ -231,18 +240,34 @@ struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd,
|
||||
drmplane = NULL;
|
||||
}
|
||||
|
||||
if (!ctx->primary_plane) {
|
||||
mp_err(log, "Failed to find primary plane\n");
|
||||
goto fail;
|
||||
// default OSD plane to primary if unspecified
|
||||
if (!ctx->osd_plane) {
|
||||
if (primary_id) {
|
||||
mp_verbose(log, "Using default plane %d for OSD\n", primary_id);
|
||||
ctx->osd_plane = drm_object_create(log, ctx->fd, primary_id, DRM_MODE_OBJECT_PLANE);
|
||||
} else {
|
||||
mp_err(log, "Failed to find OSD plane with id=%d\n", osd_plane_id);
|
||||
goto fail;
|
||||
}
|
||||
} else {
|
||||
mp_verbose(log, "Found OSD plane with ID %d\n", ctx->osd_plane->id);
|
||||
}
|
||||
|
||||
if (!ctx->overlay_plane) {
|
||||
mp_err(log, "Failed to find overlay plane with id=%d\n", overlay_id);
|
||||
goto fail;
|
||||
// default video plane to overlay if unspecified
|
||||
if (!ctx->video_plane) {
|
||||
if (overlay_id) {
|
||||
mp_verbose(log, "Using default plane %d for video\n", overlay_id);
|
||||
ctx->video_plane = drm_object_create(log, ctx->fd, overlay_id, DRM_MODE_OBJECT_PLANE);
|
||||
} else {
|
||||
mp_err(log, "Failed to find video plane with id=%d\n", video_plane_id);
|
||||
goto fail;
|
||||
}
|
||||
} else {
|
||||
mp_verbose(log, "Found video plane with ID %d\n", ctx->video_plane->id);
|
||||
}
|
||||
|
||||
mp_verbose(log, "Found Primary plane with ID %d, overlay with ID %d\n",
|
||||
ctx->primary_plane->id, ctx->overlay_plane->id);
|
||||
mp_verbose(log, "Found Video plane with ID %d, OSD with ID %d\n",
|
||||
ctx->video_plane->id, ctx->osd_plane->id);
|
||||
|
||||
drmModeFreePlaneResources(plane_res);
|
||||
drmModeFreeResources(res);
|
||||
@@ -265,7 +290,7 @@ void drm_atomic_destroy_context(struct drm_atomic_context *ctx)
|
||||
{
|
||||
drm_object_free(ctx->crtc);
|
||||
drm_object_free(ctx->connector);
|
||||
drm_object_free(ctx->primary_plane);
|
||||
drm_object_free(ctx->overlay_plane);
|
||||
drm_object_free(ctx->osd_plane);
|
||||
drm_object_free(ctx->video_plane);
|
||||
talloc_free(ctx);
|
||||
}
|
||||
|
||||
@@ -37,8 +37,8 @@ struct drm_atomic_context {
|
||||
|
||||
struct drm_object *crtc;
|
||||
struct drm_object *connector;
|
||||
struct drm_object *primary_plane;
|
||||
struct drm_object *overlay_plane;
|
||||
struct drm_object *osd_plane;
|
||||
struct drm_object *video_plane;
|
||||
|
||||
drmModeAtomicReq *request;
|
||||
};
|
||||
@@ -52,7 +52,8 @@ drmModePropertyBlobPtr drm_object_get_property_blob(struct drm_object *object, c
|
||||
struct drm_object * drm_object_create(struct mp_log *log, int fd, uint32_t object_id, uint32_t type);
|
||||
void drm_object_free(struct drm_object *object);
|
||||
void drm_object_print_info(struct mp_log *log, struct drm_object *object);
|
||||
struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd, int crtc_id, int connector_id, int overlay_id);
|
||||
struct drm_atomic_context *drm_atomic_create_context(struct mp_log *log, int fd, int crtc_id, int connector_id,
|
||||
int osd_plane_id, int video_plane_id);
|
||||
void drm_atomic_destroy_context(struct drm_atomic_context *ctx);
|
||||
|
||||
#endif // MP_DRMATOMIC_H
|
||||
|
||||
@@ -47,13 +47,18 @@ const struct m_sub_options drm_conf = {
|
||||
OPT_STRING_VALIDATE("drm-connector", drm_connector_spec,
|
||||
0, drm_validate_connector_opt),
|
||||
OPT_INT("drm-mode", drm_mode_id, 0),
|
||||
OPT_INT("drm-overlay", drm_overlay_id, 0),
|
||||
OPT_INT("drm-osd-plane-id", drm_osd_plane_id, 0),
|
||||
OPT_INT("drm-video-plane-id", drm_video_plane_id, 0),
|
||||
OPT_CHOICE("drm-format", drm_format, 0,
|
||||
({"xrgb8888", DRM_OPTS_FORMAT_XRGB8888},
|
||||
{"xrgb2101010", DRM_OPTS_FORMAT_XRGB2101010})),
|
||||
OPT_SIZE_BOX("drm-osd-size", drm_osd_size, 0),
|
||||
{0},
|
||||
},
|
||||
.defaults = &(const struct drm_opts) {
|
||||
.drm_osd_plane_id = -1,
|
||||
.drm_video_plane_id = -1,
|
||||
},
|
||||
.size = sizeof(struct drm_opts),
|
||||
};
|
||||
|
||||
@@ -238,7 +243,7 @@ static void parse_connector_spec(struct mp_log *log,
|
||||
|
||||
|
||||
struct kms *kms_create(struct mp_log *log, const char *connector_spec,
|
||||
int mode_id, int overlay_id)
|
||||
int mode_id, int osd_plane_id, int video_plane_id)
|
||||
{
|
||||
int card_no = -1;
|
||||
char *connector_name = NULL;
|
||||
@@ -286,7 +291,7 @@ struct kms *kms_create(struct mp_log *log, const char *connector_spec,
|
||||
} else {
|
||||
mp_verbose(log, "DRM Atomic support found\n");
|
||||
kms->atomic_context = drm_atomic_create_context(kms->log, kms->fd, kms->crtc_id,
|
||||
kms->connector->connector_id, overlay_id);
|
||||
kms->connector->connector_id, osd_plane_id, video_plane_id);
|
||||
if (!kms->atomic_context) {
|
||||
mp_err(log, "Failed to create DRM atomic context\n");
|
||||
goto err;
|
||||
|
||||
@@ -48,7 +48,8 @@ struct vt_switcher {
|
||||
struct drm_opts {
|
||||
char *drm_connector_spec;
|
||||
int drm_mode_id;
|
||||
int drm_overlay_id;
|
||||
int drm_osd_plane_id;
|
||||
int drm_video_plane_id;
|
||||
int drm_format;
|
||||
struct m_geometry drm_osd_size;
|
||||
};
|
||||
@@ -64,7 +65,7 @@ void vt_switcher_release(struct vt_switcher *s, void (*handler)(void*),
|
||||
void *user_data);
|
||||
|
||||
struct kms *kms_create(struct mp_log *log, const char *connector_spec,
|
||||
int mode_id, int overlay_id);
|
||||
int mode_id, int osd_plane_id, int video_plane_id);
|
||||
void kms_destroy(struct kms *kms);
|
||||
double kms_get_display_fps(const struct kms *kms);
|
||||
|
||||
|
||||
@@ -352,9 +352,9 @@ static void drm_egl_swap_buffers(struct ra_ctx *ctx)
|
||||
update_framebuffer_from_bo(ctx, p->gbm.next_bo);
|
||||
|
||||
if (atomic_ctx) {
|
||||
drm_object_set_property(atomic_ctx->request, atomic_ctx->primary_plane, "FB_ID", p->fb->id);
|
||||
drm_object_set_property(atomic_ctx->request, atomic_ctx->primary_plane, "CRTC_ID", atomic_ctx->crtc->id);
|
||||
drm_object_set_property(atomic_ctx->request, atomic_ctx->primary_plane, "ZPOS", 1);
|
||||
drm_object_set_property(atomic_ctx->request, atomic_ctx->osd_plane, "FB_ID", p->fb->id);
|
||||
drm_object_set_property(atomic_ctx->request, atomic_ctx->osd_plane, "CRTC_ID", atomic_ctx->crtc->id);
|
||||
drm_object_set_property(atomic_ctx->request, atomic_ctx->osd_plane, "ZPOS", 1);
|
||||
|
||||
ret = drmModeAtomicCommit(p->kms->fd, atomic_ctx->request,
|
||||
DRM_MODE_ATOMIC_NONBLOCK | DRM_MODE_PAGE_FLIP_EVENT, NULL);
|
||||
@@ -442,7 +442,7 @@ static bool probe_gbm_format(struct ra_ctx *ctx, uint32_t argb_format, uint32_t
|
||||
}
|
||||
|
||||
drmModePlane *drmplane =
|
||||
drmModeGetPlane(p->kms->fd, p->kms->atomic_context->primary_plane->id);
|
||||
drmModeGetPlane(p->kms->fd, p->kms->atomic_context->osd_plane->id);
|
||||
bool have_argb = false;
|
||||
bool have_xrgb = false;
|
||||
bool result = false;
|
||||
@@ -490,7 +490,8 @@ static bool drm_egl_init(struct ra_ctx *ctx)
|
||||
MP_VERBOSE(ctx, "Initializing KMS\n");
|
||||
p->kms = kms_create(ctx->log, ctx->vo->opts->drm_opts->drm_connector_spec,
|
||||
ctx->vo->opts->drm_opts->drm_mode_id,
|
||||
ctx->vo->opts->drm_opts->drm_overlay_id);
|
||||
ctx->vo->opts->drm_opts->drm_osd_plane_id,
|
||||
ctx->vo->opts->drm_opts->drm_video_plane_id);
|
||||
if (!p->kms) {
|
||||
MP_ERR(ctx, "Failed to create KMS.\n");
|
||||
return false;
|
||||
|
||||
@@ -160,23 +160,23 @@ static int overlay_frame(struct ra_hwdec *hw, struct mp_image *hw_image,
|
||||
}
|
||||
|
||||
if (request) {
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "FB_ID", next_frame.fb.fb_id);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "CRTC_ID", p->ctx->crtc->id);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "SRC_X", p->src.x0 << 16);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "SRC_Y", p->src.y0 << 16);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "SRC_W", srcw << 16);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "SRC_H", srch << 16);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "CRTC_X", MP_ALIGN_DOWN(p->dst.x0, 2));
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "CRTC_Y", MP_ALIGN_DOWN(p->dst.y0, 2));
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "CRTC_W", dstw);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "CRTC_H", dsth);
|
||||
drm_object_set_property(request, p->ctx->overlay_plane, "ZPOS", 0);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "FB_ID", next_frame.fb.fb_id);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "CRTC_ID", p->ctx->crtc->id);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "SRC_X", p->src.x0 << 16);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "SRC_Y", p->src.y0 << 16);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "SRC_W", srcw << 16);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "SRC_H", srch << 16);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "CRTC_X", MP_ALIGN_DOWN(p->dst.x0, 2));
|
||||
drm_object_set_property(request, p->ctx->video_plane, "CRTC_Y", MP_ALIGN_DOWN(p->dst.y0, 2));
|
||||
drm_object_set_property(request, p->ctx->video_plane, "CRTC_W", dstw);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "CRTC_H", dsth);
|
||||
drm_object_set_property(request, p->ctx->video_plane, "ZPOS", 0);
|
||||
} else {
|
||||
ret = drmModeSetPlane(p->ctx->fd, p->ctx->overlay_plane->id, p->ctx->crtc->id, next_frame.fb.fb_id, 0,
|
||||
ret = drmModeSetPlane(p->ctx->fd, p->ctx->video_plane->id, p->ctx->crtc->id, next_frame.fb.fb_id, 0,
|
||||
MP_ALIGN_DOWN(p->dst.x0, 2), MP_ALIGN_DOWN(p->dst.y0, 2), dstw, dsth,
|
||||
p->src.x0 << 16, p->src.y0 << 16 , srcw << 16, srch << 16);
|
||||
if (ret < 0) {
|
||||
MP_ERR(hw, "Failed to set the plane %d (buffer %d).\n", p->ctx->overlay_plane->id,
|
||||
MP_ERR(hw, "Failed to set the plane %d (buffer %d).\n", p->ctx->video_plane->id,
|
||||
next_frame.fb.fb_id);
|
||||
goto fail;
|
||||
}
|
||||
@@ -210,13 +210,14 @@ static void uninit(struct ra_hwdec *hw)
|
||||
static int init(struct ra_hwdec *hw)
|
||||
{
|
||||
struct priv *p = hw->priv;
|
||||
int drm_overlay;
|
||||
int osd_plane_id, video_plane_id;
|
||||
|
||||
p->log = hw->log;
|
||||
|
||||
void *tmp = talloc_new(NULL);
|
||||
struct drm_opts *opts = mp_get_config_group(tmp, hw->global, &drm_conf);
|
||||
drm_overlay = opts->drm_overlay_id;
|
||||
osd_plane_id = opts->drm_osd_plane_id;
|
||||
video_plane_id = opts->drm_video_plane_id;
|
||||
talloc_free(tmp);
|
||||
|
||||
struct mpv_opengl_drm_params *drm_params;
|
||||
@@ -224,7 +225,7 @@ static int init(struct ra_hwdec *hw)
|
||||
drm_params = ra_get_native_resource(hw->ra, "drm_params");
|
||||
if (drm_params) {
|
||||
p->ctx = drm_atomic_create_context(p->log, drm_params->fd, drm_params->crtc_id,
|
||||
drm_params->connector_id, drm_overlay);
|
||||
drm_params->connector_id, osd_plane_id, video_plane_id);
|
||||
if (!p->ctx) {
|
||||
mp_err(p->log, "Failed to retrieve DRM atomic context.\n");
|
||||
goto err;
|
||||
@@ -242,7 +243,6 @@ static int init(struct ra_hwdec *hw)
|
||||
drmModeFreeCrtc(crtc);
|
||||
}
|
||||
|
||||
|
||||
uint64_t has_prime;
|
||||
if (drmGetCap(p->ctx->fd, DRM_CAP_PRIME, &has_prime) < 0) {
|
||||
MP_ERR(hw, "Card does not support prime handles.\n");
|
||||
|
||||
@@ -420,7 +420,8 @@ static int preinit(struct vo *vo)
|
||||
p->kms = kms_create(
|
||||
vo->log, vo->opts->drm_opts->drm_connector_spec,
|
||||
vo->opts->drm_opts->drm_mode_id,
|
||||
vo->opts->drm_opts->drm_overlay_id);
|
||||
vo->opts->drm_opts->drm_osd_plane_id,
|
||||
vo->opts->drm_opts->drm_video_plane_id);
|
||||
if (!p->kms) {
|
||||
MP_ERR(vo, "Failed to create KMS.\n");
|
||||
goto err;
|
||||
|
||||
Reference in New Issue
Block a user