1 /* 2 * Copyright (C) 2020 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef DISPLAYCOLOR_GS101_H_ 18 #define DISPLAYCOLOR_GS101_H_ 19 20 #include <array> 21 #include <functional> 22 #include <memory> 23 24 #include <displaycolor/displaycolor.h> 25 26 namespace displaycolor { 27 28 /// An interface for accessing GS101 color management data. 29 class IDisplayColorGS101 : public IDisplayColorGeneric { 30 private: 31 /// Register data for matrices in DPP and DQE. 32 template <typename T, size_t kDimensions> 33 struct MatrixData { 34 /** 35 * DQE0_GAMMA_MATRIX_COEFF0..4[GAMMA_MATRIX_COEFF_xx] 36 * DQE0_LINEAR_MATRIX_COEFF0..4[LINEAR_MATRIX_COEFF_xx] 37 * DPP_HDR_LSI_L#_GM_COEF0..8[COEF], #(0..5) 38 */ 39 std::array<T, kDimensions * kDimensions> coeffs{}; 40 41 /** 42 * DQE0_GAMMA_MATRIX_OFFSET0..1[GAMMA_MATRIX_COEFF_n] 43 * DQE0_LINEAR_MATRIX_OFFSET0..1[LINEAR_MATRIX_COEFF_n] 44 * DPP_HDR_LSI_L#_GM_OFFS0..2[OFFS], #(0..5) 45 */ 46 std::array<T, kDimensions> offsets{}; 47 }; 48 49 public: 50 /// LUT with programmable X and Y 51 template <typename XT, typename YT, size_t N> 52 struct TransferFunctionData { 53 std::array<XT, N> posx; 54 std::array<YT, N> posy; 55 }; 56 57 template <typename XType, typename YType, size_t N> 58 struct FlexLutConfigType { 59 // keep XContainer, YContainer and kLutLen for backward compatibility. 60 using XContainer = XType; 61 using YContainer = YType; 62 static constexpr size_t kLutLen = N; 63 64 TransferFunctionData<XContainer, YContainer, kLutLen> tf_data; 65 }; 66 67 template <typename DType, size_t N> 68 struct MatrixConfigType { 69 using Container = DType; 70 static constexpr size_t kDimensions = N; 71 72 MatrixData<Container, kDimensions> matrix_data; 73 }; 74 75 /** 76 * @brief Interface for accessing data for DPP stages. 77 * 78 * Note that the data returned by this interface is applicable to both DPP 79 * in DPU and the HDR blocks in G2D. These two IPs' register specs are 80 * identical, with one caveat: While all G2D layers support display tone 81 * mapping (DTM) for HDR10+, only DPP layers L1/L3/L5 support this stage. 82 */ 83 struct IDppData { 84 struct IEotfData { 85 /// Register data for the EOTF LUT in DPP. 86 using EotfData = DisplayStage<FlexLutConfigType<uint16_t, uint32_t, 129>>; 87 88 /// Get data for the EOTF LUT. 89 virtual const EotfData& EotfLut() const = 0; ~IEotfDataIDppData::IEotfData90 virtual ~IEotfData() {} 91 }; 92 93 struct IGmData { 94 public: 95 /// Register data for the gamut mapping (GM) matrix in DPP. 96 using GmData = DisplayStage<MatrixConfigType<uint32_t, 3>>; 97 98 /// Get data for the gamut mapping (GM) matrix. 99 virtual const GmData& Gm() const = 0; ~IGmDataIDppData::IGmData100 virtual ~IGmData() {} 101 }; 102 103 struct IDtmData { 104 private: 105 struct Rgb2YData { 106 uint16_t coeff_r; // DPP_HDR_LSI_L#_TM_COEF[COEFR] #(1, 3, 5) 107 uint16_t coeff_g; // DPP_HDR_LSI_L#_TM_COEF[COEFG] #(1, 3, 5) 108 uint16_t coeff_b; // DPP_HDR_LSI_L#_TM_COEF[COEFB] #(1, 3, 5) 109 uint16_t rng_x_min; // DPP_HDR_LSI_L#_TM_RNGX[MINX] #(1, 3, 5) 110 uint16_t rng_x_max; // DPP_HDR_LSI_L#_TM_RNGX[MAXX] #(1, 3, 5) 111 uint16_t rng_y_min; // DPP_HDR_LSI_L#_TM_RNGY[MINY] #(1, 3, 5) 112 uint16_t rng_y_max; // DPP_HDR_LSI_L#_TM_RNGY[MAXY] #(1, 3, 5) 113 }; 114 115 // To avoid updating legacy source code after separate lut and rgb2y, 116 // use inheritance instead of composition. 117 struct DtmConfigType : public FlexLutConfigType<uint32_t, uint32_t, 33>, 118 public Rgb2YData {}; 119 120 public: 121 /** 122 * @brief Register data for the DTM stage in DPP. 123 * 124 * Note that this data is only applicable to DPP in layers L1/L3/L5 125 * and G2D layers. Other DPPs do not support DTM. DTM data will be 126 * provided for any layer whose DisplayScene::LayerColorData 127 * contains HDR dynamic metadata. It is the caller's (typically 128 * HWComposer) responsibility to validate layers and HW capabilities 129 * correctly, before calling this API. 130 */ 131 using DtmData = DisplayStage<DtmConfigType>; 132 133 /** 134 * @brief Get data for the DTM LUT. Only used for HDR10+, and only 135 * applicable to DPPs that support this functionality. 136 */ 137 virtual const DtmData& Dtm() const = 0; ~IDtmDataIDppData::IDtmData138 virtual ~IDtmData() {} 139 }; 140 141 struct IOetfData { 142 /// Register data for the OETF LUT in DPP. 143 using OetfData = DisplayStage<FlexLutConfigType<uint32_t, uint16_t, 33>>; 144 145 /// Get data for the OETF LUT. 146 virtual const OetfData& OetfLut() const = 0; ~IOetfDataIDppData::IOetfData147 virtual ~IOetfData() {} 148 }; 149 }; 150 151 struct IDpp 152 : public IStageDataCollection<IDppData::IEotfData, IDppData::IGmData, 153 IDppData::IDtmData, IDppData::IOetfData> { 154 /// Get the solid color 155 virtual const Color SolidColor() const = 0; 156 ~IDppIDpp157 virtual ~IDpp() {} 158 }; 159 160 /// Interface for accessing data for DQE stages. 161 struct IDqeData { 162 public: 163 struct IDqeControlData { 164 private: 165 /// 32-bit DQE dither register, same definition as in uapi 166 struct DitherConfigType { 167 uint8_t en : 1; 168 uint8_t mode : 1; 169 uint8_t frame_con : 1; 170 uint8_t frame_offset : 2; 171 uint8_t table_sel_r : 1; 172 uint8_t table_sel_g : 1; 173 uint8_t table_sel_b : 1; 174 uint32_t reserved : 24; 175 }; 176 177 struct DqeControlConfigType { 178 /// DQE force 10bpc mode 179 bool force_10bpc = false; 180 181 /// flag to use cgc_dither 182 bool cgc_dither_override = false; 183 /// CGC dither register value 184 union { 185 DitherConfigType cgc_dither_reg = {}; 186 uint16_t cgc_dither; // only lowest 16 bit is used 187 }; 188 189 /// flag to use disp_dither 190 bool disp_dither_override = false; 191 /// Display dither register value 192 union { 193 DitherConfigType disp_dither_reg = {}; 194 uint8_t disp_dither; // only lowest 8 bit is used 195 }; 196 }; 197 198 public: 199 /// DQE control data 200 using DqeControlData = DisplayStage<DqeControlConfigType>; 201 202 /// Get DQE control data 203 virtual const DqeControlData& DqeControl() const = 0; ~IDqeControlDataIDqeData::IDqeControlData204 virtual ~IDqeControlData() {} 205 }; 206 207 struct IGammaMatrixData { 208 /// Register data for the gamma and linear matrices in DQE. 209 using DqeMatrixData = DisplayStage<MatrixConfigType<uint16_t, 3>>; 210 211 /// Get data for the gamma-space matrix. 212 virtual const DqeMatrixData& GammaMatrix() const = 0; ~IGammaMatrixDataIDqeData::IGammaMatrixData213 virtual ~IGammaMatrixData() {} 214 }; 215 216 struct IDegammaLutData { 217 private: 218 struct DegammaConfigType { 219 using Container = uint16_t; 220 static constexpr size_t kLutLen = 65; 221 222 std::array<Container, kLutLen> values; 223 }; 224 225 public: 226 /// Register data for the degamma LUT in DQE. 227 using DegammaLutData = DisplayStage<DegammaConfigType>; 228 229 /// Get data for the 1D de-gamma LUT (EOTF). 230 virtual const DegammaLutData& DegammaLut() const = 0; ~IDegammaLutDataIDqeData::IDegammaLutData231 virtual ~IDegammaLutData() {} 232 }; 233 234 struct ILinearMatrixData { 235 /// Register data for the gamma and linear matrices in DQE. 236 using DqeMatrixData = DisplayStage<MatrixConfigType<uint16_t, 3>>; 237 238 /// Get data for the linear-space matrix. 239 virtual const DqeMatrixData& LinearMatrix() const = 0; ~ILinearMatrixDataIDqeData::ILinearMatrixData240 virtual ~ILinearMatrixData() {} 241 }; 242 243 struct ICgcData { 244 private: 245 struct CgcConfigType { 246 using Container = uint32_t; 247 static constexpr size_t kChannelLutLen = 2457; 248 // nodes number at each dimension of this 3d lut 249 static constexpr size_t kVirtualChanelLen = 17; 250 251 /// DQE0_CGC_LUT_R_N{0-2456} (8 bit: 0~2047, 10 bit: 0~8191) 252 std::array<Container, kChannelLutLen> r_values{}; 253 /// DQE0_CGC_LUT_G_N{0-2456} (8 bit: 0~2047, 10 bit: 0~8191) 254 std::array<Container, kChannelLutLen> g_values{}; 255 /// DQE0_CGC_LUT_B_N{0-2456} (8 bit: 0~2047, 10 bit: 0~8191) 256 std::array<Container, kChannelLutLen> b_values{}; 257 }; 258 259 public: 260 /// Register data for CGC. 261 using CgcData = DisplayStage<CgcConfigType>; 262 263 /// Get data for the Color Gamut Conversion stage (3D LUT). 264 virtual const CgcData& Cgc() const = 0; ~ICgcDataIDqeData::ICgcData265 virtual ~ICgcData() {} 266 }; 267 268 struct IRegammaLutData { 269 private: 270 struct RegammaConfigType { 271 using Container = uint16_t; 272 static constexpr size_t kChannelLutLen = 65; 273 274 /// REGAMMA LUT_R_{00-64} (8 bit: 0~1024, 10 bit: 0~4096) 275 std::array<Container, kChannelLutLen> r_values{}; 276 /// REGAMMA LUT_G_{00-64} (8 bit: 0~1024, 10 bit: 0~4096) 277 std::array<Container, kChannelLutLen> g_values{}; 278 /// REGAMMA LUT_B_{00-64} (8 bit: 0~1024, 10 bit: 0~4096) 279 std::array<Container, kChannelLutLen> b_values{}; 280 }; 281 282 public: 283 /// Register data for the regamma LUT. 284 using RegammaLutData = DisplayStage<RegammaConfigType>; 285 286 /// Get data for the 3x1D re-gamma LUTa (OETF). 287 virtual const RegammaLutData& RegammaLut() const = 0; ~IRegammaLutDataIDqeData::IRegammaLutData288 virtual ~IRegammaLutData() {} 289 }; 290 }; 291 292 struct IDqe : public IStageDataCollection< 293 IDqeData::IDqeControlData, IDqeData::IGammaMatrixData, 294 IDqeData::IDegammaLutData, IDqeData::ILinearMatrixData, 295 IDqeData::ICgcData, IDqeData::IRegammaLutData> { ~IDqeIDqe296 virtual ~IDqe() {} 297 }; 298 299 /// Interface for accessing particular display color data 300 struct IDisplayPipelineData { 301 /** 302 * @brief Get handles to Display Pre-Processor (DPP) data accessors. 303 * 304 * The order of the returned DPP handles match the order of the 305 * LayerColorData provided as part of struct DisplayScene and 306 * IDisplayColorGeneric::Update(). 307 */ 308 virtual std::vector<std::reference_wrapper<const IDpp>> Dpp() const = 0; 309 310 /// Get a handle to Display Quality Enhancer (DQE) data accessors. 311 virtual const IDqe& Dqe() const = 0; 312 313 /// Get a handle to panel data accessors 314 virtual const IPanel& Panel() const = 0; 315 ~IDisplayPipelineDataIDisplayPipelineData316 virtual ~IDisplayPipelineData() {} 317 }; 318 319 /// Get pipeline color data for specified display type 320 // deprecated by the 'int64_t display' version 321 virtual const IDisplayPipelineData* GetPipelineData(DisplayType display) const = 0; 322 virtual const IDisplayPipelineData* GetPipelineData(const int64_t display) const = 0; 323 ~IDisplayColorGS101()324 virtual ~IDisplayColorGS101() {} 325 }; 326 327 extern "C" { 328 329 /// Get the GS101 instance. 330 IDisplayColorGS101* GetDisplayColorGS101(const std::vector<DisplayInfo> &display_info); 331 } 332 333 } // namespace displaycolor 334 335 #endif // DISPLAYCOLOR_GS101_H_ 336