Home | History | Annotate | Download | only in android
      1 /*
      2  * Copyright 2018 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 #include <android/hardware/configstore/1.0/ISurfaceFlingerConfigs.h>
     18 #include <android/native_window.h>
     19 #include <android/surface_control.h>
     20 
     21 #include <configstore/Utils.h>
     22 
     23 #include <gui/HdrMetadata.h>
     24 #include <gui/ISurfaceComposer.h>
     25 #include <gui/Surface.h>
     26 #include <gui/SurfaceComposerClient.h>
     27 #include <gui/SurfaceControl.h>
     28 
     29 #include <ui/HdrCapabilities.h>
     30 
     31 #include <utils/Timers.h>
     32 
     33 using namespace android::hardware::configstore;
     34 using namespace android::hardware::configstore::V1_0;
     35 using namespace android;
     36 using android::hardware::configstore::V1_0::ISurfaceFlingerConfigs;
     37 
     38 using Transaction = SurfaceComposerClient::Transaction;
     39 
     40 #define CHECK_NOT_NULL(name) \
     41     LOG_ALWAYS_FATAL_IF(name == nullptr, "nullptr passed as " #name " argument");
     42 
     43 #define CHECK_VALID_RECT(name)                                     \
     44     LOG_ALWAYS_FATAL_IF(!static_cast<const Rect&>(name).isValid(), \
     45                         "invalid arg passed as " #name " argument");
     46 
     47 static bool getWideColorSupport(const sp<SurfaceControl>& surfaceControl) {
     48     sp<SurfaceComposerClient> client = surfaceControl->getClient();
     49 
     50     const sp<IBinder> display = client->getInternalDisplayToken();
     51     if (display == nullptr) {
     52         ALOGE("unable to get wide color support for disconnected internal display");
     53         return false;
     54     }
     55 
     56     bool isWideColorDisplay = false;
     57     status_t err = client->isWideColorDisplay(display, &isWideColorDisplay);
     58     if (err) {
     59         ALOGE("unable to get wide color support");
     60         return false;
     61     }
     62     return isWideColorDisplay;
     63 }
     64 
     65 static bool getHdrSupport(const sp<SurfaceControl>& surfaceControl) {
     66     sp<SurfaceComposerClient> client = surfaceControl->getClient();
     67 
     68     const sp<IBinder> display = client->getInternalDisplayToken();
     69     if (display == nullptr) {
     70         ALOGE("unable to get hdr capabilities for disconnected internal display");
     71         return false;
     72     }
     73 
     74     HdrCapabilities hdrCapabilities;
     75     status_t err = client->getHdrCapabilities(display, &hdrCapabilities);
     76     if (err) {
     77         ALOGE("unable to get hdr capabilities");
     78         return false;
     79     }
     80 
     81     return !hdrCapabilities.getSupportedHdrTypes().empty();
     82 }
     83 
     84 static bool isDataSpaceValid(const sp<SurfaceControl>& surfaceControl, ADataSpace dataSpace) {
     85     static_assert(static_cast<int>(ADATASPACE_UNKNOWN) == static_cast<int>(HAL_DATASPACE_UNKNOWN));
     86     static_assert(static_cast<int>(ADATASPACE_SCRGB_LINEAR) == static_cast<int>(HAL_DATASPACE_V0_SCRGB_LINEAR));
     87     static_assert(static_cast<int>(ADATASPACE_SRGB) == static_cast<int>(HAL_DATASPACE_V0_SRGB));
     88     static_assert(static_cast<int>(ADATASPACE_SCRGB) == static_cast<int>(HAL_DATASPACE_V0_SCRGB));
     89     static_assert(static_cast<int>(ADATASPACE_DISPLAY_P3) == static_cast<int>(HAL_DATASPACE_DISPLAY_P3));
     90     static_assert(static_cast<int>(ADATASPACE_BT2020_PQ) == static_cast<int>(HAL_DATASPACE_BT2020_PQ));
     91 
     92     switch (static_cast<android_dataspace_t>(dataSpace)) {
     93         case HAL_DATASPACE_UNKNOWN:
     94         case HAL_DATASPACE_V0_SRGB:
     95             return true;
     96         // These data space need wide gamut support.
     97         case HAL_DATASPACE_V0_SCRGB_LINEAR:
     98         case HAL_DATASPACE_V0_SCRGB:
     99         case HAL_DATASPACE_DISPLAY_P3:
    100             return getWideColorSupport(surfaceControl);
    101         // These data space need HDR support.
    102         case HAL_DATASPACE_BT2020_PQ:
    103             return getHdrSupport(surfaceControl);
    104         default:
    105             return false;
    106     }
    107 }
    108 
    109 Transaction* ASurfaceTransaction_to_Transaction(ASurfaceTransaction* aSurfaceTransaction) {
    110     return reinterpret_cast<Transaction*>(aSurfaceTransaction);
    111 }
    112 
    113 SurfaceControl* ASurfaceControl_to_SurfaceControl(ASurfaceControl* aSurfaceControl) {
    114     return reinterpret_cast<SurfaceControl*>(aSurfaceControl);
    115 }
    116 
    117 void SurfaceControl_acquire(SurfaceControl* surfaceControl) {
    118     // incStrong/decStrong token must be the same, doesn't matter what it is
    119     surfaceControl->incStrong((void*)SurfaceControl_acquire);
    120 }
    121 
    122 void SurfaceControl_release(SurfaceControl* surfaceControl) {
    123     // incStrong/decStrong token must be the same, doesn't matter what it is
    124     surfaceControl->decStrong((void*)SurfaceControl_acquire);
    125 }
    126 
    127 ASurfaceControl* ASurfaceControl_createFromWindow(ANativeWindow* window, const char* debug_name) {
    128     CHECK_NOT_NULL(window);
    129     CHECK_NOT_NULL(debug_name);
    130 
    131     sp<SurfaceComposerClient> client = new SurfaceComposerClient();
    132     if (client->initCheck() != NO_ERROR) {
    133         return nullptr;
    134     }
    135 
    136     uint32_t flags = ISurfaceComposerClient::eFXSurfaceBufferState;
    137     sp<SurfaceControl> surfaceControl =
    138             client->createWithSurfaceParent(String8(debug_name), 0 /* width */, 0 /* height */,
    139                                             // Format is only relevant for buffer queue layers.
    140                                             PIXEL_FORMAT_UNKNOWN /* format */, flags,
    141                                             static_cast<Surface*>(window));
    142     if (!surfaceControl) {
    143         return nullptr;
    144     }
    145 
    146     SurfaceControl_acquire(surfaceControl.get());
    147     return reinterpret_cast<ASurfaceControl*>(surfaceControl.get());
    148 }
    149 
    150 ASurfaceControl* ASurfaceControl_create(ASurfaceControl* parent, const char* debug_name) {
    151     CHECK_NOT_NULL(parent);
    152     CHECK_NOT_NULL(debug_name);
    153 
    154     SurfaceComposerClient* client = ASurfaceControl_to_SurfaceControl(parent)->getClient().get();
    155 
    156     SurfaceControl* surfaceControlParent = ASurfaceControl_to_SurfaceControl(parent);
    157 
    158     uint32_t flags = ISurfaceComposerClient::eFXSurfaceBufferState;
    159     sp<SurfaceControl> surfaceControl =
    160             client->createSurface(String8(debug_name), 0 /* width */, 0 /* height */,
    161                                   // Format is only relevant for buffer queue layers.
    162                                   PIXEL_FORMAT_UNKNOWN /* format */, flags,
    163                                   surfaceControlParent);
    164     if (!surfaceControl) {
    165         return nullptr;
    166     }
    167 
    168     SurfaceControl_acquire(surfaceControl.get());
    169     return reinterpret_cast<ASurfaceControl*>(surfaceControl.get());
    170 }
    171 
    172 void ASurfaceControl_release(ASurfaceControl* aSurfaceControl) {
    173     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    174 
    175     SurfaceControl_release(surfaceControl.get());
    176 }
    177 
    178 ASurfaceTransaction* ASurfaceTransaction_create() {
    179     Transaction* transaction = new Transaction;
    180     return reinterpret_cast<ASurfaceTransaction*>(transaction);
    181 }
    182 
    183 void ASurfaceTransaction_delete(ASurfaceTransaction* aSurfaceTransaction) {
    184     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    185     delete transaction;
    186 }
    187 
    188 void ASurfaceTransaction_apply(ASurfaceTransaction* aSurfaceTransaction) {
    189     CHECK_NOT_NULL(aSurfaceTransaction);
    190 
    191     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    192 
    193     transaction->apply();
    194 }
    195 
    196 typedef struct ASurfaceControlStats {
    197     int64_t acquireTime;
    198     sp<Fence> previousReleaseFence;
    199 } ASurfaceControlStats;
    200 
    201 struct ASurfaceTransactionStats {
    202     std::unordered_map<ASurfaceControl*, ASurfaceControlStats> aSurfaceControlStats;
    203     int64_t latchTime;
    204     sp<Fence> presentFence;
    205 };
    206 
    207 int64_t ASurfaceTransactionStats_getLatchTime(ASurfaceTransactionStats* aSurfaceTransactionStats) {
    208     CHECK_NOT_NULL(aSurfaceTransactionStats);
    209     return aSurfaceTransactionStats->latchTime;
    210 }
    211 
    212 int ASurfaceTransactionStats_getPresentFenceFd(ASurfaceTransactionStats* aSurfaceTransactionStats) {
    213     CHECK_NOT_NULL(aSurfaceTransactionStats);
    214     auto& presentFence = aSurfaceTransactionStats->presentFence;
    215     return (presentFence) ? presentFence->dup() : -1;
    216 }
    217 
    218 void ASurfaceTransactionStats_getASurfaceControls(ASurfaceTransactionStats* aSurfaceTransactionStats,
    219                                                   ASurfaceControl*** outASurfaceControls,
    220                                                   size_t* outASurfaceControlsSize) {
    221     CHECK_NOT_NULL(aSurfaceTransactionStats);
    222     CHECK_NOT_NULL(outASurfaceControls);
    223     CHECK_NOT_NULL(outASurfaceControlsSize);
    224 
    225     size_t size = aSurfaceTransactionStats->aSurfaceControlStats.size();
    226 
    227     SurfaceControl** surfaceControls = new SurfaceControl*[size];
    228     ASurfaceControl** aSurfaceControls = reinterpret_cast<ASurfaceControl**>(surfaceControls);
    229 
    230     size_t i = 0;
    231     for (auto& [aSurfaceControl, aSurfaceControlStats] : aSurfaceTransactionStats->aSurfaceControlStats) {
    232         aSurfaceControls[i] = aSurfaceControl;
    233         i++;
    234     }
    235 
    236     *outASurfaceControls = aSurfaceControls;
    237     *outASurfaceControlsSize = size;
    238 }
    239 
    240 int64_t ASurfaceTransactionStats_getAcquireTime(ASurfaceTransactionStats* aSurfaceTransactionStats,
    241                                                 ASurfaceControl* aSurfaceControl) {
    242     CHECK_NOT_NULL(aSurfaceTransactionStats);
    243     CHECK_NOT_NULL(aSurfaceControl);
    244 
    245     const auto& aSurfaceControlStats =
    246             aSurfaceTransactionStats->aSurfaceControlStats.find(aSurfaceControl);
    247     LOG_ALWAYS_FATAL_IF(
    248             aSurfaceControlStats == aSurfaceTransactionStats->aSurfaceControlStats.end(),
    249             "ASurfaceControl not found");
    250 
    251     return aSurfaceControlStats->second.acquireTime;
    252 }
    253 
    254 int ASurfaceTransactionStats_getPreviousReleaseFenceFd(
    255             ASurfaceTransactionStats* aSurfaceTransactionStats, ASurfaceControl* aSurfaceControl) {
    256     CHECK_NOT_NULL(aSurfaceTransactionStats);
    257     CHECK_NOT_NULL(aSurfaceControl);
    258 
    259     const auto& aSurfaceControlStats =
    260             aSurfaceTransactionStats->aSurfaceControlStats.find(aSurfaceControl);
    261     LOG_ALWAYS_FATAL_IF(
    262             aSurfaceControlStats == aSurfaceTransactionStats->aSurfaceControlStats.end(),
    263             "ASurfaceControl not found");
    264 
    265     auto& previousReleaseFence = aSurfaceControlStats->second.previousReleaseFence;
    266     return (previousReleaseFence) ? previousReleaseFence->dup() : -1;
    267 }
    268 
    269 void ASurfaceTransactionStats_releaseASurfaceControls(ASurfaceControl** aSurfaceControls) {
    270     CHECK_NOT_NULL(aSurfaceControls);
    271 
    272     SurfaceControl** surfaceControls = reinterpret_cast<SurfaceControl**>(aSurfaceControls);
    273     delete[] surfaceControls;
    274 }
    275 
    276 void ASurfaceTransaction_setOnComplete(ASurfaceTransaction* aSurfaceTransaction, void* context,
    277                                        ASurfaceTransaction_OnComplete func) {
    278     CHECK_NOT_NULL(aSurfaceTransaction);
    279     CHECK_NOT_NULL(context);
    280     CHECK_NOT_NULL(func);
    281 
    282     TransactionCompletedCallbackTakesContext callback = [func](void* callback_context,
    283                                                                nsecs_t latchTime,
    284                                                                const sp<Fence>& presentFence,
    285                                                                const std::vector<SurfaceControlStats>& surfaceControlStats) {
    286         ASurfaceTransactionStats aSurfaceTransactionStats;
    287 
    288         aSurfaceTransactionStats.latchTime = latchTime;
    289         aSurfaceTransactionStats.presentFence = presentFence;
    290 
    291         auto& aSurfaceControlStats = aSurfaceTransactionStats.aSurfaceControlStats;
    292 
    293         for (const auto& [surfaceControl, acquireTime, previousReleaseFence] : surfaceControlStats) {
    294             ASurfaceControl* aSurfaceControl = reinterpret_cast<ASurfaceControl*>(surfaceControl.get());
    295             aSurfaceControlStats[aSurfaceControl].acquireTime = acquireTime;
    296             aSurfaceControlStats[aSurfaceControl].previousReleaseFence = previousReleaseFence;
    297         }
    298 
    299         (*func)(callback_context, &aSurfaceTransactionStats);
    300     };
    301 
    302     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    303 
    304     transaction->addTransactionCompletedCallback(callback, context);
    305 }
    306 
    307 void ASurfaceTransaction_reparent(ASurfaceTransaction* aSurfaceTransaction,
    308                                   ASurfaceControl* aSurfaceControl,
    309                                   ASurfaceControl* newParentASurfaceControl) {
    310     CHECK_NOT_NULL(aSurfaceTransaction);
    311     CHECK_NOT_NULL(aSurfaceControl);
    312 
    313     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    314     sp<SurfaceControl> newParentSurfaceControl = ASurfaceControl_to_SurfaceControl(
    315             newParentASurfaceControl);
    316     sp<IBinder> newParentHandle = (newParentSurfaceControl)? newParentSurfaceControl->getHandle() : nullptr;
    317     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    318 
    319     transaction->reparent(surfaceControl, newParentHandle);
    320 }
    321 
    322 void ASurfaceTransaction_setVisibility(ASurfaceTransaction* aSurfaceTransaction,
    323                                        ASurfaceControl* aSurfaceControl,
    324                                        int8_t visibility) {
    325     CHECK_NOT_NULL(aSurfaceTransaction);
    326     CHECK_NOT_NULL(aSurfaceControl);
    327 
    328     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    329     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    330 
    331     switch (visibility) {
    332     case ASURFACE_TRANSACTION_VISIBILITY_SHOW:
    333         transaction->show(surfaceControl);
    334         break;
    335     case ASURFACE_TRANSACTION_VISIBILITY_HIDE:
    336         transaction->hide(surfaceControl);
    337         break;
    338     default:
    339         LOG_ALWAYS_FATAL("invalid visibility %d", visibility);
    340     }
    341 }
    342 
    343 void ASurfaceTransaction_setZOrder(ASurfaceTransaction* aSurfaceTransaction,
    344                                    ASurfaceControl* aSurfaceControl,
    345                                    int32_t z_order) {
    346     CHECK_NOT_NULL(aSurfaceTransaction);
    347     CHECK_NOT_NULL(aSurfaceControl);
    348 
    349     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    350     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    351 
    352     transaction->setLayer(surfaceControl, z_order);
    353 }
    354 
    355 void ASurfaceTransaction_setBuffer(ASurfaceTransaction* aSurfaceTransaction,
    356                                    ASurfaceControl* aSurfaceControl,
    357                                    AHardwareBuffer* buffer, int acquire_fence_fd) {
    358     CHECK_NOT_NULL(aSurfaceTransaction);
    359     CHECK_NOT_NULL(aSurfaceControl);
    360 
    361     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    362     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    363 
    364     sp<GraphicBuffer> graphic_buffer(reinterpret_cast<GraphicBuffer*>(buffer));
    365 
    366     transaction->setBuffer(surfaceControl, graphic_buffer);
    367     if (acquire_fence_fd != -1) {
    368         sp<Fence> fence = new Fence(acquire_fence_fd);
    369         transaction->setAcquireFence(surfaceControl, fence);
    370     }
    371 }
    372 
    373 void ASurfaceTransaction_setGeometry(ASurfaceTransaction* aSurfaceTransaction,
    374                                      ASurfaceControl* aSurfaceControl, const ARect& source,
    375                                      const ARect& destination, int32_t transform) {
    376     CHECK_NOT_NULL(aSurfaceTransaction);
    377     CHECK_NOT_NULL(aSurfaceControl);
    378     CHECK_VALID_RECT(source);
    379     CHECK_VALID_RECT(destination);
    380 
    381     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    382     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    383 
    384     transaction->setCrop(surfaceControl, static_cast<const Rect&>(source));
    385     transaction->setFrame(surfaceControl, static_cast<const Rect&>(destination));
    386     transaction->setTransform(surfaceControl, transform);
    387     bool transformToInverseDisplay = (NATIVE_WINDOW_TRANSFORM_INVERSE_DISPLAY & transform) ==
    388             NATIVE_WINDOW_TRANSFORM_INVERSE_DISPLAY;
    389     transaction->setTransformToDisplayInverse(surfaceControl, transformToInverseDisplay);
    390 }
    391 
    392 void ASurfaceTransaction_setBufferTransparency(ASurfaceTransaction* aSurfaceTransaction,
    393                                                ASurfaceControl* aSurfaceControl,
    394                                                int8_t transparency) {
    395     CHECK_NOT_NULL(aSurfaceTransaction);
    396     CHECK_NOT_NULL(aSurfaceControl);
    397 
    398     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    399     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    400 
    401     uint32_t flags = (transparency == ASURFACE_TRANSACTION_TRANSPARENCY_OPAQUE) ?
    402                       layer_state_t::eLayerOpaque : 0;
    403     transaction->setFlags(surfaceControl, flags, layer_state_t::eLayerOpaque);
    404 }
    405 
    406 void ASurfaceTransaction_setDamageRegion(ASurfaceTransaction* aSurfaceTransaction,
    407                                          ASurfaceControl* aSurfaceControl,
    408                                          const ARect rects[], uint32_t count) {
    409     CHECK_NOT_NULL(aSurfaceTransaction);
    410     CHECK_NOT_NULL(aSurfaceControl);
    411 
    412     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    413     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    414 
    415     Region region;
    416     for (uint32_t i = 0; i < count; ++i) {
    417         region.orSelf(static_cast<const Rect&>(rects[i]));
    418     }
    419 
    420     // Hardware composer interprets a DamageRegion with a single Rect of {0,0,0,0} to be an
    421     // undamaged region and {0,0,-1,-1} to be a fully damaged buffer. This is a confusing
    422     // distinction for a public api. Instead, default both cases to be a fully damaged buffer.
    423     if (count == 1 && region.getBounds().isEmpty()) {
    424         transaction->setSurfaceDamageRegion(surfaceControl, Region::INVALID_REGION);
    425         return;
    426     }
    427 
    428     transaction->setSurfaceDamageRegion(surfaceControl, region);
    429 }
    430 
    431 void ASurfaceTransaction_setDesiredPresentTime(ASurfaceTransaction* aSurfaceTransaction,
    432                                          int64_t desiredPresentTime) {
    433     CHECK_NOT_NULL(aSurfaceTransaction);
    434 
    435     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    436 
    437     transaction->setDesiredPresentTime(static_cast<nsecs_t>(desiredPresentTime));
    438 }
    439 
    440 void ASurfaceTransaction_setBufferAlpha(ASurfaceTransaction* aSurfaceTransaction,
    441                                          ASurfaceControl* aSurfaceControl,
    442                                          float alpha) {
    443     CHECK_NOT_NULL(aSurfaceTransaction);
    444     CHECK_NOT_NULL(aSurfaceControl);
    445 
    446     LOG_ALWAYS_FATAL_IF(alpha < 0.0 || alpha > 1.0, "invalid alpha");
    447 
    448     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    449     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    450 
    451     transaction->setAlpha(surfaceControl, alpha);
    452 }
    453 
    454 void ASurfaceTransaction_setBufferDataSpace(ASurfaceTransaction* aSurfaceTransaction,
    455                                          ASurfaceControl* aSurfaceControl,
    456                                          ADataSpace aDataSpace) {
    457     CHECK_NOT_NULL(aSurfaceTransaction);
    458     CHECK_NOT_NULL(aSurfaceControl);
    459 
    460     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    461     LOG_ALWAYS_FATAL_IF(!isDataSpaceValid(surfaceControl, aDataSpace), "invalid dataspace");
    462 
    463     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    464 
    465     transaction->setDataspace(surfaceControl, static_cast<ui::Dataspace>(aDataSpace));
    466 }
    467 
    468 void ASurfaceTransaction_setHdrMetadata_smpte2086(ASurfaceTransaction* aSurfaceTransaction,
    469                                                   ASurfaceControl* aSurfaceControl,
    470                                                   struct AHdrMetadata_smpte2086* metadata) {
    471     CHECK_NOT_NULL(aSurfaceTransaction);
    472     CHECK_NOT_NULL(aSurfaceControl);
    473 
    474     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    475     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    476 
    477     HdrMetadata hdrMetadata;
    478 
    479     if (metadata) {
    480         hdrMetadata.smpte2086.displayPrimaryRed.x = metadata->displayPrimaryRed.x;
    481         hdrMetadata.smpte2086.displayPrimaryRed.y = metadata->displayPrimaryRed.y;
    482         hdrMetadata.smpte2086.displayPrimaryGreen.x = metadata->displayPrimaryGreen.x;
    483         hdrMetadata.smpte2086.displayPrimaryGreen.y = metadata->displayPrimaryGreen.y;
    484         hdrMetadata.smpte2086.displayPrimaryBlue.x = metadata->displayPrimaryBlue.x;
    485         hdrMetadata.smpte2086.displayPrimaryBlue.y = metadata->displayPrimaryBlue.y;
    486         hdrMetadata.smpte2086.whitePoint.x = metadata->whitePoint.x;
    487         hdrMetadata.smpte2086.whitePoint.y = metadata->whitePoint.y;
    488         hdrMetadata.smpte2086.minLuminance = metadata->minLuminance;
    489         hdrMetadata.smpte2086.maxLuminance = metadata->maxLuminance;
    490 
    491         hdrMetadata.validTypes |= HdrMetadata::SMPTE2086;
    492     } else {
    493         hdrMetadata.validTypes &= ~HdrMetadata::SMPTE2086;
    494     }
    495 
    496     transaction->setHdrMetadata(surfaceControl, hdrMetadata);
    497 }
    498 
    499 void ASurfaceTransaction_setHdrMetadata_cta861_3(ASurfaceTransaction* aSurfaceTransaction,
    500                                                  ASurfaceControl* aSurfaceControl,
    501                                                  struct AHdrMetadata_cta861_3* metadata) {
    502     CHECK_NOT_NULL(aSurfaceTransaction);
    503     CHECK_NOT_NULL(aSurfaceControl);
    504 
    505     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    506     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    507 
    508     HdrMetadata hdrMetadata;
    509 
    510     if (metadata) {
    511         hdrMetadata.cta8613.maxContentLightLevel = metadata->maxContentLightLevel;
    512         hdrMetadata.cta8613.maxFrameAverageLightLevel = metadata->maxFrameAverageLightLevel;
    513 
    514         hdrMetadata.validTypes |= HdrMetadata::CTA861_3;
    515     } else {
    516         hdrMetadata.validTypes &= ~HdrMetadata::CTA861_3;
    517     }
    518 
    519     transaction->setHdrMetadata(surfaceControl, hdrMetadata);
    520 }
    521 
    522 void ASurfaceTransaction_setColor(ASurfaceTransaction* aSurfaceTransaction,
    523                                   ASurfaceControl* aSurfaceControl,
    524                                   float r, float g, float b, float alpha,
    525                                   ADataSpace dataspace) {
    526     CHECK_NOT_NULL(aSurfaceTransaction);
    527     CHECK_NOT_NULL(aSurfaceControl);
    528 
    529     sp<SurfaceControl> surfaceControl = ASurfaceControl_to_SurfaceControl(aSurfaceControl);
    530     LOG_ALWAYS_FATAL_IF(!isDataSpaceValid(surfaceControl, dataspace), "invalid dataspace");
    531     Transaction* transaction = ASurfaceTransaction_to_Transaction(aSurfaceTransaction);
    532 
    533     half3 color;
    534     color.r = r;
    535     color.g = g;
    536     color.b = b;
    537 
    538     transaction->setBackgroundColor(surfaceControl, color, alpha, static_cast<ui::Dataspace>(dataspace));
    539 }
    540