1 /* 2 * Copyright (C) 2022 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef ANDROID_HWC2_DEVICE_HWC_DISPLAY_H 18 #define ANDROID_HWC2_DEVICE_HWC_DISPLAY_H 19 20 #include <hardware/hwcomposer2.h> 21 22 #include <optional> 23 24 #include "HwcDisplayConfigs.h" 25 #include "drm/DrmAtomicStateManager.h" 26 #include "drm/ResourceManager.h" 27 #include "drm/VSyncWorker.h" 28 #include "drmhwcomposer.h" 29 #include "hwc2_device/HwcLayer.h" 30 31 namespace android { 32 33 class Backend; 34 class DrmHwcTwo; 35 36 inline constexpr uint32_t kPrimaryDisplay = 0; 37 38 class HwcDisplay { 39 public: 40 HwcDisplay(hwc2_display_t handle, HWC2::DisplayType type, DrmHwcTwo *hwc2); 41 HwcDisplay(const HwcDisplay &) = delete; 42 ~HwcDisplay(); 43 44 /* SetPipeline should be carefully used only by DrmHwcTwo hotplug handlers */ 45 void SetPipeline(DrmDisplayPipeline *pipeline); 46 47 HWC2::Error CreateComposition(AtomicCommitArgs &a_args); 48 std::vector<HwcLayer *> GetOrderLayersByZPos(); 49 50 void ClearDisplay(); 51 52 std::string Dump(); 53 54 // HWC Hooks 55 HWC2::Error AcceptDisplayChanges(); 56 HWC2::Error CreateLayer(hwc2_layer_t *layer); 57 HWC2::Error DestroyLayer(hwc2_layer_t layer); 58 HWC2::Error GetActiveConfig(hwc2_config_t *config) const; 59 HWC2::Error GetChangedCompositionTypes(uint32_t *num_elements, 60 hwc2_layer_t *layers, int32_t *types); 61 HWC2::Error GetClientTargetSupport(uint32_t width, uint32_t height, 62 int32_t format, int32_t dataspace); 63 HWC2::Error GetColorModes(uint32_t *num_modes, int32_t *modes); 64 HWC2::Error GetDisplayAttribute(hwc2_config_t config, int32_t attribute, 65 int32_t *value); 66 HWC2::Error GetDisplayConfigs(uint32_t *num_configs, hwc2_config_t *configs); 67 HWC2::Error GetDisplayName(uint32_t *size, char *name); 68 HWC2::Error GetDisplayRequests(int32_t *display_requests, 69 uint32_t *num_elements, hwc2_layer_t *layers, 70 int32_t *layer_requests); 71 HWC2::Error GetDisplayType(int32_t *type); 72 #if PLATFORM_SDK_VERSION > 27 73 HWC2::Error GetRenderIntents(int32_t mode, uint32_t *outNumIntents, 74 int32_t *outIntents); 75 HWC2::Error SetColorModeWithIntent(int32_t mode, int32_t intent); 76 #endif 77 #if PLATFORM_SDK_VERSION > 28 78 HWC2::Error GetDisplayIdentificationData(uint8_t *outPort, 79 uint32_t *outDataSize, 80 uint8_t *outData); 81 HWC2::Error GetDisplayCapabilities(uint32_t *outNumCapabilities, 82 uint32_t *outCapabilities); 83 HWC2::Error GetDisplayBrightnessSupport(bool *supported); 84 HWC2::Error SetDisplayBrightness(float); 85 #endif 86 #if PLATFORM_SDK_VERSION > 29 87 HWC2::Error GetDisplayConnectionType(uint32_t *outType); 88 89 HWC2::Error SetActiveConfigWithConstraints( 90 hwc2_config_t config, 91 hwc_vsync_period_change_constraints_t *vsyncPeriodChangeConstraints, 92 hwc_vsync_period_change_timeline_t *outTimeline); 93 HWC2::Error SetAutoLowLatencyMode(bool on); 94 HWC2::Error GetSupportedContentTypes( 95 uint32_t *outNumSupportedContentTypes, 96 const uint32_t *outSupportedContentTypes); 97 98 HWC2::Error SetContentType(int32_t contentType); 99 #endif 100 HWC2::Error GetDisplayVsyncPeriod(uint32_t *outVsyncPeriod); 101 102 HWC2::Error GetDozeSupport(int32_t *support); 103 HWC2::Error GetHdrCapabilities(uint32_t *num_types, int32_t *types, 104 float *max_luminance, 105 float *max_average_luminance, 106 float *min_luminance); 107 HWC2::Error GetReleaseFences(uint32_t *num_elements, hwc2_layer_t *layers, 108 int32_t *fences); 109 HWC2::Error PresentDisplay(int32_t *present_fence); 110 HWC2::Error SetActiveConfig(hwc2_config_t config); 111 HWC2::Error ChosePreferredConfig(); 112 HWC2::Error SetClientTarget(buffer_handle_t target, int32_t acquire_fence, 113 int32_t dataspace, hwc_region_t damage); 114 HWC2::Error SetColorMode(int32_t mode); 115 HWC2::Error SetColorTransform(const float *matrix, int32_t hint); 116 HWC2::Error SetOutputBuffer(buffer_handle_t buffer, int32_t release_fence); 117 HWC2::Error SetPowerMode(int32_t mode); 118 HWC2::Error SetVsyncEnabled(int32_t enabled); 119 HWC2::Error ValidateDisplay(uint32_t *num_types, uint32_t *num_requests); get_layer(hwc2_layer_t layer)120 HwcLayer *get_layer(hwc2_layer_t layer) { 121 auto it = layers_.find(layer); 122 if (it == layers_.end()) 123 return nullptr; 124 return &it->second; 125 } 126 127 /* Statistics */ 128 struct Stats { minusStats129 Stats minus(Stats b) const { 130 return {total_frames_ - b.total_frames_, 131 total_pixops_ - b.total_pixops_, 132 gpu_pixops_ - b.gpu_pixops_, 133 failed_kms_validate_ - b.failed_kms_validate_, 134 failed_kms_present_ - b.failed_kms_present_, 135 frames_flattened_ - b.frames_flattened_}; 136 } 137 138 uint32_t total_frames_ = 0; 139 uint64_t total_pixops_ = 0; 140 uint64_t gpu_pixops_ = 0; 141 uint32_t failed_kms_validate_ = 0; 142 uint32_t failed_kms_present_ = 0; 143 uint32_t frames_flattened_ = 0; 144 }; 145 146 const Backend *backend() const; 147 void set_backend(std::unique_ptr<Backend> backend); 148 GetHwc2()149 auto GetHwc2() { 150 return hwc2_; 151 } 152 layers()153 std::map<hwc2_layer_t, HwcLayer> &layers() { 154 return layers_; 155 } 156 GetPipe()157 auto &GetPipe() { 158 return *pipeline_; 159 } 160 color_transform_hint()161 android_color_transform_t &color_transform_hint() { 162 return color_transform_hint_; 163 } 164 total_stats()165 Stats &total_stats() { 166 return total_stats_; 167 } 168 169 /* returns true if composition should be sent to client */ 170 bool ProcessClientFlatteningState(bool skip); 171 void ProcessFlatenningVsyncInternal(); 172 173 /* Headless mode required to keep SurfaceFlinger alive when all display are 174 * disconnected, Without headless mode Android will continuously crash. 175 * Only single internal (primary) display is required to be in HEADLESS mode 176 * to prevent the crash. See: 177 * https://source.android.com/devices/graphics/hotplug#handling-common-scenarios 178 */ IsInHeadlessMode()179 bool IsInHeadlessMode() { 180 return !pipeline_; 181 } 182 183 private: 184 enum ClientFlattenningState : int32_t { 185 Disabled = -3, 186 NotRequired = -2, 187 Flattened = -1, 188 ClientRefreshRequested = 0, 189 VsyncCountdownMax = 60, /* 1 sec @ 60FPS */ 190 }; 191 192 std::atomic_int flattenning_state_{ClientFlattenningState::NotRequired}; 193 194 constexpr static size_t MATRIX_SIZE = 16; 195 196 HwcDisplayConfigs configs_; 197 198 DrmHwcTwo *const hwc2_; 199 200 std::optional<DrmMode> staged_mode_; 201 int64_t staged_mode_change_time_{}; 202 uint32_t staged_mode_config_id_{}; 203 204 DrmDisplayPipeline *pipeline_{}; 205 206 std::unique_ptr<Backend> backend_; 207 208 VSyncWorker vsync_worker_; 209 bool vsync_event_en_{}; 210 bool vsync_flattening_en_{}; 211 bool vsync_tracking_en_{}; 212 int64_t last_vsync_ts_{}; 213 214 const hwc2_display_t handle_; 215 HWC2::DisplayType type_; 216 217 uint32_t layer_idx_{}; 218 219 std::map<hwc2_layer_t, HwcLayer> layers_; 220 HwcLayer client_layer_; 221 int32_t color_mode_{}; 222 std::array<float, MATRIX_SIZE> color_transform_matrix_{}; 223 android_color_transform_t color_transform_hint_; 224 225 std::shared_ptr<DrmKmsPlan> current_plan_; 226 227 uint32_t frame_no_ = 0; 228 Stats total_stats_; 229 Stats prev_stats_; 230 std::string DumpDelta(HwcDisplay::Stats delta); 231 232 HWC2::Error Init(); 233 234 HWC2::Error SetActiveConfigInternal(uint32_t config, int64_t change_time); 235 }; 236 237 } // namespace android 238 239 #endif 240