Loading drivers/char/adsprpc.c +70 −67 Original line number Diff line number Diff line Loading @@ -136,6 +136,9 @@ #define FASTRPC_STATIC_HANDLE_MAX (20) #define FASTRPC_LATENCY_CTRL_ENB (1) /* Maximum PM timeout that can be voted through fastrpc */ #define MAX_PM_TIMEOUT_MS 50 /* timeout in us for busy polling after early response from remote processor */ #define FASTRPC_POLL_TIME (4000) Loading Loading @@ -304,7 +307,6 @@ struct smq_invoke_ctx { uint32_t early_wake_time; /* work done status flag */ bool is_work_done; bool pm_awake_voted; /* Store Async job in the context*/ struct fastrpc_async_job asyncjob; /* Async early flag to check the state of context */ Loading Loading @@ -399,11 +401,9 @@ struct fastrpc_apps { bool legacy_remote_heap; /* Unique job id for each message */ uint64_t jobid[NUM_CHANNELS]; /* Secure subsystems like ADSP/SLPI will use secure client */ struct wakeup_source *wake_source_secure; /* Non-secure subsystem like CDSP will use regular client */ struct wakeup_source *wake_source; struct gid_list gidlist; struct device *secure_dev; struct device *non_secure_dev; }; struct fastrpc_mmap { Loading Loading @@ -494,6 +494,11 @@ struct fastrpc_file { wait_queue_head_t async_wait_queue; /* IRQ safe spin lock for protecting async queue */ spinlock_t aqlock; /* Secure subsystems like ADSP/SLPI will use secure client */ struct wakeup_source *wake_source_secure; /* Non-secure subsystem like CDSP will use regular client */ struct wakeup_source *wake_source; uint32_t ws_timeout; }; static struct fastrpc_apps gfa; Loading Loading @@ -566,9 +571,7 @@ static struct fastrpc_channel_ctx gcinfo[NUM_CHANNELS] = { static int hlosvm[1] = {VMID_HLOS}; static int hlosvmperm[1] = {PERM_READ | PERM_WRITE | PERM_EXEC}; static void fastrpc_pm_awake(int fl_wake_enable, bool *pm_awake_voted, int channel_type); static void fastrpc_pm_relax(bool *pm_awake_voted, int channel_type); static inline void fastrpc_pm_awake(struct fastrpc_file *fl, int channel_type); static inline int64_t getnstimediff(struct timespec64 *start) { Loading Loading @@ -1417,7 +1420,6 @@ static int context_alloc(struct fastrpc_file *fl, uint32_t kernel, ctx->magic = FASTRPC_CTX_MAGIC; ctx->rsp_flags = NORMAL_RESPONSE; ctx->is_work_done = false; ctx->pm_awake_voted = false; ctx->copybuf = NULL; ctx->is_early_wakeup = false; if (invokefd->job) { Loading Loading @@ -1528,8 +1530,7 @@ static void fastrpc_queue_completed_async_job(struct smq_invoke_ctx *ctx) static void context_notify_user(struct smq_invoke_ctx *ctx, int retval, uint32_t rsp_flags, uint32_t early_wake_time) { fastrpc_pm_awake(ctx->fl->wake_enable, &ctx->pm_awake_voted, gcinfo[ctx->fl->cid].secure); fastrpc_pm_awake(ctx->fl, gcinfo[ctx->fl->cid].secure); ctx->retval = retval; ctx->rsp_flags = (enum fastrpc_response_flags)rsp_flags; trace_fastrpc_context_complete(ctx->fl->cid, (uint64_t)ctx, retval, Loading Loading @@ -2207,31 +2208,22 @@ static void fastrpc_init(struct fastrpc_apps *me) me->channel[CDSP_DOMAIN_ID].secure = NON_SECURE_CHANNEL; } static inline void fastrpc_pm_awake(int fl_wake_enable, bool *pm_awake_voted, int channel_type) static inline void fastrpc_pm_awake(struct fastrpc_file *fl, int channel_type) { struct fastrpc_apps *me = &gfa; struct wakeup_source *wake_source = NULL; if (!fl_wake_enable || *pm_awake_voted) if (!fl->wake_enable || !fl->wake_source || !fl->wake_source_secure) return; /* * Vote with PM to abort any suspend in progress and * keep system awake for specified timeout */ if (channel_type == SECURE_CHANNEL) __pm_stay_awake(me->wake_source_secure); wake_source = fl->wake_source_secure; else if (channel_type == NON_SECURE_CHANNEL) __pm_stay_awake(me->wake_source); *pm_awake_voted = true; } static inline void fastrpc_pm_relax(bool *pm_awake_voted, int channel_type) { struct fastrpc_apps *me = &gfa; wake_source = fl->wake_source; if (!(*pm_awake_voted)) return; if (channel_type == SECURE_CHANNEL) __pm_relax(me->wake_source_secure); else if (channel_type == NON_SECURE_CHANNEL) __pm_relax(me->wake_source); *pm_awake_voted = false; pm_wakeup_ws_event(wake_source, fl->ws_timeout, true); } static inline int fastrpc_wait_for_response(struct smq_invoke_ctx *ctx, Loading Loading @@ -2378,7 +2370,6 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, int err = 0, interrupted = 0, cid = fl->cid; struct timespec64 invoket = {0}; int64_t *perf_counter = NULL; bool pm_awake_voted = false; bool isasyncinvoke = false; VERIFY(err, cid >= ADSP_DOMAIN_ID && cid < NUM_CHANNELS && Loading @@ -2389,7 +2380,6 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, err = -EBADR; goto bail; } fastrpc_pm_awake(fl->wake_enable, &pm_awake_voted, gcinfo[cid].secure); if (fl->profile) { perf_counter = getperfcounter(fl, PERF_COUNT); Loading Loading @@ -2449,9 +2439,7 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, if (isasyncinvoke) goto invoke_end; wait: fastrpc_pm_relax(&pm_awake_voted, gcinfo[cid].secure); fastrpc_wait_for_completion(ctx, &interrupted, kernel, 0); pm_awake_voted = ctx->pm_awake_voted; VERIFY(err, 0 == (err = interrupted)); if (err) goto bail; Loading Loading @@ -2491,7 +2479,6 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, if (fl->profile && !interrupted) fastrpc_update_invoke_count(invoke->handle, perf_counter, &invoket); fastrpc_pm_relax(&pm_awake_voted, gcinfo[cid].secure); return err; } Loading Loading @@ -3855,6 +3842,8 @@ static int fastrpc_file_free(struct fastrpc_file *fl) spin_lock(&fl->apps->hlock); hlist_del_init(&fl->hn); spin_unlock(&fl->apps->hlock); wakeup_source_unregister(fl->wake_source); wakeup_source_unregister(fl->wake_source_secure); kfree(fl->debug_buf); kfree(fl->gidlist.gids); Loading Loading @@ -4199,6 +4188,21 @@ static int fastrpc_channel_open(struct fastrpc_file *fl) return err; } static inline void fastrpc_register_wakeup_source(struct device *dev, const char *client_name, struct wakeup_source **device_wake_source) { struct wakeup_source *wake_source; wake_source = wakeup_source_register(dev, client_name); if (IS_ERR_OR_NULL(wake_source)) { pr_err("adsprpc: Error: %s: %s: wakeup_source_register failed for %s (%s) with err %ld\n", __func__, current->comm, dev_name(dev), client_name, PTR_ERR(wake_source)); return; } *device_wake_source = wake_source; } static int fastrpc_device_open(struct inode *inode, struct file *filp) { int err = 0; Loading Loading @@ -4237,6 +4241,10 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp) debugfs_file = debugfs_create_file(fl->debug_buf, 0644, debugfs_root, fl, &debugfs_fops); fastrpc_register_wakeup_source(me->non_secure_dev, "adsprpc-non_secure", &fl->wake_source); fastrpc_register_wakeup_source(me->secure_dev, "adsprpc-secure", &fl->wake_source_secure); context_list_ctor(&fl->clst); spin_lock_init(&fl->hlock); spin_lock_init(&fl->aqlock); Loading Loading @@ -4375,8 +4383,26 @@ static int fastrpc_internal_control(struct fastrpc_file *fl, cp->kalloc.kalloc_support = 1; break; case FASTRPC_CONTROL_WAKELOCK: if (fl->dev_minor != MINOR_NUM_SECURE_DEV) { pr_err("adsprpc: %s: %s: PM voting not allowed for non-secure device node %d\n", current->comm, __func__, fl->dev_minor); err = -EPERM; goto bail; } fl->wake_enable = cp->wp.enable; break; case FASTRPC_CONTROL_PM: if (!fl->wake_enable) { /* Kernel PM voting not requested by this application */ err = -EACCES; goto bail; } if (cp->pm.timeout > MAX_PM_TIMEOUT_MS) fl->ws_timeout = MAX_PM_TIMEOUT_MS; else fl->ws_timeout = cp->pm.timeout; fastrpc_pm_awake(fl, gcinfo[fl->cid].secure); break; default: err = -EBADRQC; break; Loading Loading @@ -5205,8 +5231,6 @@ static struct rpmsg_driver fastrpc_rpmsg_client = { static int __init fastrpc_device_init(void) { struct fastrpc_apps *me = &gfa; struct device *dev = NULL; struct device *secure_dev = NULL; int err = 0, i; debugfs_root = debugfs_create_dir("adsprpc", NULL); Loading Loading @@ -5237,26 +5261,26 @@ static int __init fastrpc_device_init(void) * Create devices and register with sysfs * Create first device with minor number 0 */ dev = device_create(me->class, NULL, me->non_secure_dev = device_create(me->class, NULL, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV), NULL, DEVICE_NAME); VERIFY(err, !IS_ERR_OR_NULL(dev)); VERIFY(err, !IS_ERR_OR_NULL(me->non_secure_dev)); if (err) goto device_create_bail; /* Create secure device with minor number for secure device */ secure_dev = device_create(me->class, NULL, me->secure_dev = device_create(me->class, NULL, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV), NULL, DEVICE_NAME_SECURE); VERIFY(err, !IS_ERR_OR_NULL(secure_dev)); VERIFY(err, !IS_ERR_OR_NULL(me->secure_dev)); if (err) goto device_create_bail; for (i = 0; i < NUM_CHANNELS; i++) { me->jobid[i] = 1; me->channel[i].dev = secure_dev; me->channel[i].dev = me->secure_dev; if (i == CDSP_DOMAIN_ID) me->channel[i].dev = dev; me->channel[i].dev = me->non_secure_dev; me->channel[i].ssrcount = 0; me->channel[i].prevssrcount = 0; me->channel[i].issubsystemup = 1; Loading @@ -5283,23 +5307,6 @@ static int __init fastrpc_device_init(void) } me->rpmsg_register = 1; me->wake_source = wakeup_source_register(dev, "adsprpc-non_secure"); VERIFY(err, !IS_ERR_OR_NULL(me->wake_source)); if (err) { pr_err("adsprpc: Error: %s: wakeup_source_register failed for %s with err %ld\n", __func__, dev_name(dev), PTR_ERR(me->wake_source)); goto device_create_bail; } me->wake_source_secure = wakeup_source_register(secure_dev, "adsprpc-secure"); VERIFY(err, !IS_ERR_OR_NULL(me->wake_source_secure)); if (err) { pr_err("adsprpc: Error: %s: wakeup_source_register failed for %s with err %ld\n", __func__, dev_name(secure_dev), PTR_ERR(me->wake_source_secure)); goto device_create_bail; } return 0; device_create_bail: for (i = 0; i < NUM_CHANNELS; i++) { Loading @@ -5307,10 +5314,10 @@ static int __init fastrpc_device_init(void) subsys_notif_unregister_notifier(me->channel[i].handle, &me->channel[i].nb); } if (!IS_ERR_OR_NULL(dev)) if (!IS_ERR_OR_NULL(me->non_secure_dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV)); if (!IS_ERR_OR_NULL(secure_dev)) if (!IS_ERR_OR_NULL(me->secure_dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV)); class_destroy(me->class); Loading Loading @@ -5349,10 +5356,6 @@ static void __exit fastrpc_device_exit(void) unregister_chrdev_region(me->dev_no, NUM_CHANNELS); if (me->rpmsg_register == 1) unregister_rpmsg_driver(&fastrpc_rpmsg_client); if (me->wake_source) wakeup_source_unregister(me->wake_source); if (me->wake_source_secure) wakeup_source_unregister(me->wake_source_secure); kfree(me->gidlist.gids); debugfs_remove_recursive(debugfs_root); } Loading drivers/char/adsprpc_compat.c +16 −0 Original line number Diff line number Diff line Loading @@ -148,11 +148,21 @@ struct compat_fastrpc_ctrl_kalloc { compat_uint_t kalloc_support; /* Remote memory allocation from kernel */ }; struct compat_fastrpc_ctrl_wakelock { compat_uint_t enable; /* wakelock control enable */ }; struct compat_fastrpc_ctrl_pm { compat_uint_t timeout; /* timeout(in ms) for PM to keep system awake */ }; struct compat_fastrpc_ioctl_control { compat_uint_t req; union { struct compat_fastrpc_ctrl_latency lp; struct compat_fastrpc_ctrl_kalloc kalloc; struct compat_fastrpc_ctrl_wakelock wp; struct compat_fastrpc_ctrl_pm pm; }; }; Loading Loading @@ -493,6 +503,12 @@ static int compat_get_fastrpc_ioctl_control( err |= put_user(p, &ctrl->lp.enable); err |= get_user(p, &ctrl32->lp.latency); err |= put_user(p, &ctrl->lp.latency); } else if (p == FASTRPC_CONTROL_WAKELOCK) { err |= get_user(p, &ctrl32->wp.enable); err |= put_user(p, &ctrl->wp.enable); } else if (p == FASTRPC_CONTROL_PM) { err |= get_user(p, &ctrl32->pm.timeout); err |= put_user(p, &ctrl->pm.timeout); } return err; Loading drivers/char/adsprpc_shared.h +6 −0 Original line number Diff line number Diff line Loading @@ -282,6 +282,7 @@ enum fastrpc_control_type { FASTRPC_CONTROL_SMMU = 2, FASTRPC_CONTROL_KALLOC = 3, FASTRPC_CONTROL_WAKELOCK = 4, FASTRPC_CONTROL_PM = 5, }; struct fastrpc_ctrl_latency { Loading @@ -297,12 +298,17 @@ struct fastrpc_ctrl_wakelock { uint32_t enable; /* wakelock control enable */ }; struct fastrpc_ctrl_pm { uint32_t timeout; /* timeout(in ms) for PM to keep system awake */ }; struct fastrpc_ioctl_control { uint32_t req; union { struct fastrpc_ctrl_latency lp; struct fastrpc_ctrl_kalloc kalloc; struct fastrpc_ctrl_wakelock wp; struct fastrpc_ctrl_pm pm; }; }; Loading Loading
drivers/char/adsprpc.c +70 −67 Original line number Diff line number Diff line Loading @@ -136,6 +136,9 @@ #define FASTRPC_STATIC_HANDLE_MAX (20) #define FASTRPC_LATENCY_CTRL_ENB (1) /* Maximum PM timeout that can be voted through fastrpc */ #define MAX_PM_TIMEOUT_MS 50 /* timeout in us for busy polling after early response from remote processor */ #define FASTRPC_POLL_TIME (4000) Loading Loading @@ -304,7 +307,6 @@ struct smq_invoke_ctx { uint32_t early_wake_time; /* work done status flag */ bool is_work_done; bool pm_awake_voted; /* Store Async job in the context*/ struct fastrpc_async_job asyncjob; /* Async early flag to check the state of context */ Loading Loading @@ -399,11 +401,9 @@ struct fastrpc_apps { bool legacy_remote_heap; /* Unique job id for each message */ uint64_t jobid[NUM_CHANNELS]; /* Secure subsystems like ADSP/SLPI will use secure client */ struct wakeup_source *wake_source_secure; /* Non-secure subsystem like CDSP will use regular client */ struct wakeup_source *wake_source; struct gid_list gidlist; struct device *secure_dev; struct device *non_secure_dev; }; struct fastrpc_mmap { Loading Loading @@ -494,6 +494,11 @@ struct fastrpc_file { wait_queue_head_t async_wait_queue; /* IRQ safe spin lock for protecting async queue */ spinlock_t aqlock; /* Secure subsystems like ADSP/SLPI will use secure client */ struct wakeup_source *wake_source_secure; /* Non-secure subsystem like CDSP will use regular client */ struct wakeup_source *wake_source; uint32_t ws_timeout; }; static struct fastrpc_apps gfa; Loading Loading @@ -566,9 +571,7 @@ static struct fastrpc_channel_ctx gcinfo[NUM_CHANNELS] = { static int hlosvm[1] = {VMID_HLOS}; static int hlosvmperm[1] = {PERM_READ | PERM_WRITE | PERM_EXEC}; static void fastrpc_pm_awake(int fl_wake_enable, bool *pm_awake_voted, int channel_type); static void fastrpc_pm_relax(bool *pm_awake_voted, int channel_type); static inline void fastrpc_pm_awake(struct fastrpc_file *fl, int channel_type); static inline int64_t getnstimediff(struct timespec64 *start) { Loading Loading @@ -1417,7 +1420,6 @@ static int context_alloc(struct fastrpc_file *fl, uint32_t kernel, ctx->magic = FASTRPC_CTX_MAGIC; ctx->rsp_flags = NORMAL_RESPONSE; ctx->is_work_done = false; ctx->pm_awake_voted = false; ctx->copybuf = NULL; ctx->is_early_wakeup = false; if (invokefd->job) { Loading Loading @@ -1528,8 +1530,7 @@ static void fastrpc_queue_completed_async_job(struct smq_invoke_ctx *ctx) static void context_notify_user(struct smq_invoke_ctx *ctx, int retval, uint32_t rsp_flags, uint32_t early_wake_time) { fastrpc_pm_awake(ctx->fl->wake_enable, &ctx->pm_awake_voted, gcinfo[ctx->fl->cid].secure); fastrpc_pm_awake(ctx->fl, gcinfo[ctx->fl->cid].secure); ctx->retval = retval; ctx->rsp_flags = (enum fastrpc_response_flags)rsp_flags; trace_fastrpc_context_complete(ctx->fl->cid, (uint64_t)ctx, retval, Loading Loading @@ -2207,31 +2208,22 @@ static void fastrpc_init(struct fastrpc_apps *me) me->channel[CDSP_DOMAIN_ID].secure = NON_SECURE_CHANNEL; } static inline void fastrpc_pm_awake(int fl_wake_enable, bool *pm_awake_voted, int channel_type) static inline void fastrpc_pm_awake(struct fastrpc_file *fl, int channel_type) { struct fastrpc_apps *me = &gfa; struct wakeup_source *wake_source = NULL; if (!fl_wake_enable || *pm_awake_voted) if (!fl->wake_enable || !fl->wake_source || !fl->wake_source_secure) return; /* * Vote with PM to abort any suspend in progress and * keep system awake for specified timeout */ if (channel_type == SECURE_CHANNEL) __pm_stay_awake(me->wake_source_secure); wake_source = fl->wake_source_secure; else if (channel_type == NON_SECURE_CHANNEL) __pm_stay_awake(me->wake_source); *pm_awake_voted = true; } static inline void fastrpc_pm_relax(bool *pm_awake_voted, int channel_type) { struct fastrpc_apps *me = &gfa; wake_source = fl->wake_source; if (!(*pm_awake_voted)) return; if (channel_type == SECURE_CHANNEL) __pm_relax(me->wake_source_secure); else if (channel_type == NON_SECURE_CHANNEL) __pm_relax(me->wake_source); *pm_awake_voted = false; pm_wakeup_ws_event(wake_source, fl->ws_timeout, true); } static inline int fastrpc_wait_for_response(struct smq_invoke_ctx *ctx, Loading Loading @@ -2378,7 +2370,6 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, int err = 0, interrupted = 0, cid = fl->cid; struct timespec64 invoket = {0}; int64_t *perf_counter = NULL; bool pm_awake_voted = false; bool isasyncinvoke = false; VERIFY(err, cid >= ADSP_DOMAIN_ID && cid < NUM_CHANNELS && Loading @@ -2389,7 +2380,6 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, err = -EBADR; goto bail; } fastrpc_pm_awake(fl->wake_enable, &pm_awake_voted, gcinfo[cid].secure); if (fl->profile) { perf_counter = getperfcounter(fl, PERF_COUNT); Loading Loading @@ -2449,9 +2439,7 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, if (isasyncinvoke) goto invoke_end; wait: fastrpc_pm_relax(&pm_awake_voted, gcinfo[cid].secure); fastrpc_wait_for_completion(ctx, &interrupted, kernel, 0); pm_awake_voted = ctx->pm_awake_voted; VERIFY(err, 0 == (err = interrupted)); if (err) goto bail; Loading Loading @@ -2491,7 +2479,6 @@ static int fastrpc_internal_invoke(struct fastrpc_file *fl, uint32_t mode, if (fl->profile && !interrupted) fastrpc_update_invoke_count(invoke->handle, perf_counter, &invoket); fastrpc_pm_relax(&pm_awake_voted, gcinfo[cid].secure); return err; } Loading Loading @@ -3855,6 +3842,8 @@ static int fastrpc_file_free(struct fastrpc_file *fl) spin_lock(&fl->apps->hlock); hlist_del_init(&fl->hn); spin_unlock(&fl->apps->hlock); wakeup_source_unregister(fl->wake_source); wakeup_source_unregister(fl->wake_source_secure); kfree(fl->debug_buf); kfree(fl->gidlist.gids); Loading Loading @@ -4199,6 +4188,21 @@ static int fastrpc_channel_open(struct fastrpc_file *fl) return err; } static inline void fastrpc_register_wakeup_source(struct device *dev, const char *client_name, struct wakeup_source **device_wake_source) { struct wakeup_source *wake_source; wake_source = wakeup_source_register(dev, client_name); if (IS_ERR_OR_NULL(wake_source)) { pr_err("adsprpc: Error: %s: %s: wakeup_source_register failed for %s (%s) with err %ld\n", __func__, current->comm, dev_name(dev), client_name, PTR_ERR(wake_source)); return; } *device_wake_source = wake_source; } static int fastrpc_device_open(struct inode *inode, struct file *filp) { int err = 0; Loading Loading @@ -4237,6 +4241,10 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp) debugfs_file = debugfs_create_file(fl->debug_buf, 0644, debugfs_root, fl, &debugfs_fops); fastrpc_register_wakeup_source(me->non_secure_dev, "adsprpc-non_secure", &fl->wake_source); fastrpc_register_wakeup_source(me->secure_dev, "adsprpc-secure", &fl->wake_source_secure); context_list_ctor(&fl->clst); spin_lock_init(&fl->hlock); spin_lock_init(&fl->aqlock); Loading Loading @@ -4375,8 +4383,26 @@ static int fastrpc_internal_control(struct fastrpc_file *fl, cp->kalloc.kalloc_support = 1; break; case FASTRPC_CONTROL_WAKELOCK: if (fl->dev_minor != MINOR_NUM_SECURE_DEV) { pr_err("adsprpc: %s: %s: PM voting not allowed for non-secure device node %d\n", current->comm, __func__, fl->dev_minor); err = -EPERM; goto bail; } fl->wake_enable = cp->wp.enable; break; case FASTRPC_CONTROL_PM: if (!fl->wake_enable) { /* Kernel PM voting not requested by this application */ err = -EACCES; goto bail; } if (cp->pm.timeout > MAX_PM_TIMEOUT_MS) fl->ws_timeout = MAX_PM_TIMEOUT_MS; else fl->ws_timeout = cp->pm.timeout; fastrpc_pm_awake(fl, gcinfo[fl->cid].secure); break; default: err = -EBADRQC; break; Loading Loading @@ -5205,8 +5231,6 @@ static struct rpmsg_driver fastrpc_rpmsg_client = { static int __init fastrpc_device_init(void) { struct fastrpc_apps *me = &gfa; struct device *dev = NULL; struct device *secure_dev = NULL; int err = 0, i; debugfs_root = debugfs_create_dir("adsprpc", NULL); Loading Loading @@ -5237,26 +5261,26 @@ static int __init fastrpc_device_init(void) * Create devices and register with sysfs * Create first device with minor number 0 */ dev = device_create(me->class, NULL, me->non_secure_dev = device_create(me->class, NULL, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV), NULL, DEVICE_NAME); VERIFY(err, !IS_ERR_OR_NULL(dev)); VERIFY(err, !IS_ERR_OR_NULL(me->non_secure_dev)); if (err) goto device_create_bail; /* Create secure device with minor number for secure device */ secure_dev = device_create(me->class, NULL, me->secure_dev = device_create(me->class, NULL, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV), NULL, DEVICE_NAME_SECURE); VERIFY(err, !IS_ERR_OR_NULL(secure_dev)); VERIFY(err, !IS_ERR_OR_NULL(me->secure_dev)); if (err) goto device_create_bail; for (i = 0; i < NUM_CHANNELS; i++) { me->jobid[i] = 1; me->channel[i].dev = secure_dev; me->channel[i].dev = me->secure_dev; if (i == CDSP_DOMAIN_ID) me->channel[i].dev = dev; me->channel[i].dev = me->non_secure_dev; me->channel[i].ssrcount = 0; me->channel[i].prevssrcount = 0; me->channel[i].issubsystemup = 1; Loading @@ -5283,23 +5307,6 @@ static int __init fastrpc_device_init(void) } me->rpmsg_register = 1; me->wake_source = wakeup_source_register(dev, "adsprpc-non_secure"); VERIFY(err, !IS_ERR_OR_NULL(me->wake_source)); if (err) { pr_err("adsprpc: Error: %s: wakeup_source_register failed for %s with err %ld\n", __func__, dev_name(dev), PTR_ERR(me->wake_source)); goto device_create_bail; } me->wake_source_secure = wakeup_source_register(secure_dev, "adsprpc-secure"); VERIFY(err, !IS_ERR_OR_NULL(me->wake_source_secure)); if (err) { pr_err("adsprpc: Error: %s: wakeup_source_register failed for %s with err %ld\n", __func__, dev_name(secure_dev), PTR_ERR(me->wake_source_secure)); goto device_create_bail; } return 0; device_create_bail: for (i = 0; i < NUM_CHANNELS; i++) { Loading @@ -5307,10 +5314,10 @@ static int __init fastrpc_device_init(void) subsys_notif_unregister_notifier(me->channel[i].handle, &me->channel[i].nb); } if (!IS_ERR_OR_NULL(dev)) if (!IS_ERR_OR_NULL(me->non_secure_dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV)); if (!IS_ERR_OR_NULL(secure_dev)) if (!IS_ERR_OR_NULL(me->secure_dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV)); class_destroy(me->class); Loading Loading @@ -5349,10 +5356,6 @@ static void __exit fastrpc_device_exit(void) unregister_chrdev_region(me->dev_no, NUM_CHANNELS); if (me->rpmsg_register == 1) unregister_rpmsg_driver(&fastrpc_rpmsg_client); if (me->wake_source) wakeup_source_unregister(me->wake_source); if (me->wake_source_secure) wakeup_source_unregister(me->wake_source_secure); kfree(me->gidlist.gids); debugfs_remove_recursive(debugfs_root); } Loading
drivers/char/adsprpc_compat.c +16 −0 Original line number Diff line number Diff line Loading @@ -148,11 +148,21 @@ struct compat_fastrpc_ctrl_kalloc { compat_uint_t kalloc_support; /* Remote memory allocation from kernel */ }; struct compat_fastrpc_ctrl_wakelock { compat_uint_t enable; /* wakelock control enable */ }; struct compat_fastrpc_ctrl_pm { compat_uint_t timeout; /* timeout(in ms) for PM to keep system awake */ }; struct compat_fastrpc_ioctl_control { compat_uint_t req; union { struct compat_fastrpc_ctrl_latency lp; struct compat_fastrpc_ctrl_kalloc kalloc; struct compat_fastrpc_ctrl_wakelock wp; struct compat_fastrpc_ctrl_pm pm; }; }; Loading Loading @@ -493,6 +503,12 @@ static int compat_get_fastrpc_ioctl_control( err |= put_user(p, &ctrl->lp.enable); err |= get_user(p, &ctrl32->lp.latency); err |= put_user(p, &ctrl->lp.latency); } else if (p == FASTRPC_CONTROL_WAKELOCK) { err |= get_user(p, &ctrl32->wp.enable); err |= put_user(p, &ctrl->wp.enable); } else if (p == FASTRPC_CONTROL_PM) { err |= get_user(p, &ctrl32->pm.timeout); err |= put_user(p, &ctrl->pm.timeout); } return err; Loading
drivers/char/adsprpc_shared.h +6 −0 Original line number Diff line number Diff line Loading @@ -282,6 +282,7 @@ enum fastrpc_control_type { FASTRPC_CONTROL_SMMU = 2, FASTRPC_CONTROL_KALLOC = 3, FASTRPC_CONTROL_WAKELOCK = 4, FASTRPC_CONTROL_PM = 5, }; struct fastrpc_ctrl_latency { Loading @@ -297,12 +298,17 @@ struct fastrpc_ctrl_wakelock { uint32_t enable; /* wakelock control enable */ }; struct fastrpc_ctrl_pm { uint32_t timeout; /* timeout(in ms) for PM to keep system awake */ }; struct fastrpc_ioctl_control { uint32_t req; union { struct fastrpc_ctrl_latency lp; struct fastrpc_ctrl_kalloc kalloc; struct fastrpc_ctrl_wakelock wp; struct fastrpc_ctrl_pm pm; }; }; Loading