示例#1
0
PmemPool::~PmemPool()
{
    ALOGI("%s: %s E", __FUNCTION__, mName);
#if 0
    if (mHeap != NULL) {
        // Unregister preview buffers with the camera drivers.
        //  Only Unregister the preview, snapshot and thumbnail
        //  buffers with the kernel.
        if( (strcmp("postview", mName) != 0) ){
            int num_buffers = mNumBuffers;
            if(!strcmp("preview", mName)) num_buffers = PREVIEW_BUFFER_COUNT;
            for (int cnt = 0; cnt < num_buffers; ++cnt) {
                register_buf(mBufferSize,
                         mFrameSize,
                         mCbCrOffset,
                         myOffset,
                         mHeap->getHeapID(),
                         mAlignedBufferSize * cnt,
                         (uint8_t *)mHeap->base() + mAlignedBufferSize * cnt,
                         mPmemType,
                         false,
                         false /* unregister */);
            }
        }
    }
    mMMCameraDLRef.clear();
#endif
    ALOGI("%s: %s X", __FUNCTION__, mName);
}
/*===========================================================================

Function            : apr_pmem_free_ion

Description         : Free ion memory

Input parameter(s)  : Ion structure to the allocated memory block

Output parameter(s) : None

=========================================================================== */
void apr_pmem_free_ion(struct mmap_info_ion mapion) {
  int32_t rc = 0;
  struct ion_handle_data handle_data;
  uint32_t bufsize;

  if (mapion.pVirtualAddr == NULL) {
    return;
  }
  register_buf(mapion.pVirtualAddr, mapion.bufsize, -1);
  bufsize = (mapion.bufsize + 4095) & (~4095);
  rc = munmap(mapion.pVirtualAddr, bufsize);
  close(mapion.ion_info_fd.fd);

  handle_data.handle = mapion.ion_info_fd.handle;
  ioctl(mapion.ion_fd, ION_IOC_FREE, &handle_data);
  close(mapion.ion_fd);
}
void apr_pmem_alloc_ion_cached(struct mmap_info_ion *pmapion, uint32_t ionheapid) {
  struct ion_handle_data handle_data;
  struct ion_allocation_data alloc;
  struct ion_client *ion_client;
  struct ion_handle *ion_handle;
  int32_t rc;
  int32_t ion_fd;
  uint32_t ret;
  int32_t  p_pmem_fd;
  struct ion_fd_data ion_info_fd;
  struct ion_fd_data test_fd;
  struct ion_custom_data data;

  ion_fd = open("/dev/ion", O_RDONLY);
  if (ion_fd < 0) {
    CDBG_ERROR("\n apr_pmem_alloc_ion : Open ion device failed");
    pmapion->pVirtualAddr = NULL;
    return;
  }

  alloc.len = pmapion->bufsize;
  alloc.align = 4096;
  alloc.heap_mask = ionheapid;
  if (ionheapid == ION_HEAP(ION_CP_MM_HEAP_ID)) {
    alloc.flags = ION_SECURE | ION_FLAG_CACHED;
  } else {
    alloc.flags =  ION_FLAG_CACHED;
  }

  rc = ioctl(ion_fd, ION_IOC_ALLOC, &alloc);

  if (rc < 0) {
    handle_data.handle =  (pmapion->ion_info_fd).
      handle;
    CDBG_ERROR("\n apr_pmem_alloc_ion : ION alloc length %d %d", rc,
      alloc.len);
    close(ion_fd);
    pmapion->pVirtualAddr = NULL;
    return;
  } else {
    pmapion->ion_info_fd.handle = alloc.handle;
    rc = ioctl(ion_fd, ION_IOC_SHARE, &(pmapion->ion_info_fd));

    if (rc < 0) {
      CDBG_ERROR("\n apr_pmem_alloc_ion : ION map call failed %d", rc);
      handle_data.handle = pmapion->ion_info_fd.handle;
      ioctl(ion_fd, ION_IOC_FREE, &handle_data);
      close(ion_fd);
      pmapion->pVirtualAddr = NULL;
      return;
    } else {
      p_pmem_fd = pmapion->ion_info_fd.fd;
      ret = (uint32_t)mmap(NULL,
        alloc.len,
        PROT_READ  | PROT_WRITE,
        MAP_SHARED,
        p_pmem_fd,
        0);
      if (ret == (uint32_t)MAP_FAILED) {
        CDBG_ERROR("\n apr_pmem_alloc_ion : mmap call failed %d", rc);
        handle_data.handle = (pmapion->ion_info_fd).handle;
        ioctl(ion_fd, ION_IOC_FREE, &handle_data);
        close(ion_fd);
        pmapion->pVirtualAddr = NULL;
        return;
      } else {
        CDBG_ERROR("\n Ion allocation success virtaddr : %u fd %u",
          (uint32_t)ret,
          (uint32_t)p_pmem_fd);
        data.cmd = p_pmem_fd;
        pmapion->pVirtualAddr = (void *)ret;
        pmapion->ion_fd = ion_fd;
      }
    }
  }
   register_buf(pmapion->pVirtualAddr, alloc.len, p_pmem_fd);
   return;
}
示例#4
0
PmemPool::PmemPool(const char *pmem_pool,
                                           int flags,
                                           int pmem_type,
                                           int buffer_size, int num_buffers,
                                           int frame_size, int cbcr_offset,
                                           int yOffset, const char *name) :
    MemPool(buffer_size,num_buffers,frame_size,name),
    mPmemType(pmem_type),
    mCbCrOffset(cbcr_offset),
    myOffset(yOffset)
{
    ALOGI("constructing MemPool %s backed by pmem pool %s: "
         "%d frames @ %d bytes, buffer size %d",
         mName,
         pmem_pool, num_buffers, frame_size,
         buffer_size);

    //mMMCameraDLRef = MMCameraDL::getInstance();


    // Make a new mmap'ed heap that can be shared across processes.
    // mAlignedBufferSize is already in 4k aligned. (do we need total size necessary to be in power of 2??)
    mAlignedSize = mAlignedBufferSize * num_buffers;

    sp<MemoryHeapBase> masterHeap =
        new MemoryHeapBase(pmem_pool, mAlignedSize, flags);

    if (masterHeap->getHeapID() < 0) {
        ALOGE("failed to construct master heap for pmem pool %s", pmem_pool);
        masterHeap.clear();
        return;
    }

    sp<MemoryHeapPmem> pmemHeap = new MemoryHeapPmem(masterHeap, flags);
    if (pmemHeap->getHeapID() >= 0) {
        pmemHeap->slap();
        masterHeap.clear();
        mHeap = pmemHeap;
        pmemHeap.clear();

        mFd = mHeap->getHeapID();
        if (::ioctl(mFd, PMEM_GET_SIZE, &mSize)) {
            ALOGE("pmem pool %s ioctl(PMEM_GET_SIZE) error %s (%d)",
                 pmem_pool,
                 ::strerror(errno), errno);
            mHeap.clear();
            return;
        }

        ALOGE("pmem pool %s ioctl(fd = %d, PMEM_GET_SIZE) is %ld",
             pmem_pool,
             mFd,
             mSize.len);
        ALOGE("mBufferSize=%d, mAlignedBufferSize=%d\n", mBufferSize, mAlignedBufferSize);

#if 0
        // Unregister preview buffers with the camera drivers.  Allow the VFE to write
        // to all preview buffers except for the last one.
        // Only Register the preview, snapshot and thumbnail buffers with the kernel.
        if( (strcmp("postview", mName) != 0) ){
            int num_buf = num_buffers;
            if(!strcmp("preview", mName)) num_buf = kPreviewBufferCount;
            ALOGD("num_buffers = %d", num_buf);
            for (int cnt = 0; cnt < num_buf; ++cnt) {
                int active = 1;
                if(pmem_type == MSM_PMEM_VIDEO){
                     active = (cnt<ACTIVE_VIDEO_BUFFERS);
                     //When VPE is enabled, set the last record
                     //buffer as active and pmem type as PMEM_VIDEO_VPE
                     //as this is a requirement from VPE operation.
                     //No need to set this pmem type to VIDEO_VPE while unregistering,
                     //because as per camera stack design: "the VPE AXI is also configured
                     //when VFE is configured for VIDEO, which is as part of preview
                     //initialization/start. So during this VPE AXI config camera stack
                     //will lookup the PMEM_VIDEO_VPE buffer and give it as o/p of VPE and
                     //change it's type to PMEM_VIDEO".
                     if( (mVpeEnabled) && (cnt == kRecordBufferCount-1)) {
                         active = 1;
                         pmem_type = MSM_PMEM_VIDEO_VPE;
                     }
                     ALOGV(" pmempool creating video buffers : active %d ", active);
                }
                else if (pmem_type == MSM_PMEM_PREVIEW){
                    active = (cnt < ACTIVE_PREVIEW_BUFFERS);
                }
                else if ((pmem_type == MSM_PMEM_MAINIMG)
                     || (pmem_type == MSM_PMEM_THUMBNAIL)){
                    active = (cnt < ACTIVE_ZSL_BUFFERS);
                }
                register_buf(mBufferSize,
                         mFrameSize, mCbCrOffset, myOffset,
                         mHeap->getHeapID(),
                         mAlignedBufferSize * cnt,
                         (uint8_t *)mHeap->base() + mAlignedBufferSize * cnt,
                         pmem_type,
                         active);
            }
        }
#endif
        completeInitialization();
    }
    else ALOGE("pmem pool %s error: could not create master heap!",
              pmem_pool);
    ALOGI("%s: (%s) X ", __FUNCTION__, mName);
}