Home | History | Annotate | Download | only in gralloc
      1 /*
      2 * Copyright (C) 2011 The Android Open Source Project
      3 *
      4 * Licensed under the Apache License, Version 2.0 (the "License");
      5 * you may not use this file except in compliance with the License.
      6 * You may obtain a copy of the License at
      7 *
      8 * http://www.apache.org/licenses/LICENSE-2.0
      9 *
     10 * Unless required by applicable law or agreed to in writing, software
     11 * distributed under the License is distributed on an "AS IS" BASIS,
     12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13 * See the License for the specific language governing permissions and
     14 * limitations under the License.
     15 */
     16 #include <string.h>
     17 #include <pthread.h>
     18 #include <limits.h>
     19 #include <cutils/ashmem.h>
     20 #include <unistd.h>
     21 #include <errno.h>
     22 #include <dlfcn.h>
     23 #include <sys/mman.h>
     24 #include "gralloc_cb.h"
     25 #include "HostConnection.h"
     26 #include "glUtils.h"
     27 #include <cutils/log.h>
     28 #include <cutils/properties.h>
     29 
     30 /* Set to 1 or 2 to enable debug traces */
     31 #define DEBUG  0
     32 
     33 #if DEBUG >= 1
     34 #  define D(...)   ALOGD(__VA_ARGS__)
     35 #else
     36 #  define D(...)   ((void)0)
     37 #endif
     38 
     39 #if DEBUG >= 2
     40 #  define DD(...)  ALOGD(__VA_ARGS__)
     41 #else
     42 #  define DD(...)  ((void)0)
     43 #endif
     44 
     45 #define DBG_FUNC DBG("%s\n", __FUNCTION__)
     46 //
     47 // our private gralloc module structure
     48 //
     49 struct private_module_t {
     50     gralloc_module_t base;
     51 };
     52 
     53 /* If not NULL, this is a pointer to the fallback module.
     54  * This really is gralloc.default, which we'll use if we detect
     55  * that the emulator we're running in does not support GPU emulation.
     56  */
     57 static gralloc_module_t*  sFallback;
     58 static pthread_once_t     sFallbackOnce = PTHREAD_ONCE_INIT;
     59 
     60 static void fallback_init(void);  // forward
     61 
     62 
     63 typedef struct _alloc_list_node {
     64     buffer_handle_t handle;
     65     _alloc_list_node *next;
     66     _alloc_list_node *prev;
     67 } AllocListNode;
     68 
     69 //
     70 // Our gralloc device structure (alloc interface)
     71 //
     72 struct gralloc_device_t {
     73     alloc_device_t  device;
     74 
     75     AllocListNode *allocListHead;    // double linked list of allocated buffers
     76     pthread_mutex_t lock;
     77 };
     78 
     79 //
     80 // Our framebuffer device structure
     81 //
     82 struct fb_device_t {
     83     framebuffer_device_t  device;
     84 };
     85 
     86 static int map_buffer(cb_handle_t *cb, void **vaddr)
     87 {
     88     if (cb->fd < 0 || cb->ashmemSize <= 0) {
     89         return -EINVAL;
     90     }
     91 
     92     void *addr = mmap(0, cb->ashmemSize, PROT_READ | PROT_WRITE,
     93                       MAP_SHARED, cb->fd, 0);
     94     if (addr == MAP_FAILED) {
     95         return -errno;
     96     }
     97 
     98     cb->ashmemBase = intptr_t(addr);
     99     cb->ashmemBasePid = getpid();
    100 
    101     *vaddr = addr;
    102     return 0;
    103 }
    104 
    105 #define DEFINE_HOST_CONNECTION \
    106     HostConnection *hostCon = HostConnection::get(); \
    107     renderControl_encoder_context_t *rcEnc = (hostCon ? hostCon->rcEncoder() : NULL)
    108 
    109 #define DEFINE_AND_VALIDATE_HOST_CONNECTION \
    110     HostConnection *hostCon = HostConnection::get(); \
    111     if (!hostCon) { \
    112         ALOGE("gralloc: Failed to get host connection\n"); \
    113         return -EIO; \
    114     } \
    115     renderControl_encoder_context_t *rcEnc = hostCon->rcEncoder(); \
    116     if (!rcEnc) { \
    117         ALOGE("gralloc: Failed to get renderControl encoder context\n"); \
    118         return -EIO; \
    119     }
    120 
    121 
    122 //
    123 // gralloc device functions (alloc interface)
    124 //
    125 static int gralloc_alloc(alloc_device_t* dev,
    126                          int w, int h, int format, int usage,
    127                          buffer_handle_t* pHandle, int* pStride)
    128 {
    129     D("gralloc_alloc w=%d h=%d usage=0x%x\n", w, h, usage);
    130 
    131     gralloc_device_t *grdev = (gralloc_device_t *)dev;
    132     if (!grdev || !pHandle || !pStride) {
    133         ALOGE("gralloc_alloc: Bad inputs (grdev: %p, pHandle: %p, pStride: %p",
    134                 grdev, pHandle, pStride);
    135         return -EINVAL;
    136     }
    137 
    138     //
    139     // Validate usage: buffer cannot be written both by s/w and h/w access.
    140     //
    141     bool sw_write = (0 != (usage & GRALLOC_USAGE_SW_WRITE_MASK));
    142     bool hw_write = (usage & GRALLOC_USAGE_HW_RENDER);
    143     if (hw_write && sw_write) {
    144         ALOGE("gralloc_alloc: Mismatched usage flags: %d x %d, usage %x",
    145                 w, h, usage);
    146         return -EINVAL;
    147     }
    148     bool sw_read = (0 != (usage & GRALLOC_USAGE_SW_READ_MASK));
    149     bool hw_cam_write = usage & GRALLOC_USAGE_HW_CAMERA_WRITE;
    150     bool hw_cam_read = usage & GRALLOC_USAGE_HW_CAMERA_READ;
    151     bool hw_vid_enc_read = usage & GRALLOC_USAGE_HW_VIDEO_ENCODER;
    152 
    153     // Keep around original requested format for later validation
    154     int frameworkFormat = format;
    155     // Pick the right concrete pixel format given the endpoints as encoded in
    156     // the usage bits.  Every end-point pair needs explicit listing here.
    157     if (format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED) {
    158         // Camera as producer
    159         if (usage & GRALLOC_USAGE_HW_CAMERA_WRITE) {
    160             if (usage & GRALLOC_USAGE_HW_TEXTURE) {
    161                 // Camera-to-display is RGBA
    162                 format = HAL_PIXEL_FORMAT_RGBA_8888;
    163             } else if (usage & GRALLOC_USAGE_HW_VIDEO_ENCODER) {
    164                 // Camera-to-encoder is NV21
    165                 format = HAL_PIXEL_FORMAT_YCrCb_420_SP;
    166             } else if ((usage & GRALLOC_USAGE_HW_CAMERA_MASK) ==
    167                     GRALLOC_USAGE_HW_CAMERA_ZSL) {
    168                 // Camera-to-ZSL-queue is RGB_888
    169                 format = HAL_PIXEL_FORMAT_RGB_888;
    170             }
    171         }
    172 
    173         if (format == HAL_PIXEL_FORMAT_IMPLEMENTATION_DEFINED) {
    174             ALOGE("gralloc_alloc: Requested auto format selection, "
    175                     "but no known format for this usage: %d x %d, usage %x",
    176                     w, h, usage);
    177             return -EINVAL;
    178         }
    179     } else if (format == HAL_PIXEL_FORMAT_YCbCr_420_888) {
    180         // Flexible framework-accessible YUV format; map to NV21 for now
    181         if (usage & GRALLOC_USAGE_HW_CAMERA_WRITE) {
    182             format = HAL_PIXEL_FORMAT_YCrCb_420_SP;
    183         }
    184         if (format == HAL_PIXEL_FORMAT_YCbCr_420_888) {
    185             ALOGE("gralloc_alloc: Requested YCbCr_420_888, but no known "
    186                     "specific format for this usage: %d x %d, usage %x",
    187                     w, h, usage);
    188         }
    189     }
    190     bool yuv_format = false;
    191 
    192     int ashmem_size = 0;
    193     int stride = w;
    194 
    195     GLenum glFormat = 0;
    196     GLenum glType = 0;
    197 
    198     int bpp = 0;
    199     int align = 1;
    200     switch (format) {
    201         case HAL_PIXEL_FORMAT_RGBA_8888:
    202         case HAL_PIXEL_FORMAT_RGBX_8888:
    203         case HAL_PIXEL_FORMAT_BGRA_8888:
    204             bpp = 4;
    205             glFormat = GL_RGBA;
    206             glType = GL_UNSIGNED_BYTE;
    207             break;
    208         case HAL_PIXEL_FORMAT_RGB_888:
    209             bpp = 3;
    210             glFormat = GL_RGB;
    211             glType = GL_UNSIGNED_BYTE;
    212             break;
    213         case HAL_PIXEL_FORMAT_RGB_565:
    214             bpp = 2;
    215             glFormat = GL_RGB;
    216             glType = GL_UNSIGNED_SHORT_5_6_5;
    217             break;
    218         case HAL_PIXEL_FORMAT_RAW_SENSOR:
    219             bpp = 2;
    220             align = 16*bpp;
    221             if (! ((sw_read || hw_cam_read) && (sw_write || hw_cam_write) ) ) {
    222                 // Raw sensor data only goes between camera and CPU
    223                 return -EINVAL;
    224             }
    225             // Not expecting to actually create any GL surfaces for this
    226             glFormat = GL_LUMINANCE;
    227             glType = GL_UNSIGNED_SHORT;
    228             break;
    229         case HAL_PIXEL_FORMAT_BLOB:
    230             bpp = 1;
    231             if (! (sw_read && hw_cam_write) ) {
    232                 // Blob data cannot be used by HW other than camera emulator
    233                 return -EINVAL;
    234             }
    235             // Not expecting to actually create any GL surfaces for this
    236             glFormat = GL_LUMINANCE;
    237             glType = GL_UNSIGNED_BYTE;
    238             break;
    239         case HAL_PIXEL_FORMAT_YCrCb_420_SP:
    240             align = 1;
    241             bpp = 1; // per-channel bpp
    242             yuv_format = true;
    243             // Not expecting to actually create any GL surfaces for this
    244             break;
    245         case HAL_PIXEL_FORMAT_YV12:
    246             align = 16;
    247             bpp = 1; // per-channel bpp
    248             yuv_format = true;
    249             // Not expecting to actually create any GL surfaces for this
    250             break;
    251         default:
    252             ALOGE("gralloc_alloc: Unknown format %d", format);
    253             return -EINVAL;
    254     }
    255 
    256     if (usage & GRALLOC_USAGE_HW_FB) {
    257         // keep space for postCounter
    258         ashmem_size += sizeof(uint32_t);
    259     }
    260 
    261     if (sw_read || sw_write || hw_cam_write || hw_vid_enc_read) {
    262         // keep space for image on guest memory if SW access is needed
    263         // or if the camera is doing writing
    264         if (yuv_format) {
    265             size_t yStride = (w*bpp + (align - 1)) & ~(align-1);
    266             size_t uvStride = (yStride / 2 + (align - 1)) & ~(align-1);
    267             size_t uvHeight = h / 2;
    268             ashmem_size += yStride * h + 2 * (uvHeight * uvStride);
    269             stride = yStride / bpp;
    270         } else {
    271             size_t bpr = (w*bpp + (align-1)) & ~(align-1);
    272             ashmem_size += (bpr * h);
    273             stride = bpr / bpp;
    274         }
    275     }
    276 
    277     D("gralloc_alloc format=%d, ashmem_size=%d, stride=%d, tid %d\n", format,
    278             ashmem_size, stride, gettid());
    279 
    280     //
    281     // Allocate space in ashmem if needed
    282     //
    283     int fd = -1;
    284     if (ashmem_size > 0) {
    285         // round to page size;
    286         ashmem_size = (ashmem_size + (PAGE_SIZE-1)) & ~(PAGE_SIZE-1);
    287 
    288         fd = ashmem_create_region("gralloc-buffer", ashmem_size);
    289         if (fd < 0) {
    290             ALOGE("gralloc_alloc failed to create ashmem region: %s\n",
    291                     strerror(errno));
    292             return -errno;
    293         }
    294     }
    295 
    296     cb_handle_t *cb = new cb_handle_t(fd, ashmem_size, usage,
    297                                       w, h, frameworkFormat, format,
    298                                       glFormat, glType);
    299 
    300     if (ashmem_size > 0) {
    301         //
    302         // map ashmem region if exist
    303         //
    304         void *vaddr;
    305         int err = map_buffer(cb, &vaddr);
    306         if (err) {
    307             close(fd);
    308             delete cb;
    309             return err;
    310         }
    311 
    312         cb->setFd(fd);
    313     }
    314 
    315     //
    316     // Allocate ColorBuffer handle on the host (only if h/w access is allowed)
    317     // Only do this for some h/w usages, not all.
    318     //
    319     if (usage & (GRALLOC_USAGE_HW_TEXTURE | GRALLOC_USAGE_HW_RENDER |
    320                     GRALLOC_USAGE_HW_2D | GRALLOC_USAGE_HW_COMPOSER |
    321                     GRALLOC_USAGE_HW_FB) ) {
    322         DEFINE_HOST_CONNECTION;
    323         if (hostCon && rcEnc) {
    324             cb->hostHandle = rcEnc->rcCreateColorBuffer(rcEnc, w, h, glFormat);
    325             D("Created host ColorBuffer 0x%x\n", cb->hostHandle);
    326         }
    327 
    328         if (!cb->hostHandle) {
    329            // Could not create colorbuffer on host !!!
    330            close(fd);
    331            delete cb;
    332            return -EIO;
    333         }
    334     }
    335 
    336     //
    337     // alloc succeeded - insert the allocated handle to the allocated list
    338     //
    339     AllocListNode *node = new AllocListNode();
    340     pthread_mutex_lock(&grdev->lock);
    341     node->handle = cb;
    342     node->next =  grdev->allocListHead;
    343     node->prev =  NULL;
    344     if (grdev->allocListHead) {
    345         grdev->allocListHead->prev = node;
    346     }
    347     grdev->allocListHead = node;
    348     pthread_mutex_unlock(&grdev->lock);
    349 
    350     *pHandle = cb;
    351     if (frameworkFormat == HAL_PIXEL_FORMAT_YCbCr_420_888) {
    352         *pStride = 0;
    353     } else {
    354         *pStride = stride;
    355     }
    356     return 0;
    357 }
    358 
    359 static int gralloc_free(alloc_device_t* dev,
    360                         buffer_handle_t handle)
    361 {
    362     const cb_handle_t *cb = (const cb_handle_t *)handle;
    363     if (!cb_handle_t::validate((cb_handle_t*)cb)) {
    364         ERR("gralloc_free: invalid handle");
    365         return -EINVAL;
    366     }
    367 
    368     if (cb->hostHandle != 0) {
    369         DEFINE_AND_VALIDATE_HOST_CONNECTION;
    370         D("Closing host ColorBuffer 0x%x\n", cb->hostHandle);
    371         rcEnc->rcCloseColorBuffer(rcEnc, cb->hostHandle);
    372     }
    373 
    374     //
    375     // detach and unmap ashmem area if present
    376     //
    377     if (cb->fd > 0) {
    378         if (cb->ashmemSize > 0 && cb->ashmemBase) {
    379             munmap((void *)cb->ashmemBase, cb->ashmemSize);
    380         }
    381         close(cb->fd);
    382     }
    383 
    384     // remove it from the allocated list
    385     gralloc_device_t *grdev = (gralloc_device_t *)dev;
    386     pthread_mutex_lock(&grdev->lock);
    387     AllocListNode *n = grdev->allocListHead;
    388     while( n && n->handle != cb ) {
    389         n = n->next;
    390     }
    391     if (n) {
    392        // buffer found on list - remove it from list
    393        if (n->next) {
    394            n->next->prev = n->prev;
    395        }
    396        if (n->prev) {
    397            n->prev->next = n->next;
    398        }
    399        else {
    400            grdev->allocListHead = n->next;
    401        }
    402 
    403        delete n;
    404     }
    405     pthread_mutex_unlock(&grdev->lock);
    406 
    407     delete cb;
    408 
    409     return 0;
    410 }
    411 
    412 static int gralloc_device_close(struct hw_device_t *dev)
    413 {
    414     gralloc_device_t* d = reinterpret_cast<gralloc_device_t*>(dev);
    415     if (d) {
    416 
    417         // free still allocated buffers
    418         while( d->allocListHead != NULL ) {
    419             gralloc_free(&d->device, d->allocListHead->handle);
    420         }
    421 
    422         // free device
    423         free(d);
    424     }
    425     return 0;
    426 }
    427 
    428 static int fb_compositionComplete(struct framebuffer_device_t* dev)
    429 {
    430     return 0;
    431 }
    432 
    433 //
    434 // Framebuffer device functions
    435 //
    436 static int fb_post(struct framebuffer_device_t* dev, buffer_handle_t buffer)
    437 {
    438     fb_device_t *fbdev = (fb_device_t *)dev;
    439     cb_handle_t *cb = (cb_handle_t *)buffer;
    440 
    441     if (!fbdev || !cb_handle_t::validate(cb) || !cb->canBePosted()) {
    442         return -EINVAL;
    443     }
    444 
    445     // Make sure we have host connection
    446     DEFINE_AND_VALIDATE_HOST_CONNECTION;
    447 
    448     // increment the post count of the buffer
    449     intptr_t *postCountPtr = (intptr_t *)cb->ashmemBase;
    450     if (!postCountPtr) {
    451         // This should not happen
    452         return -EINVAL;
    453     }
    454     (*postCountPtr)++;
    455 
    456     // send post request to host
    457     rcEnc->rcFBPost(rcEnc, cb->hostHandle);
    458     hostCon->flush();
    459 
    460     return 0;
    461 }
    462 
    463 static int fb_setUpdateRect(struct framebuffer_device_t* dev,
    464         int l, int t, int w, int h)
    465 {
    466     fb_device_t *fbdev = (fb_device_t *)dev;
    467 
    468     if (!fbdev) {
    469         return -EINVAL;
    470     }
    471 
    472     // Make sure we have host connection
    473     DEFINE_AND_VALIDATE_HOST_CONNECTION;
    474 
    475     // send request to host
    476     // TODO: XXX - should be implemented
    477     //rcEnc->rc_XXX
    478 
    479     return 0;
    480 }
    481 
    482 static int fb_setSwapInterval(struct framebuffer_device_t* dev,
    483             int interval)
    484 {
    485     fb_device_t *fbdev = (fb_device_t *)dev;
    486 
    487     if (!fbdev) {
    488         return -EINVAL;
    489     }
    490 
    491     // Make sure we have host connection
    492     DEFINE_AND_VALIDATE_HOST_CONNECTION;
    493 
    494     // send request to host
    495     rcEnc->rcFBSetSwapInterval(rcEnc, interval);
    496     hostCon->flush();
    497 
    498     return 0;
    499 }
    500 
    501 static int fb_close(struct hw_device_t *dev)
    502 {
    503     fb_device_t *fbdev = (fb_device_t *)dev;
    504 
    505     delete fbdev;
    506 
    507     return 0;
    508 }
    509 
    510 
    511 //
    512 // gralloc module functions - refcount + locking interface
    513 //
    514 static int gralloc_register_buffer(gralloc_module_t const* module,
    515                                    buffer_handle_t handle)
    516 {
    517     pthread_once(&sFallbackOnce, fallback_init);
    518     if (sFallback != NULL) {
    519         return sFallback->registerBuffer(sFallback, handle);
    520     }
    521 
    522     D("gralloc_register_buffer(%p) called", handle);
    523 
    524     private_module_t *gr = (private_module_t *)module;
    525     cb_handle_t *cb = (cb_handle_t *)handle;
    526     if (!gr || !cb_handle_t::validate(cb)) {
    527         ERR("gralloc_register_buffer(%p): invalid buffer", cb);
    528         return -EINVAL;
    529     }
    530 
    531     if (cb->hostHandle != 0) {
    532         DEFINE_AND_VALIDATE_HOST_CONNECTION;
    533         D("Opening host ColorBuffer 0x%x\n", cb->hostHandle);
    534         rcEnc->rcOpenColorBuffer2(rcEnc, cb->hostHandle);
    535     }
    536 
    537     //
    538     // if the color buffer has ashmem region and it is not mapped in this
    539     // process map it now.
    540     //
    541     if (cb->ashmemSize > 0 && cb->mappedPid != getpid()) {
    542         void *vaddr;
    543         int err = map_buffer(cb, &vaddr);
    544         if (err) {
    545             ERR("gralloc_register_buffer(%p): map failed: %s", cb, strerror(-err));
    546             return -err;
    547         }
    548         cb->mappedPid = getpid();
    549     }
    550 
    551     return 0;
    552 }
    553 
    554 static int gralloc_unregister_buffer(gralloc_module_t const* module,
    555                                      buffer_handle_t handle)
    556 {
    557     if (sFallback != NULL) {
    558         return sFallback->unregisterBuffer(sFallback, handle);
    559     }
    560 
    561     private_module_t *gr = (private_module_t *)module;
    562     cb_handle_t *cb = (cb_handle_t *)handle;
    563     if (!gr || !cb_handle_t::validate(cb)) {
    564         ERR("gralloc_unregister_buffer(%p): invalid buffer", cb);
    565         return -EINVAL;
    566     }
    567 
    568     if (cb->hostHandle != 0) {
    569         DEFINE_AND_VALIDATE_HOST_CONNECTION;
    570         D("Closing host ColorBuffer 0x%x\n", cb->hostHandle);
    571         rcEnc->rcCloseColorBuffer(rcEnc, cb->hostHandle);
    572     }
    573 
    574     //
    575     // unmap ashmem region if it was previously mapped in this process
    576     // (through register_buffer)
    577     //
    578     if (cb->ashmemSize > 0 && cb->mappedPid == getpid()) {
    579         void *vaddr;
    580         int err = munmap((void *)cb->ashmemBase, cb->ashmemSize);
    581         if (err) {
    582             ERR("gralloc_unregister_buffer(%p): unmap failed", cb);
    583             return -EINVAL;
    584         }
    585         cb->ashmemBase = 0;
    586         cb->mappedPid = 0;
    587     }
    588 
    589     D("gralloc_unregister_buffer(%p) done\n", cb);
    590 
    591     return 0;
    592 }
    593 
    594 static int gralloc_lock(gralloc_module_t const* module,
    595                         buffer_handle_t handle, int usage,
    596                         int l, int t, int w, int h,
    597                         void** vaddr)
    598 {
    599     if (sFallback != NULL) {
    600         return sFallback->lock(sFallback, handle, usage, l, t, w, h, vaddr);
    601     }
    602 
    603     private_module_t *gr = (private_module_t *)module;
    604     cb_handle_t *cb = (cb_handle_t *)handle;
    605     if (!gr || !cb_handle_t::validate(cb)) {
    606         ALOGE("gralloc_lock bad handle\n");
    607         return -EINVAL;
    608     }
    609 
    610     // validate format
    611     if (cb->frameworkFormat == HAL_PIXEL_FORMAT_YCbCr_420_888) {
    612         ALOGE("gralloc_lock can't be used with YCbCr_420_888 format");
    613         return -EINVAL;
    614     }
    615 
    616     // Validate usage,
    617     //   1. cannot be locked for hw access
    618     //   2. lock for either sw read or write.
    619     //   3. locked sw access must match usage during alloc time.
    620     bool sw_read = (0 != (usage & GRALLOC_USAGE_SW_READ_MASK));
    621     bool sw_write = (0 != (usage & GRALLOC_USAGE_SW_WRITE_MASK));
    622     bool hw_read = (usage & GRALLOC_USAGE_HW_TEXTURE);
    623     bool hw_write = (usage & GRALLOC_USAGE_HW_RENDER);
    624     bool hw_vid_enc_read = (usage & GRALLOC_USAGE_HW_VIDEO_ENCODER);
    625     bool hw_cam_write = (usage & GRALLOC_USAGE_HW_CAMERA_WRITE);
    626     bool hw_cam_read = (usage & GRALLOC_USAGE_HW_CAMERA_READ);
    627     bool sw_read_allowed = (0 != (cb->usage & GRALLOC_USAGE_SW_READ_MASK));
    628     bool sw_write_allowed = (0 != (cb->usage & GRALLOC_USAGE_SW_WRITE_MASK));
    629 
    630     if ( (hw_read || hw_write) ||
    631          (!sw_read && !sw_write &&
    632                  !hw_cam_write && !hw_cam_read &&
    633                  !hw_vid_enc_read) ||
    634          (sw_read && !sw_read_allowed) ||
    635          (sw_write && !sw_write_allowed) ) {
    636         ALOGE("gralloc_lock usage mismatch usage=0x%x cb->usage=0x%x\n", usage,
    637                 cb->usage);
    638         return -EINVAL;
    639     }
    640 
    641     intptr_t postCount = 0;
    642     void *cpu_addr = NULL;
    643 
    644     //
    645     // make sure ashmem area is mapped if needed
    646     //
    647     if (cb->canBePosted() || sw_read || sw_write ||
    648             hw_cam_write || hw_cam_read ||
    649             hw_vid_enc_read) {
    650         if (cb->ashmemBasePid != getpid() || !cb->ashmemBase) {
    651             return -EACCES;
    652         }
    653 
    654         if (cb->canBePosted()) {
    655             postCount = *((intptr_t *)cb->ashmemBase);
    656             cpu_addr = (void *)(cb->ashmemBase + sizeof(intptr_t));
    657         }
    658         else {
    659             cpu_addr = (void *)(cb->ashmemBase);
    660         }
    661     }
    662 
    663     if (cb->hostHandle) {
    664         // Make sure we have host connection
    665         DEFINE_AND_VALIDATE_HOST_CONNECTION;
    666 
    667         //
    668         // flush color buffer write cache on host and get its sync status.
    669         //
    670         int hostSyncStatus = rcEnc->rcColorBufferCacheFlush(rcEnc, cb->hostHandle,
    671                                                             postCount,
    672                                                             sw_read);
    673         if (hostSyncStatus < 0) {
    674             // host failed the color buffer sync - probably since it was already
    675             // locked for write access. fail the lock.
    676             ALOGE("gralloc_lock cacheFlush failed postCount=%d sw_read=%d\n",
    677                  postCount, sw_read);
    678             return -EBUSY;
    679         }
    680 
    681     }
    682 
    683     //
    684     // is virtual address required ?
    685     //
    686     if (sw_read || sw_write || hw_cam_write || hw_cam_read || hw_vid_enc_read) {
    687         *vaddr = cpu_addr;
    688     }
    689 
    690     if (sw_write || hw_cam_write) {
    691         //
    692         // Keep locked region if locked for s/w write access.
    693         //
    694         cb->lockedLeft = l;
    695         cb->lockedTop = t;
    696         cb->lockedWidth = w;
    697         cb->lockedHeight = h;
    698     }
    699 
    700     DD("gralloc_lock success. vaddr: %p, *vaddr: %p, usage: %x, cpu_addr: %p",
    701             vaddr, vaddr ? *vaddr : 0, usage, cpu_addr);
    702 
    703     return 0;
    704 }
    705 
    706 static int gralloc_unlock(gralloc_module_t const* module,
    707                           buffer_handle_t handle)
    708 {
    709     if (sFallback != NULL) {
    710         return sFallback->unlock(sFallback, handle);
    711     }
    712 
    713     private_module_t *gr = (private_module_t *)module;
    714     cb_handle_t *cb = (cb_handle_t *)handle;
    715     if (!gr || !cb_handle_t::validate(cb)) {
    716         return -EINVAL;
    717     }
    718 
    719     //
    720     // if buffer was locked for s/w write, we need to update the host with
    721     // the updated data
    722     //
    723     if (cb->lockedWidth > 0 && cb->lockedHeight > 0 && cb->hostHandle) {
    724 
    725         // Make sure we have host connection
    726         DEFINE_AND_VALIDATE_HOST_CONNECTION;
    727 
    728         void *cpu_addr;
    729         if (cb->canBePosted()) {
    730             cpu_addr = (void *)(cb->ashmemBase + sizeof(int));
    731         }
    732         else {
    733             cpu_addr = (void *)(cb->ashmemBase);
    734         }
    735 
    736         if (cb->lockedWidth < cb->width || cb->lockedHeight < cb->height) {
    737             int bpp = glUtilsPixelBitSize(cb->glFormat, cb->glType) >> 3;
    738             char *tmpBuf = new char[cb->lockedWidth * cb->lockedHeight * bpp];
    739 
    740             int dst_line_len = cb->lockedWidth * bpp;
    741             int src_line_len = cb->width * bpp;
    742             char *src = (char *)cpu_addr + cb->lockedTop*src_line_len + cb->lockedLeft*bpp;
    743             char *dst = tmpBuf;
    744             for (int y=0; y<cb->lockedHeight; y++) {
    745                 memcpy(dst, src, dst_line_len);
    746                 src += src_line_len;
    747                 dst += dst_line_len;
    748             }
    749 
    750             rcEnc->rcUpdateColorBuffer(rcEnc, cb->hostHandle,
    751                                        cb->lockedLeft, cb->lockedTop,
    752                                        cb->lockedWidth, cb->lockedHeight,
    753                                        cb->glFormat, cb->glType,
    754                                        tmpBuf);
    755 
    756             delete [] tmpBuf;
    757         }
    758         else {
    759             rcEnc->rcUpdateColorBuffer(rcEnc, cb->hostHandle, 0, 0,
    760                                        cb->width, cb->height,
    761                                        cb->glFormat, cb->glType,
    762                                        cpu_addr);
    763         }
    764     }
    765 
    766     cb->lockedWidth = cb->lockedHeight = 0;
    767     return 0;
    768 }
    769 
    770 static int gralloc_lock_ycbcr(gralloc_module_t const* module,
    771                         buffer_handle_t handle, int usage,
    772                         int l, int t, int w, int h,
    773                         android_ycbcr *ycbcr)
    774 {
    775     // Not supporting fallback module for YCbCr
    776     if (sFallback != NULL) {
    777         return -EINVAL;
    778     }
    779 
    780     if (!ycbcr) {
    781         ALOGE("gralloc_lock_ycbcr got NULL ycbcr struct");
    782         return -EINVAL;
    783     }
    784 
    785     private_module_t *gr = (private_module_t *)module;
    786     cb_handle_t *cb = (cb_handle_t *)handle;
    787     if (!gr || !cb_handle_t::validate(cb)) {
    788         ALOGE("gralloc_lock_ycbcr bad handle\n");
    789         return -EINVAL;
    790     }
    791 
    792     if (cb->frameworkFormat != HAL_PIXEL_FORMAT_YCbCr_420_888) {
    793         ALOGE("gralloc_lock_ycbcr can only be used with "
    794                 "HAL_PIXEL_FORMAT_YCbCr_420_888, got %x instead",
    795                 cb->frameworkFormat);
    796         return -EINVAL;
    797     }
    798 
    799     // Validate usage
    800     // For now, only allow camera write, software read.
    801     bool sw_read = (0 != (usage & GRALLOC_USAGE_SW_READ_MASK));
    802     bool hw_cam_write = (usage & GRALLOC_USAGE_HW_CAMERA_WRITE);
    803     bool sw_read_allowed = (0 != (cb->usage & GRALLOC_USAGE_SW_READ_MASK));
    804 
    805     if ( (!hw_cam_write && !sw_read) ||
    806             (sw_read && !sw_read_allowed) ) {
    807         ALOGE("gralloc_lock_ycbcr usage mismatch usage:0x%x cb->usage:0x%x\n",
    808                 usage, cb->usage);
    809         return -EINVAL;
    810     }
    811 
    812     // Make sure memory is mapped, get address
    813     if (cb->ashmemBasePid != getpid() || !cb->ashmemBase) {
    814         return -EACCES;
    815     }
    816 
    817     uint8_t *cpu_addr = NULL;
    818 
    819     if (cb->canBePosted()) {
    820         cpu_addr = (uint8_t *)(cb->ashmemBase + sizeof(int));
    821     }
    822     else {
    823         cpu_addr = (uint8_t *)(cb->ashmemBase);
    824     }
    825 
    826     // Calculate offsets to underlying YUV data
    827     size_t yStride;
    828     size_t cStride;
    829     size_t yOffset;
    830     size_t uOffset;
    831     size_t vOffset;
    832     size_t cStep;
    833     switch (cb->format) {
    834         case HAL_PIXEL_FORMAT_YCrCb_420_SP:
    835             yStride = cb->width;
    836             cStride = cb->width;
    837             yOffset = 0;
    838             vOffset = yStride * cb->height;
    839             uOffset = vOffset + 1;
    840             cStep = 2;
    841             break;
    842         default:
    843             ALOGE("gralloc_lock_ycbcr unexpected internal format %x",
    844                     cb->format);
    845             return -EINVAL;
    846     }
    847 
    848     ycbcr->y = cpu_addr + yOffset;
    849     ycbcr->cb = cpu_addr + uOffset;
    850     ycbcr->cr = cpu_addr + vOffset;
    851     ycbcr->ystride = yStride;
    852     ycbcr->cstride = cStride;
    853     ycbcr->chroma_step = cStep;
    854 
    855     // Zero out reserved fields
    856     memset(ycbcr->reserved, 0, sizeof(ycbcr->reserved));
    857 
    858     //
    859     // Keep locked region if locked for s/w write access.
    860     //
    861     cb->lockedLeft = l;
    862     cb->lockedTop = t;
    863     cb->lockedWidth = w;
    864     cb->lockedHeight = h;
    865 
    866     DD("gralloc_lock_ycbcr success. usage: %x, ycbcr.y: %p, .cb: %p, .cr: %p, "
    867             ".ystride: %d , .cstride: %d, .chroma_step: %d", usage,
    868             ycbcr->y, ycbcr->cb, ycbcr->cr, ycbcr->ystride, ycbcr->cstride,
    869             ycbcr->chroma_step);
    870 
    871     return 0;
    872 }
    873 
    874 static int gralloc_device_open(const hw_module_t* module,
    875                                const char* name,
    876                                hw_device_t** device)
    877 {
    878     int status = -EINVAL;
    879 
    880     D("gralloc_device_open %s\n", name);
    881 
    882     pthread_once( &sFallbackOnce, fallback_init );
    883     if (sFallback != NULL) {
    884         return sFallback->common.methods->open(&sFallback->common, name, device);
    885     }
    886 
    887     if (!strcmp(name, GRALLOC_HARDWARE_GPU0)) {
    888 
    889         // Create host connection and keep it in the TLS.
    890         // return error if connection with host can not be established
    891         HostConnection *hostCon = HostConnection::get();
    892         if (!hostCon) {
    893             ALOGE("gralloc: failed to get host connection while opening %s\n", name);
    894             return -EIO;
    895         }
    896 
    897         //
    898         // Allocate memory for the gralloc device (alloc interface)
    899         //
    900         gralloc_device_t *dev;
    901         dev = (gralloc_device_t*)malloc(sizeof(gralloc_device_t));
    902         if (NULL == dev) {
    903             return -ENOMEM;
    904         }
    905 
    906         // Initialize our device structure
    907         //
    908         dev->device.common.tag = HARDWARE_DEVICE_TAG;
    909         dev->device.common.version = 0;
    910         dev->device.common.module = const_cast<hw_module_t*>(module);
    911         dev->device.common.close = gralloc_device_close;
    912 
    913         dev->device.alloc   = gralloc_alloc;
    914         dev->device.free    = gralloc_free;
    915         dev->allocListHead  = NULL;
    916         pthread_mutex_init(&dev->lock, NULL);
    917 
    918         *device = &dev->device.common;
    919         status = 0;
    920     }
    921     else if (!strcmp(name, GRALLOC_HARDWARE_FB0)) {
    922 
    923         // return error if connection with host can not be established
    924         DEFINE_AND_VALIDATE_HOST_CONNECTION;
    925 
    926         //
    927         // Query the host for Framebuffer attributes
    928         //
    929         D("gralloc: query Frabuffer attribs\n");
    930         EGLint width = rcEnc->rcGetFBParam(rcEnc, FB_WIDTH);
    931         D("gralloc: width=%d\n", width);
    932         EGLint height = rcEnc->rcGetFBParam(rcEnc, FB_HEIGHT);
    933         D("gralloc: height=%d\n", height);
    934         EGLint xdpi = rcEnc->rcGetFBParam(rcEnc, FB_XDPI);
    935         D("gralloc: xdpi=%d\n", xdpi);
    936         EGLint ydpi = rcEnc->rcGetFBParam(rcEnc, FB_YDPI);
    937         D("gralloc: ydpi=%d\n", ydpi);
    938         EGLint fps = rcEnc->rcGetFBParam(rcEnc, FB_FPS);
    939         D("gralloc: fps=%d\n", fps);
    940         EGLint min_si = rcEnc->rcGetFBParam(rcEnc, FB_MIN_SWAP_INTERVAL);
    941         D("gralloc: min_swap=%d\n", min_si);
    942         EGLint max_si = rcEnc->rcGetFBParam(rcEnc, FB_MAX_SWAP_INTERVAL);
    943         D("gralloc: max_swap=%d\n", max_si);
    944 
    945         //
    946         // Allocate memory for the framebuffer device
    947         //
    948         fb_device_t *dev;
    949         dev = (fb_device_t*)malloc(sizeof(fb_device_t));
    950         if (NULL == dev) {
    951             return -ENOMEM;
    952         }
    953         memset(dev, 0, sizeof(fb_device_t));
    954 
    955         // Initialize our device structure
    956         //
    957         dev->device.common.tag = HARDWARE_DEVICE_TAG;
    958         dev->device.common.version = 0;
    959         dev->device.common.module = const_cast<hw_module_t*>(module);
    960         dev->device.common.close = fb_close;
    961         dev->device.setSwapInterval = fb_setSwapInterval;
    962         dev->device.post            = fb_post;
    963         dev->device.setUpdateRect   = 0; //fb_setUpdateRect;
    964         dev->device.compositionComplete = fb_compositionComplete; //XXX: this is a dummy
    965 
    966         const_cast<uint32_t&>(dev->device.flags) = 0;
    967         const_cast<uint32_t&>(dev->device.width) = width;
    968         const_cast<uint32_t&>(dev->device.height) = height;
    969         const_cast<int&>(dev->device.stride) = width;
    970         const_cast<int&>(dev->device.format) = HAL_PIXEL_FORMAT_RGBA_8888;
    971         const_cast<float&>(dev->device.xdpi) = xdpi;
    972         const_cast<float&>(dev->device.ydpi) = ydpi;
    973         const_cast<float&>(dev->device.fps) = fps;
    974         const_cast<int&>(dev->device.minSwapInterval) = min_si;
    975         const_cast<int&>(dev->device.maxSwapInterval) = max_si;
    976         *device = &dev->device.common;
    977 
    978         status = 0;
    979     }
    980 
    981     return status;
    982 }
    983 
    984 //
    985 // define the HMI symbol - our module interface
    986 //
    987 static struct hw_module_methods_t gralloc_module_methods = {
    988         open: gralloc_device_open
    989 };
    990 
    991 struct private_module_t HAL_MODULE_INFO_SYM = {
    992     base: {
    993         common: {
    994             tag: HARDWARE_MODULE_TAG,
    995             module_api_version: GRALLOC_MODULE_API_VERSION_0_2,
    996             hal_api_version: 0,
    997             id: GRALLOC_HARDWARE_MODULE_ID,
    998             name: "Graphics Memory Allocator Module",
    999             author: "The Android Open Source Project",
   1000             methods: &gralloc_module_methods,
   1001             dso: NULL,
   1002             reserved: {0, }
   1003         },
   1004         registerBuffer: gralloc_register_buffer,
   1005         unregisterBuffer: gralloc_unregister_buffer,
   1006         lock: gralloc_lock,
   1007         unlock: gralloc_unlock,
   1008         perform: NULL,
   1009         lock_ycbcr: gralloc_lock_ycbcr,
   1010     }
   1011 };
   1012 
   1013 /* This function is called once to detect whether the emulator supports
   1014  * GPU emulation (this is done by looking at the qemu.gles kernel
   1015  * parameter, which must be > 0 if this is the case).
   1016  *
   1017  * If not, then load gralloc.default instead as a fallback.
   1018  */
   1019 static void
   1020 fallback_init(void)
   1021 {
   1022     char  prop[PROPERTY_VALUE_MAX];
   1023     void* module;
   1024 
   1025     property_get("ro.kernel.qemu.gles", prop, "0");
   1026     if (atoi(prop) > 0) {
   1027         return;
   1028     }
   1029     ALOGD("Emulator without GPU emulation detected.");
   1030 #if __LP64__
   1031     module = dlopen("/system/lib64/hw/gralloc.default.so", RTLD_LAZY|RTLD_LOCAL);
   1032 #else
   1033     module = dlopen("/system/lib/hw/gralloc.default.so", RTLD_LAZY|RTLD_LOCAL);
   1034 #endif
   1035     if (module != NULL) {
   1036         sFallback = reinterpret_cast<gralloc_module_t*>(dlsym(module, HAL_MODULE_INFO_SYM_AS_STR));
   1037         if (sFallback == NULL) {
   1038             dlclose(module);
   1039         }
   1040     }
   1041     if (sFallback == NULL) {
   1042         ALOGE("Could not find software fallback module!?");
   1043     }
   1044 }
   1045