dsp: add support for CMA heap allocation during call
Add support for CMA heap allocation during call. Mirror from: 3226736 Change-Id: I30a237b360ec6d690515682f0d98a86148acf059 Signed-off-by: Kunlei Zhang <kunleiz@codeaurora.org> Signed-off-by: Guodong Hu <guodhu@codeaurora.org>
This commit is contained in:

committed by
Gerrit - the friendly Code Review server

parent
994eb4e818
commit
d200c2fbe1
@@ -34,6 +34,7 @@
|
|||||||
struct msm_audio_ion_private {
|
struct msm_audio_ion_private {
|
||||||
bool smmu_enabled;
|
bool smmu_enabled;
|
||||||
struct device *cb_dev;
|
struct device *cb_dev;
|
||||||
|
struct device *cb_cma_dev;
|
||||||
u8 device_status;
|
u8 device_status;
|
||||||
struct list_head alloc_list;
|
struct list_head alloc_list;
|
||||||
struct mutex list_mutex;
|
struct mutex list_mutex;
|
||||||
@@ -88,7 +89,8 @@ static void msm_audio_ion_add_allocation(
|
|||||||
}
|
}
|
||||||
|
|
||||||
static int msm_audio_dma_buf_map(struct dma_buf *dma_buf,
|
static int msm_audio_dma_buf_map(struct dma_buf *dma_buf,
|
||||||
dma_addr_t *addr, size_t *len)
|
dma_addr_t *addr, size_t *len,
|
||||||
|
bool cma_mem)
|
||||||
{
|
{
|
||||||
|
|
||||||
struct msm_audio_alloc_data *alloc_data;
|
struct msm_audio_alloc_data *alloc_data;
|
||||||
@@ -96,6 +98,9 @@ static int msm_audio_dma_buf_map(struct dma_buf *dma_buf,
|
|||||||
unsigned long ionflag = 0;
|
unsigned long ionflag = 0;
|
||||||
int rc = 0;
|
int rc = 0;
|
||||||
|
|
||||||
|
if (cma_mem)
|
||||||
|
cb_dev = msm_audio_ion_data.cb_cma_dev;
|
||||||
|
else
|
||||||
cb_dev = msm_audio_ion_data.cb_dev;
|
cb_dev = msm_audio_ion_data.cb_dev;
|
||||||
|
|
||||||
/* Data required per buffer mapping */
|
/* Data required per buffer mapping */
|
||||||
@@ -161,14 +166,19 @@ free_alloc_data:
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int msm_audio_dma_buf_unmap(struct dma_buf *dma_buf)
|
static int msm_audio_dma_buf_unmap(struct dma_buf *dma_buf, bool cma_mem)
|
||||||
{
|
{
|
||||||
int rc = 0;
|
int rc = 0;
|
||||||
struct msm_audio_alloc_data *alloc_data = NULL;
|
struct msm_audio_alloc_data *alloc_data = NULL;
|
||||||
struct list_head *ptr, *next;
|
struct list_head *ptr, *next;
|
||||||
struct device *cb_dev = msm_audio_ion_data.cb_dev;
|
struct device *cb_dev;
|
||||||
bool found = false;
|
bool found = false;
|
||||||
|
|
||||||
|
if (cma_mem)
|
||||||
|
cb_dev = msm_audio_ion_data.cb_cma_dev;
|
||||||
|
else
|
||||||
|
cb_dev = msm_audio_ion_data.cb_dev;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Though list_for_each_safe is delete safe, lock
|
* Though list_for_each_safe is delete safe, lock
|
||||||
* should be explicitly acquired to avoid race condition
|
* should be explicitly acquired to avoid race condition
|
||||||
@@ -401,7 +411,7 @@ static int msm_audio_ion_get_phys(struct dma_buf *dma_buf,
|
|||||||
{
|
{
|
||||||
int rc = 0;
|
int rc = 0;
|
||||||
|
|
||||||
rc = msm_audio_dma_buf_map(dma_buf, addr, len);
|
rc = msm_audio_dma_buf_map(dma_buf, addr, len, false);
|
||||||
if (rc) {
|
if (rc) {
|
||||||
pr_err("%s: failed to map DMA buf, err = %d\n",
|
pr_err("%s: failed to map DMA buf, err = %d\n",
|
||||||
__func__, rc);
|
__func__, rc);
|
||||||
@@ -509,7 +519,7 @@ static int msm_audio_ion_map_buf(struct dma_buf *dma_buf, dma_addr_t *paddr,
|
|||||||
if (IS_ERR_OR_NULL(*vaddr)) {
|
if (IS_ERR_OR_NULL(*vaddr)) {
|
||||||
pr_err("%s: ION memory mapping for AUDIO failed\n", __func__);
|
pr_err("%s: ION memory mapping for AUDIO failed\n", __func__);
|
||||||
rc = -ENOMEM;
|
rc = -ENOMEM;
|
||||||
msm_audio_dma_buf_unmap(dma_buf);
|
msm_audio_dma_buf_unmap(dma_buf, false);
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -518,7 +528,7 @@ static int msm_audio_ion_map_buf(struct dma_buf *dma_buf, dma_addr_t *paddr,
|
|||||||
if (rc) {
|
if (rc) {
|
||||||
pr_err("%s: failed to do smmu map, err = %d\n",
|
pr_err("%s: failed to do smmu map, err = %d\n",
|
||||||
__func__, rc);
|
__func__, rc);
|
||||||
msm_audio_dma_buf_unmap(dma_buf);
|
msm_audio_dma_buf_unmap(dma_buf, false);
|
||||||
goto err;
|
goto err;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -623,7 +633,7 @@ EXPORT_SYMBOL(msm_audio_is_hypervisor_supported);
|
|||||||
* @bufsz: buffer size
|
* @bufsz: buffer size
|
||||||
* @paddr: Physical address to be assigned with allocated region
|
* @paddr: Physical address to be assigned with allocated region
|
||||||
* @plen: length of allocated region to be assigned
|
* @plen: length of allocated region to be assigned
|
||||||
* vaddr: virtual address to be assigned
|
* @vaddr: virtual address to be assigned
|
||||||
*
|
*
|
||||||
* Returns 0 on success or error on failure
|
* Returns 0 on success or error on failure
|
||||||
*/
|
*/
|
||||||
@@ -679,6 +689,67 @@ err:
|
|||||||
}
|
}
|
||||||
EXPORT_SYMBOL(msm_audio_ion_import);
|
EXPORT_SYMBOL(msm_audio_ion_import);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* msm_audio_ion_import_cma-
|
||||||
|
* Import ION buffer with given file descriptor
|
||||||
|
*
|
||||||
|
* @dma_buf: dma_buf for the ION memory
|
||||||
|
* @fd: file descriptor for the ION memory
|
||||||
|
* @ionflag: flags associated with ION buffer
|
||||||
|
* @bufsz: buffer size
|
||||||
|
* @paddr: Physical address to be assigned with allocated region
|
||||||
|
* @plen: length of allocated region to be assigned
|
||||||
|
* @vaddr: virtual address to be assigned
|
||||||
|
*
|
||||||
|
* Returns 0 on success or error on failure
|
||||||
|
*/
|
||||||
|
int msm_audio_ion_import_cma(struct dma_buf **dma_buf, int fd,
|
||||||
|
unsigned long *ionflag, size_t bufsz,
|
||||||
|
dma_addr_t *paddr, size_t *plen, void **vaddr)
|
||||||
|
{
|
||||||
|
int rc = 0;
|
||||||
|
|
||||||
|
if (!(msm_audio_ion_data.device_status & MSM_AUDIO_ION_PROBED)) {
|
||||||
|
pr_debug("%s: probe is not done, deferred\n", __func__);
|
||||||
|
return -EPROBE_DEFER;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!dma_buf || !paddr || !vaddr || !plen ||
|
||||||
|
!msm_audio_ion_data.cb_cma_dev) {
|
||||||
|
pr_err("%s: Invalid params\n", __func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* bufsz should be 0 and fd shouldn't be 0 as of now */
|
||||||
|
*dma_buf = dma_buf_get(fd);
|
||||||
|
pr_debug("%s: dma_buf =%pK, fd=%d\n", __func__, *dma_buf, fd);
|
||||||
|
if (IS_ERR_OR_NULL((void *)(*dma_buf))) {
|
||||||
|
pr_err("%s: dma_buf_get failed\n", __func__);
|
||||||
|
rc = -EINVAL;
|
||||||
|
goto err;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ionflag != NULL) {
|
||||||
|
rc = dma_buf_get_flags(*dma_buf, ionflag);
|
||||||
|
if (rc) {
|
||||||
|
pr_err("%s: could not get flags for the dma_buf\n",
|
||||||
|
__func__);
|
||||||
|
goto err_ion_flag;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
msm_audio_dma_buf_map(*dma_buf, paddr, plen, true);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
err_ion_flag:
|
||||||
|
dma_buf_put(*dma_buf);
|
||||||
|
err:
|
||||||
|
*dma_buf = NULL;
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
EXPORT_SYMBOL(msm_audio_ion_import_cma);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* msm_audio_ion_free -
|
* msm_audio_ion_free -
|
||||||
* fress ION memory for given client and handle
|
* fress ION memory for given client and handle
|
||||||
@@ -707,12 +778,33 @@ int msm_audio_ion_free(struct dma_buf *dma_buf)
|
|||||||
__func__, ret);
|
__func__, ret);
|
||||||
}
|
}
|
||||||
|
|
||||||
msm_audio_dma_buf_unmap(dma_buf);
|
msm_audio_dma_buf_unmap(dma_buf, false);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL(msm_audio_ion_free);
|
EXPORT_SYMBOL(msm_audio_ion_free);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* msm_audio_ion_free_cma -
|
||||||
|
* fress ION memory for given client and handle
|
||||||
|
*
|
||||||
|
* @dma_buf: dma_buf for the ION memory
|
||||||
|
*
|
||||||
|
* Returns 0 on success or error on failure
|
||||||
|
*/
|
||||||
|
int msm_audio_ion_free_cma(struct dma_buf *dma_buf)
|
||||||
|
{
|
||||||
|
if (!dma_buf) {
|
||||||
|
pr_err("%s: dma_buf invalid\n", __func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
msm_audio_dma_buf_unmap(dma_buf, true);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
EXPORT_SYMBOL(msm_audio_ion_free_cma);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* msm_audio_ion_mmap -
|
* msm_audio_ion_mmap -
|
||||||
* Audio ION memory map
|
* Audio ION memory map
|
||||||
@@ -814,6 +906,7 @@ EXPORT_SYMBOL(msm_audio_populate_upper_32_bits);
|
|||||||
|
|
||||||
static const struct of_device_id msm_audio_ion_dt_match[] = {
|
static const struct of_device_id msm_audio_ion_dt_match[] = {
|
||||||
{ .compatible = "qcom,msm-audio-ion" },
|
{ .compatible = "qcom,msm-audio-ion" },
|
||||||
|
{ .compatible = "qcom,msm-audio-ion-cma"},
|
||||||
{ }
|
{ }
|
||||||
};
|
};
|
||||||
MODULE_DEVICE_TABLE(of, msm_audio_ion_dt_match);
|
MODULE_DEVICE_TABLE(of, msm_audio_ion_dt_match);
|
||||||
@@ -833,6 +926,11 @@ static int msm_audio_ion_probe(struct platform_device *pdev)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (of_device_is_compatible(dev->of_node, "qcom,msm-audio-ion-cma")) {
|
||||||
|
msm_audio_ion_data.cb_cma_dev = dev;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
smmu_enabled = of_property_read_bool(dev->of_node,
|
smmu_enabled = of_property_read_bool(dev->of_node,
|
||||||
msm_audio_ion_dt);
|
msm_audio_ion_dt);
|
||||||
msm_audio_ion_data.smmu_enabled = smmu_enabled;
|
msm_audio_ion_data.smmu_enabled = smmu_enabled;
|
||||||
|
Reference in New Issue
Block a user