Home | History | Annotate | Download | only in HAL3
      1 /* Copyright (c) 2012-2014, The Linux Foundataion. All rights reserved.
      2  *
      3  * Redistribution and use in source and binary forms, with or without
      4  * modification, are permitted provided that the following conditions are
      5  * met:
      6  *     * Redistributions of source code must retain the above copyright
      7  *       notice, this list of conditions and the following disclaimer.
      8  *     * Redistributions in binary form must reproduce the above
      9  *       copyright notice, this list of conditions and the following
     10  *       disclaimer in the documentation and/or other materials provided
     11  *       with the distribution.
     12  *     * Neither the name of The Linux Foundation nor the names of its
     13  *       contributors may be used to endorse or promote products derived
     14  *       from this software without specific prior written permission.
     15  *
     16  * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
     17  * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
     18  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
     19  * ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
     20  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
     21  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
     22  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
     23  * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
     24  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
     25  * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
     26  * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     27  *
     28  */
     29 
     30 #define LOG_TAG "QCameraHWI_Mem"
     31 
     32 #include <string.h>
     33 #include <fcntl.h>
     34 #include <sys/mman.h>
     35 #include <utils/Log.h>
     36 #include <utils/Errors.h>
     37 #include <gralloc_priv.h>
     38 #include "QCamera3Mem.h"
     39 #include "QCamera3HWI.h"
     40 
     41 extern "C" {
     42 #include <mm_camera_interface.h>
     43 }
     44 
     45 using namespace android;
     46 
     47 namespace qcamera {
     48 
     49 // QCaemra2Memory base class
     50 
     51 /*===========================================================================
     52  * FUNCTION   : QCamera3Memory
     53  *
     54  * DESCRIPTION: default constructor of QCamera3Memory
     55  *
     56  * PARAMETERS : none
     57  *
     58  * RETURN     : None
     59  *==========================================================================*/
     60 QCamera3Memory::QCamera3Memory()
     61 {
     62     mBufferCount = 0;
     63     for (int i = 0; i < MM_CAMERA_MAX_NUM_FRAMES; i++) {
     64         mMemInfo[i].fd = 0;
     65         mMemInfo[i].main_ion_fd = 0;
     66         mMemInfo[i].handle = 0;
     67         mMemInfo[i].size = 0;
     68     }
     69 }
     70 
     71 /*===========================================================================
     72  * FUNCTION   : ~QCamera3Memory
     73  *
     74  * DESCRIPTION: deconstructor of QCamera3Memory
     75  *
     76  * PARAMETERS : none
     77  *
     78  * RETURN     : None
     79  *==========================================================================*/
     80 QCamera3Memory::~QCamera3Memory()
     81 {
     82 }
     83 
     84 /*===========================================================================
     85  * FUNCTION   : cacheOpsInternal
     86  *
     87  * DESCRIPTION: ion related memory cache operations
     88  *
     89  * PARAMETERS :
     90  *   @index   : index of the buffer
     91  *   @cmd     : cache ops command
     92  *   @vaddr   : ptr to the virtual address
     93  *
     94  * RETURN     : int32_t type of status
     95  *              NO_ERROR  -- success
     96  *              none-zero failure code
     97  *==========================================================================*/
     98 int QCamera3Memory::cacheOpsInternal(int index, unsigned int cmd, void *vaddr)
     99 {
    100     struct ion_flush_data cache_inv_data;
    101     struct ion_custom_data custom_data;
    102     int ret = OK;
    103 
    104     if (index >= mBufferCount) {
    105         ALOGE("%s: index %d out of bound [0, %d)", __func__, index, mBufferCount);
    106         return BAD_INDEX;
    107     }
    108 
    109     memset(&cache_inv_data, 0, sizeof(cache_inv_data));
    110     memset(&custom_data, 0, sizeof(custom_data));
    111     cache_inv_data.vaddr = vaddr;
    112     cache_inv_data.fd = mMemInfo[index].fd;
    113     cache_inv_data.handle = mMemInfo[index].handle;
    114     cache_inv_data.length = mMemInfo[index].size;
    115     custom_data.cmd = cmd;
    116     custom_data.arg = (unsigned long)&cache_inv_data;
    117 
    118     CDBG("%s: addr = %p, fd = %d, handle = %lx length = %d, ION Fd = %d",
    119          __func__, cache_inv_data.vaddr, cache_inv_data.fd,
    120          (unsigned long)cache_inv_data.handle, cache_inv_data.length,
    121          mMemInfo[index].main_ion_fd);
    122     ret = ioctl(mMemInfo[index].main_ion_fd, ION_IOC_CUSTOM, &custom_data);
    123     if (ret < 0)
    124         ALOGE("%s: Cache Invalidate failed: %s\n", __func__, strerror(errno));
    125 
    126     return ret;
    127 }
    128 
    129 /*===========================================================================
    130  * FUNCTION   : getFd
    131  *
    132  * DESCRIPTION: return file descriptor of the indexed buffer
    133  *
    134  * PARAMETERS :
    135  *   @index   : index of the buffer
    136  *
    137  * RETURN     : file descriptor
    138  *==========================================================================*/
    139 int QCamera3Memory::getFd(int index) const
    140 {
    141     if (index >= mBufferCount)
    142         return BAD_INDEX;
    143 
    144     return mMemInfo[index].fd;
    145 }
    146 
    147 /*===========================================================================
    148  * FUNCTION   : getSize
    149  *
    150  * DESCRIPTION: return buffer size of the indexed buffer
    151  *
    152  * PARAMETERS :
    153  *   @index   : index of the buffer
    154  *
    155  * RETURN     : buffer size
    156  *==========================================================================*/
    157 int QCamera3Memory::getSize(int index) const
    158 {
    159     if (index >= mBufferCount)
    160         return BAD_INDEX;
    161 
    162     return (int)mMemInfo[index].size;
    163 }
    164 
    165 /*===========================================================================
    166  * FUNCTION   : getCnt
    167  *
    168  * DESCRIPTION: query number of buffers allocated
    169  *
    170  * PARAMETERS : none
    171  *
    172  * RETURN     : number of buffers allocated
    173  *==========================================================================*/
    174 int QCamera3Memory::getCnt() const
    175 {
    176     return mBufferCount;
    177 }
    178 
    179 /*===========================================================================
    180  * FUNCTION   : getBufDef
    181  *
    182  * DESCRIPTION: query detailed buffer information
    183  *
    184  * PARAMETERS :
    185  *   @offset  : [input] frame buffer offset
    186  *   @bufDef  : [output] reference to struct to store buffer definition
    187  *   @index   : [input] index of the buffer
    188  *
    189  * RETURN     : int32_t type of status
    190  *              NO_ERROR  -- success
    191  *              none-zero failure code
    192  *==========================================================================*/
    193 int32_t QCamera3Memory::getBufDef(const cam_frame_len_offset_t &offset,
    194         mm_camera_buf_def_t &bufDef, int index) const
    195 {
    196     if (!mBufferCount) {
    197         ALOGE("Memory not allocated");
    198         return NO_INIT;
    199     }
    200 
    201     bufDef.fd = mMemInfo[index].fd;
    202     bufDef.frame_len = mMemInfo[index].size;
    203     bufDef.mem_info = (void *)this;
    204     bufDef.num_planes = offset.num_planes;
    205     bufDef.buffer = getPtr(index);
    206     bufDef.buf_idx = index;
    207 
    208     /* Plane 0 needs to be set separately. Set other planes in a loop */
    209     bufDef.planes[0].length = offset.mp[0].len;
    210     bufDef.planes[0].m.userptr = mMemInfo[index].fd;
    211     bufDef.planes[0].data_offset = offset.mp[0].offset;
    212     bufDef.planes[0].reserved[0] = 0;
    213     for (int i = 1; i < bufDef.num_planes; i++) {
    214          bufDef.planes[i].length = offset.mp[i].len;
    215          bufDef.planes[i].m.userptr = mMemInfo[i].fd;
    216          bufDef.planes[i].data_offset = offset.mp[i].offset;
    217          bufDef.planes[i].reserved[0] =
    218                  bufDef.planes[i-1].reserved[0] +
    219                  bufDef.planes[i-1].length;
    220     }
    221 
    222     return NO_ERROR;
    223 }
    224 
    225 /*===========================================================================
    226  * FUNCTION   : QCamera3HeapMemory
    227  *
    228  * DESCRIPTION: constructor of QCamera3HeapMemory for ion memory used internally in HAL
    229  *
    230  * PARAMETERS : none
    231  *
    232  * RETURN     : none
    233  *==========================================================================*/
    234 QCamera3HeapMemory::QCamera3HeapMemory()
    235     : QCamera3Memory()
    236 {
    237     for (int i = 0; i < MM_CAMERA_MAX_NUM_FRAMES; i ++)
    238         mPtr[i] = NULL;
    239 }
    240 
    241 /*===========================================================================
    242  * FUNCTION   : ~QCamera3HeapMemory
    243  *
    244  * DESCRIPTION: deconstructor of QCamera3HeapMemory
    245  *
    246  * PARAMETERS : none
    247  *
    248  * RETURN     : none
    249  *==========================================================================*/
    250 QCamera3HeapMemory::~QCamera3HeapMemory()
    251 {
    252 }
    253 
    254 /*===========================================================================
    255  * FUNCTION   : alloc
    256  *
    257  * DESCRIPTION: allocate requested number of buffers of certain size
    258  *
    259  * PARAMETERS :
    260  *   @count   : number of buffers to be allocated
    261  *   @size    : lenght of the buffer to be allocated
    262  *   @heap_id : heap id to indicate where the buffers will be allocated from
    263  *
    264  * RETURN     : int32_t type of status
    265  *              NO_ERROR  -- success
    266  *              none-zero failure code
    267  *==========================================================================*/
    268 int QCamera3HeapMemory::alloc(int count, int size, int heap_id)
    269 {
    270     int rc = OK;
    271     if (count > MM_CAMERA_MAX_NUM_FRAMES) {
    272         ALOGE("Buffer count %d out of bound. Max is %d", count, MM_CAMERA_MAX_NUM_FRAMES);
    273         return BAD_INDEX;
    274     }
    275     if (mBufferCount) {
    276         ALOGE("Allocating a already allocated heap memory");
    277         return INVALID_OPERATION;
    278     }
    279 
    280     for (int i = 0; i < count; i ++) {
    281         rc = allocOneBuffer(mMemInfo[i], heap_id, size);
    282         if (rc < 0) {
    283             ALOGE("AllocateIonMemory failed");
    284             for (int j = i-1; j >= 0; j--)
    285                 deallocOneBuffer(mMemInfo[j]);
    286             break;
    287         }
    288     }
    289     return rc;
    290 }
    291 
    292 /*===========================================================================
    293  * FUNCTION   : dealloc
    294  *
    295  * DESCRIPTION: deallocate buffers
    296  *
    297  * PARAMETERS : none
    298  *
    299  * RETURN     : none
    300  *==========================================================================*/
    301 void QCamera3HeapMemory::dealloc()
    302 {
    303     for (int i = 0; i < mBufferCount; i++)
    304         deallocOneBuffer(mMemInfo[i]);
    305 }
    306 
    307 /*===========================================================================
    308  * FUNCTION   : allocOneBuffer
    309  *
    310  * DESCRIPTION: impl of allocating one buffers of certain size
    311  *
    312  * PARAMETERS :
    313  *   @memInfo : [output] reference to struct to store additional memory allocation info
    314  *   @heap    : [input] heap id to indicate where the buffers will be allocated from
    315  *   @size    : [input] lenght of the buffer to be allocated
    316  *
    317  * RETURN     : int32_t type of status
    318  *              NO_ERROR  -- success
    319  *              none-zero failure code
    320  *==========================================================================*/
    321 int QCamera3HeapMemory::allocOneBuffer(QCamera3MemInfo &memInfo, int heap_id, int size)
    322 {
    323     int rc = OK;
    324     struct ion_handle_data handle_data;
    325     struct ion_allocation_data alloc;
    326     struct ion_fd_data ion_info_fd;
    327     int main_ion_fd = 0;
    328 
    329     main_ion_fd = open("/dev/ion", O_RDONLY);
    330     if (main_ion_fd < 0) {
    331         ALOGE("Ion dev open failed: %s\n", strerror(errno));
    332         goto ION_OPEN_FAILED;
    333     }
    334 
    335     memset(&alloc, 0, sizeof(alloc));
    336     alloc.len = size;
    337     /* to make it page size aligned */
    338     alloc.len = (alloc.len + 4095) & (~4095);
    339     alloc.align = 4096;
    340     alloc.flags = ION_FLAG_CACHED;
    341     alloc.heap_mask = heap_id;
    342     rc = ioctl(main_ion_fd, ION_IOC_ALLOC, &alloc);
    343     if (rc < 0) {
    344         ALOGE("ION allocation for len %d failed: %s\n", alloc.len,
    345             strerror(errno));
    346         goto ION_ALLOC_FAILED;
    347     }
    348 
    349     memset(&ion_info_fd, 0, sizeof(ion_info_fd));
    350     ion_info_fd.handle = alloc.handle;
    351     rc = ioctl(main_ion_fd, ION_IOC_SHARE, &ion_info_fd);
    352     if (rc < 0) {
    353         ALOGE("ION map failed %s\n", strerror(errno));
    354         goto ION_MAP_FAILED;
    355     }
    356 
    357     memInfo.main_ion_fd = main_ion_fd;
    358     memInfo.fd = ion_info_fd.fd;
    359     memInfo.handle = ion_info_fd.handle;
    360     memInfo.size = alloc.len;
    361     return OK;
    362 
    363 ION_MAP_FAILED:
    364     memset(&handle_data, 0, sizeof(handle_data));
    365     handle_data.handle = ion_info_fd.handle;
    366     ioctl(main_ion_fd, ION_IOC_FREE, &handle_data);
    367 ION_ALLOC_FAILED:
    368     close(main_ion_fd);
    369 ION_OPEN_FAILED:
    370     return NO_MEMORY;
    371 }
    372 
    373 /*===========================================================================
    374  * FUNCTION   : deallocOneBuffer
    375  *
    376  * DESCRIPTION: impl of deallocating one buffers
    377  *
    378  * PARAMETERS :
    379  *   @memInfo : reference to struct that stores additional memory allocation info
    380  *
    381  * RETURN     : none
    382  *==========================================================================*/
    383 void QCamera3HeapMemory::deallocOneBuffer(QCamera3MemInfo &memInfo)
    384 {
    385     struct ion_handle_data handle_data;
    386 
    387     if (memInfo.fd > 0) {
    388         close(memInfo.fd);
    389         memInfo.fd = 0;
    390     }
    391 
    392     if (memInfo.main_ion_fd > 0) {
    393         memset(&handle_data, 0, sizeof(handle_data));
    394         handle_data.handle = memInfo.handle;
    395         ioctl(memInfo.main_ion_fd, ION_IOC_FREE, &handle_data);
    396         close(memInfo.main_ion_fd);
    397         memInfo.main_ion_fd = 0;
    398     }
    399     memInfo.handle = 0;
    400     memInfo.size = 0;
    401 }
    402 
    403 /*===========================================================================
    404  * FUNCTION   : getPtr
    405  *
    406  * DESCRIPTION: return buffer pointer
    407  *
    408  * PARAMETERS :
    409  *   @index   : index of the buffer
    410  *
    411  * RETURN     : buffer ptr
    412  *==========================================================================*/
    413 void *QCamera3HeapMemory::getPtr(int index) const
    414 {
    415     if (index >= mBufferCount) {
    416         ALOGE("index out of bound");
    417         return (void *)BAD_INDEX;
    418     }
    419     return mPtr[index];
    420 }
    421 
    422 /*===========================================================================
    423  * FUNCTION   : allocate
    424  *
    425  * DESCRIPTION: allocate requested number of buffers of certain size
    426  *
    427  * PARAMETERS :
    428  *   @count   : number of buffers to be allocated
    429  *   @size    : lenght of the buffer to be allocated
    430  *   @queueAll: whether to queue all allocated buffers at the beginning
    431  *
    432  * RETURN     : int32_t type of status
    433  *              NO_ERROR  -- success
    434  *              none-zero failure code
    435  *==========================================================================*/
    436 int QCamera3HeapMemory::allocate(int count, int size, bool queueAll)
    437 {
    438     int heap_mask = 0x1 << ION_IOMMU_HEAP_ID;
    439     int rc = alloc(count, size, heap_mask);
    440     if (rc < 0)
    441         return rc;
    442 
    443     for (int i = 0; i < count; i ++) {
    444         void *vaddr = mmap(NULL,
    445                     mMemInfo[i].size,
    446                     PROT_READ | PROT_WRITE,
    447                     MAP_SHARED,
    448                     mMemInfo[i].fd, 0);
    449         if (vaddr == MAP_FAILED) {
    450             for (int j = i-1; j >= 0; j --) {
    451                 munmap(mPtr[i], mMemInfo[i].size);
    452                 rc = NO_MEMORY;
    453                 break;
    454             }
    455         } else
    456             mPtr[i] = vaddr;
    457     }
    458     if (rc == 0)
    459         mBufferCount = count;
    460 
    461     mQueueAll = queueAll;
    462     return OK;
    463 }
    464 
    465 /*===========================================================================
    466  * FUNCTION   : deallocate
    467  *
    468  * DESCRIPTION: deallocate buffers
    469  *
    470  * PARAMETERS : none
    471  *
    472  * RETURN     : none
    473  *==========================================================================*/
    474 void QCamera3HeapMemory::deallocate()
    475 {
    476     for (int i = 0; i < mBufferCount; i++) {
    477         munmap(mPtr[i], mMemInfo[i].size);
    478         mPtr[i] = NULL;
    479     }
    480     dealloc();
    481     mBufferCount = 0;
    482 }
    483 
    484 /*===========================================================================
    485  * FUNCTION   : cacheOps
    486  *
    487  * DESCRIPTION: ion related memory cache operations
    488  *
    489  * PARAMETERS :
    490  *   @index   : index of the buffer
    491  *   @cmd     : cache ops command
    492  *
    493  * RETURN     : int32_t type of status
    494  *              NO_ERROR  -- success
    495  *              none-zero failure code
    496  *==========================================================================*/
    497 int QCamera3HeapMemory::cacheOps(int index, unsigned int cmd)
    498 {
    499     if (index >= mBufferCount)
    500         return BAD_INDEX;
    501     return cacheOpsInternal(index, cmd, mPtr[index]);
    502 }
    503 
    504 /*===========================================================================
    505  * FUNCTION   : getRegFlags
    506  *
    507  * DESCRIPTION: query initial reg flags
    508  *
    509  * PARAMETERS :
    510  *   @regFlags: initial reg flags of the allocated buffers
    511  *
    512  * RETURN     : int32_t type of status
    513  *              NO_ERROR  -- success
    514  *              none-zero failure code
    515  *==========================================================================*/
    516 int QCamera3HeapMemory::getRegFlags(uint8_t * regFlags) const
    517 {
    518     int i;
    519     for (i = 0; i < mBufferCount; i ++)
    520         regFlags[i] = (mQueueAll ? 1 : 0);
    521     return NO_ERROR;
    522 }
    523 
    524 /*===========================================================================
    525  * FUNCTION   : getMatchBufIndex
    526  *
    527  * DESCRIPTION: query buffer index by object ptr
    528  *
    529  * PARAMETERS :
    530  *   @object  : object ptr
    531  *
    532  * RETURN     : buffer index if match found,
    533  *              -1 if failed
    534  *==========================================================================*/
    535 int QCamera3HeapMemory::getMatchBufIndex(void * /*object*/)
    536 {
    537 
    538 /*
    539     TODO for HEAP memory type, would there be an equivalent requirement?
    540 
    541     int index = -1;
    542     buffer_handle_t *key = (buffer_handle_t*) object;
    543     if (!key) {
    544         return BAD_VALUE;
    545     }
    546     for (int i = 0; i < mBufferCount; i++) {
    547         if (mBufferHandle[i] == key) {
    548             index = i;
    549             break;
    550         }
    551     }
    552     return index;
    553 */
    554     ALOGE("%s: FATAL: Not supposed to come here", __func__);
    555     return -1;
    556 }
    557 
    558 /*===========================================================================
    559  * FUNCTION   : QCamera3GrallocMemory
    560  *
    561  * DESCRIPTION: constructor of QCamera3GrallocMemory
    562  *              preview stream buffers are allocated from gralloc native_windoe
    563  *
    564  * PARAMETERS :
    565  *   @getMemory : camera memory request ops table
    566  *
    567  * RETURN     : none
    568  *==========================================================================*/
    569 QCamera3GrallocMemory::QCamera3GrallocMemory()
    570         : QCamera3Memory(),
    571           mColorSpace(ITU_R_601)
    572 {
    573     for (int i = 0; i < MM_CAMERA_MAX_NUM_FRAMES; i ++) {
    574         mBufferHandle[i] = NULL;
    575         mPrivateHandle[i] = NULL;
    576         mCurrentFrameNumbers[i] = -1;
    577     }
    578 }
    579 
    580 /*===========================================================================
    581  * FUNCTION   : ~QCamera3GrallocMemory
    582  *
    583  * DESCRIPTION: deconstructor of QCamera3GrallocMemory
    584  *
    585  * PARAMETERS : none
    586  *
    587  * RETURN     : none
    588  *==========================================================================*/
    589 QCamera3GrallocMemory::~QCamera3GrallocMemory()
    590 {
    591 }
    592 
    593 /*===========================================================================
    594  * FUNCTION   : registerBuffer
    595  *
    596  * DESCRIPTION: registers frameworks-allocated gralloc buffer_handle_t
    597  *
    598  * PARAMETERS :
    599  *   @buffers : buffer_handle_t pointer
    600  *
    601  * RETURN     : int32_t type of status
    602  *              NO_ERROR  -- success
    603  *              none-zero failure code
    604  *==========================================================================*/
    605 int QCamera3GrallocMemory::registerBuffer(buffer_handle_t *buffer)
    606 {
    607     status_t ret = NO_ERROR;
    608     struct ion_fd_data ion_info_fd;
    609     void *vaddr = NULL;
    610     CDBG(" %s : E ", __FUNCTION__);
    611 
    612     memset(&ion_info_fd, 0, sizeof(ion_info_fd));
    613 
    614     if (mBufferCount >= (MM_CAMERA_MAX_NUM_FRAMES - 1)) {
    615         ALOGE("%s: Number of buffers %d greater than what's supported %d",
    616             __func__, mBufferCount, MM_CAMERA_MAX_NUM_FRAMES);
    617         return -EINVAL;
    618     }
    619 
    620     if (0 <= getMatchBufIndex((void *) buffer)) {
    621         ALOGV("%s: Buffer already registered", __func__);
    622         return ALREADY_EXISTS;
    623     }
    624 
    625     mBufferHandle[mBufferCount] = buffer;
    626     mPrivateHandle[mBufferCount] =
    627         (struct private_handle_t *)(*mBufferHandle[mBufferCount]);
    628 
    629     setMetaData(mPrivateHandle[mBufferCount], UPDATE_COLOR_SPACE, &mColorSpace);
    630 
    631     mMemInfo[mBufferCount].main_ion_fd = open("/dev/ion", O_RDONLY);
    632     if (mMemInfo[mBufferCount].main_ion_fd < 0) {
    633         ALOGE("%s: failed: could not open ion device", __func__);
    634         ret = NO_MEMORY;
    635         goto end;
    636     } else {
    637         ion_info_fd.fd = mPrivateHandle[mBufferCount]->fd;
    638         if (ioctl(mMemInfo[mBufferCount].main_ion_fd,
    639                   ION_IOC_IMPORT, &ion_info_fd) < 0) {
    640             ALOGE("%s: ION import failed\n", __func__);
    641             close(mMemInfo[mBufferCount].main_ion_fd);
    642             ret = NO_MEMORY;
    643             goto end;
    644         }
    645     }
    646     ALOGV("%s: idx = %d, fd = %d, size = %d, offset = %d",
    647             __func__, mBufferCount, mPrivateHandle[mBufferCount]->fd,
    648             mPrivateHandle[mBufferCount]->size,
    649             mPrivateHandle[mBufferCount]->offset);
    650     mMemInfo[mBufferCount].fd =
    651             mPrivateHandle[mBufferCount]->fd;
    652     mMemInfo[mBufferCount].size =
    653             mPrivateHandle[mBufferCount]->size;
    654     mMemInfo[mBufferCount].handle = ion_info_fd.handle;
    655 
    656     vaddr = mmap(NULL,
    657             mMemInfo[mBufferCount].size,
    658             PROT_READ | PROT_WRITE,
    659             MAP_SHARED,
    660             mMemInfo[mBufferCount].fd, 0);
    661     if (vaddr == MAP_FAILED) {
    662         ret = NO_MEMORY;
    663     } else {
    664         mPtr[mBufferCount] = vaddr;
    665         mBufferCount++;
    666     }
    667 
    668 end:
    669     CDBG(" %s : X ",__func__);
    670     return ret;
    671 }
    672 
    673 /*===========================================================================
    674  * FUNCTION   : unregisterBuffers
    675  *
    676  * DESCRIPTION: unregister buffers
    677  *
    678  * PARAMETERS : none
    679  *
    680  * RETURN     : none
    681  *==========================================================================*/
    682 void QCamera3GrallocMemory::unregisterBuffers()
    683 {
    684     CDBG("%s: E ", __FUNCTION__);
    685 
    686     for (int cnt = 0; cnt < mBufferCount; cnt++) {
    687         munmap(mPtr[cnt], mMemInfo[cnt].size);
    688         mPtr[cnt] = NULL;
    689 
    690         struct ion_handle_data ion_handle;
    691         memset(&ion_handle, 0, sizeof(ion_handle));
    692         ion_handle.handle = mMemInfo[cnt].handle;
    693         if (ioctl(mMemInfo[cnt].main_ion_fd, ION_IOC_FREE, &ion_handle) < 0) {
    694             ALOGE("ion free failed");
    695         }
    696         close(mMemInfo[cnt].main_ion_fd);
    697         CDBG_HIGH("put buffer %d successfully", cnt);
    698     }
    699     mBufferCount = 0;
    700     CDBG(" %s : X ",__FUNCTION__);
    701 }
    702 
    703 /*===========================================================================
    704  * FUNCTION   : markFrameNumber
    705  *
    706  * DESCRIPTION: We use this function from the request call path to mark the
    707  *              buffers with the frame number they are intended for this info
    708  *              is used later when giving out callback & it is duty of PP to
    709  *              ensure that data for that particular frameNumber/Request is
    710  *              written to this buffer.
    711  * PARAMETERS :
    712  *   @index   : index of the buffer
    713  *   @frame#  : Frame number from the framework
    714  *
    715  * RETURN     : int32_t type of status
    716  *              NO_ERROR  -- success
    717  *              none-zero failure code
    718  *==========================================================================*/
    719 int32_t QCamera3GrallocMemory::markFrameNumber(int index, uint32_t frameNumber)
    720 {
    721     if(index >= mBufferCount || index >= MM_CAMERA_MAX_NUM_FRAMES) {
    722         ALOGE("%s: Index out of bounds",__func__);
    723         return BAD_INDEX;
    724     }
    725     mCurrentFrameNumbers[index] = frameNumber;
    726     return NO_ERROR;
    727 }
    728 
    729 /*===========================================================================
    730  * FUNCTION   : getFrameNumber
    731  *
    732  * DESCRIPTION: We use this to fetch the frameNumber for the request with which
    733  *              this buffer was given to HAL
    734  *
    735  *
    736  * PARAMETERS :
    737  *   @index   : index of the buffer
    738  *
    739  * RETURN     : int32_t frameNumber
    740  *              postive/zero  -- success
    741  *              negetive failure
    742  *==========================================================================*/
    743 int32_t QCamera3GrallocMemory::getFrameNumber(int index)
    744 {
    745     if(index >= mBufferCount || index >= MM_CAMERA_MAX_NUM_FRAMES) {
    746         ALOGE("%s: Index out of bounds",__func__);
    747         return -1;
    748     }
    749 
    750     return mCurrentFrameNumbers[index];
    751 }
    752 
    753 /*===========================================================================
    754  * FUNCTION   : cacheOps
    755  *
    756  * DESCRIPTION: ion related memory cache operations
    757  *
    758  * PARAMETERS :
    759  *   @index   : index of the buffer
    760  *   @cmd     : cache ops command
    761  *
    762  * RETURN     : int32_t type of status
    763  *              NO_ERROR  -- success
    764  *              none-zero failure code
    765  *==========================================================================*/
    766 int QCamera3GrallocMemory::cacheOps(int index, unsigned int cmd)
    767 {
    768     if (index >= mBufferCount)
    769         return BAD_INDEX;
    770     return cacheOpsInternal(index, cmd, mPtr[index]);
    771 }
    772 
    773 /*===========================================================================
    774  * FUNCTION   : getRegFlags
    775  *
    776  * DESCRIPTION: query initial reg flags
    777  *
    778  * PARAMETERS :
    779  *   @regFlags: initial reg flags of the allocated buffers
    780  *
    781  * RETURN     : int32_t type of status
    782  *              NO_ERROR  -- success
    783  *              none-zero failure code
    784  *==========================================================================*/
    785 int QCamera3GrallocMemory::getRegFlags(uint8_t *regFlags) const
    786 {
    787     int i;
    788     for (i = 0; i < mBufferCount; i ++)
    789         regFlags[i] = 0;
    790     return NO_ERROR;
    791 }
    792 
    793 /*===========================================================================
    794  * FUNCTION   : getMatchBufIndex
    795  *
    796  * DESCRIPTION: query buffer index by object ptr
    797  *
    798  * PARAMETERS :
    799  *   @opaque  : opaque ptr
    800  *
    801  * RETURN     : buffer index if match found,
    802  *              -1 if failed
    803  *==========================================================================*/
    804 int QCamera3GrallocMemory::getMatchBufIndex(void *object)
    805 {
    806     int index = -1;
    807     buffer_handle_t *key = (buffer_handle_t*) object;
    808     if (!key) {
    809         return BAD_VALUE;
    810     }
    811     for (int i = 0; i < mBufferCount; i++) {
    812         if (mBufferHandle[i] == key) {
    813             index = i;
    814             break;
    815         }
    816     }
    817     return index;
    818 }
    819 
    820 /*===========================================================================
    821  * FUNCTION   : getPtr
    822  *
    823  * DESCRIPTION: return buffer pointer
    824  *
    825  * PARAMETERS :
    826  *   @index   : index of the buffer
    827  *
    828  * RETURN     : buffer ptr
    829  *==========================================================================*/
    830 void *QCamera3GrallocMemory::getPtr(int index) const
    831 {
    832     if (index >= mBufferCount) {
    833         ALOGE("index out of bound");
    834         return (void *)BAD_INDEX;
    835     }
    836     return mPtr[index];
    837 }
    838 
    839 /*===========================================================================
    840  * FUNCTION   : getBufferHandle
    841  *
    842  * DESCRIPTION: return framework pointer
    843  *
    844  * PARAMETERS :
    845  *   @index   : index of the buffer
    846  *
    847  * RETURN     : buffer ptr if match found
    848                 NULL if failed
    849  *==========================================================================*/
    850 void *QCamera3GrallocMemory::getBufferHandle(int index)
    851 {
    852     if (index >= mBufferCount) {
    853         ALOGE("index out of bound");
    854         return NULL;
    855     }
    856     return mBufferHandle[index];
    857 }
    858 
    859 /*===========================================================================
    860  * FUNCTION   : setColorSpace
    861  *
    862  * DESCRIPTION: Set color space based on capture intent
    863  *
    864  * PARAMETERS :
    865  *   @intent   : capture intent
    866  *
    867  * RETURN     : int32_t type of status
    868  *              NO_ERROR -- successs
    869  *              non-zero failure ccde
    870  *==========================================================================*/
    871 int32_t QCamera3GrallocMemory::setColorSpace(uint8_t intent)
    872 {
    873     int32_t rc = NO_ERROR;
    874 
    875     switch (intent) {
    876     case ANDROID_CONTROL_CAPTURE_INTENT_VIDEO_RECORD:
    877     case ANDROID_CONTROL_CAPTURE_INTENT_VIDEO_SNAPSHOT:
    878         mColorSpace = ITU_R_709;
    879         break;
    880     default:
    881         mColorSpace = ITU_R_601;
    882         break;
    883     }
    884     ALOGI("%s: setting colorSpace to %d for capture intent %d",
    885             __func__, mColorSpace, intent);
    886 
    887     return rc;
    888 }
    889 
    890 }; //namespace qcamera
    891