--- include/drm/drm.h | 7 +- include/drm/drm_mode.h | 33 +++++++---- xf86drmMode.c | 148 ++++++++++++++++++++++++++++++++++++++++++++++++ xf86drmMode.h | 29 +++++++++ 4 files changed, 201 insertions(+), 16 deletions(-)
diff --git a/include/drm/drm.h b/include/drm/drm.h index cd384f2..bb2dea8 100644 --- a/include/drm/drm.h +++ b/include/drm/drm.h @@ -718,9 +718,10 @@ struct drm_get_cap { #define DRM_IOCTL_MODE_CREATE_DUMB DRM_IOWR(0xB2, struct drm_mode_create_dumb) #define DRM_IOCTL_MODE_MAP_DUMB DRM_IOWR(0xB3, struct drm_mode_map_dumb) #define DRM_IOCTL_MODE_DESTROY_DUMB DRM_IOWR(0xB4, struct drm_mode_destroy_dumb) -#define DRM_IOCTL_MODE_GETOVERLAYRESOURCES DRM_IOWR(0xB5, struct drm_mode_get_overlay_res) -#define DRM_IOCTL_MODE_GETOVERLAY DRM_IOWR(0xB6, struct drm_mode_get_overlay) -#define DRM_IOCTL_MODE_SETOVERLAY DRM_IOWR(0xB7, struct drm_mode_set_overlay) +#define DRM_IOCTL_MODE_GETPLANERESOURCES DRM_IOWR(0xB5, struct drm_mode_get_plane_res) +#define DRM_IOCTL_MODE_GETPLANE DRM_IOWR(0xB6, struct drm_mode_get_plane) +#define DRM_IOCTL_MODE_SETPLANE DRM_IOWR(0xB7, struct drm_mode_set_plane) +#define DRM_IOCTL_MODE_ADDFB2 DRM_IOWR(0xB8, struct drm_mode_fb_cmd2) /** * Device specific ioctls should only be in their respective headers diff --git a/include/drm/drm_mode.h b/include/drm/drm_mode.h index 349052a..4c5f01f 100644 --- a/include/drm/drm_mode.h +++ b/include/drm/drm_mode.h @@ -120,14 +120,9 @@ struct drm_mode_crtc { struct drm_mode_modeinfo mode; }; -#define DRM_MODE_OVERLAY_FORMAT_YUV422 1 /* YUV 4:2:2 packed */ -#define DRM_MODE_OVERLAY_FORMAT_RGBX101010 2 /* RGB 10bpc, ign. alpha */ -#define DRM_MODE_OVERLAY_FORMAT_RGBX888 3 /* Standard x:8:8:8 RGB */ -#define DRM_MODE_OVERLAY_FORMAT_RGBX161616 4 /* x:16:16:16 float RGB */ - -/* Overlays blend with or override other bits on the CRTC */ -struct drm_mode_set_overlay { - __u32 overlay_id; +/* Planes blend with or override other bits on the CRTC */ +struct drm_mode_set_plane { + __u32 plane_id; __u32 crtc_id; __u32 fb_id; /* contains surface format type */ @@ -137,9 +132,9 @@ struct drm_mode_set_overlay { /* FIXME: color key/mask, scaling, z-order, other? */ }; -struct drm_mode_get_overlay { +struct drm_mode_get_plane { __u64 format_type_ptr; - __u32 overlay_id; + __u32 plane_id; __u32 crtc_id; __u32 fb_id; @@ -154,9 +149,9 @@ struct drm_mode_get_overlay { }; -struct drm_mode_get_overlay_res { - __u64 overlay_id_ptr; - __u32 count_overlays; +struct drm_mode_get_plane_res { + __u64 plane_id_ptr; + __u32 count_planes; }; #define DRM_MODE_ENCODER_NONE 0 @@ -268,6 +263,18 @@ struct drm_mode_fb_cmd { __u32 handle; }; +/* For addfb2 ioctl, contains format info */ +struct drm_mode_fb_cmd2 { + __u32 fb_id; + __u32 width, height; + __u32 pitch; + __u32 bpp; + __u32 depth; + __u32 pixel_format; /* fourcc code from videodev2.h */ + /* driver specific handle */ + __u32 handle; +}; + #define DRM_MODE_FB_DIRTY_ANNOTATE_COPY 0x01 #define DRM_MODE_FB_DIRTY_ANNOTATE_FILL 0x02 #define DRM_MODE_FB_DIRTY_FLAGS 0x03 diff --git a/xf86drmMode.c b/xf86drmMode.c index 0d268fc..cf62412 100644 --- a/xf86drmMode.c +++ b/xf86drmMode.c @@ -255,6 +255,28 @@ int drmModeAddFB(int fd, uint32_t width, uint32_t height, uint8_t depth, return 0; } +int drmModeAddFB2(int fd, uint32_t width, uint32_t height, + uint32_t pixel_format, uint8_t depth, uint8_t bpp, + uint32_t pitch, uint32_t bo_handle, uint32_t *buf_id) +{ + struct drm_mode_fb_cmd2 f; + int ret; + + f.width = width; + f.height = height; + f.pitch = pitch; + f.bpp = bpp; + f.depth = depth; + f.pixel_format = pixel_format; + f.handle = bo_handle; + + if ((ret = DRM_IOCTL(fd, DRM_IOCTL_MODE_ADDFB2, &f))) + return ret; + + *buf_id = f.fb_id; + return 0; +} + int drmModeRmFB(int fd, uint32_t bufferId) { return DRM_IOCTL(fd, DRM_IOCTL_MODE_RMFB, &bufferId); @@ -806,3 +828,129 @@ int drmModePageFlip(int fd, uint32_t crtc_id, uint32_t fb_id, return DRM_IOCTL(fd, DRM_IOCTL_MODE_PAGE_FLIP, &flip); } + +int drmModeSetPlane(int fd, uint32_t plane_id, uint32_t crtc_id, + uint32_t fb_id, uint32_t crtc_x, uint32_t crtc_y, + uint32_t x, uint32_t y) + +{ + struct drm_mode_set_plane s; + + s.plane_id = plane_id; + s.crtc_id = crtc_id; + s.fb_id = fb_id; + s.crtc_x = crtc_x; + s.crtc_y = crtc_y; + s.x = x; + s.y = y; + + return DRM_IOCTL(fd, DRM_IOCTL_MODE_SETPLANE, &s); +} + + +drmModePlanePtr drmModeGetPlane(int fd, uint32_t plane_id) +{ + struct drm_mode_get_plane ovr, counts; + drmModePlanePtr r = 0; + +retry: + memset(&ovr, 0, sizeof(struct drm_mode_get_plane)); + ovr.plane_id = plane_id; + if (drmIoctl(fd, DRM_IOCTL_MODE_GETPLANE, &ovr)) + return 0; + + counts = ovr; + + if (ovr.count_format_types) { + ovr.format_type_ptr = VOID2U64(drmMalloc(ovr.count_format_types * + sizeof(uint32_t))); + if (!ovr.format_type_ptr) + goto err_allocs; + } + + if (drmIoctl(fd, DRM_IOCTL_MODE_GETPLANE, &ovr)) + goto err_allocs; + + if (counts.count_format_types < ovr.count_format_types) { + drmFree(U642VOID(ovr.format_type_ptr)); + goto retry; + } + + if (!(r = drmMalloc(sizeof(*r)))) + goto err_allocs; + + r->count_formats = ovr.count_format_types; + r->plane_id = ovr.plane_id; + r->crtc_id = ovr.crtc_id; + r->fb_id = ovr.fb_id; + r->crtc_x = ovr.crtc_x; + r->crtc_y = ovr.crtc_y; + r->x = ovr.x; + r->y = ovr.y; + r->possible_crtcs = ovr.possible_crtcs; + r->gamma_size = ovr.gamma_size; + r->formats = drmAllocCpy(U642VOID(ovr.format_type_ptr), + ovr.count_format_types, sizeof(uint32_t)); + if (ovr.count_format_types && !r->formats) { + drmFree(r->formats); + r = 0; + } + +err_allocs: + drmFree(U642VOID(ovr.format_type_ptr)); + + return r; +} + +void drmModeFreePlane(drmModePlanePtr ptr) +{ + if (!ptr) + return; + + drmFree(ptr->formats); + drmFree(ptr); +} + +drmModePlaneResPtr drmModeGetPlaneResources(int fd) +{ + struct drm_mode_get_plane_res res, counts; + drmModePlaneResPtr r = 0; + +retry: + memset(&res, 0, sizeof(struct drm_mode_get_plane_res)); + if (drmIoctl(fd, DRM_IOCTL_MODE_GETPLANERESOURCES, &res)) + return 0; + + counts = res; + + if (res.count_planes) { + res.plane_id_ptr = VOID2U64(drmMalloc(res.count_planes * + sizeof(uint32_t))); + if (!res.plane_id_ptr) + goto err_allocs; + } + + if (drmIoctl(fd, DRM_IOCTL_MODE_GETPLANERESOURCES, &res)) + goto err_allocs; + + if (counts.count_planes < res.count_planes) { + drmFree(U642VOID(res.plane_id_ptr)); + goto retry; + } + + if (!(r = drmMalloc(sizeof(*r)))) + goto err_allocs; + + r->count_planes = res.count_planes; + r->planes = drmAllocCpy(U642VOID(res.plane_id_ptr), + res.count_planes, sizeof(uint32_t)); + if (res.count_planes && !r->planes) { + drmFree(r->planes); + r = 0; + } + +err_allocs: + drmFree(U642VOID(res.plane_id_ptr)); + + return r; +} diff --git a/xf86drmMode.h b/xf86drmMode.h index ee7c454..5d36ba5 100644 --- a/xf86drmMode.h +++ b/xf86drmMode.h @@ -33,6 +33,7 @@ * */ +#include <linux/videodev2.h> #include <drm.h> /* @@ -274,7 +275,25 @@ typedef struct _drmModeConnector { uint32_t *encoders; /**< List of encoder ids */ } drmModeConnector, *drmModeConnectorPtr; +typedef struct _drmModePlane { + uint32_t count_formats; + uint32_t *formats; + uint32_t plane_id; + uint32_t crtc_id; + uint32_t fb_id; + + uint32_t crtc_x, crtc_y; + uint32_t x, y; + + uint32_t possible_crtcs; + uint32_t gamma_size; +} drmModePlane, *drmModePlanePtr; + +typedef struct _drmModePlaneRes { + uint32_t count_planes; + uint32_t *planes; +} drmModePlaneRes, *drmModePlaneResPtr; extern void drmModeFreeModeInfo( drmModeModeInfoPtr ptr ); extern void drmModeFreeResources( drmModeResPtr ptr ); @@ -282,6 +301,7 @@ extern void drmModeFreeFB( drmModeFBPtr ptr ); extern void drmModeFreeCrtc( drmModeCrtcPtr ptr ); extern void drmModeFreeConnector( drmModeConnectorPtr ptr ); extern void drmModeFreeEncoder( drmModeEncoderPtr ptr ); +extern void drmModeFreePlane( drmModePlanePtr ptr ); /** * Retrives all of the resources associated with a card. @@ -303,6 +323,10 @@ extern drmModeFBPtr drmModeGetFB(int fd, uint32_t bufferId); extern int drmModeAddFB(int fd, uint32_t width, uint32_t height, uint8_t depth, uint8_t bpp, uint32_t pitch, uint32_t bo_handle, uint32_t *buf_id); +/* ...with a specific pixel format */ +extern int drmModeAddFB2(int fd, uint32_t width, uint32_t height, + uint32_t pixel_format, uint8_t depth, uint8_t bpp, + uint32_t pitch, uint32_t bo_handle, uint32_t *buf_id); /** * Destroies the given framebuffer. */ @@ -386,3 +410,8 @@ extern int drmModeCrtcGetGamma(int fd, uint32_t crtc_id, uint32_t size, uint16_t *red, uint16_t *green, uint16_t *blue); extern int drmModePageFlip(int fd, uint32_t crtc_id, uint32_t fb_id, uint32_t flags, void *user_data); +extern drmModePlaneResPtr drmModeGetPlaneResources(int fd); +extern drmModePlanePtr drmModeGetPlane(int fd, uint32_t plane_id); +extern int drmModeSetPlane(int fd, uint32_t plane_id, uint32_t crtc_id, + uint32_t fb_id, uint32_t crtc_x, uint32_t crtc_y, + uint32_t x, uint32_t y); -- 1.7.4.1