mirror of https://gitee.com/openkylin/linux.git
rpmsg: Add driver_override device attribute for rpmsg_device
This patch adds "driver_override" device attribute for rpmsg_device which will allow users to explicitly specify the rpmsg_driver to be used via sysfs entry. The "driver_override" device attribute implemented here is very similar to "driver_override" implemented for platform, pci, and amba bus types. One important use-case of "driver_override" device attribute is to force use of rpmsg_chrdev driver for certain rpmsg_device instances. Signed-off-by: Anup Patel <anup@brainfault.org> Signed-off-by: Bjorn Andersson <bjorn.andersson@linaro.org>
This commit is contained in:
parent
60cc43fc88
commit
39e47767ec
|
@ -73,3 +73,23 @@ Description:
|
|||
This sysfs entry tells us whether the channel is a local
|
||||
server channel that is announced (values are either
|
||||
true or false).
|
||||
|
||||
What: /sys/bus/rpmsg/devices/.../driver_override
|
||||
Date: April 2018
|
||||
KernelVersion: 4.18
|
||||
Contact: Bjorn Andersson <bjorn.andersson@linaro.org>
|
||||
Description:
|
||||
Every rpmsg device is a communication channel with a remote
|
||||
processor. Channels are identified by a textual name (see
|
||||
/sys/bus/rpmsg/devices/.../name above) and have a local
|
||||
("source") rpmsg address, and remote ("destination") rpmsg
|
||||
address.
|
||||
|
||||
The listening entity (or client) which communicates with a
|
||||
remote processor is referred as rpmsg driver. The rpmsg device
|
||||
and rpmsg driver are matched based on rpmsg device name and
|
||||
rpmsg driver ID table.
|
||||
|
||||
This sysfs entry allows the rpmsg driver for a rpmsg device
|
||||
to be specified which will override standard OF, ID table
|
||||
and name matching.
|
||||
|
|
|
@ -333,11 +333,49 @@ field##_show(struct device *dev, \
|
|||
} \
|
||||
static DEVICE_ATTR_RO(field);
|
||||
|
||||
#define rpmsg_string_attr(field, member) \
|
||||
static ssize_t \
|
||||
field##_store(struct device *dev, struct device_attribute *attr, \
|
||||
const char *buf, size_t sz) \
|
||||
{ \
|
||||
struct rpmsg_device *rpdev = to_rpmsg_device(dev); \
|
||||
char *new, *old; \
|
||||
\
|
||||
new = kstrndup(buf, sz, GFP_KERNEL); \
|
||||
if (!new) \
|
||||
return -ENOMEM; \
|
||||
new[strcspn(new, "\n")] = '\0'; \
|
||||
\
|
||||
device_lock(dev); \
|
||||
old = rpdev->member; \
|
||||
if (strlen(new)) { \
|
||||
rpdev->member = new; \
|
||||
} else { \
|
||||
kfree(new); \
|
||||
rpdev->member = NULL; \
|
||||
} \
|
||||
device_unlock(dev); \
|
||||
\
|
||||
kfree(old); \
|
||||
\
|
||||
return sz; \
|
||||
} \
|
||||
static ssize_t \
|
||||
field##_show(struct device *dev, \
|
||||
struct device_attribute *attr, char *buf) \
|
||||
{ \
|
||||
struct rpmsg_device *rpdev = to_rpmsg_device(dev); \
|
||||
\
|
||||
return sprintf(buf, "%s\n", rpdev->member); \
|
||||
} \
|
||||
static DEVICE_ATTR_RW(field)
|
||||
|
||||
/* for more info, see Documentation/ABI/testing/sysfs-bus-rpmsg */
|
||||
rpmsg_show_attr(name, id.name, "%s\n");
|
||||
rpmsg_show_attr(src, src, "0x%x\n");
|
||||
rpmsg_show_attr(dst, dst, "0x%x\n");
|
||||
rpmsg_show_attr(announce, announce ? "true" : "false", "%s\n");
|
||||
rpmsg_string_attr(driver_override, driver_override);
|
||||
|
||||
static ssize_t modalias_show(struct device *dev,
|
||||
struct device_attribute *attr, char *buf)
|
||||
|
@ -359,6 +397,7 @@ static struct attribute *rpmsg_dev_attrs[] = {
|
|||
&dev_attr_dst.attr,
|
||||
&dev_attr_src.attr,
|
||||
&dev_attr_announce.attr,
|
||||
&dev_attr_driver_override.attr,
|
||||
NULL,
|
||||
};
|
||||
ATTRIBUTE_GROUPS(rpmsg_dev);
|
||||
|
|
Loading…
Reference in New Issue