msm: eva: Adopt Fastrpc Feature Request

To support multi-PDs per user process. Fastrpc handle is
no longer PID. Add change to support the FR.

Change-Id: I39d7043f048597f1e4e728c48d588f12bb740b56
Signed-off-by: George Shen <quic_sqiao@quicinc.com>
This commit is contained in:
George Shen
2023-05-08 12:04:47 -07:00
committed by Gerrit - the friendly Code Review server
parent 115a7bf5c7
commit 4e37a3a40b
5 changed files with 75 additions and 44 deletions

View File

@@ -1853,7 +1853,7 @@ int msm_cvp_session_deinit_buffers(struct msm_cvp_inst *inst)
msm_cvp_unmap_smem(inst, cbuf->smem, "unmap dsp"); msm_cvp_unmap_smem(inst, cbuf->smem, "unmap dsp");
msm_cvp_smem_put_dma_buf(cbuf->smem->dma_buf); msm_cvp_smem_put_dma_buf(cbuf->smem->dma_buf);
} else if (cbuf->ownership == DSP) { } else if (cbuf->ownership == DSP) {
rc = cvp_dsp_fastrpc_unmap(inst->process_id, cbuf); rc = cvp_dsp_fastrpc_unmap(inst->dsp_handle, cbuf);
if (rc) if (rc)
dprintk(CVP_ERR, dprintk(CVP_ERR,
"%s: failed to unmap buf from DSP\n", "%s: failed to unmap buf from DSP\n",

View File

@@ -466,7 +466,7 @@ int msm_cvp_close(void *instance)
msm_cvp_comm_session_clean(inst); msm_cvp_comm_session_clean(inst);
if (inst->session_type == MSM_CVP_DSP) if (inst->session_type == MSM_CVP_DSP)
cvp_dsp_del_sess(inst->process_id, inst); cvp_dsp_del_sess(inst->dsp_handle, inst);
kref_put(&inst->kref, close_helper); kref_put(&inst->kref, close_helper);
return 0; return 0;

View File

@@ -1019,7 +1019,6 @@ static int cvp_fastrpc_probe(struct fastrpc_device *rpc_dev)
frpc_node = cvp_get_fastrpc_node_with_handle(rpc_dev->handle); frpc_node = cvp_get_fastrpc_node_with_handle(rpc_dev->handle);
if (frpc_node) { if (frpc_node) {
frpc_node->cvp_fastrpc_device = rpc_dev; frpc_node->cvp_fastrpc_device = rpc_dev;
// static structure with signal and pid
complete(&frpc_node->fastrpc_probe_completion); complete(&frpc_node->fastrpc_probe_completion);
cvp_put_fastrpc_node(frpc_node); cvp_put_fastrpc_node(frpc_node);
} }
@@ -1117,6 +1116,27 @@ static int eva_fastrpc_dev_unmap_dma(struct fastrpc_device *frpc_device,
#endif /* End of CVP_FASTRPC_ENABLED */ #endif /* End of CVP_FASTRPC_ENABLED */
} }
static int eva_fastrpc_dev_get_pid(struct fastrpc_device *frpc_device, int *pid)
{
#ifdef CVP_FASTRPC_ENABLED
struct fastrpc_dev_get_hlos_pid get_pid = {0};
int rc = 0;
rc = __fastrpc_driver_invoke(frpc_device, FASTRPC_DEV_GET_HLOS_PID,
(unsigned long)(&get_pid));
if (rc) {
dprintk(CVP_ERR, "%s Failed to get PID %x\n",
__func__, rc);
return rc;
}
*pid = get_pid.hlos_pid;
return rc;
#else
return -ENODEV;
#endif /* End of CVP_FASTRPC_ENABLED */
}
static void eva_fastrpc_driver_add_sess( static void eva_fastrpc_driver_add_sess(
struct cvp_dsp_fastrpc_driver_entry *frpc, struct cvp_dsp_fastrpc_driver_entry *frpc,
struct msm_cvp_inst *inst) struct msm_cvp_inst *inst)
@@ -1131,16 +1151,16 @@ static void eva_fastrpc_driver_add_sess(
dprintk(CVP_DSP, "add dsp sess %pK fastrpc_driver %pK\n", inst, frpc); dprintk(CVP_DSP, "add dsp sess %pK fastrpc_driver %pK\n", inst, frpc);
} }
int cvp_dsp_fastrpc_unmap(uint32_t process_id, struct cvp_internal_buf *buf) int cvp_dsp_fastrpc_unmap(uint32_t handle, struct cvp_internal_buf *buf)
{ {
struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL; struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL;
struct fastrpc_device *frpc_device = NULL; struct fastrpc_device *frpc_device = NULL;
int rc = 0; int rc = 0;
frpc_node = cvp_get_fastrpc_node_with_handle(process_id); frpc_node = cvp_get_fastrpc_node_with_handle(handle);
if (!frpc_node) { if (!frpc_node) {
dprintk(CVP_ERR, "%s no frpc node for process id %d\n", dprintk(CVP_ERR, "%s no frpc node for dsp handle %d\n",
__func__, process_id); __func__, handle);
return -EINVAL; return -EINVAL;
} }
frpc_device = frpc_node->cvp_fastrpc_device; frpc_device = frpc_node->cvp_fastrpc_device;
@@ -1153,17 +1173,17 @@ int cvp_dsp_fastrpc_unmap(uint32_t process_id, struct cvp_internal_buf *buf)
return rc; return rc;
} }
int cvp_dsp_del_sess(uint32_t process_id, struct msm_cvp_inst *inst) int cvp_dsp_del_sess(uint32_t handle, struct msm_cvp_inst *inst)
{ {
struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL; struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL;
struct list_head *ptr = NULL, *next = NULL; struct list_head *ptr = NULL, *next = NULL;
struct msm_cvp_inst *sess; struct msm_cvp_inst *sess;
bool found = false; bool found = false;
frpc_node = cvp_get_fastrpc_node_with_handle(process_id); frpc_node = cvp_get_fastrpc_node_with_handle(handle);
if (!frpc_node) { if (!frpc_node) {
dprintk(CVP_ERR, "%s no frpc node for process id %d\n", dprintk(CVP_ERR, "%s no frpc node for dsp handle %d\n",
__func__, process_id); __func__, handle);
return -EINVAL; return -EINVAL;
} }
mutex_lock(&frpc_node->dsp_sessions.lock); mutex_lock(&frpc_node->dsp_sessions.lock);
@@ -1194,12 +1214,12 @@ static int eva_fastrpc_driver_register(uint32_t handle)
struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL; struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL;
bool skip_deregister = true; bool skip_deregister = true;
dprintk(CVP_DSP, "%s -> cvp_get_fastrpc_node_with_handle pid 0x%x\n", dprintk(CVP_DSP, "%s -> cvp_get_fastrpc_node_with_handle hdl 0x%x\n",
__func__, handle); __func__, handle);
frpc_node = cvp_get_fastrpc_node_with_handle(handle); frpc_node = cvp_get_fastrpc_node_with_handle(handle);
if (frpc_node == NULL) { if (frpc_node == NULL) {
dprintk(CVP_DSP, "%s new fastrpc node pid 0x%x\n", dprintk(CVP_DSP, "%s new fastrpc node hdl 0x%x\n",
__func__, handle); __func__, handle);
frpc_node = kzalloc(sizeof(*frpc_node), GFP_KERNEL); frpc_node = kzalloc(sizeof(*frpc_node), GFP_KERNEL);
if (!frpc_node) { if (!frpc_node) {
@@ -1251,7 +1271,7 @@ static int eva_fastrpc_driver_register(uint32_t handle)
goto fail_fastrpc_driver_register; goto fail_fastrpc_driver_register;
} }
} else { } else {
dprintk(CVP_DSP, "%s fastrpc probe hndl %pK pid 0x%x\n", dprintk(CVP_DSP, "%s fastrpc probe frpc_node %pK hdl 0x%x\n",
__func__, frpc_node, handle); __func__, frpc_node, handle);
cvp_put_fastrpc_node(frpc_node); cvp_put_fastrpc_node(frpc_node);
} }
@@ -1277,7 +1297,7 @@ static void eva_fastrpc_driver_unregister(uint32_t handle, bool force_exit)
struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL; struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL;
struct cvp_dsp2cpu_cmd *dsp2cpu_cmd = &me->pending_dsp2cpu_cmd; struct cvp_dsp2cpu_cmd *dsp2cpu_cmd = &me->pending_dsp2cpu_cmd;
dprintk(CVP_DSP, "%s Unregister fastrpc driver hdl %#x pid %#x, f %d\n", dprintk(CVP_DSP, "%s Unregister fastrpc driver hdl %#x hdl %#x, f %d\n",
__func__, handle, dsp2cpu_cmd->pid, (uint32_t)force_exit); __func__, handle, dsp2cpu_cmd->pid, (uint32_t)force_exit);
if (handle != dsp2cpu_cmd->pid) if (handle != dsp2cpu_cmd->pid)
@@ -1492,45 +1512,57 @@ static void __dsp_cvp_sess_create(struct cvp_dsp_cmd_msg *cmd)
struct cvp_dsp_apps *me = &gfa_cv; struct cvp_dsp_apps *me = &gfa_cv;
struct msm_cvp_inst *inst = NULL; struct msm_cvp_inst *inst = NULL;
uint64_t inst_handle = 0; uint64_t inst_handle = 0;
uint32_t pid;
int rc = 0; int rc = 0;
struct cvp_dsp2cpu_cmd *dsp2cpu_cmd = &me->pending_dsp2cpu_cmd; struct cvp_dsp2cpu_cmd *dsp2cpu_cmd = &me->pending_dsp2cpu_cmd;
struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL; struct cvp_dsp_fastrpc_driver_entry *frpc_node = NULL;
struct pid *pid_s = NULL; struct pid *pid_s = NULL;
struct task_struct *task = NULL; struct task_struct *task = NULL;
struct cvp_hfi_device *hdev; struct cvp_hfi_device *hdev;
struct fastrpc_device *frpc_device;
cmd->ret = 0; cmd->ret = 0;
dprintk(CVP_DSP, dprintk(CVP_DSP,
"%s sess Type %d Mask %d Prio %d Sec %d pid 0x%x\n", "%s sess Type %d Mask %d Prio %d Sec %d hdl 0x%x\n",
__func__, dsp2cpu_cmd->session_type, __func__, dsp2cpu_cmd->session_type,
dsp2cpu_cmd->kernel_mask, dsp2cpu_cmd->kernel_mask,
dsp2cpu_cmd->session_prio, dsp2cpu_cmd->session_prio,
dsp2cpu_cmd->is_secure, dsp2cpu_cmd->is_secure,
dsp2cpu_cmd->pid); dsp2cpu_cmd->pid);
pid_s = find_get_pid(dsp2cpu_cmd->pid); rc = eva_fastrpc_driver_register(dsp2cpu_cmd->pid);
if (pid_s == NULL) { if (rc) {
dprintk(CVP_WARN, "%s incorrect pid\n", __func__); dprintk(CVP_ERR, "%s Register fastrpc driver fail\n", __func__);
cmd->ret = -1; cmd->ret = -1;
return; return;
} }
dprintk(CVP_DSP, "%s get pid_s 0x%x from pidA 0x%x\n", __func__, frpc_node = cvp_get_fastrpc_node_with_handle(dsp2cpu_cmd->pid);
if (!frpc_node || !frpc_node->cvp_fastrpc_device) {
dprintk(CVP_WARN, "%s cannot get fastrpc node from %x\n",
__func__, dsp2cpu_cmd->pid);
goto fail_lookup;
}
frpc_device = frpc_node->cvp_fastrpc_device;
rc = eva_fastrpc_dev_get_pid(frpc_device, &pid);
if (rc) {
dprintk(CVP_ERR,
"%s Failed to map buffer 0x%x\n", __func__, rc);
goto fail_lookup;
}
pid_s = find_get_pid(pid);
if (pid_s == NULL) {
dprintk(CVP_WARN, "%s incorrect pid %x\n", __func__, pid);
goto fail_lookup;
}
dprintk(CVP_DSP, "%s get pid_s 0x%x from hdl 0x%x\n", __func__,
pid_s, dsp2cpu_cmd->pid); pid_s, dsp2cpu_cmd->pid);
task = get_pid_task(pid_s, PIDTYPE_TGID); task = get_pid_task(pid_s, PIDTYPE_TGID);
if (!task) { if (!task) {
dprintk(CVP_WARN, "%s task doesn't exist\n", __func__); dprintk(CVP_WARN, "%s task doesn't exist\n", __func__);
cmd->ret = -1; goto fail_lookup;
return;
}
rc = eva_fastrpc_driver_register(dsp2cpu_cmd->pid);
if (rc) {
dprintk(CVP_ERR, "%s Register fastrpc driver fail\n", __func__);
put_task_struct(task);
cmd->ret = -1;
return;
} }
inst = msm_cvp_open(MSM_CORE_CVP, MSM_CVP_DSP, task); inst = msm_cvp_open(MSM_CORE_CVP, MSM_CVP_DSP, task);
@@ -1539,7 +1571,7 @@ static void __dsp_cvp_sess_create(struct cvp_dsp_cmd_msg *cmd)
goto fail_msm_cvp_open; goto fail_msm_cvp_open;
} }
inst->process_id = dsp2cpu_cmd->pid; inst->dsp_handle = dsp2cpu_cmd->pid;
inst->prop.kernel_mask = dsp2cpu_cmd->kernel_mask; inst->prop.kernel_mask = dsp2cpu_cmd->kernel_mask;
inst->prop.type = dsp2cpu_cmd->session_type; inst->prop.type = dsp2cpu_cmd->session_type;
inst->prop.priority = dsp2cpu_cmd->session_prio; inst->prop.priority = dsp2cpu_cmd->session_prio;
@@ -1565,11 +1597,8 @@ static void __dsp_cvp_sess_create(struct cvp_dsp_cmd_msg *cmd)
cmd->session_cpu_high = (uint32_t)((inst_handle & HIGH32) >> 32); cmd->session_cpu_high = (uint32_t)((inst_handle & HIGH32) >> 32);
cmd->session_cpu_low = (uint32_t)(inst_handle & LOW32); cmd->session_cpu_low = (uint32_t)(inst_handle & LOW32);
frpc_node = cvp_get_fastrpc_node_with_handle(dsp2cpu_cmd->pid); eva_fastrpc_driver_add_sess(frpc_node, inst);
if (frpc_node) { cvp_put_fastrpc_node(frpc_node);
eva_fastrpc_driver_add_sess(frpc_node, inst);
cvp_put_fastrpc_node(frpc_node);
}
inst->task = task; inst->task = task;
dprintk(CVP_DSP, dprintk(CVP_DSP,
@@ -1589,9 +1618,10 @@ fail_get_session_info:
fail_session_create: fail_session_create:
msm_cvp_close(inst); msm_cvp_close(inst);
fail_msm_cvp_open: fail_msm_cvp_open:
put_task_struct(task);
fail_lookup:
/* unregister fastrpc driver */ /* unregister fastrpc driver */
eva_fastrpc_driver_unregister(dsp2cpu_cmd->pid, false); eva_fastrpc_driver_unregister(dsp2cpu_cmd->pid, false);
put_task_struct(task);
cmd->ret = -1; cmd->ret = -1;
} }
@@ -1791,7 +1821,7 @@ static void __dsp_cvp_buf_deregister(struct cvp_dsp_cmd_msg *cmd)
cmd->ret = 0; cmd->ret = 0;
dprintk(CVP_DSP, dprintk(CVP_DSP,
"%s : sess id 0x%x, low 0x%x, high 0x%x, pid 0x%x\n", "%s : sess id 0x%x, low 0x%x, high 0x%x, hdl 0x%x\n",
__func__, dsp2cpu_cmd->session_id, __func__, dsp2cpu_cmd->session_id,
dsp2cpu_cmd->session_cpu_low, dsp2cpu_cmd->session_cpu_low,
dsp2cpu_cmd->session_cpu_high, dsp2cpu_cmd->session_cpu_high,
@@ -1847,7 +1877,7 @@ static void __dsp_cvp_mem_alloc(struct cvp_dsp_cmd_msg *cmd)
cmd->ret = 0; cmd->ret = 0;
dprintk(CVP_DSP, dprintk(CVP_DSP,
"%s sess id 0x%x, low 0x%x, high 0x%x, pid 0x%x\n", "%s sess id 0x%x, low 0x%x, high 0x%x, hdl 0x%x\n",
__func__, dsp2cpu_cmd->session_id, __func__, dsp2cpu_cmd->session_id,
dsp2cpu_cmd->session_cpu_low, dsp2cpu_cmd->session_cpu_low,
dsp2cpu_cmd->session_cpu_high, dsp2cpu_cmd->session_cpu_high,
@@ -1931,7 +1961,7 @@ static void __dsp_cvp_mem_free(struct cvp_dsp_cmd_msg *cmd)
cmd->ret = 0; cmd->ret = 0;
dprintk(CVP_DSP, dprintk(CVP_DSP,
"%s sess id 0x%x, low 0x%x, high 0x%x, pid 0x%x\n", "%s sess id 0x%x, low 0x%x, high 0x%x, hnl 0x%x\n",
__func__, dsp2cpu_cmd->session_id, __func__, dsp2cpu_cmd->session_id,
dsp2cpu_cmd->session_cpu_low, dsp2cpu_cmd->session_cpu_low,
dsp2cpu_cmd->session_cpu_high, dsp2cpu_cmd->session_cpu_high,

View File

@@ -28,6 +28,7 @@ enum fastrpc_driver_status {
enum fastrpc_driver_invoke_nums { enum fastrpc_driver_invoke_nums {
FASTRPC_DEV_MAP_DMA = 1, FASTRPC_DEV_MAP_DMA = 1,
FASTRPC_DEV_UNMAP_DMA, FASTRPC_DEV_UNMAP_DMA,
FASTRPC_DEV_GET_HLOS_PID,
}; };
struct fastrpc_driver { struct fastrpc_driver {
@@ -210,7 +211,7 @@ enum DRIVER_NAME_STATUS {
struct cvp_dsp_fastrpc_driver_entry { struct cvp_dsp_fastrpc_driver_entry {
struct list_head list; struct list_head list;
uint32_t handle; uint32_t handle; /*handle is not PID*/
uint32_t session_cnt; uint32_t session_cnt;
uint32_t driver_name_idx; uint32_t driver_name_idx;
atomic_t refcount; atomic_t refcount;
@@ -298,9 +299,9 @@ int cvp_dsp_deregister_buffer(uint32_t session_id, uint32_t buff_fd,
uint32_t buff_offset, uint32_t buff_index, uint32_t buff_offset, uint32_t buff_index,
uint32_t buff_fd_iova); uint32_t buff_fd_iova);
int cvp_dsp_fastrpc_unmap(uint32_t process_id, struct cvp_internal_buf *buf); int cvp_dsp_fastrpc_unmap(uint32_t handle, struct cvp_internal_buf *buf);
int cvp_dsp_del_sess(uint32_t process_id, struct msm_cvp_inst *inst); int cvp_dsp_del_sess(uint32_t handle, struct msm_cvp_inst *inst);
void cvp_dsp_send_debug_mask(void); void cvp_dsp_send_debug_mask(void);

View File

@@ -370,7 +370,7 @@ struct msm_cvp_inst {
struct mutex sync_lock, lock; struct mutex sync_lock, lock;
struct msm_cvp_core *core; struct msm_cvp_core *core;
enum session_type session_type; enum session_type session_type;
u32 process_id; u32 dsp_handle;
struct task_struct *task; struct task_struct *task;
atomic_t smem_count; atomic_t smem_count;
struct cvp_session_queue session_queue; struct cvp_session_queue session_queue;