OSDN Git Service

Add null ptr checks for callbacks.
[android-x86/external-IA-Hardware-Composer.git] / os / android / iahwc2.cpp
1 /*
2  * Copyright (C) 2016 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 #define ATRACE_TAG ATRACE_TAG_GRAPHICS
18
19 #include "iahwc2.h"
20 #include "utils_android.h"
21
22 #include <inttypes.h>
23
24 #include <cutils/log.h>
25 #include <cutils/properties.h>
26 #include <hardware/hardware.h>
27 #include <hardware/hwcomposer2.h>
28
29 #include <gpudevice.h>
30 #include <hwcdefs.h>
31 #include <nativedisplay.h>
32
33 #include <string>
34 #include <memory>
35 #include <algorithm>
36 #include <vector>
37
38 namespace android {
39
40 class IAVsyncCallback : public hwcomposer::VsyncCallback {
41  public:
42   IAVsyncCallback(hwc2_callback_data_t data, hwc2_function_pointer_t hook)
43       : data_(data), hook_(hook) {
44   }
45
46   void Callback(uint32_t display, int64_t timestamp) {
47     if (hook_ != NULL) {
48       auto hook = reinterpret_cast<HWC2_PFN_VSYNC>(hook_);
49       hook(data_, display, timestamp);
50     }
51   }
52
53  private:
54   hwc2_callback_data_t data_;
55   hwc2_function_pointer_t hook_;
56 };
57
58 class IARefreshCallback : public hwcomposer::RefreshCallback {
59  public:
60   IARefreshCallback(hwc2_callback_data_t data, hwc2_function_pointer_t hook)
61       : data_(data), hook_(hook) {
62   }
63
64   void Callback(uint32_t display) {
65     if (hook_ != NULL) {
66       auto hook = reinterpret_cast<HWC2_PFN_REFRESH>(hook_);
67       hook(data_, display);
68     }
69   }
70
71  private:
72   hwc2_callback_data_t data_;
73   hwc2_function_pointer_t hook_;
74 };
75
76 class IAHotPlugEventCallback : public hwcomposer::HotPlugCallback {
77  public:
78   IAHotPlugEventCallback(hwc2_callback_data_t data,
79                          hwc2_function_pointer_t hook,
80                          IAHWC2::HwcDisplay *display)
81       : data_(data), hook_(hook), display_(display) {
82   }
83
84   void Callback(uint32_t display, bool connected) {
85     if (display == 0) {
86       // SF expects primary display to be always
87       // connected. Let's notify it first time and ignore
88       // any followup status changes.
89       if (notified_) {
90         return;
91       }
92
93       if (connected)
94         notified_ = true;
95     }
96
97     auto hook = reinterpret_cast<HWC2_PFN_HOTPLUG>(hook_);
98     int32_t status = static_cast<int32_t>(HWC2::Connection::Connected);
99     if (!connected) {
100       status = static_cast<int32_t>(HWC2::Connection::Disconnected);
101     }
102
103     IHOTPLUGEVENTTRACE(
104         "IAHotPlugEventCallback called displayid: %d status: %d \n", display,
105         status);
106     if (hook)
107       hook(data_, display, status);
108
109     // FIXME: SurfaceFlinger doesn't seem to reset layers correctly
110     // when display is connected/disconnected. We force it here.
111     // Remove this workaround once fixed correctly in SurfaceFlinger.
112     if (!connected && display > 0) {
113       display_->FreeAllLayers();
114     }
115   }
116
117  private:
118   hwc2_callback_data_t data_;
119   hwc2_function_pointer_t hook_;
120   IAHWC2::HwcDisplay *display_;
121   bool notified_ = false;
122 };
123
124 IAHWC2::IAHWC2() {
125   common.tag = HARDWARE_DEVICE_TAG;
126   common.version = HWC_DEVICE_API_VERSION_2_0;
127   common.close = HookDevClose;
128   getCapabilities = HookDevGetCapabilities;
129   getFunction = HookDevGetFunction;
130 }
131
132 HWC2::Error IAHWC2::Init() {
133   char value[PROPERTY_VALUE_MAX];
134   property_get("board.disable.explicit.sync", value, "0");
135   disable_explicit_sync_ = atoi(value);
136   if (disable_explicit_sync_)
137     ALOGI("EXPLICIT SYNC support is disabled");
138   else
139     ALOGI("EXPLICIT SYNC support is enabled");
140
141   if (!device_.Initialize()) {
142     ALOGE("Can't initialize drm object.");
143     return HWC2::Error::NoResources;
144   }
145
146   std::vector<NativeDisplay *> displays = device_.GetAllDisplays();
147   size_t size = displays.size();
148   NativeDisplay *primary_display = NULL;
149   for (size_t i = 0; i < size; i++) {
150     hwcomposer::NativeDisplay *display = displays.at(i);
151     if (display->IsConnected()) {
152       primary_display = display;
153       break;
154     }
155   }
156
157   if (!primary_display) {
158     primary_display = displays.at(0);
159   }
160
161   primary_display_.Init(primary_display, 0, disable_explicit_sync_);
162
163   uint32_t external_display_id = 1;
164   for (size_t i = 0; i < size; ++i) {
165     hwcomposer::NativeDisplay *display = displays.at(i);
166     if (primary_display == display) {
167       continue;
168     }
169
170     std::unique_ptr<HwcDisplay> temp(new HwcDisplay());
171     temp->Init(display, external_display_id, disable_explicit_sync_);
172     extended_displays_.emplace_back(std::move(temp));
173     external_display_id++;
174   }
175
176   // Start the hwc service
177   // FIXME(IAHWC-76): On Android, with userdebug on Joule this is causing
178   //        to hang in a loop while cold boot before going to home screen
179   // hwcService_.Start(*this);
180
181   return HWC2::Error::None;
182 }
183
184 template <typename... Args>
185 static inline HWC2::Error unsupported(char const *func, Args... /*args*/) {
186   ALOGV("Unsupported function: %s", func);
187   return HWC2::Error::Unsupported;
188 }
189
190 static inline void supported(char const *func) {
191   ALOGV("supported function: %s", func);
192 }
193
194 HWC2::Error IAHWC2::CreateVirtualDisplay(uint32_t width, uint32_t height,
195                                          int32_t *format,
196                                          hwc2_display_t *display) {
197   *display = (hwc2_display_t)HWC_DISPLAY_VIRTUAL;
198   virtual_display_.InitVirtualDisplay(device_.GetVirtualDisplay(), width,
199                                       height, disable_explicit_sync_);
200   if (*format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED) {
201     // fallback to RGBA_8888, align with framework requirement
202     *format = HAL_PIXEL_FORMAT_RGBA_8888;
203   }
204
205   return HWC2::Error::None;
206 }
207
208 HWC2::Error IAHWC2::DestroyVirtualDisplay(hwc2_display_t display) {
209   if (display != (hwc2_display_t)HWC_DISPLAY_VIRTUAL) {
210     ALOGE("Not Virtual Display Type in DestroyVirtualDisplay");
211     return HWC2::Error::BadDisplay;
212   }
213
214   return HWC2::Error::None;
215 }
216
217 void IAHWC2::Dump(uint32_t *size, char *buffer) {
218   // TODO: Implement dump
219   unsupported(__func__, size, buffer);
220 }
221
222 uint32_t IAHWC2::GetMaxVirtualDisplayCount() {
223   return 1;
224 }
225
226 HWC2::Error IAHWC2::RegisterCallback(int32_t descriptor,
227                                      hwc2_callback_data_t data,
228                                      hwc2_function_pointer_t function) {
229   supported(__func__);
230   auto callback = static_cast<HWC2::Callback>(descriptor);
231   size_t size = extended_displays_.size();
232
233   switch (callback) {
234     case HWC2::Callback::Hotplug: {
235       primary_display_.RegisterHotPlugCallback(data, function);
236       for (size_t i = 0; i < size; ++i) {
237         IAHWC2::HwcDisplay *display = extended_displays_.at(i).get();
238         display->RegisterHotPlugCallback(data, function);
239         // TODO: Remove this when we want to add support for more than 2
240         // Displays.
241         break;
242       }
243
244       break;
245     }
246     case HWC2::Callback::Vsync: {
247       primary_display_.RegisterVsyncCallback(data, function);
248       for (size_t i = 0; i < size; ++i) {
249         IAHWC2::HwcDisplay *display = extended_displays_.at(i).get();
250         display->RegisterVsyncCallback(data, function);
251       }
252
253       break;
254     }
255     case HWC2::Callback::Refresh: {
256       primary_display_.RegisterRefreshCallback(data, function);
257       for (size_t i = 0; i < size; ++i) {
258         IAHWC2::HwcDisplay *display = extended_displays_.at(i).get();
259         display->RegisterRefreshCallback(data, function);
260       }
261
262       break;
263     }
264     default:
265       break;
266   }
267   return HWC2::Error::None;
268 }
269
270 IAHWC2::HwcDisplay::HwcDisplay() {
271   supported(__func__);
272 }
273
274 // This function will be called only for Virtual Display Init
275 HWC2::Error IAHWC2::HwcDisplay::InitVirtualDisplay(
276     hwcomposer::NativeDisplay *display, uint32_t width, uint32_t height,
277     bool disable_explicit_sync) {
278   supported(__func__);
279   display_ = display;
280   type_ = HWC2::DisplayType::Virtual;
281   handle_ = HWC_DISPLAY_VIRTUAL;
282   display_->InitVirtualDisplay(width, height);
283   disable_explicit_sync_ = disable_explicit_sync;
284   display_->SetExplicitSyncSupport(disable_explicit_sync_);
285   return HWC2::Error::None;
286 }
287
288 HWC2::Error IAHWC2::HwcDisplay::Init(hwcomposer::NativeDisplay *display,
289                                      int display_index,
290                                      bool disable_explicit_sync) {
291   supported(__func__);
292   display_ = display;
293   type_ = HWC2::DisplayType::Physical;
294   if (display_index == 0) {
295     handle_ = HWC_DISPLAY_PRIMARY;
296   } else {
297     handle_ = HWC_DISPLAY_EXTERNAL;
298   }
299
300   disable_explicit_sync_ = disable_explicit_sync;
301   display_->SetExplicitSyncSupport(disable_explicit_sync_);
302   if (!display_->IsConnected()) {
303     return HWC2::Error::None;
304   }
305   // Fetch the number of modes from the display
306   uint32_t num_configs;
307   HWC2::Error err = GetDisplayConfigs(&num_configs, NULL);
308   if (err != HWC2::Error::None || !num_configs)
309     return err;
310
311   // Grab the first mode, we'll choose this as the active mode
312   hwc2_config_t default_config;
313   num_configs = 1;
314   err = GetDisplayConfigs(&num_configs, &default_config);
315   if (err != HWC2::Error::None)
316     return err;
317
318   return SetActiveConfig(default_config);
319 }
320
321 HWC2::Error IAHWC2::HwcDisplay::RegisterVsyncCallback(
322     hwc2_callback_data_t data, hwc2_function_pointer_t func) {
323   supported(__func__);
324   auto callback = std::make_shared<IAVsyncCallback>(data, func);
325   int ret = display_->RegisterVsyncCallback(std::move(callback),
326                                             static_cast<int>(handle_));
327   if (ret) {
328     ALOGE("Failed to register callback d=%" PRIu64 " ret=%d", handle_, ret);
329     return HWC2::Error::BadDisplay;
330   }
331   return HWC2::Error::None;
332 }
333
334 HWC2::Error IAHWC2::HwcDisplay::RegisterRefreshCallback(
335     hwc2_callback_data_t data, hwc2_function_pointer_t func) {
336   supported(__func__);
337   auto callback = std::make_shared<IARefreshCallback>(data, func);
338   display_->RegisterRefreshCallback(std::move(callback),
339                                     static_cast<int>(handle_));
340   return HWC2::Error::None;
341 }
342
343 HWC2::Error IAHWC2::HwcDisplay::RegisterHotPlugCallback(
344     hwc2_callback_data_t data, hwc2_function_pointer_t func) {
345   supported(__func__);
346   auto callback = std::make_shared<IAHotPlugEventCallback>(data, func, this);
347   display_->RegisterHotPlugCallback(std::move(callback),
348                                     static_cast<int>(handle_));
349   return HWC2::Error::None;
350 }
351
352 HWC2::Error IAHWC2::HwcDisplay::AcceptDisplayChanges() {
353   supported(__func__);
354   if (!checkValidateDisplay) {
355     ALOGV("AcceptChanges failed, not validated");
356     return HWC2::Error::NotValidated;
357   }
358
359   for (std::pair<const hwc2_layer_t, IAHWC2::Hwc2Layer> &l : layers_)
360     l.second.accept_type_change();
361
362   // reset the value to false
363   checkValidateDisplay = false;
364   return HWC2::Error::None;
365 }
366
367 HWC2::Error IAHWC2::HwcDisplay::CreateLayer(hwc2_layer_t *layer) {
368   supported(__func__);
369   layers_.emplace(static_cast<hwc2_layer_t>(layer_idx_), IAHWC2::Hwc2Layer());
370   *layer = static_cast<hwc2_layer_t>(layer_idx_);
371   ++layer_idx_;
372   return HWC2::Error::None;
373 }
374
375 HWC2::Error IAHWC2::HwcDisplay::DestroyLayer(hwc2_layer_t layer) {
376   supported(__func__);
377   if (layers_.empty())
378     return HWC2::Error::None;
379
380   layers_.erase(layer);
381   return HWC2::Error::None;
382 }
383
384 void IAHWC2::HwcDisplay::FreeAllLayers() {
385   if (layers_.empty())
386     return;
387
388   std::map<hwc2_layer_t, Hwc2Layer>().swap(layers_);
389   layer_idx_ = 0;
390 }
391
392 HWC2::Error IAHWC2::HwcDisplay::GetActiveConfig(hwc2_config_t *config) {
393   supported(__func__);
394   IHOTPLUGEVENTTRACE("GetActiveConfig called for Display: %p \n", display_);
395
396   if (!display_->GetActiveConfig(config))
397     return HWC2::Error::BadConfig;
398
399   return HWC2::Error::None;
400 }
401
402 HWC2::Error IAHWC2::HwcDisplay::GetChangedCompositionTypes(
403     uint32_t *num_elements, hwc2_layer_t *layers, int32_t *types) {
404   supported(__func__);
405   uint32_t num_changes = 0;
406   for (std::pair<const hwc2_layer_t, IAHWC2::Hwc2Layer> &l : layers_) {
407     if (l.second.type_changed()) {
408       if (layers && num_changes < *num_elements)
409         layers[num_changes] = l.first;
410       if (types && num_changes < *num_elements)
411         types[num_changes] = static_cast<int32_t>(l.second.validated_type());
412       ++num_changes;
413     }
414   }
415   if (!layers && !types)
416     *num_elements = num_changes;
417   return HWC2::Error::None;
418 }
419
420 HWC2::Error IAHWC2::HwcDisplay::GetClientTargetSupport(uint32_t width,
421                                                        uint32_t height,
422                                                        int32_t format,
423                                                        int32_t dataspace) {
424   if (width != display_->Width() || height != display_->Height()) {
425     return HWC2::Error::Unsupported;
426   }
427
428   if (format == HAL_PIXEL_FORMAT_RGBA_8888 &&
429       (dataspace == HAL_DATASPACE_UNKNOWN ||
430        dataspace == HAL_DATASPACE_STANDARD_UNSPECIFIED)) {
431     return HWC2::Error::None;
432   } else {
433     // Convert HAL to fourcc-based DRM formats
434     uint32_t drm_format = GetDrmFormatFromHALFormat(format);
435     if (display_->CheckPlaneFormat(drm_format) &&
436         (dataspace == HAL_DATASPACE_UNKNOWN ||
437          dataspace == HAL_DATASPACE_STANDARD_UNSPECIFIED))
438       return HWC2::Error::None;
439   }
440
441   return HWC2::Error::Unsupported;
442 }
443
444 HWC2::Error IAHWC2::HwcDisplay::GetColorModes(uint32_t *num_modes,
445                                               int32_t *modes) {
446   supported(__func__);
447   if (!modes)
448     *num_modes = 1;
449 #ifndef DISABLE_NATIVE_COLOR_MODES
450   if (modes)
451     *modes = HAL_COLOR_MODE_NATIVE;
452 #endif
453
454   return HWC2::Error::None;
455 }
456
457 HWC2::Error IAHWC2::HwcDisplay::GetDisplayAttribute(hwc2_config_t config,
458                                                     int32_t attribute_in,
459                                                     int32_t *value) {
460   supported(__func__);
461   auto attribute = static_cast<HWC2::Attribute>(attribute_in);
462   switch (attribute) {
463     case HWC2::Attribute::Width:
464       display_->GetDisplayAttribute(
465           config, hwcomposer::HWCDisplayAttribute::kWidth, value);
466       break;
467     case HWC2::Attribute::Height:
468       display_->GetDisplayAttribute(
469           config, hwcomposer::HWCDisplayAttribute::kHeight, value);
470       break;
471     case HWC2::Attribute::VsyncPeriod:
472       // in nanoseconds
473       display_->GetDisplayAttribute(
474           config, hwcomposer::HWCDisplayAttribute::kRefreshRate, value);
475       break;
476     case HWC2::Attribute::DpiX:
477       // Dots per 1000 inches
478       display_->GetDisplayAttribute(
479           config, hwcomposer::HWCDisplayAttribute::kDpiX, value);
480       break;
481     case HWC2::Attribute::DpiY:
482       // Dots per 1000 inches
483       display_->GetDisplayAttribute(
484           config, hwcomposer::HWCDisplayAttribute::kDpiY, value);
485       break;
486     default:
487       *value = -1;
488       return HWC2::Error::BadConfig;
489   }
490   return HWC2::Error::None;
491 }
492
493 HWC2::Error IAHWC2::HwcDisplay::GetDisplayConfigs(uint32_t *num_configs,
494                                                   hwc2_config_t *configs) {
495   supported(__func__);
496   if (!display_->GetDisplayConfigs(num_configs, configs))
497     return HWC2::Error::BadDisplay;
498
499   return HWC2::Error::None;
500 }
501
502 HWC2::Error IAHWC2::HwcDisplay::GetDisplayName(uint32_t *size, char *name) {
503   supported(__func__);
504   if (!display_->GetDisplayName(size, name))
505     return HWC2::Error::BadDisplay;
506
507   return HWC2::Error::None;
508 }
509
510 HWC2::Error IAHWC2::HwcDisplay::GetDisplayRequests(int32_t *display_requests,
511                                                    uint32_t *num_elements,
512                                                    hwc2_layer_t *layers,
513                                                    int32_t *layer_requests) {
514   supported(__func__);
515   // TODO: I think virtual display should request
516   //      HWC2_DISPLAY_REQUEST_WRITE_CLIENT_TARGET_TO_OUTPUT here
517   unsupported(__func__, display_requests, num_elements, layers, layer_requests);
518   *num_elements = 0;
519   return HWC2::Error::None;
520 }
521
522 HWC2::Error IAHWC2::HwcDisplay::GetDisplayType(int32_t *type) {
523   supported(__func__);
524   *type = static_cast<int32_t>(type_);
525   return HWC2::Error::None;
526 }
527
528 HWC2::Error IAHWC2::HwcDisplay::GetDozeSupport(int32_t *support) {
529   supported(__func__);
530   *support = true;
531   return HWC2::Error::None;
532 }
533
534 HWC2::Error IAHWC2::HwcDisplay::GetHdrCapabilities(
535     uint32_t *num_types, int32_t * /*types*/, float * /*max_luminance*/,
536     float * /*max_average_luminance*/, float * /*min_luminance*/) {
537   supported(__func__);
538   *num_types = 0;
539   return HWC2::Error::None;
540 }
541
542 HWC2::Error IAHWC2::HwcDisplay::GetReleaseFences(uint32_t *num_elements,
543                                                  hwc2_layer_t *layers,
544                                                  int32_t *fences) {
545   supported(__func__);
546   if (layers == NULL || fences == NULL) {
547     *num_elements = layers_.size();
548     return HWC2::Error::None;
549   }
550
551   uint32_t num_layers = 0;
552   for (std::pair<const hwc2_layer_t, IAHWC2::Hwc2Layer> &l : layers_) {
553     ++num_layers;
554     if (num_layers > *num_elements) {
555       ALOGW("Overflow num_elements %d/%d", num_layers, *num_elements);
556       return HWC2::Error::None;
557     }
558
559     layers[num_layers - 1] = l.first;
560     fences[num_layers - 1] = l.second.GetLayer()->GetReleaseFence();
561   }
562
563   *num_elements = num_layers;
564   return HWC2::Error::None;
565 }
566
567 HWC2::Error IAHWC2::HwcDisplay::PresentDisplay(int32_t *retire_fence) {
568   supported(__func__);
569   // order the layers by z-order
570   bool use_client_layer = false;
571   uint32_t client_z_order = 0;
572   bool use_cursor_layer = false;
573   uint32_t cursor_z_order = 0;
574   IAHWC2::Hwc2Layer *cursor_layer;
575   *retire_fence = -1;
576   std::map<uint32_t, IAHWC2::Hwc2Layer *> z_map;
577
578   // if the power mode is doze suspend then its the hint that the drawing
579   // into the display has suspended and remain in the low power state and
580   // continue displaying the current state and stop applying display
581   // update from the client
582   if (display_->PowerMode() == HWC2_POWER_MODE_DOZE_SUSPEND)
583     return HWC2::Error::None;
584   for (std::pair<const hwc2_layer_t, IAHWC2::Hwc2Layer> &l : layers_) {
585     if (l.second.IsCursorLayer()) {
586       use_cursor_layer = true;
587       cursor_layer = &l.second;
588       cursor_z_order = l.second.z_order();
589       continue;
590     }
591
592     switch (l.second.validated_type()) {
593       case HWC2::Composition::Device:
594         z_map.emplace(std::make_pair(l.second.z_order(), &l.second));
595         break;
596       case HWC2::Composition::Client:
597         // Place it at the z_order of the highest client layer
598         use_client_layer = true;
599         client_z_order = std::max(client_z_order, l.second.z_order());
600         break;
601       default:
602         continue;
603     }
604   }
605   if (use_client_layer && client_layer_.GetLayer() &&
606       client_layer_.GetLayer()->GetNativeHandle() &&
607       client_layer_.GetLayer()->GetNativeHandle()->handle_) {
608     z_map.emplace(std::make_pair(client_z_order, &client_layer_));
609   }
610
611   // Place the cursor at the highest z-order
612   if (use_cursor_layer) {
613     if (z_map.size()) {
614       if (z_map.rbegin()->second->z_order() > cursor_z_order)
615         cursor_z_order = (z_map.rbegin()->second->z_order()) + 1;
616     }
617     z_map.emplace(std::make_pair(cursor_z_order, cursor_layer));
618   }
619
620   std::vector<hwcomposer::HwcLayer *> layers;
621   // now that they're ordered by z, add them to the composition
622   for (std::pair<const uint32_t, IAHWC2::Hwc2Layer *> &l : z_map) {
623     layers.emplace_back(l.second->GetLayer());
624   }
625
626   if (layers.empty())
627     return HWC2::Error::None;
628
629   IHOTPLUGEVENTTRACE("PhysicalDisplay called for Display: %p \n", display_);
630
631   bool success = display_->Present(layers, retire_fence);
632   if (!success) {
633     ALOGE("Failed to set layers in the composition");
634     return HWC2::Error::BadLayer;
635   }
636
637   ++frame_no_;
638
639   return HWC2::Error::None;
640 }
641
642 HWC2::Error IAHWC2::HwcDisplay::SetActiveConfig(hwc2_config_t config) {
643   supported(__func__);
644   if (!display_->SetActiveConfig(config)) {
645     ALOGE("Could not find active mode for %d", config);
646     return HWC2::Error::BadConfig;
647   }
648
649   // Setup the client layer's dimensions
650   hwc_rect_t display_frame = {.left = 0,
651                               .top = 0,
652                               .right = static_cast<int>(display_->Width()),
653                               .bottom = static_cast<int>(display_->Height())};
654   client_layer_.SetLayerDisplayFrame(display_frame);
655   hwc_frect_t source_crop = {.left = 0.0f,
656                              .top = 0.0f,
657                              .right = display_->Width() + 0.0f,
658                              .bottom = display_->Height() + 0.0f};
659   client_layer_.SetLayerSourceCrop(source_crop);
660
661   return HWC2::Error::None;
662 }
663
664 HWC2::Error IAHWC2::HwcDisplay::SetClientTarget(buffer_handle_t target,
665                                                 int32_t acquire_fence,
666                                                 int32_t dataspace,
667                                                 hwc_region_t damage) {
668   supported(__func__);
669   client_layer_.set_buffer(target);
670   client_layer_.set_acquire_fence(acquire_fence);
671   client_layer_.SetLayerDataspace(dataspace);
672   client_layer_.SetLayerSurfaceDamage(damage);
673
674   return HWC2::Error::None;
675 }
676
677 HWC2::Error IAHWC2::HwcDisplay::SetColorMode(int32_t mode) {
678   supported(__func__);
679   color_mode_ = mode;
680   return HWC2::Error::None;
681 }
682
683 HWC2::Error IAHWC2::HwcDisplay::SetColorTransform(const float *matrix,
684                                                   int32_t hint) {
685   supported(__func__);
686   // TODO: Force client composition if we get this
687   return unsupported(__func__, matrix, hint);
688 }
689
690 HWC2::Error IAHWC2::HwcDisplay::SetOutputBuffer(buffer_handle_t buffer,
691                                                 int32_t release_fence) {
692   supported(__func__);
693
694   struct gralloc_handle *temp = new struct gralloc_handle();
695   temp->handle_ = buffer;
696   display_->SetOutputBuffer(temp, release_fence);
697   return HWC2::Error::None;
698 }
699
700 HWC2::Error IAHWC2::HwcDisplay::SetPowerMode(int32_t mode_in) {
701   supported(__func__);
702   uint32_t power_mode = 0;
703   auto mode = static_cast<HWC2::PowerMode>(mode_in);
704   switch (mode) {
705     case HWC2::PowerMode::Off:
706       power_mode = HWC2_POWER_MODE_OFF;
707       break;
708     case HWC2::PowerMode::Doze:
709       power_mode = HWC2_POWER_MODE_DOZE;
710       break;
711     case HWC2::PowerMode::DozeSuspend:
712       power_mode = HWC2_POWER_MODE_DOZE_SUSPEND;
713       break;
714     case HWC2::PowerMode::On:
715       power_mode = HWC2_POWER_MODE_ON;
716       break;
717     default:
718       ALOGI("Power mode %d is unsupported\n", mode);
719       return HWC2::Error::BadParameter;
720   };
721
722   display_->SetPowerMode(power_mode);
723
724   return HWC2::Error::None;
725 }
726
727 HWC2::Error IAHWC2::HwcDisplay::SetVsyncEnabled(int32_t enabled) {
728   supported(__func__);
729   display_->VSyncControl(enabled);
730   return HWC2::Error::None;
731 }
732
733 HWC2::Error IAHWC2::HwcDisplay::ValidateDisplay(uint32_t *num_types,
734                                                 uint32_t *num_requests) {
735   supported(__func__);
736   *num_types = 0;
737   *num_requests = 0;
738   for (std::pair<const hwc2_layer_t, IAHWC2::Hwc2Layer> &l : layers_) {
739     IAHWC2::Hwc2Layer &layer = l.second;
740     switch (layer.sf_type()) {
741       case HWC2::Composition::Sideband:
742         layer.set_validated_type(HWC2::Composition::Client);
743         ++*num_types;
744         break;
745       case HWC2::Composition::Cursor:
746         layer.set_validated_type(HWC2::Composition::Device);
747         ++*num_types;
748         break;
749       default:
750         if (disable_explicit_sync_ ||
751             display_->PowerMode() == HWC2_POWER_MODE_DOZE_SUSPEND) {
752           layer.set_validated_type(HWC2::Composition::Client);
753         } else {
754           layer.set_validated_type(layer.sf_type());
755         }
756         break;
757     }
758   }
759
760   checkValidateDisplay = true;
761   return HWC2::Error::None;
762 }
763
764 HWC2::Error IAHWC2::Hwc2Layer::SetCursorPosition(int32_t /*x*/, int32_t /*y*/) {
765   supported(__func__);
766   return HWC2::Error::None;
767 }
768
769 HWC2::Error IAHWC2::Hwc2Layer::SetLayerBlendMode(int32_t mode) {
770   supported(__func__);
771   switch (static_cast<HWC2::BlendMode>(mode)) {
772     case HWC2::BlendMode::None:
773       hwc_layer_.SetBlending(hwcomposer::HWCBlending::kBlendingNone);
774       break;
775     case HWC2::BlendMode::Premultiplied:
776       hwc_layer_.SetBlending(hwcomposer::HWCBlending::kBlendingPremult);
777       break;
778     case HWC2::BlendMode::Coverage:
779       hwc_layer_.SetBlending(hwcomposer::HWCBlending::kBlendingCoverage);
780       break;
781     default:
782       ALOGE("Unknown blending mode b=%d", mode);
783       hwc_layer_.SetBlending(hwcomposer::HWCBlending::kBlendingNone);
784       break;
785   }
786   return HWC2::Error::None;
787 }
788
789 HWC2::Error IAHWC2::Hwc2Layer::SetLayerBuffer(buffer_handle_t buffer,
790                                               int32_t acquire_fence) {
791   supported(__func__);
792
793   // The buffer and acquire_fence are handled elsewhere
794   if (sf_type_ == HWC2::Composition::Client ||
795       sf_type_ == HWC2::Composition::Sideband)
796     return HWC2::Error::None;
797
798   native_handle_.handle_ = buffer;
799   hwc_layer_.SetNativeHandle(&native_handle_);
800   if (acquire_fence > 0)
801     hwc_layer_.SetAcquireFence(acquire_fence);
802   return HWC2::Error::None;
803 }
804
805 HWC2::Error IAHWC2::Hwc2Layer::SetLayerColor(hwc_color_t color) {
806   // We only support Opaque colors so far.
807   if (color.r == 0 && color.g == 0 && color.b == 0 && color.a == 255) {
808     sf_type_ = HWC2::Composition::SolidColor;
809     return HWC2::Error::None;
810   }
811
812   sf_type_ = HWC2::Composition::Client;
813   return HWC2::Error::None;
814 }
815
816 HWC2::Error IAHWC2::Hwc2Layer::SetLayerCompositionType(int32_t type) {
817   sf_type_ = static_cast<HWC2::Composition>(type);
818   if (sf_type_ == HWC2::Composition::Cursor) {
819     is_cursor_layer_ = true;
820   }
821
822   return HWC2::Error::None;
823 }
824
825 HWC2::Error IAHWC2::Hwc2Layer::SetLayerDataspace(int32_t dataspace) {
826   supported(__func__);
827   dataspace_ = static_cast<android_dataspace_t>(dataspace);
828   return HWC2::Error::None;
829 }
830
831 HWC2::Error IAHWC2::Hwc2Layer::SetLayerDisplayFrame(hwc_rect_t frame) {
832   supported(__func__);
833   hwc_layer_.SetDisplayFrame(hwcomposer::HwcRect<int>(
834       frame.left, frame.top, frame.right, frame.bottom));
835   return HWC2::Error::None;
836 }
837
838 HWC2::Error IAHWC2::Hwc2Layer::SetLayerPlaneAlpha(float alpha) {
839   supported(__func__);
840   hwc_layer_.SetAlpha(static_cast<uint8_t>(255.0f * alpha + 0.5f));
841   return HWC2::Error::None;
842 }
843
844 HWC2::Error IAHWC2::Hwc2Layer::SetLayerSidebandStream(
845     const native_handle_t *stream) {
846   supported(__func__);
847   // TODO: We don't support sideband
848   return unsupported(__func__, stream);
849 }
850
851 HWC2::Error IAHWC2::Hwc2Layer::SetLayerSourceCrop(hwc_frect_t crop) {
852   supported(__func__);
853   hwc_layer_.SetSourceCrop(
854       hwcomposer::HwcRect<float>(crop.left, crop.top, crop.right, crop.bottom));
855   return HWC2::Error::None;
856 }
857
858 HWC2::Error IAHWC2::Hwc2Layer::SetLayerSurfaceDamage(hwc_region_t damage) {
859   uint32_t num_rects = damage.numRects;
860   hwcomposer::HwcRegion hwc_region;
861
862   for (size_t rect = 0; rect < num_rects; ++rect) {
863     hwc_region.emplace_back(damage.rects[rect].left, damage.rects[rect].top,
864                             damage.rects[rect].right,
865                             damage.rects[rect].bottom);
866   }
867
868   hwc_layer_.SetSurfaceDamage(hwc_region);
869
870   return HWC2::Error::None;
871 }
872
873 HWC2::Error IAHWC2::Hwc2Layer::SetLayerTransform(int32_t transform) {
874   supported(__func__);
875   // 270* and 180* cannot be combined with flips. More specifically, they
876   // already contain both horizontal and vertical flips, so those fields are
877   // redundant in this case. 90* rotation can be combined with either horizontal
878   // flip or vertical flip, so treat it differently
879   if (transform == HWC_TRANSFORM_ROT_270) {
880     transform = hwcomposer::HWCTransform::kRotate270;
881   } else if (transform == HWC_TRANSFORM_ROT_180) {
882     transform = hwcomposer::HWCTransform::kRotate180;
883   } else {
884     if (transform & HWC_TRANSFORM_FLIP_H)
885       transform |= hwcomposer::HWCTransform::kReflectX;
886     if (transform & HWC_TRANSFORM_FLIP_V)
887       transform |= hwcomposer::HWCTransform::kReflectY;
888     if (transform & HWC_TRANSFORM_ROT_90)
889       transform |= hwcomposer::HWCTransform::kRotate90;
890   }
891   hwc_layer_.SetTransform(transform);
892   return HWC2::Error::None;
893 }
894
895 HWC2::Error IAHWC2::Hwc2Layer::SetLayerVisibleRegion(hwc_region_t visible) {
896   uint32_t num_rects = visible.numRects;
897   hwcomposer::HwcRegion hwc_region;
898
899   for (size_t rect = 0; rect < num_rects; ++rect) {
900     hwc_region.emplace_back(visible.rects[rect].left, visible.rects[rect].top,
901                             visible.rects[rect].right,
902                             visible.rects[rect].bottom);
903   }
904
905   hwc_layer_.SetVisibleRegion(hwc_region);
906   return HWC2::Error::None;
907 }
908
909 HWC2::Error IAHWC2::Hwc2Layer::SetLayerZOrder(uint32_t order) {
910   supported(__func__);
911
912   hwc_layer_.SetLayerZOrder(order);
913   return HWC2::Error::None;
914 }
915
916 // static
917 int IAHWC2::HookDevClose(hw_device_t * /*dev*/) {
918   unsupported(__func__);
919   return 0;
920 }
921
922 // static
923 void IAHWC2::HookDevGetCapabilities(hwc2_device_t * /*dev*/,
924                                     uint32_t *out_count,
925                                     int32_t * /*out_capabilities*/) {
926   supported(__func__);
927   *out_count = 0;
928 }
929
930 // static
931 hwc2_function_pointer_t IAHWC2::HookDevGetFunction(struct hwc2_device * /*dev*/,
932                                                    int32_t descriptor) {
933   supported(__func__);
934   auto func = static_cast<HWC2::FunctionDescriptor>(descriptor);
935   switch (func) {
936     // Device functions
937     case HWC2::FunctionDescriptor::CreateVirtualDisplay:
938       return ToHook<HWC2_PFN_CREATE_VIRTUAL_DISPLAY>(
939           DeviceHook<int32_t, decltype(&IAHWC2::CreateVirtualDisplay),
940                      &IAHWC2::CreateVirtualDisplay, uint32_t, uint32_t,
941                      int32_t *, hwc2_display_t *>);
942     case HWC2::FunctionDescriptor::DestroyVirtualDisplay:
943       return ToHook<HWC2_PFN_DESTROY_VIRTUAL_DISPLAY>(
944           DeviceHook<int32_t, decltype(&IAHWC2::DestroyVirtualDisplay),
945                      &IAHWC2::DestroyVirtualDisplay, hwc2_display_t>);
946     case HWC2::FunctionDescriptor::Dump:
947       return ToHook<HWC2_PFN_DUMP>(DeviceHook<
948           void, decltype(&IAHWC2::Dump), &IAHWC2::Dump, uint32_t *, char *>);
949     case HWC2::FunctionDescriptor::GetMaxVirtualDisplayCount:
950       return ToHook<HWC2_PFN_GET_MAX_VIRTUAL_DISPLAY_COUNT>(
951           DeviceHook<uint32_t, decltype(&IAHWC2::GetMaxVirtualDisplayCount),
952                      &IAHWC2::GetMaxVirtualDisplayCount>);
953     case HWC2::FunctionDescriptor::RegisterCallback:
954       return ToHook<HWC2_PFN_REGISTER_CALLBACK>(
955           DeviceHook<int32_t, decltype(&IAHWC2::RegisterCallback),
956                      &IAHWC2::RegisterCallback, int32_t, hwc2_callback_data_t,
957                      hwc2_function_pointer_t>);
958
959     // Display functions
960     case HWC2::FunctionDescriptor::AcceptDisplayChanges:
961       return ToHook<HWC2_PFN_ACCEPT_DISPLAY_CHANGES>(
962           DisplayHook<decltype(&HwcDisplay::AcceptDisplayChanges),
963                       &HwcDisplay::AcceptDisplayChanges>);
964     case HWC2::FunctionDescriptor::CreateLayer:
965       return ToHook<HWC2_PFN_CREATE_LAYER>(
966           DisplayHook<decltype(&HwcDisplay::CreateLayer),
967                       &HwcDisplay::CreateLayer, hwc2_layer_t *>);
968     case HWC2::FunctionDescriptor::DestroyLayer:
969       return ToHook<HWC2_PFN_DESTROY_LAYER>(
970           DisplayHook<decltype(&HwcDisplay::DestroyLayer),
971                       &HwcDisplay::DestroyLayer, hwc2_layer_t>);
972     case HWC2::FunctionDescriptor::GetActiveConfig:
973       return ToHook<HWC2_PFN_GET_ACTIVE_CONFIG>(
974           DisplayHook<decltype(&HwcDisplay::GetActiveConfig),
975                       &HwcDisplay::GetActiveConfig, hwc2_config_t *>);
976     case HWC2::FunctionDescriptor::GetChangedCompositionTypes:
977       return ToHook<HWC2_PFN_GET_CHANGED_COMPOSITION_TYPES>(
978           DisplayHook<decltype(&HwcDisplay::GetChangedCompositionTypes),
979                       &HwcDisplay::GetChangedCompositionTypes, uint32_t *,
980                       hwc2_layer_t *, int32_t *>);
981     case HWC2::FunctionDescriptor::GetClientTargetSupport:
982       return ToHook<HWC2_PFN_GET_CLIENT_TARGET_SUPPORT>(
983           DisplayHook<decltype(&HwcDisplay::GetClientTargetSupport),
984                       &HwcDisplay::GetClientTargetSupport, uint32_t, uint32_t,
985                       int32_t, int32_t>);
986     case HWC2::FunctionDescriptor::GetColorModes:
987       return ToHook<HWC2_PFN_GET_COLOR_MODES>(
988           DisplayHook<decltype(&HwcDisplay::GetColorModes),
989                       &HwcDisplay::GetColorModes, uint32_t *, int32_t *>);
990     case HWC2::FunctionDescriptor::GetDisplayAttribute:
991       return ToHook<HWC2_PFN_GET_DISPLAY_ATTRIBUTE>(DisplayHook<
992           decltype(&HwcDisplay::GetDisplayAttribute),
993           &HwcDisplay::GetDisplayAttribute, hwc2_config_t, int32_t, int32_t *>);
994     case HWC2::FunctionDescriptor::GetDisplayConfigs:
995       return ToHook<HWC2_PFN_GET_DISPLAY_CONFIGS>(DisplayHook<
996           decltype(&HwcDisplay::GetDisplayConfigs),
997           &HwcDisplay::GetDisplayConfigs, uint32_t *, hwc2_config_t *>);
998     case HWC2::FunctionDescriptor::GetDisplayName:
999       return ToHook<HWC2_PFN_GET_DISPLAY_NAME>(
1000           DisplayHook<decltype(&HwcDisplay::GetDisplayName),
1001                       &HwcDisplay::GetDisplayName, uint32_t *, char *>);
1002     case HWC2::FunctionDescriptor::GetDisplayRequests:
1003       return ToHook<HWC2_PFN_GET_DISPLAY_REQUESTS>(
1004           DisplayHook<decltype(&HwcDisplay::GetDisplayRequests),
1005                       &HwcDisplay::GetDisplayRequests, int32_t *, uint32_t *,
1006                       hwc2_layer_t *, int32_t *>);
1007     case HWC2::FunctionDescriptor::GetDisplayType:
1008       return ToHook<HWC2_PFN_GET_DISPLAY_TYPE>(
1009           DisplayHook<decltype(&HwcDisplay::GetDisplayType),
1010                       &HwcDisplay::GetDisplayType, int32_t *>);
1011     case HWC2::FunctionDescriptor::GetDozeSupport:
1012       return ToHook<HWC2_PFN_GET_DOZE_SUPPORT>(
1013           DisplayHook<decltype(&HwcDisplay::GetDozeSupport),
1014                       &HwcDisplay::GetDozeSupport, int32_t *>);
1015     case HWC2::FunctionDescriptor::GetHdrCapabilities:
1016       return ToHook<HWC2_PFN_GET_HDR_CAPABILITIES>(
1017           DisplayHook<decltype(&HwcDisplay::GetHdrCapabilities),
1018                       &HwcDisplay::GetHdrCapabilities, uint32_t *, int32_t *,
1019                       float *, float *, float *>);
1020     case HWC2::FunctionDescriptor::GetReleaseFences:
1021       return ToHook<HWC2_PFN_GET_RELEASE_FENCES>(
1022           DisplayHook<decltype(&HwcDisplay::GetReleaseFences),
1023                       &HwcDisplay::GetReleaseFences, uint32_t *, hwc2_layer_t *,
1024                       int32_t *>);
1025     case HWC2::FunctionDescriptor::PresentDisplay:
1026       return ToHook<HWC2_PFN_PRESENT_DISPLAY>(
1027           DisplayHook<decltype(&HwcDisplay::PresentDisplay),
1028                       &HwcDisplay::PresentDisplay, int32_t *>);
1029     case HWC2::FunctionDescriptor::SetActiveConfig:
1030       return ToHook<HWC2_PFN_SET_ACTIVE_CONFIG>(
1031           DisplayHook<decltype(&HwcDisplay::SetActiveConfig),
1032                       &HwcDisplay::SetActiveConfig, hwc2_config_t>);
1033     case HWC2::FunctionDescriptor::SetClientTarget:
1034       return ToHook<HWC2_PFN_SET_CLIENT_TARGET>(DisplayHook<
1035           decltype(&HwcDisplay::SetClientTarget), &HwcDisplay::SetClientTarget,
1036           buffer_handle_t, int32_t, int32_t, hwc_region_t>);
1037     case HWC2::FunctionDescriptor::SetColorMode:
1038       return ToHook<HWC2_PFN_SET_COLOR_MODE>(
1039           DisplayHook<decltype(&HwcDisplay::SetColorMode),
1040                       &HwcDisplay::SetColorMode, int32_t>);
1041     case HWC2::FunctionDescriptor::SetColorTransform:
1042       return ToHook<HWC2_PFN_SET_COLOR_TRANSFORM>(
1043           DisplayHook<decltype(&HwcDisplay::SetColorTransform),
1044                       &HwcDisplay::SetColorTransform, const float *, int32_t>);
1045     case HWC2::FunctionDescriptor::SetOutputBuffer:
1046       return ToHook<HWC2_PFN_SET_OUTPUT_BUFFER>(
1047           DisplayHook<decltype(&HwcDisplay::SetOutputBuffer),
1048                       &HwcDisplay::SetOutputBuffer, buffer_handle_t, int32_t>);
1049     case HWC2::FunctionDescriptor::SetPowerMode:
1050       return ToHook<HWC2_PFN_SET_POWER_MODE>(
1051           DisplayHook<decltype(&HwcDisplay::SetPowerMode),
1052                       &HwcDisplay::SetPowerMode, int32_t>);
1053     case HWC2::FunctionDescriptor::SetVsyncEnabled:
1054       return ToHook<HWC2_PFN_SET_VSYNC_ENABLED>(
1055           DisplayHook<decltype(&HwcDisplay::SetVsyncEnabled),
1056                       &HwcDisplay::SetVsyncEnabled, int32_t>);
1057     case HWC2::FunctionDescriptor::ValidateDisplay:
1058       return ToHook<HWC2_PFN_VALIDATE_DISPLAY>(
1059           DisplayHook<decltype(&HwcDisplay::ValidateDisplay),
1060                       &HwcDisplay::ValidateDisplay, uint32_t *, uint32_t *>);
1061
1062     // Layer functions
1063     case HWC2::FunctionDescriptor::SetCursorPosition:
1064       return ToHook<HWC2_PFN_SET_CURSOR_POSITION>(
1065           LayerHook<decltype(&Hwc2Layer::SetCursorPosition),
1066                     &Hwc2Layer::SetCursorPosition, int32_t, int32_t>);
1067     case HWC2::FunctionDescriptor::SetLayerBlendMode:
1068       return ToHook<HWC2_PFN_SET_LAYER_BLEND_MODE>(
1069           LayerHook<decltype(&Hwc2Layer::SetLayerBlendMode),
1070                     &Hwc2Layer::SetLayerBlendMode, int32_t>);
1071     case HWC2::FunctionDescriptor::SetLayerBuffer:
1072       return ToHook<HWC2_PFN_SET_LAYER_BUFFER>(
1073           LayerHook<decltype(&Hwc2Layer::SetLayerBuffer),
1074                     &Hwc2Layer::SetLayerBuffer, buffer_handle_t, int32_t>);
1075     case HWC2::FunctionDescriptor::SetLayerColor:
1076       return ToHook<HWC2_PFN_SET_LAYER_COLOR>(
1077           LayerHook<decltype(&Hwc2Layer::SetLayerColor),
1078                     &Hwc2Layer::SetLayerColor, hwc_color_t>);
1079     case HWC2::FunctionDescriptor::SetLayerCompositionType:
1080       return ToHook<HWC2_PFN_SET_LAYER_COMPOSITION_TYPE>(
1081           LayerHook<decltype(&Hwc2Layer::SetLayerCompositionType),
1082                     &Hwc2Layer::SetLayerCompositionType, int32_t>);
1083     case HWC2::FunctionDescriptor::SetLayerDataspace:
1084       return ToHook<HWC2_PFN_SET_LAYER_DATASPACE>(
1085           LayerHook<decltype(&Hwc2Layer::SetLayerDataspace),
1086                     &Hwc2Layer::SetLayerDataspace, int32_t>);
1087     case HWC2::FunctionDescriptor::SetLayerDisplayFrame:
1088       return ToHook<HWC2_PFN_SET_LAYER_DISPLAY_FRAME>(
1089           LayerHook<decltype(&Hwc2Layer::SetLayerDisplayFrame),
1090                     &Hwc2Layer::SetLayerDisplayFrame, hwc_rect_t>);
1091     case HWC2::FunctionDescriptor::SetLayerPlaneAlpha:
1092       return ToHook<HWC2_PFN_SET_LAYER_PLANE_ALPHA>(
1093           LayerHook<decltype(&Hwc2Layer::SetLayerPlaneAlpha),
1094                     &Hwc2Layer::SetLayerPlaneAlpha, float>);
1095     case HWC2::FunctionDescriptor::SetLayerSidebandStream:
1096       return ToHook<HWC2_PFN_SET_LAYER_SIDEBAND_STREAM>(LayerHook<
1097           decltype(&Hwc2Layer::SetLayerSidebandStream),
1098           &Hwc2Layer::SetLayerSidebandStream, const native_handle_t *>);
1099     case HWC2::FunctionDescriptor::SetLayerSourceCrop:
1100       return ToHook<HWC2_PFN_SET_LAYER_SOURCE_CROP>(
1101           LayerHook<decltype(&Hwc2Layer::SetLayerSourceCrop),
1102                     &Hwc2Layer::SetLayerSourceCrop, hwc_frect_t>);
1103     case HWC2::FunctionDescriptor::SetLayerSurfaceDamage:
1104       return ToHook<HWC2_PFN_SET_LAYER_SURFACE_DAMAGE>(
1105           LayerHook<decltype(&Hwc2Layer::SetLayerSurfaceDamage),
1106                     &Hwc2Layer::SetLayerSurfaceDamage, hwc_region_t>);
1107     case HWC2::FunctionDescriptor::SetLayerTransform:
1108       return ToHook<HWC2_PFN_SET_LAYER_TRANSFORM>(
1109           LayerHook<decltype(&Hwc2Layer::SetLayerTransform),
1110                     &Hwc2Layer::SetLayerTransform, int32_t>);
1111     case HWC2::FunctionDescriptor::SetLayerVisibleRegion:
1112       return ToHook<HWC2_PFN_SET_LAYER_VISIBLE_REGION>(
1113           LayerHook<decltype(&Hwc2Layer::SetLayerVisibleRegion),
1114                     &Hwc2Layer::SetLayerVisibleRegion, hwc_region_t>);
1115     case HWC2::FunctionDescriptor::SetLayerZOrder:
1116       return ToHook<HWC2_PFN_SET_LAYER_Z_ORDER>(
1117           LayerHook<decltype(&Hwc2Layer::SetLayerZOrder),
1118                     &Hwc2Layer::SetLayerZOrder, uint32_t>);
1119     case HWC2::FunctionDescriptor::Invalid:
1120     default:
1121       return NULL;
1122   }
1123 }
1124
1125 // static
1126 int IAHWC2::HookDevOpen(const struct hw_module_t *module, const char *name,
1127                         struct hw_device_t **dev) {
1128   supported(__func__);
1129   if (strcmp(name, HWC_HARDWARE_COMPOSER)) {
1130     ALOGE("Invalid module name- %s", name);
1131     return -EINVAL;
1132   }
1133
1134   std::unique_ptr<IAHWC2> ctx(new IAHWC2());
1135   if (!ctx) {
1136     ALOGE("Failed to allocate IAHWC2");
1137     return -ENOMEM;
1138   }
1139
1140   HWC2::Error err = ctx->Init();
1141   if (err != HWC2::Error::None) {
1142     ALOGE("Failed to initialize IAHWC2 err=%d\n", err);
1143     return -EINVAL;
1144   }
1145
1146   ctx->common.module = const_cast<hw_module_t *>(module);
1147   *dev = &ctx->common;
1148   ctx.release();
1149   return 0;
1150 }
1151
1152 hwcomposer::NativeDisplay *IAHWC2::GetExtendedDisplay(uint32_t dispIndex) {
1153   return extended_displays_.at(dispIndex)->GetDisplay();
1154 }
1155
1156 hwcomposer::NativeDisplay *IAHWC2::GetPrimaryDisplay() {
1157   return primary_display_.GetDisplay();
1158 }
1159
1160 hwcomposer::NativeDisplay *IAHWC2::HwcDisplay::GetDisplay() {
1161   return display_;
1162 }
1163
1164 }  // namespace android
1165
1166 static struct hw_module_methods_t hwc2_module_methods = {
1167     .open = android::IAHWC2::HookDevOpen,
1168 };
1169
1170 hw_module_t HAL_MODULE_INFO_SYM = {
1171     .tag = HARDWARE_MODULE_TAG,
1172     .module_api_version = HARDWARE_MODULE_API_VERSION(2, 0),
1173     .id = HWC_HARDWARE_MODULE_ID,
1174     .name = "IA-Hardware-Composer",
1175     .author = "The Android Open Source Project",
1176     .methods = &hwc2_module_methods,
1177     .dso = NULL,
1178     .reserved = {0},
1179 };