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