msm: adsprpc: HMX,Async-FastRPC capability

Added two extra capabilities - HMX and Async FastRPC.
Async FastRPC checks the DSP for capability and
ANDs it with its own capability
which is then returned to the userspace.

Change-Id: I3310b76ccdafad664eff5f12493c9d3fc45cc4ca
Signed-off-by: Anirudh Raghavendra <araghave@codeaurora.org>
This commit is contained in:
Anirudh Raghavendra 2020-01-07 15:35:02 -08:00
parent d91fc2d48a
commit 9175d25a5f
3 changed files with 96 additions and 49 deletions

View File

@ -1,6 +1,6 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (c) 2012-2019, The Linux Foundation. All rights reserved.
* Copyright (c) 2012-2020, The Linux Foundation. All rights reserved.
*/
#include <linux/dma-buf.h>
#include <linux/dma-mapping.h>
@ -156,6 +156,8 @@
(int64_t *)(perf_ptr + offset)\
: (int64_t *)NULL) : (int64_t *)NULL)
#define IS_ASYNC_FASTRPC_AVAILABLE (0)
static int fastrpc_pdr_notifier_cb(struct notifier_block *nb,
unsigned long code,
void *data);
@ -2709,36 +2711,62 @@ static int fastrpc_get_info_from_dsp(struct fastrpc_file *fl,
}
static int fastrpc_get_info_from_kernel(
struct fastrpc_ioctl_dsp_capabilities *dsp_cap,
struct fastrpc_ioctl_remote_dsp_capability *dsp_cap,
struct fastrpc_file *fl)
{
int err = 0;
uint32_t domain_support;
uint32_t domain = dsp_cap->domain;
uint32_t async_capability = IS_ASYNC_FASTRPC_AVAILABLE;
struct fastrpc_dsp_capabilities *dsp_cap_ptr;
if (!gcinfo[domain].dsp_cap_kernel.is_cached) {
VERIFY(err, dsp_cap->domain < NUM_CHANNELS);
/*
* Check if number of attribute IDs obtained from userspace
* is less than the number of attribute IDs supported by
* kernel
*/
if (dsp_cap->attribute_ID >= FASTRPC_MAX_DSP_ATTRIBUTES) {
err = EOVERFLOW;
dsp_cap->capability = 0;
goto bail;
}
dsp_cap_ptr = &gcinfo[domain].dsp_cap_kernel;
if (!dsp_cap_ptr->is_cached) {
/*
* Information not on kernel, query device for information
* and cache on kernel
*/
err = fastrpc_get_info_from_dsp(fl, dsp_cap->dsp_attributes,
FASTRPC_MAX_DSP_ATTRIBUTES - 1,
domain);
err = fastrpc_get_info_from_dsp(fl,
dsp_cap_ptr->dsp_attributes,
FASTRPC_MAX_DSP_ATTRIBUTES - 1,
domain);
if (err)
goto bail;
domain_support = dsp_cap->dsp_attributes[0];
domain_support =
dsp_cap_ptr->dsp_attributes[0];
switch (domain_support) {
case 0:
memset(dsp_cap->dsp_attributes, 0,
sizeof(dsp_cap->dsp_attributes));
memset(&gcinfo[domain].dsp_cap_kernel.dsp_attributes,
0, sizeof(dsp_cap->dsp_attributes));
memset(&dsp_cap_ptr->dsp_attributes,
0,
sizeof(dsp_cap_ptr->dsp_attributes));
memset(&dsp_cap->capability,
0, sizeof(dsp_cap->capability));
break;
case 1:
memcpy(&gcinfo[domain].dsp_cap_kernel.dsp_attributes,
dsp_cap->dsp_attributes,
sizeof(dsp_cap->dsp_attributes));
async_capability =
async_capability &&
dsp_cap_ptr->dsp_attributes[ASYNC_FASTRPC_CAP];
dsp_cap_ptr->dsp_attributes[ASYNC_FASTRPC_CAP] =
async_capability;
memcpy(&dsp_cap->capability,
&dsp_cap_ptr->dsp_attributes[dsp_cap->attribute_ID],
sizeof(dsp_cap->capability));
break;
default:
err = -1;
@ -2746,19 +2774,19 @@ static int fastrpc_get_info_from_kernel(
* Reset is_cached flag to 0 so subsequent calls
* can try to query dsp again
*/
gcinfo[domain].dsp_cap_kernel.is_cached = 0;
dsp_cap_ptr->is_cached = 0;
pr_warn("adsprpc: %s: %s: returned bad domain support value %d\n",
current->comm,
__func__,
domain_support);
goto bail;
}
gcinfo[domain].dsp_cap_kernel.is_cached = 1;
dsp_cap_ptr->is_cached = 1;
} else {
// Information on Kernel, pass it to user
memcpy(dsp_cap->dsp_attributes,
&gcinfo[domain].dsp_cap_kernel.dsp_attributes,
sizeof(dsp_cap->dsp_attributes));
memcpy(&dsp_cap->capability,
&dsp_cap_ptr->dsp_attributes[dsp_cap->attribute_ID],
sizeof(dsp_cap->capability));
}
bail:
return err;
@ -4041,13 +4069,15 @@ static int fastrpc_control(struct fastrpc_ioctl_control *cp,
bail:
return err;
}
static int fastrpc_get_dsp_info(struct fastrpc_ioctl_dsp_capabilities *dsp_cap,
void *param, struct fastrpc_file *fl)
static int fastrpc_get_dsp_info(
struct fastrpc_ioctl_remote_dsp_capability *dsp_cap,
void *param, struct fastrpc_file *fl)
{
int err = 0;
K_COPY_FROM_USER(err, 0, dsp_cap, param,
sizeof(struct fastrpc_ioctl_dsp_capabilities));
sizeof(struct fastrpc_ioctl_remote_dsp_capability));
VERIFY(err, dsp_cap->domain < NUM_CHANNELS);
if (err)
goto bail;
@ -4055,8 +4085,13 @@ static int fastrpc_get_dsp_info(struct fastrpc_ioctl_dsp_capabilities *dsp_cap,
err = fastrpc_get_info_from_kernel(dsp_cap, fl);
if (err)
goto bail;
K_COPY_TO_USER(err, 0, param, dsp_cap,
sizeof(struct fastrpc_ioctl_dsp_capabilities));
K_COPY_TO_USER(
err,
0,
&((struct fastrpc_ioctl_remote_dsp_capability *)
param)->capability,
&dsp_cap->capability,
sizeof(dsp_cap->capability));
bail:
return err;
}
@ -4074,7 +4109,7 @@ static long fastrpc_device_ioctl(struct file *file, unsigned int ioctl_num,
struct fastrpc_ioctl_init_attrs init;
struct fastrpc_ioctl_perf perf;
struct fastrpc_ioctl_control cp;
struct fastrpc_ioctl_dsp_capabilities dsp_cap;
struct fastrpc_ioctl_remote_dsp_capability dsp_cap;
} p;
union {
struct fastrpc_ioctl_mmap mmap;

View File

@ -1,6 +1,6 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (c) 2014-2019, The Linux Foundation. All rights reserved.
* Copyright (c) 2014-2020, The Linux Foundation. All rights reserved.
*/
#include <linux/compat.h>
#include <linux/fs.h>
@ -35,7 +35,8 @@
#define COMPAT_FASTRPC_IOCTL_MUNMAP_64 \
_IOWR('R', 15, struct compat_fastrpc_ioctl_munmap_64)
#define COMPAT_FASTRPC_IOCTL_GET_DSP_INFO \
_IOWR('R', 16, struct compat_fastrpc_ioctl_dsp_capabilities)
_IOWR('R', 17, \
struct compat_fastrpc_ioctl_remote_dsp_capability)
struct compat_remote_buf {
compat_uptr_t pv; /* buffer pointer */
@ -138,9 +139,22 @@ struct compat_fastrpc_ioctl_control {
};
};
struct compat_fastrpc_ioctl_dsp_capabilities {
compat_uint_t domain; /* DSP domain to query capabilities */
compat_uint_t dsp_attributes[FASTRPC_MAX_DSP_ATTRIBUTES];
struct compat_fastrpc_ioctl_remote_dsp_capability {
/*
* @param[in]: DSP domain ADSP_DOMAIN_ID,
* SDSP_DOMAIN_ID, or CDSP_DOMAIN_ID
*/
compat_uint_t domain;
/*
* @param[in]: One of the DSP attributes
* from enum remote_dsp_attributes
*/
compat_uint_t attribute_ID;
/*
* @param[out]: Result of the DSP
* capability query based on attribute_ID
*/
compat_uint_t capability;
};
static int compat_get_fastrpc_ioctl_invoke(
@ -382,19 +396,14 @@ static int compat_get_fastrpc_ioctl_init(
}
static int compat_put_fastrpc_ioctl_get_dsp_info(
struct compat_fastrpc_ioctl_dsp_capabilities __user *info32,
struct fastrpc_ioctl_dsp_capabilities __user *info)
struct compat_fastrpc_ioctl_remote_dsp_capability __user *info32,
struct fastrpc_ioctl_remote_dsp_capability __user *info)
{
compat_uint_t u, *dsp_attr, *dsp_attr_32;
int err, ii;
dsp_attr = info->dsp_attributes;
dsp_attr_32 = info32->dsp_attributes;
for (ii = 0, err = 0; ii < FASTRPC_MAX_DSP_ATTRIBUTES; ii++) {
err |= get_user(u, dsp_attr++);
err |= put_user(u, dsp_attr_32++);
}
compat_uint_t u;
int err = 0;
err |= get_user(u, &info->capability);
err |= put_user(u, &info32->capability);
return err;
}
@ -466,8 +475,8 @@ static int compat_fastrpc_getperf(struct file *filp,
static int compat_fastrpc_get_dsp_info(struct file *filp,
unsigned long arg)
{
struct compat_fastrpc_ioctl_dsp_capabilities __user *info32;
struct fastrpc_ioctl_dsp_capabilities *info;
struct compat_fastrpc_ioctl_remote_dsp_capability __user *info32;
struct fastrpc_ioctl_remote_dsp_capability *info;
compat_uint_t u;
long ret;
int err = 0;

View File

@ -1,6 +1,6 @@
/* SPDX-License-Identifier: GPL-2.0-only */
/*
* Copyright (c) 2012-2019, The Linux Foundation. All rights reserved.
* Copyright (c) 2012-2020, The Linux Foundation. All rights reserved.
*/
#ifndef ADSPRPC_SHARED_H
#define ADSPRPC_SHARED_H
@ -24,7 +24,7 @@
#define FASTRPC_IOCTL_CONTROL _IOWR('R', 12, struct fastrpc_ioctl_control)
#define FASTRPC_IOCTL_MUNMAP_FD _IOWR('R', 13, struct fastrpc_ioctl_munmap_fd)
#define FASTRPC_IOCTL_GET_DSP_INFO \
_IOWR('R', 16, struct fastrpc_ioctl_dsp_capabilities)
_IOWR('R', 17, struct fastrpc_ioctl_remote_dsp_capability)
#define FASTRPC_GLINK_GUID "fastrpcglink-apps-dsp"
#define FASTRPC_SMD_GUID "fastrpcsmd-apps-dsp"
@ -263,10 +263,13 @@ struct fastrpc_ioctl_control {
};
};
#define FASTRPC_MAX_DSP_ATTRIBUTES (7)
struct fastrpc_ioctl_dsp_capabilities {
uint32_t domain; //! DSP domain to query capabilities
uint32_t dsp_attributes[FASTRPC_MAX_DSP_ATTRIBUTES];
#define FASTRPC_MAX_DSP_ATTRIBUTES (9)
#define ASYNC_FASTRPC_CAP (8)
struct fastrpc_ioctl_remote_dsp_capability {
uint32_t domain;
uint32_t attribute_ID;
uint32_t capability;
};
struct smq_null_invoke {