1d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin/*
21c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed* Copyright (c) 2014 - 2016, The Linux Foundation. All rights reserved.
3d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*
4d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* Redistribution and use in source and binary forms, with or without modification, are permitted
5d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* provided that the following conditions are met:
6d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*    * Redistributions of source code must retain the above copyright notice, this list of
7d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*      conditions and the following disclaimer.
8d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*    * Redistributions in binary form must reproduce the above copyright notice, this list of
9d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*      conditions and the following disclaimer in the documentation and/or other materials provided
10d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*      with the distribution.
11d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*    * Neither the name of The Linux Foundation nor the names of its contributors may be used to
12d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*      endorse or promote products derived from this software without specific prior written
13d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*      permission.
14d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*
15d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
16d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* NON-INFRINGEMENT ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
18d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
19d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
20d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
21d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
22d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin*/
24d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
25d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#include <math.h>
26d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#include <utils/constants.h>
27d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#include <utils/debug.h>
28d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#include <utils/rect.h>
291c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed#include <utils/formats.h>
30d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#include <dlfcn.h>
31d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
32d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#include "resource_default.h"
33d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
34d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#define __CLASS__ "ResourceDefault"
35d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
36d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinnamespace sdm {
37d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
38d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::Init(const HWResourceInfo &hw_res_info) {
39d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
40d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
41829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  num_pipe_ = hw_res_info.num_vig_pipe + hw_res_info.num_rgb_pipe + hw_res_info.num_dma_pipe;
42d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
43829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  if (!num_pipe_) {
44829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    DLOGE("Number of H/W pipes is Zero!");
45d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorParameters;
46d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
47d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
48829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  src_pipes_ = new SourcePipe[num_pipe_];
49d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  hw_res_info_ = hw_res_info;
50d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
51829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  // Priority order of pipes: VIG, RGB, DMA
52829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t vig_index = 0;
53829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t rgb_index = hw_res_info_.num_vig_pipe;
54829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t dma_index = rgb_index + hw_res_info_.num_rgb_pipe;
55d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
56829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  for (uint32_t i = 0; i < num_pipe_; i++) {
57829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    const HWPipeCaps &pipe_caps = hw_res_info_.hw_pipes.at(i);
58829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    if (pipe_caps.type == kPipeTypeVIG) {
59829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[vig_index].type = kPipeTypeVIG;
60829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[vig_index].index = i;
61829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[vig_index].mdss_pipe_id = pipe_caps.id;
62829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      vig_index++;
63829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    } else if (pipe_caps.type == kPipeTypeRGB) {
64829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[rgb_index].type = kPipeTypeRGB;
65829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[rgb_index].index = i;
66829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[rgb_index].mdss_pipe_id = pipe_caps.id;
67829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      rgb_index++;
68829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    } else if (pipe_caps.type == kPipeTypeDMA) {
69829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[dma_index].type = kPipeTypeDMA;
70829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[dma_index].index = i;
71829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      src_pipes_[dma_index].mdss_pipe_id = pipe_caps.id;
72829790261efb161bff68251b0a1baceae6610430Mekala Natarajan      dma_index++;
73829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    }
74d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
75d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
76d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  for (uint32_t i = 0; i < num_pipe_; i++) {
771c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed    src_pipes_[i].priority = INT(i);
78d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
79d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
80d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGI("hw_rev=%x, DMA=%d RGB=%d VIG=%d", hw_res_info_.hw_revision, hw_res_info_.num_dma_pipe,
81d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    hw_res_info_.num_rgb_pipe, hw_res_info_.num_vig_pipe);
82d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
83d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (hw_res_info_.max_scale_down < 1 || hw_res_info_.max_scale_up < 1) {
84d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGE("Max scaling setting is invalid! max_scale_down = %d, max_scale_up = %d",
85d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin          hw_res_info_.max_scale_down, hw_res_info_.max_scale_up);
86d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    hw_res_info_.max_scale_down = 1;
87d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    hw_res_info_.max_scale_up = 1;
88d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
89d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
90d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // TODO(user): clean it up, query from driver for initial pipe status.
91d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#ifndef SDM_VIRTUAL_DRIVER
92829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  rgb_index = hw_res_info_.num_vig_pipe;
93829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  src_pipes_[rgb_index].owner = kPipeOwnerKernelMode;
94829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  src_pipes_[rgb_index + 1].owner = kPipeOwnerKernelMode;
95d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin#endif
96d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
97d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return error;
98d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
99d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
100d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::Deinit() {
101829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  delete[] src_pipes_;
102d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
103d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
104d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
105d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::RegisterDisplay(DisplayType type,
106d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                              const HWDisplayAttributes &attributes,
107d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                              const HWPanelInfo &hw_panel_info,
108d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                              Handle *display_ctx) {
109d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
110d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
111d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWBlockType hw_block_id = kHWBlockMax;
112d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  switch (type) {
113d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  case kPrimary:
114d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (!hw_block_ctx_[kHWPrimary].is_in_use) {
115d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      hw_block_id = kHWPrimary;
116d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
117d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    break;
118d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
119d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  case kHDMI:
120d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (!hw_block_ctx_[kHWHDMI].is_in_use) {
121d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      hw_block_id = kHWHDMI;
122d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
123d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    break;
124d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
125d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  default:
126d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGW("RegisterDisplay, invalid type %d", type);
127d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorParameters;
128d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
129d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
130d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (hw_block_id == kHWBlockMax) {
131d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorResources;
132d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
133d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
134d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayResourceContext *display_resource_ctx = new DisplayResourceContext();
135d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!display_resource_ctx) {
136d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorMemory;
137d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
138d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
139d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  hw_block_ctx_[hw_block_id].is_in_use = true;
140d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
141d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  display_resource_ctx->display_attributes = attributes;
142d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  display_resource_ctx->hw_block_id = hw_block_id;
143d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
144d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!display_resource_ctx->display_attributes.is_device_split) {
145d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    display_resource_ctx->display_attributes.split_left = attributes.x_pixels;
146d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
147d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
148d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  *display_ctx = display_resource_ctx;
149d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return error;
150d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
151d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
152d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::UnregisterDisplay(Handle display_ctx) {
153d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayResourceContext *display_resource_ctx =
154d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          reinterpret_cast<DisplayResourceContext *>(display_ctx);
155d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Purge(display_ctx);
156d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
157d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  hw_block_ctx_[display_resource_ctx->hw_block_id].is_in_use = false;
158d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
159d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  delete display_resource_ctx;
160d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
161d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
162d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
163d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
164d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinvoid ResourceDefault::ReconfigureDisplay(Handle display_ctx, const HWDisplayAttributes &attributes,
165d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                    const HWPanelInfo &hw_panel_info) {
166d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SCOPE_LOCK(locker_);
167d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
168d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayResourceContext *display_resource_ctx =
169d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          reinterpret_cast<DisplayResourceContext *>(display_ctx);
170d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
171d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  display_resource_ctx->display_attributes = attributes;
172d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
173d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
174d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::Start(Handle display_ctx) {
175d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  locker_.Lock();
176d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
177d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
178d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
179d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
180d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::Stop(Handle display_ctx) {
181d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  locker_.Unlock();
182d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
183d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
184d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
185d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
186d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::Acquire(Handle display_ctx, HWLayers *hw_layers) {
187d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayResourceContext *display_resource_ctx =
188d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          reinterpret_cast<DisplayResourceContext *>(display_ctx);
189d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
190d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
191d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const struct HWLayersInfo &layer_info = hw_layers->info;
192d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWBlockType hw_block_id = display_resource_ctx->hw_block_id;
193d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
194d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "==== Resource reserving start: hw_block = %d ====", hw_block_id);
195d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
196d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (layer_info.count > 1) {
197d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "More than one FB layers");
198d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorResources;
199d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
200d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
201d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Layer &layer = layer_info.stack->layers[layer_info.index[0]];
202d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
203d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (layer.composition != kCompositionGPUTarget) {
204d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "Not an FB layer");
205d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorParameters;
206d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
207d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
208d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = Config(display_resource_ctx, hw_layers);
209d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
210d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "Resource config failed");
211d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
212d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
213d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
214d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  for (uint32_t i = 0; i < num_pipe_; i++) {
215d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (src_pipes_[i].hw_block_id == hw_block_id && src_pipes_[i].owner == kPipeOwnerUserMode) {
216d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      src_pipes_[i].ResetState();
217d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
218d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
219d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
220829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t left_index = num_pipe_;
221829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t right_index = num_pipe_;
222d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  bool need_scale = false;
223d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
224d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  struct HWLayerConfig &layer_config = hw_layers->config[0];
225d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
226d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo *left_pipe = &layer_config.left_pipe;
227d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo *right_pipe = &layer_config.right_pipe;
228d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
229d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // left pipe is needed
230d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (left_pipe->valid) {
231d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    need_scale = IsScalingNeeded(left_pipe);
232d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_index = GetPipe(hw_block_id, need_scale);
233d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (left_index >= num_pipe_) {
234d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      DLOGV_IF(kTagResources, "Get left pipe failed: hw_block_id = %d, need_scale = %d",
235d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin               hw_block_id, need_scale);
236d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      ResourceStateLog();
237d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      goto CleanupOnError;
238d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
239d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
240d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
241d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = SetDecimationFactor(left_pipe);
242d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
243d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    goto CleanupOnError;
244d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
245d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
246d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!right_pipe->valid) {
247d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    // assign single pipe
248d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (left_index < num_pipe_) {
249d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      left_pipe->pipe_id = src_pipes_[left_index].mdss_pipe_id;
250d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
251d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "1 pipe acquired for FB layer, left_pipe = %x", left_pipe->pipe_id);
252d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNone;
253d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
254d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
255d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  need_scale = IsScalingNeeded(right_pipe);
256d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
257d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  right_index = GetPipe(hw_block_id, need_scale);
258d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (right_index >= num_pipe_) {
259d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "Get right pipe failed: hw_block_id = %d, need_scale = %d", hw_block_id,
260d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin             need_scale);
261d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    ResourceStateLog();
262d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    goto CleanupOnError;
263d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
264d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
265d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (src_pipes_[right_index].priority < src_pipes_[left_index].priority) {
266d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    // Swap pipe based on priority
267d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Swap(left_index, right_index);
268d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
269d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
270d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // assign dual pipes
271d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  left_pipe->pipe_id = src_pipes_[left_index].mdss_pipe_id;
272d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  right_pipe->pipe_id = src_pipes_[right_index].mdss_pipe_id;
273d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
274d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = SetDecimationFactor(right_pipe);
275d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
276d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    goto CleanupOnError;
277d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
278d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
279d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "2 pipes acquired for FB layer, left_pipe = %x, right_pipe = %x",
280d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin           left_pipe->pipe_id,  right_pipe->pipe_id);
281d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
282d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
283d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
284d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinCleanupOnError:
285d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "Resource reserving failed! hw_block = %d", hw_block_id);
286d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
287d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorResources;
288d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
289d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
290d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::PostPrepare(Handle display_ctx, HWLayers *hw_layers) {
291d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SCOPE_LOCK(locker_);
292d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
293d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
294d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
295d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
296d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::PostCommit(Handle display_ctx, HWLayers *hw_layers) {
297d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SCOPE_LOCK(locker_);
298d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayResourceContext *display_resource_ctx =
299d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          reinterpret_cast<DisplayResourceContext *>(display_ctx);
300d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWBlockType hw_block_id = display_resource_ctx->hw_block_id;
301d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  uint64_t frame_count = display_resource_ctx->frame_count;
302d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
303d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "Resource for hw_block = %d, frame_count = %d", hw_block_id, frame_count);
304d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
305d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // handoff pipes which are used by splash screen
306d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if ((frame_count == 0) && (hw_block_id == kHWPrimary)) {
307d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    for (uint32_t i = 0; i < num_pipe_; i++) {
308d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      if (src_pipes_[i].hw_block_id == hw_block_id && src_pipes_[i].owner == kPipeOwnerKernelMode) {
309d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin        src_pipes_[i].owner = kPipeOwnerUserMode;
310d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      }
311d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
312d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
313d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
314d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  display_resource_ctx->frame_count++;
315d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
316d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
317d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
318d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
319d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinvoid ResourceDefault::Purge(Handle display_ctx) {
320d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SCOPE_LOCK(locker_);
321d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
322d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayResourceContext *display_resource_ctx =
323d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          reinterpret_cast<DisplayResourceContext *>(display_ctx);
324d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWBlockType hw_block_id = display_resource_ctx->hw_block_id;
325d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
326d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  for (uint32_t i = 0; i < num_pipe_; i++) {
327d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (src_pipes_[i].hw_block_id == hw_block_id && src_pipes_[i].owner == kPipeOwnerUserMode) {
328d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      src_pipes_[i].ResetState();
329d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
330d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
331d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "display id = %d", display_resource_ctx->hw_block_id);
332d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
333d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
334d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::SetMaxMixerStages(Handle display_ctx, uint32_t max_mixer_stages) {
335d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SCOPE_LOCK(locker_);
336d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
337d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
338d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
339d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
340d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinuint32_t ResourceDefault::SearchPipe(HWBlockType hw_block_id, SourcePipe *src_pipes,
341d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                uint32_t num_pipe) {
342829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t index = num_pipe_;
343d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SourcePipe *src_pipe;
344d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
345d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // search the pipe being used
346d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  for (uint32_t i = 0; i < num_pipe; i++) {
347d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    src_pipe = &src_pipes[i];
348d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (src_pipe->owner == kPipeOwnerUserMode && src_pipe->hw_block_id == kHWBlockMax) {
349d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      index = src_pipe->index;
350d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      src_pipe->hw_block_id = hw_block_id;
351d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      break;
352d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
353d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
354d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
355d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return index;
356d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
357d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
358d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinuint32_t ResourceDefault::NextPipe(PipeType type, HWBlockType hw_block_id) {
359d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  uint32_t num_pipe = 0;
360d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  SourcePipe *src_pipes = NULL;
361d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
362d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  switch (type) {
363d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  case kPipeTypeVIG:
364829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    src_pipes = &src_pipes_[0];
365d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    num_pipe = hw_res_info_.num_vig_pipe;
366d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    break;
367d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  case kPipeTypeRGB:
368829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    src_pipes = &src_pipes_[hw_res_info_.num_vig_pipe];
369d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    num_pipe = hw_res_info_.num_rgb_pipe;
370d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    break;
371d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  case kPipeTypeDMA:
372d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  default:
373829790261efb161bff68251b0a1baceae6610430Mekala Natarajan    src_pipes = &src_pipes_[hw_res_info_.num_vig_pipe + hw_res_info_.num_rgb_pipe];
374d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    num_pipe = hw_res_info_.num_dma_pipe;
375d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    break;
376d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
377d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
378d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return SearchPipe(hw_block_id, src_pipes, num_pipe);
379d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
380d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
381d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinuint32_t ResourceDefault::GetPipe(HWBlockType hw_block_id, bool need_scale) {
382829790261efb161bff68251b0a1baceae6610430Mekala Natarajan  uint32_t index = num_pipe_;
383d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
384d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // The default behavior is to assume RGB and VG pipes have scalars
385d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!need_scale) {
386d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    index = NextPipe(kPipeTypeDMA, hw_block_id);
387d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
388d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
389d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if ((index >= num_pipe_) && (!need_scale || !hw_res_info_.has_non_scalar_rgb)) {
390d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    index = NextPipe(kPipeTypeRGB, hw_block_id);
391d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
392d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
393d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (index >= num_pipe_) {
394d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    index = NextPipe(kPipeTypeVIG, hw_block_id);
395d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
396d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
397d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return index;
398d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
399d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
400d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinbool ResourceDefault::IsScalingNeeded(const HWPipeInfo *pipe_info) {
401d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const LayerRect &src_roi = pipe_info->src_roi;
402d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const LayerRect &dst_roi = pipe_info->dst_roi;
403d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
404d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return ((dst_roi.right - dst_roi.left) != (src_roi.right - src_roi.left)) ||
405d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin          ((dst_roi.bottom - dst_roi.top) != (src_roi.bottom - src_roi.top));
406d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
407d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
408d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinvoid ResourceDefault::ResourceStateLog() {
409d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "==== resource manager pipe state ====");
410d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  uint32_t i;
411d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  for (i = 0; i < num_pipe_; i++) {
412d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    SourcePipe *src_pipe = &src_pipes_[i];
413d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "index = %d, id = %x, hw_block = %d, owner = %s",
414d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                 src_pipe->index, src_pipe->mdss_pipe_id, src_pipe->hw_block_id,
415d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                 (src_pipe->owner == kPipeOwnerUserMode) ? "user mode" : "kernel mode");
416d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
417d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
418d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
419d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::SrcSplitConfig(DisplayResourceContext *display_resource_ctx,
420d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                        const LayerRect &src_rect, const LayerRect &dst_rect,
421d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                        HWLayerConfig *layer_config) {
422d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo *left_pipe = &layer_config->left_pipe;
423d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo *right_pipe = &layer_config->right_pipe;
424d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float src_width = src_rect.right - src_rect.left;
425d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_width = dst_rect.right - dst_rect.left;
426d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
427d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // Layer cannot qualify for SrcSplit if source or destination width exceeds max pipe width.
428d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if ((src_width > hw_res_info_.max_pipe_width) || (dst_width > hw_res_info_.max_pipe_width)) {
429d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    SplitRect(src_rect, dst_rect, &left_pipe->src_roi, &left_pipe->dst_roi, &right_pipe->src_roi,
430d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin              &right_pipe->dst_roi);
431d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->valid = true;
432d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->valid = true;
433d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  } else {
434d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->src_roi = src_rect;
435d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->dst_roi = dst_rect;
436d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->valid = true;
437d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->Reset();
438d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
439d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
440d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
441d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
442d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
443d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::DisplaySplitConfig(DisplayResourceContext *display_resource_ctx,
444d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                            const LayerRect &src_rect, const LayerRect &dst_rect,
445d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                            HWLayerConfig *layer_config) {
446d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWDisplayAttributes &display_attributes = display_resource_ctx->display_attributes;
447d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
448d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // for display split case
449d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo *left_pipe = &layer_config->left_pipe;
450d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo *right_pipe = &layer_config->right_pipe;
451d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  LayerRect scissor_left, scissor_right, dst_left, crop_left, crop_right, dst_right;
452d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
453d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  scissor_left.right = FLOAT(display_attributes.split_left);
454d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  scissor_left.bottom = FLOAT(display_attributes.y_pixels);
455d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
456d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  scissor_right.left = FLOAT(display_attributes.split_left);
457d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  scissor_right.top = 0.0f;
458d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  scissor_right.right = FLOAT(display_attributes.x_pixels);
459d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  scissor_right.bottom = FLOAT(display_attributes.y_pixels);
460d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
461d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  crop_left = src_rect;
462d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_left = dst_rect;
463d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  crop_right = crop_left;
464d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_right = dst_left;
465d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
466d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  bool crop_left_valid = CalculateCropRects(scissor_left, &crop_left, &dst_left);
467d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  bool crop_right_valid = false;
468d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
469d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (IsValid(scissor_right)) {
470d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    crop_right_valid = CalculateCropRects(scissor_right, &crop_right, &dst_right);
471d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
472d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
473d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // Reset left_pipe and right_pipe to invalid by default
474d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  left_pipe->Reset();
475d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  right_pipe->Reset();
476d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
477d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (crop_left_valid) {
478d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    // assign left pipe
479d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->src_roi = crop_left;
480d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->dst_roi = dst_left;
481d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_pipe->valid = true;
482d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
483d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
484d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // assign right pipe if needed
485d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (crop_right_valid) {
486d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->src_roi = crop_right;
487d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->dst_roi = dst_right;
488d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->valid = true;
489d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
490d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
491d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
492d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
493d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
494d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::Config(DisplayResourceContext *display_resource_ctx,
495d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                HWLayers *hw_layers) {
496d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWLayersInfo &layer_info = hw_layers->info;
497d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
498d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Layer& layer = layer_info.stack->layers[layer_info.index[0]];
499d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
500d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateLayerParams(layer);
501d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
502d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
503d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
504d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
505d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  struct HWLayerConfig *layer_config = &hw_layers->config[0];
506d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo &left_pipe = layer_config->left_pipe;
507d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  HWPipeInfo &right_pipe = layer_config->right_pipe;
508d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
509d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  LayerRect src_rect = layer.src_rect;
510d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  LayerRect dst_rect = layer.dst_rect;
511d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
512d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateDimensions(src_rect, dst_rect);
513d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
514d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
515d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
516d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
517d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  bool ubwc_tiled = IsUBWCFormat(layer.input_buffer->format);
518d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateScaling(src_rect, dst_rect, false /*rotated90 */, ubwc_tiled,
519d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          false /* use_rotator_downscale */);
520d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
521d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
522d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
523d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
524d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (hw_res_info_.is_src_split) {
525d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    error = SrcSplitConfig(display_resource_ctx, src_rect, dst_rect, layer_config);
526d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  } else {
527d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    error = DisplaySplitConfig(display_resource_ctx, src_rect, dst_rect, layer_config);
528d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
529d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
530d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
531d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
532d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
533d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
534d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = AlignPipeConfig(layer, &left_pipe, &right_pipe);
535d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
536d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
537d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
538d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
539d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // set z_order, left_pipe should always be valid
540d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  left_pipe.z_order = 0;
541d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
542d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "==== FB layer Config ====");
543d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Log(kTagResources, "input layer src_rect", layer.src_rect);
544d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Log(kTagResources, "input layer dst_rect", layer.dst_rect);
545d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Log(kTagResources, "cropped src_rect", src_rect);
546d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Log(kTagResources, "cropped dst_rect", dst_rect);
547d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Log(kTagResources, "left pipe src", layer_config->left_pipe.src_roi);
548d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Log(kTagResources, "left pipe dst", layer_config->left_pipe.dst_roi);
549d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (right_pipe.valid) {
550d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe.z_order = 0;
551d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Log(kTagResources, "right pipe src", layer_config->right_pipe.src_roi);
552d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Log(kTagResources, "right pipe dst", layer_config->right_pipe.dst_roi);
553d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
554d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
555d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return error;
556d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
557d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
558d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinbool ResourceDefault::CalculateCropRects(const LayerRect &scissor, LayerRect *crop,
559d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                         LayerRect *dst) {
560d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &crop_left = crop->left;
561d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &crop_top = crop->top;
562d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &crop_right = crop->right;
563d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &crop_bottom = crop->bottom;
564d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float crop_width = crop->right - crop->left;
565d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float crop_height = crop->bottom - crop->top;
566d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
567d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &dst_left = dst->left;
568d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &dst_top = dst->top;
569d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &dst_right = dst->right;
570d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float &dst_bottom = dst->bottom;
571d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_width = dst->right - dst->left;
572d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_height = dst->bottom - dst->top;
573d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
574d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const float &sci_left = scissor.left;
575d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const float &sci_top = scissor.top;
576d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const float &sci_right = scissor.right;
577d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const float &sci_bottom = scissor.bottom;
578d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
579d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float left_cut_ratio = 0.0, right_cut_ratio = 0.0, top_cut_ratio = 0.0, bottom_cut_ratio = 0.0;
580d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  bool need_cut = false;
581d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
582d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (dst_left < sci_left) {
583d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    left_cut_ratio = (sci_left - dst_left) / dst_width;
584d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    dst_left = sci_left;
585d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    need_cut = true;
586d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
587d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
588d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (dst_right > sci_right) {
589d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_cut_ratio = (dst_right - sci_right) / dst_width;
590d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    dst_right = sci_right;
591d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    need_cut = true;
592d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
593d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
594d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (dst_top < sci_top) {
595d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    top_cut_ratio = (sci_top - dst_top) / (dst_height);
596d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    dst_top = sci_top;
597d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    need_cut = true;
598d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
599d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
600d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (dst_bottom > sci_bottom) {
601d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    bottom_cut_ratio = (dst_bottom - sci_bottom) / (dst_height);
602d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    dst_bottom = sci_bottom;
603d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    need_cut = true;
604d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
605d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
606d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!need_cut)
607d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return true;
608d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
609d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  crop_left += crop_width * left_cut_ratio;
610d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  crop_top += crop_height * top_cut_ratio;
611d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  crop_right -= crop_width * right_cut_ratio;
612d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  crop_bottom -= crop_height * bottom_cut_ratio;
613d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Normalize(1, 1, crop);
614d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  Normalize(1, 1, dst);
615d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (IsValid(*crop) && IsValid(*dst))
616d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return true;
617d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  else
618d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return false;
619d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
620d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
621d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateLayerParams(const Layer &layer) {
622d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const LayerRect &src = layer.src_rect;
623d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const LayerRect &dst = layer.dst_rect;
624d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  LayerBuffer *input_buffer = layer.input_buffer;
625d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
626d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (input_buffer->format == kFormatInvalid) {
627d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "Invalid input buffer format %d", input_buffer->format);
628d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
629d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
630d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
631d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!IsValid(src) || !IsValid(dst)) {
632d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Log(kTagResources, "input layer src_rect", src);
633d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Log(kTagResources, "input layer dst_rect", dst);
634d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
635d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
636d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
637d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // Make sure source in integral only if it is a non secure layer.
6381c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed  if (!input_buffer->flags.secure &&
6391c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed      ((src.left - roundf(src.left) != 0.0f) ||
6401c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed       (src.top - roundf(src.top) != 0.0f) ||
6411c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed       (src.right - roundf(src.right) != 0.0f) ||
6421c83c9c682ae9a6a43bd7e1a199355333c70a8cdNaseer Ahmed       (src.bottom - roundf(src.bottom) != 0.0f))) {
643d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "Input ROI is not integral");
644d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
645d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
646d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
647d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
648d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
649d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
650d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateDimensions(const LayerRect &crop, const LayerRect &dst) {
651d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!IsValid(crop)) {
652d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Log(kTagResources, "Invalid crop rect", crop);
653d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
654d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
655d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
656d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!IsValid(dst)) {
657d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    Log(kTagResources, "Invalid dst rect", dst);
658d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
659d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
660d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
661d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float crop_width = crop.right - crop.left;
662d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float crop_height = crop.bottom - crop.top;
663d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_width = dst.right - dst.left;
664d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_height = dst.bottom - dst.top;
665d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
666d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if ((UINT32(crop_width - dst_width) == 1) || (UINT32(crop_height - dst_height) == 1)) {
667d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "One pixel downscaling detected crop_w = %.0f, dst_w = %.0f, " \
668d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin             "crop_h = %.0f, dst_h = %.0f", crop_width, dst_width, crop_height, dst_height);
669d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
670d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
671d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
672d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
673d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
674d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
675d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidatePipeParams(HWPipeInfo *pipe_info, bool ubwc_tiled) {
676d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
677d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
678d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const LayerRect &src_rect = pipe_info->src_roi;
679d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  const LayerRect &dst_rect = pipe_info->dst_roi;
680d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
681d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateDimensions(src_rect, dst_rect);
682d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
683d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
684d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
685d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
686d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateScaling(src_rect, dst_rect, false /* rotated90 */, ubwc_tiled,
687d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                          false /* use_rotator_downscale */);
688d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
689d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
690d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
691d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
692d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
693d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
694d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
695d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateScaling(const LayerRect &crop, const LayerRect &dst,
696d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                              bool rotate90, bool ubwc_tiled,
697d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                              bool use_rotator_downscale) {
698d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
699d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
700d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float scale_x = 1.0f;
701d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float scale_y = 1.0f;
702d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
703d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = GetScaleFactor(crop, dst, &scale_x, &scale_y);
704d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
705d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
706d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
707d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
708d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateDownScaling(scale_x, scale_y, ubwc_tiled);
709d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
710d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
711d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
712d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
713d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidateUpScaling(scale_x, scale_y);
714d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
715d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return error;
716d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
717d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
718d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
719d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
720d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
721d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateDownScaling(float scale_x, float scale_y, bool ubwc_tiled) {
722d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if ((UINT32(scale_x) > 1) || (UINT32(scale_y) > 1)) {
723d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    float max_scale_down = FLOAT(hw_res_info_.max_scale_down);
724d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
725d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    // MDP H/W cannot apply decimation on UBWC tiled framebuffer
726d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (!ubwc_tiled && hw_res_info_.has_decimation) {
727d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      max_scale_down *= FLOAT(kMaxDecimationDownScaleRatio);
728d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
729d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
730d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if (scale_x > max_scale_down || scale_y > max_scale_down) {
731d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      DLOGV_IF(kTagResources,
732d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin               "Scaling down is over the limit: scale_x = %.0f, scale_y = %.0f, " \
733d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin               "has_deci = %d", scale_x, scale_y, hw_res_info_.has_decimation);
734d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      return kErrorNotSupported;
735d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
736d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
737d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
738d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "scale_x = %.4f, scale_y = %.4f", scale_x, scale_y);
739d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
740d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
741d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
742d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
743d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateUpScaling(float scale_x, float scale_y) {
744d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float max_scale_up = FLOAT(hw_res_info_.max_scale_up);
745d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
746d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (UINT32(scale_x) < 1 && scale_x > 0.0f) {
747d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if ((1.0f / scale_x) > max_scale_up) {
748d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      DLOGV_IF(kTagResources, "Scaling up is over limit scale_x = %f", 1.0f / scale_x);
749d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      return kErrorNotSupported;
750d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
751d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
752d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
753d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (UINT32(scale_y) < 1 && scale_y > 0.0f) {
754d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    if ((1.0f / scale_y) > max_scale_up) {
755d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      DLOGV_IF(kTagResources, "Scaling up is over limit scale_y = %f", 1.0f / scale_y);
756d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin      return kErrorNotSupported;
757d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    }
758d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
759d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
760d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGV_IF(kTagResources, "scale_x = %.4f, scale_y = %.4f", scale_x, scale_y);
761d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
762d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
763d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
764d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
765d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::GetScaleFactor(const LayerRect &crop, const LayerRect &dst,
766d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                        float *scale_x, float *scale_y) {
767d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float crop_width = crop.right - crop.left;
768d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float crop_height = crop.bottom - crop.top;
769d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_width = dst.right - dst.left;
770d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_height = dst.bottom - dst.top;
771d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
772d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  *scale_x = crop_width / dst_width;
773d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  *scale_y = crop_height / dst_height;
774d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
775d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
776d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
777d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
778d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::SetDecimationFactor(HWPipeInfo *pipe) {
779d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float src_h = pipe->src_roi.bottom - pipe->src_roi.top;
780d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_h = pipe->dst_roi.bottom - pipe->dst_roi.top;
781d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float down_scale_h = src_h / dst_h;
782d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
783d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float src_w = pipe->src_roi.right - pipe->src_roi.left;
784d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_w = pipe->dst_roi.right - pipe->dst_roi.left;
785d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float down_scale_w = src_w / dst_w;
786d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
787d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  pipe->horizontal_decimation = 0;
788d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  pipe->vertical_decimation = 0;
789d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
790d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (CalculateDecimation(down_scale_w, &pipe->horizontal_decimation) != kErrorNone) {
791d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
792d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
793d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
794d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (CalculateDecimation(down_scale_h, &pipe->vertical_decimation) != kErrorNone) {
795d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
796d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
797d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
798d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DLOGI_IF(kTagResources, "horizontal_decimation %d, vertical_decimation %d",
799d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin           pipe->horizontal_decimation, pipe->vertical_decimation);
800d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
801d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
802d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
803d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
804d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjinvoid ResourceDefault::SplitRect(const LayerRect &src_rect, const LayerRect &dst_rect,
805d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                           LayerRect *src_left, LayerRect *dst_left, LayerRect *src_right,
806d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                           LayerRect *dst_right) {
807d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // Split rectangle horizontally and evenly into two.
808d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float src_width = src_rect.right - src_rect.left;
809d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float dst_width = dst_rect.right - dst_rect.left;
810d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float src_width_ori = src_width;
811d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_width = ROUND_UP_ALIGN_DOWN(src_width / 2, 1);
812d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_width = ROUND_UP_ALIGN_DOWN(dst_width * src_width / src_width_ori, 1);
813d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
814d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_left->left = src_rect.left;
815d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_left->right = src_rect.left + src_width;
816d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_right->left = src_left->right;
817d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_right->right = src_rect.right;
818d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
819d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_left->top = src_rect.top;
820d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_left->bottom = src_rect.bottom;
821d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_right->top = src_rect.top;
822d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  src_right->bottom = src_rect.bottom;
823d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
824d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_left->top = dst_rect.top;
825d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_left->bottom = dst_rect.bottom;
826d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_right->top = dst_rect.top;
827d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_right->bottom = dst_rect.bottom;
828d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
829d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_left->left = dst_rect.left;
830d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_left->right = dst_rect.left + dst_width;
831d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_right->left = dst_left->right;
832d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  dst_right->right = dst_rect.right;
833d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
834d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
835d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::AlignPipeConfig(const Layer &layer, HWPipeInfo *left_pipe,
836d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                         HWPipeInfo *right_pipe) {
837d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  DisplayError error = kErrorNone;
838d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (!left_pipe->valid) {
839d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGE_IF(kTagResources, "left_pipe should not be invalid");
840d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
841d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
842d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
843d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  bool ubwc_tiled = IsUBWCFormat(layer.input_buffer->format);
844d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  error = ValidatePipeParams(left_pipe, ubwc_tiled);
845d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
846d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    goto PipeConfigExit;
847d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
848d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
849d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (right_pipe->valid) {
850d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    // Make sure the  left and right ROI are conjunct
851d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->src_roi.left = left_pipe->src_roi.right;
852d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    right_pipe->dst_roi.left = left_pipe->dst_roi.right;
853d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    error = ValidatePipeParams(right_pipe, ubwc_tiled);
854d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
855d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
856d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinPipeConfigExit:
857d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (error != kErrorNone) {
858d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGV_IF(kTagResources, "AlignPipeConfig failed");
859d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
860d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return error;
861d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
862d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
863d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::CalculateDecimation(float downscale, uint8_t *decimation) {
864d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  float max_down_scale = FLOAT(hw_res_info_.max_scale_down);
865d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
866d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  if (downscale <= max_down_scale) {
867d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    *decimation = 0;
868d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNone;
869d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  } else if (!hw_res_info_.has_decimation) {
870d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    DLOGE("Downscaling exceeds the maximum MDP downscale limit but decimation not enabled");
871d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin    return kErrorNotSupported;
872d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  }
873d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
874d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // Decimation is the remaining downscale factor after doing max SDE downscale.
875d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // In SDE, decimation is supported in powers of 2.
876d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // For ex: If a pipe needs downscale of 8 but max_down_scale is 4
877d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  // So decimation = powf(2.0, ceilf(log2f(8 / 4))) = powf(2.0, 1.0) = 2
878d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  *decimation = UINT8(ceilf(log2f(downscale / max_down_scale)));
879d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNone;
880d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
881d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
882d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateCursorConfig(Handle display_ctx, const Layer& layer,
883d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                                   bool is_top) {
884d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNotSupported;
885d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
886d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
887d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::ValidateCursorPosition(Handle display_ctx, HWLayers *hw_layers,
888d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin                                                     int x, int y) {
889d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNotSupported;
890d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
891d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
892d68a2e45260f864503d7bd6da93fd29589afd89ePatrick TjinDisplayError ResourceDefault::SetMaxBandwidthMode(HWBwModes mode) {
893d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin  return kErrorNotSupported;
894d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}
895d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin
896d68a2e45260f864503d7bd6da93fd29589afd89ePatrick Tjin}  // namespace sdm
897