17510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/* 27510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * Copyright (C) 2008 The Android Open Source Project 37510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * 47510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 57510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * you may not use this file except in compliance with the License. 67510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * You may obtain a copy of the License at 77510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * 87510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 97510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * 107510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 117510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 127510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 137510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * See the License for the specific language governing permissions and 147510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * limitations under the License. 157510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project */ 167510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 177510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 187510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#define LOG_TAG "copybit" 197510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 207510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <cutils/log.h> 217510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 227510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <linux/msm_mdp.h> 237510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <linux/fb.h> 247510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 257510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <stdint.h> 267510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <string.h> 277510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <unistd.h> 287510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <errno.h> 297510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <fcntl.h> 307510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 317510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <sys/ioctl.h> 327510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <sys/types.h> 337510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <sys/mman.h> 347510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 357510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project#include <hardware/copybit.h> 367510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 37bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian#include "gralloc_priv.h" 38bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian 39b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian#define DEBUG_MDP_ERRORS 1 4087ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian 417510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/******************************************************************************/ 427510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 433f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian#if defined(COPYBIT_MSM7K) 443f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian#define MAX_SCALE_FACTOR (4) 4542e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian#define MAX_DIMENSION (4096) 46c9410082453abfb6eaaf43e6c97e04711d0751c0Dima Zavin#elif defined(COPYBIT_QSD8K) 473f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian#define MAX_SCALE_FACTOR (8) 4842e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian#define MAX_DIMENSION (2048) 493f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian#else 503f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian#error "Unsupported MDP version" 513f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian#endif 523f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian 533f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian/******************************************************************************/ 543f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian 557510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** State information for each device instance */ 567510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstruct copybit_context_t { 577510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_device_t device; 587510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int mFD; 597510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project uint8_t mAlpha; 607510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project uint8_t mFlags; 617510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project}; 627510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 637510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** 647510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * Common hardware methods 657510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project */ 667510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 677510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int open_copybit(const struct hw_module_t* module, const char* name, 687510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct hw_device_t** device); 697510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 707510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic struct hw_module_methods_t copybit_module_methods = { 71bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian open: open_copybit 727510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project}; 737510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 747510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/* 757510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project * The COPYBIT Module 767510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project */ 77bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopianstruct copybit_module_t HAL_MODULE_INFO_SYM = { 78bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian common: { 79bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian tag: HARDWARE_MODULE_TAG, 80bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian version_major: 1, 81bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian version_minor: 0, 82bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian id: COPYBIT_HARDWARE_MODULE_ID, 83bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian name: "QCT MSM7K COPYBIT Module", 84bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian author: "Google, Inc.", 85bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian methods: ©bit_module_methods 867510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 877510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project}; 887510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 897510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/******************************************************************************/ 907510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 917510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** min of int a, b */ 927510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic inline int min(int a, int b) { 937510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return (a<b) ? a : b; 947510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 957510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 967510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** max of int a, b */ 977510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic inline int max(int a, int b) { 987510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return (a>b) ? a : b; 997510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 1007510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1017510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** scale each parameter by mul/div. Assume div isn't 0 */ 1027510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic inline void MULDIV(uint32_t *a, uint32_t *b, int mul, int div) { 1037510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (mul != div) { 1047510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project *a = (mul * *a) / div; 1057510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project *b = (mul * *b) / div; 1067510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 1077510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 1087510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1097510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** Determine the intersection of lhs & rhs store in out */ 1107510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic void intersect(struct copybit_rect_t *out, 1117510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const struct copybit_rect_t *lhs, 1127510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const struct copybit_rect_t *rhs) { 1137510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project out->l = max(lhs->l, rhs->l); 1147510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project out->t = max(lhs->t, rhs->t); 1157510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project out->r = min(lhs->r, rhs->r); 1167510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project out->b = min(lhs->b, rhs->b); 1177510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 1187510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1197510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** convert COPYBIT_FORMAT to MDP format */ 1207510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int get_format(int format) { 1217510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project switch (format) { 1221900dda992fc9102ff4cb241137340c7cb89d62dMathias Agopian case COPYBIT_FORMAT_RGB_565: return MDP_RGB_565; 123dae6f22eb3b062aee703886796645fa480c714aaMathias Agopian case COPYBIT_FORMAT_RGBX_8888: return MDP_RGBX_8888; 1241900dda992fc9102ff4cb241137340c7cb89d62dMathias Agopian case COPYBIT_FORMAT_RGB_888: return MDP_RGB_888; 1257510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_FORMAT_RGBA_8888: return MDP_RGBA_8888; 1267510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_FORMAT_BGRA_8888: return MDP_BGRA_8888; 12766a2ed90dca705fc92c07e05242cf546b98d0eb7Mathias Agopian case COPYBIT_FORMAT_YCrCb_420_SP: return MDP_Y_CBCR_H2V2; 128399a0f191ea47ce17a06ee70097d3ee755689082Mathias Agopian case COPYBIT_FORMAT_YCbCr_422_SP: return MDP_Y_CRCB_H2V1; 1297510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 1307510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return -1; 1317510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 1327510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1337510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** convert from copybit image to mdp image structure */ 134bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopianstatic void set_image(struct mdp_img *img, const struct copybit_image_t *rhs) 135bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian{ 136bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian private_handle_t* hnd = (private_handle_t*)rhs->handle; 1377510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project img->width = rhs->w; 1387510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project img->height = rhs->h; 1397510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project img->format = get_format(rhs->format); 140bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian img->offset = hnd->offset; 14142089bcaff1c89c6aec145ffb6d32cdad7dfa346Mathias Agopian#if defined(COPYBIT_MSM7K) 142cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian if (hnd->flags & private_handle_t::PRIV_FLAGS_USES_GPU) { 1439c2781aab28f21e74b7a30bbaf50747d82743d54Mathias Agopian img->offset += hnd->map_offset; 144cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian img->memory_id = hnd->gpu_fd; 145cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian if (img->format == MDP_RGBA_8888) { 146cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian // msm7201A GPU only supports BGRA_8888 destinations 147cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian img->format = MDP_BGRA_8888; 148cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian } 149cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian } else { 150cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian img->memory_id = hnd->fd; 151cd2ad42c8c37a56c7d69f44529aaa0a6bb3066e4Mathias Agopian } 15242089bcaff1c89c6aec145ffb6d32cdad7dfa346Mathias Agopian#else 15342089bcaff1c89c6aec145ffb6d32cdad7dfa346Mathias Agopian img->memory_id = hnd->fd; 15442089bcaff1c89c6aec145ffb6d32cdad7dfa346Mathias Agopian#endif 1557510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 1567510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** setup rectangles */ 1577510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic void set_rects(struct copybit_context_t *dev, 1587510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct mdp_blit_req *e, 1597510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const struct copybit_rect_t *dst, 1607510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const struct copybit_rect_t *src, 1617510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const struct copybit_rect_t *scissor) { 1627510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_rect_t clip; 1637510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project intersect(&clip, scissor, dst); 1647510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1657510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->dst_rect.x = clip.l; 1667510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->dst_rect.y = clip.t; 1677510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->dst_rect.w = clip.r - clip.l; 1687510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->dst_rect.h = clip.b - clip.t; 1697510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1707510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project uint32_t W, H; 1717510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (dev->mFlags & COPYBIT_TRANSFORM_ROT_90) { 1727510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.x = (clip.t - dst->t) + src->t; 1737510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.y = (dst->r - clip.r) + src->l; 1747510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.w = (clip.b - clip.t); 1757510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.h = (clip.r - clip.l); 1767510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project W = dst->b - dst->t; 1777510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project H = dst->r - dst->l; 1787510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 1797510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.x = (clip.l - dst->l) + src->l; 1807510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.y = (clip.t - dst->t) + src->t; 1817510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.w = (clip.r - clip.l); 1827510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.h = (clip.b - clip.t); 1837510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project W = dst->r - dst->l; 1847510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project H = dst->b - dst->t; 1857510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 1867510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project MULDIV(&e->src_rect.x, &e->src_rect.w, src->r - src->l, W); 1877510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project MULDIV(&e->src_rect.y, &e->src_rect.h, src->b - src->t, H); 1887510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (dev->mFlags & COPYBIT_TRANSFORM_FLIP_V) { 1897510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.y = e->src.height - (e->src_rect.y + e->src_rect.h); 1907510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 1917510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (dev->mFlags & COPYBIT_TRANSFORM_FLIP_H) { 1927510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project e->src_rect.x = e->src.width - (e->src_rect.x + e->src_rect.w); 1937510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 1947510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 1957510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 1967510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** setup mdp request */ 1977510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic void set_infos(struct copybit_context_t *dev, struct mdp_blit_req *req) { 1987510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project req->alpha = dev->mAlpha; 1997510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project req->transp_mask = MDP_TRANSP_NOP; 200afff0dae18bbea0b39ad151e73ae20cbc11e3eddDima Zavin req->flags = dev->mFlags | MDP_BLEND_FG_PREMULT; 2017510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 2027510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 2037510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** copy the bits */ 2047510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int msm_copybit(struct copybit_context_t *dev, void const *list) 2057510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 2067510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int err = ioctl(dev->mFD, MSMFB_BLIT, 2077510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project (struct mdp_blit_req_list const*)list); 208c3dee7890047bad1136078f0f6e2b6d1a9a24947Steve Block ALOGE_IF(err<0, "copyBits failed (%s)", strerror(errno)); 20987ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian if (err == 0) { 2107510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return 0; 21187ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian } else { 21287ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian#if DEBUG_MDP_ERRORS 21387ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian struct mdp_blit_req_list const* l = (struct mdp_blit_req_list const*)list; 21487ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian for (int i=0 ; i<l->count ; i++) { 215f9452ed4a7c7bbde537f3f2690fc124e5a1beaffSteve Block ALOGD("%d: src={w=%d, h=%d, f=%d, rect={%d,%d,%d,%d}}\n" 21687ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian " dst={w=%d, h=%d, f=%d, rect={%d,%d,%d,%d}}\n" 21787ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian " flags=%08lx" 21887ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian , 21987ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian i, 22087ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src.width, 22187ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src.height, 22287ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src.format, 22387ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src_rect.x, 22487ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src_rect.y, 22587ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src_rect.w, 22687ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].src_rect.h, 22787ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst.width, 22887ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst.height, 22987ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst.format, 23087ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst_rect.x, 23187ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst_rect.y, 23287ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst_rect.w, 23387ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].dst_rect.h, 23487ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian l->req[i].flags 23587ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian ); 23687ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian } 23787ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian#endif 2387510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return -errno; 23987ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian } 2407510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 2417510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 2427510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/*****************************************************************************/ 2437510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 2447510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** Set a parameter to value */ 2457510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int set_parameter_copybit( 2467510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_device_t *dev, 2477510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int name, 2487510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int value) 2497510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 2507510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 2517510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int status = 0; 2527510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ctx) { 2537510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project switch(name) { 2547510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_ROTATION_DEG: 2557510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project switch (value) { 2567510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case 0: 2577510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags &= ~0x7; 2587510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2597510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case 90: 2607510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags &= ~0x7; 2617510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags |= MDP_ROT_90; 2627510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2637510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case 180: 2647510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags &= ~0x7; 2657510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags |= MDP_ROT_180; 2667510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2677510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case 270: 2687510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags &= ~0x7; 2697510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags |= MDP_ROT_270; 2707510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2717510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project default: 272c3dee7890047bad1136078f0f6e2b6d1a9a24947Steve Block ALOGE("Invalid value for COPYBIT_ROTATION_DEG"); 2737510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -EINVAL; 2747510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2757510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 2767510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2777510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_PLANE_ALPHA: 2787510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (value < 0) value = 0; 2797510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (value >= 256) value = 255; 2807510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mAlpha = value; 2817510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2827510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_DITHER: 2837510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (value == COPYBIT_ENABLE) { 2847510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags |= MDP_DITHER; 2857510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else if (value == COPYBIT_DISABLE) { 2867510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags &= ~MDP_DITHER; 2877510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 2887510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 2898cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian case COPYBIT_BLUR: 2908cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian if (value == COPYBIT_ENABLE) { 2918cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian ctx->mFlags |= MDP_BLUR; 2928cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian } else if (value == COPYBIT_DISABLE) { 2938cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian ctx->mFlags &= ~MDP_BLUR; 2948cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian } 2958cfaf3511ae89c7dee6c64ec888a63b385e9d0c9Mathias Agopian break; 2967510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_TRANSFORM: 2977510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags &= ~0x7; 2987510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags |= value & 0x7; 2997510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 3007510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project default: 3017510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -EINVAL; 3027510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 3037510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 3047510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 3057510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -EINVAL; 3067510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 3077510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return status; 3087510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 3097510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 3107510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** Get a static info value */ 3117510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int get(struct copybit_device_t *dev, int name) 3127510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 3137510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 3147510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int value; 3157510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ctx) { 3167510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project switch(name) { 3177510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_MINIFICATION_LIMIT: 3183f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian value = MAX_SCALE_FACTOR; 3197510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 3207510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_MAGNIFICATION_LIMIT: 3213f204e86d4a4449fa6196ba26e668d345e24bfb1Mathias Agopian value = MAX_SCALE_FACTOR; 3227510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 3237510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_SCALING_FRAC_BITS: 3247510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project value = 32; 3257510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 3267510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_ROTATION_STEP_DEG: 3277510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project value = 90; 3287510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project break; 3297510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project default: 3307510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project value = -EINVAL; 3317510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 3327510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 3337510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project value = -EINVAL; 3347510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 3357510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return value; 3367510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 3377510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 3387510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** do a stretch blit type operation */ 3397510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int stretch_copybit( 3407510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_device_t *dev, 3417510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_image_t const *dst, 3427510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_image_t const *src, 3437510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_rect_t const *dst_rect, 3447510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_rect_t const *src_rect, 3457510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_region_t const *region) 3467510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 3477510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 3487510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int status = 0; 3497510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ctx) { 3507510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct { 3517510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project uint32_t count; 3527510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct mdp_blit_req req[12]; 3537510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } list; 3547510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 3557510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ctx->mAlpha < 255) { 3567510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project switch (src->format) { 3577510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project // we don't support plane alpha with RGBA formats 3587510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_FORMAT_RGBA_8888: 3597510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_FORMAT_BGRA_8888: 3607510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_FORMAT_RGBA_5551: 3617510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project case COPYBIT_FORMAT_RGBA_4444: 3627510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return -EINVAL; 3637510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 3647510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 365b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian 366b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian if (src_rect->l < 0 || src_rect->r > src->w || 367b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian src_rect->t < 0 || src_rect->b > src->h) { 368b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian // this is always invalid 369b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian return -EINVAL; 370b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian } 371b7f7f038529135a5c21234ae89e4b87a1c56854aMathias Agopian 37242e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian if (src->w > MAX_DIMENSION || src->h > MAX_DIMENSION) 37342e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian return -EINVAL; 37442e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian 37542e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian if (dst->w > MAX_DIMENSION || dst->h > MAX_DIMENSION) 37642e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian return -EINVAL; 37742e2860adbfcf08146fe44e6c3e197b98849ae0aMathias Agopian 3787510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const uint32_t maxCount = sizeof(list.req)/sizeof(list.req[0]); 3797510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project const struct copybit_rect_t bounds = { 0, 0, dst->w, dst->h }; 3807510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_rect_t clip; 3817510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project list.count = 0; 3827510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = 0; 3837510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project while ((status == 0) && region->next(region, &clip)) { 3847510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project intersect(&clip, &bounds, &clip); 38587ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian mdp_blit_req* req = &list.req[list.count]; 38687ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian set_infos(ctx, req); 38787ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian set_image(&req->dst, dst); 38887ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian set_image(&req->src, src); 38987ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian set_rects(ctx, req, dst_rect, src_rect, &clip); 39087ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian 39187ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian if (req->src_rect.w<=0 || req->src_rect.h<=0) 39287ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian continue; 39387ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian 39487ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian if (req->dst_rect.w<=0 || req->dst_rect.h<=0) 39587ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian continue; 39687ea1dfa60cf130fafdbab8e94cb2ce9ff8d0975Mathias Agopian 3977510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (++list.count == maxCount) { 3987510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = msm_copybit(ctx, &list); 3997510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project list.count = 0; 4007510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4017510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4027510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if ((status == 0) && list.count) { 4037510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = msm_copybit(ctx, &list); 4047510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4057510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 4067510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -EINVAL; 4077510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4087510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return status; 4097510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 4107510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4117510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** Perform a blit type operation */ 4127510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int blit_copybit( 4137510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_device_t *dev, 4147510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_image_t const *dst, 4157510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_image_t const *src, 4167510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_region_t const *region) 4177510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 4187510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_rect_t dr = { 0, 0, dst->w, dst->h }; 4197510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_rect_t sr = { 0, 0, src->w, src->h }; 4207510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return stretch_copybit(dev, dst, src, &dr, &sr, region); 4217510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 4227510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4237510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/*****************************************************************************/ 4247510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4257510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** Close the copybit device */ 4267510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int close_copybit(struct hw_device_t *dev) 4277510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 4287510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct copybit_context_t* ctx = (struct copybit_context_t*)dev; 4297510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ctx) { 4307510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project close(ctx->mFD); 4317510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project free(ctx); 4327510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4337510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return 0; 4347510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 4357510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4367510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project/** Open a new instance of a copybit device using name */ 4377510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Projectstatic int open_copybit(const struct hw_module_t* module, const char* name, 4387510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct hw_device_t** device) 4397510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project{ 4407510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project int status = -EINVAL; 441bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian copybit_context_t *ctx; 442bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian ctx = (copybit_context_t *)malloc(sizeof(copybit_context_t)); 4437510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project memset(ctx, 0, sizeof(*ctx)); 4447510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4457510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->device.common.tag = HARDWARE_DEVICE_TAG; 446bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian ctx->device.common.version = 1; 447bb451691e0e9c153dab4a3ba3eee7ba29f087514Mathias Agopian ctx->device.common.module = const_cast<hw_module_t*>(module); 4487510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->device.common.close = close_copybit; 4497510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->device.set_parameter = set_parameter_copybit; 4507510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->device.get = get; 4517510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->device.blit = blit_copybit; 4527510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->device.stretch = stretch_copybit; 4537510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mAlpha = MDP_ALPHA_NOP; 4547510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFlags = 0; 4557510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project ctx->mFD = open("/dev/graphics/fb0", O_RDWR, 0); 4567510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4577510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ctx->mFD < 0) { 4587510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = errno; 459c3dee7890047bad1136078f0f6e2b6d1a9a24947Steve Block ALOGE("Error opening frame buffer errno=%d (%s)", 4607510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status, strerror(status)); 4617510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -status; 4627510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 4637510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project struct fb_fix_screeninfo finfo; 4647510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (ioctl(ctx->mFD, FBIOGET_FSCREENINFO, &finfo) == 0) { 4657510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (strcmp(finfo.id, "msmfb") == 0) { 4667510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project /* Success */ 4677510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = 0; 4687510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 469c3dee7890047bad1136078f0f6e2b6d1a9a24947Steve Block ALOGE("Error not msm frame buffer"); 4707510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -EINVAL; 4717510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4727510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 473c3dee7890047bad1136078f0f6e2b6d1a9a24947Steve Block ALOGE("Error executing ioctl for screen info"); 4747510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project status = -errno; 4757510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4767510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4777510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project 4787510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project if (status == 0) { 4797510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project *device = &ctx->device.common; 4807510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } else { 4817510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project close_copybit(&ctx->device.common); 4827510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project } 4837510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project return status; 4847510aaf4b3a3c545d943b09e0fb9f56ea2fc5e24The Android Open Source Project} 485