1 /*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "hdi_layer.h"
17 #include <unistd.h>
18 #include <cerrno>
19 #include "display_gralloc_private.h"
20
21
22 namespace OHOS {
23 namespace HDI {
24 namespace DISPLAY {
25 uint32_t HdiLayer::mIdleId = 0;
26 std::unordered_set<uint32_t> HdiLayer::mIdSets;
27
HdiLayerBuffer(const BufferHandle & hdl)28 HdiLayerBuffer::HdiLayerBuffer(const BufferHandle &hdl)
29 : mPhyAddr(hdl.phyAddr), mHeight(hdl.height), mWidth(hdl.width), mStride(hdl.stride), mFormat(hdl.format)
30 {
31 PriBufferHandle &hdlp = (PriBufferHandle&) hdl;
32 mFd = dup(hdl.fd);
33 mHandle = hdl;
34 if (mFd < 0) {
35 DISPLAY_LOGE("the fd : %{public}d dup failed errno %{public}d return:%{public}d gralloc id:%{public}llu",
36 hdl.fd, errno, mFd, hdlp.id);
37 }
38 }
39
~HdiLayerBuffer()40 HdiLayerBuffer::~HdiLayerBuffer()
41 {
42 DISPLAY_LOGD();
43 if (mFd >= 0) {
44 close(mFd);
45 }
46 }
47
operator =(const BufferHandle & right)48 HdiLayerBuffer &HdiLayerBuffer::operator = (const BufferHandle &right)
49 {
50 DISPLAY_LOGD();
51 if (mFd >= 0) {
52 close(mFd);
53 }
54 mFd = right.fd;
55 mPhyAddr = right.phyAddr;
56 mWidth = right.width;
57 mHeight = right.height;
58 mStride = right.stride;
59 mFormat = right.format;
60 return *this;
61 }
62
GetIdleId()63 uint32_t HdiLayer::GetIdleId()
64 {
65 const uint32_t oldIdleId = mIdleId;
66 uint32_t id = INVALIDE_LAYER_ID;
67 // ensure the mIdleId not INVALIDE_LAYER_ID
68 mIdleId = mIdleId % INVALIDE_LAYER_ID;
69 do {
70 auto iter = mIdSets.find(mIdleId);
71 if (iter == mIdSets.end()) {
72 id = mIdleId;
73 break;
74 }
75 mIdleId = (mIdleId + 1) % INVALIDE_LAYER_ID;
76 } while (oldIdleId != mIdleId);
77 mIdSets.emplace(id);
78 mIdleId++;
79 DISPLAY_LOGD("id %{public}d mIdleId %{public}d", id, mIdleId);
80 return id;
81 }
82
Init()83 int32_t HdiLayer::Init()
84 {
85 DISPLAY_LOGD();
86 uint32_t id = GetIdleId();
87 DISPLAY_CHK_RETURN((id == INVALIDE_LAYER_ID), DISPLAY_FAILURE, DISPLAY_LOGE("have no id to used"));
88 mId = id;
89 return DISPLAY_SUCCESS;
90 }
91
SetLayerSize(IRect * rect)92 int32_t HdiLayer::SetLayerSize(IRect *rect)
93 {
94 DISPLAY_CHK_RETURN((rect == nullptr), DISPLAY_NULL_PTR, DISPLAY_LOGE("in rect is nullptr"));
95 DISPLAY_LOGD(" displayRect x: %{public}d y : %{public}d w : %{public}d h : %{public}d", rect->x, rect->y, rect->w,
96 rect->h);
97 mDisplayRect = *rect;
98 return DISPLAY_SUCCESS;
99 }
100
SetLayerCrop(IRect * rect)101 int32_t HdiLayer::SetLayerCrop(IRect *rect)
102 {
103 DISPLAY_CHK_RETURN((rect == nullptr), DISPLAY_NULL_PTR, DISPLAY_LOGE("in rect is nullptr"));
104 DISPLAY_LOGD("id : %{public}d crop x: %{public}d y : %{public}d w : %{public}d h : %{public}d", mId, rect->x,
105 rect->y, rect->w, rect->h);
106 mCrop = *rect;
107 return DISPLAY_SUCCESS;
108 }
109
SetLayerZorder(uint32_t zorder)110 void HdiLayer::SetLayerZorder(uint32_t zorder)
111 {
112 DISPLAY_LOGD("id : %{public}d zorder : %{public}d ", mId, zorder);
113 mZorder = zorder;
114 }
115
SetLayerPreMulti(bool preMul)116 int32_t HdiLayer::SetLayerPreMulti(bool preMul)
117 {
118 DISPLAY_LOGD();
119 mPreMul = preMul;
120 return DISPLAY_SUCCESS;
121 }
122
SetLayerAlpha(LayerAlpha * alpha)123 int32_t HdiLayer::SetLayerAlpha(LayerAlpha *alpha)
124 {
125 DISPLAY_CHK_RETURN((alpha == nullptr), DISPLAY_NULL_PTR, DISPLAY_LOGE("in alpha is nullptr"));
126 DISPLAY_LOGD("enable alpha %{public}d galpha 0x%{public}x", alpha->enGlobalAlpha, alpha->gAlpha);
127 mAlpha = *alpha;
128 return DISPLAY_SUCCESS;
129 }
130
SetTransformMode(TransformType type)131 int32_t HdiLayer::SetTransformMode(TransformType type)
132 {
133 DISPLAY_LOGD("TransformType %{public}d", type);
134 mTransformType = type;
135 return DISPLAY_SUCCESS;
136 }
137
SetLayerDirtyRegion(IRect * region)138 int32_t HdiLayer::SetLayerDirtyRegion(IRect *region)
139 {
140 DISPLAY_CHK_RETURN((region == nullptr), DISPLAY_FAILURE, DISPLAY_LOGE("the in rect is null"));
141 DISPLAY_LOGD("id : %{public}d DirtyRegion x: %{public}d y : %{public}d w : %{public}d h : %{public}d", mId,
142 region->x, region->y, region->w, region->h);
143 return DISPLAY_SUCCESS;
144 }
145
SetLayerVisibleRegion(uint32_t num,IRect * rect)146 int32_t HdiLayer::SetLayerVisibleRegion(uint32_t num, IRect *rect)
147 {
148 DISPLAY_LOGD("id : %{public}d DirtyRegion x: %{public}d y : %{public}d w : %{public}d h : %{public}d", mId, rect->x,
149 rect->y, rect->w, rect->h);
150 return DISPLAY_SUCCESS;
151 }
152
SetLayerBuffer(const BufferHandle * buffer,int32_t fence)153 int32_t HdiLayer::SetLayerBuffer(const BufferHandle *buffer, int32_t fence)
154 {
155 DISPLAY_LOGD();
156 DISPLAY_CHK_RETURN((buffer == nullptr), DISPLAY_NULL_PTR, DISPLAY_LOGE("buffer is nullptr"));
157 std::unique_ptr<HdiLayerBuffer> layerbuffer = std::make_unique<HdiLayerBuffer>(*buffer);
158 mHdiBuffer = std::move(layerbuffer);
159 mAcquireFence = dup(fence);
160 return DISPLAY_SUCCESS;
161 }
162
SetLayerCompositionType(CompositionType type)163 int32_t HdiLayer::SetLayerCompositionType(CompositionType type)
164 {
165 DISPLAY_LOGD("CompositionType type %{public}d", type);
166 mCompositionType = type;
167 return DISPLAY_SUCCESS;
168 }
169
SetLayerBlendType(BlendType type)170 int32_t HdiLayer::SetLayerBlendType(BlendType type)
171 {
172 DISPLAY_LOGD("BlendType type %{public}d", type);
173 mBlendType = type;
174 return DISPLAY_SUCCESS;
175 }
176
SetLayerVisible(bool visible)177 int32_t HdiLayer::SetLayerVisible(bool visible)
178 {
179 DISPLAY_LOGD("SetLayerVisible type %{public}d", visible);
180 mVisible = visible;
181 return DISPLAY_SUCCESS;
182 }
183
SetPixel(const BufferHandle & handle,int x,int y,uint32_t color)184 void HdiLayer::SetPixel(const BufferHandle &handle, int x, int y, uint32_t color)
185 {
186 const int32_t pixelBytes = 4;
187 DISPLAY_CHK_RETURN_NOT_VALUE((handle.format <= 0),
188 DISPLAY_LOGE("CheckPixel do not support format %{public}d", handle.format));
189 DISPLAY_CHK_RETURN_NOT_VALUE((handle.virAddr == nullptr), DISPLAY_LOGE("CheckPixel viraddr is null must map it"));
190 DISPLAY_CHK_RETURN_NOT_VALUE((x < 0 || x >= handle.width),
191 DISPLAY_LOGE("CheckPixel invalid parameter x:%{public}d width:%{public}d", x, handle.width));
192 DISPLAY_CHK_RETURN_NOT_VALUE((y < 0 || y >= handle.height),
193 DISPLAY_LOGE("CheckPixel invalid parameter y:%{public}d height:%{public}d", y, handle.height));
194 int32_t position = y * handle.width + x;
195 if ((position * pixelBytes) > handle.size) {
196 DISPLAY_LOGE("the pixel postion outside\n");
197 }
198 uint32_t *pixel = reinterpret_cast<uint32_t *>(handle.virAddr) + position;
199 *pixel = color;
200 }
201
ClearColor(uint32_t color)202 void HdiLayer::ClearColor(uint32_t color)
203 {
204 DISPLAY_LOGD();
205 BufferHandle &handle = mHdiBuffer->mHandle;
206 for (int32_t x = 0; x < handle.width; x++) {
207 for (int32_t y = 0; y < handle.height; y++) {
208 SetPixel(handle, x, y, color);
209 }
210 }
211 }
212 } // namespace OHOS
213 } // namespace HDI
214 } // namespace DISPLAY
215