hwc.cpp revision 1a8cda0b2cb535656eb18bf5dc07a02fcddec9ab
129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/*
229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Copyright (C) 2010 The Android Open Source Project
356f610dd235b577725198e9341caae92379fdf23Saurabh Shah * Copyright (C) 2012, The Linux Foundation. All rights reserved.
429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Licensed under the Apache License, Version 2.0 (the "License");
629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * you may not use this file except in compliance with the License.
729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * You may obtain a copy of the License at
829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *      http://www.apache.org/licenses/LICENSE-2.0
1029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
1129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Unless required by applicable law or agreed to in writing, software
1229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * distributed under the License is distributed on an "AS IS" BASIS,
1329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * See the License for the specific language governing permissions and
1529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * limitations under the License.
1629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed */
1729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
1829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <fcntl.h>
1929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <errno.h>
2029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
2129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <cutils/log.h>
2229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <cutils/atomic.h>
2372cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed#include <EGL/egl.h>
2429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
2572cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed#include <overlay.h>
2672cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed#include <fb_priv.h>
2796c4c95d48dc075196c601b30a8798a262df9720Naseer Ahmed#include <mdp_version.h>
2829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include "hwc_utils.h"
29f48aef64b218d42bd2ede62dcb03a3d7831ebbf9Naseer Ahmed#include "hwc_video.h"
3086623d7d5106cd568a64be4e51be7ee77f078e08Saurabh Shah#include "hwc_uimirror.h"
3156f610dd235b577725198e9341caae92379fdf23Saurabh Shah#include "external.h"
327c958d445fe88a82eedbd1b887cd1e474a7526b1Naseer Ahmed#include "hwc_mdpcomp.h"
3329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
34ff4f0254be575a264504687c407e0db2fd5573d7Naseer Ahmed#define VSYNC_DEBUG 0
3529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedusing namespace qhwc;
3629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
3729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedstatic int hwc_device_open(const struct hw_module_t* module,
3829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                           const char* name,
3929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                           struct hw_device_t** device);
4029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
4129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedstatic struct hw_module_methods_t hwc_module_methods = {
4229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    open: hwc_device_open
4329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed};
4429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
4529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedhwc_module_t HAL_MODULE_INFO_SYM = {
4629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    common: {
4729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        tag: HARDWARE_MODULE_TAG,
4829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        version_major: 2,
4929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        version_minor: 0,
5029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        id: HWC_HARDWARE_MODULE_ID,
5129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        name: "Qualcomm Hardware Composer Module",
5229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        author: "CodeAurora Forum",
5329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        methods: &hwc_module_methods,
5429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        dso: 0,
5529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        reserved: {0},
5629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
5729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed};
5829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
5929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/*
6029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Save callback functions registered to HWC
6129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed */
625b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmedstatic void hwc_registerProcs(struct hwc_composer_device_1* dev,
6329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                              hwc_procs_t const* procs)
6429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
650f9c397181604f28d15c9273de42f97ae2b4c613Iliyan Malchev    ALOGI("%s", __FUNCTION__);
6629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    hwc_context_t* ctx = (hwc_context_t*)(dev);
6729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if(!ctx) {
6829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        ALOGE("%s: Invalid context", __FUNCTION__);
6929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        return;
7029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
713be78d9816da84e48a40232165189f9deb16808fJesse Hall    ctx->proc = procs;
723be78d9816da84e48a40232165189f9deb16808fJesse Hall
73ff4f0254be575a264504687c407e0db2fd5573d7Naseer Ahmed    // Now that we have the functions needed, kick off
74ff4f0254be575a264504687c407e0db2fd5573d7Naseer Ahmed    // the uevent & vsync threads
753be78d9816da84e48a40232165189f9deb16808fJesse Hall    init_uevent_thread(ctx);
76ff4f0254be575a264504687c407e0db2fd5573d7Naseer Ahmed    init_vsync_thread(ctx);
7729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
7829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
79649cda6710c01fbc4259f8ab61aff2cdb05b242cSaurabh Shah//Helper
803e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahstatic void reset(hwc_context_t *ctx, int numDisplays) {
813e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    memset(ctx->listStats, 0, sizeof(ctx->listStats));
821a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah    for(int i = 0; i < HWC_NUM_DISPLAY_TYPES; i++){
831a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        ctx->overlayInUse[i] = false;
843e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        ctx->listStats[i].yuvIndex = -1;
853e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
863e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah}
873e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
883e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahstatic int hwc_prepare_primary(hwc_composer_device_1 *dev,
893e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        hwc_display_contents_1_t *list) {
903e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    hwc_context_t* ctx = (hwc_context_t*)(dev);
911a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah
921a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah    if (LIKELY(list && list->numHwLayers > 1) &&
931a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        ctx->dpyAttr[HWC_DISPLAY_PRIMARY].isActive) {
941a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah
9586623d7d5106cd568a64be4e51be7ee77f078e08Saurabh Shah        uint32_t last = list->numHwLayers - 1;
961a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        hwc_layer_1_t *fbLayer = &list->hwLayers[last];
971a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        if(fbLayer->handle) {
981a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            setListStats(ctx, list, HWC_DISPLAY_PRIMARY);
991a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            if(VideoOverlay::prepare(ctx, list, HWC_DISPLAY_PRIMARY)) {
1001a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ctx->overlayInUse[HWC_DISPLAY_PRIMARY] = true;
1011a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            } else if(MDPComp::configure(ctx, list)) {
1021a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ctx->overlayInUse[HWC_DISPLAY_PRIMARY] = true;
1031a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            } else {
1041a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ctx->overlayInUse[HWC_DISPLAY_PRIMARY] = false;
1051a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            }
1063e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        }
1073e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
1083e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return 0;
1093e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah}
1103e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
1113e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahstatic int hwc_prepare_external(hwc_composer_device_1 *dev,
1123e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        hwc_display_contents_1_t *list) {
1133e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    hwc_context_t* ctx = (hwc_context_t*)(dev);
114c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
115ae823e773536ee9b6cf97c575463f1a9902370d9Saurabh Shah    if (LIKELY(list && list->numHwLayers > 1) &&
116c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        ctx->dpyAttr[HWC_DISPLAY_EXTERNAL].isActive &&
117c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        ctx->dpyAttr[HWC_DISPLAY_EXTERNAL].connected) {
118c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
119c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        setListStats(ctx, list, HWC_DISPLAY_EXTERNAL);
120c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
121c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        uint32_t last = list->numHwLayers - 1;
1221a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        hwc_layer_1_t *fbLayer = &list->hwLayers[last];
1231a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        if(fbLayer->handle) {
1241a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            if(UIMirrorOverlay::prepare(ctx, fbLayer)) {
1251a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ctx->overlayInUse[HWC_DISPLAY_EXTERNAL] = true;
1261a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            }
127c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
1281a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            if(VideoOverlay::prepare(ctx, list, HWC_DISPLAY_EXTERNAL)) {
1291a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ctx->overlayInUse[HWC_DISPLAY_EXTERNAL] = true;
1301a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            } else {
1311a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ctx->mOverlay[HWC_DISPLAY_EXTERNAL]->setState(
1321a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                        ovutils::OV_UI_MIRROR);
1331a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            }
134c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        }
1353e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
1363e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return 0;
137649cda6710c01fbc4259f8ab61aff2cdb05b242cSaurabh Shah}
138649cda6710c01fbc4259f8ab61aff2cdb05b242cSaurabh Shah
1395b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmedstatic int hwc_prepare(hwc_composer_device_1 *dev, size_t numDisplays,
1405b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed                       hwc_display_contents_1_t** displays)
14129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
1423e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    int ret = 0;
14329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    hwc_context_t* ctx = (hwc_context_t*)(dev);
1443e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    reset(ctx, numDisplays);
14556f610dd235b577725198e9341caae92379fdf23Saurabh Shah
14656f610dd235b577725198e9341caae92379fdf23Saurabh Shah    //If securing of h/w in progress skip comp using overlay.
14756f610dd235b577725198e9341caae92379fdf23Saurabh Shah    if(ctx->mSecuring == true) return 0;
14856f610dd235b577725198e9341caae92379fdf23Saurabh Shah
1499171ec698c218df6eec5c91fe438f8b5ae4ff79fSaurabh Shah    for (uint32_t i = 0; i < numDisplays; i++) {
1509171ec698c218df6eec5c91fe438f8b5ae4ff79fSaurabh Shah        hwc_display_contents_1_t *list = displays[i];
1511a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        switch(i) {
1521a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            case HWC_DISPLAY_PRIMARY:
1531a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ret = hwc_prepare_primary(dev, list);
1541a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                break;
1551a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            case HWC_DISPLAY_EXTERNAL:
1561a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ret = hwc_prepare_external(dev, list);
1571a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                break;
1581a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            default:
1591a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah                ret = -EINVAL;
16029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        }
16129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
1623e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return ret;
16329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
16429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
1655b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmedstatic int hwc_eventControl(struct hwc_composer_device_1* dev, int dpy,
16672cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed                             int event, int enabled)
16772cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed{
16872cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    int ret = 0;
169ff4f0254be575a264504687c407e0db2fd5573d7Naseer Ahmed
17072cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    hwc_context_t* ctx = (hwc_context_t*)(dev);
17172cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    private_module_t* m = reinterpret_cast<private_module_t*>(
17272cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed                ctx->mFbDev->common.module);
173eac8965bf481a17c6bca291c0864d0eb3c0eac07Iliyan Malchev    pthread_mutex_lock(&ctx->vstate.lock);
17472cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    switch(event) {
17572cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        case HWC_EVENT_VSYNC:
1761ef881ceed7b39b4034adba23368c2006bfd074cOmprakash Dhyade            if (ctx->vstate.enable == enabled)
1771ef881ceed7b39b4034adba23368c2006bfd074cOmprakash Dhyade                break;
178eac8965bf481a17c6bca291c0864d0eb3c0eac07Iliyan Malchev            ctx->vstate.enable = !!enabled;
179c7faa70f4a92f020f9d5df20a4ae4bb80be7a022Naseer Ahmed            pthread_cond_signal(&ctx->vstate.cond);
180eac8965bf481a17c6bca291c0864d0eb3c0eac07Iliyan Malchev            ALOGD_IF (VSYNC_DEBUG, "VSYNC state changed to %s",
181eac8965bf481a17c6bca291c0864d0eb3c0eac07Iliyan Malchev                      (enabled)?"ENABLED":"DISABLED");
182eac8965bf481a17c6bca291c0864d0eb3c0eac07Iliyan Malchev            break;
18372cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        default:
18472cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed            ret = -EINVAL;
18572cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    }
186eac8965bf481a17c6bca291c0864d0eb3c0eac07Iliyan Malchev    pthread_mutex_unlock(&ctx->vstate.lock);
18772cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    return ret;
18872cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed}
18972cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed
1905b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmedstatic int hwc_blank(struct hwc_composer_device_1* dev, int dpy, int blank)
1915b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed{
192934790c2fc35a02925f7abd872f16d3baa628712Naseer Ahmed    hwc_context_t* ctx = (hwc_context_t*)(dev);
193934790c2fc35a02925f7abd872f16d3baa628712Naseer Ahmed    private_module_t* m = reinterpret_cast<private_module_t*>(
194934790c2fc35a02925f7abd872f16d3baa628712Naseer Ahmed        ctx->mFbDev->common.module);
1953e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    int ret = 0;
1963e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    ALOGD("%s: Doing Dpy=%d, blank=%d", __FUNCTION__, dpy, blank);
1973e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    switch(dpy) {
1983e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_PRIMARY:
1993e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            if(blank) {
20032ff225e6d77baeb38925faba4b6b8457fab6b7bNaseer Ahmed                Locker::Autolock _l(ctx->mBlankLock);
201c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                ctx->mOverlay[dpy]->setState(ovutils::OV_CLOSED);
2023e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                ret = ioctl(m->framebuffer->fd, FBIOBLANK, FB_BLANK_POWERDOWN);
2033e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            } else {
2043e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                ret = ioctl(m->framebuffer->fd, FBIOBLANK, FB_BLANK_UNBLANK);
2053e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            }
2063e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
2073e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_EXTERNAL:
2083e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            if(blank) {
2093e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                //TODO actual
2103e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            } else {
2113e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            }
2123e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
2133e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        default:
2143e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            return -EINVAL;
2153e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
2163e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
2173e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    if(ret < 0) {
2183e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        ALOGE("%s: failed. Dpy=%d, blank=%d : %s",
2193e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                __FUNCTION__, dpy, blank, strerror(errno));
2203e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        return ret;
2215b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed    }
2223e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    ALOGD("%s: Done Dpy=%d, blank=%d", __FUNCTION__, dpy, blank);
2233e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    ctx->dpyAttr[dpy].isActive = !blank;
2245b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed    return 0;
2255b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed}
2265b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed
2275b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmedstatic int hwc_query(struct hwc_composer_device_1* dev,
22872cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed                     int param, int* value)
22972cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed{
23072cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    hwc_context_t* ctx = (hwc_context_t*)(dev);
23172cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    private_module_t* m = reinterpret_cast<private_module_t*>(
23272cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        ctx->mFbDev->common.module);
2333e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    int supported = HWC_DISPLAY_PRIMARY_BIT;
23472cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed
23572cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    switch (param) {
23672cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    case HWC_BACKGROUND_LAYER_SUPPORTED:
23772cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        // Not supported for now
23872cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        value[0] = 0;
23972cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        break;
2403e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    case HWC_VSYNC_PERIOD: //Not used for hwc > 1.1
2412e2798c71ad66cef2bd82967058c88f85d3501a8Saurabh Shah        value[0] = m->fps;
24272cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        ALOGI("fps: %d", value[0]);
24372cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        break;
2443e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    case HWC_DISPLAY_TYPES_SUPPORTED:
245c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        if(ctx->mMDP.hasOverlay)
246c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            supported |= HWC_DISPLAY_EXTERNAL_BIT;
2473e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        value[0] = supported;
2483e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        break;
24972cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    default:
25072cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        return -EINVAL;
25172cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    }
25272cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed    return 0;
25372cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed
25472cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed}
25572cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed
2563e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahstatic int hwc_set_primary(hwc_context_t *ctx, hwc_display_contents_1_t* list) {
257ae823e773536ee9b6cf97c575463f1a9902370d9Saurabh Shah    if (LIKELY(list && list->numHwLayers > 1) &&
258ae823e773536ee9b6cf97c575463f1a9902370d9Saurabh Shah        ctx->dpyAttr[HWC_DISPLAY_PRIMARY].isActive) {
259c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        uint32_t last = list->numHwLayers - 1;
260c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        hwc_layer_1_t *fbLayer = &list->hwLayers[last];
261c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
2628c8bfd2f827946ad88ea181d7f952d41ca4938feSaurabh Shah        hwc_sync(ctx, list, HWC_DISPLAY_PRIMARY);
2638c8bfd2f827946ad88ea181d7f952d41ca4938feSaurabh Shah
2643e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        VideoOverlay::draw(ctx, list, HWC_DISPLAY_PRIMARY);
2653e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        MDPComp::draw(ctx, list);
266c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
2673e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        //TODO We dont check for SKIP flag on this layer because we need PAN
2683e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        //always. Last layer is always FB
2693e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        if(list->hwLayers[last].compositionType == HWC_FRAMEBUFFER_TARGET) {
270c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            ctx->mFbDev->post(ctx->mFbDev, fbLayer->handle);
2713e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        }
2723e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
2733e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return 0;
2743e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah}
2753e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
2763e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahstatic int hwc_set_external(hwc_context_t *ctx,
2773e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        hwc_display_contents_1_t* list) {
278f83d4480f2c7e37374c4516750aae79c6b12eb79Kinjal Bhavsar    Locker::Autolock _l(ctx->mExtSetLock);
279c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
280ae823e773536ee9b6cf97c575463f1a9902370d9Saurabh Shah    if (LIKELY(list && list->numHwLayers > 1) &&
281c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        ctx->dpyAttr[HWC_DISPLAY_EXTERNAL].isActive &&
282c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        ctx->dpyAttr[HWC_DISPLAY_EXTERNAL].connected) {
2833e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        uint32_t last = list->numHwLayers - 1;
284c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        hwc_layer_1_t *fbLayer = &list->hwLayers[last];
285c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
286c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        hwc_sync(ctx, list, HWC_DISPLAY_EXTERNAL);
287c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
288c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        VideoOverlay::draw(ctx, list, HWC_DISPLAY_EXTERNAL);
289c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
290c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        private_handle_t *hnd = (private_handle_t *)fbLayer->handle;
291150806ae0ed82d1d26fa144a6950031570b06bfbSaurabh Shah        if(fbLayer->compositionType == HWC_FRAMEBUFFER_TARGET &&
292150806ae0ed82d1d26fa144a6950031570b06bfbSaurabh Shah                !(fbLayer->flags & HWC_SKIP_LAYER) && hnd) {
293c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            UIMirrorOverlay::draw(ctx, fbLayer);
2943e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        }
295150806ae0ed82d1d26fa144a6950031570b06bfbSaurabh Shah        ctx->mExtDisplay->post();
2963e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
2973e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return 0;
2983e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah}
2993e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
3005b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmedstatic int hwc_set(hwc_composer_device_1 *dev,
3015b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed                   size_t numDisplays,
3025b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed                   hwc_display_contents_1_t** displays)
30329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
30429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int ret = 0;
30529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    hwc_context_t* ctx = (hwc_context_t*)(dev);
30632ff225e6d77baeb38925faba4b6b8457fab6b7bNaseer Ahmed    Locker::Autolock _l(ctx->mBlankLock);
307c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
3081a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah    for(uint32_t i = 0; i < HWC_NUM_DISPLAY_TYPES; i++) {
3091a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah        if(!ctx->overlayInUse[i])
3101a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah            ctx->mOverlay[i]->setState(ovutils::OV_CLOSED);
3111a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah    }
3121a8cda0b2cb535656eb18bf5dc07a02fcddec9abSaurabh Shah
3133e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    for (uint32_t i = 0; i < numDisplays; i++) {
3145b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed        hwc_display_contents_1_t* list = displays[i];
3153e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        switch(i) {
3163e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            case HWC_DISPLAY_PRIMARY:
3173e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                ret = hwc_set_primary(ctx, list);
318c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                break;
3193e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            case HWC_DISPLAY_EXTERNAL:
3203e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                ret = hwc_set_external(ctx, list);
321c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                break;
3223e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            default:
3233e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                ret = -EINVAL;
3245b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed        }
3253e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
3263e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return ret;
3273e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah}
328f48aef64b218d42bd2ede62dcb03a3d7831ebbf9Naseer Ahmed
3293e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahint hwc_getDisplayConfigs(struct hwc_composer_device_1* dev, int disp,
3303e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        uint32_t* configs, size_t* numConfigs) {
3313e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    int ret = 0;
332c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah    hwc_context_t* ctx = (hwc_context_t*)(dev);
3333e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    //in 1.1 there is no way to choose a config, report as config id # 0
3343e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    //This config is passed to getDisplayAttributes. Ignore for now.
3353e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    switch(disp) {
3363e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_PRIMARY:
337c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            if(*numConfigs > 0) {
338c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                configs[0] = 0;
339c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                *numConfigs = 1;
340c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            }
341c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            ret = 0; //NO_ERROR
3423e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
3433e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_EXTERNAL:
344c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            ret = -1; //Not connected
345c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            if(ctx->dpyAttr[HWC_DISPLAY_EXTERNAL].connected) {
346c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                ret = 0; //NO_ERROR
347c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                if(*numConfigs > 0) {
348c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                    configs[0] = 0;
349c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                    *numConfigs = 1;
350c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                }
351c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            }
3523e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
3535b6708ac87dc9681b3dd142b82702a8b995c6e22Naseer Ahmed    }
35429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    return ret;
35529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
35629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
3573e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shahint hwc_getDisplayAttributes(struct hwc_composer_device_1* dev, int disp,
3583e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        uint32_t config, const uint32_t* attributes, int32_t* values) {
3593e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
3603e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    hwc_context_t* ctx = (hwc_context_t*)(dev);
361c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah    //If hotpluggable displays are inactive return error
362c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah    if(disp == HWC_DISPLAY_EXTERNAL && !ctx->dpyAttr[disp].connected) {
363c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah        return -1;
364c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah    }
365c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah
3663e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    //From HWComposer
3673e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    static const uint32_t DISPLAY_ATTRIBUTES[] = {
3683e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        HWC_DISPLAY_VSYNC_PERIOD,
3693e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        HWC_DISPLAY_WIDTH,
3703e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        HWC_DISPLAY_HEIGHT,
3713e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        HWC_DISPLAY_DPI_X,
3723e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        HWC_DISPLAY_DPI_Y,
3733e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        HWC_DISPLAY_NO_ATTRIBUTE,
3743e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    };
3753e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
3763e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    const int NUM_DISPLAY_ATTRIBUTES = (sizeof(DISPLAY_ATTRIBUTES) /
3773e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            sizeof(DISPLAY_ATTRIBUTES)[0]);
3783e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
3793e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    for (size_t i = 0; i < NUM_DISPLAY_ATTRIBUTES - 1; i++) {
3803e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        switch (attributes[i]) {
3813e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_VSYNC_PERIOD:
3823e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            values[i] = ctx->dpyAttr[disp].vsync_period;
3833e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
3843e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_WIDTH:
3853e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            values[i] = ctx->dpyAttr[disp].xres;
386c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            ALOGD("%s disp = %d, width = %d",__FUNCTION__, disp,
387c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                    ctx->dpyAttr[disp].xres);
3883e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
3893e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_HEIGHT:
3903e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            values[i] = ctx->dpyAttr[disp].yres;
391c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah            ALOGD("%s disp = %d, height = %d",__FUNCTION__, disp,
392c4d034f4b8d12953632907d30c0b78856d829579Saurabh Shah                    ctx->dpyAttr[disp].yres);
3933e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
3943e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_DPI_X:
3957b80d9c8cb345f7020093e0afb691bf3a72deec6Naseer Ahmed            values[i] = (int32_t) (ctx->dpyAttr[disp].xdpi*1000.0);
3963e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
3973e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        case HWC_DISPLAY_DPI_Y:
3987b80d9c8cb345f7020093e0afb691bf3a72deec6Naseer Ahmed            values[i] = (int32_t) (ctx->dpyAttr[disp].ydpi*1000.0);
3993e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            break;
4003e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        default:
4013e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            ALOGE("Unknown display attribute %d",
4023e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah                    attributes[i]);
4033e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah            return -EINVAL;
4043e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        }
4053e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    }
4063e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah    return 0;
4073e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah}
4083e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah
40929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedstatic int hwc_device_close(struct hw_device_t *dev)
41029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
41129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if(!dev) {
41272cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        ALOGE("%s: NULL device pointer", __FUNCTION__);
41329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        return -1;
41429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
41529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    closeContext((hwc_context_t*)dev);
41629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    free(dev);
41729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
41829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    return 0;
41929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
42029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
42129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedstatic int hwc_device_open(const struct hw_module_t* module, const char* name,
42229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                           struct hw_device_t** device)
42329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
42429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int status = -EINVAL;
42529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
42629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if (!strcmp(name, HWC_HARDWARE_COMPOSER)) {
42729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        struct hwc_context_t *dev;
42829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        dev = (hwc_context_t*)malloc(sizeof(*dev));
42929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        memset(dev, 0, sizeof(*dev));
43072cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed
43172cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        //Initialize hwc context
43229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        initContext(dev);
43372cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed
43472cf9762f84aab07faab86e35fe830b63ec54d72Naseer Ahmed        //Setup HWC methods
4353e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.common.tag          = HARDWARE_DEVICE_TAG;
4363e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.common.version      = HWC_DEVICE_API_VERSION_1_1;
4373e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.common.module       = const_cast<hw_module_t*>(module);
4383e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.common.close        = hwc_device_close;
4393e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.prepare             = hwc_prepare;
4403e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.set                 = hwc_set;
4413e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.eventControl        = hwc_eventControl;
4423e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.blank               = hwc_blank;
4433e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.query               = hwc_query;
4443e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.registerProcs       = hwc_registerProcs;
4453e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.dump                = NULL;
4463e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.getDisplayConfigs   = hwc_getDisplayConfigs;
4473e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        dev->device.getDisplayAttributes = hwc_getDisplayAttributes;
4483e858ebde3f2b4e762af8f7f2808d45ba59b890dSaurabh Shah        *device = &dev->device.common;
44929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        status = 0;
45029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
45129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    return status;
45229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
453