drm/vkms: Add cursor plane support
authorHaneen Mohammed <hamohammed.sa@gmail.com>
Thu, 6 Sep 2018 05:17:16 +0000 (08:17 +0300)
committerDaniel Vetter <daniel.vetter@ffwll.ch>
Tue, 11 Sep 2018 17:56:13 +0000 (19:56 +0200)
Add cursor plane support and update vkms_plane_atomic_check to enable
positioning cursor plane.

Signed-off-by: Haneen Mohammed <hamohammed.sa@gmail.com>
Signed-off-by: Daniel Vetter <daniel.vetter@ffwll.ch>
Link: https://patchwork.freedesktop.org/patch/msgid/c69078820eacf3246fa77beb0c6227b692cc5e82.1536210181.git.hamohammed.sa@gmail.com
drivers/gpu/drm/vkms/vkms_drv.h
drivers/gpu/drm/vkms/vkms_output.c
drivers/gpu/drm/vkms/vkms_plane.c

index 80af6d3a65e72a83eb79090c3ceb4d67b3bca081..b5ed90a8f19c07afbe91e0da4e013a0665b009c6 100644 (file)
@@ -7,8 +7,8 @@
 #include <drm/drm_encoder.h>
 #include <linux/hrtimer.h>
 
-#define XRES_MIN    32
-#define YRES_MIN    32
+#define XRES_MIN    20
+#define YRES_MIN    20
 
 #define XRES_DEF  1024
 #define YRES_DEF   768
@@ -20,6 +20,10 @@ static const u32 vkms_formats[] = {
        DRM_FORMAT_XRGB8888,
 };
 
+static const u32 vkms_cursor_formats[] = {
+       DRM_FORMAT_ARGB8888,
+};
+
 struct vkms_crc_data {
        struct drm_rect src;
        struct drm_framebuffer fb;
@@ -104,7 +108,8 @@ bool vkms_get_vblank_timestamp(struct drm_device *dev, unsigned int pipe,
 
 int vkms_output_init(struct vkms_device *vkmsdev);
 
-struct drm_plane *vkms_plane_init(struct vkms_device *vkmsdev);
+struct drm_plane *vkms_plane_init(struct vkms_device *vkmsdev,
+                                 enum drm_plane_type type);
 
 /* Gem stuff */
 struct drm_gem_object *vkms_gem_create(struct drm_device *dev,
index 901012cb1af1dfdbc29eb3bb458afe1bd0f1e68c..19f9ffcbf9eb6e1161ae7e04b269399900a5c9bb 100644 (file)
@@ -49,14 +49,20 @@ int vkms_output_init(struct vkms_device *vkmsdev)
        struct drm_connector *connector = &output->connector;
        struct drm_encoder *encoder = &output->encoder;
        struct drm_crtc *crtc = &output->crtc;
-       struct drm_plane *primary;
+       struct drm_plane *primary, *cursor = NULL;
        int ret;
 
-       primary = vkms_plane_init(vkmsdev);
+       primary = vkms_plane_init(vkmsdev, DRM_PLANE_TYPE_PRIMARY);
        if (IS_ERR(primary))
                return PTR_ERR(primary);
 
-       ret = vkms_crtc_init(dev, crtc, primary, NULL);
+       cursor = vkms_plane_init(vkmsdev, DRM_PLANE_TYPE_CURSOR);
+       if (IS_ERR(cursor)) {
+               ret = PTR_ERR(cursor);
+               goto err_cursor;
+       }
+
+       ret = vkms_crtc_init(dev, crtc, primary, cursor);
        if (ret)
                goto err_crtc;
 
@@ -106,6 +112,10 @@ err_connector:
        drm_crtc_cleanup(crtc);
 
 err_crtc:
+       drm_plane_cleanup(cursor);
+
+err_cursor:
        drm_plane_cleanup(primary);
+
        return ret;
 }
index c91661631c76ab091ac794c7c93359c5b3e5ecf2..428247d403dce9308c46eafb6ade1db5da01d801 100644 (file)
@@ -81,8 +81,8 @@ static const struct drm_plane_funcs vkms_plane_funcs = {
        .atomic_destroy_state   = vkms_plane_destroy_state,
 };
 
-static void vkms_primary_plane_update(struct drm_plane *plane,
-                                     struct drm_plane_state *old_state)
+static void vkms_plane_atomic_update(struct drm_plane *plane,
+                                    struct drm_plane_state *old_state)
 {
        struct vkms_plane_state *vkms_plane_state;
        struct vkms_crc_data *crc_data;
@@ -101,6 +101,7 @@ static int vkms_plane_atomic_check(struct drm_plane *plane,
                                   struct drm_plane_state *state)
 {
        struct drm_crtc_state *crtc_state;
+       bool can_position = false;
        int ret;
 
        if (!state->fb | !state->crtc)
@@ -110,15 +111,18 @@ static int vkms_plane_atomic_check(struct drm_plane *plane,
        if (IS_ERR(crtc_state))
                return PTR_ERR(crtc_state);
 
+       if (plane->type == DRM_PLANE_TYPE_CURSOR)
+               can_position = true;
+
        ret = drm_atomic_helper_check_plane_state(state, crtc_state,
                                                  DRM_PLANE_HELPER_NO_SCALING,
                                                  DRM_PLANE_HELPER_NO_SCALING,
-                                                 false, true);
+                                                 can_position, true);
        if (ret != 0)
                return ret;
 
        /* for now primary plane must be visible and full screen */
-       if (!state->visible)
+       if (!state->visible && !can_position)
                return -EINVAL;
 
        return 0;
@@ -156,15 +160,17 @@ static void vkms_cleanup_fb(struct drm_plane *plane,
 }
 
 static const struct drm_plane_helper_funcs vkms_primary_helper_funcs = {
-       .atomic_update          = vkms_primary_plane_update,
+       .atomic_update          = vkms_plane_atomic_update,
        .atomic_check           = vkms_plane_atomic_check,
        .prepare_fb             = vkms_prepare_fb,
        .cleanup_fb             = vkms_cleanup_fb,
 };
 
-struct drm_plane *vkms_plane_init(struct vkms_device *vkmsdev)
+struct drm_plane *vkms_plane_init(struct vkms_device *vkmsdev,
+                                 enum drm_plane_type type)
 {
        struct drm_device *dev = &vkmsdev->drm;
+       const struct drm_plane_helper_funcs *funcs;
        struct drm_plane *plane;
        const u32 *formats;
        int ret, nformats;
@@ -173,19 +179,26 @@ struct drm_plane *vkms_plane_init(struct vkms_device *vkmsdev)
        if (!plane)
                return ERR_PTR(-ENOMEM);
 
-       formats = vkms_formats;
-       nformats = ARRAY_SIZE(vkms_formats);
+       if (type == DRM_PLANE_TYPE_CURSOR) {
+               formats = vkms_cursor_formats;
+               nformats = ARRAY_SIZE(vkms_cursor_formats);
+               funcs = &vkms_primary_helper_funcs;
+       } else {
+               formats = vkms_formats;
+               nformats = ARRAY_SIZE(vkms_formats);
+               funcs = &vkms_primary_helper_funcs;
+       }
 
        ret = drm_universal_plane_init(dev, plane, 0,
                                       &vkms_plane_funcs,
                                       formats, nformats,
-                                      NULL, DRM_PLANE_TYPE_PRIMARY, NULL);
+                                      NULL, type, NULL);
        if (ret) {
                kfree(plane);
                return ERR_PTR(ret);
        }
 
-       drm_plane_helper_add(plane, &vkms_primary_helper_funcs);
+       drm_plane_helper_add(plane, funcs);
 
        return plane;
 }