Home | History | Annotate | Download | only in hwc2
      1 /*
      2  * Copyright (c) 2014-2018, The Linux Foundation. All rights reserved.
      3  * Not a Contribution.
      4  *
      5  * Copyright 2015 The Android Open Source Project
      6  *
      7  * Licensed under the Apache License, Version 2.0 (the "License");
      8  * you may not use this file except in compliance with the License.
      9  * You may obtain a copy of the License at
     10  *
     11  *      http://www.apache.org/licenses/LICENSE-2.0
     12  *
     13  * Unless required by applicable law or agreed to in writing, software
     14  * distributed under the License is distributed on an "AS IS" BASIS,
     15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     16  * See the License for the specific language governing permissions and
     17  * limitations under the License.
     18  */
     19 
     20 #include <cutils/properties.h>
     21 #include <errno.h>
     22 #include <math.h>
     23 #include <sync/sync.h>
     24 #include <sys/types.h>
     25 #include <sys/stat.h>
     26 #include <utils/constants.h>
     27 #include <utils/debug.h>
     28 #include <utils/formats.h>
     29 #include <utils/rect.h>
     30 #include <qd_utils.h>
     31 
     32 #include <algorithm>
     33 #include <iomanip>
     34 #include <map>
     35 #include <sstream>
     36 #include <string>
     37 #include <utility>
     38 #include <vector>
     39 
     40 #include "hwc_display.h"
     41 #include "hwc_debugger.h"
     42 #include "blit_engine_c2d.h"
     43 #include "hwc_tonemapper.h"
     44 
     45 #ifndef USE_GRALLOC1
     46 #include <gr.h>
     47 #endif
     48 
     49 #ifdef QTI_BSP
     50 #include <hardware/display_defs.h>
     51 #endif
     52 
     53 #define __CLASS__ "HWCDisplay"
     54 
     55 namespace sdm {
     56 
     57 std::bitset<kDisplayMax> HWCDisplay::validated_ = 0;
     58 
     59 // This weight function is needed because the color primaries are not sorted by gamut size
     60 static ColorPrimaries WidestPrimaries(ColorPrimaries p1, ColorPrimaries p2) {
     61   int weight = 10;
     62   int lp1 = p1, lp2 = p2;
     63   // TODO(user) add weight to other wide gamut primaries
     64   if (lp1 == ColorPrimaries_BT2020) {
     65     lp1 *= weight;
     66   }
     67   if (lp1 == ColorPrimaries_BT2020) {
     68     lp2 *= weight;
     69   }
     70   if (lp1 >= lp2) {
     71     return p1;
     72   } else {
     73     return p2;
     74   }
     75 }
     76 
     77 HWCColorMode::HWCColorMode(DisplayInterface *display_intf) : display_intf_(display_intf) {}
     78 
     79 HWC2::Error HWCColorMode::Init() {
     80   PopulateColorModes();
     81   return ApplyDefaultColorMode();
     82 }
     83 
     84 HWC2::Error HWCColorMode::DeInit() {
     85   color_mode_transform_map_.clear();
     86   return HWC2::Error::None;
     87 }
     88 
     89 uint32_t HWCColorMode::GetColorModeCount() {
     90   uint32_t count = UINT32(color_mode_transform_map_.size());
     91   DLOGI("Supported color mode count = %d", count);
     92 #ifdef EXCLUDE_DISPLAY_PP
     93   return count;
     94 #else
     95   return std::max(1U, count);
     96 #endif
     97 }
     98 
     99 HWC2::Error HWCColorMode::GetColorModes(uint32_t *out_num_modes,
    100                                         android_color_mode_t *out_modes) {
    101   auto it = color_mode_transform_map_.begin();
    102   for (auto i = 0; it != color_mode_transform_map_.end(); it++, i++) {
    103     out_modes[i] = it->first;
    104     DLOGI("Supports color mode[%d] = %d", i, it->first);
    105   }
    106   *out_num_modes = UINT32(color_mode_transform_map_.size());
    107   return HWC2::Error::None;
    108 }
    109 
    110 HWC2::Error HWCColorMode::SetColorMode(android_color_mode_t mode) {
    111   // first mode in 2D matrix is the mode (identity)
    112   if (mode < HAL_COLOR_MODE_NATIVE || mode > HAL_COLOR_MODE_DISPLAY_P3) {
    113     DLOGE("Could not find mode: %d", mode);
    114     return HWC2::Error::BadParameter;
    115   }
    116   if (color_mode_transform_map_.find(mode) == color_mode_transform_map_.end()) {
    117     return HWC2::Error::Unsupported;
    118   }
    119 
    120   auto status = HandleColorModeTransform(mode, current_color_transform_, color_matrix_);
    121   if (status != HWC2::Error::None) {
    122     DLOGE("failed for mode = %d", mode);
    123   }
    124 
    125   DLOGV_IF(kTagClient, "Color mode %d successfully set.", mode);
    126   return status;
    127 }
    128 
    129 HWC2::Error HWCColorMode::RestoreColorTransform() {
    130   DisplayError error = display_intf_->SetColorTransform(kColorTransformMatrixCount, color_matrix_);
    131   if (error != kErrorNone) {
    132     DLOGI_IF(kTagClient,"Failed to set Color Transform");
    133     return HWC2::Error::BadParameter;
    134   }
    135 
    136   return HWC2::Error::None;
    137 }
    138 
    139 HWC2::Error HWCColorMode::SetColorTransform(const float *matrix, android_color_transform_t hint) {
    140   DTRACE_SCOPED();
    141   double color_matrix[kColorTransformMatrixCount] = {0};
    142   CopyColorTransformMatrix(matrix, color_matrix);
    143 
    144   auto status = HandleColorModeTransform(current_color_mode_, hint, color_matrix);
    145   if (status != HWC2::Error::None) {
    146     DLOGE("failed for hint = %d", hint);
    147   }
    148 
    149   return status;
    150 }
    151 
    152 HWC2::Error HWCColorMode::HandleColorModeTransform(android_color_mode_t mode,
    153                                                    android_color_transform_t hint,
    154                                                    const double *matrix) {
    155   android_color_transform_t transform_hint = hint;
    156   std::string color_mode_transform;
    157   bool use_matrix = false;
    158   if (hint != HAL_COLOR_TRANSFORM_ARBITRARY_MATRIX) {
    159     // if the mode + transfrom request from HWC matches one mode in SDM, set that
    160     if (color_mode_transform.empty()) {
    161       transform_hint = HAL_COLOR_TRANSFORM_IDENTITY;
    162       use_matrix = true;
    163     } else {
    164       color_mode_transform = color_mode_transform_map_[mode][hint];
    165     }
    166   } else {
    167     use_matrix = true;
    168     transform_hint = HAL_COLOR_TRANSFORM_IDENTITY;
    169   }
    170 
    171   // if the mode count is 1, then only native mode is supported, so just apply matrix w/o
    172   // setting mode
    173   if (color_mode_transform_map_.size() > 1U && current_color_mode_ != mode) {
    174     color_mode_transform = color_mode_transform_map_[mode][transform_hint];
    175     DisplayError error = display_intf_->SetColorMode(color_mode_transform);
    176     if (error != kErrorNone) {
    177       DLOGE("Failed to set color_mode  = %d transform_hint = %d", mode, hint);
    178       // failure to force client composition
    179       return HWC2::Error::Unsupported;
    180     }
    181     DLOGI("Setting Color Mode = %d Transform Hint = %d Success", mode, hint);
    182   }
    183 
    184   if (use_matrix) {
    185     DisplayError error = display_intf_->SetColorTransform(kColorTransformMatrixCount, matrix);
    186     if (error != kErrorNone) {
    187       DLOGE("Failed to set Color Transform Matrix");
    188       // failure to force client composition
    189       return HWC2::Error::Unsupported;
    190     }
    191   }
    192 
    193   current_color_mode_ = mode;
    194   current_color_transform_ = hint;
    195   CopyColorTransformMatrix(matrix, color_matrix_);
    196 
    197   return HWC2::Error::None;
    198 }
    199 
    200 void HWCColorMode::PopulateColorModes() {
    201   uint32_t color_mode_count = 0;
    202   // SDM returns modes which is string combination of mode + transform.
    203   DisplayError error = display_intf_->GetColorModeCount(&color_mode_count);
    204   if (error != kErrorNone || (color_mode_count == 0)) {
    205 #ifndef EXCLUDE_DISPLAY_PP
    206     DLOGW("GetColorModeCount failed, use native color mode");
    207     PopulateTransform(HAL_COLOR_MODE_NATIVE, "native", "identity");
    208 #endif
    209     return;
    210   }
    211 
    212   DLOGV_IF(kTagClient, "Color Modes supported count = %d", color_mode_count);
    213 
    214   const std::string color_transform = "identity";
    215   std::vector<std::string> color_modes(color_mode_count);
    216   error = display_intf_->GetColorModes(&color_mode_count, &color_modes);
    217   for (uint32_t i = 0; i < color_mode_count; i++) {
    218     std::string &mode_string = color_modes.at(i);
    219     DLOGV_IF(kTagClient, "Color Mode[%d] = %s", i, mode_string.c_str());
    220     AttrVal attr;
    221     error = display_intf_->GetColorModeAttr(mode_string, &attr);
    222     std::string color_gamut, dynamic_range, pic_quality;
    223     if (!attr.empty()) {
    224       for (auto &it : attr) {
    225         if (it.first.find(kColorGamutAttribute) != std::string::npos) {
    226           color_gamut = it.second;
    227         } else if (it.first.find(kDynamicRangeAttribute) != std::string::npos) {
    228           dynamic_range = it.second;
    229         } else if (it.first.find(kPictureQualityAttribute) != std::string::npos) {
    230           pic_quality = it.second;
    231         }
    232       }
    233 
    234       DLOGV_IF(kTagClient, "color_gamut : %s, dynamic_range : %s, pic_quality : %s",
    235                color_gamut.c_str(), dynamic_range.c_str(), pic_quality.c_str());
    236 
    237       if (dynamic_range == kHdr) {
    238         continue;
    239       }
    240       if ((color_gamut == kNative) &&
    241           (pic_quality.empty() || pic_quality == kStandard)) {
    242         PopulateTransform(HAL_COLOR_MODE_NATIVE, mode_string, color_transform);
    243       } else if ((color_gamut == kSrgb) &&
    244                  (pic_quality.empty() || pic_quality == kStandard)) {
    245         PopulateTransform(HAL_COLOR_MODE_SRGB, mode_string, color_transform);
    246       } else if ((color_gamut == kDcip3) &&
    247                  (pic_quality.empty() || pic_quality == kStandard)) {
    248         PopulateTransform(HAL_COLOR_MODE_DISPLAY_P3, mode_string, color_transform);
    249       } else if ((color_gamut == kDisplayP3) &&
    250                  (pic_quality.empty() || pic_quality == kStandard)) {
    251         PopulateTransform(HAL_COLOR_MODE_DISPLAY_P3, mode_string, color_transform);
    252       }
    253     }
    254 
    255     // Look at the mode name, if no color gamut is found
    256     if (color_gamut.empty()) {
    257       if (mode_string.find("hal_native") != std::string::npos) {
    258         PopulateTransform(HAL_COLOR_MODE_NATIVE, mode_string, mode_string);
    259       } else if (mode_string.find("hal_srgb") != std::string::npos) {
    260         PopulateTransform(HAL_COLOR_MODE_SRGB, mode_string, mode_string);
    261       } else if (mode_string.find("hal_adobe") != std::string::npos) {
    262         PopulateTransform(HAL_COLOR_MODE_ADOBE_RGB, mode_string, mode_string);
    263       } else if (mode_string.find("hal_dci_p3") != std::string::npos) {
    264         PopulateTransform(HAL_COLOR_MODE_DCI_P3, mode_string, mode_string);
    265       } else if (mode_string.find("hal_display_p3") != std::string::npos) {
    266         PopulateTransform(HAL_COLOR_MODE_DISPLAY_P3, mode_string, mode_string);
    267       }
    268     }
    269   }
    270 }
    271 
    272 void HWCColorMode::PopulateTransform(const android_color_mode_t &mode,
    273                                      const std::string &color_mode,
    274                                      const std::string &color_transform) {
    275   // TODO(user): Check the substring from QDCM
    276   if (color_transform.find("identity") != std::string::npos) {
    277     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_IDENTITY] = color_mode;
    278   } else if (color_transform.find("arbitrary") != std::string::npos) {
    279     // no color mode for arbitrary
    280   } else if (color_transform.find("inverse") != std::string::npos) {
    281     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_VALUE_INVERSE] = color_mode;
    282   } else if (color_transform.find("grayscale") != std::string::npos) {
    283     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_GRAYSCALE] = color_mode;
    284   } else if (color_transform.find("correct_protonopia") != std::string::npos) {
    285     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_CORRECT_PROTANOPIA] = color_mode;
    286   } else if (color_transform.find("correct_deuteranopia") != std::string::npos) {
    287     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_CORRECT_DEUTERANOPIA] = color_mode;
    288   } else if (color_transform.find("correct_tritanopia") != std::string::npos) {
    289     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_CORRECT_TRITANOPIA] = color_mode;
    290   } else {
    291     color_mode_transform_map_[mode][HAL_COLOR_TRANSFORM_IDENTITY] = color_mode;
    292   }
    293 }
    294 
    295 HWC2::Error HWCColorMode::ApplyDefaultColorMode() {
    296   android_color_mode_t color_mode = HAL_COLOR_MODE_NATIVE;
    297   if (color_mode_transform_map_.size() == 1U) {
    298     color_mode = color_mode_transform_map_.begin()->first;
    299   } else if (color_mode_transform_map_.size() > 1U) {
    300     std::string default_color_mode;
    301     bool found = false;
    302     DisplayError error = display_intf_->GetDefaultColorMode(&default_color_mode);
    303     if (error == kErrorNone) {
    304       // get the default mode corresponding android_color_mode_t
    305       for (auto &it_mode : color_mode_transform_map_) {
    306         for (auto &it : it_mode.second) {
    307           if (it.second == default_color_mode) {
    308             found = true;
    309             break;
    310           }
    311         }
    312         if (found) {
    313           color_mode = it_mode.first;
    314           break;
    315         }
    316       }
    317     }
    318 
    319     // return the first andrid_color_mode_t when we encouter if not found
    320     if (!found) {
    321       color_mode = color_mode_transform_map_.begin()->first;
    322     }
    323   }
    324   return SetColorMode(color_mode);
    325 }
    326 
    327 void HWCColorMode::Dump(std::ostringstream* os) {
    328   *os << "color modes supported: ";
    329   for (auto it : color_mode_transform_map_) {
    330     *os << it.first <<" ";
    331   }
    332   *os << "current mode: " << current_color_mode_ << std::endl;
    333   *os << "current transform: ";
    334   for (uint32_t i = 0; i < kColorTransformMatrixCount; i++) {
    335     if (i % 4 == 0) {
    336      *os << std::endl;
    337     }
    338     *os << std::fixed << std::setprecision(2) << std::setw(6) << std::setfill(' ')
    339         << color_matrix_[i] << " ";
    340   }
    341   *os << std::endl;
    342 }
    343 
    344 HWCDisplay::HWCDisplay(CoreInterface *core_intf, HWCCallbacks *callbacks, DisplayType type,
    345                        hwc2_display_t id, bool needs_blit, qService::QService *qservice,
    346                        DisplayClass display_class, BufferAllocator *buffer_allocator)
    347     : core_intf_(core_intf),
    348       callbacks_(callbacks),
    349       type_(type),
    350       id_(id),
    351       needs_blit_(needs_blit),
    352       qservice_(qservice),
    353       display_class_(display_class) {
    354   buffer_allocator_ = static_cast<HWCBufferAllocator *>(buffer_allocator);
    355 }
    356 
    357 int HWCDisplay::Init() {
    358   DisplayError error = core_intf_->CreateDisplay(type_, this, &display_intf_);
    359   if (error != kErrorNone) {
    360     DLOGE("Display create failed. Error = %d display_type %d event_handler %p disp_intf %p", error,
    361           type_, this, &display_intf_);
    362     return -EINVAL;
    363   }
    364 
    365   validated_.reset();
    366   HWCDebugHandler::Get()->GetProperty(DISABLE_HDR, &disable_hdr_handling_);
    367   if (disable_hdr_handling_) {
    368     DLOGI("HDR Handling disabled");
    369   }
    370 
    371   int property_swap_interval = 1;
    372   HWCDebugHandler::Get()->GetProperty("debug.egl.swapinterval", &property_swap_interval);
    373   if (property_swap_interval == 0) {
    374     swap_interval_zero_ = true;
    375   }
    376 
    377   client_target_ = new HWCLayer(id_, buffer_allocator_);
    378 
    379   int blit_enabled = 0;
    380   HWCDebugHandler::Get()->GetProperty(DISABLE_BLIT_COMPOSITION_PROP, &blit_enabled);
    381   if (needs_blit_ && blit_enabled) {
    382     // TODO(user): Add blit engine when needed
    383   }
    384 
    385   error = display_intf_->GetNumVariableInfoConfigs(&num_configs_);
    386   if (error != kErrorNone) {
    387     DLOGE("Getting config count failed. Error = %d", error);
    388     return -EINVAL;
    389   }
    390 
    391   tone_mapper_ = new HWCToneMapper(buffer_allocator_);
    392 
    393   display_intf_->GetRefreshRateRange(&min_refresh_rate_, &max_refresh_rate_);
    394   current_refresh_rate_ = max_refresh_rate_;
    395 
    396   GetUnderScanConfig();
    397   DLOGI("Display created with id: %d", id_);
    398 
    399   return 0;
    400 }
    401 
    402 int HWCDisplay::Deinit() {
    403   DisplayError error = core_intf_->DestroyDisplay(display_intf_);
    404   if (error != kErrorNone) {
    405     DLOGE("Display destroy failed. Error = %d", error);
    406     return -EINVAL;
    407   }
    408 
    409   delete client_target_;
    410   for (auto hwc_layer : layer_set_) {
    411     delete hwc_layer;
    412   }
    413 
    414   if (color_mode_) {
    415     color_mode_->DeInit();
    416     delete color_mode_;
    417   }
    418 
    419   delete tone_mapper_;
    420   tone_mapper_ = nullptr;
    421 
    422   return 0;
    423 }
    424 
    425 // LayerStack operations
    426 HWC2::Error HWCDisplay::CreateLayer(hwc2_layer_t *out_layer_id) {
    427   HWCLayer *layer = *layer_set_.emplace(new HWCLayer(id_, buffer_allocator_));
    428   layer_map_.emplace(std::make_pair(layer->GetId(), layer));
    429   *out_layer_id = layer->GetId();
    430   geometry_changes_ |= GeometryChanges::kAdded;
    431   validated_.reset();
    432   return HWC2::Error::None;
    433 }
    434 
    435 HWCLayer *HWCDisplay::GetHWCLayer(hwc2_layer_t layer_id) {
    436   const auto map_layer = layer_map_.find(layer_id);
    437   if (map_layer == layer_map_.end()) {
    438     DLOGE("[%" PRIu64 "] GetLayer(%" PRIu64 ") failed: no such layer", id_, layer_id);
    439     return nullptr;
    440   } else {
    441     return map_layer->second;
    442   }
    443 }
    444 
    445 HWC2::Error HWCDisplay::DestroyLayer(hwc2_layer_t layer_id) {
    446   const auto map_layer = layer_map_.find(layer_id);
    447   if (map_layer == layer_map_.end()) {
    448     DLOGE("[%" PRIu64 "] destroyLayer(%" PRIu64 ") failed: no such layer", id_, layer_id);
    449     return HWC2::Error::BadLayer;
    450   }
    451   const auto layer = map_layer->second;
    452   layer_map_.erase(map_layer);
    453   const auto z_range = layer_set_.equal_range(layer);
    454   for (auto current = z_range.first; current != z_range.second; ++current) {
    455     if (*current == layer) {
    456       current = layer_set_.erase(current);
    457       delete layer;
    458       break;
    459     }
    460   }
    461 
    462   geometry_changes_ |= GeometryChanges::kRemoved;
    463   validated_.reset();
    464   return HWC2::Error::None;
    465 }
    466 
    467 
    468 void HWCDisplay::BuildLayerStack() {
    469   layer_stack_ = LayerStack();
    470   display_rect_ = LayerRect();
    471   metadata_refresh_rate_ = 0;
    472   auto working_primaries = ColorPrimaries_BT709_5;
    473   bool secure_display_active = false;
    474   layer_stack_.flags.animating = animating_;
    475 
    476   // Add one layer for fb target
    477   // TODO(user): Add blit target layers
    478   for (auto hwc_layer : layer_set_) {
    479     Layer *layer = hwc_layer->GetSDMLayer();
    480     layer->flags = {};   // Reset earlier flags
    481     if (hwc_layer->GetClientRequestedCompositionType() == HWC2::Composition::Client) {
    482       layer->flags.skip = true;
    483     } else if (hwc_layer->GetClientRequestedCompositionType() == HWC2::Composition::SolidColor) {
    484       layer->flags.solid_fill = true;
    485     }
    486 
    487     if (!hwc_layer->ValidateAndSetCSC()) {
    488 #ifdef FEATURE_WIDE_COLOR
    489       layer->flags.skip = true;
    490 #endif
    491     }
    492 
    493     working_primaries = WidestPrimaries(working_primaries,
    494                                         layer->input_buffer.color_metadata.colorPrimaries);
    495 
    496     // set default composition as GPU for SDM
    497     layer->composition = kCompositionGPU;
    498 
    499     if (swap_interval_zero_) {
    500       if (layer->input_buffer.acquire_fence_fd >= 0) {
    501         close(layer->input_buffer.acquire_fence_fd);
    502         layer->input_buffer.acquire_fence_fd = -1;
    503       }
    504     }
    505 
    506     const private_handle_t *handle =
    507         reinterpret_cast<const private_handle_t *>(layer->input_buffer.buffer_id);
    508     if (handle) {
    509 #ifdef USE_GRALLOC1
    510       if (handle->buffer_type == BUFFER_TYPE_VIDEO) {
    511 #else
    512       if (handle->bufferType == BUFFER_TYPE_VIDEO) {
    513 #endif
    514         layer_stack_.flags.video_present = true;
    515       }
    516       // TZ Protected Buffer - L1
    517       if (handle->flags & private_handle_t::PRIV_FLAGS_SECURE_BUFFER) {
    518         layer_stack_.flags.secure_present = true;
    519       }
    520       // Gralloc Usage Protected Buffer - L3 - which needs to be treated as Secure & avoid fallback
    521       if (handle->flags & private_handle_t::PRIV_FLAGS_PROTECTED_BUFFER) {
    522         layer_stack_.flags.secure_present = true;
    523       }
    524     }
    525 
    526     if (layer->flags.skip) {
    527       layer_stack_.flags.skip_present = true;
    528     }
    529 
    530     if (layer->input_buffer.flags.secure_display) {
    531       secure_display_active = true;
    532     }
    533 
    534     if (hwc_layer->GetClientRequestedCompositionType() == HWC2::Composition::Cursor) {
    535       // Currently we support only one HWCursor & only at top most z-order
    536       if ((*layer_set_.rbegin())->GetId() == hwc_layer->GetId()) {
    537         layer->flags.cursor = true;
    538         layer_stack_.flags.cursor_present = true;
    539       }
    540     }
    541 
    542     bool hdr_layer = layer->input_buffer.color_metadata.colorPrimaries == ColorPrimaries_BT2020 &&
    543                      (layer->input_buffer.color_metadata.transfer == Transfer_SMPTE_ST2084 ||
    544                      layer->input_buffer.color_metadata.transfer == Transfer_HLG);
    545     if (hdr_layer && !disable_hdr_handling_) {
    546       // dont honor HDR when its handling is disabled
    547       layer->input_buffer.flags.hdr = true;
    548       layer_stack_.flags.hdr_present = true;
    549     }
    550 
    551     // TODO(user): Move to a getter if this is needed at other places
    552     hwc_rect_t scaled_display_frame = {INT(layer->dst_rect.left), INT(layer->dst_rect.top),
    553                                        INT(layer->dst_rect.right), INT(layer->dst_rect.bottom)};
    554     if (hwc_layer->GetGeometryChanges() & kDisplayFrame) {
    555       ApplyScanAdjustment(&scaled_display_frame);
    556     }
    557     hwc_layer->SetLayerDisplayFrame(scaled_display_frame);
    558     // SDM requires these details even for solid fill
    559     if (layer->flags.solid_fill) {
    560       LayerBuffer *layer_buffer = &layer->input_buffer;
    561       layer_buffer->width = UINT32(layer->dst_rect.right - layer->dst_rect.left);
    562       layer_buffer->height = UINT32(layer->dst_rect.bottom - layer->dst_rect.top);
    563       layer_buffer->unaligned_width = layer_buffer->width;
    564       layer_buffer->unaligned_height = layer_buffer->height;
    565       layer_buffer->acquire_fence_fd = -1;
    566       layer_buffer->release_fence_fd = -1;
    567       layer->src_rect.left = 0;
    568       layer->src_rect.top = 0;
    569       layer->src_rect.right = layer_buffer->width;
    570       layer->src_rect.bottom = layer_buffer->height;
    571     }
    572 
    573     if (layer->frame_rate > metadata_refresh_rate_) {
    574       metadata_refresh_rate_ = SanitizeRefreshRate(layer->frame_rate);
    575     } else {
    576       layer->frame_rate = current_refresh_rate_;
    577     }
    578     display_rect_ = Union(display_rect_, layer->dst_rect);
    579     geometry_changes_ |= hwc_layer->GetGeometryChanges();
    580 
    581     layer->flags.updating = true;
    582     if (layer_set_.size() <= kMaxLayerCount) {
    583       layer->flags.updating = IsLayerUpdating(layer);
    584     }
    585 
    586     layer_stack_.layers.push_back(layer);
    587   }
    588 
    589 
    590 #ifdef FEATURE_WIDE_COLOR
    591   for (auto hwc_layer : layer_set_) {
    592     auto layer = hwc_layer->GetSDMLayer();
    593     if (layer->input_buffer.color_metadata.colorPrimaries != working_primaries &&
    594         !hwc_layer->SupportLocalConversion(working_primaries)) {
    595       layer->flags.skip = true;
    596     }
    597     if (layer->flags.skip) {
    598       layer_stack_.flags.skip_present = true;
    599     }
    600   }
    601 #endif
    602 
    603   // TODO(user): Set correctly when SDM supports geometry_changes as bitmask
    604   layer_stack_.flags.geometry_changed = UINT32(geometry_changes_ > 0);
    605   // Append client target to the layer stack
    606 
    607   Layer *sdm_client_target = client_target_->GetSDMLayer();
    608   layer_stack_.layers.push_back(sdm_client_target);
    609   // fall back frame composition to GPU when client target is 10bit
    610   // TODO(user): clarify the behaviour from Client(SF) and SDM Extn -
    611   // when handling 10bit FBT, as it would affect blending
    612   if (Is10BitFormat(sdm_client_target->input_buffer.format)) {
    613     // Must fall back to client composition
    614     MarkLayersForClientComposition();
    615   }
    616 
    617   // set secure display
    618   SetSecureDisplay(secure_display_active);
    619 }
    620 
    621 void HWCDisplay::BuildSolidFillStack() {
    622   layer_stack_ = LayerStack();
    623   display_rect_ = LayerRect();
    624 
    625   layer_stack_.layers.push_back(solid_fill_layer_);
    626   layer_stack_.flags.geometry_changed = 1U;
    627   // Append client target to the layer stack
    628   layer_stack_.layers.push_back(client_target_->GetSDMLayer());
    629 }
    630 
    631 HWC2::Error HWCDisplay::SetLayerZOrder(hwc2_layer_t layer_id, uint32_t z) {
    632   const auto map_layer = layer_map_.find(layer_id);
    633   if (map_layer == layer_map_.end()) {
    634     DLOGE("[%" PRIu64 "] updateLayerZ failed to find layer", id_);
    635     return HWC2::Error::BadLayer;
    636   }
    637 
    638   const auto layer = map_layer->second;
    639   const auto z_range = layer_set_.equal_range(layer);
    640   bool layer_on_display = false;
    641   for (auto current = z_range.first; current != z_range.second; ++current) {
    642     if (*current == layer) {
    643       if ((*current)->GetZ() == z) {
    644         // Don't change anything if the Z hasn't changed
    645         return HWC2::Error::None;
    646       }
    647       current = layer_set_.erase(current);
    648       layer_on_display = true;
    649       break;
    650     }
    651   }
    652 
    653   if (!layer_on_display) {
    654     DLOGE("[%" PRIu64 "] updateLayerZ failed to find layer on display", id_);
    655     return HWC2::Error::BadLayer;
    656   }
    657 
    658   layer->SetLayerZOrder(z);
    659   layer_set_.emplace(layer);
    660   return HWC2::Error::None;
    661 }
    662 
    663 HWC2::Error HWCDisplay::SetVsyncEnabled(HWC2::Vsync enabled) {
    664   DLOGV("Display ID: %d enabled: %s", id_, to_string(enabled).c_str());
    665   DisplayError error = kErrorNone;
    666 
    667   if (shutdown_pending_ || !callbacks_->VsyncCallbackRegistered()) {
    668     return HWC2::Error::None;
    669   }
    670 
    671   bool state;
    672   if (enabled == HWC2::Vsync::Enable)
    673     state = true;
    674   else if (enabled == HWC2::Vsync::Disable)
    675     state = false;
    676   else
    677     return HWC2::Error::BadParameter;
    678 
    679   error = display_intf_->SetVSyncState(state);
    680 
    681   if (error != kErrorNone) {
    682     if (error == kErrorShutDown) {
    683       shutdown_pending_ = true;
    684       return HWC2::Error::None;
    685     }
    686     DLOGE("Failed. enabled = %s, error = %d", to_string(enabled).c_str(), error);
    687     return HWC2::Error::BadDisplay;
    688   }
    689 
    690   return HWC2::Error::None;
    691 }
    692 
    693 HWC2::Error HWCDisplay::SetPowerMode(HWC2::PowerMode mode) {
    694   DLOGV("display = %d, mode = %s", id_, to_string(mode).c_str());
    695   DisplayState state = kStateOff;
    696   bool flush_on_error = flush_on_error_;
    697 
    698   if (shutdown_pending_) {
    699     return HWC2::Error::None;
    700   }
    701 
    702   switch (mode) {
    703     case HWC2::PowerMode::Off:
    704       // During power off, all of the buffers are released.
    705       // Do not flush until a buffer is successfully submitted again.
    706       flush_on_error = false;
    707       state = kStateOff;
    708       if (tone_mapper_) {
    709         tone_mapper_->Terminate();
    710       }
    711       break;
    712     case HWC2::PowerMode::On:
    713       state = kStateOn;
    714       last_power_mode_ = HWC2::PowerMode::On;
    715       break;
    716     case HWC2::PowerMode::Doze:
    717       state = kStateDoze;
    718       last_power_mode_ = HWC2::PowerMode::Doze;
    719       break;
    720     case HWC2::PowerMode::DozeSuspend:
    721       state = kStateDozeSuspend;
    722       last_power_mode_ = HWC2::PowerMode::DozeSuspend;
    723       break;
    724     default:
    725       return HWC2::Error::BadParameter;
    726   }
    727 
    728   DisplayError error = display_intf_->SetDisplayState(state);
    729   validated_.reset();
    730 
    731   if (error == kErrorNone) {
    732     flush_on_error_ = flush_on_error;
    733   } else {
    734     if (error == kErrorShutDown) {
    735       shutdown_pending_ = true;
    736       return HWC2::Error::None;
    737     }
    738     DLOGE("Set state failed. Error = %d", error);
    739     return HWC2::Error::BadParameter;
    740   }
    741 
    742   return HWC2::Error::None;
    743 }
    744 
    745 HWC2::Error HWCDisplay::GetClientTargetSupport(uint32_t width, uint32_t height, int32_t format,
    746                                                int32_t dataspace) {
    747   ColorMetaData color_metadata = {};
    748   if (dataspace != HAL_DATASPACE_UNKNOWN) {
    749     GetColorPrimary(dataspace, &(color_metadata.colorPrimaries));
    750     GetTransfer(dataspace, &(color_metadata.transfer));
    751     GetRange(dataspace, &(color_metadata.range));
    752   }
    753 
    754   LayerBufferFormat sdm_format = GetSDMFormat(format, 0);
    755   if (display_intf_->GetClientTargetSupport(width, height, sdm_format,
    756                                             color_metadata) != kErrorNone) {
    757     return HWC2::Error::Unsupported;
    758   }
    759 
    760   return HWC2::Error::None;
    761 }
    762 
    763 HWC2::Error HWCDisplay::GetColorModes(uint32_t *out_num_modes, android_color_mode_t *out_modes) {
    764   if (out_modes) {
    765     out_modes[0] = HAL_COLOR_MODE_NATIVE;
    766   }
    767   *out_num_modes = 1;
    768 
    769   return HWC2::Error::None;
    770 }
    771 
    772 HWC2::Error HWCDisplay::GetDisplayConfigs(uint32_t *out_num_configs, hwc2_config_t *out_configs) {
    773   if (out_configs == nullptr) {
    774     *out_num_configs = num_configs_;
    775     return HWC2::Error::None;
    776   }
    777 
    778   *out_num_configs = num_configs_;
    779 
    780   for (uint32_t i = 0; i < num_configs_; i++) {
    781     out_configs[i] = i;
    782   }
    783 
    784   return HWC2::Error::None;
    785 }
    786 
    787 HWC2::Error HWCDisplay::GetDisplayAttribute(hwc2_config_t config, HWC2::Attribute attribute,
    788                                             int32_t *out_value) {
    789   DisplayConfigVariableInfo variable_config;
    790   // Get display attributes from config index only if resolution switch is supported.
    791   // Otherwise always send mixer attributes. This is to support destination scaler.
    792   if (num_configs_ > 1) {
    793     if (GetDisplayAttributesForConfig(INT(config), &variable_config) != kErrorNone) {
    794       DLOGE("Get variable config failed");
    795       return HWC2::Error::BadDisplay;
    796     }
    797   } else {
    798     if (display_intf_->GetFrameBufferConfig(&variable_config) != kErrorNone) {
    799       DLOGV("Get variable config failed");
    800       return HWC2::Error::BadDisplay;
    801     }
    802   }
    803 
    804   switch (attribute) {
    805     case HWC2::Attribute::VsyncPeriod:
    806       *out_value = INT32(variable_config.vsync_period_ns);
    807       break;
    808     case HWC2::Attribute::Width:
    809       *out_value = INT32(variable_config.x_pixels);
    810       break;
    811     case HWC2::Attribute::Height:
    812       *out_value = INT32(variable_config.y_pixels);
    813       break;
    814     case HWC2::Attribute::DpiX:
    815       *out_value = INT32(variable_config.x_dpi * 1000.0f);
    816       break;
    817     case HWC2::Attribute::DpiY:
    818       *out_value = INT32(variable_config.y_dpi * 1000.0f);
    819       break;
    820     default:
    821       DLOGW("Spurious attribute type = %s", to_string(attribute).c_str());
    822       *out_value = -1;
    823       return HWC2::Error::BadConfig;
    824   }
    825 
    826   return HWC2::Error::None;
    827 }
    828 
    829 HWC2::Error HWCDisplay::GetDisplayName(uint32_t *out_size, char *out_name) {
    830   // TODO(user): Get panel name and EDID name and populate it here
    831   if (out_name == nullptr) {
    832     *out_size = 32;
    833   } else {
    834     std::string name;
    835     switch (id_) {
    836       case HWC_DISPLAY_PRIMARY:
    837         name = "Primary Display";
    838         break;
    839       case HWC_DISPLAY_EXTERNAL:
    840         name = "External Display";
    841         break;
    842       case HWC_DISPLAY_VIRTUAL:
    843         name = "Virtual Display";
    844         break;
    845       default:
    846         name = "Unknown";
    847         break;
    848     }
    849     std::strncpy(out_name, name.c_str(), name.size());
    850     *out_size = UINT32(name.size());
    851   }
    852   return HWC2::Error::None;
    853 }
    854 
    855 HWC2::Error HWCDisplay::GetDisplayType(int32_t *out_type) {
    856   if (out_type != nullptr) {
    857     if (id_ == HWC_DISPLAY_VIRTUAL) {
    858       *out_type = HWC2_DISPLAY_TYPE_VIRTUAL;
    859     } else {
    860       *out_type = HWC2_DISPLAY_TYPE_PHYSICAL;
    861     }
    862     return HWC2::Error::None;
    863   } else {
    864     return HWC2::Error::BadParameter;
    865   }
    866 }
    867 
    868 HWC2::Error HWCDisplay::GetActiveConfig(hwc2_config_t *out_config) {
    869   if (out_config == nullptr) {
    870     return HWC2::Error::BadDisplay;
    871   }
    872 
    873   uint32_t active_index = 0;
    874   if (GetActiveDisplayConfig(&active_index) != kErrorNone) {
    875     return HWC2::Error::BadConfig;
    876   }
    877 
    878   *out_config = active_index;
    879 
    880   return HWC2::Error::None;
    881 }
    882 
    883 HWC2::Error HWCDisplay::SetClientTarget(buffer_handle_t target, int32_t acquire_fence,
    884                                         int32_t dataspace, hwc_region_t damage) {
    885   // TODO(user): SurfaceFlinger gives us a null pointer here when doing full SDE composition
    886   // The error is problematic for layer caching as it would overwrite our cached client target.
    887   // Reported bug 28569722 to resolve this.
    888   // For now, continue to use the last valid buffer reported to us for layer caching.
    889   if (target == nullptr) {
    890     return HWC2::Error::None;
    891   }
    892 
    893   if (acquire_fence == 0) {
    894     DLOGE("acquire_fence is zero");
    895     return HWC2::Error::BadParameter;
    896   }
    897 
    898   client_target_->SetLayerBuffer(target, acquire_fence);
    899   client_target_->SetLayerSurfaceDamage(damage);
    900   if (client_target_->GetLayerDataspace() != dataspace) {
    901     client_target_->SetLayerDataspace(dataspace);
    902     Layer *sdm_layer = client_target_->GetSDMLayer();
    903     // Data space would be validated at GetClientTargetSupport, so just use here.
    904     sdm::GetSDMColorSpace(dataspace, &sdm_layer->input_buffer.color_metadata);
    905   }
    906 
    907   return HWC2::Error::None;
    908 }
    909 
    910 HWC2::Error HWCDisplay::SetActiveConfig(hwc2_config_t config) {
    911   if (SetActiveDisplayConfig(config) != kErrorNone) {
    912     return HWC2::Error::BadConfig;
    913   }
    914 
    915   validated_.reset();
    916   return HWC2::Error::None;
    917 }
    918 
    919 DisplayError HWCDisplay::SetMixerResolution(uint32_t width, uint32_t height) {
    920   return kErrorNotSupported;
    921 }
    922 
    923 void HWCDisplay::SetFrameDumpConfig(uint32_t count, uint32_t bit_mask_layer_type) {
    924   dump_frame_count_ = count;
    925   dump_frame_index_ = 0;
    926   dump_input_layers_ = ((bit_mask_layer_type & (1 << INPUT_LAYER_DUMP)) != 0);
    927 
    928   if (tone_mapper_) {
    929     tone_mapper_->SetFrameDumpConfig(count);
    930   }
    931 
    932   DLOGI("num_frame_dump %d, input_layer_dump_enable %d", dump_frame_count_, dump_input_layers_);
    933   validated_.reset();
    934 }
    935 
    936 HWC2::PowerMode HWCDisplay::GetLastPowerMode() {
    937   return last_power_mode_;
    938 }
    939 
    940 DisplayError HWCDisplay::VSync(const DisplayEventVSync &vsync) {
    941   callbacks_->Vsync(id_, vsync.timestamp);
    942   return kErrorNone;
    943 }
    944 
    945 DisplayError HWCDisplay::Refresh() {
    946   return kErrorNotSupported;
    947 }
    948 
    949 DisplayError HWCDisplay::CECMessage(char *message) {
    950   if (qservice_) {
    951     qservice_->onCECMessageReceived(message, 0);
    952   } else {
    953     DLOGW("Qservice instance not available.");
    954   }
    955 
    956   return kErrorNone;
    957 }
    958 
    959 DisplayError HWCDisplay::HandleEvent(DisplayEvent event) {
    960   switch (event) {
    961     case kIdleTimeout:
    962       break;
    963     case kThermalEvent:
    964       validated_.reset();
    965       break;
    966     default:
    967       DLOGW("Unknown event: %d", event);
    968       break;
    969   }
    970 
    971   return kErrorNone;
    972 }
    973 
    974 HWC2::Error HWCDisplay::PrepareLayerStack(uint32_t *out_num_types, uint32_t *out_num_requests) {
    975   layer_changes_.clear();
    976   layer_requests_.clear();
    977   if (shutdown_pending_) {
    978     return HWC2::Error::BadDisplay;
    979   }
    980 
    981   if (!skip_prepare_) {
    982     DisplayError error = display_intf_->Prepare(&layer_stack_);
    983     if (error != kErrorNone) {
    984       if (error == kErrorShutDown) {
    985         shutdown_pending_ = true;
    986       } else if (error != kErrorPermission) {
    987         DLOGE("Prepare failed. Error = %d", error);
    988         // To prevent surfaceflinger infinite wait, flush the previous frame during Commit()
    989         // so that previous buffer and fences are released, and override the error.
    990         flush_ = true;
    991       }
    992       return HWC2::Error::BadDisplay;
    993     } else {
    994       validated_.set(type_);
    995     }
    996   } else {
    997     // Skip is not set
    998     MarkLayersForGPUBypass();
    999     skip_prepare_ = false;
   1000     DLOGI("SecureDisplay %s, Skip Prepare/Commit and Flush",
   1001           secure_display_active_ ? "Starting" : "Stopping");
   1002     flush_ = true;
   1003   }
   1004 
   1005   for (auto hwc_layer : layer_set_) {
   1006     Layer *layer = hwc_layer->GetSDMLayer();
   1007     LayerComposition &composition = layer->composition;
   1008 
   1009     if ((composition == kCompositionSDE) || (composition == kCompositionHybrid) ||
   1010         (composition == kCompositionBlit)) {
   1011       layer_requests_[hwc_layer->GetId()] = HWC2::LayerRequest::ClearClientTarget;
   1012     }
   1013 
   1014     HWC2::Composition requested_composition = hwc_layer->GetClientRequestedCompositionType();
   1015     // Set SDM composition to HWC2 type in HWCLayer
   1016     hwc_layer->SetComposition(composition);
   1017     HWC2::Composition device_composition  = hwc_layer->GetDeviceSelectedCompositionType();
   1018     // Update the changes list only if the requested composition is different from SDM comp type
   1019     // TODO(user): Take Care of other comptypes(BLIT)
   1020     if (requested_composition != device_composition) {
   1021       layer_changes_[hwc_layer->GetId()] = device_composition;
   1022     }
   1023     hwc_layer->ResetValidation();
   1024   }
   1025   client_target_->ResetValidation();
   1026   *out_num_types = UINT32(layer_changes_.size());
   1027   *out_num_requests = UINT32(layer_requests_.size());
   1028   skip_validate_ = false;
   1029   if (*out_num_types > 0) {
   1030     return HWC2::Error::HasChanges;
   1031   } else {
   1032     return HWC2::Error::None;
   1033   }
   1034 }
   1035 
   1036 HWC2::Error HWCDisplay::AcceptDisplayChanges() {
   1037   if (layer_set_.empty()) {
   1038     return HWC2::Error::None;
   1039   }
   1040 
   1041   if (!validated_.test(type_)) {
   1042     return HWC2::Error::NotValidated;
   1043   }
   1044 
   1045   for (const auto& change : layer_changes_) {
   1046     auto hwc_layer = layer_map_[change.first];
   1047     auto composition = change.second;
   1048     if (hwc_layer != nullptr) {
   1049       hwc_layer->UpdateClientCompositionType(composition);
   1050     } else {
   1051       DLOGW("Invalid layer: %" PRIu64, change.first);
   1052     }
   1053   }
   1054   return HWC2::Error::None;
   1055 }
   1056 
   1057 HWC2::Error HWCDisplay::GetChangedCompositionTypes(uint32_t *out_num_elements,
   1058                                                    hwc2_layer_t *out_layers, int32_t *out_types) {
   1059   if (layer_set_.empty()) {
   1060     return HWC2::Error::None;
   1061   }
   1062 
   1063   if (!validated_.test(type_)) {
   1064     DLOGW("Display is not validated");
   1065     return HWC2::Error::NotValidated;
   1066   }
   1067 
   1068   *out_num_elements = UINT32(layer_changes_.size());
   1069   if (out_layers != nullptr && out_types != nullptr) {
   1070     int i = 0;
   1071     for (auto change : layer_changes_) {
   1072       out_layers[i] = change.first;
   1073       out_types[i] = INT32(change.second);
   1074       i++;
   1075     }
   1076   }
   1077   return HWC2::Error::None;
   1078 }
   1079 
   1080 HWC2::Error HWCDisplay::GetReleaseFences(uint32_t *out_num_elements, hwc2_layer_t *out_layers,
   1081                                          int32_t *out_fences) {
   1082   if (out_layers != nullptr && out_fences != nullptr) {
   1083     int i = 0;
   1084     for (auto hwc_layer : layer_set_) {
   1085       out_layers[i] = hwc_layer->GetId();
   1086       out_fences[i] = hwc_layer->PopReleaseFence();
   1087       i++;
   1088     }
   1089   }
   1090   *out_num_elements = UINT32(layer_set_.size());
   1091   return HWC2::Error::None;
   1092 }
   1093 
   1094 HWC2::Error HWCDisplay::GetDisplayRequests(int32_t *out_display_requests,
   1095                                            uint32_t *out_num_elements, hwc2_layer_t *out_layers,
   1096                                            int32_t *out_layer_requests) {
   1097   if (layer_set_.empty()) {
   1098     return HWC2::Error::None;
   1099   }
   1100 
   1101   // No display requests for now
   1102   // Use for sharing blit buffers and
   1103   // writing wfd buffer directly to output if there is full GPU composition
   1104   // and no color conversion needed
   1105   if (!validated_.test(type_)) {
   1106     DLOGW("Display is not validated");
   1107     return HWC2::Error::NotValidated;
   1108   }
   1109 
   1110   *out_display_requests = 0;
   1111   *out_num_elements = UINT32(layer_requests_.size());
   1112   if (out_layers != nullptr && out_layer_requests != nullptr) {
   1113     int i = 0;
   1114     for (auto &request : layer_requests_) {
   1115       out_layers[i] = request.first;
   1116       out_layer_requests[i] = INT32(request.second);
   1117       i++;
   1118     }
   1119   }
   1120 
   1121   auto client_target_layer = client_target_->GetSDMLayer();
   1122   if (client_target_layer->request.flags.flip_buffer) {
   1123     *out_display_requests = INT32(HWC2::DisplayRequest::FlipClientTarget);
   1124   }
   1125 
   1126   return HWC2::Error::None;
   1127 }
   1128 
   1129 HWC2::Error HWCDisplay::GetHdrCapabilities(uint32_t *out_num_types, int32_t *out_types,
   1130                                            float *out_max_luminance,
   1131                                            float *out_max_average_luminance,
   1132                                            float *out_min_luminance) {
   1133   DisplayConfigFixedInfo fixed_info = {};
   1134   display_intf_->GetConfig(&fixed_info);
   1135 
   1136   if (!fixed_info.hdr_supported) {
   1137     *out_num_types = 0;
   1138     DLOGI("HDR is not supported");
   1139     return HWC2::Error::None;
   1140   }
   1141 
   1142   if (out_types == nullptr) {
   1143     // 1(now) - because we support only HDR10, change when HLG & DOLBY vision are supported
   1144     *out_num_types  = 1;
   1145   } else {
   1146     // Only HDR10 supported
   1147     *out_types = HAL_HDR_HDR10;
   1148     static const float kLuminanceFactor = 10000.0;
   1149     // luminance is expressed in the unit of 0.0001 cd/m2, convert it to 1cd/m2.
   1150     *out_max_luminance = FLOAT(fixed_info.max_luminance)/kLuminanceFactor;
   1151     *out_max_average_luminance = FLOAT(fixed_info.average_luminance)/kLuminanceFactor;
   1152     *out_min_luminance = FLOAT(fixed_info.min_luminance)/kLuminanceFactor;
   1153   }
   1154 
   1155   return HWC2::Error::None;
   1156 }
   1157 
   1158 
   1159 HWC2::Error HWCDisplay::CommitLayerStack(void) {
   1160   if (shutdown_pending_ || layer_set_.empty()) {
   1161     return HWC2::Error::None;
   1162   }
   1163 
   1164   if (skip_validate_ && !CanSkipValidate()) {
   1165     validated_.reset(type_);
   1166   }
   1167 
   1168   if (!validated_.test(type_)) {
   1169     DLOGV_IF(kTagClient, "Display %d is not validated", id_);
   1170     return HWC2::Error::NotValidated;
   1171   }
   1172 
   1173   DumpInputBuffers();
   1174 
   1175   if (!flush_) {
   1176     DisplayError error = kErrorUndefined;
   1177     int status = 0;
   1178     if (tone_mapper_) {
   1179       if (layer_stack_.flags.hdr_present) {
   1180         status = tone_mapper_->HandleToneMap(&layer_stack_);
   1181         if (status != 0) {
   1182           DLOGE("Error handling HDR in ToneMapper");
   1183         }
   1184       } else {
   1185         tone_mapper_->Terminate();
   1186       }
   1187     }
   1188     error = display_intf_->Commit(&layer_stack_);
   1189 
   1190     if (error == kErrorNone) {
   1191       // A commit is successfully submitted, start flushing on failure now onwards.
   1192       flush_on_error_ = true;
   1193     } else {
   1194       if (error == kErrorShutDown) {
   1195         shutdown_pending_ = true;
   1196         return HWC2::Error::Unsupported;
   1197       } else if (error == kErrorNotValidated) {
   1198         validated_.reset(type_);
   1199         return HWC2::Error::NotValidated;
   1200       } else if (error != kErrorPermission) {
   1201         DLOGE("Commit failed. Error = %d", error);
   1202         // To prevent surfaceflinger infinite wait, flush the previous frame during Commit()
   1203         // so that previous buffer and fences are released, and override the error.
   1204         flush_ = true;
   1205       }
   1206     }
   1207   }
   1208 
   1209   skip_validate_ = true;
   1210   return HWC2::Error::None;
   1211 }
   1212 
   1213 HWC2::Error HWCDisplay::PostCommitLayerStack(int32_t *out_retire_fence) {
   1214   auto status = HWC2::Error::None;
   1215 
   1216   // Do no call flush on errors, if a successful buffer is never submitted.
   1217   if (flush_ && flush_on_error_) {
   1218     display_intf_->Flush();
   1219     validated_.reset();
   1220   }
   1221 
   1222   if (tone_mapper_ && tone_mapper_->IsActive()) {
   1223      tone_mapper_->PostCommit(&layer_stack_);
   1224   }
   1225 
   1226   // TODO(user): No way to set the client target release fence on SF
   1227   int32_t &client_target_release_fence =
   1228       client_target_->GetSDMLayer()->input_buffer.release_fence_fd;
   1229   if (client_target_release_fence >= 0) {
   1230     close(client_target_release_fence);
   1231     client_target_release_fence = -1;
   1232   }
   1233   client_target_->ResetGeometryChanges();
   1234 
   1235   for (auto hwc_layer : layer_set_) {
   1236     hwc_layer->ResetGeometryChanges();
   1237     Layer *layer = hwc_layer->GetSDMLayer();
   1238     LayerBuffer *layer_buffer = &layer->input_buffer;
   1239 
   1240     if (!flush_) {
   1241       // If swapinterval property is set to 0 or for single buffer layers, do not update f/w
   1242       // release fences and discard fences from driver
   1243       if (swap_interval_zero_ || layer->flags.single_buffer) {
   1244         close(layer_buffer->release_fence_fd);
   1245       } else if (layer->composition != kCompositionGPU) {
   1246         hwc_layer->PushReleaseFence(layer_buffer->release_fence_fd);
   1247       } else {
   1248         hwc_layer->PushReleaseFence(-1);
   1249       }
   1250     } else {
   1251       // In case of flush, we don't return an error to f/w, so it will get a release fence out of
   1252       // the hwc_layer's release fence queue. We should push a -1 to preserve release fence
   1253       // circulation semantics.
   1254       hwc_layer->PushReleaseFence(-1);
   1255     }
   1256 
   1257     layer_buffer->release_fence_fd = -1;
   1258     if (layer_buffer->acquire_fence_fd >= 0) {
   1259       close(layer_buffer->acquire_fence_fd);
   1260       layer_buffer->acquire_fence_fd = -1;
   1261     }
   1262   }
   1263 
   1264   *out_retire_fence = -1;
   1265   if (!flush_) {
   1266     // if swapinterval property is set to 0 then close and reset the list retire fence
   1267     if (swap_interval_zero_) {
   1268       close(layer_stack_.retire_fence_fd);
   1269       layer_stack_.retire_fence_fd = -1;
   1270     }
   1271     *out_retire_fence = layer_stack_.retire_fence_fd;
   1272     layer_stack_.retire_fence_fd = -1;
   1273 
   1274     if (dump_frame_count_) {
   1275       dump_frame_count_--;
   1276       dump_frame_index_++;
   1277     }
   1278   }
   1279 
   1280   geometry_changes_ = GeometryChanges::kNone;
   1281   flush_ = false;
   1282 
   1283   ClearRequestFlags();
   1284 
   1285   return status;
   1286 }
   1287 
   1288 void HWCDisplay::SetIdleTimeoutMs(uint32_t timeout_ms) {
   1289   return;
   1290 }
   1291 
   1292 DisplayError HWCDisplay::SetMaxMixerStages(uint32_t max_mixer_stages) {
   1293   DisplayError error = kErrorNone;
   1294 
   1295   if (display_intf_) {
   1296     error = display_intf_->SetMaxMixerStages(max_mixer_stages);
   1297     validated_.reset();
   1298   }
   1299 
   1300   return error;
   1301 }
   1302 
   1303 LayerBufferFormat HWCDisplay::GetSDMFormat(const int32_t &source, const int flags) {
   1304   LayerBufferFormat format = kFormatInvalid;
   1305   if (flags & private_handle_t::PRIV_FLAGS_UBWC_ALIGNED) {
   1306     switch (source) {
   1307       case HAL_PIXEL_FORMAT_RGBA_8888:
   1308         format = kFormatRGBA8888Ubwc;
   1309         break;
   1310       case HAL_PIXEL_FORMAT_RGBX_8888:
   1311         format = kFormatRGBX8888Ubwc;
   1312         break;
   1313       case HAL_PIXEL_FORMAT_BGR_565:
   1314         format = kFormatBGR565Ubwc;
   1315         break;
   1316       case HAL_PIXEL_FORMAT_YCbCr_420_SP_VENUS:
   1317       case HAL_PIXEL_FORMAT_YCbCr_420_SP_VENUS_UBWC:
   1318       case HAL_PIXEL_FORMAT_NV12_ENCODEABLE:
   1319         format = kFormatYCbCr420SPVenusUbwc;
   1320         break;
   1321       case HAL_PIXEL_FORMAT_RGBA_1010102:
   1322         format = kFormatRGBA1010102Ubwc;
   1323         break;
   1324       case HAL_PIXEL_FORMAT_RGBX_1010102:
   1325         format = kFormatRGBX1010102Ubwc;
   1326         break;
   1327       case HAL_PIXEL_FORMAT_YCbCr_420_TP10_UBWC:
   1328         format = kFormatYCbCr420TP10Ubwc;
   1329         break;
   1330       case HAL_PIXEL_FORMAT_YCbCr_420_P010_UBWC:
   1331         format = kFormatYCbCr420P010Ubwc;
   1332         break;
   1333       default:
   1334         DLOGE("Unsupported format type for UBWC %d", source);
   1335         return kFormatInvalid;
   1336     }
   1337     return format;
   1338   }
   1339 
   1340   switch (source) {
   1341     case HAL_PIXEL_FORMAT_RGBA_8888:
   1342       format = kFormatRGBA8888;
   1343       break;
   1344     case HAL_PIXEL_FORMAT_RGBA_5551:
   1345       format = kFormatRGBA5551;
   1346       break;
   1347     case HAL_PIXEL_FORMAT_RGBA_4444:
   1348       format = kFormatRGBA4444;
   1349       break;
   1350     case HAL_PIXEL_FORMAT_BGRA_8888:
   1351       format = kFormatBGRA8888;
   1352       break;
   1353     case HAL_PIXEL_FORMAT_RGBX_8888:
   1354       format = kFormatRGBX8888;
   1355       break;
   1356     case HAL_PIXEL_FORMAT_BGRX_8888:
   1357       format = kFormatBGRX8888;
   1358       break;
   1359     case HAL_PIXEL_FORMAT_RGB_888:
   1360       format = kFormatRGB888;
   1361       break;
   1362     case HAL_PIXEL_FORMAT_RGB_565:
   1363       format = kFormatRGB565;
   1364       break;
   1365     case HAL_PIXEL_FORMAT_BGR_565:
   1366       format = kFormatBGR565;
   1367       break;
   1368     case HAL_PIXEL_FORMAT_BGR_888:
   1369       format = kFormatBGR888;
   1370       break;
   1371     case HAL_PIXEL_FORMAT_NV12_ENCODEABLE:
   1372     case HAL_PIXEL_FORMAT_YCbCr_420_SP_VENUS:
   1373       format = kFormatYCbCr420SemiPlanarVenus;
   1374       break;
   1375     case HAL_PIXEL_FORMAT_YCrCb_420_SP_VENUS:
   1376       format = kFormatYCrCb420SemiPlanarVenus;
   1377       break;
   1378     case HAL_PIXEL_FORMAT_YCbCr_420_SP_VENUS_UBWC:
   1379       format = kFormatYCbCr420SPVenusUbwc;
   1380       break;
   1381     case HAL_PIXEL_FORMAT_YV12:
   1382       format = kFormatYCrCb420PlanarStride16;
   1383       break;
   1384     case HAL_PIXEL_FORMAT_YCrCb_420_SP:
   1385       format = kFormatYCrCb420SemiPlanar;
   1386       break;
   1387     case HAL_PIXEL_FORMAT_YCbCr_420_SP:
   1388       format = kFormatYCbCr420SemiPlanar;
   1389       break;
   1390     case HAL_PIXEL_FORMAT_YCbCr_422_SP:
   1391       format = kFormatYCbCr422H2V1SemiPlanar;
   1392       break;
   1393     case HAL_PIXEL_FORMAT_YCbCr_422_I:
   1394       format = kFormatYCbCr422H2V1Packed;
   1395       break;
   1396     case HAL_PIXEL_FORMAT_CbYCrY_422_I:
   1397       format = kFormatCbYCrY422H2V1Packed;
   1398       break;
   1399     case HAL_PIXEL_FORMAT_RGBA_1010102:
   1400       format = kFormatRGBA1010102;
   1401       break;
   1402     case HAL_PIXEL_FORMAT_ARGB_2101010:
   1403       format = kFormatARGB2101010;
   1404       break;
   1405     case HAL_PIXEL_FORMAT_RGBX_1010102:
   1406       format = kFormatRGBX1010102;
   1407       break;
   1408     case HAL_PIXEL_FORMAT_XRGB_2101010:
   1409       format = kFormatXRGB2101010;
   1410       break;
   1411     case HAL_PIXEL_FORMAT_BGRA_1010102:
   1412       format = kFormatBGRA1010102;
   1413       break;
   1414     case HAL_PIXEL_FORMAT_ABGR_2101010:
   1415       format = kFormatABGR2101010;
   1416       break;
   1417     case HAL_PIXEL_FORMAT_BGRX_1010102:
   1418       format = kFormatBGRX1010102;
   1419       break;
   1420     case HAL_PIXEL_FORMAT_XBGR_2101010:
   1421       format = kFormatXBGR2101010;
   1422       break;
   1423     case HAL_PIXEL_FORMAT_YCbCr_420_P010:
   1424       format = kFormatYCbCr420P010;
   1425       break;
   1426     case HAL_PIXEL_FORMAT_YCbCr_420_TP10_UBWC:
   1427       format = kFormatYCbCr420TP10Ubwc;
   1428       break;
   1429     case HAL_PIXEL_FORMAT_YCbCr_420_P010_UBWC:
   1430       format = kFormatYCbCr420P010Ubwc;
   1431       break;
   1432     default:
   1433       DLOGW("Unsupported format type = %d", source);
   1434       return kFormatInvalid;
   1435   }
   1436 
   1437   return format;
   1438 }
   1439 
   1440 void HWCDisplay::DumpInputBuffers() {
   1441   char dir_path[PATH_MAX];
   1442 
   1443   if (!dump_frame_count_ || flush_ || !dump_input_layers_) {
   1444     return;
   1445   }
   1446 
   1447   DLOGI("dump_frame_count %d dump_input_layers %d", dump_frame_count_, dump_input_layers_);
   1448   snprintf(dir_path, sizeof(dir_path), "%s/frame_dump_%s", HWCDebugHandler::DumpDir(),
   1449            GetDisplayString());
   1450 
   1451   if (mkdir(dir_path, 0777) != 0 && errno != EEXIST) {
   1452     DLOGW("Failed to create %s directory errno = %d, desc = %s", dir_path, errno, strerror(errno));
   1453     return;
   1454   }
   1455 
   1456   // if directory exists already, need to explicitly change the permission.
   1457   if (errno == EEXIST && chmod(dir_path, 0777) != 0) {
   1458     DLOGW("Failed to change permissions on %s directory", dir_path);
   1459     return;
   1460   }
   1461 
   1462   for (uint32_t i = 0; i < layer_stack_.layers.size(); i++) {
   1463     auto layer = layer_stack_.layers.at(i);
   1464     const private_handle_t *pvt_handle =
   1465         reinterpret_cast<const private_handle_t *>(layer->input_buffer.buffer_id);
   1466     auto acquire_fence_fd = layer->input_buffer.acquire_fence_fd;
   1467 
   1468     if (acquire_fence_fd >= 0) {
   1469       int error = sync_wait(acquire_fence_fd, 1000);
   1470       if (error < 0) {
   1471         DLOGW("sync_wait error errno = %d, desc = %s", errno, strerror(errno));
   1472         return;
   1473       }
   1474     }
   1475 
   1476     DLOGI("Dump layer[%d] of %d pvt_handle %x pvt_handle->base %x", i, layer_stack_.layers.size(),
   1477           pvt_handle, pvt_handle? pvt_handle->base : 0);
   1478 
   1479     if (!pvt_handle) {
   1480       DLOGE("Buffer handle is null");
   1481       return;
   1482     }
   1483 
   1484     if (!pvt_handle->base) {
   1485       DisplayError error = buffer_allocator_->MapBuffer(pvt_handle, -1);
   1486       if (error != kErrorNone) {
   1487         DLOGE("Failed to map buffer, error = %d", error);
   1488         return;
   1489       }
   1490     }
   1491 
   1492     char dump_file_name[PATH_MAX];
   1493     size_t result = 0;
   1494 
   1495     snprintf(dump_file_name, sizeof(dump_file_name), "%s/input_layer%d_%dx%d_%s_frame%d.raw",
   1496              dir_path, i, pvt_handle->width, pvt_handle->height,
   1497              qdutils::GetHALPixelFormatString(pvt_handle->format), dump_frame_index_);
   1498 
   1499     FILE *fp = fopen(dump_file_name, "w+");
   1500     if (fp) {
   1501       result = fwrite(reinterpret_cast<void *>(pvt_handle->base), pvt_handle->size, 1, fp);
   1502       fclose(fp);
   1503     }
   1504 
   1505     int release_fence = -1;
   1506     DisplayError error = buffer_allocator_->UnmapBuffer(pvt_handle, &release_fence);
   1507     if (error != kErrorNone) {
   1508       DLOGE("Failed to unmap buffer, error = %d", error);
   1509       return;
   1510     }
   1511 
   1512     DLOGI("Frame Dump %s: is %s", dump_file_name, result ? "Successful" : "Failed");
   1513   }
   1514 }
   1515 
   1516 void HWCDisplay::DumpOutputBuffer(const BufferInfo &buffer_info, void *base, int fence) {
   1517   char dir_path[PATH_MAX];
   1518 
   1519   snprintf(dir_path, sizeof(dir_path), "%s/frame_dump_%s", HWCDebugHandler::DumpDir(),
   1520            GetDisplayString());
   1521 
   1522   if (mkdir(dir_path, 777) != 0 && errno != EEXIST) {
   1523     DLOGW("Failed to create %s directory errno = %d, desc = %s", dir_path, errno, strerror(errno));
   1524     return;
   1525   }
   1526 
   1527   // if directory exists already, need to explicitly change the permission.
   1528   if (errno == EEXIST && chmod(dir_path, 0777) != 0) {
   1529     DLOGW("Failed to change permissions on %s directory", dir_path);
   1530     return;
   1531   }
   1532 
   1533   if (base) {
   1534     char dump_file_name[PATH_MAX];
   1535     size_t result = 0;
   1536 
   1537     if (fence >= 0) {
   1538       int error = sync_wait(fence, 1000);
   1539       if (error < 0) {
   1540         DLOGW("sync_wait error errno = %d, desc = %s", errno, strerror(errno));
   1541         return;
   1542       }
   1543     }
   1544 
   1545     snprintf(dump_file_name, sizeof(dump_file_name), "%s/output_layer_%dx%d_%s_frame%d.raw",
   1546              dir_path, buffer_info.buffer_config.width, buffer_info.buffer_config.height,
   1547              GetFormatString(buffer_info.buffer_config.format), dump_frame_index_);
   1548 
   1549     FILE *fp = fopen(dump_file_name, "w+");
   1550     if (fp) {
   1551       result = fwrite(base, buffer_info.alloc_buffer_info.size, 1, fp);
   1552       fclose(fp);
   1553     }
   1554 
   1555     DLOGI("Frame Dump of %s is %s", dump_file_name, result ? "Successful" : "Failed");
   1556   }
   1557 }
   1558 
   1559 const char *HWCDisplay::GetDisplayString() {
   1560   switch (type_) {
   1561     case kPrimary:
   1562       return "primary";
   1563     case kHDMI:
   1564       return "hdmi";
   1565     case kVirtual:
   1566       return "virtual";
   1567     default:
   1568       return "invalid";
   1569   }
   1570 }
   1571 
   1572 int HWCDisplay::SetFrameBufferResolution(uint32_t x_pixels, uint32_t y_pixels) {
   1573   if (x_pixels <= 0 || y_pixels <= 0) {
   1574     DLOGW("Unsupported config: x_pixels=%d, y_pixels=%d", x_pixels, y_pixels);
   1575     return -EINVAL;
   1576   }
   1577 
   1578   DisplayConfigVariableInfo fb_config;
   1579   DisplayError error = display_intf_->GetFrameBufferConfig(&fb_config);
   1580   if (error != kErrorNone) {
   1581     DLOGV("Get frame buffer config failed. Error = %d", error);
   1582     return -EINVAL;
   1583   }
   1584 
   1585   fb_config.x_pixels = x_pixels;
   1586   fb_config.y_pixels = y_pixels;
   1587 
   1588   error = display_intf_->SetFrameBufferConfig(fb_config);
   1589   if (error != kErrorNone) {
   1590     DLOGV("Set frame buffer config failed. Error = %d", error);
   1591     return -EINVAL;
   1592   }
   1593 
   1594   // Create rects to represent the new source and destination crops
   1595   LayerRect crop = LayerRect(0, 0, FLOAT(x_pixels), FLOAT(y_pixels));
   1596   hwc_rect_t scaled_display_frame = {0, 0, INT(x_pixels), INT(y_pixels)};
   1597   ApplyScanAdjustment(&scaled_display_frame);
   1598   client_target_->SetLayerDisplayFrame(scaled_display_frame);
   1599 
   1600   auto client_target_layer = client_target_->GetSDMLayer();
   1601   client_target_layer->src_rect = crop;
   1602 
   1603   int aligned_width;
   1604   int aligned_height;
   1605   uint32_t usage = GRALLOC_USAGE_HW_FB;
   1606   int format = HAL_PIXEL_FORMAT_RGBA_8888;
   1607   int ubwc_disabled = 0;
   1608   int flags = 0;
   1609 
   1610   // By default UBWC is enabled and below property is global enable/disable for all
   1611   // buffers allocated through gralloc , including framebuffer targets.
   1612   HWCDebugHandler::Get()->GetProperty(DISABLE_UBWC_PROP, &ubwc_disabled);
   1613   if (!ubwc_disabled) {
   1614     usage |= GRALLOC_USAGE_PRIVATE_ALLOC_UBWC;
   1615     flags |= private_handle_t::PRIV_FLAGS_UBWC_ALIGNED;
   1616   }
   1617 
   1618 #ifdef USE_GRALLOC1
   1619   buffer_allocator_->GetAlignedWidthAndHeight(INT(x_pixels), INT(y_pixels), format, usage,
   1620                                               &aligned_width, &aligned_height);
   1621 #else
   1622   AdrenoMemInfo::getInstance().getAlignedWidthAndHeight(INT(x_pixels), INT(y_pixels), format,
   1623                                                         INT(usage), aligned_width, aligned_height);
   1624 #endif
   1625 
   1626   // TODO(user): How does the dirty region get set on the client target? File bug on Google
   1627   client_target_layer->composition = kCompositionGPUTarget;
   1628   client_target_layer->input_buffer.format = GetSDMFormat(format, flags);
   1629   client_target_layer->input_buffer.width = UINT32(aligned_width);
   1630   client_target_layer->input_buffer.height = UINT32(aligned_height);
   1631   client_target_layer->input_buffer.unaligned_width = x_pixels;
   1632   client_target_layer->input_buffer.unaligned_height = y_pixels;
   1633   client_target_layer->plane_alpha = 255;
   1634 
   1635   DLOGI("New framebuffer resolution (%dx%d)", fb_config.x_pixels, fb_config.y_pixels);
   1636 
   1637   return 0;
   1638 }
   1639 
   1640 void HWCDisplay::GetFrameBufferResolution(uint32_t *x_pixels, uint32_t *y_pixels) {
   1641   DisplayConfigVariableInfo fb_config;
   1642   display_intf_->GetFrameBufferConfig(&fb_config);
   1643 
   1644   *x_pixels = fb_config.x_pixels;
   1645   *y_pixels = fb_config.y_pixels;
   1646 }
   1647 
   1648 DisplayError HWCDisplay::GetMixerResolution(uint32_t *x_pixels, uint32_t *y_pixels) {
   1649   return display_intf_->GetMixerResolution(x_pixels, y_pixels);
   1650 }
   1651 
   1652 void HWCDisplay::GetPanelResolution(uint32_t *x_pixels, uint32_t *y_pixels) {
   1653   DisplayConfigVariableInfo display_config;
   1654   uint32_t active_index = 0;
   1655 
   1656   display_intf_->GetActiveConfig(&active_index);
   1657   display_intf_->GetConfig(active_index, &display_config);
   1658 
   1659   *x_pixels = display_config.x_pixels;
   1660   *y_pixels = display_config.y_pixels;
   1661 }
   1662 
   1663 int HWCDisplay::SetDisplayStatus(DisplayStatus display_status) {
   1664   int status = 0;
   1665 
   1666   switch (display_status) {
   1667     case kDisplayStatusResume:
   1668       display_paused_ = false;
   1669     case kDisplayStatusOnline:
   1670       status = INT32(SetPowerMode(HWC2::PowerMode::On));
   1671       break;
   1672     case kDisplayStatusPause:
   1673       display_paused_ = true;
   1674     case kDisplayStatusOffline:
   1675       status = INT32(SetPowerMode(HWC2::PowerMode::Off));
   1676       break;
   1677     default:
   1678       DLOGW("Invalid display status %d", display_status);
   1679       return -EINVAL;
   1680   }
   1681 
   1682   if (display_status == kDisplayStatusResume || display_status == kDisplayStatusPause) {
   1683     callbacks_->Refresh(HWC_DISPLAY_PRIMARY);
   1684     validated_.reset();
   1685   }
   1686 
   1687   return status;
   1688 }
   1689 
   1690 HWC2::Error HWCDisplay::SetCursorPosition(hwc2_layer_t layer, int x, int y) {
   1691   if (shutdown_pending_) {
   1692     return HWC2::Error::None;
   1693   }
   1694 
   1695   HWCLayer *hwc_layer = GetHWCLayer(layer);
   1696   if (hwc_layer == nullptr) {
   1697     return HWC2::Error::BadLayer;
   1698   }
   1699   if (hwc_layer->GetDeviceSelectedCompositionType() != HWC2::Composition::Cursor) {
   1700     return HWC2::Error::None;
   1701   }
   1702   if (!skip_validate_ && validated_.test(type_)) {
   1703     // the device is currently in the middle of the validate/present sequence,
   1704     // cannot set the Position(as per HWC2 spec)
   1705     return HWC2::Error::NotValidated;
   1706   }
   1707 
   1708   DisplayState state;
   1709   if (display_intf_->GetDisplayState(&state) == kErrorNone) {
   1710     if (state != kStateOn) {
   1711       return HWC2::Error::None;
   1712     }
   1713   }
   1714 
   1715   // TODO(user): HWC1.5 was not letting SetCursorPosition before validateDisplay,
   1716   // but HWC2.0 doesn't let setting cursor position after validate before present.
   1717   // Need to revisit.
   1718 
   1719   auto error = display_intf_->SetCursorPosition(x, y);
   1720   if (error != kErrorNone) {
   1721     if (error == kErrorShutDown) {
   1722       shutdown_pending_ = true;
   1723       return HWC2::Error::None;
   1724     }
   1725 
   1726     DLOGE("Failed for x = %d y = %d, Error = %d", x, y, error);
   1727     return HWC2::Error::BadDisplay;
   1728   }
   1729 
   1730   return HWC2::Error::None;
   1731 }
   1732 
   1733 int HWCDisplay::OnMinHdcpEncryptionLevelChange(uint32_t min_enc_level) {
   1734   DisplayError error = display_intf_->OnMinHdcpEncryptionLevelChange(min_enc_level);
   1735   if (error != kErrorNone) {
   1736     DLOGE("Failed. Error = %d", error);
   1737     return -1;
   1738   }
   1739 
   1740   validated_.reset();
   1741   return 0;
   1742 }
   1743 
   1744 void HWCDisplay::MarkLayersForGPUBypass() {
   1745   for (auto hwc_layer : layer_set_) {
   1746     auto layer = hwc_layer->GetSDMLayer();
   1747     layer->composition = kCompositionSDE;
   1748   }
   1749   validated_.set(type_);
   1750 }
   1751 
   1752 void HWCDisplay::MarkLayersForClientComposition() {
   1753   // ClientComposition - GPU comp, to achieve this, set skip flag so that
   1754   // SDM does not handle this layer and hwc_layer composition will be
   1755   // set correctly at the end of Prepare.
   1756   DLOGV_IF(kTagClient, "HWC Layers marked for GPU comp");
   1757   for (auto hwc_layer : layer_set_) {
   1758     Layer *layer = hwc_layer->GetSDMLayer();
   1759     layer->flags.skip = true;
   1760   }
   1761   layer_stack_.flags.skip_present = true;
   1762 }
   1763 
   1764 void HWCDisplay::ApplyScanAdjustment(hwc_rect_t *display_frame) {
   1765 }
   1766 
   1767 int HWCDisplay::SetPanelBrightness(int level) {
   1768   int ret = 0;
   1769   if (display_intf_) {
   1770     ret = display_intf_->SetPanelBrightness(level);
   1771     validated_.reset();
   1772   } else {
   1773     ret = -EINVAL;
   1774   }
   1775 
   1776   return ret;
   1777 }
   1778 
   1779 int HWCDisplay::GetPanelBrightness(int *level) {
   1780   return display_intf_->GetPanelBrightness(level);
   1781 }
   1782 
   1783 int HWCDisplay::ToggleScreenUpdates(bool enable) {
   1784   display_paused_ = enable ? false : true;
   1785   callbacks_->Refresh(HWC_DISPLAY_PRIMARY);
   1786   validated_.reset();
   1787   return 0;
   1788 }
   1789 
   1790 int HWCDisplay::ColorSVCRequestRoute(const PPDisplayAPIPayload &in_payload,
   1791                                      PPDisplayAPIPayload *out_payload,
   1792                                      PPPendingParams *pending_action) {
   1793   int ret = 0;
   1794 
   1795   if (display_intf_)
   1796     ret = display_intf_->ColorSVCRequestRoute(in_payload, out_payload, pending_action);
   1797   else
   1798     ret = -EINVAL;
   1799 
   1800   return ret;
   1801 }
   1802 
   1803 void HWCDisplay::SolidFillPrepare() {
   1804   if (solid_fill_enable_) {
   1805     if (solid_fill_layer_ == NULL) {
   1806       // Create a dummy layer here
   1807       solid_fill_layer_ = new Layer();
   1808     }
   1809     uint32_t primary_width = 0, primary_height = 0;
   1810     GetMixerResolution(&primary_width, &primary_height);
   1811 
   1812     LayerBuffer *layer_buffer = &solid_fill_layer_->input_buffer;
   1813     layer_buffer->width = primary_width;
   1814     layer_buffer->height = primary_height;
   1815     layer_buffer->unaligned_width = primary_width;
   1816     layer_buffer->unaligned_height = primary_height;
   1817     layer_buffer->acquire_fence_fd = -1;
   1818     layer_buffer->release_fence_fd = -1;
   1819 
   1820     LayerRect rect;
   1821     rect.top = 0; rect.left = 0;
   1822     rect.right = primary_width;
   1823     rect.bottom = primary_height;
   1824 
   1825     solid_fill_layer_->composition = kCompositionGPU;
   1826     solid_fill_layer_->src_rect = rect;
   1827     solid_fill_layer_->dst_rect = rect;
   1828 
   1829     solid_fill_layer_->blending = kBlendingPremultiplied;
   1830     solid_fill_layer_->solid_fill_color = solid_fill_color_;
   1831     solid_fill_layer_->frame_rate = 60;
   1832     solid_fill_layer_->visible_regions.push_back(solid_fill_layer_->dst_rect);
   1833     solid_fill_layer_->flags.updating = 1;
   1834     solid_fill_layer_->flags.solid_fill = true;
   1835   } else {
   1836     // delete the dummy layer
   1837     delete solid_fill_layer_;
   1838     solid_fill_layer_ = NULL;
   1839   }
   1840 
   1841   if (solid_fill_enable_ && solid_fill_layer_) {
   1842     BuildSolidFillStack();
   1843     MarkLayersForGPUBypass();
   1844   }
   1845 
   1846   return;
   1847 }
   1848 
   1849 void HWCDisplay::SolidFillCommit() {
   1850   if (solid_fill_enable_ && solid_fill_layer_) {
   1851     LayerBuffer *layer_buffer = &solid_fill_layer_->input_buffer;
   1852     if (layer_buffer->release_fence_fd > 0) {
   1853       close(layer_buffer->release_fence_fd);
   1854       layer_buffer->release_fence_fd = -1;
   1855     }
   1856     if (layer_stack_.retire_fence_fd > 0) {
   1857       close(layer_stack_.retire_fence_fd);
   1858       layer_stack_.retire_fence_fd = -1;
   1859     }
   1860   }
   1861 }
   1862 
   1863 int HWCDisplay::GetVisibleDisplayRect(hwc_rect_t *visible_rect) {
   1864   if (!IsValid(display_rect_)) {
   1865     return -EINVAL;
   1866   }
   1867 
   1868   visible_rect->left = INT(display_rect_.left);
   1869   visible_rect->top = INT(display_rect_.top);
   1870   visible_rect->right = INT(display_rect_.right);
   1871   visible_rect->bottom = INT(display_rect_.bottom);
   1872   DLOGI("Dpy = %d Visible Display Rect(%d %d %d %d)", visible_rect->left, visible_rect->top,
   1873         visible_rect->right, visible_rect->bottom);
   1874 
   1875   return 0;
   1876 }
   1877 
   1878 void HWCDisplay::SetSecureDisplay(bool secure_display_active) {
   1879   if (secure_display_active_ != secure_display_active) {
   1880     DLOGI("SecureDisplay state changed from %d to %d Needs Flush!!", secure_display_active_,
   1881           secure_display_active);
   1882     secure_display_active_ = secure_display_active;
   1883     skip_prepare_ = true;
   1884   }
   1885   return;
   1886 }
   1887 
   1888 int HWCDisplay::SetActiveDisplayConfig(uint32_t config) {
   1889   int status = (display_intf_->SetActiveConfig(config) == kErrorNone) ? 0 : -1;
   1890   validated_.reset();
   1891   return status;
   1892 }
   1893 
   1894 int HWCDisplay::GetActiveDisplayConfig(uint32_t *config) {
   1895   return display_intf_->GetActiveConfig(config) == kErrorNone ? 0 : -1;
   1896 }
   1897 
   1898 int HWCDisplay::GetDisplayConfigCount(uint32_t *count) {
   1899   return display_intf_->GetNumVariableInfoConfigs(count) == kErrorNone ? 0 : -1;
   1900 }
   1901 
   1902 int HWCDisplay::GetDisplayAttributesForConfig(int config,
   1903                                             DisplayConfigVariableInfo *display_attributes) {
   1904   return display_intf_->GetConfig(UINT32(config), display_attributes) == kErrorNone ? 0 : -1;
   1905 }
   1906 
   1907 uint32_t HWCDisplay::GetUpdatingLayersCount(void) {
   1908   uint32_t updating_count = 0;
   1909 
   1910   for (uint i = 0; i < layer_stack_.layers.size(); i++) {
   1911     auto layer = layer_stack_.layers.at(i);
   1912     if (layer->flags.updating) {
   1913       updating_count++;
   1914     }
   1915   }
   1916 
   1917   return updating_count;
   1918 }
   1919 
   1920 bool HWCDisplay::IsLayerUpdating(const Layer *layer) {
   1921   // Layer should be considered updating if
   1922   //   a) layer is in single buffer mode, or
   1923   //   b) valid dirty_regions(android specific hint for updating status), or
   1924   //   c) layer stack geometry has changed (TODO(user): Remove when SDM accepts
   1925   //      geometry_changed as bit fields).
   1926   return (layer->flags.single_buffer || IsSurfaceUpdated(layer->dirty_regions) ||
   1927           geometry_changes_);
   1928 }
   1929 
   1930 bool HWCDisplay::IsSurfaceUpdated(const std::vector<LayerRect> &dirty_regions) {
   1931   // based on dirty_regions determine if its updating
   1932   // dirty_rect count = 0 - whole layer - updating.
   1933   // dirty_rect count = 1 or more valid rects - updating.
   1934   // dirty_rect count = 1 with (0,0,0,0) - not updating.
   1935   return (dirty_regions.empty() || IsValid(dirty_regions.at(0)));
   1936 }
   1937 
   1938 uint32_t HWCDisplay::SanitizeRefreshRate(uint32_t req_refresh_rate) {
   1939   uint32_t refresh_rate = req_refresh_rate;
   1940 
   1941   if (refresh_rate < min_refresh_rate_) {
   1942     // Pick the next multiple of request which is within the range
   1943     refresh_rate =
   1944         (((min_refresh_rate_ / refresh_rate) + ((min_refresh_rate_ % refresh_rate) ? 1 : 0)) *
   1945          refresh_rate);
   1946   }
   1947 
   1948   if (refresh_rate > max_refresh_rate_) {
   1949     refresh_rate = max_refresh_rate_;
   1950   }
   1951 
   1952   return refresh_rate;
   1953 }
   1954 
   1955 DisplayClass HWCDisplay::GetDisplayClass() {
   1956   return display_class_;
   1957 }
   1958 
   1959 void HWCDisplay::CloseAcquireFds() {
   1960   for (auto hwc_layer : layer_set_) {
   1961     auto layer = hwc_layer->GetSDMLayer();
   1962     if (layer->input_buffer.acquire_fence_fd >= 0) {
   1963       close(layer->input_buffer.acquire_fence_fd);
   1964       layer->input_buffer.acquire_fence_fd = -1;
   1965     }
   1966   }
   1967   int32_t &client_target_acquire_fence =
   1968       client_target_->GetSDMLayer()->input_buffer.acquire_fence_fd;
   1969   if (client_target_acquire_fence >= 0) {
   1970     close(client_target_acquire_fence);
   1971     client_target_acquire_fence = -1;
   1972   }
   1973 }
   1974 
   1975 void HWCDisplay::ClearRequestFlags() {
   1976   for (Layer *layer : layer_stack_.layers) {
   1977     layer->request.flags = {};
   1978   }
   1979 }
   1980 
   1981 std::string HWCDisplay::Dump() {
   1982   std::ostringstream os;
   1983   os << "\n------------HWC----------------\n";
   1984   os << "HWC2 display_id: " << id_ << std::endl;
   1985   for (auto layer : layer_set_) {
   1986     auto sdm_layer = layer->GetSDMLayer();
   1987     auto transform = sdm_layer->transform;
   1988     os << "layer: " << std::setw(4) << layer->GetId();
   1989     os << " z: " << layer->GetZ();
   1990     os << " compositon: " <<
   1991           to_string(layer->GetClientRequestedCompositionType()).c_str();
   1992     os << "/" <<
   1993           to_string(layer->GetDeviceSelectedCompositionType()).c_str();
   1994     os << " alpha: " << std::to_string(sdm_layer->plane_alpha).c_str();
   1995     os << " format: " << std::setw(22) << GetFormatString(sdm_layer->input_buffer.format);
   1996     os << " dataspace:" << std::hex << "0x" << std::setw(8) << std::setfill('0')
   1997        << layer->GetLayerDataspace() << std::dec << std::setfill(' ');
   1998     os << " transform: " << transform.rotation << "/" << transform.flip_horizontal <<
   1999           "/"<< transform.flip_vertical;
   2000     os << " buffer_id: " << std::hex << "0x" << sdm_layer->input_buffer.buffer_id << std::dec
   2001        << std::endl;
   2002   }
   2003 
   2004   if (color_mode_) {
   2005     os << "\n----------Color Modes---------\n";
   2006     color_mode_->Dump(&os);
   2007   }
   2008 
   2009   if (display_intf_) {
   2010     os << "\n------------SDM----------------\n";
   2011     os << display_intf_->Dump();
   2012   }
   2013 
   2014   os << "\n";
   2015 
   2016   return os.str();
   2017 }
   2018 
   2019 bool HWCDisplay::CanSkipValidate() {
   2020   // Layer Stack checks
   2021   if (layer_stack_.flags.hdr_present && (tone_mapper_ && tone_mapper_->IsActive())) {
   2022     DLOGV_IF(kTagClient, "HDR content present with tone mapping enabled. Returning false.");
   2023     return false;
   2024   }
   2025 
   2026   if (client_target_->NeedsValidation()) {
   2027     DLOGV_IF(kTagClient, "Framebuffer target needs validation. Returning false.");
   2028     return false;
   2029   }
   2030 
   2031   for (auto hwc_layer : layer_set_) {
   2032     if (hwc_layer->NeedsValidation()) {
   2033       DLOGV_IF(kTagClient, "hwc_layer[%d] needs validation. Returning false.",
   2034                hwc_layer->GetId());
   2035       return false;
   2036     }
   2037 
   2038     // Do not allow Skip Validate, if any layer needs GPU Composition.
   2039     if (hwc_layer->GetDeviceSelectedCompositionType() == HWC2::Composition::Client) {
   2040       DLOGV_IF(kTagClient, "hwc_layer[%d] is GPU composed. Returning false.",
   2041                hwc_layer->GetId());
   2042       return false;
   2043     }
   2044   }
   2045 
   2046   return true;
   2047 }
   2048 
   2049 }  // namespace sdm
   2050