1/*
2* Copyright (c) 2016-2017, The Linux Foundation. All rights reserved.
3*
4* Redistribution and use in source and binary forms, with or without
5* modification, are permitted provided that the following conditions are
6* met:
7*     * Redistributions of source code must retain the above copyright
8*       notice, this list of conditions and the following disclaimer.
9*     * Redistributions in binary form must reproduce the above
10*       copyright notice, this list of conditions and the following
11*       disclaimer in the documentation and/or other materials provided
12*       with the distribution.
13*     * Neither the name of The Linux Foundation nor the names of its
14*       contributors may be used to endorse or promote products derived
15*       from this software without specific prior written permission.
16*
17* THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
18* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
19* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
20* ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
21* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
24* BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
25* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
26* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
27* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28*/
29
30#include <stdio.h>
31#include <utils/debug.h>
32
33#include "hw_scale_drm.h"
34
35#define __CLASS__ "HWScaleDRM"
36
37namespace sdm {
38
39static uint32_t GetScalingFilter(ScalingFilterConfig filter_cfg) {
40  switch (filter_cfg) {
41    case kFilterEdgeDirected:
42      return FILTER_EDGE_DIRECTED_2D;
43    case kFilterCircular:
44      return FILTER_CIRCULAR_2D;
45    case kFilterSeparable:
46      return FILTER_SEPARABLE_1D;
47    case kFilterBilinear:
48      return FILTER_BILINEAR;
49    default:
50      DLOGE("Invalid Scaling Filter");
51      return kFilterMax;
52  }
53}
54
55static uint32_t GetAlphaInterpolation(HWAlphaInterpolation alpha_filter_cfg) {
56  switch (alpha_filter_cfg) {
57    case kInterpolationPixelRepeat:
58      return FILTER_ALPHA_DROP_REPEAT;
59    case kInterpolationBilinear:
60      return FILTER_ALPHA_BILINEAR;
61    default:
62      DLOGE("Invalid Alpha Interpolation");
63      return kInterpolationMax;
64  }
65}
66
67void HWScaleDRM::SetPlaneScaler(const HWScaleData &scale_data, SDEScaler *scaler) {
68  if (version_ == Version::V2) {
69    SetPlaneScalerV2(scale_data, &scaler->scaler_v2);
70  }
71}
72
73void HWScaleDRM::SetPlaneScalerV2(const HWScaleData &scale_data, sde_drm_scaler_v2 *scaler) {
74  if (!scale_data.enable.scale && !scale_data.enable.direction_detection &&
75      !scale_data.enable.detail_enhance) {
76    return;
77  }
78
79  scaler->enable = scale_data.enable.scale;
80  scaler->dir_en = scale_data.enable.direction_detection;
81  scaler->de.enable = scale_data.detail_enhance.enable;
82
83  for (int i = 0; i < SDE_MAX_PLANES; i++) {
84    const HWPlane &plane = scale_data.plane[i];
85    scaler->init_phase_x[i] = plane.init_phase_x;
86    scaler->phase_step_x[i] = plane.phase_step_x;
87    scaler->init_phase_y[i] = plane.init_phase_y;
88    scaler->phase_step_y[i] = plane.phase_step_y;
89
90    // TODO(user): Remove right, bottom from HWPlane and rename to LR, TB similar to qseed3
91    // Also remove roi_width which is unused.
92    scaler->pe.num_ext_pxls_lr[i] = plane.left.extension;
93    scaler->pe.num_ext_pxls_tb[i] = plane.top.extension;
94
95    scaler->pe.left_ftch[i] = plane.left.overfetch;
96    scaler->pe.top_ftch[i] = plane.top.overfetch;
97    scaler->pe.right_ftch[i] = plane.right.overfetch;
98    scaler->pe.btm_ftch[i] = plane.bottom.overfetch;
99
100    scaler->pe.left_rpt[i] = plane.left.repeat;
101    scaler->pe.top_rpt[i] = plane.top.repeat;
102    scaler->pe.right_rpt[i] = plane.right.repeat;
103    scaler->pe.btm_rpt[i] = plane.bottom.repeat;
104
105    scaler->preload_x[i] = UINT32(plane.preload_x);
106    scaler->preload_y[i] = UINT32(plane.preload_y);
107
108    scaler->src_width[i] = plane.src_width;
109    scaler->src_height[i] = plane.src_height;
110  }
111
112  scaler->dst_width = scale_data.dst_width;
113  scaler->dst_height = scale_data.dst_height;
114
115  scaler->y_rgb_filter_cfg = GetScalingFilter(scale_data.y_rgb_filter_cfg);
116  scaler->uv_filter_cfg = GetScalingFilter(scale_data.uv_filter_cfg);
117  scaler->alpha_filter_cfg = GetAlphaInterpolation(scale_data.alpha_filter_cfg);
118  scaler->blend_cfg = scale_data.blend_cfg;
119
120  scaler->lut_flag = (scale_data.lut_flag.lut_swap ? SCALER_LUT_SWAP : 0) |
121                     (scale_data.lut_flag.lut_dir_wr ? SCALER_LUT_DIR_WR : 0) |
122                     (scale_data.lut_flag.lut_y_cir_wr ? SCALER_LUT_Y_CIR_WR : 0) |
123                     (scale_data.lut_flag.lut_uv_cir_wr ? SCALER_LUT_UV_CIR_WR : 0) |
124                     (scale_data.lut_flag.lut_y_sep_wr ? SCALER_LUT_Y_SEP_WR : 0) |
125                     (scale_data.lut_flag.lut_uv_sep_wr ? SCALER_LUT_UV_SEP_WR : 0);
126
127  scaler->dir_lut_idx = scale_data.dir_lut_idx;
128  scaler->y_rgb_cir_lut_idx = scale_data.y_rgb_cir_lut_idx;
129  scaler->uv_cir_lut_idx = scale_data.uv_cir_lut_idx;
130  scaler->y_rgb_sep_lut_idx = scale_data.y_rgb_sep_lut_idx;
131  scaler->uv_sep_lut_idx = scale_data.uv_sep_lut_idx;
132
133  /* TODO(user): Uncomment when de support is added
134  if (scaler->de.enable) {
135    sde_drm_de_v1 *det_enhance = &scaler->de;
136    det_enhance->sharpen_level1 = scale_data.detail_enhance.sharpen_level1;
137    det_enhance->sharpen_level2 = scale_data.detail_enhance.sharpen_level2;
138    det_enhance->clip = scale_data.detail_enhance.clip;
139    det_enhance->limit = scale_data.detail_enhance.limit;
140    det_enhance->thr_quiet = scale_data.detail_enhance.thr_quiet;
141    det_enhance->thr_dieout = scale_data.detail_enhance.thr_dieout;
142    det_enhance->thr_low = scale_data.detail_enhance.thr_low;
143    det_enhance->thr_high = scale_data.detail_enhance.thr_high;
144    det_enhance->prec_shift = scale_data.detail_enhance.prec_shift;
145
146    for (int i = 0; i < SDE_MAX_DE_CURVES; i++) {
147      det_enhance->adjust_a[i] = scale_data.detail_enhance.adjust_a[i];
148      det_enhance->adjust_b[i] = scale_data.detail_enhance.adjust_b[i];
149      det_enhance->adjust_c[i] = scale_data.detail_enhance.adjust_c[i];
150    }
151  }
152  */
153
154  return;
155}
156
157}  // namespace sdm
158