blob: dd96efe397aa0843ddb68a955d84bd2c90c45cef [file] [log] [blame]
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -07001/*
2 * Copyright (C) 2010 The Android Open Source Project
Saurabh Shah56f610d2012-08-07 15:27:06 -07003 * Copyright (C) 2012, The Linux Foundation. All rights reserved.
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -07004 *
5 * Not a Contribution, Apache license notifications and license are
6 * retained 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
Naseer Ahmed72cf9762012-07-21 12:17:13 -070021#define HWC_UI_MIRROR 0
22#include <gralloc_priv.h>
23#include <fb_priv.h>
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070024#include "hwc_uimirror.h"
Saurabh Shah56f610d2012-08-07 15:27:06 -070025#include "external.h"
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070026
27namespace qhwc {
28
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070029//Static Members
30ovutils::eOverlayState UIMirrorOverlay::sState = ovutils::OV_CLOSED;
31bool UIMirrorOverlay::sIsUiMirroringOn = false;
32
Saurabh Shah56f610d2012-08-07 15:27:06 -070033void UIMirrorOverlay::reset() {
34 sIsUiMirroringOn = false;
35 sState = ovutils::OV_CLOSED;
36}
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070037
38//Prepare the overlay for the UI mirroring
Saurabh Shah3e858eb2012-09-17 16:53:21 -070039bool UIMirrorOverlay::prepare(hwc_context_t *ctx, hwc_layer_1_t *fblayer) {
Saurabh Shahc4d034f2012-09-27 15:55:15 -070040 reset();
Naseer Ahmedf8ec1622012-07-31 18:56:23 -070041
Naseer Ahmed96c4c952012-07-25 18:27:14 -070042 if(!ctx->mMDP.hasOverlay) {
Saurabh Shah3e858eb2012-09-17 16:53:21 -070043 ALOGD_IF(HWC_UI_MIRROR, "%s, this hw doesnt support mirroring",
44 __FUNCTION__);
Naseer Ahmedf8ec1622012-07-31 18:56:23 -070045 return false;
46 }
Saurabh Shahc4d034f2012-09-27 15:55:15 -070047
48 sState = ovutils::OV_UI_MIRROR;
49 ovutils::eOverlayState newState = ctx->mOverlay[HWC_DISPLAY_EXTERNAL]->getState();
50 if(newState == ovutils::OV_UI_VIDEO_TV) {
51 sState = newState;
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070052 }
Saurabh Shahc4d034f2012-09-27 15:55:15 -070053
54 configure(ctx, fblayer);
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070055 return sIsUiMirroringOn;
56}
57
58// Configure
Saurabh Shah3e858eb2012-09-17 16:53:21 -070059bool UIMirrorOverlay::configure(hwc_context_t *ctx, hwc_layer_1_t *layer)
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070060{
Saurabh Shahc4d034f2012-09-27 15:55:15 -070061 if (LIKELY(ctx->mOverlay[HWC_DISPLAY_EXTERNAL])) {
62 overlay::Overlay& ov = *(ctx->mOverlay[HWC_DISPLAY_EXTERNAL]);
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070063 // Set overlay state
64 ov.setState(sState);
Saurabh Shahc4d034f2012-09-27 15:55:15 -070065 private_handle_t *hnd = (private_handle_t *)layer->handle;
Saurabh Shahae823e72012-10-05 00:08:11 -040066 if (!hnd) {
67 ALOGE("%s:NULL private handle for layer!", __FUNCTION__);
68 return false;
69 }
Saurabh Shahc4d034f2012-09-27 15:55:15 -070070 ovutils::Whf info(hnd->width, hnd->height, hnd->format, hnd->size);
71 // Determine the RGB pipe for UI depending on the state
72 ovutils::eDest dest = ovutils::OV_PIPE0;
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070073
Saurabh Shahc4d034f2012-09-27 15:55:15 -070074 ovutils::eMdpFlags mdpFlags = ovutils::OV_MDP_FLAGS_NONE;
75 if(ctx->mSecureMode) {
76 ovutils::setMdpFlags(mdpFlags,
77 ovutils::OV_MDP_SECURE_OVERLAY_SESSION);
78 }
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070079
Saurabh Shahc4d034f2012-09-27 15:55:15 -070080 ovutils::PipeArgs parg(mdpFlags,
81 info,
82 ovutils::ZORDER_0,
83 ovutils::IS_FG_OFF,
84 ovutils::ROT_FLAG_DISABLED);
85 ovutils::PipeArgs pargs[ovutils::MAX_PIPES] = { parg, parg, parg };
86 ov.setSource(pargs, dest);
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070087
Saurabh Shahc4d034f2012-09-27 15:55:15 -070088 hwc_rect_t sourceCrop = layer->sourceCrop;
89 // x,y,w,h
90 ovutils::Dim dcrop(sourceCrop.left, sourceCrop.top,
Saurabh Shah3e858eb2012-09-17 16:53:21 -070091 sourceCrop.right - sourceCrop.left,
92 sourceCrop.bottom - sourceCrop.top);
Saurabh Shahc4d034f2012-09-27 15:55:15 -070093 ov.setCrop(dcrop, dest);
Saurabh Shah3e858eb2012-09-17 16:53:21 -070094
Saurabh Shahc4d034f2012-09-27 15:55:15 -070095 int transform = layer->transform;
96 ovutils::eTransform orient =
97 static_cast<ovutils::eTransform>(transform);
98 ov.setTransform(orient, dest);
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -070099
Saurabh Shahc4d034f2012-09-27 15:55:15 -0700100 hwc_rect_t displayFrame = layer->displayFrame;
101 ovutils::Dim dpos(displayFrame.left,
Saurabh Shah3e858eb2012-09-17 16:53:21 -0700102 displayFrame.top,
103 displayFrame.right - displayFrame.left,
104 displayFrame.bottom - displayFrame.top);
Saurabh Shahc4d034f2012-09-27 15:55:15 -0700105 ov.setPosition(dpos, dest);
Saurabh Shah3e858eb2012-09-17 16:53:21 -0700106
Saurabh Shahc4d034f2012-09-27 15:55:15 -0700107 if (!ov.commit(dest)) {
108 ALOGE("%s: commit fails", __FUNCTION__);
109 sIsUiMirroringOn = false;
110 return false;
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -0700111 }
Saurabh Shahc4d034f2012-09-27 15:55:15 -0700112 sIsUiMirroringOn = true;
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -0700113 }
114 return sIsUiMirroringOn;
115}
116
Saurabh Shah3e858eb2012-09-17 16:53:21 -0700117bool UIMirrorOverlay::draw(hwc_context_t *ctx, hwc_layer_1_t *layer)
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -0700118{
119 if(!sIsUiMirroringOn) {
120 return true;
121 }
122 bool ret = true;
Saurabh Shahc4d034f2012-09-27 15:55:15 -0700123 overlay::Overlay& ov = *(ctx->mOverlay[HWC_DISPLAY_EXTERNAL]);
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -0700124 ovutils::eOverlayState state = ov.getState();
Saurabh Shahc4d034f2012-09-27 15:55:15 -0700125 ovutils::eDest dest = ovutils::OV_PIPE0;
126 private_handle_t *hnd = (private_handle_t *)layer->handle;
127 switch (state) {
128 case ovutils::OV_UI_MIRROR:
129 case ovutils::OV_UI_VIDEO_TV:
130 if (!ov.queueBuffer(hnd->fd, hnd->offset, dest)) {
131 ALOGE("%s: queueBuffer failed for external", __FUNCTION__);
132 ret = false;
133 }
134 break;
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -0700135 default:
136 break;
Naseer Ahmed0c8b7b52012-07-20 09:06:13 -0700137 }
138 return ret;
139}
140
141//---------------------------------------------------------------------
142}; //namespace qhwc