mirror of
https://github.com/archr-linux/Arch-R.git
synced 2026-03-31 14:41:55 -07:00
Merge pull request #4250 from jernejsk/colours
Allwinner: Linux: Improve colour management
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@@ -555,22 +555,33 @@ index dff27934287c..c922639e25eb 100644
|
||||
|
||||
ddc_node = of_parse_phandle(np, "ddc-i2c-bus", 0);
|
||||
|
||||
From 59c0e09a4133d36772397e59224fd32f1410cc26 Mon Sep 17 00:00:00 2001
|
||||
From cb6130315f4ae856051725b2de4e208ed90eb740 Mon Sep 17 00:00:00 2001
|
||||
From: Jonas Karlman <jonas@kwiboo.se>
|
||||
Date: Sun, 8 Dec 2019 23:41:44 +0000
|
||||
Subject: [PATCH] WIP: drm: dw-hdmi: do not force none scan mode
|
||||
Subject: [PATCH v2 2/4] drm/bridge: dw-hdmi: do not force "none" scan mode
|
||||
|
||||
Setting scan mode to "none" confuses some TVs like LG B8, which randomly
|
||||
change overscan percentage over time. Digital outputs like HDMI and DVI,
|
||||
handled by this controller, don't really need overscan, so we can always
|
||||
set scan mode to underscan. Actually, this is exactly what
|
||||
drm_hdmi_avi_infoframe_from_display_mode() already does, so we can just
|
||||
remove offending line.
|
||||
|
||||
Reviewed-by: Neil Armstrong <narmstrong@baylibre.com>
|
||||
Acked-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com>
|
||||
Signed-off-by: Jonas Karlman <jonas@kwiboo.se>
|
||||
[updated commit message]
|
||||
Signed-off-by: Jernej Skrabec <jernej.skrabec@siol.net>
|
||||
---
|
||||
drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 2 --
|
||||
1 file changed, 2 deletions(-)
|
||||
|
||||
diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
|
||||
index c922639e25eb..ea4f940406fc 100644
|
||||
index 24965e53d351..de2c7ec887c8 100644
|
||||
--- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
|
||||
+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
|
||||
@@ -1658,8 +1658,6 @@ static void hdmi_config_AVI(struct dw_hdmi *hdmi, struct drm_display_mode *mode)
|
||||
break;
|
||||
@@ -1654,8 +1654,6 @@ static void hdmi_config_AVI(struct dw_hdmi *hdmi, struct drm_display_mode *mode)
|
||||
HDMI_EXTENDED_COLORIMETRY_XV_YCC_601;
|
||||
}
|
||||
|
||||
- frame.scan_mode = HDMI_SCAN_MODE_NONE;
|
||||
@@ -578,4 +589,138 @@ index c922639e25eb..ea4f940406fc 100644
|
||||
/*
|
||||
* The Designware IP uses a different byte format from standard
|
||||
* AVI info frames, though generally the bits are in the correct
|
||||
--
|
||||
2.25.1
|
||||
|
||||
From 3043a1caa3f6d26128c746b991d086bbb85d50c2 Mon Sep 17 00:00:00 2001
|
||||
From: Jernej Skrabec <jernej.skrabec@siol.net>
|
||||
Date: Sat, 29 Feb 2020 16:23:38 +0100
|
||||
Subject: [PATCH v2 3/4] drm/bridge: dw-hdmi: Add support for RGB limited range
|
||||
|
||||
CEA 861 standard requestis that RGB quantization range is "limited" for
|
||||
CEA modes. Support that by adding CSC matrix which downscales values.
|
||||
|
||||
This allows proper color reproduction on TV and PC monitor at the same
|
||||
time. In future, override property can be added, like "Broadcast RGB"
|
||||
in i915 driver.
|
||||
|
||||
Signed-off-by: Jernej Skrabec <jernej.skrabec@siol.net>
|
||||
---
|
||||
drivers/gpu/drm/bridge/synopsys/dw-hdmi.c | 63 +++++++++++++++++------
|
||||
1 file changed, 46 insertions(+), 17 deletions(-)
|
||||
|
||||
diff --git a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
|
||||
index de2c7ec887c8..c8a02e5b5e1b 100644
|
||||
--- a/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
|
||||
+++ b/drivers/gpu/drm/bridge/synopsys/dw-hdmi.c
|
||||
@@ -92,6 +92,12 @@ static const u16 csc_coeff_rgb_in_eitu709[3][4] = {
|
||||
{ 0x6756, 0x78ab, 0x2000, 0x0200 }
|
||||
};
|
||||
|
||||
+static const u16 csc_coeff_rgb_full_to_rgb_limited[3][4] = {
|
||||
+ { 0x1b7c, 0x0000, 0x0000, 0x0020 },
|
||||
+ { 0x0000, 0x1b7c, 0x0000, 0x0020 },
|
||||
+ { 0x0000, 0x0000, 0x1b7c, 0x0020 }
|
||||
+};
|
||||
+
|
||||
struct hdmi_vmode {
|
||||
bool mdataenablepolarity;
|
||||
|
||||
@@ -109,6 +115,7 @@ struct hdmi_data_info {
|
||||
unsigned int pix_repet_factor;
|
||||
unsigned int hdcp_enable;
|
||||
struct hdmi_vmode video_mode;
|
||||
+ bool rgb_limited_range;
|
||||
};
|
||||
|
||||
struct dw_hdmi_i2c {
|
||||
@@ -956,7 +963,11 @@ static void hdmi_video_sample(struct dw_hdmi *hdmi)
|
||||
|
||||
static int is_color_space_conversion(struct dw_hdmi *hdmi)
|
||||
{
|
||||
- return hdmi->hdmi_data.enc_in_bus_format != hdmi->hdmi_data.enc_out_bus_format;
|
||||
+ return (hdmi->hdmi_data.enc_in_bus_format !=
|
||||
+ hdmi->hdmi_data.enc_out_bus_format) ||
|
||||
+ (hdmi_bus_fmt_is_rgb(hdmi->hdmi_data.enc_in_bus_format) &&
|
||||
+ hdmi_bus_fmt_is_rgb(hdmi->hdmi_data.enc_out_bus_format) &&
|
||||
+ hdmi->hdmi_data.rgb_limited_range);
|
||||
}
|
||||
|
||||
static int is_color_space_decimation(struct dw_hdmi *hdmi)
|
||||
@@ -986,25 +997,27 @@ static int is_color_space_interpolation(struct dw_hdmi *hdmi)
|
||||
static void dw_hdmi_update_csc_coeffs(struct dw_hdmi *hdmi)
|
||||
{
|
||||
const u16 (*csc_coeff)[3][4] = &csc_coeff_default;
|
||||
+ bool is_input_rgb, is_output_rgb;
|
||||
unsigned i;
|
||||
u32 csc_scale = 1;
|
||||
|
||||
- if (is_color_space_conversion(hdmi)) {
|
||||
- if (hdmi_bus_fmt_is_rgb(hdmi->hdmi_data.enc_out_bus_format)) {
|
||||
- if (hdmi->hdmi_data.enc_out_encoding ==
|
||||
- V4L2_YCBCR_ENC_601)
|
||||
- csc_coeff = &csc_coeff_rgb_out_eitu601;
|
||||
- else
|
||||
- csc_coeff = &csc_coeff_rgb_out_eitu709;
|
||||
- } else if (hdmi_bus_fmt_is_rgb(
|
||||
- hdmi->hdmi_data.enc_in_bus_format)) {
|
||||
- if (hdmi->hdmi_data.enc_out_encoding ==
|
||||
- V4L2_YCBCR_ENC_601)
|
||||
- csc_coeff = &csc_coeff_rgb_in_eitu601;
|
||||
- else
|
||||
- csc_coeff = &csc_coeff_rgb_in_eitu709;
|
||||
- csc_scale = 0;
|
||||
- }
|
||||
+ is_input_rgb = hdmi_bus_fmt_is_rgb(hdmi->hdmi_data.enc_in_bus_format);
|
||||
+ is_output_rgb = hdmi_bus_fmt_is_rgb(hdmi->hdmi_data.enc_out_bus_format);
|
||||
+
|
||||
+ if (!is_input_rgb && is_output_rgb) {
|
||||
+ if (hdmi->hdmi_data.enc_out_encoding == V4L2_YCBCR_ENC_601)
|
||||
+ csc_coeff = &csc_coeff_rgb_out_eitu601;
|
||||
+ else
|
||||
+ csc_coeff = &csc_coeff_rgb_out_eitu709;
|
||||
+ } else if (is_input_rgb && !is_output_rgb) {
|
||||
+ if (hdmi->hdmi_data.enc_out_encoding == V4L2_YCBCR_ENC_601)
|
||||
+ csc_coeff = &csc_coeff_rgb_in_eitu601;
|
||||
+ else
|
||||
+ csc_coeff = &csc_coeff_rgb_in_eitu709;
|
||||
+ csc_scale = 0;
|
||||
+ } else if (is_input_rgb && is_output_rgb &&
|
||||
+ hdmi->hdmi_data.rgb_limited_range) {
|
||||
+ csc_coeff = &csc_coeff_rgb_full_to_rgb_limited;
|
||||
}
|
||||
|
||||
/* The CSC registers are sequential, alternating MSB then LSB */
|
||||
@@ -1614,6 +1627,18 @@ static void hdmi_config_AVI(struct dw_hdmi *hdmi, struct drm_display_mode *mode)
|
||||
drm_hdmi_avi_infoframe_from_display_mode(&frame,
|
||||
&hdmi->connector, mode);
|
||||
|
||||
+ if (hdmi_bus_fmt_is_rgb(hdmi->hdmi_data.enc_out_bus_format)) {
|
||||
+ drm_hdmi_avi_infoframe_quant_range(&frame, &hdmi->connector,
|
||||
+ mode,
|
||||
+ hdmi->hdmi_data.rgb_limited_range ?
|
||||
+ HDMI_QUANTIZATION_RANGE_LIMITED :
|
||||
+ HDMI_QUANTIZATION_RANGE_FULL);
|
||||
+ } else {
|
||||
+ frame.quantization_range = HDMI_QUANTIZATION_RANGE_DEFAULT;
|
||||
+ frame.ycc_quantization_range =
|
||||
+ HDMI_YCC_QUANTIZATION_RANGE_LIMITED;
|
||||
+ }
|
||||
+
|
||||
if (hdmi_bus_fmt_is_yuv444(hdmi->hdmi_data.enc_out_bus_format))
|
||||
frame.colorspace = HDMI_COLORSPACE_YUV444;
|
||||
else if (hdmi_bus_fmt_is_yuv422(hdmi->hdmi_data.enc_out_bus_format))
|
||||
@@ -2099,6 +2124,10 @@ static int dw_hdmi_setup(struct dw_hdmi *hdmi, struct drm_display_mode *mode)
|
||||
/* TOFIX: Default to RGB888 output format */
|
||||
hdmi->hdmi_data.enc_out_bus_format = MEDIA_BUS_FMT_RGB888_1X24;
|
||||
|
||||
+ hdmi->hdmi_data.rgb_limited_range = hdmi->sink_is_hdmi &&
|
||||
+ drm_default_rgb_quant_range(mode) ==
|
||||
+ HDMI_QUANTIZATION_RANGE_LIMITED;
|
||||
+
|
||||
hdmi->hdmi_data.pix_repet_factor = 0;
|
||||
hdmi->hdmi_data.hdcp_enable = 0;
|
||||
hdmi->hdmi_data.video_mode.mdataenablepolarity = true;
|
||||
--
|
||||
2.25.1
|
||||
|
||||
|
||||
@@ -1,43 +0,0 @@
|
||||
From c8217462c6c143a9fada595bf3e34af83eb15f87 Mon Sep 17 00:00:00 2001
|
||||
From: Jernej Skrabec <jernej.skrabec@siol.net>
|
||||
Date: Thu, 27 Jun 2019 21:50:16 +0200
|
||||
Subject: [PATCH 4/4] HACK: Force full range
|
||||
|
||||
Signed-off-by: Jernej Skrabec <jernej.skrabec@siol.net>
|
||||
---
|
||||
drivers/gpu/drm/sun4i/sun8i_csc.c | 8 ++++----
|
||||
1 file changed, 4 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/drivers/gpu/drm/sun4i/sun8i_csc.c b/drivers/gpu/drm/sun4i/sun8i_csc.c
|
||||
index 70c792d052fe..7b60fce1a8c6 100644
|
||||
--- a/drivers/gpu/drm/sun4i/sun8i_csc.c
|
||||
+++ b/drivers/gpu/drm/sun4i/sun8i_csc.c
|
||||
@@ -160,10 +160,10 @@ static void sun8i_csc_set_coefficients(struct regmap *map, u32 base,
|
||||
|
||||
switch (mode) {
|
||||
case SUN8I_CSC_MODE_YUV2RGB:
|
||||
- table = yuv2rgb[range][encoding];
|
||||
+ table = yuv2rgb[DRM_COLOR_YCBCR_FULL_RANGE][encoding];
|
||||
break;
|
||||
case SUN8I_CSC_MODE_YVU2RGB:
|
||||
- table = yvu2rgb[range][encoding];
|
||||
+ table = yvu2rgb[DRM_COLOR_YCBCR_FULL_RANGE][encoding];
|
||||
break;
|
||||
default:
|
||||
DRM_WARN("Wrong CSC mode specified.\n");
|
||||
@@ -184,10 +184,10 @@ static void sun8i_de3_ccsc_set_coefficients(struct regmap *map, int layer,
|
||||
|
||||
switch (mode) {
|
||||
case SUN8I_CSC_MODE_YUV2RGB:
|
||||
- table = yuv2rgb_de3[range][encoding];
|
||||
+ table = yuv2rgb_de3[DRM_COLOR_YCBCR_FULL_RANGE][encoding];
|
||||
break;
|
||||
case SUN8I_CSC_MODE_YVU2RGB:
|
||||
- table = yvu2rgb_de3[range][encoding];
|
||||
+ table = yvu2rgb_de3[DRM_COLOR_YCBCR_FULL_RANGE][encoding];
|
||||
break;
|
||||
default:
|
||||
DRM_WARN("Wrong CSC mode specified.\n");
|
||||
--
|
||||
2.22.0
|
||||
|
||||
Reference in New Issue
Block a user