Context banks could be set as a shared one using a DT propery
"qcom,nsessions". The property takes the number of session to
be created of the context bank. This change provides a control
mechanism for user to use shared context banks for light weight
processes. The session is set as shared while its creation and if
a user requests for shared context bank, the same will be allocated
during process initialization.
Signed-off-by: Ekansh Gupta <quic_ekangupt@quicinc.com>
---
drivers/misc/fastrpc.c | 121 +++++++++++++++++++++++++++++++++----------------
1 file changed, 82 insertions(+), 39 deletions(-)
diff --git a/drivers/misc/fastrpc.c b/drivers/misc/fastrpc.c
index 1b26718..6ac1403 100644
--- a/drivers/misc/fastrpc.c
+++ b/drivers/misc/fastrpc.c
@@ -296,6 +296,7 @@ struct fastrpc_session_ctx {
int sid;
bool used;
bool valid;
+ bool sharedcb;
};
struct fastrpc_channel_ctx {
@@ -343,12 +344,22 @@ struct fastrpc_user {
int tgid;
int pd;
bool is_secure_dev;
+ bool sharedcb;
/* Lock for lists */
spinlock_t lock;
/* lock for allocations */
struct mutex mutex;
};
+struct fastrpc_ctrl_smmu {
+ u32 sharedcb; /* Set to SMMU share context bank */
+};
+
+struct fastrpc_internal_control {
+ u32 req;
+ struct fastrpc_ctrl_smmu smmu;
+};
+
static inline int64_t getnstimediff(struct timespec64 *start)
{
int64_t ns;
@@ -850,6 +861,37 @@ static const struct dma_buf_ops fastrpc_dma_buf_ops = {
.release = fastrpc_release,
};
+static struct fastrpc_session_ctx *fastrpc_session_alloc(
+ struct fastrpc_channel_ctx *cctx, bool sharedcb)
+{
+ struct fastrpc_session_ctx *session = NULL;
+ unsigned long flags;
+ int i;
+
+ spin_lock_irqsave(&cctx->lock, flags);
+ for (i = 0; i < cctx->sesscount; i++) {
+ if (!cctx->session[i].used && cctx->session[i].valid &&
+ cctx->session[i].sharedcb == sharedcb) {
+ cctx->session[i].used = true;
+ session = &cctx->session[i];
+ break;
+ }
+ }
+ spin_unlock_irqrestore(&cctx->lock, flags);
+
+ return session;
+}
+
+static void fastrpc_session_free(struct fastrpc_channel_ctx *cctx,
+ struct fastrpc_session_ctx *session)
+{
+ unsigned long flags;
+
+ spin_lock_irqsave(&cctx->lock, flags);
+ session->used = false;
+ spin_unlock_irqrestore(&cctx->lock, flags);
+}
+
static int fastrpc_map_create(struct fastrpc_user *fl, int fd,
u64 len, u32 attr, struct fastrpc_map **ppmap)
{
@@ -1446,6 +1488,10 @@ static int fastrpc_init_create_static_process(struct fastrpc_user *fl,
goto err_name;
}
+ fl->sctx = fastrpc_session_alloc(fl->cctx, fl->sharedcb);
+ if (!fl->sctx)
+ return -EBUSY;
+
if (!fl->cctx->remote_heap) {
err = fastrpc_remote_heap_alloc(fl, fl->sctx->dev, init.memlen,
&fl->cctx->remote_heap);
@@ -1563,6 +1609,10 @@ static int fastrpc_init_create_process(struct fastrpc_user *fl,
goto err;
}
+ fl->sctx = fastrpc_session_alloc(fl->cctx, fl->sharedcb);
+ if (!fl->sctx)
+ return -EBUSY;
+
inbuf.pgid = fl->tgid;
inbuf.namelen = strlen(current->comm) + 1;
inbuf.filelen = init.filelen;
@@ -1637,36 +1687,6 @@ static int fastrpc_init_create_process(struct fastrpc_user *fl,
return err;
}
-static struct fastrpc_session_ctx *fastrpc_session_alloc(
- struct fastrpc_channel_ctx *cctx)
-{
- struct fastrpc_session_ctx *session = NULL;
- unsigned long flags;
- int i;
-
- spin_lock_irqsave(&cctx->lock, flags);
- for (i = 0; i < cctx->sesscount; i++) {
- if (!cctx->session[i].used && cctx->session[i].valid) {
- cctx->session[i].used = true;
- session = &cctx->session[i];
- break;
- }
- }
- spin_unlock_irqrestore(&cctx->lock, flags);
-
- return session;
-}
-
-static void fastrpc_session_free(struct fastrpc_channel_ctx *cctx,
- struct fastrpc_session_ctx *session)
-{
- unsigned long flags;
-
- spin_lock_irqsave(&cctx->lock, flags);
- session->used = false;
- spin_unlock_irqrestore(&cctx->lock, flags);
-}
-
static void fastrpc_context_list_free(struct fastrpc_user *fl)
{
struct fastrpc_invoke_ctx *ctx, *n;
@@ -1771,15 +1791,6 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp)
fl->cctx = cctx;
fl->is_secure_dev = fdevice->secure;
- fl->sctx = fastrpc_session_alloc(cctx);
- if (!fl->sctx) {
- dev_err(&cctx->rpdev->dev, "No session available\n");
- mutex_destroy(&fl->mutex);
- kfree(fl);
-
- return -EBUSY;
- }
-
spin_lock_irqsave(&cctx->lock, flags);
list_add_tail(&fl->user, &cctx->users);
spin_unlock_irqrestore(&cctx->lock, flags);
@@ -1838,6 +1849,10 @@ static int fastrpc_init_attach(struct fastrpc_user *fl, int pd)
struct fastrpc_enhanced_invoke ioctl;
int tgid = fl->tgid;
+ fl->sctx = fastrpc_session_alloc(fl->cctx, fl->sharedcb);
+ if (!fl->sctx)
+ return -EBUSY;
+
args[0].ptr = (u64)(uintptr_t) &tgid;
args[0].length = sizeof(tgid);
args[0].fd = -1;
@@ -1884,11 +1899,32 @@ static int fastrpc_invoke(struct fastrpc_user *fl, char __user *argp)
return err;
}
+static int fastrpc_internal_control(struct fastrpc_user *fl,
+ struct fastrpc_internal_control *cp)
+{
+ int err = 0;
+
+ if (!fl)
+ return -EBADF;
+ if (!cp)
+ return -EINVAL;
+
+ case FASTRPC_CONTROL_SMMU:
+ fl->sharedcb = cp->smmu.sharedcb;
+ break;
+ default:
+ err = -EBADRQC;
+ break;
+ }
+ return err;
+}
+
static int fastrpc_multimode_invoke(struct fastrpc_user *fl, char __user *argp)
{
struct fastrpc_enhanced_invoke einv;
struct fastrpc_invoke_args *args = NULL;
struct fastrpc_ioctl_multimode_invoke invoke;
+ struct fastrpc_internal_control cp = {0};
u32 nscalars;
u64 *perf_kernel;
int err;
@@ -1921,6 +1957,12 @@ static int fastrpc_multimode_invoke(struct fastrpc_user *fl, char __user *argp)
err = fastrpc_internal_invoke(fl, false, &einv);
kfree(args);
break;
+ case FASTRPC_INVOKE_CONTROL:
+ if (copy_from_user(&cp, (void __user *)(uintptr_t)invoke.invparam, sizeof(cp)))
+ return -EFAULT;
+
+ err = fastrpc_internal_control(fl, &cp);
+ break;
default:
err = -ENOTTY;
break;
@@ -2421,6 +2463,7 @@ static int fastrpc_cb_probe(struct platform_device *pdev)
if (sessions > 0) {
struct fastrpc_session_ctx *dup_sess;
+ sess->sharedcb = true;
for (i = 1; i < sessions; i++) {
if (cctx->sesscount >= FASTRPC_MAX_SESSIONS)
break;
--
2.7.4
Hi Ekansh,
kernel test robot noticed the following build warnings:
[auto build test WARNING on char-misc/char-misc-testing]
[also build test WARNING on char-misc/char-misc-next char-misc/char-misc-linus linus/master v6.5 next-20230831]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch#_base_tree_information]
url: https://github.com/intel-lab-lkp/linux/commits/Ekansh-Gupta/misc-fastrpc-Add-fastrpc-multimode-invoke-request-support/20230901-002929
base: char-misc/char-misc-testing
patch link: https://lore.kernel.org/r/1693499292-19083-6-git-send-email-quic_ekangupt%40quicinc.com
patch subject: [PATCH v1 5/5] misc: fastrpc: Add support to allocate shared context bank
config: m68k-allyesconfig (https://download.01.org/0day-ci/archive/20230901/202309011446.SVM4HbHv-lkp@intel.com/config)
compiler: m68k-linux-gcc (GCC) 13.2.0
reproduce (this is a W=1 build): (https://download.01.org/0day-ci/archive/20230901/202309011446.SVM4HbHv-lkp@intel.com/reproduce)
If you fix the issue in a separate patch/commit (i.e. not just a new version of
the same patch/commit), kindly add following tags
| Reported-by: kernel test robot <lkp@intel.com>
| Closes: https://lore.kernel.org/oe-kbuild-all/202309011446.SVM4HbHv-lkp@intel.com/
All warnings (new ones prefixed by >>):
drivers/misc/fastrpc.c: In function 'fastrpc_context_alloc':
drivers/misc/fastrpc.c:674:29: warning: cast to pointer from integer of different size [-Wint-to-pointer-cast]
674 | ctx->args = (struct fastrpc_invoke_args *)invoke->inv.args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_init_create_static_process':
drivers/misc/fastrpc.c:1540:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
1540 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_init_create_process':
drivers/misc/fastrpc.c:1677:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
1677 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_release_current_dsp_process':
drivers/misc/fastrpc.c:1730:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
1730 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_device_release':
drivers/misc/fastrpc.c:1739:42: warning: unused variable 'n' [-Wunused-variable]
1739 | struct fastrpc_invoke_ctx *ctx, *n;
| ^
drivers/misc/fastrpc.c:1739:36: warning: unused variable 'ctx' [-Wunused-variable]
1739 | struct fastrpc_invoke_ctx *ctx, *n;
| ^~~
drivers/misc/fastrpc.c: In function 'fastrpc_init_attach':
drivers/misc/fastrpc.c:1871:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
1871 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_invoke':
drivers/misc/fastrpc.c:1902:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
1902 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_internal_control':
drivers/misc/fastrpc.c:1920:14: error: 'FASTRPC_CONTROL_SMMU' undeclared (first use in this function); did you mean 'FASTRPC_IOCTL_MMAP'?
1920 | case FASTRPC_CONTROL_SMMU:
| ^~~~~~~~~~~~~~~~~~~~
| FASTRPC_IOCTL_MMAP
drivers/misc/fastrpc.c:1920:14: note: each undeclared identifier is reported only once for each function it appears in
drivers/misc/fastrpc.c:1920:9: error: case label not within a switch statement
1920 | case FASTRPC_CONTROL_SMMU:
| ^~~~
drivers/misc/fastrpc.c:1922:17: error: break statement not within loop or switch
1922 | break;
| ^~~~~
drivers/misc/fastrpc.c:1923:9: error: 'default' label not within a switch statement
1923 | default:
| ^~~~~~~
drivers/misc/fastrpc.c:1925:17: error: break statement not within loop or switch
1925 | break;
| ^~~~~
>> drivers/misc/fastrpc.c:1913:13: warning: variable 'err' set but not used [-Wunused-but-set-variable]
1913 | int err = 0;
| ^~~
drivers/misc/fastrpc.c: At top level:
drivers/misc/fastrpc.c:1927:9: error: expected identifier or '(' before 'return'
1927 | return err;
| ^~~~~~
drivers/misc/fastrpc.c:1928:1: error: expected identifier or '(' before '}' token
1928 | }
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_multimode_invoke':
drivers/misc/fastrpc.c:1964:33: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
1964 | einv.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_get_info_from_dsp':
drivers/misc/fastrpc.c:2000:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
2000 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_req_munmap_impl':
drivers/misc/fastrpc.c:2103:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
2103 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_req_mmap':
drivers/misc/fastrpc.c:2201:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
2201 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_req_mem_unmap_impl':
drivers/misc/fastrpc.c:2282:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
2282 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_req_mem_map':
drivers/misc/fastrpc.c:2351:26: warning: cast from pointer to integer of different size [-Wpointer-to-int-cast]
2351 | ioctl.inv.args = (__u64)args;
| ^
drivers/misc/fastrpc.c: In function 'fastrpc_internal_control':
drivers/misc/fastrpc.c:1926:9: error: control reaches end of non-void function [-Werror=return-type]
1926 | }
| ^
cc1: some warnings being treated as errors
vim +/err +1913 drivers/misc/fastrpc.c
1909
1910 static int fastrpc_internal_control(struct fastrpc_user *fl,
1911 struct fastrpc_internal_control *cp)
1912 {
> 1913 int err = 0;
1914
1915 if (!fl)
1916 return -EBADF;
1917 if (!cp)
1918 return -EINVAL;
1919
1920 case FASTRPC_CONTROL_SMMU:
1921 fl->sharedcb = cp->smmu.sharedcb;
> 1922 break;
1923 default:
1924 err = -EBADRQC;
1925 break;
1926 }
1927 return err;
1928 }
1929
--
0-DAY CI Kernel Test Service
https://github.com/intel/lkp-tests/wiki
© 2016 - 2025 Red Hat, Inc.