1b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* 2b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * Copyright (C) 2008 The Android Open Source Project 3b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * Copyright (c) 2010-2013, The Linux Foundation. All rights reserved. 4b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * 5b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * Not a Contribution, Apache license notifications and license are retained 6b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * for attribution purposes only. 7b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * 8b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * Licensed under the Apache License, Version 2.0 (the "License"); 9b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * you may not use this file except in compliance with the License. 10b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * You may obtain a copy of the License at 11b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * 12b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * http://www.apache.org/licenses/LICENSE-2.0 13b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * 14b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * Unless required by applicable law or agreed to in writing, software 15b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * distributed under the License is distributed on an "AS IS" BASIS, 16b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 17b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * See the License for the specific language governing permissions and 18b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * limitations under the License. 19b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 20b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <cutils/log.h> 21b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <sys/resource.h> 22b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <sys/prctl.h> 23b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 24b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <stdint.h> 25b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <string.h> 26b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <unistd.h> 27b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <errno.h> 28b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <fcntl.h> 29b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 30b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <sys/ioctl.h> 31b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <sys/types.h> 32b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <sys/mman.h> 33b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 34b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <linux/msm_kgsl.h> 35b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 36b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <EGL/eglplatform.h> 37b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <cutils/native_handle.h> 38b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <cutils/ashmem.h> 39b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <linux/ashmem.h> 40b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <gralloc_priv.h> 41b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 42b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <copybit.h> 43b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <alloc_controller.h> 44b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <memalloc.h> 45b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 46b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include "c2d2.h" 47b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include "software_converter.h" 48b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 49b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#include <dlfcn.h> 50b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 51b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyusing gralloc::IMemAlloc; 52b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyusing gralloc::IonController; 53b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyusing gralloc::alloc_data; 54b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 55b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dCreateSurface)( uint32 *surface_id, 56b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 surface_bits, 57b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_TYPE surface_type, 58b166940edca6e312463461438e2aa66e9852c26aBenoit Goby void *surface_definition ); 59b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 60b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dUpdateSurface)( uint32 surface_id, 61b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 surface_bits, 62b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_TYPE surface_type, 63b166940edca6e312463461438e2aa66e9852c26aBenoit Goby void *surface_definition ); 64b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 65b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dReadSurface)( uint32 surface_id, 66b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_TYPE surface_type, 67b166940edca6e312463461438e2aa66e9852c26aBenoit Goby void *surface_definition, 68b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int32 x, int32 y ); 69b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 70b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dDraw)( uint32 target_id, 71b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 target_config, C2D_RECT *target_scissor, 72b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 target_mask_id, uint32 target_color_key, 73b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT *objects_list, uint32 num_objects ); 74b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 75b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dFinish)( uint32 target_id); 76b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 77b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dFlush)( uint32 target_id, c2d_ts_handle *timestamp); 78b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 79b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dWaitTimestamp)( c2d_ts_handle timestamp ); 80b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 81b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dDestroySurface)( uint32 surface_id ); 82b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 83b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dMapAddr) ( int mem_fd, void * hostptr, uint32 len, 84b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 offset, uint32 flags, void ** gpuaddr); 85b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 86b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dUnMapAddr) ( void * gpuaddr); 87b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 88b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dGetDriverCapabilities) ( C2D_DRIVER_INFO * driver_info); 89b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 90b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* create a fence fd for the timestamp */ 91b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dCreateFenceFD) ( uint32 target_id, c2d_ts_handle timestamp, 92b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int32 *fd); 93b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 94b166940edca6e312463461438e2aa66e9852c26aBenoit GobyC2D_STATUS (*LINK_c2dFillSurface) ( uint32 surface_id, uint32 fill_color, 95b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_RECT * fill_rect); 96b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 97b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/******************************************************************************/ 98b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 99b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#if defined(COPYBIT_Z180) 100b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_SCALE_FACTOR (4096) 101b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_DIMENSION (4096) 102b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#else 103b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#error "Unsupported HW version" 104b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#endif 105b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 106b166940edca6e312463461438e2aa66e9852c26aBenoit Goby// The following defines can be changed as required i.e. as we encounter 107b166940edca6e312463461438e2aa66e9852c26aBenoit Goby// complex use cases. 108b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_RGB_SURFACES 8 // Max. RGB layers currently supported per draw 109b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_YUV_2_PLANE_SURFACES 4// Max. 2-plane YUV layers currently supported per draw 110b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_YUV_3_PLANE_SURFACES 1// Max. 3-plane YUV layers currently supported per draw 111b166940edca6e312463461438e2aa66e9852c26aBenoit Goby// +1 for the destination surface. We cannot have multiple destination surfaces. 112b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_SURFACES (MAX_RGB_SURFACES + MAX_YUV_2_PLANE_SURFACES + MAX_YUV_3_PLANE_SURFACES + 1) 113b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define NUM_SURFACE_TYPES 3 // RGB_SURFACE + YUV_SURFACE_2_PLANES + YUV_SURFACE_3_PLANES 114b166940edca6e312463461438e2aa66e9852c26aBenoit Goby#define MAX_BLIT_OBJECT_COUNT 50 // Max. blit objects that can be passed per draw 115b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 116b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyenum { 117b166940edca6e312463461438e2aa66e9852c26aBenoit Goby RGB_SURFACE, 118b166940edca6e312463461438e2aa66e9852c26aBenoit Goby YUV_SURFACE_2_PLANES, 119b166940edca6e312463461438e2aa66e9852c26aBenoit Goby YUV_SURFACE_3_PLANES 120b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 121b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 122b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyenum eConversionType { 123b166940edca6e312463461438e2aa66e9852c26aBenoit Goby CONVERT_TO_ANDROID_FORMAT, 124b166940edca6e312463461438e2aa66e9852c26aBenoit Goby CONVERT_TO_C2D_FORMAT 125b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 126b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 127b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyenum eC2DFlags { 128b166940edca6e312463461438e2aa66e9852c26aBenoit Goby FLAGS_PREMULTIPLIED_ALPHA = 1<<0, 129b166940edca6e312463461438e2aa66e9852c26aBenoit Goby FLAGS_YUV_DESTINATION = 1<<1, 130b166940edca6e312463461438e2aa66e9852c26aBenoit Goby FLAGS_TEMP_SRC_DST = 1<<2 131b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 132b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 133b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic gralloc::IAllocController* sAlloc = 0; 134b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/******************************************************************************/ 135b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 136b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** State information for each device instance */ 137b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystruct copybit_context_t { 138b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_device_t device; 139b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Templates for the various source surfaces. These templates are created 140b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // to avoid the expensive create/destroy C2D Surfaces 141b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT_STR blit_rgb_object[MAX_RGB_SURFACES]; 142b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT_STR blit_yuv_2_plane_object[MAX_YUV_2_PLANE_SURFACES]; 143b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT_STR blit_yuv_3_plane_object[MAX_YUV_3_PLANE_SURFACES]; 144b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT_STR blit_list[MAX_BLIT_OBJECT_COUNT]; // Z-ordered list of blit objects 145b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_DRIVER_INFO c2d_driver_info; 146b166940edca6e312463461438e2aa66e9852c26aBenoit Goby void *libc2d2; 147b166940edca6e312463461438e2aa66e9852c26aBenoit Goby alloc_data temp_src_buffer; 148b166940edca6e312463461438e2aa66e9852c26aBenoit Goby alloc_data temp_dst_buffer; 149b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unsigned int dst[NUM_SURFACE_TYPES]; // dst surfaces 150b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unsigned int mapped_gpu_addr[MAX_SURFACES]; // GPU addresses mapped inside copybit 151b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int blit_rgb_count; // Total RGB surfaces being blit 152b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int blit_yuv_2_plane_count; // Total 2 plane YUV surfaces being 153b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int blit_yuv_3_plane_count; // Total 3 plane YUV surfaces being blit 154b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int blit_count; // Total blit objects. 155b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unsigned int trg_transform; /* target transform */ 156b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int fb_width; 157b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int fb_height; 158b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int src_global_alpha; 159b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int config_mask; 160b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int dst_surface_type; 161b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool is_premultiplied_alpha; 162b166940edca6e312463461438e2aa66e9852c26aBenoit Goby void* time_stamp; 163b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 164b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // used for signaling the wait thread 165b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool wait_timestamp; 166b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_t wait_thread_id; 167b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool stop_thread; 168b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_t wait_cleanup_lock; 169b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_cond_t wait_cleanup_cond; 170b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 171b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 172b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 173b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystruct bufferInfo { 174b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int width; 175b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int height; 176b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int format; 177b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 178b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 179b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystruct yuvPlaneInfo { 180b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int yStride; //luma stride 181b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int plane1_stride; 182b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int plane2_stride; 183b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int plane1_offset; 184b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int plane2_offset; 185b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 186b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 187b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** 188b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * Common hardware methods 189b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 190b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 191b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int open_copybit(const struct hw_module_t* module, const char* name, 192b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct hw_device_t** device); 193b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 194b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic struct hw_module_methods_t copybit_module_methods = { 195b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyopen: open_copybit 196b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 197b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 198b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* 199b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * The COPYBIT Module 200b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 201b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystruct copybit_module_t HAL_MODULE_INFO_SYM = { 202b166940edca6e312463461438e2aa66e9852c26aBenoit Gobycommon: { 203b166940edca6e312463461438e2aa66e9852c26aBenoit Gobytag: HARDWARE_MODULE_TAG, 204b166940edca6e312463461438e2aa66e9852c26aBenoit Goby version_major: 1, 205b166940edca6e312463461438e2aa66e9852c26aBenoit Goby version_minor: 0, 206b166940edca6e312463461438e2aa66e9852c26aBenoit Goby id: COPYBIT_HARDWARE_MODULE_ID, 207b166940edca6e312463461438e2aa66e9852c26aBenoit Goby name: "QCT COPYBIT C2D 2.0 Module", 208b166940edca6e312463461438e2aa66e9852c26aBenoit Goby author: "Qualcomm", 209b166940edca6e312463461438e2aa66e9852c26aBenoit Goby methods: ©bit_module_methods 210b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 211b166940edca6e312463461438e2aa66e9852c26aBenoit Goby}; 212b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 213b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 214b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* thread function which waits on the timeStamp and cleans up the surfaces */ 215b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void* c2d_wait_loop(void* ptr) { 216b166940edca6e312463461438e2aa66e9852c26aBenoit Goby copybit_context_t* ctx = (copybit_context_t*)(ptr); 217b166940edca6e312463461438e2aa66e9852c26aBenoit Goby char thread_name[64] = "copybitWaitThr"; 218b166940edca6e312463461438e2aa66e9852c26aBenoit Goby prctl(PR_SET_NAME, (unsigned long) &thread_name, 0, 0, 0); 219b166940edca6e312463461438e2aa66e9852c26aBenoit Goby setpriority(PRIO_PROCESS, 0, HAL_PRIORITY_URGENT_DISPLAY); 220b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 221b166940edca6e312463461438e2aa66e9852c26aBenoit Goby while(ctx->stop_thread == false) { 222b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 223b166940edca6e312463461438e2aa66e9852c26aBenoit Goby while(ctx->wait_timestamp == false && !ctx->stop_thread) { 224b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_cond_wait(&(ctx->wait_cleanup_cond), 225b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &(ctx->wait_cleanup_lock)); 226b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 227b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(ctx->wait_timestamp) { 228b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dWaitTimestamp(ctx->time_stamp)) { 229b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: LINK_c2dWaitTimeStamp ERROR!!", __FUNCTION__); 230b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 231b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->wait_timestamp = false; 232b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Unmap any mapped addresses. 233b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_SURFACES; i++) { 234b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->mapped_gpu_addr[i]) { 235b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dUnMapAddr( (void*)ctx->mapped_gpu_addr[i]); 236b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->mapped_gpu_addr[i] = 0; 237b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 238b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 239b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Reset the counts after the draw. 240b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_count = 0; 241b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_count = 0; 242b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_count = 0; 243b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_count = 0; 244b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 245b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 246b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(ctx->stop_thread) 247b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 248b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 249b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_exit(NULL); 250b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return NULL; 251b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 252b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 253b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 254b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* convert COPYBIT_FORMAT to C2D format */ 255b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int get_format(int format) { 256b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch (format) { 257b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGB_565: return C2D_COLOR_FORMAT_565_RGB; 258b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGBX_8888: return C2D_COLOR_FORMAT_8888_ARGB | 259b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_FORMAT_SWAP_RB | 260b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_FORMAT_DISABLE_ALPHA; 261b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGBA_8888: return C2D_COLOR_FORMAT_8888_ARGB | 262b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_FORMAT_SWAP_RB; 263b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_BGRA_8888: return C2D_COLOR_FORMAT_8888_ARGB; 264b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: return C2D_COLOR_FORMAT_420_NV12; 265b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE:return C2D_COLOR_FORMAT_420_NV12; 266b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: return C2D_COLOR_FORMAT_420_NV21; 267b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED: return C2D_COLOR_FORMAT_420_NV12 | 268b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_FORMAT_MACROTILED; 269b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: ALOGE("%s: invalid format (0x%x", 270b166940edca6e312463461438e2aa66e9852c26aBenoit Goby __FUNCTION__, format); 271b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 272b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 273b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 274b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 275b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 276b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Get the C2D formats needed for conversion to YUV */ 277b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int get_c2d_format_for_yuv_destination(int halFormat) { 278b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch (halFormat) { 279b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // We do not swap the RB when the target is YUV 280b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGBX_8888: return C2D_COLOR_FORMAT_8888_ARGB | 281b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_FORMAT_DISABLE_ALPHA; 282b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGBA_8888: return C2D_COLOR_FORMAT_8888_ARGB; 283b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // The U and V need to be interchanged when the target is YUV 284b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: return C2D_COLOR_FORMAT_420_NV21; 285b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE:return C2D_COLOR_FORMAT_420_NV21; 286b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: return C2D_COLOR_FORMAT_420_NV12; 287b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: return get_format(halFormat); 288b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 289b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 290b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 291b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 292b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* ------------------------------------------------------------------- *//*! 293b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * \internal 294b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * \brief Get the bpp for a particular color format 295b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * \param color format 296b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * \return bits per pixel 297b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *//* ------------------------------------------------------------------- */ 298b166940edca6e312463461438e2aa66e9852c26aBenoit Gobyint c2diGetBpp(int32 colorformat) 299b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 300b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 301b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int c2dBpp = 0; 302b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 303b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(colorformat&0xFF) 304b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 305b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_4444_RGBA: 306b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_4444_ARGB: 307b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_1555_ARGB: 308b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_565_RGB: 309b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_5551_RGBA: 310b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dBpp = 16; 311b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 312b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_8888_RGBA: 313b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_8888_ARGB: 314b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dBpp = 32; 315b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 316b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_8_L: 317b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_8_A: 318b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dBpp = 8; 319b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 320b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_4_A: 321b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dBpp = 4; 322b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 323b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_1: 324b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dBpp = 1; 325b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 326b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 327b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s ERROR", __func__); 328b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 329b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 330b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return c2dBpp; 331b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 332b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 333b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic uint32 c2d_get_gpuaddr(copybit_context_t* ctx, struct private_handle_t *handle, 334b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int &mapped_idx) 335b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 336b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 memtype, *gpuaddr; 337b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_STATUS rc; 338b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 339b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(!handle) 340b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return 0; 341b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 342b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (handle->flags & (private_handle_t::PRIV_FLAGS_USES_PMEM | 343b166940edca6e312463461438e2aa66e9852c26aBenoit Goby private_handle_t::PRIV_FLAGS_USES_PMEM_ADSP)) 344b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memtype = KGSL_USER_MEM_TYPE_PMEM; 345b166940edca6e312463461438e2aa66e9852c26aBenoit Goby else if (handle->flags & private_handle_t::PRIV_FLAGS_USES_ASHMEM) 346b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memtype = KGSL_USER_MEM_TYPE_ASHMEM; 347b166940edca6e312463461438e2aa66e9852c26aBenoit Goby else if (handle->flags & private_handle_t::PRIV_FLAGS_USES_ION) 348b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memtype = KGSL_USER_MEM_TYPE_ION; 349b166940edca6e312463461438e2aa66e9852c26aBenoit Goby else { 350b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("Invalid handle flags: 0x%x", handle->flags); 351b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return 0; 352b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 353b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 354b166940edca6e312463461438e2aa66e9852c26aBenoit Goby rc = LINK_c2dMapAddr(handle->fd, (void*)handle->base, handle->size, 355b166940edca6e312463461438e2aa66e9852c26aBenoit Goby handle->offset, memtype, (void**)&gpuaddr); 356b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 357b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (rc == C2D_STATUS_OK) { 358b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // We have mapped the GPU address inside copybit. We need to unmap this 359b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // address after the blit. Store this address 360b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_SURFACES; i++) { 361b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->mapped_gpu_addr[i] == 0) { 362b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->mapped_gpu_addr[i] = (uint32) gpuaddr; 363b166940edca6e312463461438e2aa66e9852c26aBenoit Goby mapped_idx = i; 364b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 365b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 366b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 367b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 368b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return (uint32) gpuaddr; 369b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 370b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return 0; 371b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 372b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 373b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void unmap_gpuaddr(copybit_context_t* ctx, int mapped_idx) 374b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 375b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx || (mapped_idx == -1)) 376b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return; 377b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 378b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->mapped_gpu_addr[mapped_idx]) { 379b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dUnMapAddr( (void*)ctx->mapped_gpu_addr[mapped_idx]); 380b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->mapped_gpu_addr[mapped_idx] = 0; 381b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 382b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 383b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 384b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int is_supported_rgb_format(int format) 385b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 386b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(format) { 387b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGBA_8888: 388b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGBX_8888: 389b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_RGB_565: 390966f989a6d502dc12ad7f5ad950180df6581f382Mathias Agopian case HAL_PIXEL_FORMAT_BGRA_8888: { 391b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_SUCCESS; 392b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 393b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 394b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 395b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 396b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 397b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 398b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int get_num_planes(int format) 399b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 400b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(format) { 401b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: 402b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: 403b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: 404b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED: { 405b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return 2; 406b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 407b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YV12: { 408b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return 3; 409b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 410b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 411b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 412b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 413b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 414b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 415b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int is_supported_yuv_format(int format) 416b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 417b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(format) { 418b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: 419b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: 420b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: 421b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED: { 422b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_SUCCESS; 423b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 424b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 425b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 426b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 427b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 428b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 429b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int is_valid_destination_format(int format) 430b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 431b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (format == HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED) { 432b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // C2D does not support NV12Tile as a destination format. 433b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 434b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 435b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_SUCCESS; 436b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 437b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 438b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int calculate_yuv_offset_and_stride(const bufferInfo& info, 439b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvPlaneInfo& yuvInfo) 440b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 441b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int width = info.width; 442b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int height = info.height; 443b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int format = info.format; 444b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 445b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int aligned_height = 0; 446b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int aligned_width = 0, size = 0; 447b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 448b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch (format) { 449b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP_TILED: { 450b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* NV12 Tile buffers have their luma height aligned to 32bytes and width 451b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * aligned to 128 bytes. The chroma offset starts at an 8K boundary 452b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 453b166940edca6e312463461438e2aa66e9852c26aBenoit Goby aligned_height = ALIGN(height, 32); 454b166940edca6e312463461438e2aa66e9852c26aBenoit Goby aligned_width = ALIGN(width, 128); 455b166940edca6e312463461438e2aa66e9852c26aBenoit Goby size = aligned_width * aligned_height; 456b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.plane1_offset = ALIGN(size,8192); 457b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.yStride = aligned_width; 458b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.plane1_stride = aligned_width; 459b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 460b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 461b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: 462b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: 463b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: { 464b166940edca6e312463461438e2aa66e9852c26aBenoit Goby aligned_width = ALIGN(width, 32); 465b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.yStride = aligned_width; 466b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.plane1_stride = aligned_width; 467b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (HAL_PIXEL_FORMAT_NV12_ENCODEABLE == format) { 468b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // The encoder requires a 2K aligned chroma offset 469b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.plane1_offset = ALIGN(aligned_width * height, 2048); 470b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else 471b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvInfo.plane1_offset = aligned_width * height; 472b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 473b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 474b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 475b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: { 476b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 477b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 478b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 479b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_SUCCESS; 480b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 481b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 482b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** create C2D surface from copybit image */ 483b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int set_image(copybit_context_t* ctx, uint32 surfaceId, 484b166940edca6e312463461438e2aa66e9852c26aBenoit Goby const struct copybit_image_t *rhs, 485b166940edca6e312463461438e2aa66e9852c26aBenoit Goby const eC2DFlags flags, int &mapped_idx) 486b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 487b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct private_handle_t* handle = (struct private_handle_t*)rhs->handle; 488b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_TYPE surfaceType; 489b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_SUCCESS; 490b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 gpuaddr = 0; 491b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int c2d_format; 492b166940edca6e312463461438e2aa66e9852c26aBenoit Goby mapped_idx = -1; 493b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 494b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (flags & FLAGS_YUV_DESTINATION) { 495b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2d_format = get_c2d_format_for_yuv_destination(rhs->format); 496b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 497b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2d_format = get_format(rhs->format); 498b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 499b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 500b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(c2d_format == -EINVAL) { 501b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: invalid format", __FUNCTION__); 502b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 503b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 504b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 505b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(handle == NULL) { 506b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: invalid handle", __func__); 507b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 508b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 509b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 510b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (handle->gpuaddr == 0) { 511b166940edca6e312463461438e2aa66e9852c26aBenoit Goby gpuaddr = c2d_get_gpuaddr(ctx, handle, mapped_idx); 512b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(!gpuaddr) { 513b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: c2d_get_gpuaddr failed", __FUNCTION__); 514b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 515b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 516b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 517b166940edca6e312463461438e2aa66e9852c26aBenoit Goby gpuaddr = handle->gpuaddr; 518b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 519b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 520b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* create C2D surface */ 521b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(is_supported_rgb_format(rhs->format) == COPYBIT_SUCCESS) { 522b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* RGB */ 523b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_RGB_SURFACE_DEF surfaceDef; 524b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 525b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceType = (C2D_SURFACE_TYPE) (C2D_SURFACE_RGB_HOST | C2D_SURFACE_WITH_PHYS); 526b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 527b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.phys = (void*) gpuaddr; 528b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.buffer = (void*) (handle->base); 529b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 530b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.format = c2d_format | 531b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ((flags & FLAGS_PREMULTIPLIED_ALPHA) ? C2D_FORMAT_PREMULTIPLIED : 0); 532b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.width = rhs->w; 533b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.height = rhs->h; 534b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int aligned_width = ALIGN(surfaceDef.width,32); 535b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.stride = (aligned_width * c2diGetBpp(surfaceDef.format))>>3; 536b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 537b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dUpdateSurface( surfaceId,C2D_TARGET | C2D_SOURCE, surfaceType, 538b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &surfaceDef)) { 539b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: RGB Surface c2dUpdateSurface ERROR", __FUNCTION__); 540b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_idx); 541b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 542b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 543b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (is_supported_yuv_format(rhs->format) == COPYBIT_SUCCESS) { 544b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_YUV_SURFACE_DEF surfaceDef; 545b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memset(&surfaceDef, 0, sizeof(surfaceDef)); 546b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceType = (C2D_SURFACE_TYPE)(C2D_SURFACE_YUV_HOST | C2D_SURFACE_WITH_PHYS); 547b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.format = c2d_format; 548b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 549b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bufferInfo info; 550b166940edca6e312463461438e2aa66e9852c26aBenoit Goby info.width = rhs->w; 551b166940edca6e312463461438e2aa66e9852c26aBenoit Goby info.height = rhs->h; 552b166940edca6e312463461438e2aa66e9852c26aBenoit Goby info.format = rhs->format; 553b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 554b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvPlaneInfo yuvInfo = {0}; 555b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = calculate_yuv_offset_and_stride(info, yuvInfo); 556b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(status != COPYBIT_SUCCESS) { 557b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: calculate_yuv_offset_and_stride error", __FUNCTION__); 558b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_idx); 559b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 560b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 561b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.width = rhs->w; 562b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.height = rhs->h; 563b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.plane0 = (void*) (handle->base); 564b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.phys0 = (void*) (gpuaddr); 565b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.stride0 = yuvInfo.yStride; 566b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 567b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.plane1 = (void*) (handle->base + yuvInfo.plane1_offset); 568b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.phys1 = (void*) (gpuaddr + yuvInfo.plane1_offset); 569b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.stride1 = yuvInfo.plane1_stride; 570b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (3 == get_num_planes(rhs->format)) { 571b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.plane2 = (void*) (handle->base + yuvInfo.plane2_offset); 572b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.phys2 = (void*) (gpuaddr + yuvInfo.plane2_offset); 573b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfaceDef.stride2 = yuvInfo.plane2_stride; 574b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 575b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 576b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dUpdateSurface( surfaceId,C2D_TARGET | C2D_SOURCE, surfaceType, 577b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &surfaceDef)) { 578b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: YUV Surface c2dUpdateSurface ERROR", __FUNCTION__); 579b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_idx); 580b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 581b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 582b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 583b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: invalid format 0x%x", __FUNCTION__, rhs->format); 584b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_idx); 585b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 586b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 587b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 588b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 589b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 590b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 591b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** copy the bits */ 592b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int msm_copybit(struct copybit_context_t *ctx, unsigned int target) 593b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 594b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->blit_count == 0) { 595b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_SUCCESS; 596b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 597b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 598b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < ctx->blit_count; i++) 599b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 600b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_list[i].next = &(ctx->blit_list[i+1]); 601b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 602b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_list[ctx->blit_count-1].next = NULL; 603b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32_t target_transform = ctx->trg_transform; 604b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->c2d_driver_info.capabilities_mask & 605b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_DRIVER_SUPPORTS_OVERRIDE_TARGET_ROTATE_OP) { 606b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // For A3xx - set 0x0 as the transform is set in the config_mask 607b166940edca6e312463461438e2aa66e9852c26aBenoit Goby target_transform = 0x0; 608b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 609b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dDraw(target, target_transform, 0x0, 0, 0, ctx->blit_list, 610b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_count)) { 611b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: LINK_c2dDraw ERROR", __FUNCTION__); 612b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 613b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 614b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_SUCCESS; 615b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 616b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 617b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 618b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 619b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int flush_get_fence_copybit (struct copybit_device_t *dev, int* fd) 620b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 621b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 622b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_FAILURE; 623b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx) 624b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 625b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 626b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = msm_copybit(ctx, ctx->dst[ctx->dst_surface_type]); 627b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 628b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dFlush(ctx->dst[ctx->dst_surface_type], &ctx->time_stamp)) { 629b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: LINK_c2dFlush ERROR", __FUNCTION__); 630b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // unlock the mutex and return failure 631b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 632b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 633b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 634b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dCreateFenceFD(ctx->dst[ctx->dst_surface_type], ctx->time_stamp, 635b166940edca6e312463461438e2aa66e9852c26aBenoit Goby fd)) { 636b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: LINK_c2dCreateFenceFD ERROR", __FUNCTION__); 637b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 638b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 639b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(status == COPYBIT_SUCCESS) { 640b166940edca6e312463461438e2aa66e9852c26aBenoit Goby //signal the wait_thread 641b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->wait_timestamp = true; 642b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_cond_signal(&ctx->wait_cleanup_cond); 643b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 644b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 645b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 646b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 647b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 648b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int finish_copybit(struct copybit_device_t *dev) 649b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 650b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 651b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx) 652b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 653b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 654b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = msm_copybit(ctx, ctx->dst[ctx->dst_surface_type]); 655b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 656b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(LINK_c2dFinish(ctx->dst[ctx->dst_surface_type])) { 657b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: LINK_c2dFinish ERROR", __FUNCTION__); 658b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 659b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 660b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 661b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Unmap any mapped addresses. 662b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_SURFACES; i++) { 663b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->mapped_gpu_addr[i]) { 664b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dUnMapAddr( (void*)ctx->mapped_gpu_addr[i]); 665b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->mapped_gpu_addr[i] = 0; 666b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 667b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 668b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 669b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Reset the counts after the draw. 670b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_count = 0; 671b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_count = 0; 672b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_count = 0; 673b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_count = 0; 674b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 675b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 676b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 677b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int clear_copybit(struct copybit_device_t *dev, 678b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *buf, 679b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t *rect) 680b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 681b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int ret = COPYBIT_SUCCESS; 682b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int flags = FLAGS_PREMULTIPLIED_ALPHA; 683b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int mapped_dst_idx = -1; 684b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 685b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_RECT c2drect = {rect->l, rect->t, rect->r - rect->l, rect->b - rect->t}; 686b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 687b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ret = set_image(ctx, ctx->dst[RGB_SURFACE], buf, 688b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (eC2DFlags)flags, mapped_dst_idx); 689b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(ret) { 690b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: set_image error", __FUNCTION__); 691b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 692b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 693b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 694b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 695b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 696b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ret = LINK_c2dFillSurface(ctx->dst[RGB_SURFACE], 0x0, &c2drect); 697b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 698b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return ret; 699b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 700b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 701b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 702b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** setup rectangles */ 703b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void set_rects(struct copybit_context_t *ctx, 704b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT *c2dObject, 705b166940edca6e312463461438e2aa66e9852c26aBenoit Goby const struct copybit_rect_t *dst, 706b166940edca6e312463461438e2aa66e9852c26aBenoit Goby const struct copybit_rect_t *src, 707b166940edca6e312463461438e2aa66e9852c26aBenoit Goby const struct copybit_rect_t *scissor) 708b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 709b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Set the target rect. 710b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if((ctx->trg_transform & C2D_TARGET_ROTATE_90) && 711b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (ctx->trg_transform & C2D_TARGET_ROTATE_180)) { 712b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* target rotation is 270 */ 713b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.x = (dst->t)<<16; 714b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.y = ctx->fb_width?(ALIGN(ctx->fb_width,32)- dst->r):dst->r; 715b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.y = c2dObject->target_rect.y<<16; 716b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.height = ((dst->r) - (dst->l))<<16; 717b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.width = ((dst->b) - (dst->t))<<16; 718b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if(ctx->trg_transform & C2D_TARGET_ROTATE_90) { 719b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.x = ctx->fb_height?(ctx->fb_height - dst->b):dst->b; 720b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.x = c2dObject->target_rect.x<<16; 721b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.y = (dst->l)<<16; 722b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.height = ((dst->r) - (dst->l))<<16; 723b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.width = ((dst->b) - (dst->t))<<16; 724b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if(ctx->trg_transform & C2D_TARGET_ROTATE_180) { 725b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.y = ctx->fb_height?(ctx->fb_height - dst->b):dst->b; 726b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.y = c2dObject->target_rect.y<<16; 727b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.x = ctx->fb_width?(ALIGN(ctx->fb_width,32) - dst->r):dst->r; 728b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.x = c2dObject->target_rect.x<<16; 729b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.height = ((dst->b) - (dst->t))<<16; 730b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.width = ((dst->r) - (dst->l))<<16; 731b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 732b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.x = (dst->l)<<16; 733b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.y = (dst->t)<<16; 734b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.height = ((dst->b) - (dst->t))<<16; 735b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->target_rect.width = ((dst->r) - (dst->l))<<16; 736b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 737b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->config_mask |= C2D_TARGET_RECT_BIT; 738b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 739b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Set the source rect 740b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->source_rect.x = (src->l)<<16; 741b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->source_rect.y = (src->t)<<16; 742b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->source_rect.height = ((src->b) - (src->t))<<16; 743b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->source_rect.width = ((src->r) - (src->l))<<16; 744b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->config_mask |= C2D_SOURCE_RECT_BIT; 745b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 746b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Set the scissor rect 747b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->scissor_rect.x = scissor->l; 748b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->scissor_rect.y = scissor->t; 749b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->scissor_rect.height = (scissor->b) - (scissor->t); 750b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->scissor_rect.width = (scissor->r) - (scissor->l); 751b166940edca6e312463461438e2aa66e9852c26aBenoit Goby c2dObject->config_mask |= C2D_SCISSOR_RECT_BIT; 752b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 753b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 754b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/*****************************************************************************/ 755b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 756b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** Set a parameter to value */ 757b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int set_parameter_copybit( 758b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_device_t *dev, 759b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int name, 760b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int value) 761b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 762b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 763b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_SUCCESS; 764b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx) { 765b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: null context", __FUNCTION__); 766b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 767b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 768b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 769b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 770b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(name) { 771b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_PLANE_ALPHA: 772b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 773b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (value < 0) value = 0; 774b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (value >= 256) value = 255; 775b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 776b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->src_global_alpha = value; 777b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (value < 255) 778b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->config_mask |= C2D_GLOBAL_ALPHA_BIT; 779b166940edca6e312463461438e2aa66e9852c26aBenoit Goby else 780b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->config_mask &= ~C2D_GLOBAL_ALPHA_BIT; 781b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 782b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 783b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_BLEND_MODE: 784b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 785b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (value == COPYBIT_BLENDING_NONE) { 786b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->config_mask |= C2D_ALPHA_BLEND_NONE; 787b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->is_premultiplied_alpha = true; 788b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (value == COPYBIT_BLENDING_PREMULT) { 789b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->is_premultiplied_alpha = true; 790b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 791b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->config_mask &= ~C2D_ALPHA_BLEND_NONE; 792b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 793b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 794b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 795b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_TRANSFORM: 796b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 797b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unsigned int transform = 0; 798b166940edca6e312463461438e2aa66e9852c26aBenoit Goby uint32 config_mask = 0; 799b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_OVERRIDE_GLOBAL_TARGET_ROTATE_CONFIG; 800b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if((value & 0x7) == COPYBIT_TRANSFORM_ROT_180) { 801b166940edca6e312463461438e2aa66e9852c26aBenoit Goby transform = C2D_TARGET_ROTATE_180; 802b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_OVERRIDE_TARGET_ROTATE_180; 803b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if((value & 0x7) == COPYBIT_TRANSFORM_ROT_270) { 804b166940edca6e312463461438e2aa66e9852c26aBenoit Goby transform = C2D_TARGET_ROTATE_90; 805b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_OVERRIDE_TARGET_ROTATE_90; 806b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if(value == COPYBIT_TRANSFORM_ROT_90) { 807b166940edca6e312463461438e2aa66e9852c26aBenoit Goby transform = C2D_TARGET_ROTATE_270; 808b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_OVERRIDE_TARGET_ROTATE_270; 809b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 810b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_OVERRIDE_TARGET_ROTATE_0; 811b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(value & COPYBIT_TRANSFORM_FLIP_H) { 812b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_MIRROR_H_BIT; 813b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if(value & COPYBIT_TRANSFORM_FLIP_V) { 814b166940edca6e312463461438e2aa66e9852c26aBenoit Goby config_mask |= C2D_MIRROR_V_BIT; 815b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 816b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 817b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 818b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->c2d_driver_info.capabilities_mask & 819b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_DRIVER_SUPPORTS_OVERRIDE_TARGET_ROTATE_OP) { 820b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->config_mask |= config_mask; 821b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 822b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // The transform for this surface does not match the current 823b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // target transform. Draw all previous surfaces. This will be 824b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // changed once we have a new mechanism to send different 825b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // target rotations to c2d. 826b166940edca6e312463461438e2aa66e9852c26aBenoit Goby finish_copybit(dev); 827b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 828b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->trg_transform = transform; 829b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 830b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 831b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_FRAMEBUFFER_WIDTH: 832b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->fb_width = value; 833b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 834b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_FRAMEBUFFER_HEIGHT: 835b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->fb_height = value; 836b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 837b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_ROTATION_DEG: 838b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_DITHER: 839b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_BLUR: 840b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_BLIT_TO_FRAMEBUFFER: 841b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Do nothing 842b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 843b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 844b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: default case param=0x%x", __FUNCTION__, name); 845b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = -EINVAL; 846b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 847b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 848b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 849b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 850b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 851b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 852b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** Get a static info value */ 853b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int get(struct copybit_device_t *dev, int name) 854b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 855b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 856b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int value; 857b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 858b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx) { 859b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: null context error", __FUNCTION__); 860b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 861b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 862b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 863b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(name) { 864b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_MINIFICATION_LIMIT: 865b166940edca6e312463461438e2aa66e9852c26aBenoit Goby value = MAX_SCALE_FACTOR; 866b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 867b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_MAGNIFICATION_LIMIT: 868b166940edca6e312463461438e2aa66e9852c26aBenoit Goby value = MAX_SCALE_FACTOR; 869b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 870b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_SCALING_FRAC_BITS: 871b166940edca6e312463461438e2aa66e9852c26aBenoit Goby value = 32; 872b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 873b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case COPYBIT_ROTATION_STEP_DEG: 874b166940edca6e312463461438e2aa66e9852c26aBenoit Goby value = 1; 875b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 876b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 877b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: default case param=0x%x", __FUNCTION__, name); 878b166940edca6e312463461438e2aa66e9852c26aBenoit Goby value = -EINVAL; 879b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 880b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return value; 881b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 882b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 883b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int is_alpha(int cformat) 884b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 885b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int alpha = 0; 886b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch (cformat & 0xFF) { 887b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_8888_ARGB: 888b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_8888_RGBA: 889b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_5551_RGBA: 890b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case C2D_COLOR_FORMAT_4444_ARGB: 891b166940edca6e312463461438e2aa66e9852c26aBenoit Goby alpha = 1; 892b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 893b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: 894b166940edca6e312463461438e2aa66e9852c26aBenoit Goby alpha = 0; 895b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 896b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 897b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 898b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(alpha && (cformat&C2D_FORMAT_DISABLE_ALPHA)) 899b166940edca6e312463461438e2aa66e9852c26aBenoit Goby alpha = 0; 900b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 901b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return alpha; 902b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 903b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 904b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Function to check if we need a temporary buffer for the blit. 905b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * This would happen if the requested destination stride and the 906b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * C2D stride do not match. We ignore RGB buffers, since their 907b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * stride is always aligned to 32. 908b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 909b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic bool need_temp_buffer(struct copybit_image_t const *img) 910b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 911b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (COPYBIT_SUCCESS == is_supported_rgb_format(img->format)) 912b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return false; 913b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 914b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct private_handle_t* handle = (struct private_handle_t*)img->handle; 915b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 916b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // The width parameter in the handle contains the aligned_w. We check if we 917b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // need to convert based on this param. YUV formats have bpp=1, so checking 918b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // if the requested stride is aligned should suffice. 919b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (0 == (handle->width)%32) { 920b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return false; 921b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 922b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 923b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return true; 924b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 925b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 926b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Function to extract the information from the copybit image and set the corresponding 927b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * values in the bufferInfo struct. 928b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 929b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void populate_buffer_info(struct copybit_image_t const *img, bufferInfo& info) 930b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 931b166940edca6e312463461438e2aa66e9852c26aBenoit Goby info.width = img->w; 932b166940edca6e312463461438e2aa66e9852c26aBenoit Goby info.height = img->h; 933b166940edca6e312463461438e2aa66e9852c26aBenoit Goby info.format = img->format; 934b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 935b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 936b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Function to get the required size for a particular format, inorder for C2D to perform 937b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * the blit operation. 938b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 939b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic size_t get_size(const bufferInfo& info) 940b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 941b166940edca6e312463461438e2aa66e9852c26aBenoit Goby size_t size = 0; 942b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int w = info.width; 943b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int h = info.height; 944b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int aligned_w = ALIGN(w, 32); 945b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(info.format) { 946b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: 947b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 948b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Chroma for this format is aligned to 2K. 949b166940edca6e312463461438e2aa66e9852c26aBenoit Goby size = ALIGN((aligned_w*h), 2048) + 950b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALIGN(aligned_w/2, 32) * (h/2) *2; 951b166940edca6e312463461438e2aa66e9852c26aBenoit Goby size = ALIGN(size, 4096); 952b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } break; 953b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: 954b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: 955b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 956b166940edca6e312463461438e2aa66e9852c26aBenoit Goby size = aligned_w * h + 957b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALIGN(aligned_w/2, 32) * (h/2) * 2; 958b166940edca6e312463461438e2aa66e9852c26aBenoit Goby size = ALIGN(size, 4096); 959b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } break; 960b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: break; 961b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 962b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return size; 963b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 964b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 965b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Function to allocate memory for the temporary buffer. This memory is 966b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * allocated from Ashmem. It is the caller's responsibility to free this 967b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * memory. 968b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 969b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int get_temp_buffer(const bufferInfo& info, alloc_data& data) 970b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 971b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGD("%s E", __FUNCTION__); 972b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Alloc memory from system heap 973b166940edca6e312463461438e2aa66e9852c26aBenoit Goby data.base = 0; 974b166940edca6e312463461438e2aa66e9852c26aBenoit Goby data.fd = -1; 975b166940edca6e312463461438e2aa66e9852c26aBenoit Goby data.offset = 0; 976b166940edca6e312463461438e2aa66e9852c26aBenoit Goby data.size = get_size(info); 977b166940edca6e312463461438e2aa66e9852c26aBenoit Goby data.align = getpagesize(); 978b166940edca6e312463461438e2aa66e9852c26aBenoit Goby data.uncached = true; 979b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int allocFlags = GRALLOC_USAGE_PRIVATE_SYSTEM_HEAP; 980b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 981b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (sAlloc == 0) { 982b166940edca6e312463461438e2aa66e9852c26aBenoit Goby sAlloc = gralloc::IAllocController::getInstance(); 983b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 984b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 985b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (sAlloc == 0) { 986b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: sAlloc is still NULL", __FUNCTION__); 987b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 988b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 989b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 990b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int err = sAlloc->allocate(data, allocFlags); 991b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (0 != err) { 992b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: allocate failed", __FUNCTION__); 993b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 994b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 995b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 996b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGD("%s X", __FUNCTION__); 997b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return err; 998b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 999b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1000b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Function to free the temporary allocated memory.*/ 1001b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void free_temp_buffer(alloc_data &data) 1002b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1003b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (-1 != data.fd) { 1004b166940edca6e312463461438e2aa66e9852c26aBenoit Goby IMemAlloc* memalloc = sAlloc->getAllocator(data.allocType); 1005b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memalloc->free_buffer(data.base, data.size, 0, data.fd); 1006b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1007b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1008b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1009b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/* Function to perform the software color conversion. Convert the 1010b166940edca6e312463461438e2aa66e9852c26aBenoit Goby * C2D compatible format to the Android compatible format 1011b166940edca6e312463461438e2aa66e9852c26aBenoit Goby */ 1012b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int copy_image(private_handle_t *src_handle, 1013b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *rhs, 1014b166940edca6e312463461438e2aa66e9852c26aBenoit Goby eConversionType conversionType) 1015b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1016b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (src_handle->fd == -1) { 1017b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: src_handle fd is invalid", __FUNCTION__); 1018b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1019b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1020b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1021b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Copy the info. 1022b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int ret = COPYBIT_SUCCESS; 1023b166940edca6e312463461438e2aa66e9852c26aBenoit Goby switch(rhs->format) { 1024b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_NV12_ENCODEABLE: 1025b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCbCr_420_SP: 1026b166940edca6e312463461438e2aa66e9852c26aBenoit Goby case HAL_PIXEL_FORMAT_YCrCb_420_SP: 1027b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 1028b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (CONVERT_TO_ANDROID_FORMAT == conversionType) { 1029b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return convert_yuv_c2d_to_yuv_android(src_handle, rhs); 1030b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1031b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return convert_yuv_android_to_yuv_c2d(src_handle, rhs); 1032b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1033b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1034b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } break; 1035b166940edca6e312463461438e2aa66e9852c26aBenoit Goby default: { 1036b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: invalid format 0x%x", __FUNCTION__, rhs->format); 1037b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ret = COPYBIT_FAILURE; 1038b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } break; 1039b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1040b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return ret; 1041b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1042b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1043b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void delete_handle(private_handle_t *handle) 1044b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1045b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (handle) { 1046b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete handle; 1047b166940edca6e312463461438e2aa66e9852c26aBenoit Goby handle = 0; 1048b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1049b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1050b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1051b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic bool need_to_execute_draw(struct copybit_context_t* ctx, 1052b166940edca6e312463461438e2aa66e9852c26aBenoit Goby eC2DFlags flags) 1053b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1054b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (flags & FLAGS_TEMP_SRC_DST) { 1055b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return true; 1056b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1057b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (flags & FLAGS_YUV_DESTINATION) { 1058b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return true; 1059b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1060b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return false; 1061b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1062b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1063b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** do a stretch blit type operation */ 1064b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int stretch_copybit_internal( 1065b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_device_t *dev, 1066b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *dst, 1067b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *src, 1068b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t const *dst_rect, 1069b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t const *src_rect, 1070b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_region_t const *region, 1071b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool enableBlend) 1072b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1073b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 1074b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_SUCCESS; 1075b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int flags = 0; 1076b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int src_surface_type; 1077b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int mapped_src_idx = -1, mapped_dst_idx = -1; 1078b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_OBJECT_STR src_surface; 1079b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1080b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx) { 1081b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: null context error", __FUNCTION__); 1082b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 1083b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1084b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1085b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (src->w > MAX_DIMENSION || src->h > MAX_DIMENSION) { 1086b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: src dimension error", __FUNCTION__); 1087b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 1088b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1089b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1090b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (dst->w > MAX_DIMENSION || dst->h > MAX_DIMENSION) { 1091b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s : dst dimension error dst w %d h %d", __FUNCTION__, dst->w, 1092b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst->h); 1093b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 1094b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1095b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1096b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (is_valid_destination_format(dst->format) == COPYBIT_FAILURE) { 1097b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: Invalid destination format format = 0x%x", __FUNCTION__, 1098b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst->format); 1099b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1100b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1101b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1102b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int dst_surface_type; 1103b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (is_supported_rgb_format(dst->format) == COPYBIT_SUCCESS) { 1104b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_surface_type = RGB_SURFACE; 1105b166940edca6e312463461438e2aa66e9852c26aBenoit Goby flags |= FLAGS_PREMULTIPLIED_ALPHA; 1106b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (is_supported_yuv_format(dst->format) == COPYBIT_SUCCESS) { 1107b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int num_planes = get_num_planes(dst->format); 1108b166940edca6e312463461438e2aa66e9852c26aBenoit Goby flags |= FLAGS_YUV_DESTINATION; 1109b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (num_planes == 2) { 1110b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_surface_type = YUV_SURFACE_2_PLANES; 1111b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (num_planes == 3) { 1112b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_surface_type = YUV_SURFACE_3_PLANES; 1113b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1114b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: dst number of YUV planes is invalid dst format = 0x%x", 1115b166940edca6e312463461438e2aa66e9852c26aBenoit Goby __FUNCTION__, dst->format); 1116b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1117b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1118b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1119b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: Invalid dst surface format 0x%x", __FUNCTION__, 1120b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst->format); 1121b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1122b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1123b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1124b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->blit_rgb_count == MAX_RGB_SURFACES || 1125b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_count == MAX_YUV_2_PLANE_SURFACES || 1126b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_count == MAX_YUV_2_PLANE_SURFACES || 1127b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_count == MAX_BLIT_OBJECT_COUNT || 1128b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->dst_surface_type != dst_surface_type) { 1129b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // we have reached the max. limits of our internal structures or 1130b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // changed the target. 1131b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Draw the remaining surfaces. We need to do the finish here since 1132b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // we need to free up the surface templates. 1133b166940edca6e312463461438e2aa66e9852c26aBenoit Goby finish_copybit(dev); 1134b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1135b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1136b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->dst_surface_type = dst_surface_type; 1137b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1138b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Update the destination 1139b166940edca6e312463461438e2aa66e9852c26aBenoit Goby copybit_image_t dst_image; 1140b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_image.w = dst->w; 1141b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_image.h = dst->h; 1142b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_image.format = dst->format; 1143b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_image.handle = dst->handle; 1144b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Check if we need a temp. copy for the destination. We'd need this the destination 1145b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // width is not aligned to 32. This case occurs for YUV formats. RGB formats are 1146b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // aligned to 32. 1147b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool need_temp_dst = need_temp_buffer(dst); 1148b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bufferInfo dst_info; 1149b166940edca6e312463461438e2aa66e9852c26aBenoit Goby populate_buffer_info(dst, dst_info); 1150b166940edca6e312463461438e2aa66e9852c26aBenoit Goby private_handle_t* dst_hnd = new private_handle_t(-1, 0, 0, 0, dst_info.format, 1151b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_info.width, dst_info.height); 1152b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (dst_hnd == NULL) { 1153b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: dst_hnd is null", __FUNCTION__); 1154b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1155b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1156b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (need_temp_dst) { 1157b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (get_size(dst_info) != ctx->temp_dst_buffer.size) { 1158b166940edca6e312463461438e2aa66e9852c26aBenoit Goby free_temp_buffer(ctx->temp_dst_buffer); 1159b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Create a temp buffer and set that as the destination. 1160b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (COPYBIT_FAILURE == get_temp_buffer(dst_info, ctx->temp_dst_buffer)) { 1161b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: get_temp_buffer(dst) failed", __FUNCTION__); 1162b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1163b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1164b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1165b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1166b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->fd = ctx->temp_dst_buffer.fd; 1167b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->size = ctx->temp_dst_buffer.size; 1168b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->flags = ctx->temp_dst_buffer.allocType; 1169b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->base = (int)(ctx->temp_dst_buffer.base); 1170b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->offset = ctx->temp_dst_buffer.offset; 1171b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->gpuaddr = 0; 1172b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_image.handle = dst_hnd; 1173b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1174b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1175b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = set_image(ctx, ctx->dst[ctx->dst_surface_type], &dst_image, 1176b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (eC2DFlags)flags, mapped_dst_idx); 1177b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(status) { 1178b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: dst: set_image error", __FUNCTION__); 1179b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1180b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1181b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1182b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1183b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1184b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Update the source 1185b166940edca6e312463461438e2aa66e9852c26aBenoit Goby flags = 0; 1186b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(is_supported_rgb_format(src->format) == COPYBIT_SUCCESS) { 1187b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface_type = RGB_SURFACE; 1188b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface = ctx->blit_rgb_object[ctx->blit_rgb_count]; 1189b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (is_supported_yuv_format(src->format) == COPYBIT_SUCCESS) { 1190b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int num_planes = get_num_planes(src->format); 1191b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (num_planes == 2) { 1192b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface_type = YUV_SURFACE_2_PLANES; 1193b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface = ctx->blit_yuv_2_plane_object[ctx->blit_yuv_2_plane_count]; 1194b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (num_planes == 3) { 1195b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface_type = YUV_SURFACE_3_PLANES; 1196b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface = ctx->blit_yuv_3_plane_object[ctx->blit_yuv_2_plane_count]; 1197b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1198b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: src number of YUV planes is invalid src format = 0x%x", 1199b166940edca6e312463461438e2aa66e9852c26aBenoit Goby __FUNCTION__, src->format); 1200b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1201b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1202b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 1203b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1204b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1205b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: Invalid source surface format 0x%x", __FUNCTION__, 1206b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src->format); 1207b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1208b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1209b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return -EINVAL; 1210b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1211b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1212b166940edca6e312463461438e2aa66e9852c26aBenoit Goby copybit_image_t src_image; 1213b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_image.w = src->w; 1214b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_image.h = src->h; 1215b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_image.format = src->format; 1216b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_image.handle = src->handle; 1217b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1218b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool need_temp_src = need_temp_buffer(src); 1219b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bufferInfo src_info; 1220b166940edca6e312463461438e2aa66e9852c26aBenoit Goby populate_buffer_info(src, src_info); 1221b166940edca6e312463461438e2aa66e9852c26aBenoit Goby private_handle_t* src_hnd = new private_handle_t(-1, 0, 0, 0, src_info.format, 1222b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_info.width, src_info.height); 1223b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (NULL == src_hnd) { 1224b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: src_hnd is null", __FUNCTION__); 1225b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1226b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1227b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1228b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1229b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (need_temp_src) { 1230b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (get_size(src_info) != ctx->temp_src_buffer.size) { 1231b166940edca6e312463461438e2aa66e9852c26aBenoit Goby free_temp_buffer(ctx->temp_src_buffer); 1232b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Create a temp buffer and set that as the destination. 1233b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (COPYBIT_SUCCESS != get_temp_buffer(src_info, 1234b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_src_buffer)) { 1235b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: get_temp_buffer(src) failed", __FUNCTION__); 1236b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1237b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1238b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1239b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1240b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1241b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1242b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->fd = ctx->temp_src_buffer.fd; 1243b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->size = ctx->temp_src_buffer.size; 1244b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->flags = ctx->temp_src_buffer.allocType; 1245b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->base = (int)(ctx->temp_src_buffer.base); 1246b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->offset = ctx->temp_src_buffer.offset; 1247b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->gpuaddr = 0; 1248b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_image.handle = src_hnd; 1249b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1250b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Copy the source. 1251b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = copy_image((private_handle_t *)src->handle, &src_image, 1252b166940edca6e312463461438e2aa66e9852c26aBenoit Goby CONVERT_TO_C2D_FORMAT); 1253b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (status == COPYBIT_FAILURE) { 1254b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s:copy_image failed in temp source",__FUNCTION__); 1255b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1256b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1257b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1258b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1259b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1260b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1261b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Clean the cache 1262b166940edca6e312463461438e2aa66e9852c26aBenoit Goby IMemAlloc* memalloc = sAlloc->getAllocator(src_hnd->flags); 1263b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (memalloc->clean_buffer((void *)(src_hnd->base), src_hnd->size, 1264b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_hnd->offset, src_hnd->fd, 1265b166940edca6e312463461438e2aa66e9852c26aBenoit Goby gralloc::CACHE_CLEAN)) { 1266b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: clean_buffer failed", __FUNCTION__); 1267b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1268b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1269b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1270b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1271b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1272b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1273b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1274b166940edca6e312463461438e2aa66e9852c26aBenoit Goby flags |= (ctx->is_premultiplied_alpha) ? FLAGS_PREMULTIPLIED_ALPHA : 0; 1275b166940edca6e312463461438e2aa66e9852c26aBenoit Goby flags |= (ctx->dst_surface_type != RGB_SURFACE) ? FLAGS_YUV_DESTINATION : 0; 1276b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = set_image(ctx, src_surface.surface_id, &src_image, 1277b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (eC2DFlags)flags, mapped_src_idx); 1278b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(status) { 1279b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: set_image (src) error", __FUNCTION__); 1280b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1281b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1282b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1283b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_src_idx); 1284b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1285b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1286b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1287b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface.config_mask = C2D_NO_ANTIALIASING_BIT | ctx->config_mask; 1288b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface.global_alpha = ctx->src_global_alpha; 1289b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (enableBlend) { 1290b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(src_surface.config_mask & C2D_GLOBAL_ALPHA_BIT) { 1291b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface.config_mask &= ~C2D_ALPHA_BLEND_NONE; 1292b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(!(src_surface.global_alpha)) { 1293b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // src alpha is zero 1294b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1295b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1296b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1297b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_src_idx); 1298b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1299b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1300b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1301b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1302b166940edca6e312463461438e2aa66e9852c26aBenoit Goby src_surface.config_mask |= C2D_ALPHA_BLEND_NONE; 1303b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1304b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1305b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (src_surface_type == RGB_SURFACE) { 1306b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_object[ctx->blit_rgb_count] = src_surface; 1307b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_count++; 1308b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else if (src_surface_type == YUV_SURFACE_2_PLANES) { 1309b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_object[ctx->blit_yuv_2_plane_count] = src_surface; 1310b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_count++; 1311b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1312b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_object[ctx->blit_yuv_3_plane_count] = src_surface; 1313b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_count++; 1314b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1315b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1316b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t clip; 1317b166940edca6e312463461438e2aa66e9852c26aBenoit Goby while ((status == 0) && region->next(region, &clip)) { 1318b166940edca6e312463461438e2aa66e9852c26aBenoit Goby set_rects(ctx, &(src_surface), dst_rect, src_rect, &clip); 1319b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->blit_count == MAX_BLIT_OBJECT_COUNT) { 1320b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGW("Reached end of blit count"); 1321b166940edca6e312463461438e2aa66e9852c26aBenoit Goby finish_copybit(dev); 1322b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1323b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_list[ctx->blit_count] = src_surface; 1324b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_count++; 1325b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1326b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1327b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Check if we need to perform an early draw-finish. 1328b166940edca6e312463461438e2aa66e9852c26aBenoit Goby flags |= (need_temp_dst || need_temp_src) ? FLAGS_TEMP_SRC_DST : 0; 1329b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (need_to_execute_draw(ctx, (eC2DFlags)flags)) 1330b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 1331b166940edca6e312463461438e2aa66e9852c26aBenoit Goby finish_copybit(dev); 1332b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1333b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1334b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (need_temp_dst) { 1335b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // copy the temp. destination without the alignment to the actual 1336b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // destination. 1337b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = copy_image(dst_hnd, dst, CONVERT_TO_ANDROID_FORMAT); 1338b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (status == COPYBIT_FAILURE) { 1339b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s:copy_image failed in temp Dest",__FUNCTION__); 1340b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1341b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1342b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_dst_idx); 1343b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unmap_gpuaddr(ctx, mapped_src_idx); 1344b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1345b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1346b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Clean the cache. 1347b166940edca6e312463461438e2aa66e9852c26aBenoit Goby IMemAlloc* memalloc = sAlloc->getAllocator(dst_hnd->flags); 1348b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memalloc->clean_buffer((void *)(dst_hnd->base), dst_hnd->size, 1349b166940edca6e312463461438e2aa66e9852c26aBenoit Goby dst_hnd->offset, dst_hnd->fd, 1350b166940edca6e312463461438e2aa66e9852c26aBenoit Goby gralloc::CACHE_CLEAN); 1351b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1352b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(dst_hnd); 1353b166940edca6e312463461438e2aa66e9852c26aBenoit Goby delete_handle(src_hnd); 1354b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1355b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->is_premultiplied_alpha = false; 1356b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->fb_width = 0; 1357b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->fb_height = 0; 1358b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->config_mask = 0; 1359b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1360b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1361b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1362b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1363b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int stretch_copybit( 1364b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_device_t *dev, 1365b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *dst, 1366b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *src, 1367b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t const *dst_rect, 1368b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t const *src_rect, 1369b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_region_t const *region) 1370b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1371b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 1372b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_SUCCESS; 1373b166940edca6e312463461438e2aa66e9852c26aBenoit Goby bool needsBlending = (ctx->src_global_alpha != 0); 1374b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 1375b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = stretch_copybit_internal(dev, dst, src, dst_rect, src_rect, 1376b166940edca6e312463461438e2aa66e9852c26aBenoit Goby region, needsBlending); 1377b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 1378b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1379b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1380b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1381b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** Perform a blit type operation */ 1382b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int blit_copybit( 1383b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_device_t *dev, 1384b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *dst, 1385b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_image_t const *src, 1386b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_region_t const *region) 1387b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1388b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_SUCCESS; 1389b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 1390b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t dr = { 0, 0, dst->w, dst->h }; 1391b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_rect_t sr = { 0, 0, src->w, src->h }; 1392b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 1393b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = stretch_copybit_internal(dev, dst, src, &dr, &sr, region, false); 1394b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 1395b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1396b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1397b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1398b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/*****************************************************************************/ 1399b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1400b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic void clean_up(copybit_context_t* ctx) 1401b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1402b166940edca6e312463461438e2aa66e9852c26aBenoit Goby void* ret; 1403b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx) 1404b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return; 1405b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1406b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // stop the wait_cleanup_thread 1407b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_lock(&ctx->wait_cleanup_lock); 1408b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->stop_thread = true; 1409b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Signal waiting thread 1410b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_cond_signal(&ctx->wait_cleanup_cond); 1411b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_unlock(&ctx->wait_cleanup_lock); 1412b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // waits for the cleanup thread to exit 1413b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_join(ctx->wait_thread_id, &ret); 1414b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_destroy(&ctx->wait_cleanup_lock); 1415b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_cond_destroy (&ctx->wait_cleanup_cond); 1416b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1417b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < NUM_SURFACE_TYPES; i++) { 1418b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->dst[i]) 1419b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dDestroySurface(ctx->dst[i]); 1420b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1421b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1422b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_RGB_SURFACES; i++) { 1423b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->blit_rgb_object[i].surface_id) 1424b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dDestroySurface(ctx->blit_rgb_object[i].surface_id); 1425b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1426b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1427b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_YUV_2_PLANE_SURFACES; i++) { 1428b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->blit_yuv_2_plane_object[i].surface_id) 1429b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dDestroySurface(ctx->blit_yuv_2_plane_object[i].surface_id); 1430b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1431b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1432b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_YUV_3_PLANE_SURFACES; i++) { 1433b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->blit_yuv_3_plane_object[i].surface_id) 1434b166940edca6e312463461438e2aa66e9852c26aBenoit Goby LINK_c2dDestroySurface(ctx->blit_yuv_3_plane_object[i].surface_id); 1435b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1436b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1437b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx->libc2d2) { 1438b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ::dlclose(ctx->libc2d2); 1439b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGV("dlclose(libc2d2)"); 1440b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1441b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1442b166940edca6e312463461438e2aa66e9852c26aBenoit Goby free(ctx); 1443b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1444b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1445b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** Close the copybit device */ 1446b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int close_copybit(struct hw_device_t *dev) 1447b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1448b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 1449b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (ctx) { 1450b166940edca6e312463461438e2aa66e9852c26aBenoit Goby free_temp_buffer(ctx->temp_src_buffer); 1451b166940edca6e312463461438e2aa66e9852c26aBenoit Goby free_temp_buffer(ctx->temp_dst_buffer); 1452b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1453b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1454b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return 0; 1455b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1456b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1457b166940edca6e312463461438e2aa66e9852c26aBenoit Goby/** Open a new instance of a copybit device using name */ 1458b166940edca6e312463461438e2aa66e9852c26aBenoit Gobystatic int open_copybit(const struct hw_module_t* module, const char* name, 1459b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct hw_device_t** device) 1460b166940edca6e312463461438e2aa66e9852c26aBenoit Goby{ 1461b166940edca6e312463461438e2aa66e9852c26aBenoit Goby int status = COPYBIT_SUCCESS; 1462b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_RGB_SURFACE_DEF surfDefinition = {0}; 1463b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_YUV_SURFACE_DEF yuvSurfaceDef = {0} ; 1464b166940edca6e312463461438e2aa66e9852c26aBenoit Goby struct copybit_context_t *ctx; 1465b166940edca6e312463461438e2aa66e9852c26aBenoit Goby char fbName[64]; 1466b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1467b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx = (struct copybit_context_t *)malloc(sizeof(struct copybit_context_t)); 1468b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if(!ctx) { 1469b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: malloc failed", __FUNCTION__); 1470b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return COPYBIT_FAILURE; 1471b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1472b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1473b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* initialize drawstate */ 1474b166940edca6e312463461438e2aa66e9852c26aBenoit Goby memset(ctx, 0, sizeof(*ctx)); 1475b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->libc2d2 = ::dlopen("libC2D2.so", RTLD_NOW); 1476b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!ctx->libc2d2) { 1477b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("FATAL ERROR: could not dlopen libc2d2.so: %s", dlerror()); 1478b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1479b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1480b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1481b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1482b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1483b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dCreateSurface = ::dlsym(ctx->libc2d2, 1484b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dCreateSurface"); 1485b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dUpdateSurface = ::dlsym(ctx->libc2d2, 1486b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dUpdateSurface"); 1487b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dReadSurface = ::dlsym(ctx->libc2d2, 1488b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dReadSurface"); 1489b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dDraw = ::dlsym(ctx->libc2d2, "c2dDraw"); 1490b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dFlush = ::dlsym(ctx->libc2d2, "c2dFlush"); 1491b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dFinish = ::dlsym(ctx->libc2d2, "c2dFinish"); 1492b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dWaitTimestamp = ::dlsym(ctx->libc2d2, 1493b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dWaitTimestamp"); 1494b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dDestroySurface = ::dlsym(ctx->libc2d2, 1495b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dDestroySurface"); 1496b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dMapAddr = ::dlsym(ctx->libc2d2, 1497b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dMapAddr"); 1498b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dUnMapAddr = ::dlsym(ctx->libc2d2, 1499b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dUnMapAddr"); 1500b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dGetDriverCapabilities = ::dlsym(ctx->libc2d2, 1501b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dGetDriverCapabilities"); 1502b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dCreateFenceFD = ::dlsym(ctx->libc2d2, 1503b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dCreateFenceFD"); 1504b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *(void **)&LINK_c2dFillSurface = ::dlsym(ctx->libc2d2, 1505b166940edca6e312463461438e2aa66e9852c26aBenoit Goby "c2dFillSurface"); 1506b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1507b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (!LINK_c2dCreateSurface || !LINK_c2dUpdateSurface || !LINK_c2dReadSurface 1508b166940edca6e312463461438e2aa66e9852c26aBenoit Goby || !LINK_c2dDraw || !LINK_c2dFlush || !LINK_c2dWaitTimestamp || 1509b166940edca6e312463461438e2aa66e9852c26aBenoit Goby !LINK_c2dFinish || !LINK_c2dDestroySurface || 1510b166940edca6e312463461438e2aa66e9852c26aBenoit Goby !LINK_c2dGetDriverCapabilities || !LINK_c2dCreateFenceFD || 1511b166940edca6e312463461438e2aa66e9852c26aBenoit Goby !LINK_c2dFillSurface) { 1512b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: dlsym ERROR", __FUNCTION__); 1513b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1514b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1515b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1516b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1517b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1518b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1519b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.common.tag = HARDWARE_DEVICE_TAG; 1520b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.common.version = 1; 1521b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.common.module = (hw_module_t*)(module); 1522b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.common.close = close_copybit; 1523b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.set_parameter = set_parameter_copybit; 1524b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.get = get; 1525b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.blit = blit_copybit; 1526b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.stretch = stretch_copybit; 1527b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.finish = finish_copybit; 1528b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.flush_get_fence = flush_get_fence_copybit; 1529b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->device.clear = clear_copybit; 1530b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1531b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* Create RGB Surface */ 1532b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfDefinition.buffer = (void*)0xdddddddd; 1533b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfDefinition.phys = (void*)0xdddddddd; 1534b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfDefinition.stride = 1 * 4; 1535b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfDefinition.width = 1; 1536b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfDefinition.height = 1; 1537b166940edca6e312463461438e2aa66e9852c26aBenoit Goby surfDefinition.format = C2D_COLOR_FORMAT_8888_ARGB; 1538b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dCreateSurface(&(ctx->dst[RGB_SURFACE]), C2D_TARGET | C2D_SOURCE, 1539b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (C2D_SURFACE_TYPE)(C2D_SURFACE_RGB_HOST | 1540b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS | 1541b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS_DUMMY ), 1542b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &surfDefinition)) { 1543b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: create ctx->dst_surface[RGB_SURFACE] failed", __FUNCTION__); 1544b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->dst[RGB_SURFACE] = 0; 1545b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1546b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1547b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1548b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1549b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1550b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1551b166940edca6e312463461438e2aa66e9852c26aBenoit Goby unsigned int surface_id = 0; 1552b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i = 0; i < MAX_RGB_SURFACES; i++) 1553b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 1554b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dCreateSurface(&surface_id, C2D_TARGET | C2D_SOURCE, 1555b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (C2D_SURFACE_TYPE)(C2D_SURFACE_RGB_HOST | 1556b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS | 1557b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS_DUMMY ), 1558b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &surfDefinition)) { 1559b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: create RGB source surface %d failed", __FUNCTION__, i); 1560b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_object[i].surface_id = 0; 1561b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1562b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 1563b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1564b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_object[i].surface_id = surface_id; 1565b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGW("%s i = %d surface_id=%d", __FUNCTION__, i, 1566b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_object[i].surface_id); 1567b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1568b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1569b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1570b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (status == COPYBIT_FAILURE) { 1571b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1572b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1573b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1574b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1575b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1576b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1577b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Create 2 plane YUV surfaces 1578b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.format = C2D_COLOR_FORMAT_420_NV12; 1579b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.width = 4; 1580b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.height = 4; 1581b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.plane0 = (void*)0xaaaaaaaa; 1582b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.phys0 = (void*) 0xaaaaaaaa; 1583b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.stride0 = 4; 1584b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1585b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.plane1 = (void*)0xaaaaaaaa; 1586b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.phys1 = (void*) 0xaaaaaaaa; 1587b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.stride1 = 4; 1588b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dCreateSurface(&(ctx->dst[YUV_SURFACE_2_PLANES]), 1589b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_TARGET | C2D_SOURCE, 1590b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (C2D_SURFACE_TYPE)(C2D_SURFACE_YUV_HOST | 1591b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS | 1592b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS_DUMMY), 1593b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &yuvSurfaceDef)) { 1594b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: create ctx->dst[YUV_SURFACE_2_PLANES] failed", __FUNCTION__); 1595b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->dst[YUV_SURFACE_2_PLANES] = 0; 1596b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1597b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1598b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1599b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1600b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1601b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1602b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i=0; i < MAX_YUV_2_PLANE_SURFACES; i++) 1603b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 1604b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dCreateSurface(&surface_id, C2D_TARGET | C2D_SOURCE, 1605b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (C2D_SURFACE_TYPE)(C2D_SURFACE_YUV_HOST | 1606b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS | 1607b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS_DUMMY ), 1608b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &yuvSurfaceDef)) { 1609b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: create YUV source %d failed", __FUNCTION__, i); 1610b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_object[i].surface_id = 0; 1611b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1612b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 1613b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1614b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_object[i].surface_id = surface_id; 1615b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGW("%s: 2 Plane YUV i=%d surface_id=%d", __FUNCTION__, i, 1616b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_object[i].surface_id); 1617b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1618b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1619b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1620b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (status == COPYBIT_FAILURE) { 1621b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1622b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1623b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1624b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1625b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1626b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1627b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Create YUV 3 plane surfaces 1628b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.format = C2D_COLOR_FORMAT_420_YV12; 1629b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.plane2 = (void*)0xaaaaaaaa; 1630b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.phys2 = (void*) 0xaaaaaaaa; 1631b166940edca6e312463461438e2aa66e9852c26aBenoit Goby yuvSurfaceDef.stride2 = 4; 1632b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1633b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dCreateSurface(&(ctx->dst[YUV_SURFACE_3_PLANES]), 1634b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_TARGET | C2D_SOURCE, 1635b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (C2D_SURFACE_TYPE)(C2D_SURFACE_YUV_HOST | 1636b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS | 1637b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS_DUMMY), 1638b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &yuvSurfaceDef)) { 1639b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: create ctx->dst[YUV_SURFACE_3_PLANES] failed", __FUNCTION__); 1640b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->dst[YUV_SURFACE_3_PLANES] = 0; 1641b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1642b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1643b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1644b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1645b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1646b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1647b166940edca6e312463461438e2aa66e9852c26aBenoit Goby for (int i=0; i < MAX_YUV_3_PLANE_SURFACES; i++) 1648b166940edca6e312463461438e2aa66e9852c26aBenoit Goby { 1649b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dCreateSurface(&(surface_id), 1650b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_TARGET | C2D_SOURCE, 1651b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (C2D_SURFACE_TYPE)(C2D_SURFACE_YUV_HOST | 1652b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS | 1653b166940edca6e312463461438e2aa66e9852c26aBenoit Goby C2D_SURFACE_WITH_PHYS_DUMMY), 1654b166940edca6e312463461438e2aa66e9852c26aBenoit Goby &yuvSurfaceDef)) { 1655b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: create 3 plane YUV surface %d failed", __FUNCTION__, i); 1656b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_object[i].surface_id = 0; 1657b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1658b166940edca6e312463461438e2aa66e9852c26aBenoit Goby break; 1659b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } else { 1660b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_object[i].surface_id = surface_id; 1661b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGW("%s: 3 Plane YUV i=%d surface_id=%d", __FUNCTION__, i, 1662b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_object[i].surface_id); 1663b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1664b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1665b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1666b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (status == COPYBIT_FAILURE) { 1667b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1668b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1669b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1670b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1671b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1672b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1673b166940edca6e312463461438e2aa66e9852c26aBenoit Goby if (LINK_c2dGetDriverCapabilities(&(ctx->c2d_driver_info))) { 1674b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ALOGE("%s: LINK_c2dGetDriverCapabilities failed", __FUNCTION__); 1675b166940edca6e312463461438e2aa66e9852c26aBenoit Goby clean_up(ctx); 1676b166940edca6e312463461438e2aa66e9852c26aBenoit Goby status = COPYBIT_FAILURE; 1677b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = NULL; 1678b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1679b166940edca6e312463461438e2aa66e9852c26aBenoit Goby } 1680b166940edca6e312463461438e2aa66e9852c26aBenoit Goby // Initialize context variables. 1681b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->trg_transform = C2D_TARGET_ROTATE_0; 1682b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1683b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_src_buffer.fd = -1; 1684b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_src_buffer.base = 0; 1685b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_src_buffer.size = 0; 1686b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1687b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_dst_buffer.fd = -1; 1688b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_dst_buffer.base = 0; 1689b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->temp_dst_buffer.size = 0; 1690b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1691b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->fb_width = 0; 1692b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->fb_height = 0; 1693b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1694b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_rgb_count = 0; 1695b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_2_plane_count = 0; 1696b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_yuv_3_plane_count = 0; 1697b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->blit_count = 0; 1698b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1699b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->wait_timestamp = false; 1700b166940edca6e312463461438e2aa66e9852c26aBenoit Goby ctx->stop_thread = false; 1701b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_mutex_init(&(ctx->wait_cleanup_lock), NULL); 1702b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_cond_init(&(ctx->wait_cleanup_cond), NULL); 1703b166940edca6e312463461438e2aa66e9852c26aBenoit Goby /* Start the wait thread */ 1704b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_attr_t attr; 1705b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_attr_init(&attr); 1706b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE); 1707b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1708b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_create(&ctx->wait_thread_id, &attr, &c2d_wait_loop, 1709b166940edca6e312463461438e2aa66e9852c26aBenoit Goby (void *)ctx); 1710b166940edca6e312463461438e2aa66e9852c26aBenoit Goby pthread_attr_destroy(&attr); 1711b166940edca6e312463461438e2aa66e9852c26aBenoit Goby 1712b166940edca6e312463461438e2aa66e9852c26aBenoit Goby *device = &ctx->device.common; 1713b166940edca6e312463461438e2aa66e9852c26aBenoit Goby return status; 1714b166940edca6e312463461438e2aa66e9852c26aBenoit Goby} 1715