Re: [PATCH V9 26/43] drm/amd/display: Add support for sRGB EOTF in DEGAM block
On Mon, 12 May 2025 15:50:17 -0300 Melissa Wen wrote: > On 04/29, Alex Hung wrote: > > Expose one 1D curve colorop with support for > > DRM_COLOROP_1D_CURVE_SRGB_EOTF and program HW to perform > > the sRGB transform when the colorop is not in bypass. > > > > With this change the following IGT test passes: > > kms_colorop --run plane-XR30-XR30-srgb_eotf > > > > The color pipeline now consists of a single colorop: > > 1. 1D curve colorop w/ sRGB EOTF > > > > Signed-off-by: Alex Hung > > Co-developed-by: Harry Wentland > > Signed-off-by: Harry Wentland > > Reviewed-by: Daniel Stone > > --- > > V9: > > - Update function names by _plane_ (Chaitanya Kumar Borah) > > - Update replace cleanup code by drm_colorop_pipeline_destroy (Simon Ser) > > > > v8: > > - Fix incorrect && by || in __set_colorop_in_tf_1d_curve (Leo Li) > > > > v7: > > - Fix checkpatch warnings > > - Change switch "{ }" position > > - Delete double ";" > > - Delete "{ }" for single-line if-statement > > - Add a new line at EOF > > - Change SPDX-License-Identifier: GPL-2.0+ from // to /* */ > > > > v6: > > - cleanup if colorop alloc or init fails > > > > .../gpu/drm/amd/display/amdgpu_dm/Makefile| 3 +- > > .../amd/display/amdgpu_dm/amdgpu_dm_color.c | 86 +++ > > .../amd/display/amdgpu_dm/amdgpu_dm_colorop.c | 69 +++ > > .../amd/display/amdgpu_dm/amdgpu_dm_colorop.h | 34 > > .../amd/display/amdgpu_dm/amdgpu_dm_plane.c | 10 +++ > > 5 files changed, 201 insertions(+), 1 deletion(-) > > create mode 100644 > > drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_colorop.c > > create mode 100644 > > drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_colorop.h > > > > diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > b/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > index ab2a97e354da..46158d67ab12 100644 > > --- a/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > @@ -38,7 +38,8 @@ AMDGPUDM = \ > > amdgpu_dm_pp_smu.o \ > > amdgpu_dm_psr.o \ > > amdgpu_dm_replay.o \ > > - amdgpu_dm_wb.o > > + amdgpu_dm_wb.o \ > > + amdgpu_dm_colorop.o > > > > ifdef CONFIG_DRM_AMD_DC_FP > > AMDGPUDM += dc_fpu.o > > diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > index ebabfe3a512f..0b513ab5050f 100644 > > --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > @@ -668,6 +668,18 @@ amdgpu_tf_to_dc_tf(enum amdgpu_transfer_function tf) > > } > > } > > > > +static enum dc_transfer_func_predefined > > +amdgpu_colorop_tf_to_dc_tf(enum drm_colorop_curve_1d_type tf) > > +{ > > + switch (tf) { > > + case DRM_COLOROP_1D_CURVE_SRGB_EOTF: > > + case DRM_COLOROP_1D_CURVE_SRGB_INV_EOTF: > > + return TRANSFER_FUNCTION_SRGB; > > + default: > > + return TRANSFER_FUNCTION_LINEAR; > > + } > > +} > > + > > static void __to_dc_lut3d_color(struct dc_rgb *rgb, > > const struct drm_color_lut lut, > > int bit_precision) > > @@ -1137,6 +1149,59 @@ __set_dm_plane_degamma(struct drm_plane_state > > *plane_state, > > return 0; > > } > > > > +static int > > +__set_colorop_in_tf_1d_curve(struct dc_plane_state *dc_plane_state, > > + struct drm_colorop_state *colorop_state) > > +{ > > + struct dc_transfer_func *tf = &dc_plane_state->in_transfer_func; > > + struct drm_colorop *colorop = colorop_state->colorop; > > + struct drm_device *drm = colorop->dev; > > + > > + if (colorop->type != DRM_COLOROP_1D_CURVE || > > + colorop_state->curve_1d_type != DRM_COLOROP_1D_CURVE_SRGB_EOTF) > > + return -EINVAL; > > + > > + if (colorop_state->bypass) { > > + tf->type = TF_TYPE_BYPASS; > > + tf->tf = TRANSFER_FUNCTION_LINEAR; > > + return 0; > > + } > > + > > + drm_dbg(drm, "Degamma colorop with ID: %d\n", colorop->base.id); > > + > > + tf->type = TF_TYPE_PREDEFINED; > > + tf->tf = amdgpu_colorop_tf_to_dc_tf(colorop_state->curve_1d_type); > > + > > + return 0; > > +} > > + > > +static int > > +__set_dm_plane_colorop_degamma(struct drm_plane_state *plane_state, > > + struct dc_plane_state *dc_plane_state, > > + struct drm_colorop *colorop) > > +{ > > + struct drm_colorop *old_colorop; > > + struct drm_colorop_state *colorop_state = NULL, *new_colorop_state; > > + struct drm_atomic_state *state = plane_state->state; > > + int i = 0; > > + > > + old_colorop = colorop; > > + > > + /* 1st op: 1d curve - degamma */ > > + for_each_new_colorop_in_state(state, colorop, new_colorop_state, i) { > > + if (new_colorop_state->colorop == old_colorop && > > + new_colorop_state->curve_1d_type == > > DRM_COLOROP_1D_CURVE_SRGB_EOTF) { >
Re: [PATCH V9 00/43] Color Pipeline API w/ VKMS
On 04/29, Alex Hung wrote: > This is an RFC set for a color pipeline API, along with implementations > in VKMS and amdgpu. It is tested with a set of IGT tests that can be > found at [1]. The IGT tests run a pixel-by-pixel comparison with an > allowable delta variation as the goal for these transformations is > perceptual correctness, not complete pixel accuracy. Hi, Thanks for this work. I found it very solid and well documented. The drm colorop implementation looks good to me, but I still have some questions about AMD specific bits. Patches 1, 3-13, 16, 21-23, 25, 35-41 and 43 are: Reviewed-by: Melissa Wen And I dropped some comments and questions to some AMD-specific patches. > > v5 of this patchset fleshed out documentation for colorops and the > various defines that are being introduced. > > v6 addresses a few comments from various reviewers. > > v7 simplifies 3D LUT and addresses more comments from various reviewers. > > v8 fixes typo and errors and address comments from reviewers. > > v9 refactors cleanup functions, fixes typo and errors, and addresses >comments from reviewers. > > VKMS supports two named transfer function colorops and two matrix > colorops. > > Amdgpu advertises the following pipeline for GPUs with DCN 3 or newer: > > 1. 1D Curve EOTF > 2. 3x4 CTM > 3. Multiplier > 4. 1D Curve Inverse EOTF > 5. 1D LUT > 6. 3D LUT > 7. 1D Curve EOTF > 8. 1D LUT > > The supported curves for the 1D Curve type are: > - sRGB EOTF and its inverse > - PQ EOTF, scaled to [0.0, 125.0] and its inverse > - BT.2020/BT.709 OETF and its inverse > > Note that the 1st and 5th colorops take the EOTF or Inverse > OETF while the 3rd colorop takes the Inverse EOTF or OETF. > > The 3D LUT is a 17^3 tetrahedrally interpolated LUT but the mechanism > exists for other drivers to describe their own 3D LUT capability. > > This mirrors the color pipeline used by gamescope and presented by > Melissa Wen, with the exception of the DEGAM LUT, which is not currently > used. See [1] > https://indico.freedesktop.org/event/4/contributions/186/attachments/138/218/xdc2023-TheRainbowTreasureMap-MelissaWen.pdf > > At this point we're hoping to see gamescope and kwin implementations > take shape. The existing pipeline should be enough to satisfy the > gamescope use-cases on the drm_plane. > > In order to support YUV we'll need to add COLOR_ENCODING and COLOR_RANGE > support to the color pipeline. I have sketched these out already but > don't have it all hooked up yet. This should not hinder adoption of this > API for gaming use-cases. > > We'll also want to advertise IN_FORMATS on a color pipeline as some > color pipelines won't be able to work for all IN_FORMATS on a plane. > Again, I have a sketch but no full implementation yet. This is not > currently required by the AMD color pipeline and could be added after > the merge of this set. > > VKMS patches could still be improved in a few ways, though the > payoff might be limited and I would rather focus on other work > at the moment. The most obvious thing to improve would be to > eliminate the hard-coded LUTs for identity, and sRGB, and replace > them with fixed-point math instead. > > There are plenty of things that I would like to see, but they could > be added after the merge of this patchset: > - COLOR_ENCODING and COLOR_RANGE > - IN_FORMATS for a color pipeline > - Is it possible to support HW which can't bypass entire pipeline? > - Can we do a LOAD / COMMIT model for LUTs (and other properties)? > - read-only scaling colorop which defines scaling taps and position > - named matrices, for things like converting YUV to RGB > - Add custom LUT colorops to VKMS > > IGT tests can be found at [1] or on the igt-dev mailing list. There > have been no updates since v5 and rebase on latest main is straight- > forward. > > A kernel branch can be found at [2]. > > [1] > https://gitlab.freedesktop.org/alex.hung/igt-gpu-tools/-/tree/amd-color-pipeline-v8 > [2] > https://gitlab.freedesktop.org/alex.hung/linux/-/tree/amd-color-pipeline-v9 > > v9: > - Update RFC documents for 3DLUT and fallback behaviours (Simon Ser) > - Specify colorop function names by _plane_ (Chaitanya Kumar Borah) > - Remove redundant comments (Simon Ser) > - Fix typo in commit description (Shengyu Qu) > - Move destroy and cleanup functions earlier (Simon Ser) > - Move DRM_COLOROP_1D_CURVE_BT2020_* from middle to end (Simon Ser) > - Chagne "bool allow_bypass" to "uint32_t flags" for better extensibility > (Simon Ser) > - Return a value in __set_dm_plane_colorop_3dlut > > v8: > - Change VKMS config names (Louis Chauvet) > - Remove deprecated function "drm_atomic_get_existing_colorop_state" (Louis > Chauvet) > - Remove null check in drm_colorop_set_next_property (Simon Ser) > - Remove MAX_COLOR_PIPELINES in drm (Simon Ser) > - Update kernel docs and documents for DRM_COLOROP_3D_LUT (Simon Ser) > - Add comments for dmr_color_lut (Louis Chauvet) > - Fix typos and replace D
Re: [PATCH V9 42/43] drm/amd/display: add 3D LUT colorop
On 05/12, Alex Hung wrote: > > > On 5/12/25 18:52, Melissa Wen wrote: > > On 04/29, Alex Hung wrote: > > > This adds support for a 3D LUT. > > > > > > The color pipeline now consists of the following colorops: > > > 1. 1D curve colorop > > > 2. Multiplier > > > 3. 3x4 CTM > > > 4. 1D curve colorop > > > 5. 1D LUT > > > 6. 3D LUT > > > 7. 1D curve colorop > > > 8. 1D LUT > > > > > > Signed-off-by: Alex Hung > > > Reviewed-by: Daniel Stone > > > --- > > > V9: > > > - Return a value in __set_dm_plane_colorop_3dlut > > > > > > v8: > > > - Set initialized to 0 and return when drm_lut3d_size is 0 (Harry > > > Wentland) > > > - Rework tf->type = TF_TYPE_BYPASS for shaper (Harry Wentland & Leo Li) > > > > > > v7: > > > - Simplify 3D LUT according to drm_colorop changes (Simon Ser) > > > > > > .../amd/display/amdgpu_dm/amdgpu_dm_color.c | 94 +++ > > > .../amd/display/amdgpu_dm/amdgpu_dm_colorop.c | 20 > > > 2 files changed, 114 insertions(+) > > > > > > diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > index 313716f2003f..dfdd3f557570 100644 > > > --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > @@ -1293,6 +1293,7 @@ __set_dm_plane_colorop_shaper(struct > > > drm_plane_state *plane_state, > > > struct dc_transfer_func *tf = &dc_plane_state->in_shaper_func; > > > const struct drm_color_lut *shaper_lut; > > > struct drm_device *dev = colorop->dev; > > > + bool enabled = false; > > > uint32_t shaper_size; > > > int i = 0, ret = 0; > > > @@ -1314,6 +1315,7 @@ __set_dm_plane_colorop_shaper(struct > > > drm_plane_state *plane_state, > > > ret = __set_output_tf(tf, 0, 0, false); > > > if (ret) > > > return ret; > > > + enabled = true; > > > } > > > /* 1D LUT - SHAPER LUT */ > > > @@ -1345,12 +1347,93 @@ __set_dm_plane_colorop_shaper(struct > > > drm_plane_state *plane_state, > > > ret = __set_output_tf(tf, shaper_lut, > > > shaper_size, false); > > > if (ret) > > > return ret; > > > + enabled = true; > > > } > > > } > > > + if (!enabled) > > > + tf->type = TF_TYPE_BYPASS; > > > + > > > return 0; > > > } > > > +/* __set_colorop_3dlut - set DRM 3D LUT to DC stream > > > + * @drm_lut3d: user 3D LUT > > > + * @drm_lut3d_size: size of 3D LUT > > > + * @lut3d: DC 3D LUT > > > + * > > > + * Map user 3D LUT data to DC 3D LUT and all necessary bits to program it > > > + * on DCN accordingly. > > > + */ > > > +static void __set_colorop_3dlut(const struct drm_color_lut *drm_lut3d, > > > + uint32_t drm_lut3d_size, > > > + struct dc_3dlut *lut) > > > +{ > > > + if (!drm_lut3d_size) { > > > + lut->state.bits.initialized = 0; > > > + return; > > > + } > > > + > > > + /* Only supports 17x17x17 3D LUT (12-bit) now */ > > > + lut->lut_3d.use_12bits = true; > > > + lut->lut_3d.use_tetrahedral_9 = false; > > > + > > > + lut->state.bits.initialized = 1; > > > + __drm_3dlut_to_dc_3dlut(drm_lut3d, drm_lut3d_size, &lut->lut_3d, > > > + lut->lut_3d.use_tetrahedral_9, 12); > > > + > > > +} > > > + > > > +static int > > > +__set_dm_plane_colorop_3dlut(struct drm_plane_state *plane_state, > > > + struct dc_plane_state *dc_plane_state, > > > + struct drm_colorop *colorop) > > > +{ > > > + struct drm_colorop *old_colorop; > > > + struct drm_colorop_state *colorop_state = NULL, *new_colorop_state; > > > + struct dc_transfer_func *tf = &dc_plane_state->in_shaper_func; > > > + struct drm_atomic_state *state = plane_state->state; > > > + const struct amdgpu_device *adev = drm_to_adev(colorop->dev); > > > + const struct drm_device *dev = colorop->dev; > > > + const struct drm_color_lut *lut3d; > > > + uint32_t lut3d_size; > > > + int i = 0, ret = 0; > > > + > > > + /* 3D LUT */ > > > + old_colorop = colorop; > > > + for_each_new_colorop_in_state(state, colorop, new_colorop_state, i) { > > > + if (new_colorop_state->colorop == old_colorop && > > > + new_colorop_state->colorop->type == DRM_COLOROP_3D_LUT) { > > > + colorop_state = new_colorop_state; > > > + break; > > > + } > > > + } > > > + > > > + if (colorop_state && !colorop_state->bypass && colorop->type == > > > DRM_COLOROP_3D_LUT) { > > > + if (!adev->dm.dc->caps.color.dpp.hw_3d_lut) { > > > > I wonder if this check is no longer accurate in DCN versions with MCM > > (MPC only) 3D LUT caps, such as DCN 3.2 and DCN 4.01. > > The current goal is to validate on specific fixed platforms. We will add
Re: [PATCH V9 26/43] drm/amd/display: Add support for sRGB EOTF in DEGAM block
On 05/13, Pekka Paalanen wrote: > On Mon, 12 May 2025 15:50:17 -0300 > Melissa Wen wrote: > > > On 04/29, Alex Hung wrote: > > > Expose one 1D curve colorop with support for > > > DRM_COLOROP_1D_CURVE_SRGB_EOTF and program HW to perform > > > the sRGB transform when the colorop is not in bypass. > > > > > > With this change the following IGT test passes: > > > kms_colorop --run plane-XR30-XR30-srgb_eotf > > > > > > The color pipeline now consists of a single colorop: > > > 1. 1D curve colorop w/ sRGB EOTF > > > > > > Signed-off-by: Alex Hung > > > Co-developed-by: Harry Wentland > > > Signed-off-by: Harry Wentland > > > Reviewed-by: Daniel Stone > > > --- > > > V9: > > > - Update function names by _plane_ (Chaitanya Kumar Borah) > > > - Update replace cleanup code by drm_colorop_pipeline_destroy (Simon Ser) > > > > > > v8: > > > - Fix incorrect && by || in __set_colorop_in_tf_1d_curve (Leo Li) > > > > > > v7: > > > - Fix checkpatch warnings > > > - Change switch "{ }" position > > > - Delete double ";" > > > - Delete "{ }" for single-line if-statement > > > - Add a new line at EOF > > > - Change SPDX-License-Identifier: GPL-2.0+ from // to /* */ > > > > > > v6: > > > - cleanup if colorop alloc or init fails > > > > > > .../gpu/drm/amd/display/amdgpu_dm/Makefile| 3 +- > > > .../amd/display/amdgpu_dm/amdgpu_dm_color.c | 86 +++ > > > .../amd/display/amdgpu_dm/amdgpu_dm_colorop.c | 69 +++ > > > .../amd/display/amdgpu_dm/amdgpu_dm_colorop.h | 34 > > > .../amd/display/amdgpu_dm/amdgpu_dm_plane.c | 10 +++ > > > 5 files changed, 201 insertions(+), 1 deletion(-) > > > create mode 100644 > > > drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_colorop.c > > > create mode 100644 > > > drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_colorop.h > > > > > > diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > > b/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > > index ab2a97e354da..46158d67ab12 100644 > > > --- a/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > > +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile > > > @@ -38,7 +38,8 @@ AMDGPUDM = \ > > > amdgpu_dm_pp_smu.o \ > > > amdgpu_dm_psr.o \ > > > amdgpu_dm_replay.o \ > > > - amdgpu_dm_wb.o > > > + amdgpu_dm_wb.o \ > > > + amdgpu_dm_colorop.o > > > > > > ifdef CONFIG_DRM_AMD_DC_FP > > > AMDGPUDM += dc_fpu.o > > > diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > index ebabfe3a512f..0b513ab5050f 100644 > > > --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c > > > @@ -668,6 +668,18 @@ amdgpu_tf_to_dc_tf(enum amdgpu_transfer_function tf) > > > } > > > } > > > > > > +static enum dc_transfer_func_predefined > > > +amdgpu_colorop_tf_to_dc_tf(enum drm_colorop_curve_1d_type tf) > > > +{ > > > + switch (tf) { > > > + case DRM_COLOROP_1D_CURVE_SRGB_EOTF: > > > + case DRM_COLOROP_1D_CURVE_SRGB_INV_EOTF: > > > + return TRANSFER_FUNCTION_SRGB; > > > + default: > > > + return TRANSFER_FUNCTION_LINEAR; > > > + } > > > +} > > > + > > > static void __to_dc_lut3d_color(struct dc_rgb *rgb, > > > const struct drm_color_lut lut, > > > int bit_precision) > > > @@ -1137,6 +1149,59 @@ __set_dm_plane_degamma(struct drm_plane_state > > > *plane_state, > > > return 0; > > > } > > > > > > +static int > > > +__set_colorop_in_tf_1d_curve(struct dc_plane_state *dc_plane_state, > > > +struct drm_colorop_state *colorop_state) > > > +{ > > > + struct dc_transfer_func *tf = &dc_plane_state->in_transfer_func; > > > + struct drm_colorop *colorop = colorop_state->colorop; > > > + struct drm_device *drm = colorop->dev; > > > + > > > + if (colorop->type != DRM_COLOROP_1D_CURVE || > > > + colorop_state->curve_1d_type != DRM_COLOROP_1D_CURVE_SRGB_EOTF) > > > + return -EINVAL; > > > + > > > + if (colorop_state->bypass) { > > > + tf->type = TF_TYPE_BYPASS; > > > + tf->tf = TRANSFER_FUNCTION_LINEAR; > > > + return 0; > > > + } > > > + > > > + drm_dbg(drm, "Degamma colorop with ID: %d\n", colorop->base.id); > > > + > > > + tf->type = TF_TYPE_PREDEFINED; > > > + tf->tf = amdgpu_colorop_tf_to_dc_tf(colorop_state->curve_1d_type); > > > + > > > + return 0; > > > +} > > > + > > > +static int > > > +__set_dm_plane_colorop_degamma(struct drm_plane_state *plane_state, > > > +struct dc_plane_state *dc_plane_state, > > > +struct drm_colorop *colorop) > > > +{ > > > + struct drm_colorop *old_colorop; > > > + struct drm_colorop_state *colorop_state = NULL, *new_colorop_state; > > > + struct drm_atomic_state *state = plane_state->state; > > > + int i = 0; > > > + > > > + old_colorop = colorop; > > > + > > > + /* 1st op: 1d curve - degamma */ > > > + for_each_new_coloro
Re: [PATCH V9 26/43] drm/amd/display: Add support for sRGB EOTF in DEGAM block
On 2025-05-13 11:36, Melissa Wen wrote: > On 05/13, Pekka Paalanen wrote: >> On Mon, 12 May 2025 15:50:17 -0300 >> Melissa Wen wrote: >> >>> On 04/29, Alex Hung wrote: Expose one 1D curve colorop with support for DRM_COLOROP_1D_CURVE_SRGB_EOTF and program HW to perform the sRGB transform when the colorop is not in bypass. With this change the following IGT test passes: kms_colorop --run plane-XR30-XR30-srgb_eotf The color pipeline now consists of a single colorop: 1. 1D curve colorop w/ sRGB EOTF Signed-off-by: Alex Hung Co-developed-by: Harry Wentland Signed-off-by: Harry Wentland Reviewed-by: Daniel Stone --- V9: - Update function names by _plane_ (Chaitanya Kumar Borah) - Update replace cleanup code by drm_colorop_pipeline_destroy (Simon Ser) v8: - Fix incorrect && by || in __set_colorop_in_tf_1d_curve (Leo Li) v7: - Fix checkpatch warnings - Change switch "{ }" position - Delete double ";" - Delete "{ }" for single-line if-statement - Add a new line at EOF - Change SPDX-License-Identifier: GPL-2.0+ from // to /* */ v6: - cleanup if colorop alloc or init fails .../gpu/drm/amd/display/amdgpu_dm/Makefile| 3 +- .../amd/display/amdgpu_dm/amdgpu_dm_color.c | 86 +++ .../amd/display/amdgpu_dm/amdgpu_dm_colorop.c | 69 +++ .../amd/display/amdgpu_dm/amdgpu_dm_colorop.h | 34 .../amd/display/amdgpu_dm/amdgpu_dm_plane.c | 10 +++ 5 files changed, 201 insertions(+), 1 deletion(-) create mode 100644 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_colorop.c create mode 100644 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_colorop.h diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile b/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile index ab2a97e354da..46158d67ab12 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/Makefile @@ -38,7 +38,8 @@ AMDGPUDM = \ amdgpu_dm_pp_smu.o \ amdgpu_dm_psr.o \ amdgpu_dm_replay.o \ - amdgpu_dm_wb.o + amdgpu_dm_wb.o \ + amdgpu_dm_colorop.o ifdef CONFIG_DRM_AMD_DC_FP AMDGPUDM += dc_fpu.o diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c index ebabfe3a512f..0b513ab5050f 100644 --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_color.c @@ -668,6 +668,18 @@ amdgpu_tf_to_dc_tf(enum amdgpu_transfer_function tf) } } +static enum dc_transfer_func_predefined +amdgpu_colorop_tf_to_dc_tf(enum drm_colorop_curve_1d_type tf) +{ + switch (tf) { + case DRM_COLOROP_1D_CURVE_SRGB_EOTF: + case DRM_COLOROP_1D_CURVE_SRGB_INV_EOTF: + return TRANSFER_FUNCTION_SRGB; + default: + return TRANSFER_FUNCTION_LINEAR; + } +} + static void __to_dc_lut3d_color(struct dc_rgb *rgb, const struct drm_color_lut lut, int bit_precision) @@ -1137,6 +1149,59 @@ __set_dm_plane_degamma(struct drm_plane_state *plane_state, return 0; } +static int +__set_colorop_in_tf_1d_curve(struct dc_plane_state *dc_plane_state, + struct drm_colorop_state *colorop_state) +{ + struct dc_transfer_func *tf = &dc_plane_state->in_transfer_func; + struct drm_colorop *colorop = colorop_state->colorop; + struct drm_device *drm = colorop->dev; + + if (colorop->type != DRM_COLOROP_1D_CURVE || + colorop_state->curve_1d_type != DRM_COLOROP_1D_CURVE_SRGB_EOTF) + return -EINVAL; + + if (colorop_state->bypass) { + tf->type = TF_TYPE_BYPASS; + tf->tf = TRANSFER_FUNCTION_LINEAR; + return 0; + } + + drm_dbg(drm, "Degamma colorop with ID: %d\n", colorop->base.id); + + tf->type = TF_TYPE_PREDEFINED; + tf->tf = amdgpu_colorop_tf_to_dc_tf(colorop_state->curve_1d_type); + + return 0; +} + +static int +__set_dm_plane_colorop_degamma(struct drm_plane_state *plane_state, + struct dc_plane_state *dc_plane_state, + struct drm_colorop *colorop) +{ + struct drm_colorop *old_colorop; + struct drm_colorop_state *colorop_state = NULL, *new_colorop_state; + struct drm_atomic_state *state = plane_state->state; + int i = 0; + + old_colorop = colorop; + + /* 1st op: 1d curve - degamma */ + for_each_new_colorop_in_state(state, colorop, new_colorop_state, i