mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2026-05-16 11:21:26 -04:00
drm: Add CRTC background color property
Some display controllers can be hardware programmed to show non-black colors for pixels that are either not covered by any plane or are exposed through transparent regions of higher planes. This feature can help reduce memory bandwidth usage, e.g. in compositors managing a UI with a solid background color while using smaller planes to render the remaining content. To support this capability, introduce the BACKGROUND_COLOR standard DRM mode property, which can be attached to a CRTC through the drm_crtc_attach_background_color_property() helper function. Additionally, define a 64-bit ARGB format value to be built with the help of a couple of dedicated DRM_ARGB64_PREP*() helpers. Individual color components can be extracted with desired precision using the corresponding DRM_ARGB64_GET*() macros. Co-developed-by: Matt Roper <matthew.d.roper@intel.com> Signed-off-by: Matt Roper <matthew.d.roper@intel.com> Reviewed-by: Nícolas F. R. A. Prado <nfraprado@collabora.com> Tested-by: Diederik de Haas <diederik@cknow-tech.com> Signed-off-by: Cristian Ciocaltea <cristian.ciocaltea@collabora.com> Link: https://patch.msgid.link/20260303-rk3588-bgcolor-v8-2-fee377037ad1@collabora.com Signed-off-by: Daniel Stone <daniels@collabora.com>
This commit is contained in:
committed by
Daniel Stone
parent
de9e2b3d88
commit
4c684596cd
@@ -27,6 +27,9 @@
|
||||
#ifndef _DRM_MODE_H
|
||||
#define _DRM_MODE_H
|
||||
|
||||
#include <linux/bits.h>
|
||||
#include <linux/const.h>
|
||||
|
||||
#include "drm.h"
|
||||
|
||||
#if defined(__cplusplus)
|
||||
@@ -1549,6 +1552,83 @@ struct drm_mode_closefb {
|
||||
__u32 pad;
|
||||
};
|
||||
|
||||
/*
|
||||
* Put 16-bit ARGB values into a standard 64-bit representation that can be
|
||||
* used for ioctl parameters, inter-driver communication, etc.
|
||||
*
|
||||
* If the component values being provided contain less than 16 bits of
|
||||
* precision, use a conversion ratio to get a better color approximation.
|
||||
* The ratio is computed as (2^16 - 1) / (2^bpc - 1), where bpc and 16 are
|
||||
* the input and output precision, respectively.
|
||||
* Also note bpc must be greater than 0.
|
||||
*/
|
||||
#define __DRM_ARGB64_PREP(c, shift) \
|
||||
(((__u64)(c) & __GENMASK(15, 0)) << (shift))
|
||||
|
||||
#define __DRM_ARGB64_PREP_BPC(c, shift, bpc) \
|
||||
({ \
|
||||
__u16 mask = __GENMASK((bpc) - 1, 0); \
|
||||
__u16 conv = __KERNEL_DIV_ROUND_CLOSEST((mask & (c)) * \
|
||||
__GENMASK(15, 0), mask);\
|
||||
__DRM_ARGB64_PREP(conv, shift); \
|
||||
})
|
||||
|
||||
#define DRM_ARGB64_PREP(alpha, red, green, blue) \
|
||||
( \
|
||||
__DRM_ARGB64_PREP(alpha, 48) | \
|
||||
__DRM_ARGB64_PREP(red, 32) | \
|
||||
__DRM_ARGB64_PREP(green, 16) | \
|
||||
__DRM_ARGB64_PREP(blue, 0) \
|
||||
)
|
||||
|
||||
#define DRM_ARGB64_PREP_BPC(alpha, red, green, blue, bpc) \
|
||||
({ \
|
||||
__typeof__(bpc) __bpc = bpc; \
|
||||
__DRM_ARGB64_PREP_BPC(alpha, 48, __bpc) | \
|
||||
__DRM_ARGB64_PREP_BPC(red, 32, __bpc) | \
|
||||
__DRM_ARGB64_PREP_BPC(green, 16, __bpc) | \
|
||||
__DRM_ARGB64_PREP_BPC(blue, 0, __bpc); \
|
||||
})
|
||||
|
||||
/*
|
||||
* Extract the specified color component from a standard 64-bit ARGB value.
|
||||
*
|
||||
* If the requested precision is less than 16 bits, make use of a conversion
|
||||
* ratio calculated as (2^bpc - 1) / (2^16 - 1), where bpc and 16 are the
|
||||
* output and input precision, respectively.
|
||||
*
|
||||
* If speed is more important than accuracy, use DRM_ARGB64_GET*_BPCS()
|
||||
* instead of DRM_ARGB64_GET*_BPC() in order to replace the expensive
|
||||
* division with a simple bit right-shift operation.
|
||||
*/
|
||||
#define __DRM_ARGB64_GET(c, shift) \
|
||||
((__u16)(((__u64)(c) >> (shift)) & __GENMASK(15, 0)))
|
||||
|
||||
#define __DRM_ARGB64_GET_BPC(c, shift, bpc) \
|
||||
({ \
|
||||
__u16 comp = __DRM_ARGB64_GET(c, shift); \
|
||||
__KERNEL_DIV_ROUND_CLOSEST(comp * __GENMASK((bpc) - 1, 0), \
|
||||
__GENMASK(15, 0)); \
|
||||
})
|
||||
|
||||
#define __DRM_ARGB64_GET_BPCS(c, shift, bpc) \
|
||||
(__DRM_ARGB64_GET(c, shift) >> (16 - (bpc)))
|
||||
|
||||
#define DRM_ARGB64_GETA(c) __DRM_ARGB64_GET(c, 48)
|
||||
#define DRM_ARGB64_GETR(c) __DRM_ARGB64_GET(c, 32)
|
||||
#define DRM_ARGB64_GETG(c) __DRM_ARGB64_GET(c, 16)
|
||||
#define DRM_ARGB64_GETB(c) __DRM_ARGB64_GET(c, 0)
|
||||
|
||||
#define DRM_ARGB64_GETA_BPC(c, bpc) __DRM_ARGB64_GET_BPC(c, 48, bpc)
|
||||
#define DRM_ARGB64_GETR_BPC(c, bpc) __DRM_ARGB64_GET_BPC(c, 32, bpc)
|
||||
#define DRM_ARGB64_GETG_BPC(c, bpc) __DRM_ARGB64_GET_BPC(c, 16, bpc)
|
||||
#define DRM_ARGB64_GETB_BPC(c, bpc) __DRM_ARGB64_GET_BPC(c, 0, bpc)
|
||||
|
||||
#define DRM_ARGB64_GETA_BPCS(c, bpc) __DRM_ARGB64_GET_BPCS(c, 48, bpc)
|
||||
#define DRM_ARGB64_GETR_BPCS(c, bpc) __DRM_ARGB64_GET_BPCS(c, 32, bpc)
|
||||
#define DRM_ARGB64_GETG_BPCS(c, bpc) __DRM_ARGB64_GET_BPCS(c, 16, bpc)
|
||||
#define DRM_ARGB64_GETB_BPCS(c, bpc) __DRM_ARGB64_GET_BPCS(c, 0, bpc)
|
||||
|
||||
#if defined(__cplusplus)
|
||||
}
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user