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

          Line data    Source code
       1             : /*
       2             :  * Copyright 2012-17 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             : 
      27             : #include "reg_helper.h"
      28             : #include "resource.h"
      29             : #include "dwb.h"
      30             : #include "dcn20_dwb.h"
      31             : 
      32             : 
      33             : #define REG(reg)\
      34             :         dwbc20->dwbc_regs->reg
      35             : 
      36             : #define CTX \
      37             :         dwbc20->base.ctx
      38             : 
      39             : #define DC_LOGGER \
      40             :         dwbc20->base.ctx->logger
      41             : #undef FN
      42             : #define FN(reg_name, field_name) \
      43             :         dwbc20->dwbc_shift->field_name, dwbc20->dwbc_mask->field_name
      44             : 
      45             : enum dwb_outside_pix_strategy {
      46             :         DWB_OUTSIDE_PIX_STRATEGY_BLACK = 0,
      47             :         DWB_OUTSIDE_PIX_STRATEGY_EDGE  = 1
      48             : };
      49             : 
      50           0 : static bool dwb2_get_caps(struct dwbc *dwbc, struct dwb_caps *caps)
      51             : {
      52           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
      53           0 :         if (caps) {
      54           0 :                 caps->adapter_id = 0;        /* we only support 1 adapter currently */
      55           0 :                 caps->hw_version = DCN_VERSION_2_0;
      56           0 :                 caps->num_pipes = 1;
      57           0 :                 memset(&caps->reserved, 0, sizeof(caps->reserved));
      58           0 :                 memset(&caps->reserved2, 0, sizeof(caps->reserved2));
      59           0 :                 caps->sw_version = dwb_ver_1_0;
      60           0 :                 caps->caps.support_dwb = true;
      61           0 :                 caps->caps.support_ogam = false;
      62           0 :                 caps->caps.support_wbscl = false;
      63           0 :                 caps->caps.support_ocsc = false;
      64           0 :                 DC_LOG_DWB("%s SUPPORTED! inst = %d", __func__, dwbc20->base.inst);
      65           0 :                 return true;
      66             :         } else {
      67           0 :                 DC_LOG_DWB("%s NOT SUPPORTED! inst = %d", __func__, dwbc20->base.inst);
      68           0 :                 return false;
      69             :         }
      70             : }
      71             : 
      72           0 : void dwb2_config_dwb_cnv(struct dwbc *dwbc, struct dc_dwb_params *params)
      73             : {
      74           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
      75           0 :         DC_LOG_DWB("%s inst = %d", __func__, dwbc20->base.inst);
      76             : 
      77             :         /* Set DWB source size */
      78           0 :         REG_UPDATE_2(CNV_SOURCE_SIZE, CNV_SOURCE_WIDTH, params->cnv_params.src_width,
      79             :                         CNV_SOURCE_HEIGHT, params->cnv_params.src_height);
      80             : 
      81             :         /* source size is not equal the source size, then enable cropping. */
      82           0 :         if (params->cnv_params.crop_en) {
      83           0 :                 REG_UPDATE(CNV_MODE, CNV_WINDOW_CROP_EN, 1);
      84           0 :                 REG_UPDATE(CNV_WINDOW_START, CNV_WINDOW_START_X, params->cnv_params.crop_x);
      85           0 :                 REG_UPDATE(CNV_WINDOW_START, CNV_WINDOW_START_Y, params->cnv_params.crop_y);
      86           0 :                 REG_UPDATE(CNV_WINDOW_SIZE,  CNV_WINDOW_WIDTH,   params->cnv_params.crop_width);
      87           0 :                 REG_UPDATE(CNV_WINDOW_SIZE,  CNV_WINDOW_HEIGHT,  params->cnv_params.crop_height);
      88             :         } else {
      89           0 :                 REG_UPDATE(CNV_MODE, CNV_WINDOW_CROP_EN, 0);
      90             :         }
      91             : 
      92             :         /* Set CAPTURE_RATE */
      93           0 :         REG_UPDATE(CNV_MODE, CNV_FRAME_CAPTURE_RATE, params->capture_rate);
      94             : 
      95             :         /* Set CNV output pixel depth */
      96           0 :         REG_UPDATE(CNV_MODE, CNV_OUT_BPC, params->cnv_params.cnv_out_bpc);
      97           0 : }
      98             : 
      99           0 : static bool dwb2_enable(struct dwbc *dwbc, struct dc_dwb_params *params)
     100             : {
     101           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     102             : 
     103             :         /* Only chroma scaling (sub-sampling) is supported in DCN2 */
     104           0 :         if ((params->cnv_params.src_width  != params->dest_width) ||
     105             :             (params->cnv_params.src_height != params->dest_height)) {
     106             : 
     107           0 :                 DC_LOG_DWB("%s inst = %d, FAILED!LUMA SCALING NOT SUPPORTED", __func__, dwbc20->base.inst);
     108           0 :                 return false;
     109             :         }
     110           0 :         DC_LOG_DWB("%s inst = %d, ENABLED", __func__, dwbc20->base.inst);
     111             : 
     112             :         /* disable power gating */
     113             :         //REG_UPDATE_5(WB_EC_CONFIG, DISPCLK_R_WB_GATE_DIS, 1,
     114             :         //                       DISPCLK_G_WB_GATE_DIS, 1, DISPCLK_G_WBSCL_GATE_DIS, 1,
     115             :         //                       WB_LB_LS_DIS, 1, WB_LUT_LS_DIS, 1);
     116             : 
     117             :         /* Set WB_ENABLE (not double buffered; capture not enabled) */
     118           0 :         REG_UPDATE(WB_ENABLE, WB_ENABLE, 1);
     119             : 
     120             :         /* Set CNV parameters */
     121           0 :         dwb2_config_dwb_cnv(dwbc, params);
     122             : 
     123             :         /* Set scaling parameters */
     124           0 :         dwb2_set_scaler(dwbc, params);
     125             : 
     126             :         /* Enable DWB capture enable (double buffered) */
     127           0 :         REG_UPDATE(CNV_MODE, CNV_FRAME_CAPTURE_EN, DWB_FRAME_CAPTURE_ENABLE);
     128             : 
     129             :         // disable warmup
     130           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL1, GMC_WARM_UP_ENABLE, 0);
     131             : 
     132           0 :         return true;
     133             : }
     134             : 
     135           0 : bool dwb2_disable(struct dwbc *dwbc)
     136             : {
     137           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     138           0 :         DC_LOG_DWB("%s inst = %d, Disabled", __func__, dwbc20->base.inst);
     139             : 
     140             :         /* disable CNV */
     141           0 :         REG_UPDATE(CNV_MODE, CNV_FRAME_CAPTURE_EN, DWB_FRAME_CAPTURE_DISABLE);
     142             : 
     143             :         /* disable WB */
     144           0 :         REG_UPDATE(WB_ENABLE, WB_ENABLE, 0);
     145             : 
     146             :         /* soft reset */
     147           0 :         REG_UPDATE(WB_SOFT_RESET, WB_SOFT_RESET, 1);
     148           0 :         REG_UPDATE(WB_SOFT_RESET, WB_SOFT_RESET, 0);
     149             : 
     150             :         /* enable power gating */
     151             :         //REG_UPDATE_5(WB_EC_CONFIG, DISPCLK_R_WB_GATE_DIS, 0,
     152             :         //                       DISPCLK_G_WB_GATE_DIS, 0, DISPCLK_G_WBSCL_GATE_DIS, 0,
     153             :         //                       WB_LB_LS_DIS, 0, WB_LUT_LS_DIS, 0);
     154             : 
     155           0 :         return true;
     156             : }
     157             : 
     158           0 : static bool dwb2_update(struct dwbc *dwbc, struct dc_dwb_params *params)
     159             : {
     160           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     161             :         unsigned int pre_locked;
     162             : 
     163             :         /* Only chroma scaling (sub-sampling) is supported in DCN2 */
     164           0 :         if ((params->cnv_params.src_width != params->dest_width) ||
     165             :                         (params->cnv_params.src_height != params->dest_height)) {
     166           0 :                 DC_LOG_DWB("%s inst = %d, FAILED!LUMA SCALING NOT SUPPORTED", __func__, dwbc20->base.inst);
     167           0 :                 return false;
     168             :         }
     169           0 :         DC_LOG_DWB("%s inst = %d, scaling", __func__, dwbc20->base.inst);
     170             : 
     171             :         /*
     172             :          * Check if the caller has already locked CNV registers.
     173             :          * If so: assume the caller will unlock, so don't touch the lock.
     174             :          * If not: lock them for this update, then unlock after the
     175             :          * update is complete.
     176             :          */
     177           0 :         REG_GET(CNV_UPDATE, CNV_UPDATE_LOCK, &pre_locked);
     178             : 
     179           0 :         if (pre_locked == 0) {
     180             :                 /* Lock DWB registers */
     181           0 :                 REG_UPDATE(CNV_UPDATE, CNV_UPDATE_LOCK, 1);
     182             :         }
     183             : 
     184             :         /* Set CNV parameters */
     185           0 :         dwb2_config_dwb_cnv(dwbc, params);
     186             : 
     187             :         /* Set scaling parameters */
     188           0 :         dwb2_set_scaler(dwbc, params);
     189             : 
     190           0 :         if (pre_locked == 0) {
     191             :                 /* Unlock DWB registers */
     192           0 :                 REG_UPDATE(CNV_UPDATE, CNV_UPDATE_LOCK, 0);
     193             :         }
     194             : 
     195             :         return true;
     196             : }
     197             : 
     198           0 : bool dwb2_is_enabled(struct dwbc *dwbc)
     199             : {
     200           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     201           0 :         unsigned int wb_enabled = 0;
     202           0 :         unsigned int cnv_frame_capture_en = 0;
     203             : 
     204           0 :         REG_GET(WB_ENABLE, WB_ENABLE, &wb_enabled);
     205           0 :         REG_GET(CNV_MODE, CNV_FRAME_CAPTURE_EN, &cnv_frame_capture_en);
     206             : 
     207           0 :         return ((wb_enabled != 0) && (cnv_frame_capture_en != 0));
     208             : }
     209             : 
     210           0 : void dwb2_set_stereo(struct dwbc *dwbc,
     211             :                 struct dwb_stereo_params *stereo_params)
     212             : {
     213           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     214           0 :         DC_LOG_DWB("%s inst = %d, enabled =%d", __func__,\
     215             :                 dwbc20->base.inst, stereo_params->stereo_enabled);
     216             : 
     217           0 :         if (stereo_params->stereo_enabled) {
     218           0 :                 REG_UPDATE(CNV_MODE, CNV_STEREO_TYPE,     stereo_params->stereo_type);
     219           0 :                 REG_UPDATE(CNV_MODE, CNV_EYE_SELECTION,   stereo_params->stereo_eye_select);
     220           0 :                 REG_UPDATE(CNV_MODE, CNV_STEREO_POLARITY, stereo_params->stereo_polarity);
     221             :         } else {
     222           0 :                 REG_UPDATE(CNV_MODE, CNV_EYE_SELECTION, 0);
     223             :         }
     224           0 : }
     225             : 
     226           0 : void dwb2_set_new_content(struct dwbc *dwbc,
     227             :                                                 bool is_new_content)
     228             : {
     229           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     230           0 :         DC_LOG_DWB("%s inst = %d", __func__, dwbc20->base.inst);
     231             : 
     232           0 :         REG_UPDATE(CNV_MODE, CNV_NEW_CONTENT, is_new_content);
     233           0 : }
     234             : 
     235           0 : static void dwb2_set_warmup(struct dwbc *dwbc,
     236             :                 struct dwb_warmup_params *warmup_params)
     237             : {
     238           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     239           0 :         DC_LOG_DWB("%s inst = %d", __func__, dwbc20->base.inst);
     240             : 
     241           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL1, GMC_WARM_UP_ENABLE, warmup_params->warmup_en);
     242           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL1, WIDTH_WARMUP, warmup_params->warmup_width);
     243           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL1, HEIGHT_WARMUP, warmup_params->warmup_height);
     244             : 
     245           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL2, DATA_VALUE_WARMUP, warmup_params->warmup_data);
     246           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL2, MODE_WARMUP, warmup_params->warmup_mode);
     247           0 :         REG_UPDATE(WB_WARM_UP_MODE_CTL2, DATA_DEPTH_WARMUP, warmup_params->warmup_depth);
     248           0 : }
     249             : 
     250           0 : void dwb2_set_scaler(struct dwbc *dwbc, struct dc_dwb_params *params)
     251             : {
     252           0 :         struct dcn20_dwbc *dwbc20 = TO_DCN20_DWBC(dwbc);
     253           0 :         DC_LOG_DWB("%s inst = %d", __func__, dwbc20->base.inst);
     254             : 
     255             :         /* Program scaling mode */
     256           0 :         REG_UPDATE_2(WBSCL_MODE, WBSCL_MODE, params->out_format,
     257             :                         WBSCL_OUT_BIT_DEPTH, params->output_depth);
     258             : 
     259           0 :         if (params->out_format != dwb_scaler_mode_bypass444) {
     260             :                 /* Program output size */
     261           0 :                 REG_UPDATE(WBSCL_DEST_SIZE, WBSCL_DEST_WIDTH,   params->dest_width);
     262           0 :                 REG_UPDATE(WBSCL_DEST_SIZE, WBSCL_DEST_HEIGHT,  params->dest_height);
     263             : 
     264             :                 /* Program round offsets */
     265           0 :                 REG_UPDATE(WBSCL_ROUND_OFFSET, WBSCL_ROUND_OFFSET_Y_RGB, 0x40);
     266           0 :                 REG_UPDATE(WBSCL_ROUND_OFFSET, WBSCL_ROUND_OFFSET_CBCR,  0x200);
     267             : 
     268             :                 /* Program clamp values */
     269           0 :                 REG_UPDATE(WBSCL_CLAMP_Y_RGB,   WBSCL_CLAMP_UPPER_Y_RGB,        0x3fe);
     270           0 :                 REG_UPDATE(WBSCL_CLAMP_Y_RGB,   WBSCL_CLAMP_LOWER_Y_RGB,        0x1);
     271           0 :                 REG_UPDATE(WBSCL_CLAMP_CBCR,    WBSCL_CLAMP_UPPER_CBCR,         0x3fe);
     272           0 :                 REG_UPDATE(WBSCL_CLAMP_CBCR,    WBSCL_CLAMP_LOWER_CBCR,         0x1);
     273             : 
     274             :                 /* Program outside pixel strategy to use edge pixels */
     275           0 :                 REG_UPDATE(WBSCL_OUTSIDE_PIX_STRATEGY, WBSCL_OUTSIDE_PIX_STRATEGY, DWB_OUTSIDE_PIX_STRATEGY_EDGE);
     276             : 
     277           0 :                 if (params->cnv_params.crop_en) {
     278             :                         /* horizontal scale */
     279           0 :                         dwb_program_horz_scalar(dwbc20, params->cnv_params.crop_width,
     280             :                                                         params->dest_width,
     281             :                                                         params->scaler_taps);
     282             : 
     283             :                         /* vertical scale */
     284           0 :                         dwb_program_vert_scalar(dwbc20, params->cnv_params.crop_height,
     285             :                                                         params->dest_height,
     286             :                                                         params->scaler_taps,
     287             :                                                         params->subsample_position);
     288             :                 } else {
     289             :                         /* horizontal scale */
     290           0 :                         dwb_program_horz_scalar(dwbc20, params->cnv_params.src_width,
     291             :                                                         params->dest_width,
     292             :                                                         params->scaler_taps);
     293             : 
     294             :                         /* vertical scale */
     295           0 :                         dwb_program_vert_scalar(dwbc20, params->cnv_params.src_height,
     296             :                                                         params->dest_height,
     297             :                                                         params->scaler_taps,
     298             :                                                         params->subsample_position);
     299             :                 }
     300             :         }
     301             : 
     302           0 : }
     303             : 
     304             : const struct dwbc_funcs dcn20_dwbc_funcs = {
     305             :         .get_caps               = dwb2_get_caps,
     306             :         .enable                 = dwb2_enable,
     307             :         .disable                = dwb2_disable,
     308             :         .update                 = dwb2_update,
     309             :         .is_enabled             = dwb2_is_enabled,
     310             :         .set_stereo             = dwb2_set_stereo,
     311             :         .set_new_content        = dwb2_set_new_content,
     312             :         .set_warmup             = dwb2_set_warmup,
     313             :         .dwb_set_scaler         = dwb2_set_scaler,
     314             : };
     315             : 
     316           0 : void dcn20_dwbc_construct(struct dcn20_dwbc *dwbc20,
     317             :                 struct dc_context *ctx,
     318             :                 const struct dcn20_dwbc_registers *dwbc_regs,
     319             :                 const struct dcn20_dwbc_shift *dwbc_shift,
     320             :                 const struct dcn20_dwbc_mask *dwbc_mask,
     321             :                 int inst)
     322             : {
     323           0 :         dwbc20->base.ctx = ctx;
     324             : 
     325           0 :         dwbc20->base.inst = inst;
     326           0 :         dwbc20->base.funcs = &dcn20_dwbc_funcs;
     327             : 
     328           0 :         dwbc20->dwbc_regs = dwbc_regs;
     329           0 :         dwbc20->dwbc_shift = dwbc_shift;
     330           0 :         dwbc20->dwbc_mask = dwbc_mask;
     331           0 : }
     332             : 

Generated by: LCOV version 1.14