1 /* 2 * Copyright (c) 2023 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 #ifndef OHOS_HDI_DISPLAY_V1_0_DISPLAY_CMD_REQUESTER_H 17 #define OHOS_HDI_DISPLAY_V1_0_DISPLAY_CMD_REQUESTER_H 18 19 #include <unordered_map> 20 #include "base/hdi_smq.h" 21 #include "command_pack/command_data_packer.h" 22 #include "command_pack/command_data_unpacker.h" 23 #include "common/include/display_interface_utils.h" 24 #include "display_cmd_utils.h" 25 #include "hdifd_parcelable.h" 26 #include "hdf_log.h" 27 #include "v1_0/display_composer_type.h" 28 #include "v1_0/idisplay_composer.h" 29 30 namespace OHOS { 31 namespace HDI { 32 namespace Display { 33 namespace Composer { 34 namespace V1_0 { 35 using namespace OHOS::HDI::Base; 36 using namespace OHOS::HDI::Display::Composer::V1_0; 37 38 template <typename Transfer, typename CompHdi> 39 class DisplayCmdRequester { 40 public: DisplayCmdRequester(sptr<CompHdi> hdi)41 DisplayCmdRequester(sptr<CompHdi> hdi) 42 : initFlag_(false), 43 hdi_(hdi), 44 request_(nullptr), 45 reply_(nullptr) 46 { 47 } 48 Create(sptr<CompHdi> hdi)49 static std::unique_ptr<DisplayCmdRequester> Create(sptr<CompHdi> hdi) 50 { 51 DISPLAY_CHK_RETURN(hdi == nullptr, nullptr, HDF_LOGE("%{public}s: hdi is nullptr", __func__)); 52 auto requester = std::make_unique<DisplayCmdRequester>(hdi); 53 DISPLAY_CHK_RETURN(requester == nullptr, nullptr, 54 HDF_LOGE("%{public}s: CmdRequester is nullptr", __func__)); 55 auto ret = requester->Init(CmdUtils::INIT_ELEMENT_COUNT); 56 if (ret != HDF_SUCCESS) { 57 HDF_LOGE("DisplayCmdRequester init failed"); 58 return nullptr; 59 } 60 return requester; 61 } 62 Init(uint32_t eleCnt)63 int32_t Init(uint32_t eleCnt) 64 { 65 request_ = std::make_shared<Transfer>(eleCnt, SmqType::SYNCED_SMQ); 66 DISPLAY_CHK_RETURN(request_ == nullptr, HDF_FAILURE, 67 HDF_LOGE("%{public}s: request_ is nullptr", __func__)); 68 69 DISPLAY_CHK_RETURN(hdi_ == nullptr, HDF_FAILURE, 70 HDF_LOGE("%{public}s: hdi_ is nullptr", __func__)); 71 72 int32_t ret = hdi_->InitCmdRequest(request_); 73 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 74 HDF_LOGE("%{public}s: InitCmdRequest failure, ret=%{public}d", __func__, ret)); 75 76 if (requestPacker_.Init(request_->GetSize() << CmdUtils::MOVE_SIZE) == false) { 77 HDF_LOGE("%{public}s: requestPacker init failed", __func__); 78 return HDF_FAILURE; 79 } 80 81 replyData_.reset(new char[CmdUtils::INIT_ELEMENT_COUNT], std::default_delete<char[]>()); 82 if (replyData_ == nullptr) { 83 HDF_LOGE("replyData alloc failed."); 84 return HDF_FAILURE; 85 } 86 87 ret = hdi_->GetCmdReply(reply_); 88 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 89 HDF_LOGE("%{public}s: GetCmdReply failure, ret=%{public}d", __func__, ret)); 90 initFlag_ = true; 91 92 ret = CmdUtils::StartPack(CONTROL_CMD_REQUEST_BEGIN, requestPacker_); 93 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 94 HDF_LOGE("%{public}s: StartPack failed", __func__)); 95 96 return HDF_SUCCESS; 97 } 98 PrepareDisplayLayers(uint32_t devId,bool & needFlushFb)99 int32_t PrepareDisplayLayers(uint32_t devId, bool &needFlushFb) 100 { 101 uint32_t replyEleCnt; 102 std::vector<HdifdInfo> outFds; 103 104 int32_t ret = CmdUtils::StartSection(REQUEST_CMD_PREPARE_DISPLAY_LAYERS, requestPacker_); 105 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 106 107 ret = requestPacker_.WriteUint32(devId) ? HDF_SUCCESS : HDF_FAILURE; 108 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 109 110 ret = CmdUtils::EndSection(requestPacker_); 111 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 112 113 ret = CmdUtils::EndPack(requestPacker_); 114 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 115 116 ret = DoRequest(replyEleCnt, outFds); 117 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 118 119 ret = DoReplyResults(replyEleCnt, outFds, [&](void *data) -> int32_t { 120 needFlushFb = *(reinterpret_cast<bool *>(data)); 121 return HDF_SUCCESS; 122 }); 123 if (ret != HDF_SUCCESS) { 124 HDF_LOGE("DoReplyResults failure, ret=%{public}d", ret); 125 } 126 127 EXIT: 128 return PeriodDataReset() == HDF_SUCCESS ? ret : HDF_FAILURE; 129 } 130 SetDisplayClientBuffer(uint32_t devId,const BufferHandle * buffer,uint32_t seqNo,int32_t fence)131 int32_t SetDisplayClientBuffer(uint32_t devId, const BufferHandle* buffer, uint32_t seqNo, 132 int32_t fence) 133 { 134 int32_t ret = 0; 135 bool retBool = false; 136 size_t writePos = requestPacker_.ValidSize(); 137 138 do { 139 ret = CmdUtils::StartSection(REQUEST_CMD_SET_DISPLAY_CLIENT_BUFFER, requestPacker_); 140 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 141 HDF_LOGE("%{public}s: StartSection failed", __func__)); 142 143 retBool = requestPacker_.WriteUint32(devId); 144 DISPLAY_CHK_BREAK(retBool == false, 145 HDF_LOGE("%{public}s: write devId failed", __func__)); 146 147 ret = CmdUtils::BufferHandlePack(buffer, requestPacker_, requestHdiFds_); 148 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 149 HDF_LOGE("%{public}s: BufferHandlePack failed", __func__)); 150 151 retBool = requestPacker_.WriteUint32(seqNo); 152 DISPLAY_CHK_BREAK(retBool == false, 153 HDF_LOGE("%{public}s: write seqNo failed", __func__)); 154 155 ret = CmdUtils::FileDescriptorPack(fence, requestPacker_, requestHdiFds_); 156 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 157 HDF_LOGE("%{public}s: FileDescriptorPack failed", __func__)); 158 159 ret = CmdUtils::EndSection(requestPacker_); 160 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 161 HDF_LOGE("%{public}s: EndSection failed", __func__)); 162 } while (0); 163 164 if (retBool == false || ret != HDF_SUCCESS) { 165 requestPacker_.RollBack(writePos); 166 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 167 return HDF_FAILURE; 168 } 169 return HDF_SUCCESS; 170 } 171 SetDisplayClientDamage(uint32_t devId,std::vector<IRect> & rects)172 int32_t SetDisplayClientDamage(uint32_t devId, std::vector<IRect> &rects) 173 { 174 int32_t ret = 0; 175 bool retBool = false; 176 size_t writePos = requestPacker_.ValidSize(); 177 178 do { 179 ret = CmdUtils::StartSection(REQUEST_CMD_SET_DISPLAY_CLIENT_DAMAGE, requestPacker_); 180 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 181 HDF_LOGE("%{public}s: StartSection failed", __func__)); 182 183 ret = requestPacker_.WriteUint32(devId) ? HDF_SUCCESS : HDF_FAILURE; 184 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 185 HDF_LOGE("%{public}s: write devId failed", __func__)); 186 187 uint32_t vectSize = static_cast<uint32_t>(rects.size()); 188 retBool = requestPacker_.WriteUint32(vectSize); 189 DISPLAY_CHK_BREAK(retBool == false, 190 HDF_LOGE("%{public}s: write damage vector size failed", __func__)); 191 192 for (uint32_t i = 0; i < vectSize; i++) { 193 ret = CmdUtils::RectPack(rects[i], requestPacker_); 194 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 195 HDF_LOGE("%{public}s: RectPack failed", __func__)); 196 } 197 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 198 HDF_LOGE("%{public}s: RectPack failed, break!", __func__)); 199 200 ret = CmdUtils::EndSection(requestPacker_); 201 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 202 HDF_LOGE("%{public}s: EndSection failed", __func__)); 203 } while (0); 204 205 if (retBool == false || ret != HDF_SUCCESS) { 206 requestPacker_.RollBack(writePos); 207 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 208 return HDF_FAILURE; 209 } 210 return HDF_SUCCESS; 211 } 212 Commit(uint32_t devId,int32_t & fence)213 int32_t Commit(uint32_t devId, int32_t &fence) 214 { 215 uint32_t replyEleCnt = 0; 216 std::vector<HdifdInfo> outFds; 217 218 int32_t ret = CmdUtils::StartSection(REQUEST_CMD_COMMIT, requestPacker_); 219 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 220 221 ret = requestPacker_.WriteUint32(devId) ? HDF_SUCCESS : HDF_FAILURE; 222 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 223 224 ret = CmdUtils::EndSection(requestPacker_); 225 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 226 227 ret = CmdUtils::EndPack(requestPacker_); 228 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 229 230 ret = DoRequest(replyEleCnt, outFds); 231 DISPLAY_CHECK(ret != HDF_SUCCESS, goto EXIT); 232 233 ret = DoReplyResults(replyEleCnt, outFds, [&](void *data) -> int32_t { 234 fence = *(reinterpret_cast<int32_t *>(data)); 235 return HDF_SUCCESS; 236 }); 237 if (ret != HDF_SUCCESS) { 238 HDF_LOGE("DoReplyResults failure, ret=%{public}d", ret); 239 } 240 241 EXIT: 242 return PeriodDataReset() == HDF_SUCCESS ? ret : HDF_FAILURE; 243 } 244 SetLayerAlpha(uint32_t devId,uint32_t layerId,const LayerAlpha & alpha)245 int32_t SetLayerAlpha(uint32_t devId, uint32_t layerId, const LayerAlpha &alpha) 246 { 247 int32_t ret = 0; 248 bool retBool = false; 249 size_t writePos = requestPacker_.ValidSize(); 250 251 do { 252 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_ALPHA, requestPacker_); 253 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 254 HDF_LOGE("%{public}s: StartSection failed", __func__)); 255 256 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 257 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 258 HDF_LOGE("%{public}s: write devId failed", __func__)); 259 260 retBool = requestPacker_.WriteBool(alpha.enGlobalAlpha); 261 DISPLAY_CHK_BREAK(retBool == false, 262 HDF_LOGE("%{public}s: write enGlobalAlpha failed", __func__)); 263 264 retBool = requestPacker_.WriteBool(alpha.enPixelAlpha); 265 DISPLAY_CHK_BREAK(retBool == false, 266 HDF_LOGE("%{public}s: write enPixelAlpha failed", __func__)); 267 268 retBool = requestPacker_.WriteUint8(alpha.alpha0); 269 DISPLAY_CHK_BREAK(retBool == false, 270 HDF_LOGE("%{public}s: write alpha0 failed", __func__)); 271 272 retBool = requestPacker_.WriteUint8(alpha.alpha1); 273 DISPLAY_CHK_BREAK(retBool == false, 274 HDF_LOGE("%{public}s: write alpha1 failed", __func__)); 275 276 retBool = requestPacker_.WriteUint8(alpha.gAlpha); 277 DISPLAY_CHK_BREAK(retBool == false, 278 HDF_LOGE("%{public}s: write gAlpha failed", __func__)); 279 280 ret = CmdUtils::EndSection(requestPacker_); 281 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 282 HDF_LOGE("%{public}s: EndSection failed", __func__)); 283 } while (0); 284 285 if (retBool == false || ret != HDF_SUCCESS) { 286 requestPacker_.RollBack(writePos); 287 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 288 return HDF_FAILURE; 289 } 290 return HDF_SUCCESS; 291 } 292 SetLayerRegion(uint32_t devId,uint32_t layerId,const IRect & rect)293 int32_t SetLayerRegion(uint32_t devId, uint32_t layerId, const IRect &rect) 294 { 295 int32_t ret = 0; 296 size_t writePos = requestPacker_.ValidSize(); 297 298 do { 299 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_REGION, requestPacker_); 300 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 301 HDF_LOGE("%{public}s: StartSection failed", __func__)); 302 303 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 304 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 305 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 306 307 ret = CmdUtils::RectPack(rect, requestPacker_); 308 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 309 HDF_LOGE("%{public}s: RectPack failed", __func__)); 310 311 ret = CmdUtils::EndSection(requestPacker_); 312 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 313 HDF_LOGE("%{public}s: EndSection failed", __func__)); 314 } while (0); 315 316 if (ret != HDF_SUCCESS) { 317 requestPacker_.RollBack(writePos); 318 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 319 return HDF_FAILURE; 320 } 321 return HDF_SUCCESS; 322 } 323 SetLayerCrop(uint32_t devId,uint32_t layerId,const IRect & rect)324 int32_t SetLayerCrop(uint32_t devId, uint32_t layerId, const IRect &rect) 325 { 326 int32_t ret = 0; 327 size_t writePos = requestPacker_.ValidSize(); 328 329 do { 330 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_CROP, requestPacker_); 331 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 332 HDF_LOGE("%{public}s: StartSection failed", __func__)); 333 334 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 335 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 336 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 337 338 ret = CmdUtils::RectPack(rect, requestPacker_); 339 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 340 HDF_LOGE("%{public}s: RectPack failed", __func__)); 341 342 ret = CmdUtils::EndSection(requestPacker_); 343 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 344 HDF_LOGE("%{public}s: EndSection failed", __func__)); 345 } while (0); 346 347 if (ret != HDF_SUCCESS) { 348 requestPacker_.RollBack(writePos); 349 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 350 return HDF_FAILURE; 351 } 352 return HDF_SUCCESS; 353 } 354 SetLayerZorder(uint32_t devId,uint32_t layerId,uint32_t zorder)355 int32_t SetLayerZorder(uint32_t devId, uint32_t layerId, uint32_t zorder) 356 { 357 int32_t ret = 0; 358 bool retBool = false; 359 size_t writePos = requestPacker_.ValidSize(); 360 361 do { 362 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_ZORDER, requestPacker_); 363 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 364 HDF_LOGE("%{public}s: StartSection failed", __func__)); 365 366 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 367 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 368 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 369 370 retBool = requestPacker_.WriteUint32(zorder); 371 DISPLAY_CHK_BREAK(retBool == false, 372 HDF_LOGE("%{public}s: write zorder failed", __func__)); 373 374 ret = CmdUtils::EndSection(requestPacker_); 375 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 376 HDF_LOGE("%{public}s: EndSection failed", __func__)); 377 } while (0); 378 379 if (retBool == false || ret != HDF_SUCCESS) { 380 requestPacker_.RollBack(writePos); 381 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 382 return HDF_FAILURE; 383 } 384 return HDF_SUCCESS; 385 } 386 SetLayerPreMulti(uint32_t devId,uint32_t layerId,bool preMul)387 int32_t SetLayerPreMulti(uint32_t devId, uint32_t layerId, bool preMul) 388 { 389 int32_t ret = 0; 390 bool retBool = false; 391 size_t writePos = requestPacker_.ValidSize(); 392 393 do { 394 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_PREMULTI, requestPacker_); 395 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 396 HDF_LOGE("%{public}s: StartSection failed", __func__)); 397 398 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 399 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 400 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 401 402 retBool = requestPacker_.WriteBool(preMul); 403 DISPLAY_CHK_BREAK(retBool == false, 404 HDF_LOGE("%{public}s: write preMul failed", __func__)); 405 406 ret = CmdUtils::EndSection(requestPacker_); 407 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 408 HDF_LOGE("%{public}s: EndSection failed", __func__)); 409 } while (0); 410 411 if (retBool == false || ret != HDF_SUCCESS) { 412 requestPacker_.RollBack(writePos); 413 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 414 return HDF_FAILURE; 415 } 416 417 return HDF_SUCCESS; 418 } 419 SetLayerTransformMode(uint32_t devId,uint32_t layerId,TransformType type)420 int32_t SetLayerTransformMode(uint32_t devId, uint32_t layerId, TransformType type) 421 { 422 int32_t ret = 0; 423 bool retBool = false; 424 size_t writePos = requestPacker_.ValidSize(); 425 426 do { 427 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_TRANSFORM_MODE, requestPacker_); 428 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 429 HDF_LOGE("%{public}s: StartSection failed", __func__)); 430 431 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 432 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 433 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 434 435 retBool = requestPacker_.WriteInt32(type); 436 DISPLAY_CHK_BREAK(retBool == false, 437 HDF_LOGE("%{public}s: write transform-type failed", __func__)); 438 439 ret = CmdUtils::EndSection(requestPacker_); 440 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 441 HDF_LOGE("%{public}s: EndSection failed", __func__)); 442 } while (0); 443 444 if (retBool == false || ret != HDF_SUCCESS) { 445 requestPacker_.RollBack(writePos); 446 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 447 return HDF_FAILURE; 448 } 449 return HDF_SUCCESS; 450 } 451 SetLayerDirtyRegion(uint32_t devId,uint32_t layerId,const std::vector<IRect> & rects)452 int32_t SetLayerDirtyRegion(uint32_t devId, uint32_t layerId, const std::vector<IRect> &rects) 453 { 454 int32_t ret = 0; 455 bool retBool = false; 456 size_t writePos = requestPacker_.ValidSize(); 457 458 do { 459 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_DIRTY_REGION, requestPacker_); 460 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 461 HDF_LOGE("%{public}s: StartSection failed", __func__)); 462 463 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 464 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 465 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 466 467 uint32_t vSize = rects.size(); 468 retBool = requestPacker_.WriteUint32(vSize); 469 DISPLAY_CHK_BREAK(retBool == false, 470 HDF_LOGE("%{public}s: write vSize failed", __func__)); 471 for (uint32_t i = 0; i < vSize; i++) { 472 ret = CmdUtils::RectPack(rects[i], requestPacker_); 473 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 474 HDF_LOGE("%{public}s: RectPack failed", __func__)); 475 } 476 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 477 HDF_LOGE("%{public}s: RectPack failed, break", __func__)); 478 479 ret = CmdUtils::EndSection(requestPacker_); 480 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 481 HDF_LOGE("%{public}s: EndSection failed", __func__)); 482 } while (0); 483 484 if (retBool == false || ret != HDF_SUCCESS) { 485 requestPacker_.RollBack(writePos); 486 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 487 return HDF_FAILURE; 488 } 489 return HDF_SUCCESS; 490 } 491 SetLayerVisibleRegion(uint32_t devId,uint32_t layerId,std::vector<IRect> & rects)492 int32_t SetLayerVisibleRegion(uint32_t devId, uint32_t layerId, std::vector<IRect> &rects) 493 { 494 int32_t ret = 0; 495 bool retBool = false; 496 size_t writePos = requestPacker_.ValidSize(); 497 498 do { 499 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_VISIBLE_REGION, requestPacker_); 500 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 501 HDF_LOGE("%{public}s: StartSection failed", __func__)); 502 503 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 504 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 505 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 506 507 uint32_t vSize = rects.size(); 508 retBool = requestPacker_.WriteUint32(vSize); 509 DISPLAY_CHK_BREAK(retBool == false, 510 HDF_LOGE("%{public}s: write vSize failed", __func__)); 511 for (uint32_t i = 0; i < vSize; i++) { 512 ret = CmdUtils::RectPack(rects[i], requestPacker_); 513 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 514 HDF_LOGE("%{public}s: RectPack failed", __func__)); 515 } 516 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 517 HDF_LOGE("%{public}s: RectPack failed, break", __func__)); 518 519 ret = CmdUtils::EndSection(requestPacker_); 520 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 521 HDF_LOGE("%{public}s: EndSection failed", __func__)); 522 } while (0); 523 524 if (retBool == false || ret != HDF_SUCCESS) { 525 requestPacker_.RollBack(writePos); 526 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 527 return HDF_FAILURE; 528 } 529 return HDF_SUCCESS; 530 } 531 SetLayerBuffer(uint32_t devId,uint32_t layerId,const BufferHandle * buffer,uint32_t seqNo,int32_t fence,const std::vector<uint32_t> & deletingList)532 int32_t SetLayerBuffer(uint32_t devId, uint32_t layerId, const BufferHandle* buffer, uint32_t seqNo, 533 int32_t fence, const std::vector<uint32_t>& deletingList) 534 { 535 int32_t ret = 0; 536 bool retBool = false; 537 bool result = false; 538 size_t writePos = requestPacker_.ValidSize(); 539 540 do { 541 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_BUFFER, requestPacker_); 542 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 543 HDF_LOGE("%{public}s: StartSection failed", __func__)); 544 545 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 546 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 547 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 548 549 ret = CmdUtils::BufferHandlePack(buffer, requestPacker_, requestHdiFds_); 550 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 551 HDF_LOGE("%{public}s: BufferHandlePack failed", __func__)); 552 553 result = requestPacker_.WriteUint32(seqNo); 554 DISPLAY_CHK_BREAK(result == false, 555 HDF_LOGE("%{public}s: write seqNo failed", __func__)); 556 557 ret = CmdUtils::FileDescriptorPack(fence, requestPacker_, requestHdiFds_); 558 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 559 HDF_LOGE("%{public}s: FileDescriptorPack failed", __func__)); 560 // write deletingList 561 uint32_t vectSize = static_cast<uint32_t>(deletingList.size()); 562 retBool = requestPacker_.WriteUint32(vectSize); 563 DISPLAY_CHK_BREAK(retBool == false, 564 HDF_LOGE("%{public}s: write vector size failed", __func__)); 565 566 for (uint32_t i = 0; i < vectSize; i++) { 567 bool result = requestPacker_.WriteUint32(deletingList[i]); 568 DISPLAY_CHK_BREAK(result == false, 569 HDF_LOGE("%{public}s: write deletingList failed", __func__)); 570 } 571 DISPLAY_CHK_BREAK(result == false, 572 HDF_LOGE("%{public}s: write deletingList failed, break!", __func__)); 573 574 ret = CmdUtils::EndSection(requestPacker_); 575 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 576 HDF_LOGE("%{public}s: EndSection failed", __func__)); 577 } while (0); 578 579 if (retBool == false || result == false || ret != HDF_SUCCESS) { 580 requestPacker_.RollBack(writePos); 581 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 582 return HDF_FAILURE; 583 } 584 return HDF_SUCCESS; 585 } 586 SetLayerCompositionType(uint32_t devId,uint32_t layerId,CompositionType type)587 int32_t SetLayerCompositionType(uint32_t devId, uint32_t layerId, CompositionType type) 588 { 589 int32_t ret = 0; 590 bool retBool = false; 591 size_t writePos = requestPacker_.ValidSize(); 592 593 do { 594 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_COMPOSITION_TYPE, requestPacker_); 595 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 596 HDF_LOGE("%{public}s: StartSection failed", __func__)); 597 598 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 599 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 600 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 601 602 retBool = requestPacker_.WriteInt32(type); 603 DISPLAY_CHK_BREAK(retBool == false, 604 HDF_LOGE("%{public}s: write composition type failed", __func__)); 605 606 ret = CmdUtils::EndSection(requestPacker_); 607 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 608 HDF_LOGE("%{public}s: EndSection failed", __func__)); 609 } while (0); 610 611 if (retBool == false || ret != HDF_SUCCESS) { 612 requestPacker_.RollBack(writePos); 613 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 614 return HDF_FAILURE; 615 } 616 return HDF_SUCCESS; 617 } 618 SetLayerBlendType(uint32_t devId,uint32_t layerId,BlendType type)619 int32_t SetLayerBlendType(uint32_t devId, uint32_t layerId, BlendType type) 620 { 621 int32_t ret = 0; 622 bool retBool = false; 623 size_t writePos = requestPacker_.ValidSize(); 624 625 do { 626 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_BLEND_TYPE, requestPacker_); 627 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 628 HDF_LOGE("%{public}s: StartSection failed", __func__)); 629 630 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 631 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 632 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 633 634 retBool = requestPacker_.WriteInt32(type); 635 DISPLAY_CHK_BREAK(retBool == false, 636 HDF_LOGE("%{public}s: write blend type failed", __func__)); 637 638 ret = CmdUtils::EndSection(requestPacker_); 639 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 640 HDF_LOGE("%{public}s: EndSection failed", __func__)); 641 } while (0); 642 643 if (retBool == false || ret != HDF_SUCCESS) { 644 requestPacker_.RollBack(writePos); 645 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 646 return HDF_FAILURE; 647 } 648 return HDF_SUCCESS; 649 } 650 SetLayerMaskInfo(uint32_t devId,uint32_t layerId,const MaskInfo maskInfo)651 int32_t SetLayerMaskInfo(uint32_t devId, uint32_t layerId, const MaskInfo maskInfo) 652 { 653 int32_t ret = 0; 654 bool retBool = false; 655 size_t writePos = requestPacker_.ValidSize(); 656 657 do { 658 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_MASK_INFO, requestPacker_); 659 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 660 HDF_LOGE("%{public}s: StartSection failed", __func__)); 661 662 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 663 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 664 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 665 666 retBool = requestPacker_.WriteUint32(maskInfo); 667 DISPLAY_CHK_BREAK(retBool == false, 668 HDF_LOGE("%{public}s: write maskInfo failed", __func__)); 669 670 ret = CmdUtils::EndSection(requestPacker_); 671 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 672 HDF_LOGE("%{public}s: EndSection failed", __func__)); 673 } while (0); 674 675 if (retBool == false || ret != HDF_SUCCESS) { 676 requestPacker_.RollBack(writePos); 677 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 678 return HDF_FAILURE; 679 } 680 return HDF_SUCCESS; 681 } 682 SetLayerColor(uint32_t devId,uint32_t layerId,const LayerColor & layerColor)683 int32_t SetLayerColor(uint32_t devId, uint32_t layerId, const LayerColor& layerColor) 684 { 685 int32_t ret = 0; 686 size_t writePos = requestPacker_.ValidSize(); 687 688 do { 689 ret = CmdUtils::StartSection(REQUEST_CMD_SET_LAYER_COLOR, requestPacker_); 690 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 691 HDF_LOGE("%{public}s: StartSection failed", __func__)); 692 693 ret = CmdUtils::SetupDevice(devId, layerId, requestPacker_); 694 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 695 HDF_LOGE("%{public}s: SetupDevice failed", __func__)); 696 697 ret = CmdUtils::LayerColorPack(layerColor, requestPacker_); 698 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 699 HDF_LOGE("%{public}s: RectPack failed", __func__)); 700 701 ret = CmdUtils::EndSection(requestPacker_); 702 DISPLAY_CHK_BREAK(ret != HDF_SUCCESS, 703 HDF_LOGE("%{public}s: EndSection failed", __func__)); 704 } while (0); 705 706 if (ret != HDF_SUCCESS) { 707 requestPacker_.RollBack(writePos); 708 HDF_LOGE("%{public}s: writePos_ rollback", __func__); 709 return HDF_FAILURE; 710 } 711 return HDF_SUCCESS; 712 } 713 GetDisplayCompChange(uint32_t devId,std::vector<uint32_t> & layers,std::vector<int32_t> & types)714 int32_t GetDisplayCompChange(uint32_t devId, std::vector<uint32_t>& layers, std::vector<int32_t>& types) 715 { 716 layers = compChangeLayers_[devId]; 717 types = compChangeTypes_[devId]; 718 compChangeLayers_.erase(devId); 719 compChangeTypes_.erase(devId); 720 return HDF_SUCCESS; 721 } 722 protected: OnReplySetError(CommandDataUnpacker & replyUnpacker,std::unordered_map<int32_t,int32_t> & errMaps)723 int32_t OnReplySetError(CommandDataUnpacker& replyUnpacker, std::unordered_map<int32_t, int32_t> &errMaps) 724 { 725 uint32_t errCnt = 0; 726 bool retBool = replyUnpacker.ReadUint32(errCnt); 727 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, 728 HDF_LOGE("%{public}s: read err cnt failed", __func__)); 729 730 int32_t errCmd = -1; 731 int32_t errCode = -1; 732 for (; errCnt > 0; errCnt--) { 733 retBool = replyUnpacker.ReadInt32(errCmd); 734 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, 735 HDF_LOGE("%{public}s: read err cmd failed", __func__)); 736 retBool = replyUnpacker.ReadInt32(errCode); 737 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, 738 HDF_LOGE("%{public}s: read err code failed", __func__)); 739 errMaps.emplace(errCmd, errCode); 740 } 741 742 return HDF_SUCCESS; 743 } 744 OnReplyPrepareDisplayLayers(CommandDataUnpacker & replyUnpacker,bool & needFlushFb)745 int32_t OnReplyPrepareDisplayLayers(CommandDataUnpacker& replyUnpacker, bool &needFlushFb) 746 { 747 uint32_t devId = 0; 748 int32_t retBool = replyUnpacker.ReadUint32(devId); 749 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, HDF_LOGE("%{public}s: read devId failed", __func__)); 750 751 retBool = replyUnpacker.ReadBool(needFlushFb); 752 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, HDF_LOGE("%{public}s: read needFlushFb failed", __func__)); 753 // unpack layers vector 754 uint32_t vectSize = 0; 755 retBool = replyUnpacker.ReadUint32(vectSize); 756 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, HDF_LOGE("%{public}s: read vect size failed", __func__)); 757 if (vectSize > CmdUtils::MAX_MEMORY) { 758 HDF_LOGE("%{public}s: layers vectSize:%{public}u is too large", __func__, vectSize); 759 return HDF_FAILURE; 760 } 761 762 compChangeLayers_[devId].resize(vectSize); 763 for (uint32_t i = 0; i < vectSize; i++) { 764 DISPLAY_CHK_RETURN(replyUnpacker.ReadUint32(compChangeLayers_[devId][i]) == false, HDF_FAILURE, 765 HDF_LOGE("%{public}s: read layer vector failed", __func__)); 766 } 767 // unpack types vector 768 vectSize = 0; 769 retBool = replyUnpacker.ReadUint32(vectSize); 770 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, HDF_LOGE("%{public}s: read vect size failed", __func__)); 771 if (vectSize > CmdUtils::MAX_MEMORY) { 772 HDF_LOGE("%{public}s: types vectSize:%{public}u is too large", __func__, vectSize); 773 return HDF_FAILURE; 774 } 775 776 compChangeTypes_[devId].resize(vectSize); 777 for (uint32_t i = 0; i < vectSize; i++) { 778 DISPLAY_CHK_RETURN(replyUnpacker.ReadInt32(compChangeTypes_[devId][i]) == false, HDF_FAILURE, 779 HDF_LOGE("%{public}s: read composition type vector failed", __func__)); 780 } 781 782 return HDF_SUCCESS; 783 } 784 OnReplyCommit(CommandDataUnpacker & replyUnpacker,std::vector<HdifdInfo> & replyFds,int32_t & fenceFd)785 int32_t OnReplyCommit( 786 CommandDataUnpacker& replyUnpacker, std::vector<HdifdInfo>& replyFds, int32_t &fenceFd) 787 { 788 int32_t ret = CmdUtils::FileDescriptorUnpack(replyUnpacker, replyFds, fenceFd); 789 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 790 HDF_LOGE("%{public}s: FileDescriptorUnpack failed", __func__)); 791 return HDF_SUCCESS; 792 } 793 ProcessUnpackCmd(CommandDataUnpacker & replyUnpacker,int32_t unpackCmd,std::vector<HdifdInfo> & replyFds,std::function<int32_t (void *)> fn)794 int32_t ProcessUnpackCmd(CommandDataUnpacker& replyUnpacker, int32_t unpackCmd, 795 std::vector<HdifdInfo>& replyFds, std::function<int32_t(void *)> fn) 796 { 797 int32_t ret = HDF_SUCCESS; 798 while (replyUnpacker.NextSection()) { 799 bool retBool = replyUnpacker.BeginSection(unpackCmd); 800 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, 801 HDF_LOGE("%{public}s: BeginSection failed", __func__)); 802 803 bool needFlushFb; 804 int32_t fenceFd = -1; 805 std::unordered_map<int32_t, int32_t> errMaps; 806 switch (unpackCmd) { 807 case REPLY_CMD_PREPARE_DISPLAY_LAYERS: 808 ret = OnReplyPrepareDisplayLayers(replyUnpacker, needFlushFb); 809 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 810 HDF_LOGE("%{public}s: OnReplyPrepareDisplayLayers failed", __func__)); 811 812 ret = fn(&needFlushFb); 813 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 814 HDF_LOGE("%{public}s: ReadBool failed, unpackCmd=%{public}s", 815 __func__, CmdUtils::CommandToString(unpackCmd))); 816 break; 817 case REPLY_CMD_COMMIT: 818 ret = OnReplyCommit(replyUnpacker, replyFds, fenceFd); 819 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 820 HDF_LOGE("%{public}s: OnReplyCommit failed unpackCmd=%{public}s", 821 __func__, CmdUtils::CommandToString(unpackCmd))); 822 823 ret = fn(&fenceFd); 824 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 825 HDF_LOGE("%{public}s: return fence fd error, unpackCmd=%{public}s", 826 __func__, CmdUtils::CommandToString(unpackCmd))); 827 break; 828 case REPLY_CMD_SET_ERROR: 829 ret = OnReplySetError(replyUnpacker, errMaps); 830 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 831 HDF_LOGE("%{public}s: OnReplySetError failed", __func__)); 832 DISPLAY_CHK_RETURN(errMaps.size() > 0, HDF_FAILURE, 833 HDF_LOGE("error: server return errs, size=%{public}zu", errMaps.size())); 834 break; 835 default: 836 HDF_LOGE("Unpack command failure"); 837 return HDF_FAILURE; 838 } 839 } 840 return HDF_SUCCESS; 841 } 842 DoReplyResults(uint32_t replyEleCnt,std::vector<HdifdInfo> & replyFds,std::function<int32_t (void *)> fn)843 int32_t DoReplyResults(uint32_t replyEleCnt, std::vector<HdifdInfo>& replyFds, std::function<int32_t(void *)> fn) 844 { 845 CommandDataUnpacker replyUnpacker; 846 replyUnpacker.Init(replyData_.get(), replyEleCnt << CmdUtils::MOVE_SIZE); 847 #ifdef DEBUG_DISPLAY_CMD_RAW_DATA 848 replyUnpacker.Dump(); 849 #endif // DEBUG_DISPLAY_CMD_RAW_DATA 850 int32_t unpackCmd = -1; 851 bool retBool = replyUnpacker.PackBegin(unpackCmd); 852 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, 853 HDF_LOGE("%{public}s: PackBegin failed", __func__)); 854 DISPLAY_CHK_RETURN(unpackCmd != CONTROL_CMD_REPLY_BEGIN, HDF_FAILURE, 855 HDF_LOGE("%{public}s: PackBegin cmd not match, unpackCmd=%{public}d", __func__, unpackCmd)); 856 if (ProcessUnpackCmd(replyUnpacker, unpackCmd, replyFds, fn) != HDF_SUCCESS) { 857 return HDF_FAILURE; 858 } 859 860 retBool = replyUnpacker.PackEnd(unpackCmd); 861 DISPLAY_CHK_RETURN(retBool == false, HDF_FAILURE, 862 HDF_LOGE("%{public}s: PackEnd failed", __func__)); 863 864 DISPLAY_CHK_RETURN(unpackCmd != CONTROL_CMD_REPLY_END, HDF_FAILURE, 865 HDF_LOGE("%{public}s: PackEnd failed, endCmd = %{public}s", 866 __func__, CmdUtils::CommandToString(unpackCmd))); 867 868 return HDF_SUCCESS; 869 } 870 DoRequest(uint32_t & replyEleCnt,std::vector<HdifdInfo> & outFds)871 int32_t DoRequest(uint32_t &replyEleCnt, std::vector<HdifdInfo> &outFds) 872 { 873 #ifdef DEBUG_DISPLAY_CMD_RAW_DATA 874 requestPacker_.Dump(); 875 #endif // DEBUG_DISPLAY_CMD_RAW_DATA 876 uint32_t eleCnt = requestPacker_.ValidSize() >> CmdUtils::MOVE_SIZE; 877 int32_t ret = request_->Write( 878 reinterpret_cast<int32_t *>(requestPacker_.GetDataPtr()), eleCnt, CmdUtils::TRANSFER_WAIT_TIME); 879 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 880 HDF_LOGE("%{public}s: CmdRequest write failed", __func__)); 881 882 ret = hdi_->CmdRequest(eleCnt, requestHdiFds_, replyEleCnt, outFds); 883 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 884 HDF_LOGE("%{public}s: CmdRequest failed", __func__)); 885 886 if (replyEleCnt != 0) { 887 ret = reply_->Read(reinterpret_cast<int32_t *>(replyData_.get()), 888 replyEleCnt, CmdUtils::TRANSFER_WAIT_TIME); 889 if (ret != HDF_SUCCESS) { 890 HDF_LOGE("reply read data failure, ret=%{public}d", ret); 891 } 892 } 893 894 return ret; 895 } 896 PeriodDataReset()897 int32_t PeriodDataReset() 898 { 899 for (uint32_t i = 0; i < requestHdiFds_.size(); ++i) { 900 int32_t fd = requestHdiFds_[i].hdiFd->Move(); 901 if (fd != -1) { 902 close(fd); 903 } 904 } 905 requestHdiFds_.clear(); 906 int32_t ret = CmdUtils::StartPack(CONTROL_CMD_REQUEST_BEGIN, requestPacker_); 907 DISPLAY_CHK_RETURN(ret != HDF_SUCCESS, ret, 908 HDF_LOGE("%{public}s: StartPack failed", __func__)); 909 910 return HDF_SUCCESS; 911 } 912 913 protected: 914 bool initFlag_; 915 sptr<CompHdi> hdi_; 916 std::shared_ptr<Transfer> request_; 917 std::shared_ptr<Transfer> reply_; 918 std::shared_ptr<char> replyData_; 919 // Period data 920 CommandDataPacker requestPacker_; 921 std::vector<HdifdInfo> requestHdiFds_; 922 // Composition layers/types changed 923 std::unordered_map<uint32_t, std::vector<uint32_t>> compChangeLayers_; 924 std::unordered_map<uint32_t, std::vector<int32_t>> compChangeTypes_; 925 }; 926 using HdiDisplayCmdRequester = DisplayCmdRequester<SharedMemQueue<int32_t>, IDisplayComposer>; 927 } // namespace V1_0 928 } // namespace Composer 929 } // namespace Display 930 } // namespace HDI 931 } // namespace OHOS 932 #endif // OHOS_HDI_DISPLAY_V1_0_DISPLAY_CMD_REQUESTER_H 933