diff options
Diffstat (limited to 'drivers/dsp/syslink/multicore_ipc/nameserver_ioctl.c')
-rw-r--r-- | drivers/dsp/syslink/multicore_ipc/nameserver_ioctl.c | 118 |
1 files changed, 99 insertions, 19 deletions
diff --git a/drivers/dsp/syslink/multicore_ipc/nameserver_ioctl.c b/drivers/dsp/syslink/multicore_ipc/nameserver_ioctl.c index c4cc75e40cb6..4411bef0dc41 100644 --- a/drivers/dsp/syslink/multicore_ipc/nameserver_ioctl.c +++ b/drivers/dsp/syslink/multicore_ipc/nameserver_ioctl.c @@ -27,6 +27,50 @@ * FUNCTIONS NEED TO BE REVIEWED OPTIMIZED! */ +static struct resource_info *find_nameserver_resource( + struct ipc_process_context *pr_ctxt, + unsigned int cmd, + struct nameserver_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 nameserver_cmd_args *args = + (struct nameserver_cmd_args *)info->data; + if (info->cmd == cmd) { + switch (cmd) { + case CMD_NAMESERVER_DELETE: + { + void *handle = + args->args.delete_instance.handle; + void *temp = + cargs->args.delete_instance.handle; + if (temp == handle) + found = true; + break; + } + case CMD_NAMESERVER_DESTROY: + { + found = true; + break; + } + } + if (found == true) + break; + } + } + + spin_unlock(&pr_ctxt->res_lock); + + if (found == false) + info = NULL; + + return info; +} + /* * ======== nameserver_ioctl_setup ======== * Purpose: @@ -489,31 +533,39 @@ exit: * This ioctl interface for nameserver module */ int nameserver_ioctl(struct inode *inode, struct file *filp, - unsigned int cmd, unsigned long args) + unsigned int cmd, unsigned long args, bool user) { s32 status = 0; s32 size = 0; struct nameserver_cmd_args __user *uarg = (struct nameserver_cmd_args __user *)args; struct nameserver_cmd_args cargs; + struct ipc_process_context *pr_ctxt = + (struct ipc_process_context *)filp->private_data; - 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 (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 (status) { + 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 nameserver_cmd_args)); - if (size) { - status = -EFAULT; - goto exit; + if (size) { + status = -EFAULT; + goto exit; + } + } else { + if (args != 0) + memcpy(&cargs, (void *)args, + sizeof(struct nameserver_cmd_args)); } switch (cmd) { @@ -551,11 +603,27 @@ int nameserver_ioctl(struct inode *inode, struct file *filp, case CMD_NAMESERVER_CREATE: status = nameserver_ioctl_create(&cargs); + if (status >= 0) { + struct nameserver_cmd_args *temp = kmalloc( + sizeof(struct nameserver_cmd_args), + GFP_KERNEL); + temp->args.delete_instance.handle = + cargs.args.create.handle; + add_pr_res(pr_ctxt, CMD_NAMESERVER_DELETE, + (void *)temp); + } break; case CMD_NAMESERVER_DELETE: + { + struct resource_info *info = NULL; + info = find_nameserver_resource(pr_ctxt, + CMD_NAMESERVER_DELETE, + &cargs); status = nameserver_ioctl_delete(&cargs); + remove_pr_res(pr_ctxt, info); break; + } case CMD_NAMESERVER_GETHANDLE: status = nameserver_ioctl_get_handle(&cargs); @@ -563,11 +631,20 @@ int nameserver_ioctl(struct inode *inode, struct file *filp, case CMD_NAMESERVER_SETUP: status = nameserver_ioctl_setup(&cargs); + if (cargs.api_status >= 0) + add_pr_res(pr_ctxt, CMD_NAMESERVER_DESTROY, NULL); break; case CMD_NAMESERVER_DESTROY: + { + struct resource_info *info = NULL; + info = find_nameserver_resource(pr_ctxt, + CMD_NAMESERVER_DESTROY, + &cargs); status = nameserver_ioctl_destroy(&cargs); + remove_pr_res(pr_ctxt, info); break; + } default: WARN_ON(cmd); @@ -581,11 +658,14 @@ int nameserver_ioctl(struct inode *inode, struct file *filp, if (status < 0) goto exit; - /* Copy the full args to the user-side. */ - size = copy_to_user(uarg, &cargs, sizeof(struct nameserver_cmd_args)); - if (size) { - status = -EFAULT; - goto exit; + if (user == true) { + /* Copy the full args to the user-side. */ + size = copy_to_user(uarg, &cargs, + sizeof(struct nameserver_cmd_args)); + if (size) { + status = -EFAULT; + goto exit; + } } exit: |