LCOV - code coverage report
Current view: top level - drivers/gpu/drm/amd/display/dc/dce110 - dce110_opp_csc_v.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 0 180 0.0 %
Date: 2022-12-09 01:23:36 Functions: 0 6 0.0 %

          Line data    Source code
       1             : /*
       2             :  * Copyright 2012-15 Advanced Micro Devices, Inc.
       3             :  *
       4             :  * Permission is hereby granted, free of charge, to any person obtaining a
       5             :  * copy of this software and associated documentation files (the "Software"),
       6             :  * to deal in the Software without restriction, including without limitation
       7             :  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
       8             :  *  and/or sell copies of the Software, and to permit persons to whom the
       9             :  * Software is furnished to do so, subject to the following conditions:
      10             :  *
      11             :  * The above copyright notice and this permission notice shall be included in
      12             :  * all copies or substantial portions of the Software.
      13             :  *
      14             :  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
      15             :  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
      16             :  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
      17             :  * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
      18             :  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
      19             :  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
      20             :  * OTHER DEALINGS IN THE SOFTWARE.
      21             :  *
      22             :  * Authors: AMD
      23             :  *
      24             :  */
      25             : 
      26             : #include "dm_services.h"
      27             : #include "dce110_transform_v.h"
      28             : #include "basics/conversion.h"
      29             : 
      30             : /* include DCE11 register header files */
      31             : #include "dce/dce_11_0_d.h"
      32             : #include "dce/dce_11_0_sh_mask.h"
      33             : #include "dce/dce_11_0_enum.h"
      34             : 
      35             : enum {
      36             :         OUTPUT_CSC_MATRIX_SIZE = 12
      37             : };
      38             : 
      39             : /* constrast:0 - 2.0, default 1.0 */
      40             : #define UNDERLAY_CONTRAST_DEFAULT 100
      41             : #define UNDERLAY_CONTRAST_MAX     200
      42             : #define UNDERLAY_CONTRAST_MIN       0
      43             : #define UNDERLAY_CONTRAST_STEP      1
      44             : #define UNDERLAY_CONTRAST_DIVIDER 100
      45             : 
      46             : /* Saturation: 0 - 2.0; default 1.0 */
      47             : #define UNDERLAY_SATURATION_DEFAULT   100 /*1.00*/
      48             : #define UNDERLAY_SATURATION_MIN         0
      49             : #define UNDERLAY_SATURATION_MAX       200 /* 2.00 */
      50             : #define UNDERLAY_SATURATION_STEP        1 /* 0.01 */
      51             : /*actual max overlay saturation
      52             :  * value = UNDERLAY_SATURATION_MAX /UNDERLAY_SATURATION_DIVIDER
      53             :  */
      54             : 
      55             : /* Hue */
      56             : #define  UNDERLAY_HUE_DEFAULT      0
      57             : #define  UNDERLAY_HUE_MIN       -300
      58             : #define  UNDERLAY_HUE_MAX        300
      59             : #define  UNDERLAY_HUE_STEP         5
      60             : #define  UNDERLAY_HUE_DIVIDER   10 /* HW range: -30 ~ +30 */
      61             : #define UNDERLAY_SATURATION_DIVIDER   100
      62             : 
      63             : /* Brightness: in DAL usually -.25 ~ .25.
      64             :  * In MMD is -100 to +100 in 16-235 range; which when scaled to full range is
      65             :  *  ~-116 to +116. When normalized this is about 0.4566.
      66             :  * With 100 divider this becomes 46, but we may use another for better precision
      67             :  * The ideal one is 100/219 ((100/255)*(255/219)),
      68             :  * i.e. min/max = +-100, divider = 219
      69             :  * default 0.0
      70             :  */
      71             : #define  UNDERLAY_BRIGHTNESS_DEFAULT    0
      72             : #define  UNDERLAY_BRIGHTNESS_MIN      -46 /* ~116/255 */
      73             : #define  UNDERLAY_BRIGHTNESS_MAX       46
      74             : #define  UNDERLAY_BRIGHTNESS_STEP       1 /*  .01 */
      75             : #define  UNDERLAY_BRIGHTNESS_DIVIDER  100
      76             : 
      77             : static const struct out_csc_color_matrix global_color_matrix[] = {
      78             : { COLOR_SPACE_SRGB,
      79             :         { 0x2000, 0, 0, 0, 0, 0x2000, 0, 0, 0, 0, 0x2000, 0} },
      80             : { COLOR_SPACE_SRGB_LIMITED,
      81             :         { 0x1B60, 0, 0, 0x200, 0, 0x1B60, 0, 0x200, 0, 0, 0x1B60, 0x200} },
      82             : { COLOR_SPACE_YCBCR601,
      83             :         { 0xE00, 0xF447, 0xFDB9, 0x1000, 0x82F, 0x1012, 0x31F, 0x200, 0xFB47,
      84             :                 0xF6B9, 0xE00, 0x1000} },
      85             : { COLOR_SPACE_YCBCR709, { 0xE00, 0xF349, 0xFEB7, 0x1000, 0x5D2, 0x1394, 0x1FA,
      86             :         0x200, 0xFCCB, 0xF535, 0xE00, 0x1000} },
      87             : /* TODO: correct values below */
      88             : { COLOR_SPACE_YCBCR601_LIMITED, { 0xE00, 0xF447, 0xFDB9, 0x1000, 0x991,
      89             :         0x12C9, 0x3A6, 0x200, 0xFB47, 0xF6B9, 0xE00, 0x1000} },
      90             : { COLOR_SPACE_YCBCR709_LIMITED, { 0xE00, 0xF349, 0xFEB7, 0x1000, 0x6CE, 0x16E3,
      91             :         0x24F, 0x200, 0xFCCB, 0xF535, 0xE00, 0x1000} }
      92             : };
      93             : 
      94             : enum csc_color_mode {
      95             :         /* 00 - BITS2:0 Bypass */
      96             :         CSC_COLOR_MODE_GRAPHICS_BYPASS,
      97             :         /* 01 - hard coded coefficient TV RGB */
      98             :         CSC_COLOR_MODE_GRAPHICS_PREDEFINED,
      99             :         /* 04 - programmable OUTPUT CSC coefficient */
     100             :         CSC_COLOR_MODE_GRAPHICS_OUTPUT_CSC,
     101             : };
     102             : 
     103             : enum grph_color_adjust_option {
     104             :         GRPH_COLOR_MATRIX_HW_DEFAULT = 1,
     105             :         GRPH_COLOR_MATRIX_SW
     106             : };
     107             : 
     108           0 : static void program_color_matrix_v(
     109             :         struct dce_transform *xfm_dce,
     110             :         const struct out_csc_color_matrix *tbl_entry,
     111             :         enum grph_color_adjust_option options)
     112             : {
     113           0 :         struct dc_context *ctx = xfm_dce->base.ctx;
     114           0 :         uint32_t cntl_value = dm_read_reg(ctx, mmCOL_MAN_OUTPUT_CSC_CONTROL);
     115           0 :         bool use_set_a = (get_reg_field_value(cntl_value,
     116             :                         COL_MAN_OUTPUT_CSC_CONTROL,
     117             :                         OUTPUT_CSC_MODE) != 4);
     118             : 
     119           0 :         set_reg_field_value(
     120             :                         cntl_value,
     121             :                 0,
     122             :                 COL_MAN_OUTPUT_CSC_CONTROL,
     123             :                 OUTPUT_CSC_MODE);
     124             : 
     125           0 :         if (use_set_a) {
     126             :                 {
     127           0 :                         uint32_t value = 0;
     128           0 :                         uint32_t addr = mmOUTPUT_CSC_C11_C12_A;
     129             :                         /* fixed S2.13 format */
     130           0 :                         set_reg_field_value(
     131             :                                 value,
     132             :                                 tbl_entry->regval[0],
     133             :                                 OUTPUT_CSC_C11_C12_A,
     134             :                                 OUTPUT_CSC_C11_A);
     135             : 
     136           0 :                         set_reg_field_value(
     137             :                                 value,
     138             :                                 tbl_entry->regval[1],
     139             :                                 OUTPUT_CSC_C11_C12_A,
     140             :                                 OUTPUT_CSC_C12_A);
     141             : 
     142           0 :                         dm_write_reg(ctx, addr, value);
     143             :                 }
     144             :                 {
     145           0 :                         uint32_t value = 0;
     146           0 :                         uint32_t addr = mmOUTPUT_CSC_C13_C14_A;
     147             :                         /* fixed S2.13 format */
     148           0 :                         set_reg_field_value(
     149             :                                 value,
     150             :                                 tbl_entry->regval[2],
     151             :                                 OUTPUT_CSC_C13_C14_A,
     152             :                                 OUTPUT_CSC_C13_A);
     153             :                         /* fixed S0.13 format */
     154           0 :                         set_reg_field_value(
     155             :                                 value,
     156             :                                 tbl_entry->regval[3],
     157             :                                 OUTPUT_CSC_C13_C14_A,
     158             :                                 OUTPUT_CSC_C14_A);
     159             : 
     160           0 :                         dm_write_reg(ctx, addr, value);
     161             :                 }
     162             :                 {
     163           0 :                         uint32_t value = 0;
     164           0 :                         uint32_t addr = mmOUTPUT_CSC_C21_C22_A;
     165             :                         /* fixed S2.13 format */
     166           0 :                         set_reg_field_value(
     167             :                                 value,
     168             :                                 tbl_entry->regval[4],
     169             :                                 OUTPUT_CSC_C21_C22_A,
     170             :                                 OUTPUT_CSC_C21_A);
     171             :                         /* fixed S2.13 format */
     172           0 :                         set_reg_field_value(
     173             :                                 value,
     174             :                                 tbl_entry->regval[5],
     175             :                                 OUTPUT_CSC_C21_C22_A,
     176             :                                 OUTPUT_CSC_C22_A);
     177             : 
     178           0 :                         dm_write_reg(ctx, addr, value);
     179             :                 }
     180             :                 {
     181           0 :                         uint32_t value = 0;
     182           0 :                         uint32_t addr = mmOUTPUT_CSC_C23_C24_A;
     183             :                         /* fixed S2.13 format */
     184           0 :                         set_reg_field_value(
     185             :                                 value,
     186             :                                 tbl_entry->regval[6],
     187             :                                 OUTPUT_CSC_C23_C24_A,
     188             :                                 OUTPUT_CSC_C23_A);
     189             :                         /* fixed S0.13 format */
     190           0 :                         set_reg_field_value(
     191             :                                 value,
     192             :                                 tbl_entry->regval[7],
     193             :                                 OUTPUT_CSC_C23_C24_A,
     194             :                                 OUTPUT_CSC_C24_A);
     195             : 
     196           0 :                         dm_write_reg(ctx, addr, value);
     197             :                 }
     198             :                 {
     199           0 :                         uint32_t value = 0;
     200           0 :                         uint32_t addr = mmOUTPUT_CSC_C31_C32_A;
     201             :                         /* fixed S2.13 format */
     202           0 :                         set_reg_field_value(
     203             :                                 value,
     204             :                                 tbl_entry->regval[8],
     205             :                                 OUTPUT_CSC_C31_C32_A,
     206             :                                 OUTPUT_CSC_C31_A);
     207             :                         /* fixed S0.13 format */
     208           0 :                         set_reg_field_value(
     209             :                                 value,
     210             :                                 tbl_entry->regval[9],
     211             :                                 OUTPUT_CSC_C31_C32_A,
     212             :                                 OUTPUT_CSC_C32_A);
     213             : 
     214           0 :                         dm_write_reg(ctx, addr, value);
     215             :                 }
     216             :                 {
     217           0 :                         uint32_t value = 0;
     218           0 :                         uint32_t addr = mmOUTPUT_CSC_C33_C34_A;
     219             :                         /* fixed S2.13 format */
     220           0 :                         set_reg_field_value(
     221             :                                 value,
     222             :                                 tbl_entry->regval[10],
     223             :                                 OUTPUT_CSC_C33_C34_A,
     224             :                                 OUTPUT_CSC_C33_A);
     225             :                         /* fixed S0.13 format */
     226           0 :                         set_reg_field_value(
     227             :                                 value,
     228             :                                 tbl_entry->regval[11],
     229             :                                 OUTPUT_CSC_C33_C34_A,
     230             :                                 OUTPUT_CSC_C34_A);
     231             : 
     232           0 :                         dm_write_reg(ctx, addr, value);
     233             :                 }
     234           0 :                 set_reg_field_value(
     235             :                         cntl_value,
     236             :                         4,
     237             :                         COL_MAN_OUTPUT_CSC_CONTROL,
     238             :                         OUTPUT_CSC_MODE);
     239             :         } else {
     240             :                 {
     241           0 :                         uint32_t value = 0;
     242           0 :                         uint32_t addr = mmOUTPUT_CSC_C11_C12_B;
     243             :                         /* fixed S2.13 format */
     244           0 :                         set_reg_field_value(
     245             :                                 value,
     246             :                                 tbl_entry->regval[0],
     247             :                                 OUTPUT_CSC_C11_C12_B,
     248             :                                 OUTPUT_CSC_C11_B);
     249             : 
     250           0 :                         set_reg_field_value(
     251             :                                 value,
     252             :                                 tbl_entry->regval[1],
     253             :                                 OUTPUT_CSC_C11_C12_B,
     254             :                                 OUTPUT_CSC_C12_B);
     255             : 
     256           0 :                         dm_write_reg(ctx, addr, value);
     257             :                 }
     258             :                 {
     259           0 :                         uint32_t value = 0;
     260           0 :                         uint32_t addr = mmOUTPUT_CSC_C13_C14_B;
     261             :                         /* fixed S2.13 format */
     262           0 :                         set_reg_field_value(
     263             :                                 value,
     264             :                                 tbl_entry->regval[2],
     265             :                                 OUTPUT_CSC_C13_C14_B,
     266             :                                 OUTPUT_CSC_C13_B);
     267             :                         /* fixed S0.13 format */
     268           0 :                         set_reg_field_value(
     269             :                                 value,
     270             :                                 tbl_entry->regval[3],
     271             :                                 OUTPUT_CSC_C13_C14_B,
     272             :                                 OUTPUT_CSC_C14_B);
     273             : 
     274           0 :                         dm_write_reg(ctx, addr, value);
     275             :                 }
     276             :                 {
     277           0 :                         uint32_t value = 0;
     278           0 :                         uint32_t addr = mmOUTPUT_CSC_C21_C22_B;
     279             :                         /* fixed S2.13 format */
     280           0 :                         set_reg_field_value(
     281             :                                 value,
     282             :                                 tbl_entry->regval[4],
     283             :                                 OUTPUT_CSC_C21_C22_B,
     284             :                                 OUTPUT_CSC_C21_B);
     285             :                         /* fixed S2.13 format */
     286           0 :                         set_reg_field_value(
     287             :                                 value,
     288             :                                 tbl_entry->regval[5],
     289             :                                 OUTPUT_CSC_C21_C22_B,
     290             :                                 OUTPUT_CSC_C22_B);
     291             : 
     292           0 :                         dm_write_reg(ctx, addr, value);
     293             :                 }
     294             :                 {
     295           0 :                         uint32_t value = 0;
     296           0 :                         uint32_t addr = mmOUTPUT_CSC_C23_C24_B;
     297             :                         /* fixed S2.13 format */
     298           0 :                         set_reg_field_value(
     299             :                                 value,
     300             :                                 tbl_entry->regval[6],
     301             :                                 OUTPUT_CSC_C23_C24_B,
     302             :                                 OUTPUT_CSC_C23_B);
     303             :                         /* fixed S0.13 format */
     304           0 :                         set_reg_field_value(
     305             :                                 value,
     306             :                                 tbl_entry->regval[7],
     307             :                                 OUTPUT_CSC_C23_C24_B,
     308             :                                 OUTPUT_CSC_C24_B);
     309             : 
     310           0 :                         dm_write_reg(ctx, addr, value);
     311             :                 }
     312             :                 {
     313           0 :                         uint32_t value = 0;
     314           0 :                         uint32_t addr = mmOUTPUT_CSC_C31_C32_B;
     315             :                         /* fixed S2.13 format */
     316           0 :                         set_reg_field_value(
     317             :                                 value,
     318             :                                 tbl_entry->regval[8],
     319             :                                 OUTPUT_CSC_C31_C32_B,
     320             :                                 OUTPUT_CSC_C31_B);
     321             :                         /* fixed S0.13 format */
     322           0 :                         set_reg_field_value(
     323             :                                 value,
     324             :                                 tbl_entry->regval[9],
     325             :                                 OUTPUT_CSC_C31_C32_B,
     326             :                                 OUTPUT_CSC_C32_B);
     327             : 
     328           0 :                         dm_write_reg(ctx, addr, value);
     329             :                 }
     330             :                 {
     331           0 :                         uint32_t value = 0;
     332           0 :                         uint32_t addr = mmOUTPUT_CSC_C33_C34_B;
     333             :                         /* fixed S2.13 format */
     334           0 :                         set_reg_field_value(
     335             :                                 value,
     336             :                                 tbl_entry->regval[10],
     337             :                                 OUTPUT_CSC_C33_C34_B,
     338             :                                 OUTPUT_CSC_C33_B);
     339             :                         /* fixed S0.13 format */
     340           0 :                         set_reg_field_value(
     341             :                                 value,
     342             :                                 tbl_entry->regval[11],
     343             :                                 OUTPUT_CSC_C33_C34_B,
     344             :                                 OUTPUT_CSC_C34_B);
     345             : 
     346           0 :                         dm_write_reg(ctx, addr, value);
     347             :                 }
     348           0 :                 set_reg_field_value(
     349             :                         cntl_value,
     350             :                         5,
     351             :                         COL_MAN_OUTPUT_CSC_CONTROL,
     352             :                         OUTPUT_CSC_MODE);
     353             :         }
     354             : 
     355           0 :         dm_write_reg(ctx, mmCOL_MAN_OUTPUT_CSC_CONTROL, cntl_value);
     356           0 : }
     357             : 
     358           0 : static bool configure_graphics_mode_v(
     359             :         struct dce_transform *xfm_dce,
     360             :         enum csc_color_mode config,
     361             :         enum graphics_csc_adjust_type csc_adjust_type,
     362             :         enum dc_color_space color_space)
     363             : {
     364           0 :         struct dc_context *ctx = xfm_dce->base.ctx;
     365           0 :         uint32_t addr = mmCOL_MAN_OUTPUT_CSC_CONTROL;
     366           0 :         uint32_t value = dm_read_reg(ctx, addr);
     367             : 
     368           0 :         set_reg_field_value(
     369             :                 value,
     370             :                 0,
     371             :                 COL_MAN_OUTPUT_CSC_CONTROL,
     372             :                 OUTPUT_CSC_MODE);
     373             : 
     374           0 :         if (csc_adjust_type == GRAPHICS_CSC_ADJUST_TYPE_SW) {
     375           0 :                 if (config == CSC_COLOR_MODE_GRAPHICS_OUTPUT_CSC)
     376             :                         return true;
     377             : 
     378           0 :                 switch (color_space) {
     379             :                 case COLOR_SPACE_SRGB:
     380             :                         /* by pass */
     381             :                         set_reg_field_value(
     382             :                                 value,
     383             :                                 0,
     384             :                                 COL_MAN_OUTPUT_CSC_CONTROL,
     385             :                                 OUTPUT_CSC_MODE);
     386             :                         break;
     387             :                 case COLOR_SPACE_SRGB_LIMITED:
     388             :                         /* not supported for underlay on CZ */
     389             :                         return false;
     390             : 
     391             :                 case COLOR_SPACE_YCBCR601_LIMITED:
     392             :                         /* YCbCr601 */
     393           0 :                         set_reg_field_value(
     394             :                                 value,
     395             :                                 2,
     396             :                                 COL_MAN_OUTPUT_CSC_CONTROL,
     397             :                                 OUTPUT_CSC_MODE);
     398             :                         break;
     399             :                 case COLOR_SPACE_YCBCR709:
     400             :                 case COLOR_SPACE_YCBCR709_LIMITED:
     401             :                         /* YCbCr709 */
     402           0 :                         set_reg_field_value(
     403             :                                 value,
     404             :                                 3,
     405             :                                 COL_MAN_OUTPUT_CSC_CONTROL,
     406             :                                 OUTPUT_CSC_MODE);
     407             :                         break;
     408             :                 default:
     409             :                         return false;
     410             :                 }
     411             : 
     412           0 :         } else if (csc_adjust_type == GRAPHICS_CSC_ADJUST_TYPE_HW) {
     413           0 :                 switch (color_space) {
     414             :                 case COLOR_SPACE_SRGB:
     415             :                         /* by pass */
     416             :                         set_reg_field_value(
     417             :                                 value,
     418             :                                 0,
     419             :                                 COL_MAN_OUTPUT_CSC_CONTROL,
     420             :                                 OUTPUT_CSC_MODE);
     421             :                         break;
     422             :                 case COLOR_SPACE_SRGB_LIMITED:
     423             :                         /* not supported for underlay on CZ */
     424             :                         return false;
     425             :                 case COLOR_SPACE_YCBCR601:
     426             :                 case COLOR_SPACE_YCBCR601_LIMITED:
     427             :                         /* YCbCr601 */
     428           0 :                         set_reg_field_value(
     429             :                                 value,
     430             :                                 2,
     431             :                                 COL_MAN_OUTPUT_CSC_CONTROL,
     432             :                                 OUTPUT_CSC_MODE);
     433             :                         break;
     434             :                 case COLOR_SPACE_YCBCR709:
     435             :                 case COLOR_SPACE_YCBCR709_LIMITED:
     436             :                          /* YCbCr709 */
     437           0 :                         set_reg_field_value(
     438             :                                 value,
     439             :                                 3,
     440             :                                 COL_MAN_OUTPUT_CSC_CONTROL,
     441             :                                 OUTPUT_CSC_MODE);
     442             :                         break;
     443             :                 default:
     444             :                         return false;
     445             :                 }
     446             : 
     447             :         } else
     448             :                 /* by pass */
     449             :                 set_reg_field_value(
     450             :                         value,
     451             :                         0,
     452             :                         COL_MAN_OUTPUT_CSC_CONTROL,
     453             :                         OUTPUT_CSC_MODE);
     454             : 
     455           0 :         addr = mmCOL_MAN_OUTPUT_CSC_CONTROL;
     456           0 :         dm_write_reg(ctx, addr, value);
     457             : 
     458             :         return true;
     459             : }
     460             : 
     461             : /*TODO: color depth is not correct when this is called*/
     462           0 : static void set_Denormalization(struct transform *xfm,
     463             :                 enum dc_color_depth color_depth)
     464             : {
     465           0 :         uint32_t value = dm_read_reg(xfm->ctx, mmDENORM_CLAMP_CONTROL);
     466             : 
     467           0 :         switch (color_depth) {
     468             :         case COLOR_DEPTH_888:
     469             :                 /* 255/256 for 8 bit output color depth */
     470           0 :                 set_reg_field_value(
     471             :                         value,
     472             :                         1,
     473             :                         DENORM_CLAMP_CONTROL,
     474             :                         DENORM_MODE);
     475             :                 break;
     476             :         case COLOR_DEPTH_101010:
     477             :                 /* 1023/1024 for 10 bit output color depth */
     478           0 :                 set_reg_field_value(
     479             :                         value,
     480             :                         2,
     481             :                         DENORM_CLAMP_CONTROL,
     482             :                         DENORM_MODE);
     483             :                 break;
     484             :         case COLOR_DEPTH_121212:
     485             :                 /* 4095/4096 for 12 bit output color depth */
     486           0 :                 set_reg_field_value(
     487             :                         value,
     488             :                         3,
     489             :                         DENORM_CLAMP_CONTROL,
     490             :                         DENORM_MODE);
     491             :                 break;
     492             :         default:
     493             :                 /* not valid case */
     494             :                 break;
     495             :         }
     496             : 
     497           0 :         set_reg_field_value(
     498             :                 value,
     499             :                 1,
     500             :                 DENORM_CLAMP_CONTROL,
     501             :                 DENORM_10BIT_OUT);
     502             : 
     503           0 :         dm_write_reg(xfm->ctx, mmDENORM_CLAMP_CONTROL, value);
     504           0 : }
     505             : 
     506             : struct input_csc_matrix {
     507             :         enum dc_color_space color_space;
     508             :         uint32_t regval[12];
     509             : };
     510             : 
     511             : static const struct input_csc_matrix input_csc_matrix[] = {
     512             :         {COLOR_SPACE_SRGB,
     513             : /*1_1   1_2   1_3   1_4   2_1   2_2   2_3   2_4   3_1   3_2   3_3   3_4 */
     514             :                 {0x2000, 0, 0, 0, 0, 0x2000, 0, 0, 0, 0, 0x2000, 0} },
     515             :         {COLOR_SPACE_SRGB_LIMITED,
     516             :                 {0x2000, 0, 0, 0, 0, 0x2000, 0, 0, 0, 0, 0x2000, 0} },
     517             :         {COLOR_SPACE_YCBCR601,
     518             :                 {0x2cdd, 0x2000, 0x0, 0xe991, 0xe926, 0x2000, 0xf4fd, 0x10ef,
     519             :                                                 0x0, 0x2000, 0x38b4, 0xe3a6} },
     520             :         {COLOR_SPACE_YCBCR601_LIMITED,
     521             :                 {0x3353, 0x2568, 0x0, 0xe400, 0xe5dc, 0x2568, 0xf367, 0x1108,
     522             :                                                 0x0, 0x2568, 0x40de, 0xdd3a} },
     523             :         {COLOR_SPACE_YCBCR709,
     524             :                 {0x3265, 0x2000, 0, 0xe6ce, 0xf105, 0x2000, 0xfa01, 0xa7d, 0,
     525             :                                                 0x2000, 0x3b61, 0xe24f} },
     526             :         {COLOR_SPACE_YCBCR709_LIMITED,
     527             :                 {0x39a6, 0x2568, 0, 0xe0d6, 0xeedd, 0x2568, 0xf925, 0x9a8, 0,
     528             :                                                 0x2568, 0x43ee, 0xdbb2} }
     529             : };
     530             : 
     531           0 : static void program_input_csc(
     532             :                 struct transform *xfm, enum dc_color_space color_space)
     533             : {
     534           0 :         int arr_size = sizeof(input_csc_matrix)/sizeof(struct input_csc_matrix);
     535           0 :         struct dc_context *ctx = xfm->ctx;
     536           0 :         const uint32_t *regval = NULL;
     537             :         bool use_set_a;
     538             :         uint32_t value;
     539             :         int i;
     540             : 
     541           0 :         for (i = 0; i < arr_size; i++)
     542           0 :                 if (input_csc_matrix[i].color_space == color_space) {
     543           0 :                         regval = input_csc_matrix[i].regval;
     544             :                         break;
     545             :                 }
     546           0 :         if (regval == NULL) {
     547           0 :                 BREAK_TO_DEBUGGER();
     548             :                 return;
     549             :         }
     550             : 
     551             :         /*
     552             :          * 1 == set A, the logic is 'if currently we're not using set A,
     553             :          * then use set A, otherwise use set B'
     554             :          */
     555           0 :         value = dm_read_reg(ctx, mmCOL_MAN_INPUT_CSC_CONTROL);
     556           0 :         use_set_a = get_reg_field_value(
     557             :                 value, COL_MAN_INPUT_CSC_CONTROL, INPUT_CSC_MODE) != 1;
     558             : 
     559           0 :         if (use_set_a) {
     560             :                 /* fixed S2.13 format */
     561           0 :                 value = 0;
     562           0 :                 set_reg_field_value(
     563             :                         value, regval[0], INPUT_CSC_C11_C12_A, INPUT_CSC_C11_A);
     564           0 :                 set_reg_field_value(
     565             :                         value, regval[1], INPUT_CSC_C11_C12_A, INPUT_CSC_C12_A);
     566           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C11_C12_A, value);
     567             : 
     568           0 :                 value = 0;
     569           0 :                 set_reg_field_value(
     570             :                         value, regval[2], INPUT_CSC_C13_C14_A, INPUT_CSC_C13_A);
     571           0 :                 set_reg_field_value(
     572             :                         value, regval[3], INPUT_CSC_C13_C14_A, INPUT_CSC_C14_A);
     573           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C13_C14_A, value);
     574             : 
     575           0 :                 value = 0;
     576           0 :                 set_reg_field_value(
     577             :                         value, regval[4], INPUT_CSC_C21_C22_A, INPUT_CSC_C21_A);
     578           0 :                 set_reg_field_value(
     579             :                         value, regval[5], INPUT_CSC_C21_C22_A, INPUT_CSC_C22_A);
     580           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C21_C22_A, value);
     581             : 
     582           0 :                 value = 0;
     583           0 :                 set_reg_field_value(
     584             :                         value, regval[6], INPUT_CSC_C23_C24_A, INPUT_CSC_C23_A);
     585           0 :                 set_reg_field_value(
     586             :                         value, regval[7], INPUT_CSC_C23_C24_A, INPUT_CSC_C24_A);
     587           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C23_C24_A, value);
     588             : 
     589           0 :                 value = 0;
     590           0 :                 set_reg_field_value(
     591             :                         value, regval[8], INPUT_CSC_C31_C32_A, INPUT_CSC_C31_A);
     592           0 :                 set_reg_field_value(
     593             :                         value, regval[9], INPUT_CSC_C31_C32_A, INPUT_CSC_C32_A);
     594           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C31_C32_A, value);
     595             : 
     596           0 :                 value = 0;
     597           0 :                 set_reg_field_value(
     598             :                         value, regval[10], INPUT_CSC_C33_C34_A, INPUT_CSC_C33_A);
     599           0 :                 set_reg_field_value(
     600             :                         value, regval[11], INPUT_CSC_C33_C34_A, INPUT_CSC_C34_A);
     601           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C33_C34_A, value);
     602             :         } else {
     603             :                 /* fixed S2.13 format */
     604           0 :                 value = 0;
     605           0 :                 set_reg_field_value(
     606             :                         value, regval[0], INPUT_CSC_C11_C12_B, INPUT_CSC_C11_B);
     607           0 :                 set_reg_field_value(
     608             :                         value, regval[1], INPUT_CSC_C11_C12_B, INPUT_CSC_C12_B);
     609           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C11_C12_B, value);
     610             : 
     611           0 :                 value = 0;
     612           0 :                 set_reg_field_value(
     613             :                         value, regval[2], INPUT_CSC_C13_C14_B, INPUT_CSC_C13_B);
     614           0 :                 set_reg_field_value(
     615             :                         value, regval[3], INPUT_CSC_C13_C14_B, INPUT_CSC_C14_B);
     616           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C13_C14_B, value);
     617             : 
     618           0 :                 value = 0;
     619           0 :                 set_reg_field_value(
     620             :                         value, regval[4], INPUT_CSC_C21_C22_B, INPUT_CSC_C21_B);
     621           0 :                 set_reg_field_value(
     622             :                         value, regval[5], INPUT_CSC_C21_C22_B, INPUT_CSC_C22_B);
     623           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C21_C22_B, value);
     624             : 
     625           0 :                 value = 0;
     626           0 :                 set_reg_field_value(
     627             :                         value, regval[6], INPUT_CSC_C23_C24_B, INPUT_CSC_C23_B);
     628           0 :                 set_reg_field_value(
     629             :                         value, regval[7], INPUT_CSC_C23_C24_B, INPUT_CSC_C24_B);
     630           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C23_C24_B, value);
     631             : 
     632           0 :                 value = 0;
     633           0 :                 set_reg_field_value(
     634             :                         value, regval[8], INPUT_CSC_C31_C32_B, INPUT_CSC_C31_B);
     635           0 :                 set_reg_field_value(
     636             :                         value, regval[9], INPUT_CSC_C31_C32_B, INPUT_CSC_C32_B);
     637           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C31_C32_B, value);
     638             : 
     639           0 :                 value = 0;
     640           0 :                 set_reg_field_value(
     641             :                         value, regval[10], INPUT_CSC_C33_C34_B, INPUT_CSC_C33_B);
     642           0 :                 set_reg_field_value(
     643             :                         value, regval[11], INPUT_CSC_C33_C34_B, INPUT_CSC_C34_B);
     644           0 :                 dm_write_reg(ctx, mmINPUT_CSC_C33_C34_B, value);
     645             :         }
     646             : 
     647             :         /* KK: leave INPUT_CSC_CONVERSION_MODE at default */
     648           0 :         value = 0;
     649             :         /*
     650             :          * select 8.4 input type instead of default 12.0. From the discussion
     651             :          * with HW team, this format depends on the UNP surface format, so for
     652             :          * 8-bit we should select 8.4 (4 bits truncated). For 10 it should be
     653             :          * 10.2. For Carrizo we only support 8-bit surfaces on underlay pipe
     654             :          * so we can always keep this at 8.4 (input_type=2). If the later asics
     655             :          * start supporting 10+ bits, we will have a problem: surface
     656             :          * programming including UNP_GRPH* is being done in DalISR after this,
     657             :          * so either we pass surface format to here, or move this logic to ISR
     658             :          */
     659             : 
     660           0 :         set_reg_field_value(
     661             :                 value, 2, COL_MAN_INPUT_CSC_CONTROL, INPUT_CSC_INPUT_TYPE);
     662           0 :         set_reg_field_value(
     663             :                 value,
     664             :                 use_set_a ? 1 : 2,
     665             :                 COL_MAN_INPUT_CSC_CONTROL,
     666             :                 INPUT_CSC_MODE);
     667             : 
     668           0 :         dm_write_reg(ctx, mmCOL_MAN_INPUT_CSC_CONTROL, value);
     669             : }
     670             : 
     671           0 : void dce110_opp_v_set_csc_default(
     672             :         struct transform *xfm,
     673             :         const struct default_adjustment *default_adjust)
     674             : {
     675           0 :         struct dce_transform *xfm_dce = TO_DCE_TRANSFORM(xfm);
     676           0 :         enum csc_color_mode config =
     677             :                         CSC_COLOR_MODE_GRAPHICS_PREDEFINED;
     678             : 
     679           0 :         if (default_adjust->force_hw_default == false) {
     680             :                 const struct out_csc_color_matrix *elm;
     681             :                 /* currently parameter not in use */
     682             :                 enum grph_color_adjust_option option;
     683             :                 uint32_t i;
     684             :                 /*
     685             :                  * HW default false we program locally defined matrix
     686             :                  * HW default true  we use predefined hw matrix and we
     687             :                  * do not need to program matrix
     688             :                  * OEM wants the HW default via runtime parameter.
     689             :                  */
     690             :                 option = GRPH_COLOR_MATRIX_SW;
     691             : 
     692           0 :                 for (i = 0; i < ARRAY_SIZE(global_color_matrix); ++i) {
     693           0 :                         elm = &global_color_matrix[i];
     694           0 :                         if (elm->color_space != default_adjust->out_color_space)
     695           0 :                                 continue;
     696             :                         /* program the matrix with default values from this
     697             :                          * file
     698             :                          */
     699           0 :                         program_color_matrix_v(xfm_dce, elm, option);
     700           0 :                         config = CSC_COLOR_MODE_GRAPHICS_OUTPUT_CSC;
     701           0 :                         break;
     702             :                 }
     703             :         }
     704             : 
     705           0 :         program_input_csc(xfm, default_adjust->in_color_space);
     706             : 
     707             :         /* configure the what we programmed :
     708             :          * 1. Default values from this file
     709             :          * 2. Use hardware default from ROM_A and we do not need to program
     710             :          * matrix
     711             :          */
     712             : 
     713           0 :         configure_graphics_mode_v(xfm_dce, config,
     714             :                 default_adjust->csc_adjust_type,
     715             :                 default_adjust->out_color_space);
     716             : 
     717           0 :         set_Denormalization(xfm, default_adjust->color_depth);
     718           0 : }
     719             : 
     720           0 : void dce110_opp_v_set_csc_adjustment(
     721             :         struct transform *xfm,
     722             :         const struct out_csc_color_matrix *tbl_entry)
     723             : {
     724           0 :         struct dce_transform *xfm_dce = TO_DCE_TRANSFORM(xfm);
     725           0 :         enum csc_color_mode config =
     726             :                         CSC_COLOR_MODE_GRAPHICS_OUTPUT_CSC;
     727             : 
     728           0 :         program_color_matrix_v(
     729             :                         xfm_dce, tbl_entry, GRPH_COLOR_MATRIX_SW);
     730             : 
     731             :         /*  We did everything ,now program DxOUTPUT_CSC_CONTROL */
     732           0 :         configure_graphics_mode_v(xfm_dce, config, GRAPHICS_CSC_ADJUST_TYPE_SW,
     733             :                         tbl_entry->color_space);
     734             : 
     735             :         /*TODO: Check if denormalization is needed*/
     736             :         /*set_Denormalization(opp, adjust->color_depth);*/
     737           0 : }

Generated by: LCOV version 1.14