hwc2: add client target support
am: 7b213359e6
Change-Id: I6e3ce656f40172bfd8d0459739fa4fe763cecffb
diff --git a/hwc2/hwc2.cpp b/hwc2/hwc2.cpp
index 041e772..2864d34 100644
--- a/hwc2/hwc2.cpp
+++ b/hwc2/hwc2.cpp
@@ -111,11 +111,13 @@
out_layers, out_types);
}
-hwc2_error_t get_client_target_support(hwc2_device_t* /*device*/,
- hwc2_display_t /*display*/, uint32_t /*width*/, uint32_t /*height*/,
- android_pixel_format_t /*format*/, android_dataspace_t /*dataspace*/)
+hwc2_error_t get_client_target_support(hwc2_device_t *device,
+ hwc2_display_t display, uint32_t width, uint32_t height,
+ android_pixel_format_t format, android_dataspace_t dataspace)
{
- return HWC2_ERROR_NONE;
+ hwc2_dev *dev = reinterpret_cast<hwc2_context *>(device)->hwc2_dev;
+ return dev->get_client_target_support(display, width, height, format,
+ dataspace);
}
hwc2_error_t get_color_modes(hwc2_device_t* /*device*/,
@@ -199,12 +201,13 @@
return dev->set_active_config(display, config);
}
-hwc2_error_t set_client_target(hwc2_device_t* /*device*/,
- hwc2_display_t /*display*/, buffer_handle_t /*target*/,
- int32_t /*acquire_fence*/, android_dataspace_t /*dataspace*/,
- hwc_region_t /*damage*/)
+hwc2_error_t set_client_target(hwc2_device_t *device, hwc2_display_t display,
+ buffer_handle_t target, int32_t acquire_fence,
+ android_dataspace_t dataspace, hwc_region_t damage)
{
- return HWC2_ERROR_NONE;
+ hwc2_dev *dev = reinterpret_cast<hwc2_context *>(device)->hwc2_dev;
+ return dev->set_client_target(display, target, acquire_fence, dataspace,
+ damage);
}
hwc2_error_t set_color_mode(hwc2_device_t* /*device*/,
diff --git a/hwc2/hwc2.h b/hwc2/hwc2.h
index 27e894b..8ca3507 100644
--- a/hwc2/hwc2.h
+++ b/hwc2/hwc2.h
@@ -406,6 +406,14 @@
hwc2_error_t set_active_config(struct adf_hwc_helper *adf_helper,
hwc2_config_t config);
+ /* Client target functions */
+ hwc2_error_t get_client_target_support(uint32_t width, uint32_t height,
+ android_pixel_format_t format,
+ android_dataspace_t dataspace);
+ hwc2_error_t set_client_target(buffer_handle_t target,
+ int32_t acquire_fence, android_dataspace_t dataspace,
+ const hwc_region_t &surface_damage);
+
/* Set layer functions */
hwc2_error_t create_layer(hwc2_layer_t *out_layer);
hwc2_error_t destroy_layer(hwc2_layer_t lyr_id);
@@ -470,6 +478,9 @@
/* The display windows */
std::array<hwc2_window, HWC2_WINDOW_COUNT> windows;
+ /* Recieves the output of the client composition */
+ hwc2_buffer client_target;
+
/* The layers currently in use */
std::unordered_map<hwc2_layer_t, hwc2_layer> layers;
@@ -538,6 +549,16 @@
hwc2_config_t *out_config) const;
hwc2_error_t set_active_config(hwc2_display_t dpy_id, hwc2_config_t config);
+ /* Client target functions */
+ hwc2_error_t get_client_target_support(hwc2_display_t dpy_id,
+ uint32_t width, uint32_t height,
+ android_pixel_format_t format,
+ android_dataspace_t dataspace);
+ hwc2_error_t set_client_target(hwc2_display_t dpy_id,
+ buffer_handle_t target, int32_t acquire_fence,
+ android_dataspace_t dataspace,
+ const hwc_region_t &surface_damage);
+
/* Layer functions */
hwc2_error_t create_layer(hwc2_display_t dpy_id, hwc2_layer_t *out_layer);
hwc2_error_t destroy_layer(hwc2_display_t dpy_id, hwc2_layer_t lyr_id);
diff --git a/hwc2/hwc2_dev.cpp b/hwc2/hwc2_dev.cpp
index 57e0d3a..9af6a56 100644
--- a/hwc2/hwc2_dev.cpp
+++ b/hwc2/hwc2_dev.cpp
@@ -210,6 +210,34 @@
return it->second.set_active_config(adf_helper, config);
}
+hwc2_error_t hwc2_dev::get_client_target_support(hwc2_display_t dpy_id,
+ uint32_t width, uint32_t height, android_pixel_format_t format,
+ android_dataspace_t dataspace)
+{
+ auto it = displays.find(dpy_id);
+ if (it == displays.end()) {
+ ALOGE("dpy %" PRIu64 ": invalid display handle", dpy_id);
+ return HWC2_ERROR_BAD_DISPLAY;
+ }
+
+ return it->second.get_client_target_support(width, height, format,
+ dataspace);
+}
+
+hwc2_error_t hwc2_dev::set_client_target(hwc2_display_t dpy_id,
+ buffer_handle_t target, int32_t acquire_fence,
+ android_dataspace_t dataspace, const hwc_region_t &surface_damage)
+{
+ auto it = displays.find(dpy_id);
+ if (it == displays.end()) {
+ ALOGE("dpy %" PRIu64 ": invalid display handle", dpy_id);
+ return HWC2_ERROR_BAD_DISPLAY;
+ }
+
+ return it->second.set_client_target(target, acquire_fence, dataspace,
+ surface_damage);
+}
+
hwc2_error_t hwc2_dev::create_layer(hwc2_display_t dpy_id, hwc2_layer_t *out_layer)
{
auto it = displays.find(dpy_id);
diff --git a/hwc2/hwc2_display.cpp b/hwc2/hwc2_display.cpp
index 1fc08e1..ff3fba6 100644
--- a/hwc2/hwc2_display.cpp
+++ b/hwc2/hwc2_display.cpp
@@ -35,6 +35,7 @@
display_state(modified),
client_target_used(false),
windows(),
+ client_target(),
layers(),
vsync_enabled(HWC2_VSYNC_DISABLE),
changed_comp_types(),
@@ -457,6 +458,58 @@
return HWC2_ERROR_NONE;
}
+hwc2_error_t hwc2_display::get_client_target_support(uint32_t width,
+ uint32_t height, android_pixel_format_t format,
+ android_dataspace_t dataspace)
+{
+ if (active_config >= configs.size()) {
+ ALOGE("dpy %" PRIu64 ": no active_config", id);
+ return HWC2_ERROR_UNSUPPORTED;
+ }
+
+ int32_t cnfg_width = configs[active_config].get_attribute(
+ HWC2_ATTRIBUTE_WIDTH);
+ int32_t cnfg_height = configs[active_config].get_attribute(
+ HWC2_ATTRIBUTE_HEIGHT);
+
+ if (cnfg_width < 0 || width != static_cast<uint32_t>(cnfg_width)) {
+ ALOGE("dpy %" PRIu64 ": unsupported client target width", id);
+ return HWC2_ERROR_UNSUPPORTED;
+ }
+
+ if (cnfg_height < 0 || height != static_cast<uint32_t>(cnfg_height)) {
+ ALOGE("dpy %" PRIu64 ": unsupported client target height", id);
+ return HWC2_ERROR_UNSUPPORTED;
+ }
+
+ if (format != HAL_PIXEL_FORMAT_RGBA_8888) {
+ ALOGE("dpy %" PRIu64 ": unsupported client target format", id);
+ return HWC2_ERROR_UNSUPPORTED;
+ }
+
+ if (dataspace != HAL_DATASPACE_UNKNOWN) {
+ ALOGE("dpy %" PRIu64 ": unsupported client target dataspace", id);
+ return HWC2_ERROR_UNSUPPORTED;
+ }
+
+ return HWC2_ERROR_NONE;
+}
+
+hwc2_error_t hwc2_display::set_client_target(buffer_handle_t handle,
+ int32_t acquire_fence, android_dataspace_t dataspace,
+ const hwc_region_t &surface_damage)
+{
+ hwc2_error_t ret = client_target.set_buffer(handle, acquire_fence);
+ if (ret != HWC2_ERROR_NONE)
+ return ret;
+
+ ret = client_target.set_dataspace(dataspace);
+ if (ret != HWC2_ERROR_NONE)
+ return ret;
+
+ return client_target.set_surface_damage(surface_damage);
+}
+
hwc2_error_t hwc2_display::create_layer(hwc2_layer_t *out_layer)
{
display_state = modified;