diff options
author | Angela Stegmaier <angelabaker@ti.com> | 2010-06-22 18:00:47 -0500 |
---|---|---|
committer | Ricardo Perez Olivares <x0081762@ti.com> | 2010-07-16 17:41:48 -0500 |
commit | 05fca4546d51e1363872cb623167e738944fd191 (patch) | |
tree | a4c29e54e1ba8276db6f03d7267d18aff4a016eb | |
parent | 42b92332d1e4724b256b1cbca4c3ccdcbd4f626e (diff) |
SYSLINK: ipc- resource cleanup sharedregion changes
Changes to sharedregion for resource cleanup.
Signed-off-by: Angela Stegmaier <angelabaker@ti.com>
-rw-r--r-- | arch/arm/plat-omap/include/syslink/sharedregion_ioctl.h | 2 | ||||
-rw-r--r-- | drivers/dsp/syslink/multicore_ipc/ipc_ioctl.c | 2 | ||||
-rw-r--r-- | drivers/dsp/syslink/multicore_ipc/sharedregion_ioctl.c | 156 |
3 files changed, 119 insertions, 41 deletions
diff --git a/arch/arm/plat-omap/include/syslink/sharedregion_ioctl.h b/arch/arm/plat-omap/include/syslink/sharedregion_ioctl.h index 4d45df002046..b095dcf9771e 100644 --- a/arch/arm/plat-omap/include/syslink/sharedregion_ioctl.h +++ b/arch/arm/plat-omap/include/syslink/sharedregion_ioctl.h @@ -184,6 +184,6 @@ struct sharedregion_cmd_args { * This ioctl interface for sharedregion module */ int sharedregion_ioctl(struct inode *inode, struct file *filp, - unsigned int cmd, unsigned long args); + unsigned int cmd, unsigned long args, bool user); #endif /* _SHAREDREGION_IOCTL_H */ diff --git a/drivers/dsp/syslink/multicore_ipc/ipc_ioctl.c b/drivers/dsp/syslink/multicore_ipc/ipc_ioctl.c index b0c695e16009..7088496e17f0 100644 --- a/drivers/dsp/syslink/multicore_ipc/ipc_ioctl.c +++ b/drivers/dsp/syslink/multicore_ipc/ipc_ioctl.c @@ -77,7 +77,7 @@ int ipc_ioc_router(u32 cmd, ulong arg, struct file *filp, bool user) retval = heapbufmp_ioctl(NULL, filp, cmd, arg, user); else if (ioc_nr >= SHAREDREGION_BASE_CMD && ioc_nr <= SHAREDREGION_END_CMD) - retval = sharedregion_ioctl(NULL, filp, cmd, arg); + retval = sharedregion_ioctl(NULL, filp, cmd, arg, user); else if (ioc_nr >= GATEMP_BASE_CMD && ioc_nr <= GATEMP_END_CMD) retval = gatemp_ioctl(NULL, filp, cmd, arg); else if (ioc_nr >= LISTMP_BASE_CMD && ioc_nr <= LISTMP_END_CMD) diff --git a/drivers/dsp/syslink/multicore_ipc/sharedregion_ioctl.c b/drivers/dsp/syslink/multicore_ipc/sharedregion_ioctl.c index 646e34a00790..2e8b2bcfbb0a 100644 --- a/drivers/dsp/syslink/multicore_ipc/sharedregion_ioctl.c +++ b/drivers/dsp/syslink/multicore_ipc/sharedregion_ioctl.c @@ -21,12 +21,56 @@ #include <linux/types.h> #include <linux/bug.h> #include <linux/fs.h> +#include <linux/mm.h> +#include <linux/slab.h> #include <multiproc.h> #include <sharedregion.h> #include <sharedregion_ioctl.h> #include <platform_mem.h> +static struct resource_info *find_sharedregion_resource( + struct ipc_process_context *pr_ctxt, + unsigned int cmd, + struct sharedregion_cmd_args *cargs) +{ + struct resource_info *info = NULL; + bool found = false; + + spin_lock(&pr_ctxt->res_lock); + + list_for_each_entry(info, &pr_ctxt->resources, res) { + struct sharedregion_cmd_args *args = + (struct sharedregion_cmd_args *)info->data; + if (info->cmd == cmd) { + switch (cmd) { + case CMD_SHAREDREGION_CLEARENTRY: + { + u16 id = args->args.clear_entry.id; + u16 temp = cargs->args.clear_entry.id; + if (temp == id) + found = true; + break; + } + case CMD_SHAREDREGION_DESTROY: + { + found = true; + break; + } + } + if (found == true) + break; + } + } + + spin_unlock(&pr_ctxt->res_lock); + + if (found == false) + info = NULL; + + return info; +} + /* This ioctl interface to sharedregion_get_config function */ static int sharedregion_ioctl_get_config(struct sharedregion_cmd_args *cargs) { @@ -378,102 +422,136 @@ exit: /* This ioctl interface for sharedregion module */ int sharedregion_ioctl(struct inode *inode, struct file *filp, - unsigned int cmd, unsigned long args) + unsigned int cmd, unsigned long args, bool user) { - s32 os_status = 0; + s32 status = 0; s32 size = 0; struct sharedregion_cmd_args __user *uarg = (struct sharedregion_cmd_args __user *)args; struct sharedregion_cmd_args cargs; + struct ipc_process_context *pr_ctxt = + (struct ipc_process_context *)filp->private_data; + + if (user == true) { + if (_IOC_DIR(cmd) & _IOC_READ) + status = !access_ok(VERIFY_WRITE, uarg, _IOC_SIZE(cmd)); + else if (_IOC_DIR(cmd) & _IOC_WRITE) + status = !access_ok(VERIFY_READ, uarg, _IOC_SIZE(cmd)); + + if (status) { + status = -EFAULT; + goto exit; + } - if (_IOC_DIR(cmd) & _IOC_READ) - os_status = !access_ok(VERIFY_WRITE, uarg, _IOC_SIZE(cmd)); - else if (_IOC_DIR(cmd) & _IOC_WRITE) - os_status = !access_ok(VERIFY_READ, uarg, _IOC_SIZE(cmd)); - - if (os_status) { - os_status = -EFAULT; - goto exit; - } - - /* Copy the full args from user-side */ - size = copy_from_user(&cargs, uarg, + /* Copy the full args from user-side */ + size = copy_from_user(&cargs, uarg, sizeof(struct sharedregion_cmd_args)); - if (size) { - os_status = -EFAULT; - goto exit; + if (size) { + status = -EFAULT; + goto exit; + } + } else { + if (args != 0) + memcpy(&cargs, (void *)args, + sizeof(struct sharedregion_cmd_args)); } switch (cmd) { case CMD_SHAREDREGION_GETCONFIG: - os_status = sharedregion_ioctl_get_config(&cargs); + status = sharedregion_ioctl_get_config(&cargs); break; case CMD_SHAREDREGION_SETUP: - os_status = sharedregion_ioctl_setup(&cargs); + status = sharedregion_ioctl_setup(&cargs); + if (status >= 0) + add_pr_res(pr_ctxt, CMD_SHAREDREGION_DESTROY, NULL); break; case CMD_SHAREDREGION_DESTROY: - os_status = sharedregion_ioctl_destroy(&cargs); + { + struct resource_info *info = NULL; + info = find_sharedregion_resource(pr_ctxt, + CMD_SHAREDREGION_DESTROY, + &cargs); + status = sharedregion_ioctl_destroy(&cargs); + remove_pr_res(pr_ctxt, info); break; + } case CMD_SHAREDREGION_START: - os_status = sharedregion_ioctl_start(&cargs); + status = sharedregion_ioctl_start(&cargs); break; case CMD_SHAREDREGION_STOP: - os_status = sharedregion_ioctl_stop(&cargs); + status = sharedregion_ioctl_stop(&cargs); break; case CMD_SHAREDREGION_ATTACH: - os_status = sharedregion_ioctl_attach(&cargs); + status = sharedregion_ioctl_attach(&cargs); break; case CMD_SHAREDREGION_DETACH: - os_status = sharedregion_ioctl_detach(&cargs); + status = sharedregion_ioctl_detach(&cargs); break; case CMD_SHAREDREGION_GETHEAP: - os_status = sharedregion_ioctl_get_heap(&cargs); + status = sharedregion_ioctl_get_heap(&cargs); break; case CMD_SHAREDREGION_CLEARENTRY: - os_status = sharedregion_ioctl_clear_entry(&cargs); + { + struct resource_info *info = NULL; + info = find_sharedregion_resource(pr_ctxt, + CMD_SHAREDREGION_CLEARENTRY, + &cargs); + status = sharedregion_ioctl_clear_entry(&cargs); + remove_pr_res(pr_ctxt, info); break; + } case CMD_SHAREDREGION_SETENTRY: - os_status = sharedregion_ioctl_set_entry(&cargs); + status = sharedregion_ioctl_set_entry(&cargs); + if (status >= 0) { + struct sharedregion_cmd_args *temp = + kmalloc(sizeof(struct sharedregion_cmd_args), + GFP_KERNEL); + temp->args.clear_entry.id = cargs.args.set_entry.id; + add_pr_res(pr_ctxt, CMD_SHAREDREGION_CLEARENTRY, temp); + } break; case CMD_SHAREDREGION_RESERVEMEMORY: - os_status = sharedregion_ioctl_reserve_memory(&cargs); + status = sharedregion_ioctl_reserve_memory(&cargs); break; case CMD_SHAREDREGION_CLEARRESERVEDMEMORY: - os_status = sharedregion_ioctl_clear_reserved_memory(&cargs); + status = sharedregion_ioctl_clear_reserved_memory(&cargs); break; case CMD_SHAREDREGION_GETREGIONINFO: - os_status = sharedregion_ioctl_get_region_info(&cargs); + status = sharedregion_ioctl_get_region_info(&cargs); break; default: WARN_ON(cmd); - os_status = -ENOTTY; + status = -ENOTTY; break; } - /* Copy the full args to the user-side. */ - size = copy_to_user(uarg, &cargs, sizeof(struct sharedregion_cmd_args)); - if (size) { - os_status = -EFAULT; - goto exit; + if (user == true) { + /* Copy the full args to the user-side. */ + size = copy_to_user(uarg, &cargs, + sizeof(struct sharedregion_cmd_args)); + if (size) { + status = -EFAULT; + goto exit; + } } exit: - if (os_status < 0) { + if (status < 0) { printk(KERN_ERR "sharedregion_ioctl failed! status = 0x%x", - os_status); + status); } - return os_status; + return status; } |