/*
 * Copyright (C) 2008 The Android Open Source Project
 * Copyright@ Samsung Electronics Co. LTD
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

/*!
 * \file      exynos_gscaler.c
 * \brief     header file for Gscaler HAL
 * \author    ShinWon Lee (shinwon.lee@samsung.com)
 * \date      2012/01/09
 *
 * <b>Revision History: </b>
 * - 2012.01.09 : ShinWon Lee(shinwon.lee@samsung.com) \n
 *   Create
 *
 * - 2012.02.07 : ShinWon Lee(shinwon.lee@samsung.com) \n
 *   Change file name to exynos_gscaler.h
 *
 * - 2012.02.09 : Sangwoo, Parkk(sw5771.park@samsung.com) \n
 *   Use Multiple Gscaler by Multiple Process
 *
 * - 2012.02.20 : Sangwoo, Park(sw5771.park@samsung.com) \n
 *   Add exynos_gsc_set_rotation() API
 *
 * - 2012.02.20 : ShinWon Lee(shinwon.lee@samsung.com) \n
 *   Add size constrain
 *
 */

//#define LOG_NDEBUG 0
#include "exynos_gsc_utils.h"
#include "content_protect.h"

static int exynos_gsc_m2m_wait_frame_done(void *handle);
static int exynos_gsc_m2m_stop(void *handle);

static unsigned int m_gsc_get_plane_count(
    int v4l_pixel_format)
{
    int plane_count = 0;

    switch (v4l_pixel_format) {
    case V4L2_PIX_FMT_RGB32:
    case V4L2_PIX_FMT_BGR32:
    case V4L2_PIX_FMT_RGB24:
    case V4L2_PIX_FMT_RGB565:
    case V4L2_PIX_FMT_RGB555X:
    case V4L2_PIX_FMT_RGB444:
    case V4L2_PIX_FMT_YUYV:
    case V4L2_PIX_FMT_UYVY:
    case V4L2_PIX_FMT_NV16:
    case V4L2_PIX_FMT_NV61:
        plane_count = 1;
        break;
    case V4L2_PIX_FMT_NV12M:
    case V4L2_PIX_FMT_NV12MT_16X16:
    case V4L2_PIX_FMT_NV12:
    case V4L2_PIX_FMT_NV21:
    case V4L2_PIX_FMT_NV21M:
        plane_count = 2;
        break;
    case V4L2_PIX_FMT_YVU420M:
    case V4L2_PIX_FMT_YUV422P:
    case V4L2_PIX_FMT_YUV420M:
        plane_count = 3;
        break;
    default:
        ALOGE("%s::unmatched v4l_pixel_format color_space(0x%x)\n",
             __func__, v4l_pixel_format);
        plane_count = -1;
        break;
    }

    return plane_count;
}

static unsigned int m_gsc_get_plane_size(
    unsigned int *plane_size,
    unsigned int  width,
    unsigned int  height,
    int           v4l_pixel_format)
{
    switch (v4l_pixel_format) {
    /* 1 plane */
    case V4L2_PIX_FMT_RGB32:
    case V4L2_PIX_FMT_BGR32:
        plane_size[0] = width * height * 4;
        plane_size[1] = 0;
        plane_size[2] = 0;
        break;
    case V4L2_PIX_FMT_RGB24:
        plane_size[0] = width * height * 3;
        plane_size[1] = 0;
        plane_size[2] = 0;
        break;
    case V4L2_PIX_FMT_RGB565:
    case V4L2_PIX_FMT_RGB555X:
    case V4L2_PIX_FMT_RGB444:
    case V4L2_PIX_FMT_YUYV:
    case V4L2_PIX_FMT_UYVY:
        plane_size[0] = width * height * 2;
        plane_size[1] = 0;
        plane_size[2] = 0;
        break;
    /* 2 planes */
    case V4L2_PIX_FMT_NV12M:
    case V4L2_PIX_FMT_NV12:
    case V4L2_PIX_FMT_NV21:
    case V4L2_PIX_FMT_NV21M:
        plane_size[0] = width * height;
        plane_size[1] = width * (height / 2);
        plane_size[2] = 0;
        break;
    case V4L2_PIX_FMT_NV16:
    case V4L2_PIX_FMT_NV61:
        plane_size[0] = width * height * 2;
        plane_size[1] = 0;
        plane_size[2] = 0;
        break;
    case V4L2_PIX_FMT_NV12MT_16X16:
        plane_size[0] = ALIGN(width, 16) * ALIGN(height, 16);
        plane_size[1] = ALIGN(width, 16) * ALIGN(height / 2, 8);
        plane_size[2] = 0;
        break;
    /* 3 planes */
    case V4L2_PIX_FMT_YVU420M:
    case V4L2_PIX_FMT_YUV422P:
        plane_size[0] = width * height;
        plane_size[1] = (width / 2) * (height / 2);
        plane_size[2] = (width / 2) * (height / 2);
        break;
    default:
        ALOGE("%s::unmatched v4l_pixel_format color_space(0x%x)\n",
             __func__, v4l_pixel_format);
        return -1;
        break;
    }

    return 0;
}

static int m_exynos_gsc_multiple_of_n(
    int number, int N)
{
    int result = number;
    switch (N) {
    case 1:
    case 2:
    case 4:
    case 8:
    case 16:
    case 32:
    case 64:
    case 128:
    case 256:
        result = (number - (number & (N-1)));
        break;
    default:
        result = number - (number % N);
        break;
    }
    return result;
}

static bool m_exynos_gsc_check_src_size(
    unsigned int *w,      unsigned int *h,
    unsigned int *crop_x, unsigned int *crop_y,
    unsigned int *crop_w, unsigned int *crop_h,
    int v4l2_colorformat)
{
    if (*w < GSC_MIN_W_SIZE || *h < GSC_MIN_H_SIZE) {
        ALOGE("%s::too small size (w : %d < %d) (h : %d < %d)",
            __func__, GSC_MIN_W_SIZE, *w, GSC_MIN_H_SIZE, *h);
        return false;
    }

    if (*crop_w < GSC_MIN_W_SIZE || *crop_h < GSC_MIN_H_SIZE) {
        ALOGE("%s::too small size (w : %d < %d) (h : %d < %d)",
            __func__, GSC_MIN_W_SIZE,* crop_w, GSC_MIN_H_SIZE, *crop_h);
        return false;
    }

    switch (v4l2_colorformat) {
    // YUV420
    case V4L2_PIX_FMT_YUV420M:
    case V4L2_PIX_FMT_YVU420M:
    case V4L2_PIX_FMT_NV12M:
    case V4L2_PIX_FMT_NV12MT:
    case V4L2_PIX_FMT_NV21:
    case V4L2_PIX_FMT_NV21M:
        *w = (*w + 15) & ~15;
        *h = (*h + 15) & ~15;
        //*w      = m_exynos_gsc_multiple_of_n(*w, 16);
        //*h      = m_exynos_gsc_multiple_of_n(*h, 16);
        *crop_w = m_exynos_gsc_multiple_of_n(*crop_w, 4);
        *crop_h = m_exynos_gsc_multiple_of_n(*crop_h, 4);
        break;
    // YUV422
    case V4L2_PIX_FMT_YUYV:
    case V4L2_PIX_FMT_YUV422P:
    case V4L2_PIX_FMT_UYVY:
    case V4L2_PIX_FMT_NV16:
    case V4L2_PIX_FMT_YVYU:
    case V4L2_PIX_FMT_VYUY:
        *h = (*h + 7) & ~7;
        //*h      = m_exynos_gsc_multiple_of_n(*h, 8);
        *crop_w = m_exynos_gsc_multiple_of_n(*crop_w, 4);
        *crop_h = m_exynos_gsc_multiple_of_n(*crop_h, 2);
        break;
    // RGB
    case V4L2_PIX_FMT_RGB32:
    case V4L2_PIX_FMT_RGB24:
    case V4L2_PIX_FMT_RGB565:
    case V4L2_PIX_FMT_BGR32:
    case V4L2_PIX_FMT_RGB555X:
    case V4L2_PIX_FMT_RGB444:
    default:
        *h = (*h + 7) & ~7;
        //*h      = m_exynos_gsc_multiple_of_n(*h, 8);
        *crop_w = m_exynos_gsc_multiple_of_n(*crop_w, 2);
        *crop_h = m_exynos_gsc_multiple_of_n(*crop_h, 2);
        break;
    }

    return true;
}

static bool m_exynos_gsc_check_dst_size(
    unsigned int *w,      unsigned int *h,
    unsigned int *crop_x, unsigned int *crop_y,
    unsigned int *crop_w, unsigned int *crop_h,
    int v4l2_colorformat,
    int rotation)
{
    unsigned int *new_w;
    unsigned int *new_h;
    unsigned int *new_crop_w;
    unsigned int *new_crop_h;

        new_w = w;
        new_h = h;
        new_crop_w = crop_w;
        new_crop_h = crop_h;

    if (*w < GSC_MIN_W_SIZE || *h < GSC_MIN_H_SIZE) {
        ALOGE("%s::too small size (w : %d < %d) (h : %d < %d)",
            __func__, GSC_MIN_W_SIZE, *w, GSC_MIN_H_SIZE, *h);
        return false;
    }

    if (*crop_w < GSC_MIN_W_SIZE || *crop_h < GSC_MIN_H_SIZE) {
        ALOGE("%s::too small size (w : %d < %d) (h : %d < %d)",
            __func__, GSC_MIN_W_SIZE,* crop_w, GSC_MIN_H_SIZE, *crop_h);
        return false;
    }

    switch (v4l2_colorformat) {
    // YUV420
    case V4L2_PIX_FMT_NV12M:
    case V4L2_PIX_FMT_NV12MT:
    case V4L2_PIX_FMT_NV21:
    case V4L2_PIX_FMT_NV21M:
    case V4L2_PIX_FMT_YUV420M:
    case V4L2_PIX_FMT_YVU420M:
        *new_w = m_exynos_gsc_multiple_of_n(*new_w, 2);
        *new_h = m_exynos_gsc_multiple_of_n(*new_h, 2);
        break;
    // YUV422
    case V4L2_PIX_FMT_YUYV:
    case V4L2_PIX_FMT_YUV422P:
    case V4L2_PIX_FMT_UYVY:
    case V4L2_PIX_FMT_NV16:
    case V4L2_PIX_FMT_YVYU:
    case V4L2_PIX_FMT_VYUY:
        *new_w = m_exynos_gsc_multiple_of_n(*new_w, 2);
        break;
    // RGB
    case V4L2_PIX_FMT_RGB32:
    case V4L2_PIX_FMT_RGB24:
    case V4L2_PIX_FMT_RGB565:
    case V4L2_PIX_FMT_BGR32:
    case V4L2_PIX_FMT_RGB555X:
    case V4L2_PIX_FMT_RGB444:
    default:
        break;
    }

    return true;
}

static int m_exynos_gsc_output_create(
    struct GSC_HANDLE *gsc_handle,
    int dev_num,
    int out_mode)
{
    struct media_device *media0;
    struct media_entity *gsc_sd_entity;
    struct media_entity *gsc_vd_entity;
    struct media_entity *sink_sd_entity;
    struct media_link *links;
    char node[32];
    char devname[32];
    unsigned int cap;
    int         i;
    int         fd = 0;

    Exynos_gsc_In();

    if ((out_mode != GSC_OUT_FIMD) &&
        (out_mode != GSC_OUT_TV))
        return -1;

    gsc_handle->out_mode = out_mode;
    /* GSCX => FIMD_WINX : arbitrary linking is not allowed */
    if ((out_mode == GSC_OUT_FIMD) &&
        (dev_num > 2))
        return -1;

    /* media0 */
    sprintf(node, "%s%d", PFX_NODE_MEDIADEV, 0);
    media0 = exynos_media_open(node);
    if (media0 == NULL) {
        ALOGE("%s::exynos_media_open failed (node=%s)", __func__, node);
        return false;
    }

    /* Get the sink subdev entity by name and make the node of sink subdev*/
    if (out_mode == GSC_OUT_FIMD)
        sprintf(devname, PFX_FIMD_ENTITY, dev_num);
    else
        sprintf(devname, PFX_MXR_ENTITY, 0);

    sink_sd_entity = exynos_media_get_entity_by_name(media0, devname, strlen(devname));
    sink_sd_entity->fd = exynos_subdev_open_devname(devname, O_RDWR);
    if ( sink_sd_entity->fd < 0) {
        ALOGE("%s:: failed to open sink subdev node", __func__);
        goto gsc_output_err;
    }

    /* get GSC video dev & sub dev entity by name*/
    sprintf(devname, PFX_GSC_VIDEODEV_ENTITY, dev_num);
    gsc_vd_entity= exynos_media_get_entity_by_name(media0, devname, strlen(devname));

    sprintf(devname, PFX_GSC_SUBDEV_ENTITY, dev_num);
    gsc_sd_entity= exynos_media_get_entity_by_name(media0, devname, strlen(devname));

    /* gsc sub-dev open */
    sprintf(devname, PFX_GSC_SUBDEV_ENTITY, dev_num);
    gsc_sd_entity->fd = exynos_subdev_open_devname(devname, O_RDWR);

    /* setup link : GSC : video device --> sub device */
    for (i = 0; i < (int) gsc_vd_entity->num_links; i++) {
        links = &gsc_vd_entity->links[i];

        if (links == NULL ||
            links->source->entity != gsc_vd_entity ||
            links->sink->entity   != gsc_sd_entity) {
            continue;
        } else if (exynos_media_setup_link(media0,  links->source,  links->sink, MEDIA_LNK_FL_ENABLED) < 0) {
            ALOGE("%s::exynos_media_setup_link [src.entity=%d->sink.entity=%d] failed",
                  __func__, links->source->entity->info.id, links->sink->entity->info.id);
            return -1;
        }
    }

    /* setup link : GSC: sub device --> sink device */
    for (i = 0; i < (int) gsc_sd_entity->num_links; i++) {
        links = &gsc_sd_entity->links[i];

        if (links == NULL || links->source->entity != gsc_sd_entity ||
                             links->sink->entity   != sink_sd_entity) {
            continue;
        } else if (exynos_media_setup_link(media0,  links->source,  links->sink, MEDIA_LNK_FL_ENABLED) < 0) {
            ALOGE("%s::exynos_media_setup_link [src.entity=%d->sink.entity=%d] failed",
                  __func__, links->source->entity->info.id, links->sink->entity->info.id);
            return -1;
        }
    }

    /* gsc video-dev open */
    sprintf(devname, PFX_GSC_VIDEODEV_ENTITY, dev_num);
    gsc_vd_entity->fd = exynos_v4l2_open_devname(devname, O_RDWR);
    cap = V4L2_CAP_STREAMING |
          V4L2_CAP_VIDEO_OUTPUT_MPLANE;

    if (exynos_v4l2_querycap(gsc_vd_entity->fd, cap) == false) {
        ALOGE("%s::exynos_v4l2_querycap() fail", __func__);
        goto gsc_output_err;
    }
    gsc_handle->gsc_sd_entity = gsc_sd_entity;
    gsc_handle->gsc_vd_entity = gsc_vd_entity;
    gsc_handle->sink_sd_entity = sink_sd_entity;
    gsc_handle->media0 = media0;

    Exynos_gsc_Out();

    return 0;

gsc_output_err:
    /* to do */
    return -1;

}

static int m_exynos_gsc_m2m_create(
    int dev)
{
    int          fd = 0;
    int          video_node_num;
    unsigned int cap;
    char         node[32];

    Exynos_gsc_In();

    switch(dev) {
    case 0:
        video_node_num = NODE_NUM_GSC_0;
        break;
    case 1:
        video_node_num = NODE_NUM_GSC_1;
        break;
    case 2:
        video_node_num = NODE_NUM_GSC_2;
        break;
    case 3:
        video_node_num = NODE_NUM_GSC_3;
        break;
    default:
        ALOGE("%s::unexpected dev(%d) fail", __func__, dev);
        return -1;
        break;
    }

    sprintf(node, "%s%d", PFX_NODE_GSC, video_node_num);
    fd = exynos_v4l2_open(node, O_RDWR);
    if (fd < 0) {
        ALOGE("%s::exynos_v4l2_open(%s) fail", __func__, node);
        return -1;
    }

    cap = V4L2_CAP_STREAMING |
          V4L2_CAP_VIDEO_OUTPUT_MPLANE |
          V4L2_CAP_VIDEO_CAPTURE_MPLANE;

    if (exynos_v4l2_querycap(fd, cap) == false) {
        ALOGE("%s::exynos_v4l2_querycap() fail", __func__);
        if (0 < fd)
            close(fd);
        fd = 0;
        return -1;
    }

    Exynos_gsc_Out();

    return fd;
}


static bool m_exynos_gsc_out_destroy(struct GSC_HANDLE *gsc_handle)
{
    struct media_link * links;
    int i;

    Exynos_gsc_In();

    if (gsc_handle == NULL) {
        ALOGE("%s::gsc_handle is NULL", __func__);
        return false;
    }

    if (gsc_handle->src.stream_on == true) {
        if (exynos_gsc_out_stop((void *)gsc_handle) < 0)
            ALOGE("%s::exynos_gsc_out_stop() fail", __func__);

            gsc_handle->src.stream_on = false;
    }

    /* unlink : gscaler-out --> fimd */
        for (i = 0; i < (int) gsc_handle->gsc_sd_entity->num_links; i++) {
            links = &gsc_handle->gsc_sd_entity->links[i];

            if (links == NULL || links->source->entity != gsc_handle->gsc_sd_entity ||
                                 links->sink->entity   != gsc_handle->sink_sd_entity) {
                continue;
            } else if (exynos_media_setup_link(gsc_handle->media0,  links->source,
                                                                        links->sink, 0) < 0) {
                ALOGE("%s::exynos_media_setup_unlink [src.entity=%d->sink.entity=%d] failed",
                      __func__, links->source->entity->info.id, links->sink->entity->info.id);
            }
        }

        close(gsc_handle->gsc_vd_entity->fd);
        close(gsc_handle->gsc_sd_entity->fd);
        gsc_handle->gsc_vd_entity->fd = -1;
        gsc_handle->gsc_vd_entity->fd = -1;

        Exynos_gsc_Out();

        return true;

}

static bool m_exynos_gsc_destroy(
    struct GSC_HANDLE *gsc_handle)
{
    Exynos_gsc_In();

    /* just in case, we call stop here because we cannot afford to leave
     * secure side protection on if things failed.
     */
    exynos_gsc_m2m_stop(gsc_handle);

    if (0 < gsc_handle->gsc_fd)
        close(gsc_handle->gsc_fd);
    gsc_handle->gsc_fd = 0;

    Exynos_gsc_Out();

    return true;
}

bool m_exynos_gsc_find_and_trylock_and_create(
    struct GSC_HANDLE *gsc_handle)
{
    int          i                 = 0;
    bool         flag_find_new_gsc = false;
    unsigned int total_sleep_time  = 0;

    Exynos_gsc_In();

    do {
        for (i = 0; i < NUM_OF_GSC_HW; i++) {
            // HACK : HWComposer, HDMI uses gscaler with their own code.
            //        So, This obj_mutex cannot defense their open()
            if (i == 0 || i == 3)
                continue;

            if (exynos_mutex_trylock(gsc_handle->obj_mutex[i]) == true) {

                // destroy old one.
                m_exynos_gsc_destroy(gsc_handle);

                // create new one.
                gsc_handle->gsc_id = i;
                gsc_handle->gsc_fd = m_exynos_gsc_m2m_create(i);
                if (gsc_handle->gsc_fd < 0) {
                    gsc_handle->gsc_fd = 0;
                    exynos_mutex_unlock(gsc_handle->obj_mutex[i]);
                    continue;
                }

                if (gsc_handle->cur_obj_mutex)
                    exynos_mutex_unlock(gsc_handle->cur_obj_mutex);

                gsc_handle->cur_obj_mutex = gsc_handle->obj_mutex[i];

                flag_find_new_gsc = true;
                break;
            }
        }

        // waiting for another process doesn't use gscaler.
        // we need to make decision how to do.
        if (flag_find_new_gsc == false) {
            usleep(GSC_WAITING_TIME_FOR_TRYLOCK);
            total_sleep_time += GSC_WAITING_TIME_FOR_TRYLOCK;
            ALOGV("%s::waiting for anthere process doens't use gscaler", __func__);
        }

    } while(   flag_find_new_gsc == false
            && total_sleep_time < MAX_GSC_WAITING_TIME_FOR_TRYLOCK);

    if (flag_find_new_gsc == false)
        ALOGE("%s::we don't have no available gsc.. fail", __func__);

    Exynos_gsc_Out();

    return flag_find_new_gsc;
}

static bool m_exynos_gsc_set_format(
    int              fd,
    struct gsc_info *info)
{
    Exynos_gsc_In();

    struct v4l2_requestbuffers req_buf;
    int                        plane_count;

    plane_count = m_gsc_get_plane_count(info->v4l2_colorformat);
    if (plane_count < 0) {
        ALOGE("%s::not supported v4l2_colorformat", __func__);
        return false;
    }

    if (exynos_v4l2_s_ctrl(fd, V4L2_CID_ROTATE, info->rotation) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_ROTATE) fail", __func__);
        return false;
    }

    if (exynos_v4l2_s_ctrl(fd, V4L2_CID_VFLIP, info->flip_horizontal) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_VFLIP) fail", __func__);
        return false;
    }

    if (exynos_v4l2_s_ctrl(fd, V4L2_CID_HFLIP, info->flip_vertical) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_HFLIP) fail", __func__);
        return false;
    }

    if (exynos_v4l2_s_ctrl(fd, V4L2_CID_CSC_RANGE, info->csc_range) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_CSC_RANGE) fail", __func__);
        return false;
    }
    info->format.type = info->buf_type;
    info->format.fmt.pix_mp.width       = info->width;
    info->format.fmt.pix_mp.height      = info->height;
    info->format.fmt.pix_mp.pixelformat = info->v4l2_colorformat;
    info->format.fmt.pix_mp.field       = V4L2_FIELD_ANY;
    info->format.fmt.pix_mp.num_planes  = plane_count;

    if (exynos_v4l2_s_fmt(fd, &info->format) < 0) {
        ALOGE("%s::exynos_v4l2_s_fmt() fail", __func__);
        return false;
    }

    info->crop.type     = info->buf_type;
    info->crop.c.left   = info->crop_left;
    info->crop.c.top    = info->crop_top;
    info->crop.c.width  = info->crop_width;
    info->crop.c.height = info->crop_height;

    if (exynos_v4l2_s_crop(fd, &info->crop) < 0) {
        ALOGE("%s::exynos_v4l2_s_crop() fail", __func__);
        return false;
    }

    if (exynos_v4l2_s_ctrl(fd, V4L2_CID_CACHEABLE, info->cacheable) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl() fail", __func__);
        return false;
    }

    req_buf.count  = 1;
    req_buf.type   = info->buf_type;
    req_buf.memory = V4L2_MEMORY_DMABUF;
    if (exynos_v4l2_reqbufs(fd, &req_buf) < 0) {
        ALOGE("%s::exynos_v4l2_reqbufs() fail", __func__);
        return false;
    }

    Exynos_gsc_Out();

    return true;
}

static bool m_exynos_gsc_set_addr(
    int              fd,
    struct gsc_info *info)
{
    unsigned int i;
    unsigned int plane_size[NUM_OF_GSC_PLANES];

    m_gsc_get_plane_size(plane_size,
                         info->width,
                         info->height,
                         info->v4l2_colorformat);

    info->buffer.index    = 0;
    info->buffer.flags    = V4L2_BUF_FLAG_USE_SYNC;
    info->buffer.type     = info->buf_type;
    info->buffer.memory   = V4L2_MEMORY_DMABUF;
    info->buffer.m.planes = info->planes;
    info->buffer.length   = info->format.fmt.pix_mp.num_planes;
    info->buffer.reserved = info->acquireFenceFd;

    for (i = 0; i < info->format.fmt.pix_mp.num_planes; i++) {
        info->buffer.m.planes[i].m.fd = (int)info->addr[i];
        info->buffer.m.planes[i].length    = plane_size[i];
        info->buffer.m.planes[i].bytesused = 0;
    }

    if (exynos_v4l2_qbuf(fd, &info->buffer) < 0) {
        ALOGE("%s::exynos_v4l2_qbuf() fail", __func__);
        return false;
    }
    info->buffer_queued = true;

    info->releaseFenceFd = info->buffer.reserved;

    return true;
}

void *exynos_gsc_create(
    void)
{
    int i     = 0;
    int op_id = 0;
    char mutex_name[32];

    Exynos_gsc_In();

    struct GSC_HANDLE *gsc_handle = (struct GSC_HANDLE *)malloc(sizeof(struct GSC_HANDLE));
    if (gsc_handle == NULL) {
        ALOGE("%s::malloc(struct GSC_HANDLE) fail", __func__);
        goto err;
    }

    gsc_handle->gsc_fd = 0;
    memset(&gsc_handle->src, 0, sizeof(struct gsc_info));
    memset(&gsc_handle->dst, 0, sizeof(struct gsc_info));

    gsc_handle->src.buf_type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
    gsc_handle->dst.buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;

    gsc_handle->op_mutex = NULL;
    for (i = 0; i < NUM_OF_GSC_HW; i++)
        gsc_handle->obj_mutex[i] = NULL;

    gsc_handle->cur_obj_mutex = NULL;
    gsc_handle->flag_local_path = false;
    gsc_handle->flag_exclusive_open = false;

    srand(time(NULL));
    op_id = rand() % 1000000; // just make random id
    sprintf(mutex_name, "%sOp%d", LOG_TAG, op_id);
    gsc_handle->op_mutex = exynos_mutex_create(EXYNOS_MUTEX_TYPE_PRIVATE, mutex_name);
    if (gsc_handle->op_mutex == NULL) {
        ALOGE("%s::exynos_mutex_create(%s) fail", __func__, mutex_name);
        goto err;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    // check if it is available
    for (i = 0; i < NUM_OF_GSC_HW; i++) {
        sprintf(mutex_name, "%sObject%d", LOG_TAG, i);

        gsc_handle->obj_mutex[i] = exynos_mutex_create(EXYNOS_MUTEX_TYPE_SHARED, mutex_name);
        if (gsc_handle->obj_mutex[i] == NULL) {
            ALOGE("%s::exynos_mutex_create(%s) fail", __func__, mutex_name);
            goto err;
        }
    }

    if (m_exynos_gsc_find_and_trylock_and_create(gsc_handle) == false) {
        ALOGE("%s::m_exynos_gsc_find_and_trylock_and_create() fail", __func__);
        goto err;
    }

    exynos_mutex_unlock(gsc_handle->cur_obj_mutex);
    exynos_mutex_unlock(gsc_handle->op_mutex);

    return (void *)gsc_handle;

err:
    if (gsc_handle) {
        m_exynos_gsc_destroy(gsc_handle);

        if (gsc_handle->cur_obj_mutex)
            exynos_mutex_unlock(gsc_handle->cur_obj_mutex);

        for (i = 0; i < NUM_OF_GSC_HW; i++) {
            if ((gsc_handle->obj_mutex[i] != NULL) &&
                (exynos_mutex_get_created_status(gsc_handle->obj_mutex[i]) == true)) {
                if (exynos_mutex_destroy(gsc_handle->obj_mutex[i]) == false)
                    ALOGE("%s::exynos_mutex_destroy() fail", __func__);
            }
        }

        if (gsc_handle->op_mutex)
            exynos_mutex_unlock(gsc_handle->op_mutex);

        if (exynos_mutex_destroy(gsc_handle->op_mutex) == false)
            ALOGE("%s::exynos_mutex_destroy(op_mutex) fail", __func__);

        free(gsc_handle);
    }

    Exynos_gsc_Out();

    return NULL;
}

void *exynos_gsc_reserve(int dev_num)
{
    char mutex_name[32];
    unsigned int total_sleep_time  = 0;
    bool    gsc_flag = false;

    if ((dev_num < 0) || (dev_num >= NUM_OF_GSC_HW)) {
        ALOGE("%s::fail:: dev_num is not valid(%d) ", __func__, dev_num);
        return NULL;
    }

    struct GSC_HANDLE *gsc_handle = (struct GSC_HANDLE *)malloc(sizeof(struct GSC_HANDLE));
    if (gsc_handle == NULL) {
        ALOGE("%s::malloc(struct GSC_HANDLE) fail", __func__);
        goto err;
    }

    gsc_handle->gsc_fd = -1;
    gsc_handle->op_mutex = NULL;
    gsc_handle->cur_obj_mutex = NULL;

    sprintf(mutex_name, "%sObject%d", LOG_TAG, dev_num);
    gsc_handle->cur_obj_mutex = exynos_mutex_create(EXYNOS_MUTEX_TYPE_SHARED, mutex_name);
    if (gsc_handle->cur_obj_mutex == NULL) {
        ALOGE("%s::exynos_mutex_create(%s) fail", __func__, mutex_name);
        goto err;
    }

    do {
        if (exynos_mutex_trylock(gsc_handle->cur_obj_mutex) == true) {
            gsc_flag = true;
            break;
        }
        usleep(GSC_WAITING_TIME_FOR_TRYLOCK);
        total_sleep_time += GSC_WAITING_TIME_FOR_TRYLOCK;
        ALOGV("%s::waiting for another process to release the requested gscaler", __func__);
    } while(total_sleep_time < MAX_GSC_WAITING_TIME_FOR_TRYLOCK);

    if (gsc_flag == true)
         return (void *)gsc_handle;

err:
    if (gsc_handle) {
        free(gsc_handle);
    }

    return NULL;
}

void exynos_gsc_release(void *handle)
{
    struct GSC_HANDLE *gsc_handle = (struct GSC_HANDLE *)handle;

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return;
    }

    exynos_mutex_unlock(gsc_handle->cur_obj_mutex);
    exynos_mutex_destroy(gsc_handle->cur_obj_mutex);
    free(gsc_handle);
    return;
}

void *exynos_gsc_create_exclusive(
    int dev_num,
    int mode,
    int out_mode,
    int allow_drm)
{
    int i     = 0;
    int op_id = 0;
    char mutex_name[32];
    unsigned int total_sleep_time  = 0;
    bool    gsc_flag = false;
    int ret = 0;

    Exynos_gsc_In();

    if ((dev_num < 0) || (dev_num >= NUM_OF_GSC_HW)) {
        ALOGE("%s::fail:: dev_num is not valid(%d) ", __func__, dev_num);
        return NULL;
    }

    if ((mode < 0) || (mode >= NUM_OF_GSC_HW)) {
        ALOGE("%s::fail:: mode is not valid(%d) ", __func__, mode);
        return NULL;
    }

    /* currently only gscalers 0 and 3 are DRM capable */
    if (allow_drm && (dev_num != 0 && dev_num != 3)) {
        ALOGE("%s::fail:: gscaler %d does not support drm\n", __func__,
              dev_num);
        return NULL;
    }

    struct GSC_HANDLE *gsc_handle = (struct GSC_HANDLE *)malloc(sizeof(struct GSC_HANDLE));
    if (gsc_handle == NULL) {
        ALOGE("%s::malloc(struct GSC_HANDLE) fail", __func__);
        goto err;
    }
    memset(gsc_handle, 0, sizeof(struct GSC_HANDLE));
    gsc_handle->gsc_fd = -1;
    gsc_handle->gsc_mode = mode;
    gsc_handle->gsc_id = dev_num;
    gsc_handle->allow_drm = allow_drm;

    gsc_handle->src.buf_type = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
    gsc_handle->dst.buf_type = V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE;

    gsc_handle->op_mutex = NULL;
    for (i = 0; i < NUM_OF_GSC_HW; i++)
        gsc_handle->obj_mutex[i] = NULL;

    gsc_handle->cur_obj_mutex = NULL;
    gsc_handle->flag_local_path = false;
    gsc_handle->flag_exclusive_open = true;

    srand(time(NULL));
    op_id = rand() % 1000000; // just make random id
    sprintf(mutex_name, "%sOp%d", LOG_TAG, op_id);
    gsc_handle->op_mutex = exynos_mutex_create(EXYNOS_MUTEX_TYPE_PRIVATE, mutex_name);
    if (gsc_handle->op_mutex == NULL) {
        ALOGE("%s::exynos_mutex_create(%s) fail", __func__, mutex_name);
        goto err;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    sprintf(mutex_name, "%sObject%d", LOG_TAG, dev_num);
    gsc_handle->cur_obj_mutex = exynos_mutex_create(EXYNOS_MUTEX_TYPE_SHARED, mutex_name);
    if (gsc_handle->cur_obj_mutex == NULL) {
        ALOGE("%s::exynos_mutex_create(%s) fail", __func__, mutex_name);
        goto err;
    }

    do {
        if (exynos_mutex_trylock(gsc_handle->cur_obj_mutex) == true) {
            if (mode == GSC_M2M_MODE) {
                gsc_handle->gsc_fd = m_exynos_gsc_m2m_create(dev_num);
                if (gsc_handle->gsc_fd < 0) {
                    ALOGE("%s::m_exynos_gsc_m2m_create(%i) fail", __func__, dev_num);
                    goto err;
                }
            } else if (mode == GSC_OUTPUT_MODE) {
                ret = m_exynos_gsc_output_create(gsc_handle, dev_num, out_mode);
                if (ret < 0) {
                    ALOGE("%s::m_exynos_gsc_output_create(%i) fail", __func__, dev_num);
                    goto err;
                }
            }
            /*else
                gsc_handle->gsc_fd = m_exynos_gsc_capture_create(dev_num);*/

            gsc_flag = true;
            break;
        }
        usleep(GSC_WAITING_TIME_FOR_TRYLOCK);
        total_sleep_time += GSC_WAITING_TIME_FOR_TRYLOCK;
        ALOGV("%s::waiting for anthere process doens't use gscaler", __func__);
    } while(total_sleep_time < MAX_GSC_WAITING_TIME_FOR_TRYLOCK);

    exynos_mutex_unlock(gsc_handle->op_mutex);
    if (gsc_flag == true) {
        Exynos_gsc_Out();
        return (void *)gsc_handle;
        }

err:
    if (gsc_handle) {
        m_exynos_gsc_destroy(gsc_handle);

        if (gsc_handle->cur_obj_mutex)
            exynos_mutex_unlock(gsc_handle->cur_obj_mutex);

        for (i = 0; i < NUM_OF_GSC_HW; i++) {
            if ((gsc_handle->obj_mutex[i] != NULL) &&
                (exynos_mutex_get_created_status(gsc_handle->obj_mutex[i]) == true)) {
                if (exynos_mutex_destroy(gsc_handle->obj_mutex[i]) == false)
                    ALOGE("%s::exynos_mutex_destroy() fail", __func__);
            }
        }

        if (gsc_handle->op_mutex)
            exynos_mutex_unlock(gsc_handle->op_mutex);

        if (exynos_mutex_destroy(gsc_handle->op_mutex) == false)
            ALOGE("%s::exynos_mutex_destroy(op_mutex) fail", __func__);

        free(gsc_handle);
    }

    Exynos_gsc_Out();

    return NULL;
}

void exynos_gsc_destroy(
    void *handle)
{
    int i = 0;
    struct GSC_HANDLE *gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    if (gsc_handle->flag_exclusive_open == false)
        exynos_mutex_lock(gsc_handle->cur_obj_mutex);

    if (gsc_handle->gsc_mode == GSC_OUTPUT_MODE)
        m_exynos_gsc_out_destroy(gsc_handle);
    else
        m_exynos_gsc_destroy(gsc_handle);

    exynos_mutex_unlock(gsc_handle->cur_obj_mutex);

    for (i = 0; i < NUM_OF_GSC_HW; i++) {
        if ((gsc_handle->obj_mutex[i] != NULL) &&
            (exynos_mutex_get_created_status(gsc_handle->obj_mutex[i]) == true)) {
            if (exynos_mutex_destroy(gsc_handle->obj_mutex[i]) == false)
                ALOGE("%s::exynos_mutex_destroy(obj_mutex) fail", __func__);
        }
    }

    exynos_mutex_unlock(gsc_handle->op_mutex);

    if (exynos_mutex_destroy(gsc_handle->op_mutex) == false)
        ALOGE("%s::exynos_mutex_destroy(op_mutex) fail", __func__);

    if (gsc_handle)
        free(gsc_handle);

    Exynos_gsc_Out();

}

int exynos_gsc_set_src_format(
    void        *handle,
    unsigned int width,
    unsigned int height,
    unsigned int crop_left,
    unsigned int crop_top,
    unsigned int crop_width,
    unsigned int crop_height,
    unsigned int v4l2_colorformat,
    unsigned int cacheable,
    unsigned int mode_drm)
{
    Exynos_gsc_In();

    struct GSC_HANDLE *gsc_handle;
    gsc_handle = (struct GSC_HANDLE *)handle;

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    gsc_handle->src.width            = width;
    gsc_handle->src.height           = height;
    gsc_handle->src.crop_left        = crop_left;
    gsc_handle->src.crop_top         = crop_top;
    gsc_handle->src.crop_width       = crop_width;
    gsc_handle->src.crop_height      = crop_height;
    gsc_handle->src.v4l2_colorformat = v4l2_colorformat;
    gsc_handle->src.cacheable        = cacheable;
    gsc_handle->src.mode_drm         = mode_drm;
    gsc_handle->src.dirty            = true;


    exynos_mutex_unlock(gsc_handle->op_mutex);

    Exynos_gsc_Out();

    return 0;
}

int exynos_gsc_set_dst_format(
    void        *handle,
    unsigned int width,
    unsigned int height,
    unsigned int crop_left,
    unsigned int crop_top,
    unsigned int crop_width,
    unsigned int crop_height,
    unsigned int v4l2_colorformat,
    unsigned int cacheable,
    unsigned int mode_drm,
    unsigned int narrowRgb)
{
    Exynos_gsc_In();

    struct GSC_HANDLE *gsc_handle;
    gsc_handle = (struct GSC_HANDLE *)handle;

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    gsc_handle->dst.width            = width;
    gsc_handle->dst.height           = height;
    gsc_handle->dst.crop_left        = crop_left;
    gsc_handle->dst.crop_top         = crop_top;
    gsc_handle->dst.crop_width       = crop_width;
    gsc_handle->dst.crop_height      = crop_height;
    gsc_handle->dst.v4l2_colorformat = v4l2_colorformat;
    gsc_handle->dst.cacheable        = cacheable;
    gsc_handle->dst.mode_drm         = mode_drm;
    gsc_handle->dst.dirty            = true;
    gsc_handle->dst.csc_range        = !narrowRgb;

    exynos_mutex_unlock(gsc_handle->op_mutex);

    Exynos_gsc_Out();
    return 0;
}

int exynos_gsc_set_rotation(
    void *handle,
    int   rotation,
    int   flip_horizontal,
    int   flip_vertical)
{
    int ret = -1;
    struct GSC_HANDLE *gsc_handle;
    gsc_handle = (struct GSC_HANDLE *)handle;

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return ret;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    int new_rotation = rotation % 360;

    if (new_rotation % 90 != 0) {
        ALOGE("%s::rotation(%d) cannot be acceptable fail", __func__, rotation);
        goto done;
    }

    if(new_rotation < 0)
        new_rotation = -new_rotation;

    gsc_handle->dst.rotation        = new_rotation;
    gsc_handle->dst.flip_horizontal = flip_horizontal;
    gsc_handle->dst.flip_vertical   = flip_vertical;

    ret = 0;
done:
    exynos_mutex_unlock(gsc_handle->op_mutex);

    return ret;
}

int exynos_gsc_set_src_addr(
    void *handle,
    void *addr[3],
    int acquireFenceFd)
{
    struct GSC_HANDLE *gsc_handle;
    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    gsc_handle->src.addr[0] = addr[0];
    gsc_handle->src.addr[1] = addr[1];
    gsc_handle->src.addr[2] = addr[2];
    gsc_handle->src.acquireFenceFd = acquireFenceFd;

    exynos_mutex_unlock(gsc_handle->op_mutex);

    Exynos_gsc_Out();

    return 0;
}

int exynos_gsc_set_dst_addr(
    void *handle,
    void *addr[3],
    int acquireFenceFd)
{
    struct GSC_HANDLE *gsc_handle;
    gsc_handle = (struct GSC_HANDLE *)handle;
    int ret = 0;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    gsc_handle->dst.addr[0] = addr[0];
    gsc_handle->dst.addr[1] = addr[1];
    gsc_handle->dst.addr[2] = addr[2];
    gsc_handle->dst.acquireFenceFd = acquireFenceFd;


    exynos_mutex_unlock(gsc_handle->op_mutex);

    Exynos_gsc_Out();

    return ret;
}

static void rotateValueHAL2GSC(unsigned int transform,
    unsigned int *rotate,
    unsigned int *hflip,
    unsigned int *vflip)
{
    int rotate_flag = transform & 0x7;
    *rotate = 0;
    *hflip = 0;
    *vflip = 0;

    switch (rotate_flag) {
    case HAL_TRANSFORM_ROT_90:
        *rotate = 90;
        break;
    case HAL_TRANSFORM_ROT_180:
        *rotate = 180;
        break;
    case HAL_TRANSFORM_ROT_270:
        *rotate = 270;
        break;
    case HAL_TRANSFORM_FLIP_H | HAL_TRANSFORM_ROT_90:
        *rotate = 90;
        *vflip = 1; /* set vflip to compensate the rot & flip order. */
        break;
    case HAL_TRANSFORM_FLIP_V | HAL_TRANSFORM_ROT_90:
        *rotate = 90;
        *hflip = 1; /* set hflip to compensate the rot & flip order. */
        break;
    case HAL_TRANSFORM_FLIP_H:
        *hflip = 1;
         break;
    case HAL_TRANSFORM_FLIP_V:
        *vflip = 1;
         break;
    default:
        break;
    }
}

static bool get_plane_size(int V4L2_PIX,
    unsigned int * size,
    unsigned int frame_size,
    int src_planes)
{
    unsigned int frame_ratio = 1;
    int src_bpp    = get_yuv_bpp(V4L2_PIX);

    src_planes = (src_planes == -1) ? 1 : src_planes;
    frame_ratio = 8 * (src_planes -1) / (src_bpp - 8);

    switch (src_planes) {
    case 1:
        switch (V4L2_PIX) {
        case V4L2_PIX_FMT_BGR32:
        case V4L2_PIX_FMT_RGB32:
            size[0] = frame_size << 2;
            break;
        case V4L2_PIX_FMT_RGB565X:
        case V4L2_PIX_FMT_NV16:
        case V4L2_PIX_FMT_NV61:
        case V4L2_PIX_FMT_YUYV:
        case V4L2_PIX_FMT_UYVY:
        case V4L2_PIX_FMT_VYUY:
        case V4L2_PIX_FMT_YVYU:
            size[0] = frame_size << 1;
            break;
        case V4L2_PIX_FMT_YUV420:
        case V4L2_PIX_FMT_NV12:
        case V4L2_PIX_FMT_NV21:
        case V4L2_PIX_FMT_NV21M:
            size[0] = (frame_size * 3) >> 1;
            break;
        default:
            ALOGE("%s::invalid color type", __func__);
            return false;
            break;
        }
        size[1] = 0;
        size[2] = 0;
        break;
    case 2:
        size[0] = frame_size;
        size[1] = frame_size / frame_ratio;
        size[2] = 0;
        break;
    case 3:
        size[0] = frame_size;
        size[1] = frame_size / frame_ratio;
        size[2] = frame_size / frame_ratio;
        break;
    default:
        ALOGE("%s::invalid color foarmt", __func__);
        return false;
        break;
    }

    return true;
}

int exynos_gsc_m2m_config(void *handle,
    exynos_gsc_img *src_img,
    exynos_gsc_img *dst_img)
{
    struct GSC_HANDLE *gsc_handle;
    int32_t      src_color_space;
    int32_t      dst_color_space;
    int ret;
    unsigned int rotate;
    unsigned int hflip;
    unsigned int vflip;

    Exynos_gsc_In();

    gsc_handle = (struct GSC_HANDLE *)handle;
    if (gsc_handle == NULL) {
        ALOGE("%s::gsc_handle == NULL() fail", __func__);
        return -1;
    }

    if ((src_img->drmMode && !gsc_handle->allow_drm) ||
        (src_img->drmMode != dst_img->drmMode)) {
        ALOGE("%s::invalid drm state request for gsc%d (s=%d d=%d)",
              __func__, gsc_handle->gsc_id,
              src_img->drmMode, dst_img->drmMode);
        return -1;
    }

    src_color_space = HAL_PIXEL_FORMAT_2_V4L2_PIX(src_img->format);
    dst_color_space = HAL_PIXEL_FORMAT_2_V4L2_PIX(dst_img->format);
    rotateValueHAL2GSC(dst_img->rot, &rotate, &hflip, &vflip);
    exynos_gsc_set_rotation(gsc_handle, rotate, hflip, vflip);

    ret = exynos_gsc_set_src_format(gsc_handle,  src_img->fw, src_img->fh,
                                  src_img->x, src_img->y, src_img->w, src_img->h,
                                  src_color_space, src_img->cacheable, src_img->drmMode);
    if (ret < 0) {
        ALOGE("%s: fail: exynos_gsc_set_src_format [fw %d fh %d x %d y %d w %d h %d f %x rot %d]",
            __func__, src_img->fw, src_img->fh, src_img->x, src_img->y, src_img->w, src_img->h,
            src_color_space, src_img->rot);
        return -1;
    }

    ret = exynos_gsc_set_dst_format(gsc_handle, dst_img->fw, dst_img->fh,
                                  dst_img->x, dst_img->y, dst_img->w, dst_img->h,
                                  dst_color_space, dst_img->cacheable, dst_img->drmMode,
                                  dst_img->narrowRgb);
    if (ret < 0) {
        ALOGE("%s: fail: exynos_gsc_set_dst_format [fw %d fh %d x %d y %d w %d h %d f %x rot %d]",
            __func__, dst_img->fw, dst_img->fh, dst_img->x, dst_img->y, dst_img->w, dst_img->h,
            src_color_space, dst_img->rot);
        return -1;
    }

    Exynos_gsc_Out();

    return 0;
}

int exynos_gsc_out_config(void *handle,
    exynos_gsc_img *src_img,
    exynos_gsc_img *dst_img)
{
    struct GSC_HANDLE *gsc_handle;
    struct v4l2_format  fmt;
    struct v4l2_crop    crop;
    struct v4l2_requestbuffers reqbuf;
    struct v4l2_subdev_format sd_fmt;
    struct v4l2_subdev_crop   sd_crop;
    int i;
    unsigned int rotate;
    unsigned int hflip;
    unsigned int vflip;
    unsigned int plane_size[NUM_OF_GSC_PLANES];
    bool rgb;
    int csc_range = !dst_img->narrowRgb;

    struct v4l2_rect dst_rect;
    int32_t      src_color_space;
    int32_t      dst_color_space;
    int32_t      src_planes;

    gsc_handle = (struct GSC_HANDLE *)handle;
     if (gsc_handle == NULL) {
        ALOGE("%s::gsc_handle == NULL() fail", __func__);
        return -1;
    }

    Exynos_gsc_In();

     if (gsc_handle->src.stream_on != false) {
        ALOGE("Error: Src is already streamed on !!!!");
        return -1;
     }

    memcpy(&gsc_handle->src_img, src_img, sizeof(exynos_gsc_img));
    memcpy(&gsc_handle->dst_img, dst_img, sizeof(exynos_gsc_img));
    src_color_space = HAL_PIXEL_FORMAT_2_V4L2_PIX(src_img->format);
    dst_color_space = HAL_PIXEL_FORMAT_2_V4L2_PIX(dst_img->format);
    src_planes = get_yuv_planes(src_color_space);
    src_planes = (src_planes == -1) ? 1 : src_planes;
    rgb = get_yuv_planes(dst_color_space) == -1;
    rotateValueHAL2GSC(dst_img->rot, &rotate, &hflip, &vflip);

    if (m_exynos_gsc_check_src_size(&gsc_handle->src_img.fw, &gsc_handle->src_img.fh,
                                        &gsc_handle->src_img.x, &gsc_handle->src_img.y,
                                        &gsc_handle->src_img.w, &gsc_handle->src_img.h,
                                        src_color_space) == false) {
            ALOGE("%s::m_exynos_gsc_check_src_size() fail", __func__);
            return -1;
    }

    if (m_exynos_gsc_check_dst_size(&gsc_handle->dst_img.fw, &gsc_handle->dst_img.fh,
                                        &gsc_handle->dst_img.x, &gsc_handle->dst_img.y,
                                        &gsc_handle->dst_img.w, &gsc_handle->dst_img.h,
                                        dst_color_space,
                                        rotate) == false) {
            ALOGE("%s::m_exynos_gsc_check_dst_size() fail", __func__);
            return -1;
    }

    /*set: src v4l2_buffer*/
    gsc_handle->src.src_buf_idx = 0;
    gsc_handle->src.qbuf_cnt = 0;
    /* set format: src pad of GSC sub-dev*/
    sd_fmt.pad   = GSCALER_SUBDEV_PAD_SOURCE;
    sd_fmt.which = V4L2_SUBDEV_FORMAT_ACTIVE;
    if (gsc_handle->out_mode == GSC_OUT_FIMD) {
        sd_fmt.format.width  = gsc_handle->dst_img.fw;
        sd_fmt.format.height = gsc_handle->dst_img.fh;
    } else {
        sd_fmt.format.width  = gsc_handle->dst_img.w;
        sd_fmt.format.height = gsc_handle->dst_img.h;
    }
    sd_fmt.format.code   = rgb ? V4L2_MBUS_FMT_XRGB8888_4X8_LE :
                                    V4L2_MBUS_FMT_YUV8_1X24;
    if (exynos_subdev_s_fmt(gsc_handle->gsc_sd_entity->fd, &sd_fmt) < 0) {
            ALOGE("%s::GSC subdev set format failed", __func__);
            return -1;
    }

    /* set crop: src crop of GSC sub-dev*/
    sd_crop.pad   = GSCALER_SUBDEV_PAD_SOURCE;
    sd_crop.which = V4L2_SUBDEV_FORMAT_ACTIVE;
    if (gsc_handle->out_mode == GSC_OUT_FIMD) {
        sd_crop.rect.left   = gsc_handle->dst_img.x;
        sd_crop.rect.top    = gsc_handle->dst_img.y;
        sd_crop.rect.width  = gsc_handle->dst_img.w;
        sd_crop.rect.height = gsc_handle->dst_img.h;
    } else {
        sd_crop.rect.left   = 0;
        sd_crop.rect.top    = 0;
        sd_crop.rect.width  = gsc_handle->dst_img.w;
        sd_crop.rect.height = gsc_handle->dst_img.h;
    }
    if (exynos_subdev_s_crop(gsc_handle->gsc_sd_entity->fd, &sd_crop) < 0) {
            ALOGE("%s::GSC subdev set crop failed", __func__);
            return -1;
    }

    /* sink pad is connected to GSC out */
    /*  set format: sink sub-dev */
    if (gsc_handle->out_mode == GSC_OUT_FIMD) {
        sd_fmt.pad   = FIMD_SUBDEV_PAD_SINK;
        sd_fmt.format.width  = gsc_handle->dst_img.w;
        sd_fmt.format.height = gsc_handle->dst_img.h;
    } else {
        sd_fmt.pad   = MIXER_V_SUBDEV_PAD_SINK;
        sd_fmt.format.width  = gsc_handle->dst_img.w + gsc_handle->dst_img.x*2;
        sd_fmt.format.height = gsc_handle->dst_img.h + gsc_handle->dst_img.y*2;
    }

    sd_fmt.which = V4L2_SUBDEV_FORMAT_ACTIVE;
    sd_fmt.format.code   = rgb ? V4L2_MBUS_FMT_XRGB8888_4X8_LE :
                                    V4L2_MBUS_FMT_YUV8_1X24;
    if (exynos_subdev_s_fmt(gsc_handle->sink_sd_entity->fd, &sd_fmt) < 0) {
        ALOGE("%s::sink:set format failed (PAD=%d)", __func__, sd_fmt.pad);
        return -1;
    }

    /*  set crop: sink sub-dev */
    if (gsc_handle->out_mode == GSC_OUT_FIMD)
        sd_crop.pad   = FIMD_SUBDEV_PAD_SINK;
    else
        sd_crop.pad   = MIXER_V_SUBDEV_PAD_SINK;

    sd_crop.which = V4L2_SUBDEV_FORMAT_ACTIVE;
    if (gsc_handle->out_mode == GSC_OUT_FIMD) {
        sd_crop.rect.left   = gsc_handle->dst_img.x;
        sd_crop.rect.top    = gsc_handle->dst_img.y;
        sd_crop.rect.width  = gsc_handle->dst_img.w;
        sd_crop.rect.height = gsc_handle->dst_img.h;
    } else {
        sd_crop.rect.left   = 0;
        sd_crop.rect.top    = 0;
        sd_crop.rect.width  = gsc_handle->dst_img.w;
        sd_crop.rect.height = gsc_handle->dst_img.h;
    }
    if (exynos_subdev_s_crop(gsc_handle->sink_sd_entity->fd, &sd_crop) < 0) {
            ALOGE("%s::sink: subdev set crop failed(PAD=%d)", __func__, sd_crop.pad);
            return -1;
    }

    if (gsc_handle->out_mode != GSC_OUT_FIMD) {
        sd_fmt.pad   = MIXER_V_SUBDEV_PAD_SOURCE;
        sd_fmt.which = V4L2_SUBDEV_FORMAT_ACTIVE;
        sd_fmt.format.width  = gsc_handle->dst_img.w + gsc_handle->dst_img.x*2;
        sd_fmt.format.height = gsc_handle->dst_img.h + gsc_handle->dst_img.y*2;
        sd_fmt.format.code   = V4L2_MBUS_FMT_XRGB8888_4X8_LE;
        if (exynos_subdev_s_fmt(gsc_handle->sink_sd_entity->fd, &sd_fmt) < 0) {
            ALOGE("%s::sink:set format failed (PAD=%d)", __func__, sd_fmt.pad);
            return -1;
        }

        sd_fmt.pad   = MIXER_V_SUBDEV_PAD_SOURCE;
        sd_crop.which = V4L2_SUBDEV_FORMAT_ACTIVE;
        sd_crop.rect.left   = gsc_handle->dst_img.x;
        sd_crop.rect.top    = gsc_handle->dst_img.y;
        sd_crop.rect.width  = gsc_handle->dst_img.w;
        sd_crop.rect.height = gsc_handle->dst_img.h;
        if (exynos_subdev_s_crop(gsc_handle->sink_sd_entity->fd, &sd_crop) < 0) {
            ALOGE("%s::sink: subdev set crop failed(PAD=%d)", __func__, sd_crop.pad);
            return -1;
        }
    }

    /*set GSC ctrls */
    if (exynos_v4l2_s_ctrl(gsc_handle->gsc_vd_entity->fd, V4L2_CID_ROTATE, rotate) < 0) {
        ALOGE("%s:: exynos_v4l2_s_ctrl (V4L2_CID_ROTATE: %d) failed", __func__,  rotate);
        return -1;
    }

    if (exynos_v4l2_s_ctrl(gsc_handle->gsc_vd_entity->fd, V4L2_CID_HFLIP, hflip) < 0) {
        ALOGE("%s:: exynos_v4l2_s_ctrl (V4L2_CID_HFLIP: %d) failed", __func__,  hflip);
        return -1;
    }

    if (exynos_v4l2_s_ctrl(gsc_handle->gsc_vd_entity->fd, V4L2_CID_VFLIP, vflip) < 0) {
        ALOGE("%s:: exynos_v4l2_s_ctrl (V4L2_CID_VFLIP: %d) failed", __func__,  vflip);
        return -1;
    }

     if (exynos_v4l2_s_ctrl(gsc_handle->gsc_vd_entity->fd, V4L2_CID_CACHEABLE, 1) < 0) {
        ALOGE("%s:: exynos_v4l2_s_ctrl (V4L2_CID_CACHEABLE: 1) failed", __func__);
        return -1;
    }

    if (exynos_v4l2_s_ctrl(gsc_handle->gsc_vd_entity->fd,
        V4L2_CID_CONTENT_PROTECTION, gsc_handle->src_img.drmMode) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_CONTENT_PROTECTION) fail", __func__);
        return -1;
    }

    if (exynos_v4l2_s_ctrl(gsc_handle->gsc_vd_entity->fd, V4L2_CID_CSC_RANGE,
            csc_range)) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_CSC_RANGE: %d) fail", __func__,
                csc_range);
        return -1;
    }

      /* set src format  :GSC video dev*/
    fmt.type  = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
    fmt.fmt.pix_mp.width            = gsc_handle->src_img.fw;
    fmt.fmt.pix_mp.height           = gsc_handle->src_img.fh;
    fmt.fmt.pix_mp.pixelformat    = src_color_space;
    fmt.fmt.pix_mp.field              = V4L2_FIELD_NONE;
    fmt.fmt.pix_mp.num_planes   = src_planes;

    if (exynos_v4l2_s_fmt(gsc_handle->gsc_vd_entity->fd, &fmt) < 0) {
            ALOGE("%s::videodev set format failed", __func__);
            return -1;
    }

    /* set src crop info :GSC video dev*/
    crop.type     = fmt.type;
    crop.c.left    = gsc_handle->src_img.x;
    crop.c.top     = gsc_handle->src_img.y;
    crop.c.width  = gsc_handle->src_img.w;
    crop.c.height = gsc_handle->src_img.h;

    if (exynos_v4l2_s_crop(gsc_handle->gsc_vd_entity->fd, &crop) < 0) {
        ALOGE("%s::videodev set crop failed", __func__);
        return -1;
    }

    reqbuf.type   = fmt.type;
    reqbuf.memory = V4L2_MEMORY_DMABUF;
    reqbuf.count  = MAX_BUFFERS_GSCALER_OUT;

    if (exynos_v4l2_reqbufs(gsc_handle->gsc_vd_entity->fd, &reqbuf) < 0) {
        ALOGE("%s::request buffers failed", __func__);
        return -1;
    }

    Exynos_gsc_Out();

    return 0;
}

static int exynos_gsc_out_run(void *handle,
    exynos_gsc_img *src_img)
{
    struct GSC_HANDLE *gsc_handle;
    struct v4l2_plane  planes[NUM_OF_GSC_PLANES];
    struct v4l2_buffer buf;
    int32_t      src_color_space;
    int32_t      src_planes;
    int             i;
    unsigned int plane_size[NUM_OF_GSC_PLANES];

    gsc_handle = (struct GSC_HANDLE *)handle;
    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    /* All buffers have been queued, dequeue one */
    if (gsc_handle->src.qbuf_cnt == MAX_BUFFERS_GSCALER_OUT) {
        memset(&buf, 0, sizeof(struct v4l2_buffer));
        for (i = 0; i < MAX_BUFFERS_GSCALER_OUT; i++)
            memset(&planes[i], 0, sizeof(struct v4l2_plane));

        buf.type     = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
        buf.memory   = V4L2_MEMORY_DMABUF;
        buf.length   = src_planes;
        buf.m.planes = planes;

        if (exynos_v4l2_dqbuf(gsc_handle->gsc_vd_entity->fd, &buf) < 0) {
            ALOGE("%s::dequeue buffer failed (index=%d)(mSrcBufNum=%d)", __func__,
                gsc_handle->src.src_buf_idx, MAX_BUFFERS_GSCALER_OUT);
            return -1;
        }
        gsc_handle->src.qbuf_cnt--;
    }

    memset(&buf, 0, sizeof(struct v4l2_buffer));
    for (i = 0; i < NUM_OF_GSC_PLANES; i++)
        memset(&planes[i], 0, sizeof(struct v4l2_plane));

    src_color_space = HAL_PIXEL_FORMAT_2_V4L2_PIX(gsc_handle->src_img.format);
    src_planes = get_yuv_planes(src_color_space);
    src_planes = (src_planes == -1) ? 1 : src_planes;

    buf.type     = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
    buf.memory   = V4L2_MEMORY_DMABUF;
    buf.flags    = V4L2_BUF_FLAG_USE_SYNC;
    buf.length   = src_planes;
    buf.index    = gsc_handle->src.src_buf_idx;
    buf.m.planes = planes;
    buf.reserved = src_img->acquireFenceFd;

    gsc_handle->src.addr[0] = src_img->yaddr;
    gsc_handle->src.addr[1] = src_img->uaddr;
    gsc_handle->src.addr[2] = src_img->vaddr;

    if (get_plane_size(src_color_space, plane_size,
        gsc_handle->src_img.fw * gsc_handle->src_img.fh, src_planes) != true) {
        ALOGE("%s:get_plane_size:fail", __func__);
        return -1;
    }

    for (i = 0; i < buf.length; i++) {
        buf.m.planes[i].m.fd = (int)gsc_handle->src.addr[i];
        buf.m.planes[i].length    = plane_size[i];
        buf.m.planes[i].bytesused = plane_size[i];
    }

    /* Queue the buf */
    if (exynos_v4l2_qbuf(gsc_handle->gsc_vd_entity->fd, &buf) < 0) {
        ALOGE("%s::queue buffer failed (index=%d)(mSrcBufNum=%d)", __func__,
            gsc_handle->src.src_buf_idx, MAX_BUFFERS_GSCALER_OUT);
        return -1;
    }
    gsc_handle->src.src_buf_idx++;
    gsc_handle->src.src_buf_idx = gsc_handle->src.src_buf_idx % MAX_BUFFERS_GSCALER_OUT;
    gsc_handle->src.qbuf_cnt++;

    if (gsc_handle->src.stream_on == false) {
        if (exynos_v4l2_streamon(gsc_handle->gsc_vd_entity->fd, buf.type) < 0) {
            ALOGE("%s::stream on failed", __func__);
            return -1;
        }
        gsc_handle->src.stream_on = true;
    }

    src_img->releaseFenceFd = buf.reserved;
    return 0;
}

int exynos_gsc_out_stop(void *handle)
{
    struct GSC_HANDLE *gsc_handle;
    struct v4l2_requestbuffers reqbuf;
    struct v4l2_buffer buf;
    struct v4l2_plane  planes[NUM_OF_GSC_PLANES];
    int i;

    Exynos_gsc_In();

    gsc_handle = (struct GSC_HANDLE *)handle;
    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    if (gsc_handle->src.stream_on == true) {
        if (exynos_v4l2_streamoff(gsc_handle->gsc_vd_entity->fd,
                                V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE) < 0) {
            ALOGE("%s::stream off failed", __func__);
            return -1;
        }
        gsc_handle->src.stream_on = false;
    }

    gsc_handle->src.src_buf_idx = 0;
    gsc_handle->src.qbuf_cnt = 0;

    reqbuf.type   = V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE;
    reqbuf.memory = V4L2_MEMORY_DMABUF;
    reqbuf.count  = 0;

    if (exynos_v4l2_reqbufs(gsc_handle->gsc_vd_entity->fd, &reqbuf) < 0) {
        ALOGE("%s::request buffers failed", __func__);
        return -1;
    }

    Exynos_gsc_Out();

    return 0;
}

static int exynos_gsc_m2m_run_core(void *handle)
{
    struct GSC_HANDLE *gsc_handle;
    bool is_dirty;
    bool is_drm;

    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    is_dirty = gsc_handle->src.dirty || gsc_handle->dst.dirty;
    is_drm = gsc_handle->src.mode_drm;

    if (is_dirty && (gsc_handle->src.mode_drm != gsc_handle->dst.mode_drm)) {
        ALOGE("%s: drm mode mismatch between src and dst, gsc%d (s=%d d=%d)",
              __func__, gsc_handle->gsc_id, gsc_handle->src.mode_drm,
              gsc_handle->dst.mode_drm);
        return -1;
    } else if (is_drm && !gsc_handle->allow_drm) {
        ALOGE("%s: drm mode is not supported on gsc%d", __func__,
              gsc_handle->gsc_id);
        return -1;
    }

    if (m_exynos_gsc_check_src_size(&gsc_handle->src.width, &gsc_handle->src.height,
                                    &gsc_handle->src.crop_left, &gsc_handle->src.crop_top,
                                    &gsc_handle->src.crop_width, &gsc_handle->src.crop_height,
                                    gsc_handle->src.v4l2_colorformat) == false) {
        ALOGE("%s::m_exynos_gsc_check_src_size() fail", __func__);
        return -1;
    }

    if (m_exynos_gsc_check_dst_size(&gsc_handle->dst.width, &gsc_handle->dst.height,
                                    &gsc_handle->dst.crop_left, &gsc_handle->dst.crop_top,
                                    &gsc_handle->dst.crop_width, &gsc_handle->dst.crop_height,
                                    gsc_handle->dst.v4l2_colorformat,
                                    gsc_handle->dst.rotation) == false) {
        ALOGE("%s::m_exynos_gsc_check_dst_size() fail", __func__);
        return -1;
    }

    /* dequeue buffers from previous work if necessary */
    if (gsc_handle->src.stream_on == true) {
        if (exynos_gsc_m2m_wait_frame_done(handle) < 0) {
            ALOGE("%s::exynos_gsc_m2m_wait_frame_done fail", __func__);
            return -1;
        }
    }

    /*
     * need to set the content protection flag before doing reqbufs
     * in set_format
     */
    if (is_dirty && gsc_handle->allow_drm && is_drm) {
        if (exynos_v4l2_s_ctrl(gsc_handle->gsc_fd,
                               V4L2_CID_CONTENT_PROTECTION, is_drm) < 0) {
            ALOGE("%s::exynos_v4l2_s_ctrl() fail", __func__);
            return -1;
        }
    }

    /*
     * from this point on, we have to ensure to call stop to clean up whatever
     * state we have set.
     */

    if (gsc_handle->src.dirty) {
        if (m_exynos_gsc_set_format(gsc_handle->gsc_fd, &gsc_handle->src) == false) {
            ALOGE("%s::m_exynos_gsc_set_format(src) fail", __func__);
            goto done;
        }
        gsc_handle->src.dirty = false;
    }

    if (gsc_handle->dst.dirty) {
        if (m_exynos_gsc_set_format(gsc_handle->gsc_fd, &gsc_handle->dst) == false) {
            ALOGE("%s::m_exynos_gsc_set_format(dst) fail", __func__);
            goto done;
        }
        gsc_handle->dst.dirty = false;
    }

    /* if we are enabling drm, make sure to enable hw protection.
     * Need to do this before queuing buffers so that the mmu is reserved
     * and power domain is kept on.
     */
    if (is_dirty && gsc_handle->allow_drm && is_drm) {
        unsigned int protect_id = 0;

        if (gsc_handle->gsc_id == 0) {
            protect_id = CP_PROTECT_GSC0;
        } else if (gsc_handle->gsc_id == 3) {
            protect_id = CP_PROTECT_GSC3;
        } else {
            ALOGE("%s::invalid gscaler id %d for content protection", __func__,
                  gsc_handle->gsc_id);
            goto done;
        }

        if (CP_Enable_Path_Protection(protect_id) != 0) {
            ALOGE("%s::CP_Enable_Path_Protection failed", __func__);
            goto done;
        }
        gsc_handle->protection_enabled = true;
    }

    if (m_exynos_gsc_set_addr(gsc_handle->gsc_fd, &gsc_handle->src) == false) {
        ALOGE("%s::m_exynos_gsc_set_addr(src) fail", __func__);
        goto done;
    }

    if (m_exynos_gsc_set_addr(gsc_handle->gsc_fd, &gsc_handle->dst) == false) {
        ALOGE("%s::m_exynos_gsc_set_addr(dst) fail", __func__);
        goto done;
    }

    if (gsc_handle->src.stream_on == false) {
        if (exynos_v4l2_streamon(gsc_handle->gsc_fd, gsc_handle->src.buf_type) < 0) {
            ALOGE("%s::exynos_v4l2_streamon(src) fail", __func__);
            goto done;
        }
        gsc_handle->src.stream_on = true;
    }

    if (gsc_handle->dst.stream_on == false) {
        if (exynos_v4l2_streamon(gsc_handle->gsc_fd, gsc_handle->dst.buf_type) < 0) {
            ALOGE("%s::exynos_v4l2_streamon(dst) fail", __func__);
            goto done;
        }
        gsc_handle->dst.stream_on = true;
    }

    Exynos_gsc_Out();

    return 0;

done:
    exynos_gsc_m2m_stop(handle);
    return -1;
}

static int exynos_gsc_m2m_wait_frame_done(void *handle)
{
    struct GSC_HANDLE *gsc_handle;

    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    if ((gsc_handle->src.stream_on == false) || (gsc_handle->dst.stream_on == false)) {
        ALOGE("%s:: src_strean_on or dst_stream_on are false", __func__);
        return -1;
    }

    if (gsc_handle->src.buffer_queued) {
        if (exynos_v4l2_dqbuf(gsc_handle->gsc_fd, &gsc_handle->src.buffer) < 0) {
            ALOGE("%s::exynos_v4l2_dqbuf(src) fail", __func__);
            return -1;
        }
        gsc_handle->src.buffer_queued = false;
    }

    if (gsc_handle->dst.buffer_queued) {
        if (exynos_v4l2_dqbuf(gsc_handle->gsc_fd, &gsc_handle->dst.buffer) < 0) {
            ALOGE("%s::exynos_v4l2_dqbuf(dst) fail", __func__);
            return -1;
        }
        gsc_handle->dst.buffer_queued = false;
    }

    Exynos_gsc_Out();

    return 0;
}

static int exynos_gsc_m2m_stop(void *handle)
{
    struct GSC_HANDLE *gsc_handle;
    struct v4l2_requestbuffers req_buf;
    int ret = 0;

    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (!gsc_handle->src.stream_on && !gsc_handle->dst.stream_on) {
        /* wasn't streaming, return success */
        return 0;
    } else if (gsc_handle->src.stream_on != gsc_handle->dst.stream_on) {
        ALOGE("%s: invalid state, queue stream state doesn't match (%d != %d)",
              __func__, gsc_handle->src.stream_on, gsc_handle->dst.stream_on);
        ret = -1;
    }

    /*
     * we need to plow forward on errors below to make sure that if we had
     * turned on content protection on secure side, we turn it off.
     *
     * also, if we only failed to turn on one of the streams, we'll turn
     * the other one off correctly.
     */
    if (gsc_handle->src.stream_on == true) {
        if (exynos_v4l2_streamoff(gsc_handle->gsc_fd, gsc_handle->src.buf_type) < 0) {
            ALOGE("%s::exynos_v4l2_streamoff(src) fail", __func__);
            ret = -1;
        }
        gsc_handle->src.stream_on = false;
    }


    if (gsc_handle->dst.stream_on == true) {
        if (exynos_v4l2_streamoff(gsc_handle->gsc_fd, gsc_handle->dst.buf_type) < 0) {
            ALOGE("%s::exynos_v4l2_streamoff(dst) fail", __func__);
            ret = -1;
        }
        gsc_handle->dst.stream_on = false;
    }

    /* if drm is enabled */
    if (gsc_handle->allow_drm && gsc_handle->protection_enabled) {
        unsigned int protect_id = 0;

        if (gsc_handle->gsc_id == 0)
            protect_id = CP_PROTECT_GSC0;
        else if (gsc_handle->gsc_id == 3)
            protect_id = CP_PROTECT_GSC3;

        CP_Disable_Path_Protection(protect_id);
        gsc_handle->protection_enabled = false;
    }

    if (exynos_v4l2_s_ctrl(gsc_handle->gsc_fd,
                           V4L2_CID_CONTENT_PROTECTION, 0) < 0) {
        ALOGE("%s::exynos_v4l2_s_ctrl(V4L2_CID_CONTENT_PROTECTION) fail",
              __func__);
        ret = -1;
    }

    /* src: clear_buf */
    req_buf.count  = 0;
    req_buf.type   = gsc_handle->src.buf_type;
    req_buf.memory = V4L2_MEMORY_DMABUF;
    if (exynos_v4l2_reqbufs(gsc_handle->gsc_fd, &req_buf) < 0) {
        ALOGE("%s::exynos_v4l2_reqbufs():src: fail", __func__);
        ret = -1;
    }

    /* dst: clear_buf */
    req_buf.count  = 0;
    req_buf.type   = gsc_handle->dst.buf_type;
    req_buf.memory = V4L2_MEMORY_DMABUF;
    if (exynos_v4l2_reqbufs(gsc_handle->gsc_fd, &req_buf) < 0) {
        ALOGE("%s::exynos_v4l2_reqbufs():dst: fail", __func__);
        ret = -1;
    }

    Exynos_gsc_Out();

    return ret;
}

int exynos_gsc_convert(
    void *handle)
{
    struct GSC_HANDLE *gsc_handle;
    int ret    = -1;
    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    if (gsc_handle->flag_local_path == true) {
        ALOGE("%s::this exynos_gsc is connected by another hw internaly. So, don't call exynos_gsc_convert()", __func__);
            goto done;
        }

    if (exynos_gsc_m2m_run_core(handle) < 0) {
        ALOGE("%s::exynos_gsc_run_core fail", __func__);
            goto done;
        }

    if (exynos_gsc_m2m_wait_frame_done(handle) < 0) {
        ALOGE("%s::exynos_gsc_m2m_wait_frame_done", __func__);
        goto done;
    }

    if (gsc_handle->src.releaseFenceFd >= 0) {
        close(gsc_handle->src.releaseFenceFd);
        gsc_handle->src.releaseFenceFd = -1;
    }

    if (gsc_handle->dst.releaseFenceFd >= 0) {
        close(gsc_handle->dst.releaseFenceFd);
        gsc_handle->dst.releaseFenceFd = -1;
    }

    if (exynos_gsc_m2m_stop(handle) < 0) {
        ALOGE("%s::exynos_gsc_m2m_stop", __func__);
        goto done;
    }

    ret = 0;

done:
    if (gsc_handle->flag_exclusive_open == false) {
        if (gsc_handle->flag_local_path == false)
            exynos_mutex_unlock(gsc_handle->cur_obj_mutex);
    }

    exynos_mutex_unlock(gsc_handle->op_mutex);

    Exynos_gsc_Out();

    return ret;
}

int exynos_gsc_m2m_run(void *handle,
    exynos_gsc_img *src_img,
    exynos_gsc_img *dst_img)
{
    struct GSC_HANDLE *gsc_handle = handle;
    void *addr[3] = {NULL, NULL, NULL};
    int ret = 0;

    Exynos_gsc_In();

    addr[0] = (void *)src_img->yaddr;
    addr[1] = (void *)src_img->uaddr;
    addr[2] = (void *)src_img->vaddr;
    ret = exynos_gsc_set_src_addr(handle, addr, src_img->acquireFenceFd);
    if (ret < 0) {
        ALOGE("%s::fail: exynos_gsc_set_src_addr[%x %x %x]", __func__,
            (unsigned int)addr[0], (unsigned int)addr[1], (unsigned int)addr[2]);
        return -1;
    }

    addr[0] = (void *)dst_img->yaddr;
    addr[1] = (void *)dst_img->uaddr;
    addr[2] = (void *)dst_img->vaddr;
    ret = exynos_gsc_set_dst_addr(handle, addr, dst_img->acquireFenceFd);
    if (ret < 0) {
        ALOGE("%s::fail: exynos_gsc_set_dst_addr[%x %x %x]", __func__,
            (unsigned int)addr[0], (unsigned int)addr[1], (unsigned int)addr[2]);
        return -1;
    }

    ret = exynos_gsc_m2m_run_core(handle);
     if (ret < 0) {
        ALOGE("%s::fail: exynos_gsc_m2m_run_core", __func__);
        return -1;
    }

    if (src_img->acquireFenceFd >= 0) {
        close(src_img->acquireFenceFd);
        src_img->acquireFenceFd = -1;
    }

    if (dst_img->acquireFenceFd >= 0) {
        close(dst_img->acquireFenceFd);
        dst_img->acquireFenceFd = -1;
    }

    src_img->releaseFenceFd = gsc_handle->src.releaseFenceFd;
    dst_img->releaseFenceFd = gsc_handle->dst.releaseFenceFd;

    Exynos_gsc_Out();

    return 0;
}

int exynos_gsc_config_exclusive(void *handle,
    exynos_gsc_img *src_img,
    exynos_gsc_img *dst_img)
{

    Exynos_gsc_In();

     struct GSC_HANDLE *gsc_handle;
    int ret = 0;
    gsc_handle = (struct GSC_HANDLE *)handle;
    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    switch (gsc_handle->gsc_mode) {
    case GSC_M2M_MODE:
        ret = exynos_gsc_m2m_config(handle, src_img, dst_img);
        break;
    case GSC_OUTPUT_MODE:
        ret = exynos_gsc_out_config(handle, src_img, dst_img);
        break;
    case  GSC_CAPTURE_MODE:
        //to do
        break;
    default:
        break;
    }

    Exynos_gsc_Out();

    return ret;

}

int exynos_gsc_run_exclusive(void *handle,
    exynos_gsc_img *src_img,
    exynos_gsc_img *dst_img)
{
    struct GSC_HANDLE *gsc_handle;
    int ret = 0;

    Exynos_gsc_In();

    gsc_handle = (struct GSC_HANDLE *)handle;
    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    switch (gsc_handle->gsc_mode) {
    case GSC_M2M_MODE:
        ret = exynos_gsc_m2m_run(handle, src_img, dst_img);
        break;
    case GSC_OUTPUT_MODE:
        ret = exynos_gsc_out_run(handle, src_img);
        break;
    case  GSC_CAPTURE_MODE:
        //to do
        break;
    default:
        break;
    }

    Exynos_gsc_Out();

    return ret;
}

int exynos_gsc_wait_frame_done_exclusive(void *handle)
{
    struct GSC_HANDLE *gsc_handle;
    int ret = 0;
    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    if (gsc_handle->gsc_mode == GSC_M2M_MODE)
        ret = exynos_gsc_m2m_wait_frame_done(handle);

    Exynos_gsc_Out();

    return ret;
}

int exynos_gsc_stop_exclusive(void *handle)
{
    struct GSC_HANDLE *gsc_handle;
    int ret = 0;
    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    switch (gsc_handle->gsc_mode) {
    case GSC_M2M_MODE:
        ret = exynos_gsc_m2m_stop(handle);
        break;
    case GSC_OUTPUT_MODE:
        ret = exynos_gsc_out_stop(handle);
        break;
    case  GSC_CAPTURE_MODE:
        //to do
        break;
    default:
        break;
    }

    Exynos_gsc_Out();

    return ret;
}

int exynos_gsc_connect(
    void *handle,
    void *hw)
{
    struct GSC_HANDLE *gsc_handle;
    int ret    = -1;
    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    gsc_handle->flag_local_path = true;

    if (exynos_mutex_trylock(gsc_handle->cur_obj_mutex) == false) {
        if (m_exynos_gsc_find_and_trylock_and_create(gsc_handle) == false) {
            ALOGE("%s::m_exynos_gsc_find_and_trylock_and_create() fail", __func__);
            goto done;
        }
    }

    ret = 0;

    Exynos_gsc_Out();

done:
    exynos_mutex_unlock(gsc_handle->op_mutex);

    return ret;
}

int exynos_gsc_disconnect(
    void *handle,
    void *hw)
{
    struct GSC_HANDLE *gsc_handle;
    gsc_handle = (struct GSC_HANDLE *)handle;

    Exynos_gsc_In();

    if (handle == NULL) {
        ALOGE("%s::handle == NULL() fail", __func__);
        return -1;
    }

    exynos_mutex_lock(gsc_handle->op_mutex);

    gsc_handle->flag_local_path = false;

    exynos_mutex_unlock(gsc_handle->cur_obj_mutex);

    exynos_mutex_unlock(gsc_handle->op_mutex);

    Exynos_gsc_Out();

    return 0;
}
