#include "KernelDevice.h"
#include "include/types.h"
#include "include/compat.h"
+#include "include/stringify.h"
#include "common/errno.h"
#include "common/debug.h"
#include "common/blkdev.h"
#include "common/align.h"
+#include "common/blkdev.h"
#define dout_context cct
#define dout_subsys ceph_subsys_bdev
path.clear();
}
+static string get_dev_property(const char *dev, const char *property)
+{
+ char val[1024] = {0};
+ get_block_device_string_property(dev, property, val, sizeof(val));
+ return val;
+}
+
+int KernelDevice::collect_metadata(string prefix, map<string,string> *pm) const
+{
+ (*pm)[prefix + "rotational"] = stringify((int)(bool)rotational);
+ (*pm)[prefix + "size"] = stringify(get_size());
+ (*pm)[prefix + "block_size"] = stringify(get_block_size());
+ (*pm)[prefix + "driver"] = "KernelDevice";
+ if (rotational) {
+ (*pm)[prefix + "type"] = "hdd";
+ } else {
+ (*pm)[prefix + "type"] = "ssd";
+ }
+
+ struct stat st;
+ int r = ::fstat(fd_buffered, &st);
+ if (r < 0)
+ return -errno;
+ if (S_ISBLK(st.st_mode)) {
+ (*pm)[prefix + "access_mode"] = "blk";
+ char partition_path[PATH_MAX];
+ char dev_node[PATH_MAX];
+ int rc = get_device_by_fd(fd_buffered, partition_path, dev_node);
+ switch (rc) {
+ case -EOPNOTSUPP:
+ case -EINVAL:
+ (*pm)[prefix + "partition_path"] = "unknown";
+ (*pm)[prefix + "dev_node"] = "unknown";
+ break;
+ case -ENODEV:
+ (*pm)[prefix + "partition_path"] = string(partition_path);
+ (*pm)[prefix + "dev_node"] = "unknown";
+ break;
+ default:
+ {
+ (*pm)[prefix + "partition_path"] = string(partition_path);
+ (*pm)[prefix + "dev_node"] = string(dev_node);
+ (*pm)[prefix + "model"] = get_dev_property(dev_node, "device/model");
+ (*pm)[prefix + "dev"] = get_dev_property(dev_node, "dev");
+
+ // nvme exposes a serial number
+ string serial = get_dev_property(dev_node, "device/serial");
+ if (serial.length()) {
+ (*pm)[prefix + "serial"] = serial;
+ }
+
+ // nvme has a device/device/* structure; infer from that. there
+ // is probably a better way?
+ string nvme_vendor = get_dev_property(dev_node, "device/device/vendor");
+ if (nvme_vendor.length()) {
+ (*pm)[prefix + "type"] = "nvme";
+ }
+ }
+ }
+ } else {
+ (*pm)[prefix + "access_mode"] = "file";
+ (*pm)[prefix + "path"] = path;
+ }
+ return 0;
+}
+
int KernelDevice::flush()
{
// protect flush with a mutex. not that we are not really protected
driver->register_device(this);
block_size = driver->get_block_size();
size = driver->get_size();
+ name = serial_number;
//nvme is non-rotational device.
rotational = false;
dout(1) << __func__ << " end" << dendl;
}
+void NVMEDevice::collect_metadata(map<string,string> *pm)
+{
+ (*pm)[prefix + "rotational"] = "0";
+ (*pm)[prefix + "size"] = stringify(get_size());
+ (*pm)[prefix + "block_size"] = stringify(get_block_size());
+ (*pm)[prefix + "driver"] = "NVMEDevice";
+ (*pm)[prefix + "type"] = "nvme";
+ (*pm)[prefix + "access_mode"] = "spdk";
+ (*pm)[prefix + "nvme_serial_number"] = name;
+}
+
int NVMEDevice::flush()
{
dout(10) << __func__ << " start" << dendl;