184 lines
5.5 KiB
Diff
184 lines
5.5 KiB
Diff
From 65af20bfb1d21b656379d0916dcb867391166d74 Mon Sep 17 00:00:00 2001
|
|
From: Tomas Winkler <tomas.winkler@intel.com>
|
|
Date: Sun, 28 Feb 2016 23:59:39 +0200
|
|
Subject: [PATCH 019/550] char: rpmb: add device attributes
|
|
|
|
Add attribute type that displays underlay storage type technology
|
|
EMMC, UFS, and attribute id, that displays underlay storage device id.
|
|
For EMMC this would be content of CID and for UFS serial number from
|
|
the device descriptor.
|
|
|
|
V2: resend
|
|
V3: set kernel version to 4.7
|
|
V4: update target date to Maj
|
|
V5: update date and kernel version
|
|
V6: 1. Add simulation device type
|
|
2. Update date and kernel version
|
|
3. Use binary attribute for id
|
|
4. use simple sprintf instead of scnprintf
|
|
5. Add more verbose documenation
|
|
V7: resend
|
|
V8: update date and kernel version
|
|
V9: 1. update date and kernel version
|
|
2. add new rd_cnt_max and wr_cnt_max attributes.
|
|
3. Use SIM as a suffix of the device type.
|
|
|
|
Change-Id: If25a96f1371d8fea5820f6e06366bc0945d32faa
|
|
Signed-off-by: Tomas Winkler <tomas.winkler@intel.com>
|
|
Signed-off-by: Alexander Usyskin <alexander.usyskin@intel.com>
|
|
---
|
|
Documentation/ABI/testing/sysfs-class-rpmb | 37 ++++++++++
|
|
drivers/char/rpmb/core.c | 84 ++++++++++++++++++++++
|
|
2 files changed, 121 insertions(+)
|
|
|
|
diff --git a/Documentation/ABI/testing/sysfs-class-rpmb b/Documentation/ABI/testing/sysfs-class-rpmb
|
|
index a9d45aa77f77..d0540be7db19 100644
|
|
--- a/Documentation/ABI/testing/sysfs-class-rpmb
|
|
+++ b/Documentation/ABI/testing/sysfs-class-rpmb
|
|
@@ -18,3 +18,40 @@ Contact: Tomas Winkler <tomas.winkler@intel.com>
|
|
Description:
|
|
The /sys/class/rpmb/rpmbN directory is created for
|
|
each RPMB registered device.
|
|
+
|
|
+What: /sys/class/rpmb/rpmbN/type
|
|
+Date: Jul 2018
|
|
+KernelVersion: 4.18
|
|
+Contact: Tomas Winkler <tomas.winkler@intel.com>
|
|
+Description:
|
|
+ The /sys/class/rpmb/rpmbN/type file contains device
|
|
+ underlying storage type technology: EMMC, UFS, NVMe.
|
|
+ In case of simulated device it will have :SIM suffix
|
|
+ i.e EMMC:SIM.
|
|
+
|
|
+What: /sys/class/rpmb/rpmbN/id
|
|
+Date: Jul 2018
|
|
+KernelVersion: 4.18
|
|
+Contact: Tomas Winkler <tomas.winkler@intel.com>
|
|
+Description:
|
|
+ The /sys/class/rpmb/rpmbN/id file contains unique device id
|
|
+ in a binary form as defined by underlying storage device.
|
|
+ In case of multiple RPMB devices a user can determine correct
|
|
+ device.
|
|
+ The content can be parsed according the storage device type.
|
|
+
|
|
+What: /sys/class/rpmb/rpmbN/wr_cnt_max
|
|
+Date: Jul 2018
|
|
+KernelVersion: 4.18
|
|
+Contact: Tomas Winkler <tomas.winkler@intel.com>
|
|
+Description:
|
|
+ The /sys/class/rpmb/rpmbN/wr_cnt_max file contains
|
|
+ number of blocks that can be reliable written in a single request.
|
|
+
|
|
+What: /sys/class/rpmb/rpmbN/rd_cnt_max
|
|
+Date: Jul 2018
|
|
+KernelVersion: 4.18
|
|
+Contact: Tomas Winkler <tomas.winkler@intel.com>
|
|
+Description:
|
|
+ The /sys/class/rpmb/rpmbN/rd_cnt_max file contains
|
|
+ number of blocks that can be read in a single request.
|
|
diff --git a/drivers/char/rpmb/core.c b/drivers/char/rpmb/core.c
|
|
index 3bf3f0db54fb..41a249c0c58f 100644
|
|
--- a/drivers/char/rpmb/core.c
|
|
+++ b/drivers/char/rpmb/core.c
|
|
@@ -214,6 +214,88 @@ struct rpmb_dev *rpmb_dev_find_by_device(struct device *parent, u8 target)
|
|
}
|
|
EXPORT_SYMBOL_GPL(rpmb_dev_find_by_device);
|
|
|
|
+static ssize_t type_show(struct device *dev,
|
|
+ struct device_attribute *attr, char *buf)
|
|
+{
|
|
+ struct rpmb_dev *rdev = to_rpmb_dev(dev);
|
|
+ const char *sim;
|
|
+ ssize_t ret;
|
|
+
|
|
+ sim = (rdev->ops->type & RPMB_TYPE_SIM) ? ":SIM" : "";
|
|
+ switch (RPMB_TYPE_HW(rdev->ops->type)) {
|
|
+ case RPMB_TYPE_EMMC:
|
|
+ ret = sprintf(buf, "EMMC%s\n", sim);
|
|
+ break;
|
|
+ case RPMB_TYPE_UFS:
|
|
+ ret = sprintf(buf, "UFS%s\n", sim);
|
|
+ break;
|
|
+ case RPMB_TYPE_NVME:
|
|
+ ret = sprintf(buf, "NVMe%s\n", sim);
|
|
+ break;
|
|
+ default:
|
|
+ ret = sprintf(buf, "UNKNOWN\n");
|
|
+ break;
|
|
+ }
|
|
+
|
|
+ return ret;
|
|
+}
|
|
+static DEVICE_ATTR_RO(type);
|
|
+
|
|
+static ssize_t id_read(struct file *file, struct kobject *kobj,
|
|
+ struct bin_attribute *attr, char *buf,
|
|
+ loff_t off, size_t count)
|
|
+{
|
|
+ struct device *dev = kobj_to_dev(kobj);
|
|
+ struct rpmb_dev *rdev = to_rpmb_dev(dev);
|
|
+ size_t sz = min_t(size_t, rdev->ops->dev_id_len, PAGE_SIZE);
|
|
+
|
|
+ if (!rdev->ops->dev_id)
|
|
+ return 0;
|
|
+
|
|
+ return memory_read_from_buffer(buf, count, &off, rdev->ops->dev_id, sz);
|
|
+}
|
|
+static BIN_ATTR_RO(id, 0);
|
|
+
|
|
+static ssize_t wr_cnt_max_show(struct device *dev,
|
|
+ struct device_attribute *attr, char *buf)
|
|
+{
|
|
+ struct rpmb_dev *rdev = to_rpmb_dev(dev);
|
|
+
|
|
+ return sprintf(buf, "%u\n", rdev->ops->wr_cnt_max);
|
|
+}
|
|
+static DEVICE_ATTR_RO(wr_cnt_max);
|
|
+
|
|
+static ssize_t rd_cnt_max_show(struct device *dev,
|
|
+ struct device_attribute *attr, char *buf)
|
|
+{
|
|
+ struct rpmb_dev *rdev = to_rpmb_dev(dev);
|
|
+
|
|
+ return sprintf(buf, "%u\n", rdev->ops->rd_cnt_max);
|
|
+}
|
|
+static DEVICE_ATTR_RO(rd_cnt_max);
|
|
+
|
|
+static struct attribute *rpmb_attrs[] = {
|
|
+ &dev_attr_type.attr,
|
|
+ &dev_attr_wr_cnt_max.attr,
|
|
+ &dev_attr_rd_cnt_max.attr,
|
|
+ NULL,
|
|
+};
|
|
+
|
|
+static struct bin_attribute *rpmb_bin_attributes[] = {
|
|
+ &bin_attr_id,
|
|
+ NULL,
|
|
+};
|
|
+
|
|
+static struct attribute_group rpmb_attr_group = {
|
|
+ .attrs = rpmb_attrs,
|
|
+ .bin_attrs = rpmb_bin_attributes,
|
|
+};
|
|
+
|
|
+static const struct attribute_group *rpmb_attr_groups[] = {
|
|
+ &rpmb_attr_group,
|
|
+ NULL
|
|
+};
|
|
+
|
|
/**
|
|
* rpmb_dev_unregister - unregister RPMB partition from the RPMB subsystem
|
|
*
|
|
@@ -329,6 +411,8 @@ struct rpmb_dev *rpmb_dev_register(struct device *dev, u8 target,
|
|
dev_set_name(&rdev->dev, "rpmb%d", id);
|
|
rdev->dev.class = &rpmb_class;
|
|
rdev->dev.parent = dev;
|
|
+ rdev->dev.groups = rpmb_attr_groups;
|
|
+
|
|
ret = device_register(&rdev->dev);
|
|
if (ret)
|
|
goto exit;
|
|
--
|
|
2.19.1
|
|
|