/*
// Copyright (c) 2014 Intel Corporation 
//
// 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.
*/

#include <HwcTrace.h>
#include <common/RotationBufferProvider.h>
#include <system/window.h>

namespace android {
namespace intel {

#define CHECK_VA_STATUS_RETURN(FUNC) \
if (vaStatus != VA_STATUS_SUCCESS) {\
    ETRACE(FUNC" failed. vaStatus = %#x", vaStatus);\
    return false;\
}

#define CHECK_VA_STATUS_BREAK(FUNC) \
if (vaStatus != VA_STATUS_SUCCESS) {\
    ETRACE(FUNC" failed. vaStatus = %#x", vaStatus);\
    break;\
}

// With this display value, VA will hook VED driver insead of VSP driver for buffer rotation
#define DISPLAYVALUE  0x56454450

RotationBufferProvider::RotationBufferProvider(Wsbm* wsbm)
    : mWsbm(wsbm),
      mVaInitialized(false),
      mVaDpy(0),
      mVaCfg(0),
      mVaCtx(0),
      mVaBufFilter(0),
      mSourceSurface(0),
      mDisplay(DISPLAYVALUE),
      mWidth(0),
      mHeight(0),
      mTransform(0),
      mRotatedWidth(0),
      mRotatedHeight(0),
      mRotatedStride(0),
      mTargetIndex(0),
      mTTMWrappers(),
      mBobDeinterlace(0)
{
    for (int i = 0; i < MAX_SURFACE_NUM; i++) {
        mKhandles[i] = 0;
        mRotatedSurfaces[i] = 0;
        mDrmBuf[i] = NULL;
    }
}

RotationBufferProvider::~RotationBufferProvider()
{
}

uint32_t RotationBufferProvider::getMilliseconds()
{
    struct timeval ptimeval;
    gettimeofday(&ptimeval, NULL);
    return (uint32_t)((ptimeval.tv_sec * 1000) + (ptimeval.tv_usec / 1000));
}

bool RotationBufferProvider::initialize()
{
    if (NULL == mWsbm)
        return false;
    mTTMWrappers.setCapacity(TTM_WRAPPER_COUNT);
    return true;
}

void RotationBufferProvider::deinitialize()
{
    stopVA();
    reset();
}

void RotationBufferProvider::reset()
{
    if (mTTMWrappers.size()) {
        invalidateCaches();
    }
}

void RotationBufferProvider::invalidateCaches()
{
    void *buf;

    for (size_t i = 0; i < mTTMWrappers.size(); i++) {
        buf = mTTMWrappers.valueAt(i);
        if (!mWsbm->destroyTTMBuffer(buf))
            WTRACE("failed to free TTMBuffer");
    }
    mTTMWrappers.clear();
}

int RotationBufferProvider::transFromHalToVa(int transform)
{
    if (transform == HAL_TRANSFORM_ROT_90)
        return VA_ROTATION_90;
    if (transform == HAL_TRANSFORM_ROT_180)
        return VA_ROTATION_180;
    if (transform == HAL_TRANSFORM_ROT_270)
        return VA_ROTATION_270;
    return 0;
}

int RotationBufferProvider::getStride(bool isTarget, int width)
{
    int stride = 0;
    if (width <= 512)
        stride = 512;
    else if (width <= 1024)
        stride = 1024;
    else if (width <= 1280) {
        stride = 1280;
        if (isTarget)
            stride = 2048;
    } else if (width <= 2048)
        stride = 2048;
    else if (width <= 4096)
        stride = 4096;
    else
        stride = (width + 0x3f) & ~0x3f;
    return stride;
}

buffer_handle_t RotationBufferProvider::createWsbmBuffer(int width, int height, void **buf)
{
    int size = width * height * 3 / 2; // YUV420 NV12 format
    int allignment = 16 * 2048; // tiling row stride aligned
    bool ret = mWsbm->allocateTTMBuffer(size, allignment, buf);

    if (ret == false) {
        ETRACE("failed to allocate TTM buffer");
        return 0;
    }

    return (buffer_handle_t) mWsbm->getKBufHandle(*buf);
}

bool RotationBufferProvider::createVaSurface(VideoPayloadBuffer *payload, int transform, bool isTarget)
{
    VAStatus vaStatus;
    VASurfaceAttributeTPI attribTpi;
    VASurfaceAttributeTPI *vaSurfaceAttrib = &attribTpi;
    int stride;
    unsigned long buffers;
    VASurfaceID *surface;
    int width = 0, height = 0, bufferHeight = 0;

    if (isTarget) {
        if (transFromHalToVa(transform) == VA_ROTATION_180) {
            width = payload->width;
            height = payload->height;
        } else {
            width = payload->height;
            height = payload->width;
        }
        mRotatedWidth = width;
        mRotatedHeight = height;
        bufferHeight = (height + 0x1f) & ~0x1f;
        stride = getStride(isTarget, width);
    } else {
        width = payload->width;
        height = payload->height;
        bufferHeight = (payload->height + 0x1f) & ~0x1f;
        stride = payload->luma_stride; /* NV12 srouce buffer */
    }

    if (!stride) {
        ETRACE("invalid stride value");
        return false;
    }

    mBobDeinterlace = payload->bob_deinterlace;
    // adjust source target for Bob deinterlace
    if (!isTarget && mBobDeinterlace) {
        height >>= 1;
        bufferHeight >>= 1;
        stride <<= 1;
    }

    vaSurfaceAttrib->count = 1;
    vaSurfaceAttrib->width = width;
    vaSurfaceAttrib->height = height;
    vaSurfaceAttrib->pixel_format = payload->format;
    vaSurfaceAttrib->type = VAExternalMemoryKernelDRMBufffer;
    vaSurfaceAttrib->tiling = payload->tiling;
    vaSurfaceAttrib->size = (stride * bufferHeight * 3) / 2;
    vaSurfaceAttrib->luma_offset = 0;
    vaSurfaceAttrib->chroma_v_offset = stride * bufferHeight;
    vaSurfaceAttrib->luma_stride = vaSurfaceAttrib->chroma_u_stride
                                 = vaSurfaceAttrib->chroma_v_stride
                                 = stride;
    vaSurfaceAttrib->chroma_u_offset = vaSurfaceAttrib->chroma_v_offset;
    vaSurfaceAttrib->buffers = &buffers;

    if (isTarget) {
        buffer_handle_t khandle = createWsbmBuffer(stride, bufferHeight, &mDrmBuf[mTargetIndex]);
        if (khandle == 0) {
            ETRACE("failed to create buffer by wsbm");
            return false;
        }

        mKhandles[mTargetIndex] = khandle;
        vaSurfaceAttrib->buffers[0] = (uintptr_t) khandle;
        mRotatedStride = stride;
        surface = &mRotatedSurfaces[mTargetIndex];
    } else {
        vaSurfaceAttrib->buffers[0] = (uintptr_t) payload->khandle;
        surface = &mSourceSurface;
        /* set src surface width/height to video crop size */
        if (payload->crop_width && payload->crop_height) {
            width = payload->crop_width;
            height = (payload->crop_height >> mBobDeinterlace);
        } else {
            VTRACE("Invalid cropping width or height");
            payload->crop_width = width;
            payload->crop_height = height;
        }
    }

    vaStatus = vaCreateSurfacesWithAttribute(mVaDpy,
                                             width,
                                             height,
                                             VA_RT_FORMAT_YUV420,
                                             1,
                                             surface,
                                             vaSurfaceAttrib);
    if (vaStatus != VA_STATUS_SUCCESS) {
        ETRACE("vaCreateSurfacesWithAttribute returns %d", vaStatus);
        ETRACE("Attributes: target: %d, width: %d, height %d, bufferHeight %d, tiling %d",
                isTarget, width, height, bufferHeight, payload->tiling);
        *surface = 0;
        return false;
    }

    return true;
}

bool RotationBufferProvider::startVA(VideoPayloadBuffer *payload, int transform)
{
    bool ret = true;
    VAStatus vaStatus;
    VAEntrypoint *entryPoint;
    VAConfigAttrib attribDummy;
    int numEntryPoints;
    bool supportVideoProcessing = false;
    int majorVer = 0, minorVer = 0;

    // VA will hold a copy of the param pointer, so local varialbe doesn't work
    mVaDpy = vaGetDisplay(&mDisplay);
    if (NULL == mVaDpy) {
        ETRACE("failed to get VADisplay");
        return false;
    }

    vaStatus = vaInitialize(mVaDpy, &majorVer, &minorVer);
    CHECK_VA_STATUS_RETURN("vaInitialize");

    numEntryPoints = vaMaxNumEntrypoints(mVaDpy);

    if (numEntryPoints <= 0) {
        ETRACE("numEntryPoints value is invalid");
        return false;
    }

    entryPoint = (VAEntrypoint*)malloc(sizeof(VAEntrypoint) * numEntryPoints);
    if (NULL == entryPoint) {
        ETRACE("failed to malloc memory for entryPoint");
        return false;
    }

    vaStatus = vaQueryConfigEntrypoints(mVaDpy,
                                        VAProfileNone,
                                        entryPoint,
                                        &numEntryPoints);
    CHECK_VA_STATUS_RETURN("vaQueryConfigEntrypoints");

    for (int i = 0; i < numEntryPoints; i++)
        if (entryPoint[i] == VAEntrypointVideoProc)
            supportVideoProcessing = true;

    free(entryPoint);
    entryPoint = NULL;

    if (!supportVideoProcessing) {
        ETRACE("VAEntrypointVideoProc is not supported");
        return false;
    }

    vaStatus = vaCreateConfig(mVaDpy,
                              VAProfileNone,
                              VAEntrypointVideoProc,
                              &attribDummy,
                              0,
                              &mVaCfg);
    CHECK_VA_STATUS_RETURN("vaCreateConfig");

    // create first target surface
    ret = createVaSurface(payload, transform, true);
    if (ret == false) {
        ETRACE("failed to create target surface with attribute");
        return false;
    }

    vaStatus = vaCreateContext(mVaDpy,
                               mVaCfg,
                               payload->width,
                               payload->height,
                               0,
                               &mRotatedSurfaces[0],
                               1,
                               &mVaCtx);
    CHECK_VA_STATUS_RETURN("vaCreateContext");

    VAProcFilterType filters[VAProcFilterCount];
    unsigned int numFilters = VAProcFilterCount;
    vaStatus = vaQueryVideoProcFilters(mVaDpy, mVaCtx, filters, &numFilters);
    CHECK_VA_STATUS_RETURN("vaQueryVideoProcFilters");

    bool supportVideoProcFilter = false;
    for (unsigned int j = 0; j < numFilters; j++)
        if (filters[j] == VAProcFilterNone)
            supportVideoProcFilter = true;

    if (!supportVideoProcFilter) {
        ETRACE("VAProcFilterNone is not supported");
        return false;
    }

    VAProcFilterParameterBuffer filter;
    filter.type = VAProcFilterNone;
    filter.value = 0;

    vaStatus = vaCreateBuffer(mVaDpy,
                              mVaCtx,
                              VAProcFilterParameterBufferType,
                              sizeof(filter),
                              1,
                              &filter,
                              &mVaBufFilter);
    CHECK_VA_STATUS_RETURN("vaCreateBuffer");

    VAProcPipelineCaps pipelineCaps;
    unsigned int numCaps = 1;
    vaStatus = vaQueryVideoProcPipelineCaps(mVaDpy,
                                            mVaCtx,
                                            &mVaBufFilter,
                                            numCaps,
                                            &pipelineCaps);
    CHECK_VA_STATUS_RETURN("vaQueryVideoProcPipelineCaps");

    if (!(pipelineCaps.rotation_flags & (1 << transFromHalToVa(transform)))) {
        ETRACE("VA_ROTATION_xxx: 0x%08x is not supported by the filter",
             transFromHalToVa(transform));
        return false;
    }

    mVaInitialized = true;

    return true;
}

bool RotationBufferProvider::setupRotationBuffer(VideoPayloadBuffer *payload, int transform)
{
#ifdef DEBUG_ROTATION_PERFROMANCE
    uint32_t setup_Begin = getMilliseconds();
#endif
    VAStatus vaStatus;
    int stride;
    bool ret = false;

    if (payload->format != VA_FOURCC_NV12 || payload->width == 0 || payload->height == 0) {
        WTRACE("payload data is not correct: format %#x, width %d, height %d",
            payload->format, payload->width, payload->height);
        return ret;
    }

    if (payload->width > 1280 && payload->width <= 2048) {
        payload->tiling = 1;
    }

    do {
        if (isContextChanged(payload->width, payload->height, transform)) {
            DTRACE("VA is restarted as rotation context changes");

            if (mVaInitialized) {
                stopVA(); // need to re-initialize VA for new rotation config
            }
            mTransform = transform;
            mWidth = payload->width;
            mHeight = payload->height;
        }

        if (!mVaInitialized) {
            ret = startVA(payload, transform);
            if (ret == false) {
                vaStatus = VA_STATUS_ERROR_OPERATION_FAILED;
                break;
            }
        }

        // start to create next target surface
        if (!mRotatedSurfaces[mTargetIndex]) {
            ret = createVaSurface(payload, transform, true);
            if (ret == false) {
                ETRACE("failed to create target surface with attribute");
                vaStatus = VA_STATUS_ERROR_OPERATION_FAILED;
                break;
            }
        }

        // create source surface
        ret = createVaSurface(payload, transform, false);
        if (ret == false) {
            ETRACE("failed to create source surface with attribute");
            vaStatus = VA_STATUS_ERROR_OPERATION_FAILED;
            break;
        }

#ifdef DEBUG_ROTATION_PERFROMANCE
        uint32_t beginPicture = getMilliseconds();
#endif
        vaStatus = vaBeginPicture(mVaDpy, mVaCtx, mRotatedSurfaces[mTargetIndex]);
        CHECK_VA_STATUS_BREAK("vaBeginPicture");

        VABufferID pipelineBuf;
        void *p;
        VAProcPipelineParameterBuffer *pipelineParam;
        vaStatus = vaCreateBuffer(mVaDpy,
                                  mVaCtx,
                                  VAProcPipelineParameterBufferType,
                                  sizeof(*pipelineParam),
                                  1,
                                  NULL,
                                  &pipelineBuf);
        CHECK_VA_STATUS_BREAK("vaCreateBuffer");

        vaStatus = vaMapBuffer(mVaDpy, pipelineBuf, &p);
        CHECK_VA_STATUS_BREAK("vaMapBuffer");

        pipelineParam = (VAProcPipelineParameterBuffer*)p;
        pipelineParam->surface = mSourceSurface;
        pipelineParam->rotation_state = transFromHalToVa(transform);
        pipelineParam->filters = &mVaBufFilter;
        pipelineParam->num_filters = 1;
        pipelineParam->surface_region = NULL;
        pipelineParam->output_region = NULL;
        pipelineParam->num_forward_references = 0;
        pipelineParam->num_backward_references = 0;
        vaStatus = vaUnmapBuffer(mVaDpy, pipelineBuf);
        CHECK_VA_STATUS_BREAK("vaUnmapBuffer");

        vaStatus = vaRenderPicture(mVaDpy, mVaCtx, &pipelineBuf, 1);
        CHECK_VA_STATUS_BREAK("vaRenderPicture");

        vaStatus = vaEndPicture(mVaDpy, mVaCtx);
        CHECK_VA_STATUS_BREAK("vaEndPicture");

        vaStatus = vaSyncSurface(mVaDpy, mRotatedSurfaces[mTargetIndex]);
        CHECK_VA_STATUS_BREAK("vaSyncSurface");

#ifdef DEBUG_ROTATION_PERFROMANCE
        ITRACE("time spent %dms from vaBeginPicture to vaSyncSurface",
             getMilliseconds() - beginPicture);
#endif

        // Populate payload fields so that overlayPlane can flip the buffer
        payload->rotated_width = mRotatedStride;
        payload->rotated_height = mRotatedHeight;
        payload->rotated_buffer_handle = mKhandles[mTargetIndex];
        // setting client transform to 0 to force re-generating rotated buffer whenever needed.
        payload->client_transform = 0;
        mTargetIndex++;
        if (mTargetIndex >= MAX_SURFACE_NUM)
            mTargetIndex = 0;

    } while (0);

#ifdef DEBUG_ROTATION_PERFROMANCE
    ITRACE("time spent %dms for setupRotationBuffer",
         getMilliseconds() - setup_Begin);
#endif

    if (mSourceSurface > 0) {
        vaStatus = vaDestroySurfaces(mVaDpy, &mSourceSurface, 1);
        if (vaStatus != VA_STATUS_SUCCESS)
            WTRACE("vaDestroySurfaces failed, vaStatus = %d", vaStatus);
        mSourceSurface = 0;
    }

    if (vaStatus != VA_STATUS_SUCCESS) {
        stopVA();
        return false; // To not block HWC, just abort instead of retry
    }

    if (!payload->khandle) {
        WTRACE("khandle is reset by decoder, surface is invalid!");
        return false;
    }

    return true;
}

bool RotationBufferProvider::prepareBufferInfo(int w, int h, int stride, VideoPayloadBuffer *payload, void *user_pt)
{
    int chroma_offset, size;
    void *buf = NULL;

    payload->width = payload->crop_width = w;
    payload->height = payload->crop_height = h;
    payload->coded_width = ((w + 0xf) & ~0xf);
    payload->coded_height = ((h + 0xf) & ~0xf);
    payload->format = VA_FOURCC_NV12;
    payload->tiling = 1;
    payload->luma_stride = stride;
    payload->chroma_u_stride = stride;
    payload->chroma_v_stride = stride;
    payload->client_transform = 0;
    payload->bob_deinterlace = 0;

    chroma_offset = stride * h;
    size = stride * h + stride * h / 2;

    ssize_t index;
    index = mTTMWrappers.indexOfKey((uint64_t)user_pt);
    if (index < 0) {
        VTRACE("wrapped userPt as wsbm buffer");
        bool ret = mWsbm->allocateTTMBufferUB(size, 0, &buf, user_pt);
        if (ret == false) {
            ETRACE("failed to allocate TTM buffer");
            return ret;
        }

        if (mTTMWrappers.size() >= TTM_WRAPPER_COUNT) {
            WTRACE("mTTMWrappers is unexpectedly full. Invalidate caches");
            invalidateCaches();
        }

        index = mTTMWrappers.add((uint64_t)user_pt, buf);
    } else {
        VTRACE("got wsbmBuffer in saved caches");
        buf = mTTMWrappers.valueAt(index);
    }

    payload->khandle = (buffer_handle_t) mWsbm->getKBufHandle(buf);
    return true;
}

void RotationBufferProvider::freeVaSurfaces()
{
    bool ret;
    VAStatus vaStatus;

    for (int i = 0; i < MAX_SURFACE_NUM; i++) {
        if (NULL != mDrmBuf[i]) {
            ret = mWsbm->destroyTTMBuffer(mDrmBuf[i]);
            if (!ret)
                WTRACE("failed to free TTMBuffer");
            mDrmBuf[i] = NULL;
        }
    }

    // remove wsbm buffer ref from VA
    for (int j = 0; j < MAX_SURFACE_NUM; j++) {
        if (0 != mRotatedSurfaces[j]) {
            vaStatus = vaDestroySurfaces(mVaDpy, &mRotatedSurfaces[j], 1);
            if (vaStatus != VA_STATUS_SUCCESS)
                WTRACE("vaDestroySurfaces failed, vaStatus = %d", vaStatus);
        }
        mRotatedSurfaces[j] = 0;
    }
}

void RotationBufferProvider::stopVA()
{
    freeVaSurfaces();

    if (0 != mVaBufFilter)
        vaDestroyBuffer(mVaDpy, mVaBufFilter);
    if (0 != mVaCfg)
        vaDestroyConfig(mVaDpy,mVaCfg);
    if (0 != mVaCtx)
        vaDestroyContext(mVaDpy, mVaCtx);
    if (0 != mVaDpy)
        vaTerminate(mVaDpy);

    mVaInitialized = false;

    for (int i = 0; i < MAX_SURFACE_NUM; i++) {
        mKhandles[i] = 0;
        mRotatedSurfaces[i] = 0;
        mDrmBuf[i] = NULL;
    }
    // reset VA variable
    mVaDpy = 0;
    mVaCfg = 0;
    mVaCtx = 0;
    mVaBufFilter = 0;
    mSourceSurface = 0;

    mWidth = 0;
    mHeight = 0;
    mRotatedWidth = 0;
    mRotatedHeight = 0;
    mRotatedStride = 0;
    mTargetIndex = 0;
    mBobDeinterlace = 0;
}

bool RotationBufferProvider::isContextChanged(int width, int height, int transform)
{
    // check rotation config
    if (height == mHeight &&
        width == mWidth &&
        transform == mTransform) {
        return false;
    }

    return true;
}

} // name space intel
} // name space android
