171 lines
3.7 KiB
C
171 lines
3.7 KiB
C
|
/*
|
||
|
* Copyright (c) 2008-2016 Allwinner Technology Co. Ltd.
|
||
|
* All rights reserved.
|
||
|
*
|
||
|
* File : cdcionUtil.c
|
||
|
* Description : get phy addr for android
|
||
|
* (it is only work in android, do not compile in LINUX)
|
||
|
* History :
|
||
|
* Comment :
|
||
|
*
|
||
|
*
|
||
|
*/
|
||
|
|
||
|
#include <string.h>
|
||
|
#include <stdio.h>
|
||
|
#include <stdlib.h>
|
||
|
#include <errno.h>
|
||
|
#include <fcntl.h>
|
||
|
#include <stdio.h>
|
||
|
#include <sys/ioctl.h>
|
||
|
#include <sys/mman.h>
|
||
|
#include <sys/types.h>
|
||
|
|
||
|
#include "aw_ion_util.h"
|
||
|
|
||
|
#ifdef __ANDROID__
|
||
|
#include <cutils/properties.h>
|
||
|
#endif
|
||
|
|
||
|
int aw_ion_get_mem_type()
|
||
|
{
|
||
|
MEMORY_TYPE eMemoryType = MEMORY_NORMAL;
|
||
|
|
||
|
#if CONF_USE_IOMMU
|
||
|
eMemoryType = MEMORY_IOMMU;
|
||
|
#else
|
||
|
|
||
|
#ifdef __ANDROID__
|
||
|
char prop_value[512];
|
||
|
property_get("ro.kernel.iomem.type", prop_value, "0xaf01");
|
||
|
logv("++++ prop_value: %s", prop_value);
|
||
|
if(strcmp(prop_value, "0xaf10")==0)
|
||
|
{
|
||
|
eMemoryType = MEMORY_IOMMU;
|
||
|
}
|
||
|
#endif
|
||
|
#endif
|
||
|
|
||
|
return eMemoryType;
|
||
|
}
|
||
|
unsigned long aw_ion_get_phy_addr(int fd, uintptr_t handle)
|
||
|
{
|
||
|
if(aw_ion_get_mem_type() == MEMORY_IOMMU)
|
||
|
{
|
||
|
return 1;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
int ret = 0;
|
||
|
ion_custom_data_t custom_data;
|
||
|
cdc_sunxi_phys_data phys_data;
|
||
|
memset(&phys_data, 0, sizeof(cdc_sunxi_phys_data));
|
||
|
custom_data.aw_cmd = ION_IOC_SUNXI_PHYS_ADDR;
|
||
|
phys_data.handle = (aw_ion_user_handle_t)handle;
|
||
|
custom_data.aw_arg = (unsigned long)&phys_data;
|
||
|
ret = ioctl(fd, AW_MEM_ION_IOC_CUSTOM, &custom_data);
|
||
|
if(ret < 0)
|
||
|
{
|
||
|
loge("CdcIonGetPhyAdr AW_MEM_ION_IOC_CUSTOM error\n");
|
||
|
return 0;
|
||
|
}
|
||
|
return phys_data.phys_addr;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
int aw_ion_get_fd(int fd, uintptr_t handle)
|
||
|
{
|
||
|
int ret;
|
||
|
ion_fd_data_t fd_data;
|
||
|
fd_data.handle = (aw_ion_user_handle_t)handle;
|
||
|
ret = ioctl(fd, AW_MEM_ION_IOC_MAP, &fd_data);
|
||
|
if(ret)
|
||
|
{
|
||
|
loge("aw_ion_get_fd map other dev's handle err, ret %d, dmabuf fd 0x%08x, handle = %d\n",
|
||
|
ret, fd_data.aw_fd, fd_data.handle);
|
||
|
return -1;
|
||
|
}
|
||
|
return fd_data.aw_fd;
|
||
|
}
|
||
|
|
||
|
int aw_ion_import(int fd, int share_fd, aw_ion_user_handle_t *ion_handle)
|
||
|
{
|
||
|
int ret;
|
||
|
ion_fd_data_t fd_data;
|
||
|
|
||
|
memset(&fd_data, 0, sizeof(ion_fd_data_t));
|
||
|
fd_data.aw_fd = share_fd;
|
||
|
ret = ioctl(fd, AW_MEM_ION_IOC_IMPORT, &fd_data);
|
||
|
if(ret)
|
||
|
{
|
||
|
loge("CdcIonImport get ion_handle err, ret %d\n",ret);
|
||
|
return -1;
|
||
|
}
|
||
|
|
||
|
*ion_handle = fd_data.handle;
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
int aw_ion_free(int fd, aw_ion_user_handle_t ion_handle)
|
||
|
{
|
||
|
int ret;
|
||
|
ion_handle_data_t sIonHandleData;
|
||
|
|
||
|
memset(&sIonHandleData, 0, sizeof(ion_handle_data_t));
|
||
|
sIonHandleData.handle = ion_handle;
|
||
|
ret = ioctl(fd, AW_MEM_ION_IOC_FREE, &sIonHandleData);
|
||
|
if(ret)
|
||
|
{
|
||
|
loge("CdcIonFree free ion_handle err, ret %d\n",ret);
|
||
|
return -1;
|
||
|
}
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
int aw_ion_open(void)
|
||
|
{
|
||
|
int fd = open("/dev/ion", O_RDWR);
|
||
|
if (fd < 0)
|
||
|
loge("open /dev/ion failed!\n");
|
||
|
return fd;
|
||
|
}
|
||
|
|
||
|
int aw_ion_close(int fd)
|
||
|
{
|
||
|
int ret = close(fd);
|
||
|
if (ret < 0)
|
||
|
{
|
||
|
loge("CdcIonClose failed with code %d: %s\n", ret, strerror(errno));
|
||
|
return -errno;
|
||
|
}
|
||
|
return ret;
|
||
|
}
|
||
|
|
||
|
int aw_ion_mmap(int buf_fd, size_t len, unsigned char **pVirAddr)
|
||
|
{
|
||
|
/* mmap to user */
|
||
|
*pVirAddr = mmap(NULL, len, \
|
||
|
PROT_READ|PROT_WRITE, MAP_SHARED, buf_fd, 0);
|
||
|
if(MAP_FAILED == pVirAddr)
|
||
|
{
|
||
|
printf("mmap failed\n");
|
||
|
loge("CdcIonMmap failed: %s\n", strerror(errno));
|
||
|
return -errno;
|
||
|
}
|
||
|
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
int aw_ion_unmap(size_t len, unsigned char *pVirAddr)
|
||
|
{
|
||
|
int ret;
|
||
|
ret = munmap((void*)pVirAddr, len);
|
||
|
if(ret)
|
||
|
{
|
||
|
loge("CdcIonUnmap failed: %s, addr = %p\n", strerror(errno), pVirAddr);
|
||
|
return -errno;
|
||
|
}
|
||
|
|
||
|
return 0;
|
||
|
}
|