diff --git a/drivers/char/adsprpc.c b/drivers/char/adsprpc.c index 0fe92ba12568..28755e98ddbf 100644 --- a/drivers/char/adsprpc.c +++ b/drivers/char/adsprpc.c @@ -1,6 +1,7 @@ // SPDX-License-Identifier: GPL-2.0-only /* * Copyright (c) 2012-2021, The Linux Foundation. All rights reserved. + * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved. */ /* Uncomment this block to log an error on every VERIFY failure */ @@ -529,6 +530,8 @@ struct fastrpc_apps { struct hlist_head drivers; spinlock_t hlock; struct device *dev; + /* Indicates fastrpc device node info */ + struct device *dev_fastrpc; unsigned int latency; int rpmsg_register; bool legacy_remote_heap; @@ -547,6 +550,8 @@ struct fastrpc_apps { void *ramdump_handle; bool enable_ramdump; struct mutex mut_uid; + /* Indicates cdsp device status */ + int remote_cdsp_status; }; struct fastrpc_mmap { @@ -2972,6 +2977,39 @@ static int fastrpc_invoke_send(struct smq_invoke_ctx *ctx, return err; } +/* + * name : fastrpc_get_dsp_status + * @in : pointer to fastrpc_apps + * @out : void + * Description : This function reads the property + * string from device node and updates the cdsp device + * avialbility status if the node belongs to cdsp device. + */ + +static void fastrpc_get_dsp_status(struct fastrpc_apps *me) +{ + int ret = -1; + struct device_node *node = NULL; + const char *name = NULL; + + do { + node = of_find_compatible_node(node, NULL, "qcom,pil-tz-generic"); + if (node) { + ret = of_property_read_string(node, "qcom,firmware-name", &name); + if (!strcmp(name, "cdsp")) { + ret = of_device_is_available(node); + me->remote_cdsp_status = ret; + ADSPRPC_INFO("adsprpc: %s: cdsp node found with ret:%x\n", + __func__, ret); + break; + } + } else { + ADSPRPC_ERR("adsprpc: Error: %s: cdsp node not found\n", __func__); + break; + } + } while (1); +} + static void fastrpc_init(struct fastrpc_apps *me) { int i; @@ -6683,6 +6721,52 @@ bail: return err; } +/* + * name : remote_cdsp_status_show + * @in : dev : pointer to device node + * attr: pointer to device attribute + * @out : buf : Contains remote cdsp status + * @Description : This function updates the buf with + * remote cdsp status by reading the fastrpc node + * @returns : bytes written to buf + */ + +static ssize_t remote_cdsp_status_show(struct device *dev, + struct device_attribute *attr, char *buf) +{ + struct fastrpc_apps *me = &gfa; + + /* + * Default remote DSP status: 0 + * driver possibly not probed yet or not the main device. + */ + + if (!dev || !dev->driver || + !of_device_is_compatible(dev->of_node, "qcom,msm-fastrpc-compute")) { + ADSPRPC_ERR( + "adsprpc: Error: %s: driver not probed yet or not the main device\n", + __func__); + return 0; + } + + return scnprintf(buf, PAGE_SIZE, "%d", + me->remote_cdsp_status); +} + +/* Remote cdsp status attribute declartion as read only */ +static DEVICE_ATTR_RO(remote_cdsp_status); + +/* Declaring attribute for remote dsp */ +static struct attribute *msm_remote_dsp_attrs[] = { + &dev_attr_remote_cdsp_status.attr, + NULL +}; + +/* Defining remote dsp attributes in attributes group */ +static struct attribute_group msm_remote_dsp_attr_group = { + .attrs = msm_remote_dsp_attrs, +}; + static int fastrpc_probe(struct platform_device *pdev) { int err = 0; @@ -6693,6 +6777,14 @@ static int fastrpc_probe(struct platform_device *pdev) if (of_device_is_compatible(dev->of_node, "qcom,msm-fastrpc-compute")) { + me->dev_fastrpc = dev; + err = sysfs_create_group(&pdev->dev.kobj, &msm_remote_dsp_attr_group); + if (err) { + ADSPRPC_ERR( + "adsprpc: Error: %s: initialization of sysfs create group failed with %d\n", + __func__, err); + goto bail; + } init_secure_vmid_list(dev, "qcom,adsp-remoteheap-vmid", &gcinfo[0].rhvm); fastrpc_init_privileged_gids(dev, "qcom,fastrpc-gids", @@ -6814,6 +6906,7 @@ static int __init fastrpc_device_init(void) } memset(me, 0, sizeof(*me)); fastrpc_init(me); + fastrpc_get_dsp_status(me); me->dev = NULL; me->legacy_remote_heap = false; VERIFY(err, 0 == platform_driver_register(&fastrpc_driver));