Loading Documentation/devicetree/bindings/qdsp/msm-fastrpc.txt +1 −0 Original line number Diff line number Diff line Loading @@ -13,6 +13,7 @@ Optional properties: - qcom,fastrpc-glink: Flag to use glink instead of smd for IPC - qcom,fastrpc-vmid-heap-shared: Flag for Dynamic heap feature, to share HLOS memory buffer to ADSP - qcom,secure-domains: FastRPC secure domain configuration Optional subnodes: - qcom,msm_fastrpc_compute_cb : Child nodes representing the compute context Loading drivers/char/adsprpc.c +117 −8 Original line number Diff line number Diff line /* * Copyright (c) 2012-2019, The Linux Foundation. All rights reserved. * Copyright (c) 2012-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading Loading @@ -72,6 +72,16 @@ #define FASTRPC_CTX_MAGIC (0xbeeddeed) #define FASTRPC_CTX_MAX (256) #define FASTRPC_CTXID_MASK (0xFF0) #define NUM_DEVICES 2 /* adsprpc-smd, adsprpc-smd-secure */ #define MINOR_NUM_DEV 0 #define MINOR_NUM_SECURE_DEV 1 #define NON_SECURE_CHANNEL 0 #define SECURE_CHANNEL 1 #define ADSP_DOMAIN_ID (0) #define MDSP_DOMAIN_ID (1) #define SDSP_DOMAIN_ID (2) #define CDSP_DOMAIN_ID (3) #define IS_CACHE_ALIGNED(x) (((x) & ((L1_CACHE_BYTES)-1)) == 0) Loading Loading @@ -245,6 +255,8 @@ struct fastrpc_channel_ctx { int ramdumpenabled; void *remoteheap_ramdump_dev; struct fastrpc_glink_info link; /* Indicates, if channel is restricted to secure node only */ int secure; }; struct fastrpc_apps { Loading Loading @@ -321,6 +333,8 @@ struct fastrpc_file { struct dentry *debugfs_file; struct mutex map_mutex; char *debug_buf; /* Identifies the device (MINOR_NUM_DEV / MINOR_NUM_SECURE_DEV) */ int dev_minor; }; static struct fastrpc_apps gfa; Loading Loading @@ -1683,7 +1697,11 @@ static void fastrpc_init(struct fastrpc_apps *me) init_completion(&me->channel[i].work); init_completion(&me->channel[i].workport); me->channel[i].sesscount = 0; /* All channels are secure by default except CDSP */ me->channel[i].secure = SECURE_CHANNEL; } /* Set CDSP channel to non secure */ me->channel[CDSP_DOMAIN_ID].secure = NON_SECURE_CHANNEL; } static int fastrpc_release_current_dsp_process(struct fastrpc_file *fl); Loading Loading @@ -2725,6 +2743,9 @@ static ssize_t fastrpc_debugfs_read(struct file *filp, char __user *buffer, len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "|%-9d", chan->ssrcount); len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "%s %d\n", "secure:", chan->secure); for (j = 0; j < chan->sesscount; j++) { sess_used += chan->session[j].used; } Loading Loading @@ -2818,6 +2839,9 @@ static ssize_t fastrpc_debugfs_read(struct file *filp, char __user *buffer, "0x%-20lX|0x%-20llX|0x%-20zu\n\n", map->va, map->phys, map->size); len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "%s %d\n\n", "DEV_MINOR:", fl->dev_minor); } len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "%-20s|%-20s|%-20s|%-20s\n", Loading Loading @@ -2974,6 +2998,19 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp) char strpid[PID_SIZE]; int buf_size = 0; /* * Indicates the device node opened * MINOR_NUM_DEV or MINOR_NUM_SECURE_DEV */ int dev_minor = MINOR(inode->i_rdev); VERIFY(err, ((dev_minor == MINOR_NUM_DEV) || (dev_minor == MINOR_NUM_SECURE_DEV))); if (err) { pr_err("adsprpc: Invalid dev minor num %d\n", dev_minor); return err; } VERIFY(err, NULL != (fl = kzalloc(sizeof(*fl), GFP_KERNEL))); if (err) return err; Loading @@ -3000,6 +3037,7 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp) fl->mode = FASTRPC_MODE_SERIAL; fl->cid = -1; fl->init_mem = NULL; fl->dev_minor = dev_minor; if (debugfs_file != NULL) fl->debugfs_file = debugfs_file; Loading @@ -3025,6 +3063,23 @@ static int fastrpc_get_info(struct fastrpc_file *fl, uint32_t *info) VERIFY(err, cid < NUM_CHANNELS); if (err) goto bail; /* Check to see if the device node is non-secure */ if (fl->dev_minor == MINOR_NUM_DEV) { /* * For non secure device node check and make sure that * the channel allows non-secure access * If not, bail. Session will not start. * cid will remain -1 and client will not be able to * invoke any other methods without failure */ if (fl->apps->channel[cid].secure == SECURE_CHANNEL) { err = -EPERM; pr_err("adsprpc: GetInfo failed dev %d, cid %d, secure %d\n", fl->dev_minor, cid, fl->apps->channel[cid].secure); goto bail; } } fl->cid = cid; fl->ssrcount = fl->apps->channel[cid].ssrcount; VERIFY(err, !fastrpc_session_alloc_locked( Loading Loading @@ -3462,12 +3517,41 @@ bail: return err; } static void configure_secure_channels(uint32_t secure_domains) { struct fastrpc_apps *me = &gfa; int ii = 0; /* * secure_domains contains the bitmask of the secure channels * Bit 0 - ADSP * Bit 1 - MDSP * Bit 2 - SLPI * Bit 3 - CDSP */ for (ii = ADSP_DOMAIN_ID; ii <= CDSP_DOMAIN_ID; ++ii) { int secure = (secure_domains >> ii) & 0x01; me->channel[ii].secure = secure; } } static int fastrpc_probe(struct platform_device *pdev) { int err = 0; struct fastrpc_apps *me = &gfa; struct device *dev = &pdev->dev; uint32_t secure_domains; if (of_get_property(dev->of_node, "qcom,secure-domains", NULL) != NULL) { VERIFY(err, !of_property_read_u32(dev->of_node, "qcom,secure-domains", &secure_domains)); if (!err) configure_secure_channels(secure_domains); else pr_info("adsprpc: unable to read the domain configuration from dts\n"); } if (of_device_is_compatible(dev->of_node, "qcom,msm-fastrpc-compute-cb")) return fastrpc_cb_probe(dev); Loading Loading @@ -3543,6 +3627,7 @@ 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 @@ -3559,7 +3644,7 @@ static int __init fastrpc_device_init(void) cdev_init(&me->cdev, &fops); me->cdev.owner = THIS_MODULE; VERIFY(err, 0 == cdev_add(&me->cdev, MKDEV(MAJOR(me->dev_no), 0), 1)); NUM_DEVICES)); if (err) goto cdev_init_bail; me->class = class_create(THIS_MODULE, "fastrpc"); Loading @@ -3567,13 +3652,28 @@ static int __init fastrpc_device_init(void) if (err) goto class_create_bail; me->compat = (NULL == fops.compat_ioctl) ? 0 : 1; /* * Create devices and register with sysfs * Create first device with minor number 0 */ dev = device_create(me->class, NULL, MKDEV(MAJOR(me->dev_no), 0), NULL, gcinfo[0].name); MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV), NULL, DEVICE_NAME); VERIFY(err, !IS_ERR_OR_NULL(dev)); if (err) goto device_create_bail; /* Create secure device with minor number for secure device */ 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)); if (err) goto device_create_bail; for (i = 0; i < NUM_CHANNELS; i++) { me->channel[i].dev = secure_dev; if (i == CDSP_DOMAIN_ID) me->channel[i].dev = dev; me->channel[i].ssrcount = 0; me->channel[i].prevssrcount = 0; Loading @@ -3598,7 +3698,11 @@ device_create_bail: &me->channel[i].nb); } if (!IS_ERR_OR_NULL(dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), 0)); device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV)); if (!IS_ERR_OR_NULL(secure_dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV)); class_destroy(me->class); class_create_bail: cdev_del(&me->cdev); Loading @@ -3620,10 +3724,15 @@ static void __exit fastrpc_device_exit(void) for (i = 0; i < NUM_CHANNELS; i++) { if (!gcinfo[i].name) continue; device_destroy(me->class, MKDEV(MAJOR(me->dev_no), i)); subsys_notif_unregister_notifier(me->channel[i].handle, &me->channel[i].nb); } /* Destroy the secure and non secure devices */ device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV)); device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV)); class_destroy(me->class); cdev_del(&me->cdev); unregister_chrdev_region(me->dev_no, NUM_CHANNELS); Loading drivers/char/adsprpc_shared.h +1 −0 Original line number Diff line number Diff line Loading @@ -34,6 +34,7 @@ #define FASTRPC_GLINK_GUID "fastrpcglink-apps-dsp" #define FASTRPC_SMD_GUID "fastrpcsmd-apps-dsp" #define DEVICE_NAME "adsprpc-smd" #define DEVICE_NAME_SECURE "adsprpc-smd-secure" /* Set for buffers that have no virtual mapping in userspace */ #define FASTRPC_ATTR_NOVA 0x1 Loading Loading
Documentation/devicetree/bindings/qdsp/msm-fastrpc.txt +1 −0 Original line number Diff line number Diff line Loading @@ -13,6 +13,7 @@ Optional properties: - qcom,fastrpc-glink: Flag to use glink instead of smd for IPC - qcom,fastrpc-vmid-heap-shared: Flag for Dynamic heap feature, to share HLOS memory buffer to ADSP - qcom,secure-domains: FastRPC secure domain configuration Optional subnodes: - qcom,msm_fastrpc_compute_cb : Child nodes representing the compute context Loading
drivers/char/adsprpc.c +117 −8 Original line number Diff line number Diff line /* * Copyright (c) 2012-2019, The Linux Foundation. All rights reserved. * Copyright (c) 2012-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading Loading @@ -72,6 +72,16 @@ #define FASTRPC_CTX_MAGIC (0xbeeddeed) #define FASTRPC_CTX_MAX (256) #define FASTRPC_CTXID_MASK (0xFF0) #define NUM_DEVICES 2 /* adsprpc-smd, adsprpc-smd-secure */ #define MINOR_NUM_DEV 0 #define MINOR_NUM_SECURE_DEV 1 #define NON_SECURE_CHANNEL 0 #define SECURE_CHANNEL 1 #define ADSP_DOMAIN_ID (0) #define MDSP_DOMAIN_ID (1) #define SDSP_DOMAIN_ID (2) #define CDSP_DOMAIN_ID (3) #define IS_CACHE_ALIGNED(x) (((x) & ((L1_CACHE_BYTES)-1)) == 0) Loading Loading @@ -245,6 +255,8 @@ struct fastrpc_channel_ctx { int ramdumpenabled; void *remoteheap_ramdump_dev; struct fastrpc_glink_info link; /* Indicates, if channel is restricted to secure node only */ int secure; }; struct fastrpc_apps { Loading Loading @@ -321,6 +333,8 @@ struct fastrpc_file { struct dentry *debugfs_file; struct mutex map_mutex; char *debug_buf; /* Identifies the device (MINOR_NUM_DEV / MINOR_NUM_SECURE_DEV) */ int dev_minor; }; static struct fastrpc_apps gfa; Loading Loading @@ -1683,7 +1697,11 @@ static void fastrpc_init(struct fastrpc_apps *me) init_completion(&me->channel[i].work); init_completion(&me->channel[i].workport); me->channel[i].sesscount = 0; /* All channels are secure by default except CDSP */ me->channel[i].secure = SECURE_CHANNEL; } /* Set CDSP channel to non secure */ me->channel[CDSP_DOMAIN_ID].secure = NON_SECURE_CHANNEL; } static int fastrpc_release_current_dsp_process(struct fastrpc_file *fl); Loading Loading @@ -2725,6 +2743,9 @@ static ssize_t fastrpc_debugfs_read(struct file *filp, char __user *buffer, len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "|%-9d", chan->ssrcount); len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "%s %d\n", "secure:", chan->secure); for (j = 0; j < chan->sesscount; j++) { sess_used += chan->session[j].used; } Loading Loading @@ -2818,6 +2839,9 @@ static ssize_t fastrpc_debugfs_read(struct file *filp, char __user *buffer, "0x%-20lX|0x%-20llX|0x%-20zu\n\n", map->va, map->phys, map->size); len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "%s %d\n\n", "DEV_MINOR:", fl->dev_minor); } len += scnprintf(fileinfo + len, DEBUGFS_SIZE - len, "%-20s|%-20s|%-20s|%-20s\n", Loading Loading @@ -2974,6 +2998,19 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp) char strpid[PID_SIZE]; int buf_size = 0; /* * Indicates the device node opened * MINOR_NUM_DEV or MINOR_NUM_SECURE_DEV */ int dev_minor = MINOR(inode->i_rdev); VERIFY(err, ((dev_minor == MINOR_NUM_DEV) || (dev_minor == MINOR_NUM_SECURE_DEV))); if (err) { pr_err("adsprpc: Invalid dev minor num %d\n", dev_minor); return err; } VERIFY(err, NULL != (fl = kzalloc(sizeof(*fl), GFP_KERNEL))); if (err) return err; Loading @@ -3000,6 +3037,7 @@ static int fastrpc_device_open(struct inode *inode, struct file *filp) fl->mode = FASTRPC_MODE_SERIAL; fl->cid = -1; fl->init_mem = NULL; fl->dev_minor = dev_minor; if (debugfs_file != NULL) fl->debugfs_file = debugfs_file; Loading @@ -3025,6 +3063,23 @@ static int fastrpc_get_info(struct fastrpc_file *fl, uint32_t *info) VERIFY(err, cid < NUM_CHANNELS); if (err) goto bail; /* Check to see if the device node is non-secure */ if (fl->dev_minor == MINOR_NUM_DEV) { /* * For non secure device node check and make sure that * the channel allows non-secure access * If not, bail. Session will not start. * cid will remain -1 and client will not be able to * invoke any other methods without failure */ if (fl->apps->channel[cid].secure == SECURE_CHANNEL) { err = -EPERM; pr_err("adsprpc: GetInfo failed dev %d, cid %d, secure %d\n", fl->dev_minor, cid, fl->apps->channel[cid].secure); goto bail; } } fl->cid = cid; fl->ssrcount = fl->apps->channel[cid].ssrcount; VERIFY(err, !fastrpc_session_alloc_locked( Loading Loading @@ -3462,12 +3517,41 @@ bail: return err; } static void configure_secure_channels(uint32_t secure_domains) { struct fastrpc_apps *me = &gfa; int ii = 0; /* * secure_domains contains the bitmask of the secure channels * Bit 0 - ADSP * Bit 1 - MDSP * Bit 2 - SLPI * Bit 3 - CDSP */ for (ii = ADSP_DOMAIN_ID; ii <= CDSP_DOMAIN_ID; ++ii) { int secure = (secure_domains >> ii) & 0x01; me->channel[ii].secure = secure; } } static int fastrpc_probe(struct platform_device *pdev) { int err = 0; struct fastrpc_apps *me = &gfa; struct device *dev = &pdev->dev; uint32_t secure_domains; if (of_get_property(dev->of_node, "qcom,secure-domains", NULL) != NULL) { VERIFY(err, !of_property_read_u32(dev->of_node, "qcom,secure-domains", &secure_domains)); if (!err) configure_secure_channels(secure_domains); else pr_info("adsprpc: unable to read the domain configuration from dts\n"); } if (of_device_is_compatible(dev->of_node, "qcom,msm-fastrpc-compute-cb")) return fastrpc_cb_probe(dev); Loading Loading @@ -3543,6 +3627,7 @@ 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 @@ -3559,7 +3644,7 @@ static int __init fastrpc_device_init(void) cdev_init(&me->cdev, &fops); me->cdev.owner = THIS_MODULE; VERIFY(err, 0 == cdev_add(&me->cdev, MKDEV(MAJOR(me->dev_no), 0), 1)); NUM_DEVICES)); if (err) goto cdev_init_bail; me->class = class_create(THIS_MODULE, "fastrpc"); Loading @@ -3567,13 +3652,28 @@ static int __init fastrpc_device_init(void) if (err) goto class_create_bail; me->compat = (NULL == fops.compat_ioctl) ? 0 : 1; /* * Create devices and register with sysfs * Create first device with minor number 0 */ dev = device_create(me->class, NULL, MKDEV(MAJOR(me->dev_no), 0), NULL, gcinfo[0].name); MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV), NULL, DEVICE_NAME); VERIFY(err, !IS_ERR_OR_NULL(dev)); if (err) goto device_create_bail; /* Create secure device with minor number for secure device */ 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)); if (err) goto device_create_bail; for (i = 0; i < NUM_CHANNELS; i++) { me->channel[i].dev = secure_dev; if (i == CDSP_DOMAIN_ID) me->channel[i].dev = dev; me->channel[i].ssrcount = 0; me->channel[i].prevssrcount = 0; Loading @@ -3598,7 +3698,11 @@ device_create_bail: &me->channel[i].nb); } if (!IS_ERR_OR_NULL(dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), 0)); device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV)); if (!IS_ERR_OR_NULL(secure_dev)) device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV)); class_destroy(me->class); class_create_bail: cdev_del(&me->cdev); Loading @@ -3620,10 +3724,15 @@ static void __exit fastrpc_device_exit(void) for (i = 0; i < NUM_CHANNELS; i++) { if (!gcinfo[i].name) continue; device_destroy(me->class, MKDEV(MAJOR(me->dev_no), i)); subsys_notif_unregister_notifier(me->channel[i].handle, &me->channel[i].nb); } /* Destroy the secure and non secure devices */ device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_DEV)); device_destroy(me->class, MKDEV(MAJOR(me->dev_no), MINOR_NUM_SECURE_DEV)); class_destroy(me->class); cdev_del(&me->cdev); unregister_chrdev_region(me->dev_no, NUM_CHANNELS); Loading
drivers/char/adsprpc_shared.h +1 −0 Original line number Diff line number Diff line Loading @@ -34,6 +34,7 @@ #define FASTRPC_GLINK_GUID "fastrpcglink-apps-dsp" #define FASTRPC_SMD_GUID "fastrpcsmd-apps-dsp" #define DEVICE_NAME "adsprpc-smd" #define DEVICE_NAME_SECURE "adsprpc-smd-secure" /* Set for buffers that have no virtual mapping in userspace */ #define FASTRPC_ATTR_NOVA 0x1 Loading