• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2012 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 <aidl/android/hardware/graphics/common/BufferUsage.h>
18 #include <utils/Errors.h>
19 #include <linux/videodev2.h>
20 #include <sys/mman.h>
21 #include <hardware/hwcomposer_defs.h>
22 #include <hardware/exynos/ion.h>
23 
24 #include "BrightnessController.h"
25 #include "ExynosLayer.h"
26 #include "ExynosResourceManager.h"
27 #include "ExynosHWCDebug.h"
28 #include "ExynosExternalDisplay.h"
29 
30 #include "VendorVideoAPI.h"
31 
32 /**
33  * ExynosLayer implementation
34  */
35 
36 using AidlBufferUsage = ::aidl::android::hardware::graphics::common::BufferUsage;
37 
ExynosLayer(ExynosDisplay * display)38 ExynosLayer::ExynosLayer(ExynosDisplay* display)
39       : ExynosMPPSource(MPP_SOURCE_LAYER, this),
40         mDisplay(display),
41         mCompositionType(HWC2_COMPOSITION_INVALID),
42         mExynosCompositionType(HWC2_COMPOSITION_INVALID),
43         mValidateCompositionType(HWC2_COMPOSITION_INVALID),
44         mValidateExynosCompositionType(HWC2_COMPOSITION_INVALID),
45         mOverlayInfo(0x0),
46         mSupportedMPPFlag(0x0),
47         mFps(0),
48         mOverlayPriority(ePriorityLow),
49         mGeometryChanged(0x0),
50         mWindowIndex(0),
51         mCompressed(false),
52         mAcquireFence(-1),
53         mPrevAcquireFence(-1),
54         mReleaseFence(-1),
55         mFrameCount(0),
56         mLastFrameCount(0),
57         mLastFpsTime(0),
58         mNextLastFrameCount(0),
59         mNextLastFpsTime(0),
60         mLastLayerBuffer(NULL),
61         mLayerBuffer(NULL),
62         mDamageNum(0),
63         mBlending(HWC2_BLEND_MODE_NONE),
64         mPlaneAlpha(1.0),
65         mTransform(0),
66         mZOrder(0),
67         mDataSpace(HAL_DATASPACE_UNKNOWN),
68         mLayerFlag(0x0),
69         mIsHdrLayer(false),
70         mBufferHasMetaParcel(false),
71         mMetaParcelFd(-1) {
72     memset(&mDisplayFrame, 0, sizeof(mDisplayFrame));
73     memset(&mSourceCrop, 0, sizeof(mSourceCrop));
74     mVisibleRegionScreen.numRects = 0;
75     mVisibleRegionScreen.rects = NULL;
76     memset(&mColor, 0, sizeof(mColor));
77     memset(&mPreprocessedInfo, 0, sizeof(mPreprocessedInfo));
78     mCheckMPPFlag.clear();
79     mCheckMPPFlag.reserve(MPP_LOGICAL_TYPE_NUM);
80     mMetaParcel = NULL;
81     mDamageRects.clear();
82 }
83 
~ExynosLayer()84 ExynosLayer::~ExynosLayer() {
85     if (mMetaParcel != NULL) {
86         munmap(mMetaParcel, sizeof(ExynosVideoMeta));
87         mMetaParcel = NULL;
88     }
89 
90     if (mMetaParcelFd >= 0) {
91         close(mMetaParcelFd);
92         mMetaParcelFd = -1;
93     }
94 
95     if (mAcquireFence >= 0) {
96         mAcquireFence =
97                 fence_close(mAcquireFence, mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_UNDEFINED);
98     }
99 
100     if (mPrevAcquireFence != -1)
101         mPrevAcquireFence = fence_close(mPrevAcquireFence, mDisplay, FENCE_TYPE_SRC_ACQUIRE,
102                                         FENCE_IP_UNDEFINED);
103 }
104 
105 /**
106  * @return float
107  */
checkFps(bool increaseCount)108 float ExynosLayer::checkFps(bool increaseCount) {
109     uint32_t frameDiff;
110     mFrameCount += increaseCount ? 1 : 0;
111 
112     nsecs_t now = systemTime();
113     if (mLastFpsTime == 0) { // Initialize values
114         mLastFpsTime = now;
115         mNextLastFpsTime = now;
116         // TODO(b/268474771): set the initial FPS to the correct peak refresh rate
117         mFps = 120;
118         return mFps;
119     }
120 
121     nsecs_t diff = now - mNextLastFpsTime;
122     // Update mLastFrameCount for every 5s, to ensure that FPS calculation is only based on
123     // frames in the past at most 10s.
124     if (diff >= kLayerFpsStableTimeNs) {
125         mLastFrameCount = mNextLastFrameCount;
126         mNextLastFrameCount = mFrameCount;
127 
128         mLastFpsTime = mNextLastFpsTime;
129         mNextLastFpsTime = now;
130     }
131 
132     bool wasLowFps = (mFps < LOW_FPS_THRESHOLD) ? true : false;
133 
134     if (mFrameCount >= mLastFrameCount)
135         frameDiff = (mFrameCount - mLastFrameCount);
136     else
137         frameDiff = (mFrameCount + (UINT_MAX - mLastFrameCount));
138 
139     diff = now - mLastFpsTime;
140     mFps = (frameDiff * float(s2ns(1))) / diff;
141 
142     bool nowLowFps = (mFps < LOW_FPS_THRESHOLD) ? true : false;
143 
144     if ((mDisplay->mDisplayControl.handleLowFpsLayers) &&
145         (wasLowFps != nowLowFps))
146         setGeometryChanged(GEOMETRY_LAYER_FPS_CHANGED);
147 
148     return mFps;
149 }
150 
151 /**
152  * @return float
153  */
getFps()154 float ExynosLayer::getFps() {
155     return mFps;
156 }
157 
doPreProcess()158 int32_t ExynosLayer::doPreProcess()
159 {
160     overlay_priority priority = ePriorityLow;
161     mIsHdrLayer = false;
162     mBufferHasMetaParcel = false;
163     mLayerFlag = 0x0;
164 
165     mPreprocessedInfo.preProcessed = false;
166     mPreprocessedInfo.sourceCrop = mSourceCrop;
167     mPreprocessedInfo.displayFrame = mDisplayFrame;
168     mPreprocessedInfo.interlacedType = V4L2_FIELD_NONE;
169     mPreprocessedInfo.sdrDimRatio = mBrightness;
170 
171     if (mCompositionType == HWC2_COMPOSITION_SOLID_COLOR) {
172         mLayerFlag |= EXYNOS_HWC_DIM_LAYER;
173     } else {
174         mLayerFlag &= ~(EXYNOS_HWC_DIM_LAYER);
175     }
176 
177     if (mLayerBuffer == NULL) {
178         if (mOverlayPriority != priority)
179             setGeometryChanged(GEOMETRY_LAYER_PRIORITY_CHANGED);
180 
181         mOverlayPriority = priority;
182         return NO_ERROR;
183     }
184 
185     VendorGraphicBufferMeta gmeta(mLayerBuffer);
186 
187     mPreprocessedInfo.mUsePrivateFormat = false;
188     mPreprocessedInfo.mPrivateFormat = gmeta.format;
189 
190     if (isFormatYUV(gmeta.format)) {
191         mPreprocessedInfo.sourceCrop.top = (int)mSourceCrop.top;
192         mPreprocessedInfo.sourceCrop.left = (int)mSourceCrop.left;
193         mPreprocessedInfo.sourceCrop.bottom = (int)(mSourceCrop.bottom + 0.9);
194         mPreprocessedInfo.sourceCrop.right = (int)(mSourceCrop.right + 0.9);
195         mPreprocessedInfo.preProcessed = true;
196     }
197 
198     if (isFormatYUV(gmeta.format)) {
199 
200         ExynosVideoMeta *metaData = NULL;
201         int priv_fd = -1;
202 
203         if (gmeta.flags & VendorGraphicBufferMeta::PRIV_FLAGS_USES_2PRIVATE_DATA)
204             priv_fd = gmeta.fd1;
205         else if (gmeta.flags & VendorGraphicBufferMeta::PRIV_FLAGS_USES_3PRIVATE_DATA)
206             priv_fd = gmeta.fd2;
207 
208         if (priv_fd >= 0) {
209 
210             metaData = (ExynosVideoMeta*)mmap(0, sizeof(ExynosVideoMeta), PROT_READ|PROT_WRITE, MAP_SHARED, priv_fd, 0);
211 
212             if (metaData == NULL) {
213                 HWC_LOGE(mDisplay, "Layer's metadata is NULL!!");
214             } else if (metaData == MAP_FAILED) {
215                 HWC_LOGE(mDisplay, "Layer's metadata map failed!!");
216             } else {
217                 mBufferHasMetaParcel = true;
218                 if ((metaData->eType & VIDEO_INFO_TYPE_HDR_STATIC) ||
219                         (metaData->eType & VIDEO_INFO_TYPE_HDR_DYNAMIC)) {
220                     if (allocMetaParcel() == NO_ERROR) {
221                         mMetaParcel->eType = metaData->eType;
222                         if (metaData->eType & VIDEO_INFO_TYPE_HDR_STATIC) {
223                             mMetaParcel->sHdrStaticInfo = metaData->sHdrStaticInfo;
224                             HDEBUGLOGD(eDebugLayer, "HWC2: Static metadata min(%d), max(%d)",
225                                     mMetaParcel->sHdrStaticInfo.sType1.mMinDisplayLuminance,
226                                     mMetaParcel->sHdrStaticInfo.sType1.mMaxDisplayLuminance);
227                         }
228                         if (metaData->eType & VIDEO_INFO_TYPE_HDR_DYNAMIC) {
229                             /* Reserved field for dynamic meta data */
230                             /* Currently It's not be used not only HWC but also OMX */
231                             mMetaParcel->sHdrDynamicInfo = metaData->sHdrDynamicInfo;
232                             HDEBUGLOGD(eDebugLayer, "HWC2: Layer has dynamic metadata");
233                         }
234                     }
235                 }
236                 if (metaData->eType & VIDEO_INFO_TYPE_INTERLACED) {
237                     mPreprocessedInfo.interlacedType = metaData->data.dec.nInterlacedType;
238                     if (mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_BT) {
239                         if ((int)mSourceCrop.left < (int)(gmeta.stride)) {
240                             mPreprocessedInfo.sourceCrop.left = (int)mSourceCrop.left + gmeta.stride;
241                             mPreprocessedInfo.sourceCrop.right = (int)mSourceCrop.right + gmeta.stride;
242                         }
243                     }
244                     if (mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_TB ||
245                             mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_BT) {
246                         mPreprocessedInfo.sourceCrop.top = (int)(mSourceCrop.top)/2;
247                         mPreprocessedInfo.sourceCrop.bottom = (int)(mSourceCrop.bottom)/2;
248                     }
249                 }
250                 if (metaData->eType & VIDEO_INFO_TYPE_CHECK_PIXEL_FORMAT) {
251                     mPreprocessedInfo.mUsePrivateFormat = true;
252                     mPreprocessedInfo.mPrivateFormat = metaData->nPixelFormat;
253                 }
254                 munmap(metaData, sizeof(ExynosVideoMeta));
255             }
256         }
257         mPreprocessedInfo.preProcessed = true;
258     }
259 
260     exynos_image src_img;
261     exynos_image dst_img;
262     setSrcExynosImage(&src_img);
263     setDstExynosImage(&dst_img);
264     ExynosMPP *exynosMPPVG = nullptr;
265     if (isFormatYUV(gmeta.format)) {
266         auto otfMPPs = ExynosResourceManager::getOtfMPPs();
267         auto mpp_it = std::find_if(otfMPPs.begin(), otfMPPs.end(),
268                 [&src_img](auto m) { return m->isSrcFormatSupported(src_img); });
269         exynosMPPVG = mpp_it == otfMPPs.end() ? nullptr : *mpp_it;
270     }
271 
272     /* Set HDR Flag */
273     if(hasHdrInfo(src_img)) mIsHdrLayer = true;
274 
275     if (isFormatYUV(gmeta.format) && exynosMPPVG) {
276         /*
277          * layer's sourceCrop should be aligned
278          */
279         uint32_t srcCropXAlign = exynosMPPVG->getSrcXOffsetAlign(src_img);
280         uint32_t srcCropYAlign = exynosMPPVG->getSrcYOffsetAlign(src_img);
281         uint32_t srcCropWidthAlign = exynosMPPVG->getSrcWidthAlign(src_img);
282         uint32_t srcCropHeightAlign = exynosMPPVG->getSrcHeightAlign(src_img);
283         mPreprocessedInfo.sourceCrop.left = pixel_align((int)mPreprocessedInfo.sourceCrop.left, srcCropXAlign);
284         mPreprocessedInfo.sourceCrop.top = pixel_align((int)mPreprocessedInfo.sourceCrop.top, srcCropYAlign);
285         mPreprocessedInfo.sourceCrop.right = mPreprocessedInfo.sourceCrop.left +
286             pixel_align_down(WIDTH(mPreprocessedInfo.sourceCrop), srcCropWidthAlign);
287         mPreprocessedInfo.sourceCrop.bottom = mPreprocessedInfo.sourceCrop.top +
288             pixel_align_down(HEIGHT(mPreprocessedInfo.sourceCrop), srcCropHeightAlign);
289         mPreprocessedInfo.preProcessed = true;
290     }
291 
292     if (exynosMPPVG && ((getDrmMode(mLayerBuffer) != NO_DRM) ||
293         (mIsHdrLayer == true)))
294     {
295         if ((mDisplay->mDisplayControl.adjustDisplayFrame == true) &&
296             ((mSupportedMPPFlag & (MPP_LOGICAL_DPP_G | MPP_LOGICAL_DPP_VG | MPP_LOGICAL_DPP_VGFS | MPP_LOGICAL_DPP_VGRFS)) == 0))
297         {
298             /*
299              * M2mMPP should be used for DRM, HDR video
300              * layer's displayFrame is the source of DPP
301              */
302             uint32_t cropWidthAlign = exynosMPPVG->getSrcCropWidthAlign(src_img);
303             uint32_t cropHeightAlign = exynosMPPVG->getSrcCropHeightAlign(src_img);
304 
305             mPreprocessedInfo.displayFrame.right = mDisplayFrame.left +
306                 pixel_align(WIDTH(mDisplayFrame), cropWidthAlign);
307             mPreprocessedInfo.displayFrame.bottom = mDisplayFrame.top +
308                 pixel_align(HEIGHT(mDisplayFrame), cropHeightAlign);
309 
310             if (mPreprocessedInfo.displayFrame.right > (int)(mDisplay->mXres)) {
311                 mPreprocessedInfo.displayFrame.left = mDisplay->mXres -
312                     pixel_align(WIDTH(mPreprocessedInfo.displayFrame), cropWidthAlign);
313                 mPreprocessedInfo.displayFrame.right = mDisplay->mXres;
314             }
315 
316             if (mPreprocessedInfo.displayFrame.bottom > (int)(mDisplay->mYres)) {
317                 mPreprocessedInfo.displayFrame.top = mDisplay->mYres -
318                     pixel_align_down(HEIGHT(mPreprocessedInfo.displayFrame), cropHeightAlign);
319                 mPreprocessedInfo.displayFrame.bottom = mDisplay->mYres;
320             }
321         }
322 
323         uint32_t minDstWidth = exynosMPPVG->getDstMinWidth(dst_img);
324         uint32_t minDstHeight = exynosMPPVG->getDstMinHeight(dst_img);
325         if ((uint32_t)WIDTH(mDisplayFrame) < minDstWidth) {
326             ALOGI("%s DRM layer displayFrame width %d is smaller than otf minWidth %d",
327                     mDisplay->mDisplayName.string(),
328                     WIDTH(mDisplayFrame), minDstWidth);
329             mPreprocessedInfo.displayFrame.right = mDisplayFrame.left +
330                 pixel_align(WIDTH(mDisplayFrame), minDstWidth);
331 
332             if (mPreprocessedInfo.displayFrame.right > (int)(mDisplay->mXres)) {
333                 mPreprocessedInfo.displayFrame.left = mDisplay->mXres -
334                     pixel_align(WIDTH(mPreprocessedInfo.displayFrame), minDstWidth);
335                 mPreprocessedInfo.displayFrame.right = mDisplay->mXres;
336             }
337         }
338         if ((uint32_t)HEIGHT(mDisplayFrame) < minDstHeight) {
339             ALOGI("%s DRM layer displayFrame height %d is smaller than vpp minHeight %d",
340                     mDisplay->mDisplayName.string(),
341                     HEIGHT(mDisplayFrame), minDstHeight);
342             mPreprocessedInfo.displayFrame.bottom = mDisplayFrame.top +
343                 pixel_align(HEIGHT(mDisplayFrame), minDstHeight);
344 
345             if (mPreprocessedInfo.displayFrame.bottom > (int)(mDisplay->mYres)) {
346                 mPreprocessedInfo.displayFrame.top = mDisplay->mYres -
347                     pixel_align(HEIGHT(mPreprocessedInfo.displayFrame), minDstHeight);
348                 mPreprocessedInfo.displayFrame.bottom = mDisplay->mYres;
349             }
350         }
351         mPreprocessedInfo.preProcessed = true;
352     }
353 
354     if (VendorGraphicBufferMeta::get_usage(mLayerBuffer) &
355                toUnderlying(AidlBufferUsage::FRONT_BUFFER)) {
356         priority = ePriorityMax;
357     } else if (getDrmMode(mLayerBuffer) != NO_DRM) {
358         priority = ePriorityMax;
359     } else if (mIsHdrLayer) {
360         if (isFormatRgb(gmeta.format))
361             priority = ePriorityMax;
362         else
363             priority = ePriorityHigh;
364     } else if (isFormatYUV(gmeta.format)) {
365         priority = ePriorityHigh;
366     } else if ((mDisplay->mDisplayControl.cursorSupport == true) &&
367                (mCompositionType == HWC2_COMPOSITION_CURSOR)) {
368         priority = ePriorityMid;
369     } else {
370         priority = ePriorityLow;
371     }
372 
373     if (mOverlayPriority != priority)
374         setGeometryChanged(GEOMETRY_LAYER_PRIORITY_CHANGED);
375 
376     mOverlayPriority = priority;
377 
378     return NO_ERROR;
379 }
380 
setCursorPosition(int32_t x,int32_t y)381 int32_t ExynosLayer::setCursorPosition(int32_t x, int32_t y) {
382     return mDisplay->setCursorPositionAsync(x, y);
383 }
384 
385 
setLayerBuffer(buffer_handle_t buffer,int32_t acquireFence)386 int32_t ExynosLayer::setLayerBuffer(buffer_handle_t buffer, int32_t acquireFence) {
387 
388     /* TODO : Exception here ? */
389     //TODO mGeometryChanged  here
390 
391     uint64_t internal_format = 0;
392 
393     if (mDisplay->mPlugState == false)
394         buffer = NULL;
395 
396     if (buffer != NULL) {
397         if (VendorGraphicBufferMeta::get_fd(buffer,0) < 0)
398             return HWC2_ERROR_BAD_LAYER;
399     }
400 
401     VendorGraphicBufferMeta gmeta(mLayerBuffer);
402     internal_format = gmeta.format;
403 
404     if ((mLayerBuffer == NULL) || (buffer == NULL))
405         setGeometryChanged(GEOMETRY_LAYER_UNKNOWN_CHANGED);
406     else {
407         if (getDrmMode(VendorGraphicBufferMeta::get_producer_usage(mLayerBuffer)) != getDrmMode(gmeta.producer_usage))
408             setGeometryChanged(GEOMETRY_LAYER_DRM_CHANGED);
409         if (VendorGraphicBufferMeta::get_format(mLayerBuffer) != gmeta.format)
410             setGeometryChanged(GEOMETRY_LAYER_FORMAT_CHANGED);
411         if ((VendorGraphicBufferMeta::get_usage(buffer) &
412                     toUnderlying(AidlBufferUsage::FRONT_BUFFER)) !=
413                 (VendorGraphicBufferMeta::get_usage(mLayerBuffer) &
414                     toUnderlying(AidlBufferUsage::FRONT_BUFFER)))
415             setGeometryChanged(GEOMETRY_LAYER_FRONT_BUFFER_USAGE_CHANGED);
416     }
417 
418     {
419         Mutex::Autolock lock(mDisplay->mDRMutex);
420         mLayerBuffer = buffer;
421         checkFps(mLastLayerBuffer != mLayerBuffer);
422     }
423     mPrevAcquireFence =
424             fence_close(mPrevAcquireFence, mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_UNDEFINED);
425     mAcquireFence = fence_close(mAcquireFence, mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_UNDEFINED);
426 
427     mAcquireFence = hwcCheckFenceDebug(mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_LAYER, acquireFence);
428     mPrevAcquireFence = hwcCheckFenceDebug(mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_LAYER,
429                                            hwc_dup(mAcquireFence, mDisplay, FENCE_TYPE_SRC_ACQUIRE,
430                                                    FENCE_IP_LAYER, true));
431     if (mReleaseFence >= 0)
432         HWC_LOGE(NULL, "Layer's release fence is not initialized");
433     mReleaseFence = -1;
434 #ifdef DISABLE_FENCE
435     if (mAcquireFence >= 0)
436         fence_close(mAcquireFence);
437     mAcquireFence = -1;
438 #endif
439     bool compressed = isAFBCCompressed(mLayerBuffer);
440     if (mCompressed != compressed)
441         setGeometryChanged(GEOMETRY_LAYER_COMPRESSED_CHANGED);
442     mCompressed = compressed;
443 
444     if (buffer != NULL) {
445         /*
446          * HAL_DATASPACE_V0_JFIF = HAL_DATASPACE_STANDARD_BT601_625 |
447          * HAL_DATASPACE_TRANSFER_SMPTE_170M | HAL_DATASPACE_RANGE_FULL,
448          */
449         if (gmeta.format == HAL_PIXEL_FORMAT_EXYNOS_YCrCb_420_SP_M_FULL)
450             setLayerDataspace(HAL_DATASPACE_V0_JFIF);
451     } else {
452         setLayerDataspace(HAL_DATASPACE_UNKNOWN);
453     }
454 
455     HDEBUGLOGD(eDebugFence,
456                "layers bufferHandle: %p, mDataSpace: 0x%8x, acquireFence: %d, afbc: %d, "
457                "internal_format: 0x%" PRIx64 "",
458                mLayerBuffer, mDataSpace, mAcquireFence, mCompressed, internal_format);
459 
460     return 0;
461 }
462 
463 
setLayerSurfaceDamage(hwc_region_t damage)464 int32_t ExynosLayer::setLayerSurfaceDamage(hwc_region_t damage) {
465 
466     mDamageNum = damage.numRects;
467     mDamageRects.clear();
468 
469     if (mDamageNum == 0) return 0;
470 
471     for (size_t i = 0; i<mDamageNum; i++){
472         mDamageRects.push_back(damage.rects[i]);
473     }
474 
475     return 0;
476 }
477 
setLayerBlendMode(int32_t mode)478 int32_t ExynosLayer::setLayerBlendMode(int32_t /*hwc2_blend_mode_t*/ mode) {
479 
480     //TODO mGeometryChanged  here
481     if (mode < 0)
482         return HWC2_ERROR_BAD_PARAMETER;
483     if (mBlending != mode)
484         setGeometryChanged(GEOMETRY_LAYER_BLEND_CHANGED);
485     mBlending = mode;
486     return HWC2_ERROR_NONE;
487 }
488 
489 
setLayerColor(hwc_color_t color)490 int32_t ExynosLayer::setLayerColor(hwc_color_t color) {
491     /* TODO : Implementation here */
492     mColor = color;
493     return 0;
494 }
495 
setLayerCompositionType(int32_t type)496 int32_t ExynosLayer::setLayerCompositionType(int32_t /*hwc2_composition_t*/ type) {
497 
498     if (type < 0)
499         return HWC2_ERROR_BAD_PARAMETER;
500 
501     // FIXME: HWC2_COMPOSITION_SCREENSHOT is not defined in AOSP
502     //        HWC guys should fix this.
503 #if 0
504     if (mDisplay->mType == HWC_DISPLAY_PRIMARY)
505         if (type == HWC2_COMPOSITION_SCREENSHOT)
506             type = HWC2_COMPOSITION_DEVICE;
507 #endif
508 
509     if (type != mCompositionType) {
510         setGeometryChanged(GEOMETRY_LAYER_TYPE_CHANGED);
511     }
512 
513     mCompositionType = type;
514 
515     return HWC2_ERROR_NONE;
516 }
517 
setLayerDataspace(int32_t dataspace)518 int32_t ExynosLayer::setLayerDataspace(int32_t /*android_dataspace_t*/ dataspace) {
519     android_dataspace currentDataSpace = (android_dataspace_t)dataspace;
520     if ((mLayerBuffer != NULL) && (VendorGraphicBufferMeta::get_format(mLayerBuffer) == HAL_PIXEL_FORMAT_EXYNOS_YCrCb_420_SP_M_FULL))
521         currentDataSpace = HAL_DATASPACE_V0_JFIF;
522     else {
523         /* Change legacy dataspace */
524         switch (dataspace) {
525         case HAL_DATASPACE_SRGB_LINEAR:
526             currentDataSpace = HAL_DATASPACE_V0_SRGB_LINEAR;
527             break;
528         case HAL_DATASPACE_SRGB:
529             currentDataSpace = HAL_DATASPACE_V0_SRGB;
530             break;
531         case HAL_DATASPACE_JFIF:
532             currentDataSpace = HAL_DATASPACE_V0_JFIF;
533             break;
534         case HAL_DATASPACE_BT601_625:
535             currentDataSpace = HAL_DATASPACE_V0_BT601_625;
536             break;
537         case HAL_DATASPACE_BT601_525:
538             currentDataSpace = HAL_DATASPACE_V0_BT601_525;
539             break;
540         case HAL_DATASPACE_BT709:
541             currentDataSpace = HAL_DATASPACE_V0_BT709;
542             break;
543         default:
544             currentDataSpace = (android_dataspace)dataspace;
545             break;
546         }
547     }
548 
549     if (currentDataSpace != mDataSpace) {
550         setGeometryChanged(GEOMETRY_LAYER_DATASPACE_CHANGED);
551         // invalidate metadata if dataspace is changed. need metadata update
552         // to be after dataspace update.
553         if (mMetaParcel != nullptr) {
554             mMetaParcel->eType = VIDEO_INFO_TYPE_INVALID;
555         }
556     }
557     mDataSpace = currentDataSpace;
558 
559     return HWC2_ERROR_NONE;
560 }
561 
setLayerDisplayFrame(hwc_rect_t frame)562 int32_t ExynosLayer::setLayerDisplayFrame(hwc_rect_t frame) {
563 
564     if ((frame.left != mDisplayFrame.left) ||
565         (frame.top != mDisplayFrame.top) ||
566         (frame.right != mDisplayFrame.right) ||
567         (frame.bottom != mDisplayFrame.bottom))
568         setGeometryChanged(GEOMETRY_LAYER_DISPLAYFRAME_CHANGED);
569     mDisplayFrame = frame;
570 
571     return HWC2_ERROR_NONE;
572 }
573 
setLayerPlaneAlpha(float alpha)574 int32_t ExynosLayer::setLayerPlaneAlpha(float alpha) {
575     if (alpha < 0.0f || alpha > 1.0f) {
576         ALOGE("%s: invalid alpha %f", __func__, alpha);
577         return HWC2_ERROR_BAD_PARAMETER;
578     }
579 
580     if ((mPlaneAlpha != alpha) && ((mPlaneAlpha == 0.0) || (alpha == 0.0)))
581         setGeometryChanged(GEOMETRY_LAYER_IGNORE_CHANGED);
582 
583     mPlaneAlpha = alpha;
584 
585     if (mPlaneAlpha > 0.0)
586         mLayerFlag &= ~(EXYNOS_HWC_IGNORE_LAYER);
587     else
588         mLayerFlag |= EXYNOS_HWC_IGNORE_LAYER;
589 
590     return HWC2_ERROR_NONE;
591 }
592 
setLayerSidebandStream(const native_handle_t * __unused stream)593 int32_t ExynosLayer::setLayerSidebandStream(const native_handle_t* __unused stream) {
594     return HWC2_ERROR_NONE;
595 }
596 
setLayerSourceCrop(hwc_frect_t crop)597 int32_t ExynosLayer::setLayerSourceCrop(hwc_frect_t crop) {
598 
599     if ((crop.left != mSourceCrop.left) ||
600         (crop.top != mSourceCrop.top) ||
601         (crop.right != mSourceCrop.right) ||
602         (crop.bottom != mSourceCrop.bottom)) {
603         setGeometryChanged(GEOMETRY_LAYER_SOURCECROP_CHANGED);
604         mSourceCrop = crop;
605     }
606 
607     return HWC2_ERROR_NONE;
608 }
609 
setLayerTransform(int32_t transform)610 int32_t ExynosLayer::setLayerTransform(int32_t /*hwc_transform_t*/ transform) {
611 
612     if (mTransform != transform) {
613         setGeometryChanged(GEOMETRY_LAYER_TRANSFORM_CHANGED);
614         mTransform = transform;
615     }
616 
617     return HWC2_ERROR_NONE;
618 }
619 
setLayerVisibleRegion(hwc_region_t visible)620 int32_t ExynosLayer::setLayerVisibleRegion(hwc_region_t visible) {
621 
622     mVisibleRegionScreen = visible;
623 
624     return HWC2_ERROR_NONE;
625 }
626 
setLayerZOrder(uint32_t z)627 int32_t ExynosLayer::setLayerZOrder(uint32_t z) {
628     if (mZOrder != z) {
629         setGeometryChanged(GEOMETRY_LAYER_ZORDER_CHANGED);
630         mZOrder = z;
631     }
632     return HWC2_ERROR_NONE;
633 }
634 
setLayerPerFrameMetadata(uint32_t numElements,const int32_t * keys,const float * metadata)635 int32_t ExynosLayer::setLayerPerFrameMetadata(uint32_t numElements,
636         const int32_t* /*hw2_per_frame_metadata_key_t*/ keys, const float* metadata)
637 {
638     if (allocMetaParcel() != NO_ERROR)
639         return -1;
640     unsigned int multipliedVal = 50000;
641     mMetaParcel->eType =
642         static_cast<ExynosVideoInfoType>(mMetaParcel->eType | VIDEO_INFO_TYPE_HDR_STATIC);
643     for (uint32_t i = 0; i < numElements; i++) {
644         HDEBUGLOGD(eDebugLayer, "HWC2: setLayerPerFrameMetadata key(%d), value(%7.5f)",
645                 keys[i], metadata[i]);
646         switch (keys[i]) {
647             case HWC2_DISPLAY_RED_PRIMARY_X:
648                 mMetaParcel->sHdrStaticInfo.sType1.mR.x =
649                     (unsigned int)(metadata[i] * multipliedVal);
650                 break;
651             case HWC2_DISPLAY_RED_PRIMARY_Y:
652                 mMetaParcel->sHdrStaticInfo.sType1.mR.y =
653                     (unsigned int)(metadata[i] * multipliedVal);
654                 break;
655             case HWC2_DISPLAY_GREEN_PRIMARY_X:
656                 mMetaParcel->sHdrStaticInfo.sType1.mG.x =
657                     (unsigned int)(metadata[i] * multipliedVal);
658                 break;
659             case HWC2_DISPLAY_GREEN_PRIMARY_Y:
660                 mMetaParcel->sHdrStaticInfo.sType1.mG.y =
661                     (unsigned int)(metadata[i] * multipliedVal);
662                 break;
663             case HWC2_DISPLAY_BLUE_PRIMARY_X:
664                 mMetaParcel->sHdrStaticInfo.sType1.mB.x =
665                     (unsigned int)(metadata[i] * multipliedVal);
666                 break;
667             case HWC2_DISPLAY_BLUE_PRIMARY_Y:
668                 mMetaParcel->sHdrStaticInfo.sType1.mB.y =
669                     (unsigned int)(metadata[i] * multipliedVal);
670                 break;
671             case HWC2_WHITE_POINT_X:
672                 mMetaParcel->sHdrStaticInfo.sType1.mW.x =
673                     (unsigned int)(metadata[i] * multipliedVal);
674                 break;
675             case HWC2_WHITE_POINT_Y:
676                 mMetaParcel->sHdrStaticInfo.sType1.mW.y =
677                     (unsigned int)(metadata[i] * multipliedVal);
678                 break;
679             case HWC2_MAX_LUMINANCE:
680                 mMetaParcel->sHdrStaticInfo.sType1.mMaxDisplayLuminance =
681                     (unsigned int)(metadata[i] * 10000);
682                 break;
683             case HWC2_MIN_LUMINANCE:
684                 mMetaParcel->sHdrStaticInfo.sType1.mMinDisplayLuminance =
685                     (unsigned int)(metadata[i] * 10000);
686                 break;
687             case HWC2_MAX_CONTENT_LIGHT_LEVEL:
688                 /* Should be checked */
689                 mMetaParcel->sHdrStaticInfo.sType1.mMaxContentLightLevel =
690                     (unsigned int)(metadata[i]);
691                 break;
692             case HWC2_MAX_FRAME_AVERAGE_LIGHT_LEVEL:
693                 /* Should be checked */
694                 mMetaParcel->sHdrStaticInfo.sType1.mMaxFrameAverageLightLevel =
695                     (unsigned int)(metadata[i]);
696                 break;
697             default:
698                 return HWC2_ERROR_UNSUPPORTED;
699         }
700     }
701     return NO_ERROR;
702 }
703 
setLayerPerFrameMetadataBlobs(uint32_t numElements,const int32_t * keys,const uint32_t * sizes,const uint8_t * metadata)704 int32_t ExynosLayer::setLayerPerFrameMetadataBlobs(uint32_t numElements, const int32_t* keys, const uint32_t* sizes,
705         const uint8_t* metadata)
706 {
707     const uint8_t *metadata_start = metadata;
708     for (uint32_t i = 0; i < numElements; i++) {
709         HDEBUGLOGD(eDebugLayer, "HWC2: setLayerPerFrameMetadataBlobs key(%d)", keys[i]);
710         switch (keys[i]) {
711         case HWC2_HDR10_PLUS_SEI:
712             if (allocMetaParcel() == NO_ERROR) {
713                 mMetaParcel->eType =
714                     static_cast<ExynosVideoInfoType>(mMetaParcel->eType | VIDEO_INFO_TYPE_HDR_DYNAMIC);
715                 ExynosHdrDynamicInfo *info = &(mMetaParcel->sHdrDynamicInfo);
716                 Exynos_parsing_user_data_registered_itu_t_t35(info, (void*)metadata_start,
717                                                               sizes[i]);
718             } else {
719                 ALOGE("Layer has no metaParcel!");
720                 return HWC2_ERROR_UNSUPPORTED;
721             }
722             break;
723         default:
724             return HWC2_ERROR_BAD_PARAMETER;
725         }
726         metadata_start += sizes[i];
727     }
728     return HWC2_ERROR_NONE;
729 }
730 
setLayerColorTransform(const float * matrix)731 int32_t ExynosLayer::setLayerColorTransform(const float* matrix)
732 {
733     mLayerColorTransform.enable = true;
734     for (uint32_t i = 0; i < TRANSFORM_MAT_SIZE; i++)
735     {
736         mLayerColorTransform.mat[i] = matrix[i];
737     }
738 
739     return 0;
740 }
741 
setLayerGenericMetadata(hwc2_layer_t __unused layer,uint32_t __unused keyLength,const char * __unused key,bool __unused mandatory,uint32_t __unused valueLength,const uint8_t * __unused value)742 int32_t ExynosLayer::setLayerGenericMetadata(hwc2_layer_t __unused layer,
743         uint32_t __unused keyLength, const char* __unused key,
744         bool __unused mandatory, uint32_t __unused valueLength, const uint8_t* __unused value)
745 {
746     return HWC2_ERROR_UNSUPPORTED;
747 }
748 
setLayerBrightness(float brightness)749 int32_t ExynosLayer::setLayerBrightness(float brightness) {
750     if (mDisplay->mBrightnessController == nullptr ||
751         !mDisplay->mBrightnessController->validateLayerBrightness(brightness)) {
752         return HWC2_ERROR_BAD_PARAMETER;
753     }
754 
755     if (mBrightness != brightness) {
756         // Trigger display validation in case client composition is needed.
757         setGeometryChanged(GEOMETRY_LAYER_WHITEPOINT_CHANGED);
758         mBrightness = brightness;
759     }
760     return HWC2_ERROR_NONE;
761 }
762 
setLayerBlockingRegion(const std::vector<hwc_rect_t> & blockingRegion)763 int32_t ExynosLayer::setLayerBlockingRegion(const std::vector<hwc_rect_t>& blockingRegion) {
764     hwc_rect_t maxRect;
765 
766     for (auto rect : blockingRegion) {
767         maxRect = std::max(maxRect, rect, [](const hwc_rect_t& lhs, const hwc_rect_t& rhs) {
768             return rectSize(lhs) < rectSize(rhs);
769         });
770     }
771 
772     mBlockingRect = maxRect;
773 
774     return HWC2_ERROR_NONE;
775 }
776 
resetValidateData()777 void ExynosLayer::resetValidateData()
778 {
779     mValidateCompositionType = HWC2_COMPOSITION_INVALID;
780     mOtfMPP = NULL;
781     mM2mMPP = NULL;
782     mOverlayInfo = 0x0;
783     mWindowIndex = 0;
784 }
785 
setSrcExynosImage(exynos_image * src_img)786 int32_t ExynosLayer::setSrcExynosImage(exynos_image *src_img)
787 {
788     buffer_handle_t handle = mLayerBuffer;
789     if (isDimLayer()) {
790         src_img->format = HAL_PIXEL_FORMAT_RGBA_8888;
791         src_img->usageFlags = 0xb00;
792         src_img->bufferHandle = 0;
793 
794         src_img->x = 0;
795         src_img->y = 0;
796 
797         if (mDisplay != NULL) {
798             src_img->fullWidth = src_img->w = mDisplay->mXres;
799             src_img->fullHeight = src_img->h = mDisplay->mYres;
800         } else {
801             src_img->fullWidth = src_img->w = 1440;
802             src_img->fullHeight = src_img->h = 2560;
803         }
804 
805         src_img->layerFlags = mLayerFlag;
806         src_img->acquireFenceFd = mAcquireFence;
807         src_img->releaseFenceFd = -1;
808         src_img->dataSpace = HAL_DATASPACE_V0_SRGB;
809         src_img->blending = mBlending;
810         src_img->transform = mTransform;
811         src_img->compressed = mCompressed;
812         src_img->planeAlpha = mPlaneAlpha;
813         src_img->zOrder = mZOrder;
814 
815 
816         return NO_ERROR;
817     }
818 
819     if (handle == NULL) {
820         src_img->fullWidth = 0;
821         src_img->fullHeight = 0;
822         src_img->format = 0;
823         src_img->usageFlags = 0x0;
824         src_img->bufferHandle = handle;
825     } else {
826         VendorGraphicBufferMeta gmeta(handle);
827 
828         if ((mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_TB) ||
829             (mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_BT))
830         {
831             src_img->fullWidth = (gmeta.stride * 2);
832             src_img->fullHeight = pixel_align_down((gmeta.vstride / 2), 2);
833         } else {
834             src_img->fullWidth = gmeta.stride;
835             src_img->fullHeight = gmeta.vstride;
836         }
837         if (!mPreprocessedInfo.mUsePrivateFormat)
838             src_img->format = gmeta.format;
839         else
840             src_img->format = mPreprocessedInfo.mPrivateFormat;
841         src_img->usageFlags = gmeta.producer_usage;
842         src_img->bufferHandle = handle;
843     }
844     src_img->x = (int)mPreprocessedInfo.sourceCrop.left;
845     src_img->y = (int)mPreprocessedInfo.sourceCrop.top;
846     src_img->w = (int)mPreprocessedInfo.sourceCrop.right - (int)mPreprocessedInfo.sourceCrop.left;
847     src_img->h = (int)mPreprocessedInfo.sourceCrop.bottom - (int)mPreprocessedInfo.sourceCrop.top;
848     if ((mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_TB) ||
849         (mPreprocessedInfo.interlacedType == V4L2_FIELD_INTERLACED_BT))
850     {
851         while ((src_img->h % 2 != 0) ||
852                (src_img->h > src_img->fullHeight)) {
853             src_img->h -= 1;
854         }
855     }
856     src_img->layerFlags = mLayerFlag;
857     src_img->acquireFenceFd = mAcquireFence;
858     src_img->releaseFenceFd = -1;
859 
860     src_img->dataSpace = mDataSpace;
861     if(src_img->dataSpace == HAL_DATASPACE_UNKNOWN)
862         src_img->dataSpace = HAL_DATASPACE_V0_SRGB;
863 
864     src_img->blending = mBlending;
865     src_img->transform = mTransform;
866     src_img->compressed = mCompressed;
867     src_img->planeAlpha = mPlaneAlpha;
868     src_img->zOrder = mZOrder;
869     /* Copy HDR metadata */
870     memset(&(src_img->metaParcel), 0, sizeof(src_img->metaParcel));
871     src_img->metaType = VIDEO_INFO_TYPE_INVALID;
872     if (mMetaParcel != NULL) {
873         memcpy(&(src_img->metaParcel), mMetaParcel, sizeof(src_img->metaParcel));
874         src_img->metaType = mMetaParcel->eType;
875         src_img->hasMetaParcel = true;
876     } else {
877         src_img->hasMetaParcel = false;
878     }
879 
880     src_img->needColorTransform = mLayerColorTransform.enable;
881 
882     return NO_ERROR;
883 }
884 
setDstExynosImage(exynos_image * dst_img)885 int32_t ExynosLayer::setDstExynosImage(exynos_image *dst_img)
886 {
887     buffer_handle_t handle = mLayerBuffer;
888 
889     if (handle == NULL) {
890         dst_img->usageFlags = 0x0;
891     } else {
892         dst_img->usageFlags = VendorGraphicBufferMeta::get_producer_usage(handle);
893     }
894 
895     if (isDimLayer()) {
896         dst_img->usageFlags = 0xb00;
897     }
898 
899     dst_img->format = DEFAULT_MPP_DST_FORMAT;
900     dst_img->x = mPreprocessedInfo.displayFrame.left;
901     dst_img->y = mPreprocessedInfo.displayFrame.top;
902     dst_img->w = (mPreprocessedInfo.displayFrame.right - mPreprocessedInfo.displayFrame.left);
903     dst_img->h = (mPreprocessedInfo.displayFrame.bottom - mPreprocessedInfo.displayFrame.top);
904     dst_img->layerFlags = mLayerFlag;
905     dst_img->acquireFenceFd = -1;
906     dst_img->releaseFenceFd = -1;
907     dst_img->bufferHandle = NULL;
908     dst_img->dataSpace = HAL_DATASPACE_UNKNOWN;
909     if (mDisplay != NULL) {
910         dst_img->fullWidth = mDisplay->mXres;
911         dst_img->fullHeight = mDisplay->mYres;
912         if (mDisplay->mColorMode != HAL_COLOR_MODE_NATIVE) {
913             dst_img->dataSpace = colorModeToDataspace(mDisplay->mColorMode);
914         } else {
915             if (hasHdrInfo(mDataSpace)) {
916                 android_dataspace hdrDataSpace =
917                     (android_dataspace)(HAL_DATASPACE_STANDARD_DCI_P3 | HAL_DATASPACE_TRANSFER_GAMMA2_2 | HAL_DATASPACE_RANGE_LIMITED);
918                 if (mDisplay->mType == HWC_DISPLAY_EXTERNAL) {
919                     ExynosExternalDisplay *externalDisplay = (ExynosExternalDisplay*)mDisplay;
920                     if (externalDisplay->mExternalHdrSupported == true)
921                         dst_img->dataSpace = HAL_DATASPACE_UNKNOWN;
922                     else
923                         dst_img->dataSpace = hdrDataSpace;
924                 } else {
925                     dst_img->dataSpace = hdrDataSpace;
926                 }
927             }
928         }
929     } else {
930         HWC_LOGE(NULL, "mDisplay is NULL");
931     }
932     dst_img->blending = mBlending;
933     dst_img->transform = 0;
934     dst_img->compressed = 0;
935     dst_img->planeAlpha = mPlaneAlpha;
936     dst_img->zOrder = mZOrder;
937 
938     /* Copy HDR metadata */
939     memset(&(dst_img->metaParcel), 0, sizeof(dst_img->metaParcel));
940     dst_img->metaType = VIDEO_INFO_TYPE_INVALID;
941     if (mMetaParcel != NULL) {
942         memcpy(&(dst_img->metaParcel), mMetaParcel, sizeof(dst_img->metaParcel));
943         dst_img->metaType = mMetaParcel->eType;
944         dst_img->hasMetaParcel = true;
945     } else {
946         dst_img->hasMetaParcel = false;
947     }
948 
949     return NO_ERROR;
950 }
951 
resetAssignedResource()952 int32_t ExynosLayer::resetAssignedResource()
953 {
954     int32_t ret = NO_ERROR;
955     if (mM2mMPP != NULL) {
956         HDEBUGLOGD(eDebugResourceManager, "\t\t %s mpp is reset", mM2mMPP->mName.string());
957         mM2mMPP->resetAssignedState(this);
958         mM2mMPP = NULL;
959     }
960     if (mOtfMPP != NULL) {
961         HDEBUGLOGD(eDebugResourceManager, "\t\t %s mpp is reset", mOtfMPP->mName.string());
962         mOtfMPP->resetAssignedState();
963         mOtfMPP = NULL;
964     }
965     return ret;
966 }
967 
checkBtsCap(const uint32_t bts_refresh_rate)968 bool ExynosLayer::checkBtsCap(const uint32_t bts_refresh_rate) {
969     if (mOtfMPP == nullptr) return true;
970 
971     exynos_image src_img;
972     exynos_image dst_img;
973     setSrcExynosImage(&src_img);
974     setDstExynosImage(&dst_img);
975     if (mOtfMPP->checkSpecificRestriction(bts_refresh_rate, src_img, dst_img)) {
976         return false;
977     }
978 
979     const bool isPerpendicular = !!(src_img.transform & HAL_TRANSFORM_ROT_90);
980     const uint32_t srcWidth = isPerpendicular ? src_img.h : src_img.w;
981     const uint32_t srcHeight = isPerpendicular ? src_img.w : src_img.h;
982     const bool scaleDown = (srcWidth > dst_img.w || srcHeight > dst_img.h);
983 
984     if (!scaleDown) return true;
985 
986     const float resolution = float(src_img.w) * float(src_img.h) * bts_refresh_rate / 1000;
987 
988     return mOtfMPP->checkDownscaleCap(resolution, float(dst_img.h) / float(mDisplay->mYres));
989 }
990 
setSrcAcquireFence()991 void ExynosLayer::setSrcAcquireFence() {
992     if (mAcquireFence == -1 && mPrevAcquireFence != -1) {
993         mAcquireFence = hwcCheckFenceDebug(mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_LAYER,
994                                            hwc_dup(mPrevAcquireFence, mDisplay,
995                                                    FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_LAYER));
996     } else if (mAcquireFence != -1) {
997         setFenceInfo(mAcquireFence, mDisplay, FENCE_TYPE_SRC_ACQUIRE, FENCE_IP_LAYER,
998                      HwcFenceDirection::FROM);
999     }
1000 }
1001 
dump(String8 & result)1002 void ExynosLayer::dump(String8& result)
1003 {
1004     int format = HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED;
1005     int32_t fd, fd1, fd2;
1006     if (mLayerBuffer != NULL)
1007     {
1008         VendorGraphicBufferMeta gmeta(mLayerBuffer);
1009         format = gmeta.format;
1010         fd = gmeta.fd;
1011         fd1 = gmeta.fd1;
1012         fd2 = gmeta.fd2;
1013     } else {
1014         format = HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED;
1015         fd = -1;
1016         fd1 = -1;
1017         fd2 = -1;
1018     }
1019 
1020     {
1021         TableBuilder tb;
1022         tb.add("zOrder", mZOrder)
1023           .add("priority", mOverlayPriority);
1024         if (mCompositionType == HWC2_COMPOSITION_SOLID_COLOR) {
1025             tb.add("color", std::vector<uint64_t>({mColor.r, mColor.g, mColor.b, mColor.a}), true);
1026         } else {
1027             tb.add("handle", mLayerBuffer)
1028               .add("fd", std::vector<int>({fd, fd1, fd2}))
1029               .add("AFBC", static_cast<bool>(mCompressed));
1030         }
1031         tb.add("format", getFormatStr(format, mCompressed ? AFBC : 0).string())
1032           .add("dataSpace", mDataSpace, true)
1033           .add("colorTr", mLayerColorTransform.enable)
1034           .add("blend", mBlending, true)
1035           .add("planeAlpha", mPlaneAlpha)
1036           .add("fps", mFps);
1037         result.append(tb.build().c_str());
1038     }
1039 
1040     result.append(TableBuilder()
1041                           .add("sourceCrop",
1042                                std::vector<double>({mPreprocessedInfo.sourceCrop.left,
1043                                                     mPreprocessedInfo.sourceCrop.top,
1044                                                     mPreprocessedInfo.sourceCrop.right,
1045                                                     mPreprocessedInfo.sourceCrop.bottom}))
1046                           .add("dispFrame",
1047                                std::vector<int>({mPreprocessedInfo.displayFrame.left,
1048                                                  mPreprocessedInfo.displayFrame.top,
1049                                                  mPreprocessedInfo.displayFrame.right,
1050                                                  mPreprocessedInfo.displayFrame.bottom}))
1051                           .add("blockRect",
1052                                std::vector<int>({mBlockingRect.left, mBlockingRect.top,
1053                                                  mBlockingRect.right, mBlockingRect.bottom}))
1054                           .add("tr", mTransform, true)
1055                           .add("windowIndex", mWindowIndex)
1056                           .add("type", mCompositionType)
1057                           .add("exynosType", mExynosCompositionType)
1058                           .add("validateType", mValidateCompositionType)
1059                           .add("overlayInfo", mOverlayInfo, true)
1060                           .build()
1061                           .c_str());
1062 
1063     result.append(TableBuilder()
1064                           .add("MPPFlag", mSupportedMPPFlag, true)
1065                           .add("dim ratio", mPreprocessedInfo.sdrDimRatio)
1066                           .build()
1067                           .c_str());
1068 
1069     if ((mDisplay != NULL) && (mDisplay->mResourceManager != NULL)) {
1070         result.appendFormat("MPPFlags for otfMPP\n");
1071         for (uint32_t i = 0; i < mDisplay->mResourceManager->getOtfMPPSize(); i++) {
1072             result.appendFormat("[%s: 0x%" PRIx64 "] ", mDisplay->mResourceManager->getOtfMPP(i)->mName.string(),
1073                     mCheckMPPFlag[mDisplay->mResourceManager->getOtfMPP(i)->mLogicalType]);
1074         }
1075         result.appendFormat("\n");
1076         result.appendFormat("MPPFlags for m2mMPP\n");
1077         for (uint32_t i = 0; i < mDisplay->mResourceManager->getM2mMPPSize(); i++) {
1078             result.appendFormat("[%s: 0x%" PRIx64 "] ", mDisplay->mResourceManager->getM2mMPP(i)->mName.string(),
1079                     mCheckMPPFlag[mDisplay->mResourceManager->getM2mMPP(i)->mLogicalType]);
1080             if ((i!=0) && (i%4==0)) result.appendFormat("\n");
1081         }
1082         result.appendFormat("\n");
1083     }
1084     result.appendFormat("acquireFence: %d\n", mAcquireFence);
1085     if ((mOtfMPP == NULL) && (mM2mMPP == NULL))
1086         result.appendFormat("\tresource is not assigned.\n");
1087     if (mOtfMPP != NULL)
1088         result.appendFormat("\tassignedMPP: %s\n", mOtfMPP->mName.string());
1089     if (mM2mMPP != NULL)
1090         result.appendFormat("\tassignedM2mMPP: %s\n", mM2mMPP->mName.string());
1091     result.appendFormat("\tdump midImg\n");
1092     dumpExynosImage(result, mMidImg);
1093 
1094 }
1095 
printLayer()1096 void ExynosLayer::printLayer()
1097 {
1098     int format = HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED;
1099     int32_t fd, fd1, fd2;
1100     String8 result;
1101     if (mLayerBuffer != NULL)
1102     {
1103         VendorGraphicBufferMeta gmeta(mLayerBuffer);
1104         format = gmeta.format;
1105         fd = gmeta.fd;
1106         fd1 = gmeta.fd1;
1107         fd2 = gmeta.fd2;
1108     } else {
1109         format = HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED;
1110         fd = -1;
1111         fd1 = -1;
1112         fd2 = -1;
1113     }
1114     result.appendFormat("handle: %p [fd: %d, %d, %d], acquireFence: %d, tr: 0x%2x, AFBC: %1d, dataSpace: 0x%8x, format: %s\n",
1115             mLayerBuffer, fd, fd1, fd2, mAcquireFence, mTransform, mCompressed, mDataSpace, getFormatStr(format, mCompressed? AFBC : 0).string());
1116     result.appendFormat("\tblend: 0x%4x, planeAlpha: %3.1f, zOrder: %d, color[0x%2x, 0x%2x, 0x%2x, 0x%2x]\n",
1117             mBlending, mPlaneAlpha, mZOrder, mColor.r, mColor.g, mColor.b, mColor.a);
1118     result.appendFormat("\tfps: %.2f, priority: %d, windowIndex: %d\n", mFps, mOverlayPriority,
1119                         mWindowIndex);
1120     result.appendFormat("\tsourceCrop[%7.1f,%7.1f,%7.1f,%7.1f], dispFrame[%5d,%5d,%5d,%5d]\n",
1121             mSourceCrop.left, mSourceCrop.top, mSourceCrop.right, mSourceCrop.bottom,
1122             mDisplayFrame.left, mDisplayFrame.top, mDisplayFrame.right, mDisplayFrame.bottom);
1123     result.appendFormat("\ttype: %2d, exynosType: %2d, validateType: %2d\n",
1124             mCompositionType, mExynosCompositionType, mValidateCompositionType);
1125     result.appendFormat("\toverlayInfo: 0x%8x, supportedMPPFlag: 0x%8x, geometryChanged: 0x%" PRIx64 "\n",
1126             mOverlayInfo, mSupportedMPPFlag, mGeometryChanged);
1127 
1128     if ((mDisplay != NULL) && (mDisplay->mResourceManager != NULL)) {
1129         result.appendFormat("MPPFlags for otfMPP\n");
1130         for (uint32_t i = 0; i < mDisplay->mResourceManager->getOtfMPPSize(); i++) {
1131             result.appendFormat("[%s: 0x%" PRIx64 "] ", mDisplay->mResourceManager->getOtfMPP(i)->mName.string(),
1132                     mCheckMPPFlag[mDisplay->mResourceManager->getOtfMPP(i)->mLogicalType]);
1133         }
1134         result.appendFormat("\n");
1135         result.appendFormat("MPPFlags for m2mMPP\n");
1136         for (uint32_t i = 0; i < mDisplay->mResourceManager->getM2mMPPSize(); i++) {
1137             result.appendFormat("[%s: 0x%" PRIx64 "] ", mDisplay->mResourceManager->getM2mMPP(i)->mName.string(),
1138                     mCheckMPPFlag[mDisplay->mResourceManager->getM2mMPP(i)->mLogicalType]);
1139             if ((i!=0) && (i%4==0)) result.appendFormat("\n");
1140         }
1141         result.appendFormat("\n");
1142     }
1143 
1144     ALOGD("%s", result.string());
1145     result.clear();
1146 
1147     if ((mOtfMPP == NULL) && (mM2mMPP == NULL))
1148         ALOGD("\tresource is not assigned.");
1149     if (mOtfMPP != NULL)
1150         ALOGD("\tassignedMPP: %s", mOtfMPP->mName.string());
1151     if (mM2mMPP != NULL)
1152         ALOGD("\tassignedM2mMPP: %s", mM2mMPP->mName.string());
1153     ALOGD("\t++ dump midImg ++");
1154     dumpExynosImage(result, mMidImg);
1155     ALOGD("%s", result.string());
1156 
1157 }
1158 
setGeometryChanged(uint64_t changedBit)1159 void ExynosLayer::setGeometryChanged(uint64_t changedBit)
1160 {
1161     mGeometryChanged |= changedBit;
1162     mDisplay->setGeometryChanged(changedBit);
1163 }
1164 
allocMetaParcel()1165 int ExynosLayer::allocMetaParcel()
1166 {
1167     /* Already allocated */
1168     if ((mMetaParcelFd >= 0) &&
1169         (mMetaParcel != NULL))
1170         return NO_ERROR;
1171 
1172     if (mMetaParcelFd < 0) {
1173          int ionFd = exynos_ion_open();
1174          if (ionFd >= 0) {
1175              mMetaParcelFd = exynos_ion_alloc(ionFd, sizeof(ExynosVideoMeta), EXYNOS_ION_HEAP_SYSTEM_MASK, 0);
1176              if (mMetaParcelFd < 0) {
1177                  ALOGE("Failed to ion alloc for metadata parcel");
1178                  return -1;
1179              }
1180              exynos_ion_close(ionFd);
1181          } else {
1182              ALOGE("Failed to open ion fd");
1183              return -1;
1184          }
1185     }
1186 
1187     mMetaParcel =
1188         (ExynosVideoMeta*)mmap(0, sizeof(ExynosVideoMeta), PROT_READ|PROT_WRITE, MAP_SHARED, mMetaParcelFd, 0);
1189     if (mMetaParcel == NULL) {
1190         ALOGE("Failed to map metadata parcel");
1191         return -1;
1192     }
1193 
1194     return NO_ERROR;
1195 }
1196 
isDimLayer()1197 bool ExynosLayer::isDimLayer()
1198 {
1199     if (mLayerFlag & EXYNOS_HWC_DIM_LAYER)
1200         return true;
1201     return false;
1202 }
1203