129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/*
2a43fb8fce6d9be5577de1e0f49c99bd4fe2f6d44Duy Truong * Copyright (c) 2011, The Linux Foundation. All rights reserved.
329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Redistribution and use in source and binary forms, with or without
529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * modification, are permitted provided that the following conditions are
629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * met:
729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *     * Redistributions of source code must retain the above copyright
829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *       notice, this list of conditions and the following disclaimer.
929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *     * Redistributions in binary form must reproduce the above
1029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *       copyright notice, this list of conditions and the following
1129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *       disclaimer in the documentation and/or other materials provided
1229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *       with the distribution.
13a43fb8fce6d9be5577de1e0f49c99bd4fe2f6d44Duy Truong *     * Neither the name of The Linux Foundation nor the names of its
1429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *       contributors may be used to endorse or promote products derived
1529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *       from this software without specific prior written permission.
1629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
1729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
1829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
1929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
2029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
2129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
2429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
2529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
2629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
2729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
2829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed */
2929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
3029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <cutils/log.h>
3129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <stdlib.h>
3229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include <errno.h>
3329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#include "software_converter.h"
3429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
3529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/** Convert YV12 to YCrCb_420_SP */
3629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedint convertYV12toYCrCb420SP(const copybit_image_t *src, private_handle_t *yv12_handle)
3729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
3829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    private_handle_t* hnd = (private_handle_t*)src->handle;
3929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
4029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if(hnd == NULL || yv12_handle == NULL){
4129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        ALOGE("Invalid handle");
4229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        return -1;
4329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
4429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
4529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // Please refer to the description of YV12 in hardware.h
4629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // for the formulae used to calculate buffer sizes and offsets
4729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
4829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // In a copybit_image_t, w is the stride and
4929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // stride - horiz_padding is the actual width
5029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // vertical stride is the same as height, so not considered
5129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   stride  = src->w;
5229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   width   = src->w - src->horiz_padding;
5329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   height  = src->h;
5429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   y_size  = stride * src->h;
5529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   c_width = ALIGN(stride/2, 16);
5629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   c_size  = c_width * src->h/2;
5729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   chromaPadding = c_width - width/2;
5829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned int   chromaSize = c_size * 2;
5929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned char* newChroma = (unsigned char *)(yv12_handle->base + y_size);
6029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned char* oldChroma = (unsigned char*)(hnd->base + y_size);
6129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    memcpy((char *)yv12_handle->base,(char *)hnd->base,y_size);
6229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
6329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#ifdef __ARM_HAVE_NEON
6429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed   /* interleave */
6529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if(!chromaPadding) {
6629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        unsigned char * t1 = newChroma;
6729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        unsigned char * t2 = oldChroma;
6829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        unsigned char * t3 = t2 + chromaSize/2;
6929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        for(unsigned int i=0; i < (chromaSize/2)>>3; i++) {
7029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            __asm__ __volatile__ (
7129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                    "vld1.u8 d0, [%0]! \n"
7229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                    "vld1.u8 d1, [%1]! \n"
7329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                    "vst2.u8 {d0, d1}, [%2]! \n"
7429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                    :"+r"(t2), "+r"(t3), "+r"(t1)
7529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                    :
7629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                    :"memory","d0","d1"
7729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                 );
7829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
7929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        }
8029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
8129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#else  //__ARM_HAVE_NEON
8229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if(!chromaPadding) {
8329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        for(unsigned int i = 0; i< chromaSize/2; i++) {
8429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            newChroma[i*2]   = oldChroma[i];
8529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            newChroma[i*2+1] = oldChroma[i+chromaSize/2];
8629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        }
8729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
8829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
8929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed#endif
9029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // If the image is not aligned to 16 pixels,
9129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // convert using the C routine below
9229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // r1 tracks the row of the source buffer
9329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // r2 tracks the row of the destination buffer
9429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // The width/2 checks are to avoid copying
9529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // from the padding
9629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
9729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if(chromaPadding) {
9829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        unsigned int r1 = 0, r2 = 0, i = 0, j = 0;
9929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        while(r1 < height/2) {
10029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            if(j == width) {
10129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                j = 0;
10229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                r2++;
10329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                continue;
10429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            }
10529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            if (j+1 == width) {
10629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                newChroma[r2*width + j] = oldChroma[r1*c_width+i];
10729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                r2++;
10829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                newChroma[r2*width] = oldChroma[r1*c_width+i+c_size];
10929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                j = 1;
11029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            } else {
11129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                newChroma[r2*width + j] = oldChroma[r1*c_width+i];
11229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                newChroma[r2*width + j + 1] = oldChroma[r1*c_width+i+c_size];
11329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                j+=2;
11429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            }
11529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            i++;
11629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            if (i == width/2 ) {
11729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                i = 0;
11829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                r1++;
11929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            }
12029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        }
12129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
12229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
12329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed  return 0;
12429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
12529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
12629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedstruct copyInfo{
12729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int width;
12829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int height;
12929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int src_stride;
13029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int dst_stride;
13129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int src_plane1_offset;
13229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int src_plane2_offset;
13329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int dst_plane1_offset;
13429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int dst_plane2_offset;
13529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed};
13629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
13729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/* Internal function to do the actual copy of source to destination */
13829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedstatic int copy_source_to_destination(const int src_base, const int dst_base,
13929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                      copyInfo& info)
14029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
14129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if (!src_base || !dst_base) {
14229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        ALOGE("%s: invalid memory src_base = 0x%x dst_base=0x%x",
14329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed             __FUNCTION__, src_base, dst_base);
14429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed         return COPYBIT_FAILURE;
14529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
14629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
14729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int width = info.width;
14829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int height = info.height;
14929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned char *src = (unsigned char*)src_base;
15029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    unsigned char *dst = (unsigned char*)dst_base;
15129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
15229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // Copy the luma
15329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    for (int i = 0; i < height; i++) {
15429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        memcpy(dst, src, width);
15529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        src += info.src_stride;
15629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        dst += info.dst_stride;
15729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
15829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
15929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    // Copy plane 1
16029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    src = (unsigned char*)(src_base + info.src_plane1_offset);
16129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    dst = (unsigned char*)(dst_base + info.dst_plane1_offset);
16229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    width = width/2;
16329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    height = height/2;
16429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    for (int i = 0; i < height; i++) {
16529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        memcpy(dst, src, info.src_stride);
16629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        src += info.src_stride;
16729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        dst += info.dst_stride;
16829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
16929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    return 0;
17029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
17129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
17229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
17329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/*
17429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Function to convert the c2d format into an equivalent Android format
17529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
17629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * @param: source buffer handle
17729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * @param: destination image
17829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
17929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * @return: return status
18029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed */
18129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedint convert_yuv_c2d_to_yuv_android(private_handle_t *hnd,
18229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                   struct copybit_image_t const *rhs)
18329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
18429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    ALOGD("Enter %s", __FUNCTION__);
18529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if (!hnd || !rhs) {
18629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        ALOGE("%s: invalid inputs hnd=%p rhs=%p", __FUNCTION__, hnd, rhs);
18729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        return COPYBIT_FAILURE;
18829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
18929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
19029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int ret = COPYBIT_SUCCESS;
19129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    private_handle_t *dst_hnd = (private_handle_t *)rhs->handle;
19229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
19329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    copyInfo info;
19429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.width = rhs->w;
19529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.height = rhs->h;
19629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.src_stride = ALIGN(info.width, 32);
19729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.dst_stride = ALIGN(info.width, 16);
19829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    switch(rhs->format) {
19929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        case HAL_PIXEL_FORMAT_YCbCr_420_SP:
20029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        case HAL_PIXEL_FORMAT_YCrCb_420_SP: {
20129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.src_plane1_offset = info.src_stride*info.height;
20229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.dst_plane1_offset = info.dst_stride*info.height;
20329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        } break;
20429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: {
20529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            // Chroma is 2K aligned for the NV12 encodeable format.
20629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.src_plane1_offset = ALIGN(info.src_stride*info.height, 2048);
20729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.dst_plane1_offset = ALIGN(info.dst_stride*info.height, 2048);
20829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        } break;
20929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        default:
21029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            ALOGE("%s: unsupported format (format=0x%x)", __FUNCTION__,
21129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                 rhs->format);
21229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            return COPYBIT_FAILURE;
21329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
21429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
21529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    ret = copy_source_to_destination(hnd->base, dst_hnd->base, info);
21629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    return ret;
21729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
21829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
21929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed/*
22029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * Function to convert the Android format into an equivalent C2D format
22129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
22229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * @param: source buffer handle
22329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * @param: destination image
22429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed *
22529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed * @return: return status
22629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed */
22729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmedint convert_yuv_android_to_yuv_c2d(private_handle_t *hnd,
22829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                                   struct copybit_image_t const *rhs)
22929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed{
23029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    if (!hnd || !rhs) {
23129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        ALOGE("%s: invalid inputs hnd=%p rhs=%p", __FUNCTION__, hnd, rhs);
23229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        return COPYBIT_FAILURE;
23329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
23429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
23529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    int ret = COPYBIT_SUCCESS;
23629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    private_handle_t *dst_hnd = (private_handle_t *)rhs->handle;
23729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
23829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    copyInfo info;
23929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.width = rhs->w;
24029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.height = rhs->h;
24129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.src_stride = ALIGN(hnd->width, 16);
24229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    info.dst_stride = ALIGN(info.width, 32);
24329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    switch(rhs->format) {
24429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        case HAL_PIXEL_FORMAT_YCbCr_420_SP:
24529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        case HAL_PIXEL_FORMAT_YCrCb_420_SP: {
24629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.src_plane1_offset = info.src_stride*info.height;
24729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.dst_plane1_offset = info.dst_stride*info.height;
24829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        } break;
24929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: {
25029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            // Chroma is 2K aligned for the NV12 encodeable format.
25129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.src_plane1_offset = ALIGN(info.src_stride*info.height, 2048);
25229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            info.dst_plane1_offset = ALIGN(info.dst_stride*info.height, 2048);
25329a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        } break;
25429a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed        default:
25529a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            ALOGE("%s: unsupported format (format=0x%x)", __FUNCTION__,
25629a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed                 rhs->format);
25729a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed            return -1;
25829a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    }
25929a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed
26029a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    ret = copy_source_to_destination(hnd->base, dst_hnd->base, info);
26129a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed    return ret;
26229a26818d7294055539167b2fbfdaa168bcf725cNaseer Ahmed}
263