hwc.cpp revision f9572cdbe3541d85522adea584f925671b375300
1/* 2 * Copyright (C) 2010 The Android Open Source Project 3 * Copyright (C) 2012-2013, The Linux Foundation. All rights reserved. 4 * 5 * Not a Contribution, Apache license notifications and license are retained 6 * for attribution purposes only. 7 * 8 * Licensed under the Apache License, Version 2.0 (the "License"); 9 * you may not use this file except in compliance with the License. 10 * You may obtain a copy of the License at 11 * 12 * http://www.apache.org/licenses/LICENSE-2.0 13 * 14 * Unless required by applicable law or agreed to in writing, software 15 * distributed under the License is distributed on an "AS IS" BASIS, 16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 17 * See the License for the specific language governing permissions and 18 * limitations under the License. 19 */ 20#define ATRACE_TAG ATRACE_TAG_GRAPHICS 21#include <fcntl.h> 22#include <errno.h> 23 24#include <cutils/log.h> 25#include <cutils/atomic.h> 26#include <EGL/egl.h> 27#include <utils/Trace.h> 28#include <sys/ioctl.h> 29#include <overlay.h> 30#include <overlayRotator.h> 31#include <mdp_version.h> 32#include "hwc_utils.h" 33#include "hwc_fbupdate.h" 34#include "hwc_mdpcomp.h" 35#include "external.h" 36#include "hwc_copybit.h" 37#include "profiler.h" 38 39using namespace qhwc; 40#define VSYNC_DEBUG 0 41#define BLANK_DEBUG 0 42 43static int hwc_device_open(const struct hw_module_t* module, 44 const char* name, 45 struct hw_device_t** device); 46 47static struct hw_module_methods_t hwc_module_methods = { 48 open: hwc_device_open 49}; 50 51hwc_module_t HAL_MODULE_INFO_SYM = { 52 common: { 53 tag: HARDWARE_MODULE_TAG, 54 version_major: 2, 55 version_minor: 0, 56 id: HWC_HARDWARE_MODULE_ID, 57 name: "Qualcomm Hardware Composer Module", 58 author: "CodeAurora Forum", 59 methods: &hwc_module_methods, 60 dso: 0, 61 reserved: {0}, 62 } 63}; 64 65/* 66 * Save callback functions registered to HWC 67 */ 68static void hwc_registerProcs(struct hwc_composer_device_1* dev, 69 hwc_procs_t const* procs) 70{ 71 ALOGI("%s", __FUNCTION__); 72 hwc_context_t* ctx = (hwc_context_t*)(dev); 73 if(!ctx) { 74 ALOGE("%s: Invalid context", __FUNCTION__); 75 return; 76 } 77 ctx->proc = procs; 78 79 // Now that we have the functions needed, kick off 80 // the uevent & vsync threads 81 init_uevent_thread(ctx); 82 init_vsync_thread(ctx); 83} 84 85//Helper 86static void reset(hwc_context_t *ctx, int numDisplays, 87 hwc_display_contents_1_t** displays) { 88 memset(ctx->listStats, 0, sizeof(ctx->listStats)); 89 for(int i = 0; i < MAX_DISPLAYS; i++) { 90 hwc_display_contents_1_t *list = displays[i]; 91 // XXX:SurfaceFlinger no longer guarantees that this 92 // value is reset on every prepare. However, for the layer 93 // cache we need to reset it. 94 // We can probably rethink that later on 95 if (LIKELY(list && list->numHwLayers > 1)) { 96 for(uint32_t j = 0; j < list->numHwLayers; j++) { 97 if(list->hwLayers[j].compositionType != HWC_FRAMEBUFFER_TARGET) 98 list->hwLayers[j].compositionType = HWC_FRAMEBUFFER; 99 } 100 } 101 102 if(ctx->mFBUpdate[i]) 103 ctx->mFBUpdate[i]->reset(); 104 if(ctx->mCopyBit[i]) 105 ctx->mCopyBit[i]->reset(); 106 } 107} 108 109//clear prev layer prop flags and realloc for current frame 110static void reset_layer_prop(hwc_context_t* ctx, int dpy, int numAppLayers) { 111 if(ctx->layerProp[dpy]) { 112 delete[] ctx->layerProp[dpy]; 113 ctx->layerProp[dpy] = NULL; 114 } 115 ctx->layerProp[dpy] = new LayerProp[numAppLayers]; 116} 117 118static int display_commit(hwc_context_t *ctx, int dpy) { 119 struct mdp_display_commit commit_info; 120 memset(&commit_info, 0, sizeof(struct mdp_display_commit)); 121 commit_info.flags = MDP_DISPLAY_COMMIT_OVERLAY; 122 if(ioctl(ctx->dpyAttr[dpy].fd, MSMFB_DISPLAY_COMMIT, &commit_info) == -1) { 123 ALOGE("%s: MSMFB_DISPLAY_COMMIT for primary failed", __FUNCTION__); 124 return -errno; 125 } 126 return 0; 127} 128 129static int hwc_prepare_primary(hwc_composer_device_1 *dev, 130 hwc_display_contents_1_t *list) { 131 hwc_context_t* ctx = (hwc_context_t*)(dev); 132 const int dpy = HWC_DISPLAY_PRIMARY; 133 if (LIKELY(list && list->numHwLayers > 1) && 134 ctx->dpyAttr[dpy].isActive) { 135 reset_layer_prop(ctx, dpy, list->numHwLayers - 1); 136 uint32_t last = list->numHwLayers - 1; 137 hwc_layer_1_t *fbLayer = &list->hwLayers[last]; 138 if(fbLayer->handle) { 139 setListStats(ctx, list, dpy); 140 int fbZOrder = ctx->mMDPComp[dpy]->prepare(ctx, list); 141 if(fbZOrder >= 0) 142 ctx->mFBUpdate[dpy]->prepare(ctx, list, fbZOrder); 143 144 /* Temporarily commenting out C2D until we support partial 145 copybit composition for mixed mode MDP 146 147 // Use Copybit, when MDP comp fails 148 if((fbZOrder >= 0) && ctx->mCopyBit[dpy]) 149 ctx->mCopyBit[dpy]->prepare(ctx, list, dpy); 150 */ 151 } 152 } 153 return 0; 154} 155 156static int hwc_prepare_external(hwc_composer_device_1 *dev, 157 hwc_display_contents_1_t *list, int dpy) { 158 hwc_context_t* ctx = (hwc_context_t*)(dev); 159 160 if (LIKELY(list && list->numHwLayers > 1) && 161 ctx->dpyAttr[dpy].isActive && 162 ctx->dpyAttr[dpy].connected) { 163 reset_layer_prop(ctx, dpy, list->numHwLayers - 1); 164 uint32_t last = list->numHwLayers - 1; 165 hwc_layer_1_t *fbLayer = &list->hwLayers[last]; 166 if(!ctx->dpyAttr[dpy].isPause) { 167 if(fbLayer->handle) { 168 ctx->mExtDispConfiguring = false; 169 setListStats(ctx, list, dpy); 170 int fbZOrder = ctx->mMDPComp[dpy]->prepare(ctx, list); 171 if(fbZOrder >= 0) 172 ctx->mFBUpdate[dpy]->prepare(ctx, list, fbZOrder); 173 174 /* Temporarily commenting out C2D until we support partial 175 copybit composition for mixed mode MDP 176 177 if((fbZOrder >= 0) && ctx->mCopyBit[dpy]) 178 ctx->mCopyBit[dpy]->prepare(ctx, list, dpy); 179 */ 180 } 181 } else { 182 // External Display is in Pause state. 183 // ToDo: 184 // Mark all application layers as OVERLAY so that 185 // GPU will not compose. This is done for power 186 // optimization 187 } 188 } 189 return 0; 190} 191 192static int hwc_prepare(hwc_composer_device_1 *dev, size_t numDisplays, 193 hwc_display_contents_1_t** displays) 194{ 195 int ret = 0; 196 hwc_context_t* ctx = (hwc_context_t*)(dev); 197 Locker::Autolock _l(ctx->mBlankLock); 198 reset(ctx, numDisplays, displays); 199 200 ctx->mOverlay->configBegin(); 201 ctx->mRotMgr->configBegin(); 202 ctx->mNeedsRotator = false; 203 204 for (int32_t i = numDisplays; i >= 0; i--) { 205 hwc_display_contents_1_t *list = displays[i]; 206 switch(i) { 207 case HWC_DISPLAY_PRIMARY: 208 ret = hwc_prepare_primary(dev, list); 209 break; 210 case HWC_DISPLAY_EXTERNAL: 211 case HWC_DISPLAY_VIRTUAL: 212 ret = hwc_prepare_external(dev, list, i); 213 break; 214 default: 215 ret = -EINVAL; 216 } 217 } 218 219 ctx->mOverlay->configDone(); 220 ctx->mRotMgr->configDone(); 221 222 return ret; 223} 224 225static int hwc_eventControl(struct hwc_composer_device_1* dev, int dpy, 226 int event, int enable) 227{ 228 int ret = 0; 229 hwc_context_t* ctx = (hwc_context_t*)(dev); 230 pthread_mutex_lock(&ctx->vstate.lock); 231 switch(event) { 232 case HWC_EVENT_VSYNC: 233 if (ctx->vstate.enable == enable) 234 break; 235 ret = hwc_vsync_control(ctx, dpy, enable); 236 if(ret == 0) { 237 ctx->vstate.enable = !!enable; 238 pthread_cond_signal(&ctx->vstate.cond); 239 } 240 ALOGD_IF (VSYNC_DEBUG, "VSYNC state changed to %s", 241 (enable)?"ENABLED":"DISABLED"); 242 break; 243 default: 244 ret = -EINVAL; 245 } 246 pthread_mutex_unlock(&ctx->vstate.lock); 247 return ret; 248} 249 250static int hwc_blank(struct hwc_composer_device_1* dev, int dpy, int blank) 251{ 252 ATRACE_CALL(); 253 hwc_context_t* ctx = (hwc_context_t*)(dev); 254 255 Locker::Autolock _l(ctx->mBlankLock); 256 int ret = 0; 257 ALOGD_IF(BLANK_DEBUG, "%s: %s display: %d", __FUNCTION__, 258 blank==1 ? "Blanking":"Unblanking", dpy); 259 if(blank) { 260 // free up all the overlay pipes in use 261 // when we get a blank for either display 262 // makes sure that all pipes are freed 263 ctx->mOverlay->configBegin(); 264 ctx->mOverlay->configDone(); 265 ctx->mRotMgr->clear(); 266 } 267 switch(dpy) { 268 case HWC_DISPLAY_PRIMARY: 269 if(blank) { 270 ret = ioctl(ctx->dpyAttr[dpy].fd, FBIOBLANK,FB_BLANK_POWERDOWN); 271 272 if(ctx->dpyAttr[HWC_DISPLAY_VIRTUAL].connected == true) { 273 // Surfaceflinger does not send Blank/unblank event to hwc 274 // for virtual display, handle it explicitly when blank for 275 // primary is invoked, so that any pipes unset get committed 276 if (display_commit(ctx, HWC_DISPLAY_VIRTUAL) < 0) { 277 ret = -1; 278 ALOGE("%s:post failed for virtual display !!", 279 __FUNCTION__); 280 } else { 281 ctx->dpyAttr[HWC_DISPLAY_VIRTUAL].isActive = !blank; 282 } 283 } 284 } else { 285 ret = ioctl(ctx->dpyAttr[dpy].fd, FBIOBLANK, FB_BLANK_UNBLANK); 286 if(ctx->dpyAttr[HWC_DISPLAY_VIRTUAL].connected == true) { 287 ctx->dpyAttr[HWC_DISPLAY_VIRTUAL].isActive = !blank; 288 } 289 } 290 break; 291 case HWC_DISPLAY_EXTERNAL: 292 if(blank) { 293 // call external framebuffer commit on blank, 294 // so that any pipe unsets gets committed 295 if (display_commit(ctx, dpy) < 0) { 296 ret = -1; 297 ALOGE("%s:post failed for external display !! ", 298 __FUNCTION__); 299 } 300 } else { 301 } 302 break; 303 default: 304 return -EINVAL; 305 } 306 // Enable HPD here, as during bootup unblank is called 307 // when SF is completely initialized 308 ctx->mExtDisplay->setHPD(1); 309 if(ret == 0){ 310 ctx->dpyAttr[dpy].isActive = !blank; 311 } else { 312 ALOGE("%s: Failed in %s display: %d error:%s", __FUNCTION__, 313 blank==1 ? "blanking":"unblanking", dpy, strerror(errno)); 314 return ret; 315 } 316 317 ALOGD_IF(BLANK_DEBUG, "%s: Done %s display: %d", __FUNCTION__, 318 blank==1 ? "blanking":"unblanking", dpy); 319 return 0; 320} 321 322static int hwc_query(struct hwc_composer_device_1* dev, 323 int param, int* value) 324{ 325 hwc_context_t* ctx = (hwc_context_t*)(dev); 326 int supported = HWC_DISPLAY_PRIMARY_BIT; 327 328 switch (param) { 329 case HWC_BACKGROUND_LAYER_SUPPORTED: 330 // Not supported for now 331 value[0] = 0; 332 break; 333 case HWC_DISPLAY_TYPES_SUPPORTED: 334 if(ctx->mMDP.hasOverlay) 335 supported |= HWC_DISPLAY_EXTERNAL_BIT; 336 value[0] = supported; 337 break; 338 default: 339 return -EINVAL; 340 } 341 return 0; 342 343} 344 345 346static int hwc_set_primary(hwc_context_t *ctx, hwc_display_contents_1_t* list) { 347 ATRACE_CALL(); 348 int ret = 0; 349 const int dpy = HWC_DISPLAY_PRIMARY; 350 if (LIKELY(list) && ctx->dpyAttr[dpy].isActive) { 351 uint32_t last = list->numHwLayers - 1; 352 hwc_layer_1_t *fbLayer = &list->hwLayers[last]; 353 int fd = -1; //FenceFD from the Copybit(valid in async mode) 354 bool copybitDone = false; 355 if(ctx->mCopyBit[dpy]) 356 copybitDone = ctx->mCopyBit[dpy]->draw(ctx, list, dpy, &fd); 357 if(list->numHwLayers > 1) 358 hwc_sync(ctx, list, dpy, fd); 359 360 if (!ctx->mMDPComp[dpy]->draw(ctx, list)) { 361 ALOGE("%s: MDPComp draw failed", __FUNCTION__); 362 ret = -1; 363 } 364 365 //TODO We dont check for SKIP flag on this layer because we need PAN 366 //always. Last layer is always FB 367 private_handle_t *hnd = (private_handle_t *)fbLayer->handle; 368 if(copybitDone) { 369 hnd = ctx->mCopyBit[dpy]->getCurrentRenderBuffer(); 370 } 371 372 if(hnd) { 373 if (!ctx->mFBUpdate[dpy]->draw(ctx, hnd)) { 374 ALOGE("%s: FBUpdate draw failed", __FUNCTION__); 375 ret = -1; 376 } 377 } 378 379 if (display_commit(ctx, dpy) < 0) { 380 ALOGE("%s: display commit fail!", __FUNCTION__); 381 return -1; 382 } 383 } 384 385 closeAcquireFds(list); 386 return ret; 387} 388 389static int hwc_set_external(hwc_context_t *ctx, 390 hwc_display_contents_1_t* list, int dpy) 391{ 392 ATRACE_CALL(); 393 int ret = 0; 394 Locker::Autolock _l(ctx->mExtSetLock); 395 396 if (LIKELY(list) && ctx->dpyAttr[dpy].isActive && 397 !ctx->dpyAttr[dpy].isPause && 398 ctx->dpyAttr[dpy].connected) { 399 uint32_t last = list->numHwLayers - 1; 400 hwc_layer_1_t *fbLayer = &list->hwLayers[last]; 401 int fd = -1; //FenceFD from the Copybit(valid in async mode) 402 bool copybitDone = false; 403 if(ctx->mCopyBit[dpy]) 404 copybitDone = ctx->mCopyBit[dpy]->draw(ctx, list, dpy, &fd); 405 406 if(list->numHwLayers > 1) 407 hwc_sync(ctx, list, dpy, fd); 408 409 if (!ctx->mMDPComp[dpy]->draw(ctx, list)) { 410 ALOGE("%s: MDPComp draw failed", __FUNCTION__); 411 ret = -1; 412 } 413 414 private_handle_t *hnd = (private_handle_t *)fbLayer->handle; 415 if(copybitDone) { 416 hnd = ctx->mCopyBit[dpy]->getCurrentRenderBuffer(); 417 } 418 419 if(hnd) { 420 if (!ctx->mFBUpdate[dpy]->draw(ctx, hnd)) { 421 ALOGE("%s: FBUpdate::draw fail!", __FUNCTION__); 422 ret = -1; 423 } 424 } 425 426 if (display_commit(ctx, dpy) < 0) { 427 ALOGE("%s: display commit fail!", __FUNCTION__); 428 ret = -1; 429 } 430 } 431 432 closeAcquireFds(list); 433 return ret; 434} 435 436static int hwc_set(hwc_composer_device_1 *dev, 437 size_t numDisplays, 438 hwc_display_contents_1_t** displays) 439{ 440 int ret = 0; 441 hwc_context_t* ctx = (hwc_context_t*)(dev); 442 Locker::Autolock _l(ctx->mBlankLock); 443 for (uint32_t i = 0; i <= numDisplays; i++) { 444 hwc_display_contents_1_t* list = displays[i]; 445 switch(i) { 446 case HWC_DISPLAY_PRIMARY: 447 ret = hwc_set_primary(ctx, list); 448 break; 449 case HWC_DISPLAY_EXTERNAL: 450 case HWC_DISPLAY_VIRTUAL: 451 /* ToDo: We are using hwc_set_external path for both External and 452 Virtual displays on HWC1.1. Eventually, we will have 453 separate functions when we move to HWC1.2 454 */ 455 ret = hwc_set_external(ctx, list, i); 456 break; 457 default: 458 ret = -EINVAL; 459 } 460 } 461 // This is only indicative of how many times SurfaceFlinger posts 462 // frames to the display. 463 CALC_FPS(); 464 return ret; 465} 466 467int hwc_getDisplayConfigs(struct hwc_composer_device_1* dev, int disp, 468 uint32_t* configs, size_t* numConfigs) { 469 int ret = 0; 470 hwc_context_t* ctx = (hwc_context_t*)(dev); 471 //in 1.1 there is no way to choose a config, report as config id # 0 472 //This config is passed to getDisplayAttributes. Ignore for now. 473 switch(disp) { 474 case HWC_DISPLAY_PRIMARY: 475 if(*numConfigs > 0) { 476 configs[0] = 0; 477 *numConfigs = 1; 478 } 479 ret = 0; //NO_ERROR 480 break; 481 case HWC_DISPLAY_EXTERNAL: 482 ret = -1; //Not connected 483 if(ctx->dpyAttr[HWC_DISPLAY_EXTERNAL].connected) { 484 ret = 0; //NO_ERROR 485 if(*numConfigs > 0) { 486 configs[0] = 0; 487 *numConfigs = 1; 488 } 489 } 490 break; 491 } 492 return ret; 493} 494 495int hwc_getDisplayAttributes(struct hwc_composer_device_1* dev, int disp, 496 uint32_t config, const uint32_t* attributes, int32_t* values) { 497 498 hwc_context_t* ctx = (hwc_context_t*)(dev); 499 //If hotpluggable displays are inactive return error 500 if(disp == HWC_DISPLAY_EXTERNAL && !ctx->dpyAttr[disp].connected) { 501 return -1; 502 } 503 504 //From HWComposer 505 static const uint32_t DISPLAY_ATTRIBUTES[] = { 506 HWC_DISPLAY_VSYNC_PERIOD, 507 HWC_DISPLAY_WIDTH, 508 HWC_DISPLAY_HEIGHT, 509 HWC_DISPLAY_DPI_X, 510 HWC_DISPLAY_DPI_Y, 511 HWC_DISPLAY_NO_ATTRIBUTE, 512 }; 513 514 const int NUM_DISPLAY_ATTRIBUTES = (sizeof(DISPLAY_ATTRIBUTES) / 515 sizeof(DISPLAY_ATTRIBUTES)[0]); 516 517 for (size_t i = 0; i < NUM_DISPLAY_ATTRIBUTES - 1; i++) { 518 switch (attributes[i]) { 519 case HWC_DISPLAY_VSYNC_PERIOD: 520 values[i] = ctx->dpyAttr[disp].vsync_period; 521 break; 522 case HWC_DISPLAY_WIDTH: 523 values[i] = ctx->dpyAttr[disp].xres; 524 ALOGD("%s disp = %d, width = %d",__FUNCTION__, disp, 525 ctx->dpyAttr[disp].xres); 526 break; 527 case HWC_DISPLAY_HEIGHT: 528 values[i] = ctx->dpyAttr[disp].yres; 529 ALOGD("%s disp = %d, height = %d",__FUNCTION__, disp, 530 ctx->dpyAttr[disp].yres); 531 break; 532 case HWC_DISPLAY_DPI_X: 533 values[i] = (int32_t) (ctx->dpyAttr[disp].xdpi*1000.0); 534 break; 535 case HWC_DISPLAY_DPI_Y: 536 values[i] = (int32_t) (ctx->dpyAttr[disp].ydpi*1000.0); 537 break; 538 default: 539 ALOGE("Unknown display attribute %d", 540 attributes[i]); 541 return -EINVAL; 542 } 543 } 544 return 0; 545} 546 547void hwc_dump(struct hwc_composer_device_1* dev, char *buff, int buff_len) 548{ 549 hwc_context_t* ctx = (hwc_context_t*)(dev); 550 android::String8 aBuf(""); 551 dumpsys_log(aBuf, "Qualcomm HWC state:\n"); 552 dumpsys_log(aBuf, " MDPVersion=%d\n", ctx->mMDP.version); 553 dumpsys_log(aBuf, " DisplayPanel=%c\n", ctx->mMDP.panel); 554 for(int dpy = 0; dpy < MAX_DISPLAYS; dpy++) { 555 if(ctx->mMDPComp[dpy]) 556 ctx->mMDPComp[dpy]->dump(aBuf); 557 } 558 char ovDump[2048] = {'\0'}; 559 ctx->mOverlay->getDump(ovDump, 2048); 560 dumpsys_log(aBuf, ovDump); 561 ovDump[0] = '\0'; 562 ctx->mRotMgr->getDump(ovDump, 2048); 563 dumpsys_log(aBuf, ovDump); 564 strlcpy(buff, aBuf.string(), buff_len); 565} 566 567static int hwc_device_close(struct hw_device_t *dev) 568{ 569 if(!dev) { 570 ALOGE("%s: NULL device pointer", __FUNCTION__); 571 return -1; 572 } 573 closeContext((hwc_context_t*)dev); 574 free(dev); 575 576 return 0; 577} 578 579static int hwc_device_open(const struct hw_module_t* module, const char* name, 580 struct hw_device_t** device) 581{ 582 int status = -EINVAL; 583 584 if (!strcmp(name, HWC_HARDWARE_COMPOSER)) { 585 struct hwc_context_t *dev; 586 dev = (hwc_context_t*)malloc(sizeof(*dev)); 587 memset(dev, 0, sizeof(*dev)); 588 589 //Initialize hwc context 590 initContext(dev); 591 592 //Setup HWC methods 593 dev->device.common.tag = HARDWARE_DEVICE_TAG; 594 dev->device.common.version = HWC_DEVICE_API_VERSION_1_1; 595 dev->device.common.module = const_cast<hw_module_t*>(module); 596 dev->device.common.close = hwc_device_close; 597 dev->device.prepare = hwc_prepare; 598 dev->device.set = hwc_set; 599 dev->device.eventControl = hwc_eventControl; 600 dev->device.blank = hwc_blank; 601 dev->device.query = hwc_query; 602 dev->device.registerProcs = hwc_registerProcs; 603 dev->device.dump = hwc_dump; 604 dev->device.getDisplayConfigs = hwc_getDisplayConfigs; 605 dev->device.getDisplayAttributes = hwc_getDisplayAttributes; 606 *device = &dev->device.common; 607 status = 0; 608 } 609 return status; 610} 611