Add hdr attributes to setSurfaceAttr
Keep original copies of hdr metadata to return to the user if requested.
Scale integer values prior to sending to system.
Test: --deqp-case=dEQP-EGL.functional.hdr_color.*
Bug: 72491459, 72828483
Change-Id: I86ed35cf96d740ac230cc10acde322acbeffe847
diff --git a/opengl/libs/EGL/eglApi.cpp b/opengl/libs/EGL/eglApi.cpp
index 26ae13d..b00602c 100644
--- a/opengl/libs/EGL/eglApi.cpp
+++ b/opengl/libs/EGL/eglApi.cpp
@@ -479,8 +479,8 @@
// Return true if we stripped any EGL_GL_COLORSPACE_KHR or HDR metadata attributes.
// Protect devices from attributes they don't recognize that are managed by Android
static EGLBoolean stripAttributes(egl_display_ptr dp, const EGLint* attrib_list,
- EGLint format,
- std::vector<EGLint>& stripped_attrib_list) {
+ EGLint format,
+ std::vector<EGLint>& stripped_attrib_list) {
std::vector<EGLint> allowedColorSpaces;
switch (format) {
case HAL_PIXEL_FORMAT_RGBA_8888:
@@ -712,7 +712,8 @@
cta8613 |= s->setCta8613Attribute(attr[0], attr[1]);
}
if (smpte2086) {
- int err = native_window_set_buffers_smpte2086_metadata(window, s->getSmpte2086Metadata());
+ android_smpte2086_metadata metadata = s->getSmpte2086Metadata();
+ int err = native_window_set_buffers_smpte2086_metadata(window, &metadata);
if (err != 0) {
ALOGE("error setting native window smpte2086 metadata: %s (%d)",
strerror(-err), err);
@@ -721,7 +722,8 @@
}
}
if (cta8613) {
- int err = native_window_set_buffers_cta861_3_metadata(window, s->getCta8613Metadata());
+ android_cta861_3_metadata metadata = s->getCta8613Metadata();
+ int err = native_window_set_buffers_cta861_3_metadata(window, &metadata);
if (err != 0) {
ALOGE("error setting native window CTS 861.3 metadata: %s (%d)",
strerror(-err), err);
@@ -1578,7 +1580,11 @@
return (err == 0) ? EGL_TRUE : setError(EGL_BAD_SURFACE, (EGLBoolean)EGL_FALSE);
}
- if (s->cnx->egl.eglSurfaceAttrib) {
+ if (s->setSmpte2086Attribute(attribute, value)) {
+ return EGL_TRUE;
+ } else if (s->setCta8613Attribute(attribute, value)) {
+ return EGL_TRUE;
+ } else if (s->cnx->egl.eglSurfaceAttrib) {
return s->cnx->egl.eglSurfaceAttrib(
dp->disp.dpy, s->surface, attribute, value);
}
diff --git a/opengl/libs/EGL/egl_object.cpp b/opengl/libs/EGL/egl_object.cpp
index 13b94b6..b68fd61 100644
--- a/opengl/libs/EGL/egl_object.cpp
+++ b/opengl/libs/EGL/egl_object.cpp
@@ -64,8 +64,8 @@
cnx(cnx),
connected(true),
colorSpace(colorSpace),
- smpte2086_metadata({}),
- cta861_3_metadata({}) {
+ egl_smpte2086_metadata({}),
+ egl_cta861_3_metadata({}) {
if (win) {
win->incStrong(this);
}
@@ -90,36 +90,35 @@
EGLBoolean egl_surface_t::setSmpte2086Attribute(EGLint attribute, EGLint value) {
switch (attribute) {
- break;
case EGL_SMPTE2086_DISPLAY_PRIMARY_RX_EXT:
- smpte2086_metadata.displayPrimaryRed.x = value;
+ egl_smpte2086_metadata.displayPrimaryRed.x = value;
return EGL_TRUE;
case EGL_SMPTE2086_DISPLAY_PRIMARY_RY_EXT:
- smpte2086_metadata.displayPrimaryRed.y = value;
+ egl_smpte2086_metadata.displayPrimaryRed.y = value;
return EGL_TRUE;
case EGL_SMPTE2086_DISPLAY_PRIMARY_GX_EXT:
- smpte2086_metadata.displayPrimaryGreen.x = value;
+ egl_smpte2086_metadata.displayPrimaryGreen.x = value;
return EGL_TRUE;
case EGL_SMPTE2086_DISPLAY_PRIMARY_GY_EXT:
- smpte2086_metadata.displayPrimaryGreen.y = value;
+ egl_smpte2086_metadata.displayPrimaryGreen.y = value;
return EGL_TRUE;
case EGL_SMPTE2086_DISPLAY_PRIMARY_BX_EXT:
- smpte2086_metadata.displayPrimaryBlue.x = value;
+ egl_smpte2086_metadata.displayPrimaryBlue.x = value;
return EGL_TRUE;
case EGL_SMPTE2086_DISPLAY_PRIMARY_BY_EXT:
- smpte2086_metadata.displayPrimaryBlue.y = value;
+ egl_smpte2086_metadata.displayPrimaryBlue.y = value;
return EGL_TRUE;
case EGL_SMPTE2086_WHITE_POINT_X_EXT:
- smpte2086_metadata.whitePoint.x = value;
+ egl_smpte2086_metadata.whitePoint.x = value;
return EGL_TRUE;
case EGL_SMPTE2086_WHITE_POINT_Y_EXT:
- smpte2086_metadata.whitePoint.y = value;
+ egl_smpte2086_metadata.whitePoint.y = value;
return EGL_TRUE;
case EGL_SMPTE2086_MAX_LUMINANCE_EXT:
- smpte2086_metadata.maxLuminance = value;
+ egl_smpte2086_metadata.maxLuminance = value;
return EGL_TRUE;
case EGL_SMPTE2086_MIN_LUMINANCE_EXT:
- smpte2086_metadata.minLuminance = value;
+ egl_smpte2086_metadata.minLuminance = value;
return EGL_TRUE;
}
return EGL_FALSE;
@@ -128,15 +127,39 @@
EGLBoolean egl_surface_t::setCta8613Attribute(EGLint attribute, EGLint value) {
switch (attribute) {
case EGL_CTA861_3_MAX_CONTENT_LIGHT_LEVEL_EXT:
- cta861_3_metadata.maxContentLightLevel = value;
+ egl_cta861_3_metadata.maxContentLightLevel = value;
return EGL_TRUE;
case EGL_CTA861_3_MAX_FRAME_AVERAGE_LEVEL_EXT:
- cta861_3_metadata.maxFrameAverageLightLevel = value;
+ egl_cta861_3_metadata.maxFrameAverageLightLevel = value;
return EGL_TRUE;
}
return EGL_FALSE;
}
+const android_smpte2086_metadata egl_surface_t::getSmpte2086Metadata() {
+ android_smpte2086_metadata metadata;
+ metadata.displayPrimaryRed.x = static_cast<float>(egl_smpte2086_metadata.displayPrimaryRed.x) / EGL_METADATA_SCALING_EXT;
+ metadata.displayPrimaryRed.y = static_cast<float>(egl_smpte2086_metadata.displayPrimaryRed.y) / EGL_METADATA_SCALING_EXT;
+ metadata.displayPrimaryGreen.x = static_cast<float>(egl_smpte2086_metadata.displayPrimaryGreen.x) / EGL_METADATA_SCALING_EXT;
+ metadata.displayPrimaryGreen.y = static_cast<float>(egl_smpte2086_metadata.displayPrimaryGreen.y) / EGL_METADATA_SCALING_EXT;
+ metadata.displayPrimaryBlue.x = static_cast<float>(egl_smpte2086_metadata.displayPrimaryBlue.x) / EGL_METADATA_SCALING_EXT;
+ metadata.displayPrimaryBlue.y = static_cast<float>(egl_smpte2086_metadata.displayPrimaryBlue.y) / EGL_METADATA_SCALING_EXT;
+ metadata.whitePoint.x = static_cast<float>(egl_smpte2086_metadata.whitePoint.x) / EGL_METADATA_SCALING_EXT;
+ metadata.whitePoint.y = static_cast<float>(egl_smpte2086_metadata.whitePoint.y) / EGL_METADATA_SCALING_EXT;
+ metadata.maxLuminance = static_cast<float>(egl_smpte2086_metadata.maxLuminance) / EGL_METADATA_SCALING_EXT;
+ metadata.minLuminance = static_cast<float>(egl_smpte2086_metadata.minLuminance) / EGL_METADATA_SCALING_EXT;
+
+ return metadata;
+}
+
+const android_cta861_3_metadata egl_surface_t::getCta8613Metadata() {
+ android_cta861_3_metadata metadata;
+ metadata.maxContentLightLevel = static_cast<float>(egl_cta861_3_metadata.maxContentLightLevel) / EGL_METADATA_SCALING_EXT;
+ metadata.maxFrameAverageLightLevel = static_cast<float>(egl_cta861_3_metadata.maxFrameAverageLightLevel) / EGL_METADATA_SCALING_EXT;
+ return metadata;
+}
+
+
EGLBoolean egl_surface_t::getColorSpaceAttribute(EGLint attribute, EGLint* value) const {
if (attribute == EGL_GL_COLORSPACE_KHR) {
*value = colorSpace;
@@ -148,43 +171,43 @@
EGLBoolean egl_surface_t::getSmpte2086Attribute(EGLint attribute, EGLint *value) const {
switch (attribute) {
case EGL_SMPTE2086_DISPLAY_PRIMARY_RX_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.displayPrimaryRed.x);
+ *value = egl_smpte2086_metadata.displayPrimaryRed.x;
return EGL_TRUE;
break;
case EGL_SMPTE2086_DISPLAY_PRIMARY_RY_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.displayPrimaryRed.y);
+ *value = egl_smpte2086_metadata.displayPrimaryRed.y;
return EGL_TRUE;
break;
case EGL_SMPTE2086_DISPLAY_PRIMARY_GX_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.displayPrimaryGreen.x);
+ *value = egl_smpte2086_metadata.displayPrimaryGreen.x;
return EGL_TRUE;
break;
case EGL_SMPTE2086_DISPLAY_PRIMARY_GY_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.displayPrimaryGreen.y);
+ *value = egl_smpte2086_metadata.displayPrimaryGreen.y;
return EGL_TRUE;
break;
case EGL_SMPTE2086_DISPLAY_PRIMARY_BX_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.displayPrimaryBlue.x);
+ *value = egl_smpte2086_metadata.displayPrimaryBlue.x;
return EGL_TRUE;
break;
case EGL_SMPTE2086_DISPLAY_PRIMARY_BY_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.displayPrimaryBlue.y);
+ *value = egl_smpte2086_metadata.displayPrimaryBlue.y;
return EGL_TRUE;
break;
case EGL_SMPTE2086_WHITE_POINT_X_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.whitePoint.x);
+ *value = egl_smpte2086_metadata.whitePoint.x;
return EGL_TRUE;
break;
case EGL_SMPTE2086_WHITE_POINT_Y_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.whitePoint.y);
+ *value = egl_smpte2086_metadata.whitePoint.y;
return EGL_TRUE;
break;
case EGL_SMPTE2086_MAX_LUMINANCE_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.maxLuminance);
+ *value = egl_smpte2086_metadata.maxLuminance;
return EGL_TRUE;
break;
case EGL_SMPTE2086_MIN_LUMINANCE_EXT:
- *value = *reinterpret_cast<const int*>(&smpte2086_metadata.minLuminance);
+ *value = egl_smpte2086_metadata.minLuminance;
return EGL_TRUE;
break;
}
@@ -194,11 +217,11 @@
EGLBoolean egl_surface_t::getCta8613Attribute(EGLint attribute, EGLint *value) const {
switch (attribute) {
case EGL_CTA861_3_MAX_CONTENT_LIGHT_LEVEL_EXT:
- *value = *reinterpret_cast<const int*>(&cta861_3_metadata.maxContentLightLevel);
+ *value = egl_cta861_3_metadata.maxContentLightLevel;
return EGL_TRUE;
break;
case EGL_CTA861_3_MAX_FRAME_AVERAGE_LEVEL_EXT:
- *value = *reinterpret_cast<const int*>(&cta861_3_metadata.maxFrameAverageLightLevel);
+ *value = egl_cta861_3_metadata.maxFrameAverageLightLevel;
return EGL_TRUE;
break;
}
diff --git a/opengl/libs/EGL/egl_object.h b/opengl/libs/EGL/egl_object.h
index a9020a1..bda91bb 100644
--- a/opengl/libs/EGL/egl_object.h
+++ b/opengl/libs/EGL/egl_object.h
@@ -142,8 +142,8 @@
EGLBoolean getColorSpaceAttribute(EGLint attribute, EGLint* value) const;
EGLBoolean getSmpte2086Attribute(EGLint attribute, EGLint* value) const;
EGLBoolean getCta8613Attribute(EGLint attribute, EGLint* value) const;
- const android_smpte2086_metadata* getSmpte2086Metadata() const { return &smpte2086_metadata; }
- const android_cta861_3_metadata* getCta8613Metadata() const { return &cta861_3_metadata; }
+ const android_smpte2086_metadata getSmpte2086Metadata();
+ const android_cta861_3_metadata getCta8613Metadata();
// Try to keep the order of these fields and size unchanged. It's not public API, but
// it's not hard to imagine native games accessing them.
@@ -157,8 +157,27 @@
bool connected;
void disconnect();
EGLint colorSpace;
- android_smpte2086_metadata smpte2086_metadata;
- android_cta861_3_metadata cta861_3_metadata;
+
+ struct egl_xy_color {
+ EGLint x;
+ EGLint y;
+ };
+
+ struct egl_smpte2086_metadata {
+ struct egl_xy_color displayPrimaryRed;
+ struct egl_xy_color displayPrimaryGreen;
+ struct egl_xy_color displayPrimaryBlue;
+ struct egl_xy_color whitePoint;
+ EGLint maxLuminance;
+ EGLint minLuminance;
+ };
+
+ struct egl_cta861_3_metadata {
+ EGLint maxContentLightLevel;
+ EGLint maxFrameAverageLightLevel;
+ };
+ egl_smpte2086_metadata egl_smpte2086_metadata;
+ egl_cta861_3_metadata egl_cta861_3_metadata;
};
class egl_context_t: public egl_object_t {