Linux Hotplug development
 help / color / mirror / Atom feed
* "udevadm settle" and "init"
From: Kay Sievers @ 2011-03-31 18:35 UTC (permalink / raw)
  To: linux-hotplug

Hey,

the underlying problem described below, is in no way specific to
systemd, it applies to all modern systems and services, existing ones,
or ones not even developed.

The udev systemd service files for udev do no longer pull-in the
barrier 'udevadm settle'. The udev coldplug run is executed fully
asynchronously in the background along with many other services, and
no other service will be blocked by default, waiting for udev to
populate /dev.

That means: non-hotplug-aware services are likely to break. Services
which assume a static /dev, rely on scanning /dev and finding "all"
devices at a certain point in time, are required to explicitly pull-in
udev-settle.service to paper-over their inability to cope with a
dynamic system. It will block the broken service until udev's coldplug
run has finished and /dev is populated with all devices known at that
time.

It's 2011 and services should cope with hotplug, devices coming and
going at any time, and a constantly changing and re-configuring
environment. No service which wants survive the next years of Linux
evolution should depend on the udev-settle.service barrier though,
please fix your stuff, or the reality might go on without you. :)

There is libudev, which connects your service to meaningful event for
news devices, device changes, and allows you to enumerate all
currently existing devices. Subscribing to events before enumeration
is started will make sure not to miss anything, and to propagate later
changes into the service.

All that even works from python, java, mono, javascript, ... programs,
so there is no excuse anymore to continue to do any of the
much-too-simple things we all did in the past. Just stop making
assumptions like: "booting has finished" or "all devices are there" --
that never really was in the past, and it will never be true in the
future.

Thanks,
Kay

^ permalink raw reply

* Re: "udevadm settle" and "init"
From: Scott James Remnant @ 2011-03-31 18:50 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <AANLkTikDtgVGPdR2b3UeTFXXekoZH1oHQGs1RFKz4iQG@mail.gmail.com>

There is, of course, one use for "settle"; I like to have a "monitor"
running during boot that creates /var/log/udev - settle is as good a
command as any to kill monitor when it's done.

On Thu, Mar 31, 2011 at 11:35 AM, Kay Sievers <kay.sievers@vrfy.org> wrote:
> Hey,
>
> the underlying problem described below, is in no way specific to
> systemd, it applies to all modern systems and services, existing ones,
> or ones not even developed.
>
> The udev systemd service files for udev do no longer pull-in the
> barrier 'udevadm settle'. The udev coldplug run is executed fully
> asynchronously in the background along with many other services, and
> no other service will be blocked by default, waiting for udev to
> populate /dev.
>
> That means: non-hotplug-aware services are likely to break. Services
> which assume a static /dev, rely on scanning /dev and finding "all"
> devices at a certain point in time, are required to explicitly pull-in
> udev-settle.service to paper-over their inability to cope with a
> dynamic system. It will block the broken service until udev's coldplug
> run has finished and /dev is populated with all devices known at that
> time.
>
> It's 2011 and services should cope with hotplug, devices coming and
> going at any time, and a constantly changing and re-configuring
> environment. No service which wants survive the next years of Linux
> evolution should depend on the udev-settle.service barrier though,
> please fix your stuff, or the reality might go on without you. :)
>
> There is libudev, which connects your service to meaningful event for
> news devices, device changes, and allows you to enumerate all
> currently existing devices. Subscribing to events before enumeration
> is started will make sure not to miss anything, and to propagate later
> changes into the service.
>
> All that even works from python, java, mono, javascript, ... programs,
> so there is no excuse anymore to continue to do any of the
> much-too-simple things we all did in the past. Just stop making
> assumptions like: "booting has finished" or "all devices are there" --
> that never really was in the past, and it will never be true in the
> future.
>
> Thanks,
> Kay
> --
> To unsubscribe from this list: send the line "unsubscribe linux-hotplug" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
>

^ permalink raw reply

* socket and udev
From: Krosh Ivanov @ 2011-04-04 14:04 UTC (permalink / raw)
  To: linux-hotplug

I want to use udev to detect a storage usb disk when it is plugged.
Since the version of udev here is v120, it is need to use sockets to
receive messages with data about events, such as it is used in
udevmonitor.c. However, bind function returns an error message ("bind
failed: Address already in use") because it is used bind again in
another process (udevd uses it first). Is there another way to get the
events from udev?

Thanks,
Ivan

^ permalink raw reply

* Re: socket and udev
From: Dan Nicholson @ 2011-04-04 16:13 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <BANLkTimcDz=Jc3sfJELr2hwZijioWOLjpg@mail.gmail.com>

On Mon, Apr 4, 2011 at 7:04 AM, Krosh Ivanov <krosh.ivan@gmail.com> wrote:
> I want to use udev to detect a storage usb disk when it is plugged.
> Since the version of udev here is v120, it is need to use sockets to
> receive messages with data about events, such as it is used in
> udevmonitor.c. However, bind function returns an error message ("bind
> failed: Address already in use") because it is used bind again in
> another process (udevd uses it first). Is there another way to get the
> events from udev?

libudev?

http://www.kernel.org/pub/linux/utils/kernel/hotplug/libudev/

I guess it's probably not available on that old udev. You could use
libhal on that system, or you could add a rule to create an AF_LOCAL
socket like was done for hal and udevmonitor:

RUN+="socket:@/your/name/here"

--
Dan

^ permalink raw reply

* [PATCH 1/2] SCSI: Add a SCSI option for persistent device names in
From: Nao Nishijima @ 2011-04-05 12:49 UTC (permalink / raw)
  To: linux-kernel, linux-scsi, linux-hotplug
  Cc: Greg KH, Kay Sievers, James Bottomley, Jon Masters,
	2nddept-manager, Nao Nishijima

This patch series provides a SCSI option for persistent device
names in kernel. With this option, user can always assign a
same device name (e.g. sda) to a specific device according to
udev rules and device id.

Issue:
Recently, kernel registers block devices in parallel. As a result,
different device names will be assigned at each boot time. This
will confuse file-system mounter, thus we usually use persistent
symbolic links provided by udev. However, dmesg and procfs outputs
show device names instead of the symbolic link names. This causes
a serious problem when managing multiple devices (e.g. on a
large-scale storage), because usually, device errors are output
with device names on dmesg. We also concern about some commands
which output device names, as well as kernel messages.

Solution:
To assign a persistent device name, I create unnamed devices (not
a block device, but an intermediate device. users cannot read/write
this device). When scsi device driver finds a LU, the LU is registered
as an unnamed device and inform to udev. After udev finds the unnamed
device, udev assigns a persistent device name to a specific device
according to udev rules and registers it as a block device. Hence,
this is just a naming, not a renaming.

Some users are satisfied with current udev solution. Therefore, my
proposal is implemented as an option.

If using this option, add the following kernel parameter.

	scsi_mod.persistent_name=1

Also, if you want to assign a device name with sda, add the
following udev rules.

SUBSYSTEM="scsi_unnamed", ATTR{disk_id}="xxx", PROGRAM="/bin/sh
-c 'echo -n sda > /sys/%p/disk_name'"

Todo:
- usb support
- hot-remove support

I've already started discussion about device naming at LKML.
https://lkml.org/lkml/2010/10/8/31

Signed-off-by: Nao Nishijima <nao.nishijima.xt@hitachi.com>
---

 drivers/scsi/Makefile       |    1 
 drivers/scsi/scsi_sysfs.c   |   26 +++
 drivers/scsi/scsi_unnamed.c |  340 +++++++++++++++++++++++++++++++++++++++++++
 drivers/scsi/scsi_unnamed.h |   25 +++
 4 files changed, 387 insertions(+), 5 deletions(-)
 create mode 100644 drivers/scsi/scsi_unnamed.c
 create mode 100644 drivers/scsi/scsi_unnamed.h

diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile
index 7ad0b8a..782adc1 100644
--- a/drivers/scsi/Makefile
+++ b/drivers/scsi/Makefile
@@ -167,6 +167,7 @@ scsi_mod-$(CONFIG_SYSCTL)	+= scsi_sysctl.o
 scsi_mod-$(CONFIG_SCSI_PROC_FS)	+= scsi_proc.o
 scsi_mod-y			+= scsi_trace.o
 scsi_mod-$(CONFIG_PM)		+= scsi_pm.o
+scsi_mod-y			+= scsi_unnamed.o
 
 scsi_tgt-y			+= scsi_tgt_lib.o scsi_tgt_if.o
 
diff --git a/drivers/scsi/scsi_sysfs.c b/drivers/scsi/scsi_sysfs.c
index e44ff64..7959f5d 100644
--- a/drivers/scsi/scsi_sysfs.c
+++ b/drivers/scsi/scsi_sysfs.c
@@ -22,6 +22,7 @@
 
 #include "scsi_priv.h"
 #include "scsi_logging.h"
+#include "scsi_unnamed.h"
 
 static struct device_type scsi_dev_type;
 
@@ -393,13 +394,27 @@ int scsi_sysfs_register(void)
 {
 	int error;
 
+	error = scsi_unnamed_register(&scsi_bus_type);
+	if (error)
+		goto cleanup;
+
 	error = bus_register(&scsi_bus_type);
-	if (!error) {
-		error = class_register(&sdev_class);
-		if (error)
-			bus_unregister(&scsi_bus_type);
-	}
+	if (error)
+		goto cleanup_scsi_unnamed;
+
+	error = class_register(&sdev_class);
+	if (error)
+		goto cleanup_bus;
+
+	return 0;
+
+cleanup_bus:
+	bus_unregister(&scsi_bus_type);
+
+cleanup_scsi_unnamed:
+	scsi_unnamed_unregister();
 
+cleanup:
 	return error;
 }
 
@@ -407,6 +422,7 @@ void scsi_sysfs_unregister(void)
 {
 	class_unregister(&sdev_class);
 	bus_unregister(&scsi_bus_type);
+	scsi_unnamed_unregister();
 }
 
 /*
diff --git a/drivers/scsi/scsi_unnamed.c b/drivers/scsi/scsi_unnamed.c
new file mode 100644
index 0000000..ed96945
--- /dev/null
+++ b/drivers/scsi/scsi_unnamed.c
@@ -0,0 +1,340 @@
+/*
+ * scsi_unnamed.c - SCSI driver for unnmaed device
+ *
+ * Copyright: Copyright (c) Hitachi, Ltd. 2011
+ *            Authors: Nao Nishijima <nao.nishijima.xt@hitachi.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA
+ */
+
+#include <linux/module.h>
+#include <linux/err.h>
+#include <linux/device.h>
+#include <linux/slab.h>
+#include <linux/kobject.h>
+#include <linux/kdev_t.h>
+#include <linux/sysdev.h>
+#include <linux/list.h>
+#include <linux/wait.h>
+
+#include <scsi/scsi_driver.h>
+#include <scsi/scsi_device.h>
+#include <scsi/scsi.h>
+
+#define MAX_BUFFER_LEN	256
+#define DISK_NAME_LEN	32
+
+#define SCSI_ID_BINARY	1
+#define SCSI_ID_ASCII	2
+#define SCSI_ID_UTF8	3
+
+static LIST_HEAD(su_list);
+static DEFINE_MUTEX(su_list_lock);
+
+static int persistent_name;
+MODULE_PARM_DESC(persistent_name, "SCSI unnamed device support");
+module_param(persistent_name, bool, S_IRUGO);
+
+static struct class su_sysfs_class = {
+	.name	= "scsi_unnamed",
+};
+
+struct scsi_unnamed {
+	struct list_head list;
+	struct device dev;
+	char disk_name[DISK_NAME_LEN];
+	char disk_lun[MAX_BUFFER_LEN];
+	char disk_id[MAX_BUFFER_LEN];
+	bool assigned;
+};
+
+#define to_scsi_unnamed(d) \
+	container_of(d, struct scsi_unnamed, dev)
+
+/* Get device identification VPD page */
+static void store_disk_id(struct scsi_device *sdev, char *disk_id)
+{
+	unsigned char *page_83;
+	int page_len, id_len, j = 0, i = 8;
+	static const char hex_str[] = "0123456789abcdef";
+
+	page_83 = kmalloc(MAX_BUFFER_LEN, GFP_KERNEL);
+	if (!page_83)
+		return;
+
+	if (scsi_get_vpd_page(sdev, 0x83, page_83, MAX_BUFFER_LEN))
+		goto err;
+
+	page_len = ((page_83[2] << 8) | page_83[3]) + 4;
+	if (page_len > 0) {
+		if ((page_83[5] & 0x30) != 0)
+			goto err;
+
+		id_len = page_83[7];
+		if (id_len > 0) {
+			switch (page_83[4] & 0x0f) {
+			case SCSI_ID_BINARY:
+				while (i < id_len) {
+					disk_id[j++] = hex_str[(page_83[i]
+						& 0xf0) >> 4];
+					disk_id[j++] = hex_str[page_83[i]
+						& 0x0f];
+					i++;
+				}
+				break;
+			case SCSI_ID_ASCII:
+			case SCSI_ID_UTF8:
+				strncpy(disk_id, strim(page_83 + 8), id_len);
+				break;
+			default:
+				break;
+			}
+		}
+	}
+
+err:
+	kfree(page_83);
+	return;
+}
+
+static ssize_t show_disk_name(struct device *dev,
+			struct device_attribute *attr, char *buf)
+{
+	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_name);
+}
+
+static ssize_t show_disk_lun(struct device *dev,
+			struct device_attribute *attr, char *buf)
+{
+	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_lun);
+}
+
+static ssize_t show_disk_id(struct device *dev,
+			struct device_attribute *attr, char *buf)
+{
+	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_id);
+}
+
+/* Assign a persistent device name */
+static ssize_t store_disk_name(struct device *dev,
+		struct device_attribute *attr, char *buf, size_t count)
+{
+	struct scsi_unnamed *su = to_scsi_unnamed(dev);
+	struct scsi_unnamed *tmp;
+	struct device *lu = dev->parent;
+	int ret = -EINVAL;
+
+	if (count >= DISK_NAME_LEN) {
+		printk(KERN_WARNING "su: Too long a persistent name!\n");
+		return -EINVAL;
+	}
+
+	if (su->assigned) {
+		printk(KERN_WARNING "su: Already assigned a persistent name!\n");
+		return -EINVAL;
+	}
+
+	if (strncmp(lu->driver->name, buf, 2)) {
+		printk(KERN_WARNING "su: Wrong prefix!\n");
+		return -EINVAL;
+	}
+
+	mutex_lock(&su_list_lock);
+	list_for_each_entry(tmp, &su_list, list) {
+		if (!strncmp(tmp->disk_name, buf, DISK_NAME_LEN)) {
+			printk(KERN_WARNING "su: Duplicate name exsists!\n");
+			return -EINVAL;
+		}
+	}
+	strncpy(su->disk_name, buf, DISK_NAME_LEN);
+	mutex_unlock(&su_list_lock);
+
+	if (!lu->driver->probe)
+		return -EINVAL;
+
+	lu->init_name = buf;
+
+	ret = lu->driver->probe(lu);
+	if (ret) {
+		lu->init_name = NULL;
+		su->disk_name[0] = '\0';
+		return ret;
+	}
+
+	su->assigned = true;
+	return count;
+}
+
+static DEVICE_ATTR(disk_name, S_IRUGO|S_IWUSR, show_disk_name,
+			store_disk_name);
+static DEVICE_ATTR(disk_lun, S_IRUGO, show_disk_lun, NULL);
+static DEVICE_ATTR(disk_id, S_IRUGO, show_disk_id, NULL);
+
+/* Confirm the driver name and the device type */
+static int check_device_type(char type, const char *name)
+{
+	switch (type) {
+	case TYPE_DISK:
+	case TYPE_MOD:
+	case TYPE_RBC:
+		if (strncmp("sd", name, 2))
+			return -ENODEV;
+		break;
+	case TYPE_ROM:
+	case TYPE_WORM:
+		if (strncmp("sr", name, 2))
+			return -ENODEV;
+		break;
+	case TYPE_TAPE:
+		if (strncmp("st", name, 2))
+			return -ENODEV;
+		break;
+	default:
+		break;
+	}
+	return 0;
+}
+
+/**
+ * scsi_unnamed_probe - Setup the unnamed device.
+ * @dev: parent scsi device
+ *
+ * This function adds a unnamed device to the device model and
+ * gets a number of device information by scsi inquiry commands.
+ * Udev identify a device by those information.
+ *
+ * Unnamed devices:
+ * This device is not a block device and user can not read/write
+ * this device. But it can advertise device information in sysfs.
+ */
+int scsi_unnamed_probe(struct device *dev)
+{
+	struct scsi_unnamed *su;
+	struct scsi_device *sdev = to_scsi_device(dev);
+	int ret = -EINVAL;
+	static int i;
+
+	if (check_device_type(sdev->type, dev->driver->name))
+		return -ENODEV;
+
+	su = kzalloc(sizeof(*su), GFP_KERNEL);
+	if (!su)
+		return -ENOMEM;
+
+	device_initialize(&su->dev);
+	su->dev.parent = dev;
+	su->dev.class = &su_sysfs_class;
+	dev_set_name(&su->dev, "su%d", i++);
+	strncpy(su->disk_lun, dev_name(dev), MAX_BUFFER_LEN);
+
+	ret = device_add(&su->dev);
+	if (ret)
+		goto err;
+
+	ret = device_create_file(&su->dev, &dev_attr_disk_name);
+	if (ret)
+		goto err_disk_name;
+
+	ret = device_create_file(&su->dev, &dev_attr_disk_lun);
+	if (ret)
+		goto err_disk_lun;
+
+	store_disk_id(sdev, su->disk_id);
+	if (su->disk_id[0] != '\0') {
+		ret = device_create_file(&su->dev, &dev_attr_disk_id);
+		if (ret)
+			goto err_disk_id;
+	}
+
+	su->assigned = false;
+	mutex_lock(&su_list_lock);
+	list_add(&su->list, &su_list);
+	mutex_unlock(&su_list_lock);
+
+	return 0;
+
+err_disk_id:
+	device_remove_file(&su->dev, &dev_attr_disk_lun);
+
+err_disk_lun:
+	device_remove_file(&su->dev, &dev_attr_disk_name);
+
+err_disk_name:
+	device_del(&su->dev);
+
+err:
+	kfree(su);
+	return ret;
+}
+
+/* Remove a unnamed device from su_list and release resources */
+void scsi_unnamed_remove(struct device *dev)
+{
+	struct scsi_unnamed *tmp;
+
+	mutex_lock(&su_list_lock);
+	list_for_each_entry(tmp, &su_list, list) {
+		if (dev = tmp->dev.parent) {
+			list_del(&tmp->list);
+			break;
+		}
+	}
+	mutex_unlock(&su_list_lock);
+
+	if (tmp->disk_id[0] != '\0')
+		device_remove_file(&tmp->dev, &dev_attr_disk_id);
+	device_remove_file(&tmp->dev, &dev_attr_disk_name);
+	device_remove_file(&tmp->dev, &dev_attr_disk_lun);
+	device_del(&tmp->dev);
+
+	device_release_driver(dev);
+
+	kfree(tmp);
+}
+
+/**
+ * copy_persistent_name - Copy the device name
+ * @disk_name: allocate to
+ * @dev: scsi device
+ *
+ * Copy an initial name of the device to disk_name.
+ */
+int copy_persistent_name(char *disk_name, struct device *dev)
+{
+	if (persistent_name) {
+		strncpy(disk_name, dev->init_name, DISK_NAME_LEN);
+		return 1;
+	}
+	return 0;
+}
+EXPORT_SYMBOL(copy_persistent_name);
+
+int scsi_unnamed_register(struct bus_type *bus)
+{
+	if (persistent_name) {
+		bus->probe = scsi_unnamed_probe;
+		bus->remove = scsi_unnamed_remove;
+		return class_register(&su_sysfs_class);
+	}
+	return 0;
+}
+EXPORT_SYMBOL(scsi_unnamed_register);
+
+void scsi_unnamed_unregister(void)
+{
+	if (persistent_name)
+		class_unregister(&su_sysfs_class);
+}
+EXPORT_SYMBOL(scsi_unnamed_unregister);
diff --git a/drivers/scsi/scsi_unnamed.h b/drivers/scsi/scsi_unnamed.h
new file mode 100644
index 0000000..ca4e852
--- /dev/null
+++ b/drivers/scsi/scsi_unnamed.h
@@ -0,0 +1,25 @@
+/*
+ * scsi_unnamed.h - SCSI driver for unnmaed device
+ *
+ * Copyright: Copyright (c) Hitachi, Ltd. 2011
+ *            Authors: Nao Nishijima <nao.nishijima.xt@hitachi.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA
+ */
+
+extern int check_disk_name_prefix(char *, struct device *);
+extern int copy_persistent_name(char *, struct device *);
+extern int scsi_unnamed_register(struct bus_type *);
+extern void scsi_unnamed_unregister(void);


^ permalink raw reply related

* [PATCH 2/2] SCSI: modify SCSI subsystem
From: Nao Nishijima @ 2011-04-05 12:50 UTC (permalink / raw)
  To: linux-kernel, linux-scsi, linux-hotplug
  Cc: Greg KH, Kay Sievers, James Bottomley, Jon Masters,
	2nddept-manager, Nao Nishijima
In-Reply-To: <20110405124946.7969.66796.stgit@ltc233.sdl.hitachi.co.jp>

Add a SCSI option for persistent device names in Kernel.

If scsi_mod.persistent_name=1, device names is assigned by udev.
If scsi_mod.persistent_name=0, device names is assigned the order
of logical unit recognizing.

Signed-off-by: Nao Nishijima <nao.nishijima.xt@hitachi.com>
---

 drivers/scsi/sd.c |   10 +++++++---
 drivers/scsi/sr.c |    4 +++-
 drivers/scsi/st.c |    4 +++-
 3 files changed, 13 insertions(+), 5 deletions(-)

diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c
index b61ebec..94ad290 100644
--- a/drivers/scsi/sd.c
+++ b/drivers/scsi/sd.c
@@ -65,6 +65,7 @@
 
 #include "sd.h"
 #include "scsi_logging.h"
+#include "scsi_unnamed.h"
 
 MODULE_AUTHOR("Eric Youngdale");
 MODULE_DESCRIPTION("SCSI disk (sd) driver");
@@ -2554,9 +2555,12 @@ static int sd_probe(struct device *dev)
 		goto out_free_index;
 	}
 
-	error = sd_format_disk_name("sd", index, gd->disk_name, DISK_NAME_LEN);
-	if (error)
-		goto out_free_index;
+	if (!copy_persistent_name(gd->disk_name, dev)) {
+		error = sd_format_disk_name("sd", index,
+				gd->disk_name, DISK_NAME_LEN);
+		if (error)
+			goto out_free_index;
+	}
 
 	sdkp->device = sdp;
 	sdkp->driver = &sd_template;
diff --git a/drivers/scsi/sr.c b/drivers/scsi/sr.c
index aefadc6..682b1a4 100644
--- a/drivers/scsi/sr.c
+++ b/drivers/scsi/sr.c
@@ -58,6 +58,7 @@
 
 #include "scsi_logging.h"
 #include "sr.h"
+#include "scsi_unnamed.h"
 
 
 MODULE_DESCRIPTION("SCSI cdrom (sr) driver");
@@ -634,7 +635,8 @@ static int sr_probe(struct device *dev)
 
 	disk->major = SCSI_CDROM_MAJOR;
 	disk->first_minor = minor;
-	sprintf(disk->disk_name, "sr%d", minor);
+	if (!copy_persistent_name(disk->disk_name, dev))
+		sprintf(disk->disk_name, "sr%d", minor);
 	disk->fops = &sr_bdops;
 	disk->flags = GENHD_FL_CD;
 	disk->events = DISK_EVENT_MEDIA_CHANGE | DISK_EVENT_EJECT_REQUEST;
diff --git a/drivers/scsi/st.c b/drivers/scsi/st.c
index 1871b8a..9acf8b2 100644
--- a/drivers/scsi/st.c
+++ b/drivers/scsi/st.c
@@ -74,6 +74,7 @@ static const char *verstr = "20101219";
 
 #include "st_options.h"
 #include "st.h"
+#include "scsi_unnamed.h"
 
 static DEFINE_MUTEX(st_mutex);
 static int buffer_kbs;
@@ -4051,7 +4052,8 @@ static int st_probe(struct device *dev)
 	}
 	kref_init(&tpnt->kref);
 	tpnt->disk = disk;
-	sprintf(disk->disk_name, "st%d", i);
+	if (!copy_persistent_name(disk->disk_name, dev))
+		sprintf(disk->disk_name, "st%d", i);
 	disk->private_data = &tpnt->driver;
 	disk->queue = SDp->request_queue;
 	tpnt->driver = &st_template;


^ permalink raw reply related

* Re: [ANNOUNCE] udev 167 release
From: Karel Zak @ 2011-04-05 13:30 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <AANLkTi=Ff2rrxHeObMMtasxpHPDkET+UneDr8-n6F89h@mail.gmail.com>

On Thu, Mar 31, 2011 at 12:08:40PM +0200, Kay Sievers wrote:
> On Thu, Mar 31, 2011 at 10:03, Gabor Z. Papp <gzp@papp.hu> wrote:
> > * Kay Sievers <kay.sievers@vrfy.org>:
> >
> > | Here comes a new udev version. Thanks to all who have contributed to
> > | this release.
> >
> > $ dmesg
> > <30>udev[1589]: converting old udev database
> > <30>udev[1590]: starting version 167
> >
> > what is/mean <30> before udev[1589]?

I'm not able reproduce this problem on Fedora-15.

After update to udev-167:

        # dmesg -r | grep udev
        <6>[    2.061910] udev[92]: starting version 166
        <6>[   10.884330] udev[362]: starting version 166
        <30>[ 3154.877757] udev[1780]: converting old udev database
        <30>[ 3154.975428] udev[1780]: starting version 167

'-r' means raw, so <30> prefix is there. Normal dmesg:

        # dmesg | grep udev
        [    2.061910] udev[92]: starting version 166
        [   10.884330] udev[362]: starting version 166
        [ 3154.877757] udev[1780]: converting old udev database
        [ 3154.975428] udev[1780]: starting version 167

        # rpm -qf /bin/dmesg
        util-linux-2.19-3.fc15.i686


> Userspace uses proper facility values now, for dmesg, syslog, the
> admin, to be able to properly distinguish kernel messages from
> userspace-injected ones.

The dmesg from util-linux supports arbitrary number of digits between
'<' and '>' in the kernel messages.

    Karel
 
-- 
 Karel Zak  <kzak@redhat.com>
 http://karelzak.blogspot.com

^ permalink raw reply

* libudev compiling
From: Maik Hänig @ 2011-04-05 15:08 UTC (permalink / raw)
  To: linux-hotplug

Hi,

if I extract the udev sources how can I compile the libudev?

Is there any file where it is described. I want to cross compile the 
libudev for arm.

best regards

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Greg KH @ 2011-04-05 16:14 UTC (permalink / raw)
  To: Nao Nishijima
  Cc: linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <20110405124946.7969.66796.stgit@ltc233.sdl.hitachi.co.jp>

On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
> This patch series provides a SCSI option for persistent device
> names in kernel. With this option, user can always assign a
> same device name (e.g. sda) to a specific device according to
> udev rules and device id.
> 
> Issue:
> Recently, kernel registers block devices in parallel. As a result,
> different device names will be assigned at each boot time. This
> will confuse file-system mounter, thus we usually use persistent
> symbolic links provided by udev.

Yes, that is what you should use if you care about this.

> However, dmesg and procfs outputs
> show device names instead of the symbolic link names. This causes
> a serious problem when managing multiple devices (e.g. on a
> large-scale storage), because usually, device errors are output
> with device names on dmesg.

Then fix your tools that read the output of these files to point to the
proper persistent name instead of trying to get the kernel to solve the
problem.

> We also concern about some commands
> which output device names, as well as kernel messages.

What commands are you concerned about?

> Solution:
> To assign a persistent device name, I create unnamed devices (not
> a block device, but an intermediate device. users cannot read/write
> this device). When scsi device driver finds a LU, the LU is registered
> as an unnamed device and inform to udev. After udev finds the unnamed
> device, udev assigns a persistent device name to a specific device
> according to udev rules and registers it as a block device. Hence,
> this is just a naming, not a renaming.

Ick, so the kernel waits for userspace before you are able to use the
device?  That sounds messy.

> Some users are satisfied with current udev solution. Therefore, my
> proposal is implemented as an option.
> 
> If using this option, add the following kernel parameter.
> 
> 	scsi_mod.persistent_name=1
> 
> Also, if you want to assign a device name with sda, add the
> following udev rules.
> 
> SUBSYSTEM="scsi_unnamed", ATTR{disk_id}="xxx", PROGRAM="/bin/sh
> -c 'echo -n sda > /sys/%p/disk_name'"
> 
> Todo:
> - usb support

Why?  USB uses scsi, so why would it not work as-is today?  What about
libata devices?

> - hot-remove support

So once you have assigned a name and the device is removed bad things
happen?  What is the problem with this?

Note, any review of the code below does not imply that I agree with the
ideas here at all.  In fact, I really don't like this idea at all, but I
might as well review the code anyway for your future contributions :)

> 
> I've already started discussion about device naming at LKML.
> https://lkml.org/lkml/2010/10/8/31
> 
> Signed-off-by: Nao Nishijima <nao.nishijima.xt@hitachi.com>
> ---
> 
>  drivers/scsi/Makefile       |    1 
>  drivers/scsi/scsi_sysfs.c   |   26 +++
>  drivers/scsi/scsi_unnamed.c |  340 +++++++++++++++++++++++++++++++++++++++++++
>  drivers/scsi/scsi_unnamed.h |   25 +++
>  4 files changed, 387 insertions(+), 5 deletions(-)
>  create mode 100644 drivers/scsi/scsi_unnamed.c
>  create mode 100644 drivers/scsi/scsi_unnamed.h
> 
> diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile
> index 7ad0b8a..782adc1 100644
> --- a/drivers/scsi/Makefile
> +++ b/drivers/scsi/Makefile
> @@ -167,6 +167,7 @@ scsi_mod-$(CONFIG_SYSCTL)	+= scsi_sysctl.o
>  scsi_mod-$(CONFIG_SCSI_PROC_FS)	+= scsi_proc.o
>  scsi_mod-y			+= scsi_trace.o
>  scsi_mod-$(CONFIG_PM)		+= scsi_pm.o
> +scsi_mod-y			+= scsi_unnamed.o
>  
>  scsi_tgt-y			+= scsi_tgt_lib.o scsi_tgt_if.o
>  
> diff --git a/drivers/scsi/scsi_sysfs.c b/drivers/scsi/scsi_sysfs.c
> index e44ff64..7959f5d 100644
> --- a/drivers/scsi/scsi_sysfs.c
> +++ b/drivers/scsi/scsi_sysfs.c
> @@ -22,6 +22,7 @@
>  
>  #include "scsi_priv.h"
>  #include "scsi_logging.h"
> +#include "scsi_unnamed.h"
>  
>  static struct device_type scsi_dev_type;
>  
> @@ -393,13 +394,27 @@ int scsi_sysfs_register(void)
>  {
>  	int error;
>  
> +	error = scsi_unnamed_register(&scsi_bus_type);
> +	if (error)
> +		goto cleanup;
> +
>  	error = bus_register(&scsi_bus_type);
> -	if (!error) {
> -		error = class_register(&sdev_class);
> -		if (error)
> -			bus_unregister(&scsi_bus_type);
> -	}
> +	if (error)
> +		goto cleanup_scsi_unnamed;
> +
> +	error = class_register(&sdev_class);
> +	if (error)
> +		goto cleanup_bus;
> +
> +	return 0;
> +
> +cleanup_bus:
> +	bus_unregister(&scsi_bus_type);
> +
> +cleanup_scsi_unnamed:
> +	scsi_unnamed_unregister();
>  
> +cleanup:
>  	return error;
>  }
>  
> @@ -407,6 +422,7 @@ void scsi_sysfs_unregister(void)
>  {
>  	class_unregister(&sdev_class);
>  	bus_unregister(&scsi_bus_type);
> +	scsi_unnamed_unregister();
>  }
>  
>  /*
> diff --git a/drivers/scsi/scsi_unnamed.c b/drivers/scsi/scsi_unnamed.c
> new file mode 100644
> index 0000000..ed96945
> --- /dev/null
> +++ b/drivers/scsi/scsi_unnamed.c
> @@ -0,0 +1,340 @@
> +/*
> + * scsi_unnamed.c - SCSI driver for unnmaed device
> + *
> + * Copyright: Copyright (c) Hitachi, Ltd. 2011
> + *            Authors: Nao Nishijima <nao.nishijima.xt@hitachi.com>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.

Do you _REALLY_ mean "any later version?  Are you sure about that?  If
so, fine, just be careful please.

> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA

Unless you wish to track the movements of the FSF's office space for the
next 40+ years and keep this file up to date, just remove this paragraph
please.

> + */
> +
> +#include <linux/module.h>
> +#include <linux/err.h>
> +#include <linux/device.h>
> +#include <linux/slab.h>
> +#include <linux/kobject.h>
> +#include <linux/kdev_t.h>
> +#include <linux/sysdev.h>
> +#include <linux/list.h>
> +#include <linux/wait.h>
> +
> +#include <scsi/scsi_driver.h>
> +#include <scsi/scsi_device.h>
> +#include <scsi/scsi.h>
> +
> +#define MAX_BUFFER_LEN	256
> +#define DISK_NAME_LEN	32

Why this limitation?

> +
> +#define SCSI_ID_BINARY	1
> +#define SCSI_ID_ASCII	2
> +#define SCSI_ID_UTF8	3
> +
> +static LIST_HEAD(su_list);
> +static DEFINE_MUTEX(su_list_lock);
> +
> +static int persistent_name;
> +MODULE_PARM_DESC(persistent_name, "SCSI unnamed device support");
> +module_param(persistent_name, bool, S_IRUGO);

Why is this a module parameter?

> +
> +static struct class su_sysfs_class = {
> +	.name	= "scsi_unnamed",
> +};

Why a static class?  What is it used for?  If you are adding sysfs
files, you need to also add Documentation/ABI/ entries at the same time.
Please do that if you really are adding new sysfs files.

> +
> +struct scsi_unnamed {
> +	struct list_head list;
> +	struct device dev;
> +	char disk_name[DISK_NAME_LEN];
> +	char disk_lun[MAX_BUFFER_LEN];
> +	char disk_id[MAX_BUFFER_LEN];
> +	bool assigned;
> +};
> +
> +#define to_scsi_unnamed(d) \
> +	container_of(d, struct scsi_unnamed, dev)
> +
> +/* Get device identification VPD page */
> +static void store_disk_id(struct scsi_device *sdev, char *disk_id)
> +{
> +	unsigned char *page_83;
> +	int page_len, id_len, j = 0, i = 8;
> +	static const char hex_str[] = "0123456789abcdef";

Don't we have functions that do this already?

> +
> +	page_83 = kmalloc(MAX_BUFFER_LEN, GFP_KERNEL);
> +	if (!page_83)
> +		return;
> +
> +	if (scsi_get_vpd_page(sdev, 0x83, page_83, MAX_BUFFER_LEN))
> +		goto err;
> +
> +	page_len = ((page_83[2] << 8) | page_83[3]) + 4;
> +	if (page_len > 0) {
> +		if ((page_83[5] & 0x30) != 0)
> +			goto err;
> +
> +		id_len = page_83[7];
> +		if (id_len > 0) {
> +			switch (page_83[4] & 0x0f) {
> +			case SCSI_ID_BINARY:
> +				while (i < id_len) {
> +					disk_id[j++] = hex_str[(page_83[i]
> +						& 0xf0) >> 4];
> +					disk_id[j++] = hex_str[page_83[i]
> +						& 0x0f];
> +					i++;
> +				}
> +				break;
> +			case SCSI_ID_ASCII:
> +			case SCSI_ID_UTF8:
> +				strncpy(disk_id, strim(page_83 + 8), id_len);
> +				break;
> +			default:
> +				break;
> +			}
> +		}
> +	}
> +
> +err:
> +	kfree(page_83);
> +	return;
> +}
> +
> +static ssize_t show_disk_name(struct device *dev,
> +			struct device_attribute *attr, char *buf)
> +{
> +	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_name);
> +}
> +
> +static ssize_t show_disk_lun(struct device *dev,
> +			struct device_attribute *attr, char *buf)
> +{
> +	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_lun);
> +}
> +
> +static ssize_t show_disk_id(struct device *dev,
> +			struct device_attribute *attr, char *buf)
> +{
> +	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_id);
> +}
> +
> +/* Assign a persistent device name */
> +static ssize_t store_disk_name(struct device *dev,
> +		struct device_attribute *attr, char *buf, size_t count)
> +{
> +	struct scsi_unnamed *su = to_scsi_unnamed(dev);
> +	struct scsi_unnamed *tmp;
> +	struct device *lu = dev->parent;
> +	int ret = -EINVAL;
> +
> +	if (count >= DISK_NAME_LEN) {
> +		printk(KERN_WARNING "su: Too long a persistent name!\n");
> +		return -EINVAL;
> +	}
> +
> +	if (su->assigned) {
> +		printk(KERN_WARNING "su: Already assigned a persistent name!\n");
> +		return -EINVAL;
> +	}
> +
> +	if (strncmp(lu->driver->name, buf, 2)) {
> +		printk(KERN_WARNING "su: Wrong prefix!\n");
> +		return -EINVAL;
> +	}
> +
> +	mutex_lock(&su_list_lock);
> +	list_for_each_entry(tmp, &su_list, list) {
> +		if (!strncmp(tmp->disk_name, buf, DISK_NAME_LEN)) {
> +			printk(KERN_WARNING "su: Duplicate name exsists!\n");
> +			return -EINVAL;
> +		}
> +	}
> +	strncpy(su->disk_name, buf, DISK_NAME_LEN);
> +	mutex_unlock(&su_list_lock);
> +
> +	if (!lu->driver->probe)
> +		return -EINVAL;
> +
> +	lu->init_name = buf;
> +
> +	ret = lu->driver->probe(lu);
> +	if (ret) {
> +		lu->init_name = NULL;
> +		su->disk_name[0] = '\0';
> +		return ret;
> +	}
> +
> +	su->assigned = true;
> +	return count;
> +}
> +
> +static DEVICE_ATTR(disk_name, S_IRUGO|S_IWUSR, show_disk_name,
> +			store_disk_name);
> +static DEVICE_ATTR(disk_lun, S_IRUGO, show_disk_lun, NULL);
> +static DEVICE_ATTR(disk_id, S_IRUGO, show_disk_id, NULL);
> +
> +/* Confirm the driver name and the device type */
> +static int check_device_type(char type, const char *name)
> +{
> +	switch (type) {
> +	case TYPE_DISK:
> +	case TYPE_MOD:
> +	case TYPE_RBC:
> +		if (strncmp("sd", name, 2))
> +			return -ENODEV;
> +		break;
> +	case TYPE_ROM:
> +	case TYPE_WORM:
> +		if (strncmp("sr", name, 2))
> +			return -ENODEV;
> +		break;
> +	case TYPE_TAPE:
> +		if (strncmp("st", name, 2))
> +			return -ENODEV;
> +		break;
> +	default:
> +		break;
> +	}
> +	return 0;
> +}
> +
> +/**
> + * scsi_unnamed_probe - Setup the unnamed device.
> + * @dev: parent scsi device
> + *
> + * This function adds a unnamed device to the device model and
> + * gets a number of device information by scsi inquiry commands.
> + * Udev identify a device by those information.
> + *
> + * Unnamed devices:
> + * This device is not a block device and user can not read/write
> + * this device. But it can advertise device information in sysfs.
> + */
> +int scsi_unnamed_probe(struct device *dev)
> +{
> +	struct scsi_unnamed *su;
> +	struct scsi_device *sdev = to_scsi_device(dev);
> +	int ret = -EINVAL;
> +	static int i;
> +
> +	if (check_device_type(sdev->type, dev->driver->name))
> +		return -ENODEV;
> +
> +	su = kzalloc(sizeof(*su), GFP_KERNEL);
> +	if (!su)
> +		return -ENOMEM;
> +
> +	device_initialize(&su->dev);
> +	su->dev.parent = dev;
> +	su->dev.class = &su_sysfs_class;

You just created a device that can not be removed from the system (i.e.
you have no release function.)  This is a major bug and as per the
documentation for kobjects and the driver model in the kernel tree, I am
allowed to mock this code mercilessly :)

> +	dev_set_name(&su->dev, "su%d", i++);
> +	strncpy(su->disk_lun, dev_name(dev), MAX_BUFFER_LEN);
> +
> +	ret = device_add(&su->dev);
> +	if (ret)
> +		goto err;
> +
> +	ret = device_create_file(&su->dev, &dev_attr_disk_name);

Nope, you just raced with userspace here.  NEVER create a sysfs file
after you have added it to the system.  Userspace just got notified of
the device and is already starting to read the file.  As it's not there
yet, you just failed :(

Use attributes properly to keep this race from happening.


> +	if (ret)
> +		goto err_disk_name;
> +
> +	ret = device_create_file(&su->dev, &dev_attr_disk_lun);
> +	if (ret)
> +		goto err_disk_lun;
> +
> +	store_disk_id(sdev, su->disk_id);
> +	if (su->disk_id[0] != '\0') {
> +		ret = device_create_file(&su->dev, &dev_attr_disk_id);
> +		if (ret)
> +			goto err_disk_id;
> +	}
> +
> +	su->assigned = false;
> +	mutex_lock(&su_list_lock);
> +	list_add(&su->list, &su_list);
> +	mutex_unlock(&su_list_lock);
> +
> +	return 0;
> +
> +err_disk_id:
> +	device_remove_file(&su->dev, &dev_attr_disk_lun);
> +
> +err_disk_lun:
> +	device_remove_file(&su->dev, &dev_attr_disk_name);
> +
> +err_disk_name:
> +	device_del(&su->dev);
> +
> +err:
> +	kfree(su);
> +	return ret;
> +}
> +
> +/* Remove a unnamed device from su_list and release resources */
> +void scsi_unnamed_remove(struct device *dev)
> +{
> +	struct scsi_unnamed *tmp;
> +
> +	mutex_lock(&su_list_lock);
> +	list_for_each_entry(tmp, &su_list, list) {
> +		if (dev = tmp->dev.parent) {
> +			list_del(&tmp->list);
> +			break;
> +		}
> +	}
> +	mutex_unlock(&su_list_lock);
> +
> +	if (tmp->disk_id[0] != '\0')
> +		device_remove_file(&tmp->dev, &dev_attr_disk_id);
> +	device_remove_file(&tmp->dev, &dev_attr_disk_name);
> +	device_remove_file(&tmp->dev, &dev_attr_disk_lun);
> +	device_del(&tmp->dev);

Your kerrnel just spit out some very nasty messages when this function
was called, right?  Why are you ignoring them?

> +
> +	device_release_driver(dev);
> +
> +	kfree(tmp);
> +}
> +
> +/**
> + * copy_persistent_name - Copy the device name
> + * @disk_name: allocate to
> + * @dev: scsi device
> + *
> + * Copy an initial name of the device to disk_name.
> + */
> +int copy_persistent_name(char *disk_name, struct device *dev)
> +{
> +	if (persistent_name) {
> +		strncpy(disk_name, dev->init_name, DISK_NAME_LEN);
> +		return 1;
> +	}
> +	return 0;
> +}
> +EXPORT_SYMBOL(copy_persistent_name);

That's a very bad global function name.

EXPORT_SYMBOL_GPL?  And why is it exported at all?  Who would ever need
to call this from a module?

> +
> +int scsi_unnamed_register(struct bus_type *bus)
> +{
> +	if (persistent_name) {
> +		bus->probe = scsi_unnamed_probe;
> +		bus->remove = scsi_unnamed_remove;
> +		return class_register(&su_sysfs_class);
> +	}
> +	return 0;
> +}
> +EXPORT_SYMBOL(scsi_unnamed_register);

Same here, why is this exported?

> +
> +void scsi_unnamed_unregister(void)
> +{
> +	if (persistent_name)
> +		class_unregister(&su_sysfs_class);
> +}
> +EXPORT_SYMBOL(scsi_unnamed_unregister);

And here.

> diff --git a/drivers/scsi/scsi_unnamed.h b/drivers/scsi/scsi_unnamed.h
> new file mode 100644
> index 0000000..ca4e852
> --- /dev/null
> +++ b/drivers/scsi/scsi_unnamed.h
> @@ -0,0 +1,25 @@
> +/*
> + * scsi_unnamed.h - SCSI driver for unnmaed device
> + *
> + * Copyright: Copyright (c) Hitachi, Ltd. 2011
> + *            Authors: Nao Nishijima <nao.nishijima.xt@hitachi.com>
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License as published by
> + * the Free Software Foundation; either version 2 of the License, or
> + * (at your option) any later version.

Same comment as above.

> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA

And again, same comment as above.

thanks,

greg k-h

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Greg KH @ 2011-04-05 16:14 UTC (permalink / raw)
  To: Nao Nishijima
  Cc: linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <20110405124946.7969.66796.stgit@ltc233.sdl.hitachi.co.jp>

On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
> This patch series provides a SCSI option for persistent device
> names in kernel. With this option, user can always assign a
> same device name (e.g. sda) to a specific device according to
> udev rules and device id.
> 
> Issue:
> Recently, kernel registers block devices in parallel. As a result,
> different device names will be assigned at each boot time. This
> will confuse file-system mounter, thus we usually use persistent
> symbolic links provided by udev. However, dmesg and procfs outputs
> show device names instead of the symbolic link names. This causes
> a serious problem when managing multiple devices (e.g. on a
> large-scale storage), because usually, device errors are output
> with device names on dmesg. We also concern about some commands
> which output device names, as well as kernel messages.
> 
> Solution:
> To assign a persistent device name, I create unnamed devices (not
> a block device, but an intermediate device. users cannot read/write
> this device). When scsi device driver finds a LU, the LU is registered
> as an unnamed device and inform to udev. After udev finds the unnamed
> device, udev assigns a persistent device name to a specific device
> according to udev rules and registers it as a block device. Hence,
> this is just a naming, not a renaming.
> 
> Some users are satisfied with current udev solution. Therefore, my
> proposal is implemented as an option.
> 
> If using this option, add the following kernel parameter.
> 
> 	scsi_mod.persistent_name=1
> 
> Also, if you want to assign a device name with sda, add the
> following udev rules.
> 
> SUBSYSTEM="scsi_unnamed", ATTR{disk_id}="xxx", PROGRAM="/bin/sh
> -c 'echo -n sda > /sys/%p/disk_name'"

Also, where is the "real" program you have created to properly name
devices from userspace?  You need that to properly test this patch,
right?

thanks,

greg k-h

^ permalink raw reply

* [PATCH] keymap: Support Dell Latitude XT2 tablet-mode navigation keys
From: Seth Forshee @ 2011-04-05 16:42 UTC (permalink / raw)
  To: linux-hotplug

Hi Martin,

The patch that follows gets some tablet-mode keys working on the
Latitude XT2. The scan codes for these keys are apparently used for
different functions on some other models, so I added a new keymap file
for the XT2 to handle the overlap. There's a good chance that what I've
done is suboptimal -- I mean that either these keys apply to some other
models, or that some of the keys in the current dell keymap should be
moved over to the new file, or both. I just don't have enough
information to know which keys are used on which models. If that
information is available somewhere I'd be happy to rearrange the
keymaps, but for now I opted for the conservative approach that won't
change how things currently work for other Dell models.

Thanks,
Seth


Seth Forshee (1):
  keymap: Support Dell Latitude XT2 tablet-mode navigation keys

 Makefile.am                             |    1 +
 extras/keymap/95-keymap.rules           |    1 +
 extras/keymap/keymaps/dell-latitude-xt2 |    4 ++++
 3 files changed, 6 insertions(+), 0 deletions(-)
 create mode 100644 extras/keymap/keymaps/dell-latitude-xt2


^ permalink raw reply

* [PATCH] keymap: Support Dell Latitude XT2 tablet-mode navigation keys
From: Seth Forshee @ 2011-04-05 16:43 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <1302021780-709-1-git-send-email-seth.forshee@canonical.com>

The XT2 has a rocker (up/down/enter) and back button on the side
in tablet mode, none of which work currently. Add entries for
these keys.

There is some overlap here with scan codes used in other Dell
models, so these buttons are put in a new file specific to this
model.

Signed-off-by: Seth Forshee <seth.forshee@canonical.com>
---
 Makefile.am                             |    1 +
 extras/keymap/95-keymap.rules           |    1 +
 extras/keymap/keymaps/dell-latitude-xt2 |    4 ++++
 3 files changed, 6 insertions(+), 0 deletions(-)
 create mode 100644 extras/keymap/keymaps/dell-latitude-xt2

diff --git a/Makefile.am b/Makefile.am
index 2c20f46..4244089 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -568,6 +568,7 @@ dist_udevkeymap_DATA = \
 	extras/keymap/keymaps/asus \
 	extras/keymap/keymaps/compaq-e_evo \
 	extras/keymap/keymaps/dell \
+	extras/keymap/keymaps/dell-latitude-xt2 \
 	extras/keymap/keymaps/everex-xt5000 \
 	extras/keymap/keymaps/fujitsu-amilo_pa_2548 \
 	extras/keymap/keymaps/fujitsu-amilo_pro_edition_v3505 \
diff --git a/extras/keymap/95-keymap.rules b/extras/keymap/95-keymap.rules
index 44d5064..350f111 100644
--- a/extras/keymap/95-keymap.rules
+++ b/extras/keymap/95-keymap.rules
@@ -67,6 +67,7 @@ LABEL="keyboard_vendorcheck"
 
 ENV{DMI_VENDOR}="Dell*", RUN+="keymap $name dell"
 ENV{DMI_VENDOR}="Dell*", ATTR{[dmi/id]product_name}="Inspiron 910|Inspiron 1010|Inspiron 1011|Inspiron 1012|Inspiron 1110|Inspiron 1210", RUN+="keymap $name 0x84 wlan"
+ENV{DMI_VENDOR}="Dell*", ATTR{[dmi/id]product_name}="Latitude XT2", RUN+="keymap $name dell-latitude-xt2"
 
 ENV{DMI_VENDOR}="Compaq*", ATTR{[dmi/id]product_name}="*E500*|*Evo N*", RUN+="keymap $name compaq-e_evo"
 
diff --git a/extras/keymap/keymaps/dell-latitude-xt2 b/extras/keymap/keymaps/dell-latitude-xt2
new file mode 100644
index 0000000..39872f5
--- /dev/null
+++ b/extras/keymap/keymaps/dell-latitude-xt2
@@ -0,0 +1,4 @@
+0x9B up # tablet rocker up
+0x9E enter # tablet rocker press
+0x9F back # tablet back
+0xA3 down # tablet rocker down
-- 
1.7.4.1


^ permalink raw reply related

* Re: [PATCH] keymap: Support Dell Latitude XT2 tablet-mode navigation
From: Martin Pitt @ 2011-04-05 17:40 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <1302021780-709-1-git-send-email-seth.forshee@canonical.com>

Hello Seth,

Seth Forshee [2011-04-05 11:42 -0500]:
> I just don't have enough information to know which keys are used on
> which models. If that information is available somewhere I'd be
> happy to rearrange the keymaps, but for now I opted for the
> conservative approach that won't change how things currently work
> for other Dell models.

I don't know either I'm afraid, so let's keep the model specific
version for now. Pushed to git, thanks!

Martin
-- 
Martin Pitt                        | http://www.piware.de
Ubuntu Developer (www.ubuntu.com)  | Debian Developer  (www.debian.org)

^ permalink raw reply

* Re: [ANNOUNCE] udev 167 release
From: Gabor Z. Papp @ 2011-04-05 18:45 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <AANLkTi=Ff2rrxHeObMMtasxpHPDkET+UneDr8-n6F89h@mail.gmail.com>

* Karel Zak <kzak@redhat.com>:

| > > what is/mean <30> before udev[1589]?

| I'm not able reproduce this problem on Fedora-15.

$ dmesg -r | grep udev
<4><30>udev[1144]: starting version 167

In this case my syslog-ng 2.1.4 is the ancient/too old?

Thanks and sorry for the noise.

^ permalink raw reply

* Re: [ANNOUNCE] udev 167 release
From: Kay Sievers @ 2011-04-05 18:54 UTC (permalink / raw)
  To: linux-hotplug
In-Reply-To: <AANLkTi=Ff2rrxHeObMMtasxpHPDkET+UneDr8-n6F89h@mail.gmail.com>

On Tue, Apr 5, 2011 at 20:45, Gabor Z. Papp <gzp@papp.hu> wrote:
> * Karel Zak <kzak@redhat.com>:
>
> | > > what is/mean <30> before udev[1589]?
>
> | I'm not able reproduce this problem on Fedora-15.
>
> $ dmesg -r | grep udev
> <4><30>udev[1144]: starting version 167
>
> In this case my syslog-ng 2.1.4 is the ancient/too old?

No, that looks fine, missed that because I'm used to see timestamps
the kernel adds. They are in-between the two prefixes then.

It's expected behavior for old kernels. Older kernels do not recognize
the multi-digit prefix, and adds another default prefix, it's just
some noise to ignore.

We patched the kernel already to do the right thing now. See the link
in the earlier mail.

Kay

^ permalink raw reply

* 75-persistent-net-generator.rules on Hyper-V virtual interfaces
From: Leonid Antonenkov @ 2011-04-06 15:12 UTC (permalink / raw)
  To: linux-hotplug

Hello!

Problem: Hyper-V changes MAC address of virtual network adapter on every migration,
So  '75-persistent-net-generator.rules' script changes network interface number.

Suggested solution: ignore MAC addresses specific for Hyper-V in the script

Tested: on Debian Lenny (5.0.x) with udev-0.125-7+lenny3
on Debian Squeze (6.0) with udev-164-3

Suggested patch: (for latest release - "udev-167")
------------------------------------------------------------------------------------------------------------
diff -r -u udev-167/extras/rule_generator/75-persistent-net-generator.rules udev-167.patched/extras/rule_generator/75-persistent-net-generator.rules
--- udev-167/extras/rule_generator/75-persistent-net-generator.rules    2010-09-03 08:08:14.000000000 -0400
+++ udev-167.patched/extras/rule_generator/75-persistent-net-generator.rules    2011-04-06 10:50:15.000000000 -0400
@@ -33,6 +33,8 @@
 ENV{MATCHADDR}="52:54:00:*", GOTO="persistent_net_generator_end"
 # ignore VMWare virtual interfaces
 ENV{MATCHADDR}="00:0c:29:*|00:50:56:*", GOTO="persistent_net_generator_end"
+# ignore Hyper-V virtual interfaces
+ENV{MATCHADDR}="00:15:5d:*", GOTO="persistent_net_generator_end"

 # These vendors are known to violate the local MAC address assignment scheme
 # Interlan, DEC (UNIBUS or QBUS), Apollo, Cisco, Racal-Datacom
------------------------------------------------------------------------------------------------------------

Thank you,

Leonid Antonenkov
Linux Developer
Intermedia


________________________________

This message (including attachments) is private and confidential. If you have received this message in error, please notify us and remove it from your system.

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Nao Nishijima @ 2011-04-08 14:07 UTC (permalink / raw)
  To: Greg KH
  Cc: linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <20110405161454.GB885@kroah.com>

Hi,

(2011/04/06 1:14), Greg KH wrote:
> On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
>> This patch series provides a SCSI option for persistent device
>> names in kernel. With this option, user can always assign a
>> same device name (e.g. sda) to a specific device according to
>> udev rules and device id.
>>
>> Issue:
>> Recently, kernel registers block devices in parallel. As a result,
>> different device names will be assigned at each boot time. This
>> will confuse file-system mounter, thus we usually use persistent
>> symbolic links provided by udev. However, dmesg and procfs outputs
>> show device names instead of the symbolic link names. This causes
>> a serious problem when managing multiple devices (e.g. on a
>> large-scale storage), because usually, device errors are output
>> with device names on dmesg. We also concern about some commands
>> which output device names, as well as kernel messages.
>>
>> Solution:
>> To assign a persistent device name, I create unnamed devices (not
>> a block device, but an intermediate device. users cannot read/write
>> this device). When scsi device driver finds a LU, the LU is registered
>> as an unnamed device and inform to udev. After udev finds the unnamed
>> device, udev assigns a persistent device name to a specific device
>> according to udev rules and registers it as a block device. Hence,
>> this is just a naming, not a renaming.
>>
>> Some users are satisfied with current udev solution. Therefore, my
>> proposal is implemented as an option.
>>
>> If using this option, add the following kernel parameter.
>>
>> 	scsi_mod.persistent_name=1
>>
>> Also, if you want to assign a device name with sda, add the
>> following udev rules.
>>
>> SUBSYSTEM="scsi_unnamed", ATTR{disk_id}="xxx", PROGRAM="/bin/sh
>> -c 'echo -n sda > /sys/%p/disk_name'"
> 
> Also, where is the "real" program you have created to properly name
> devices from userspace?  You need that to properly test this patch,
> right?
> 

In the udev rule described above, notation “xxx” indicated by
ATTR(disk_id) is scsi id given by disk. Then, when udev finds this rule,
"/bin/sh -c 'echo -n sda>  /sys/%p/disk_name'" indicated by PROGRAM is
operated using xxx (scsi id) if udev find the disk with scic id xxx.
Thus, persistent device name is assigned.

I have tested this patch using the udev rule. and It works well.


> thanks,
> 
> greg k-h
> 

Thanks,

-- 
Nao NISHIJIMA
Software Platform Research Dept. Linux Technology Center
Hitachi, Ltd., YOKOHAMA Research  Laboratory
Email: nao.nishijima.xt@hitachi.com

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Nao Nishijima @ 2011-04-08 14:12 UTC (permalink / raw)
  To: Greg KH
  Cc: linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <20110405161400.GA885@kroah.com>

Hi,

(2011/04/06 1:14), Greg KH wrote:
> On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
>> This patch series provides a SCSI option for persistent device
>> names in kernel. With this option, user can always assign a
>> same device name (e.g. sda) to a specific device according to
>> udev rules and device id.
>>
>> Issue:
>> Recently, kernel registers block devices in parallel. As a result,
>> different device names will be assigned at each boot time. This
>> will confuse file-system mounter, thus we usually use persistent
>> symbolic links provided by udev.
> 
> Yes, that is what you should use if you care about this.
> 
>> However, dmesg and procfs outputs
>> show device names instead of the symbolic link names. This causes
>> a serious problem when managing multiple devices (e.g. on a
>> large-scale storage), because usually, device errors are output
>> with device names on dmesg.
> 
> Then fix your tools that read the output of these files to point to the
> proper persistent name instead of trying to get the kernel to solve the
> problem.
> 

Yes, the tools should be revised if users get a device name using them.

The problem I would like to discuss here is that users can not identify
a disk from kernel messages when they DIRECTLY refer to these messages.
For example, a device name is used instead of a symbolic link names in
bootup messages, I/O devices errors and /proc/partitions …etc.

In particular, users can not identify an appropriate device from a
device name in syslog since different device name may be assigned to it
at each boot time.

My idea is able to fix this issue with small changes in scsi subsystem.
Also, it is implemented as an option. Therefore, it does not affect
users who do not select this option.


>> We also concern about some commands
>> which output device names, as well as kernel messages.
> 
> What commands are you concerned about?
> 

They are iostat, df, fdisk, parted and so on.
For example, the following sdc did not point a same disk.

# ls -l /dev/disk/by-id
...
lrwxrwxrwx. 1 root root  9 Apr  8 11:17 wwn-0x50014ee057a61330 -> ../../sdc
lrwxrwxrwx. 1 root root  9 Apr  8 11:17 wwn-0x50014ee204d3fcda -> ../../sdd

# iostat
...
Device:            tps   Blk_read/s   Blk_wrtn/s   Blk_read   Blk_wrtn
...
sdc               5.78        19.25        78.98     394124    1616821
sdd               7.66       893.45         0.86   18289518      17604

After rebooting, the same symbolic link name pointed different device name.


# ls -l /dev/disk/by-id
...
lrwxrwxrwx. 1 root root  9 Apr  8 11:23 wwn-0x50014ee204d3fcda -> ../../sdc
lrwxrwxrwx. 1 root root  9 Apr  8 11:23 wwn-0x50014ee057a61330 -> ../../sdd


# iostat
...
Device:            tps   Blk_read/s   Blk_wrtn/s   Blk_read   Blk_wrtn
...
sdc               7.65       892.22         0.86   18289518      17604
sdd               5.78        19.23        78.90     394124    1617447

>> Solution:
>> To assign a persistent device name, I create unnamed devices (not
>> a block device, but an intermediate device. users cannot read/write
>> this device). When scsi device driver finds a LU, the LU is registered
>> as an unnamed device and inform to udev. After udev finds the unnamed
>> device, udev assigns a persistent device name to a specific device
>> according to udev rules and registers it as a block device. Hence,
>> this is just a naming, not a renaming.
> 
> Ick, so the kernel waits for userspace before you are able to use the
> device?  That sounds messy.
> 

This option only affects the system where users selected it. Therefore,
I think that the unnamed device should not be available before users
give the name.


>> Some users are satisfied with current udev solution. Therefore, my
>> proposal is implemented as an option.
>>
>> If using this option, add the following kernel parameter.
>>
>> 	scsi_mod.persistent_name=1
>>
>> Also, if you want to assign a device name with sda, add the
>> following udev rules.
>>
>> SUBSYSTEM="scsi_unnamed", ATTR{disk_id}="xxx", PROGRAM="/bin/sh
>> -c 'echo -n sda > /sys/%p/disk_name'"
>>
>> Todo:
>> - usb support
> 
> Why?  USB uses scsi, so why would it not work as-is today?  What about
> libata devices?
> 

Sorry, my explanation was not sufficient.
It is required to get scsi id using a scsi inguiry command in order to
create the udev rule, especially in ATTR(disk_id) item in it. The USB
devices, however, do not respond to the command and we can not get their
scsi id.


>> - hot-remove support
> 
> So once you have assigned a name and the device is removed bad things
> happen?  What is the problem with this?
> 

I am deeply sorry for that I forgot including the release function in
this patch.


> Note, any review of the code below does not imply that I agree with the
> ideas here at all.  In fact, I really don't like this idea at all, but I
> might as well review the code anyway for your future contributions :)
> 

I am profoundly grateful for your review :)


>>
>> I've already started discussion about device naming at LKML.
>> https://lkml.org/lkml/2010/10/8/31
>>
>> Signed-off-by: Nao Nishijima <nao.nishijima.xt@hitachi.com>
>> ---
>>
>>  drivers/scsi/Makefile       |    1 
>>  drivers/scsi/scsi_sysfs.c   |   26 +++
>>  drivers/scsi/scsi_unnamed.c |  340 +++++++++++++++++++++++++++++++++++++++++++
>>  drivers/scsi/scsi_unnamed.h |   25 +++
>>  4 files changed, 387 insertions(+), 5 deletions(-)
>>  create mode 100644 drivers/scsi/scsi_unnamed.c
>>  create mode 100644 drivers/scsi/scsi_unnamed.h
>>
>> diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile
>> index 7ad0b8a..782adc1 100644
>> --- a/drivers/scsi/Makefile
>> +++ b/drivers/scsi/Makefile
>> @@ -167,6 +167,7 @@ scsi_mod-$(CONFIG_SYSCTL)	+= scsi_sysctl.o
>>  scsi_mod-$(CONFIG_SCSI_PROC_FS)	+= scsi_proc.o
>>  scsi_mod-y			+= scsi_trace.o
>>  scsi_mod-$(CONFIG_PM)		+= scsi_pm.o
>> +scsi_mod-y			+= scsi_unnamed.o
>>  
>>  scsi_tgt-y			+= scsi_tgt_lib.o scsi_tgt_if.o
>>  
>> diff --git a/drivers/scsi/scsi_sysfs.c b/drivers/scsi/scsi_sysfs.c
>> index e44ff64..7959f5d 100644
>> --- a/drivers/scsi/scsi_sysfs.c
>> +++ b/drivers/scsi/scsi_sysfs.c
>> @@ -22,6 +22,7 @@
>>  
>>  #include "scsi_priv.h"
>>  #include "scsi_logging.h"
>> +#include "scsi_unnamed.h"
>>  
>>  static struct device_type scsi_dev_type;
>>  
>> @@ -393,13 +394,27 @@ int scsi_sysfs_register(void)
>>  {
>>  	int error;
>>  
>> +	error = scsi_unnamed_register(&scsi_bus_type);
>> +	if (error)
>> +		goto cleanup;
>> +
>>  	error = bus_register(&scsi_bus_type);
>> -	if (!error) {
>> -		error = class_register(&sdev_class);
>> -		if (error)
>> -			bus_unregister(&scsi_bus_type);
>> -	}
>> +	if (error)
>> +		goto cleanup_scsi_unnamed;
>> +
>> +	error = class_register(&sdev_class);
>> +	if (error)
>> +		goto cleanup_bus;
>> +
>> +	return 0;
>> +
>> +cleanup_bus:
>> +	bus_unregister(&scsi_bus_type);
>> +
>> +cleanup_scsi_unnamed:
>> +	scsi_unnamed_unregister();
>>  
>> +cleanup:
>>  	return error;
>>  }
>>  
>> @@ -407,6 +422,7 @@ void scsi_sysfs_unregister(void)
>>  {
>>  	class_unregister(&sdev_class);
>>  	bus_unregister(&scsi_bus_type);
>> +	scsi_unnamed_unregister();
>>  }
>>  
>>  /*
>> diff --git a/drivers/scsi/scsi_unnamed.c b/drivers/scsi/scsi_unnamed.c
>> new file mode 100644
>> index 0000000..ed96945
>> --- /dev/null
>> +++ b/drivers/scsi/scsi_unnamed.c
>> @@ -0,0 +1,340 @@
>> +/*
>> + * scsi_unnamed.c - SCSI driver for unnmaed device
>> + *
>> + * Copyright: Copyright (c) Hitachi, Ltd. 2011
>> + *            Authors: Nao Nishijima <nao.nishijima.xt@hitachi.com>
>> + *
>> + * This program is free software; you can redistribute it and/or modify
>> + * it under the terms of the GNU General Public License as published by
>> + * the Free Software Foundation; either version 2 of the License, or
>> + * (at your option) any later version.
> 
> Do you _REALLY_ mean "any later version?  Are you sure about that?  If
> so, fine, just be careful please.
> 

OK, I will remove those paragraph.

>> + *
>> + * This program is distributed in the hope that it will be useful,
>> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
>> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
>> + * GNU General Public License for more details.
>> + *
>> + * You should have received a copy of the GNU General Public License
>> + * along with this program; if not, write to the Free Software
>> + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA
> 
> Unless you wish to track the movements of the FSF's office space for the
> next 40+ years and keep this file up to date, just remove this paragraph
> please.
> 

OK, I will remove those paragraph.


>> + */
>> +
>> +#include <linux/module.h>
>> +#include <linux/err.h>
>> +#include <linux/device.h>
>> +#include <linux/slab.h>
>> +#include <linux/kobject.h>
>> +#include <linux/kdev_t.h>
>> +#include <linux/sysdev.h>
>> +#include <linux/list.h>
>> +#include <linux/wait.h>
>> +
>> +#include <scsi/scsi_driver.h>
>> +#include <scsi/scsi_device.h>
>> +#include <scsi/scsi.h>
>> +
>> +#define MAX_BUFFER_LEN	256
>> +#define DISK_NAME_LEN	32
> 
> Why this limitation?
> 

Device name limitation which used kernel is 32.

include/linux/genhd.h
...
#define DISK_NAME_LEN                   32
...
struct gendisk {
...
char disk_name[DISK_NAME_LEN];  /* name of major driver */

I will include genhd.h.


>> +
>> +#define SCSI_ID_BINARY	1
>> +#define SCSI_ID_ASCII	2
>> +#define SCSI_ID_UTF8	3
>> +
>> +static LIST_HEAD(su_list);
>> +static DEFINE_MUTEX(su_list_lock);
>> +
>> +static int persistent_name;
>> +MODULE_PARM_DESC(persistent_name, "SCSI unnamed device support");
>> +module_param(persistent_name, bool, S_IRUGO);
> 
> Why is this a module parameter?
> 

I implemented this idea as an option.


>> +
>> +static struct class su_sysfs_class = {
>> +	.name	= "scsi_unnamed",
>> +};
> 
> Why a static class?  What is it used for?  If you are adding sysfs
> files, you need to also add Documentation/ABI/ entries at the same time.
> Please do that if you really are adding new sysfs files.
> 

OK, I have a rethink on it.

>> +
>> +struct scsi_unnamed {
>> +	struct list_head list;
>> +	struct device dev;
>> +	char disk_name[DISK_NAME_LEN];
>> +	char disk_lun[MAX_BUFFER_LEN];
>> +	char disk_id[MAX_BUFFER_LEN];
>> +	bool assigned;
>> +};
>> +
>> +#define to_scsi_unnamed(d) \
>> +	container_of(d, struct scsi_unnamed, dev)
>> +
>> +/* Get device identification VPD page */
>> +static void store_disk_id(struct scsi_device *sdev, char *disk_id)
>> +{
>> +	unsigned char *page_83;
>> +	int page_len, id_len, j = 0, i = 8;
>> +	static const char hex_str[] = "0123456789abcdef";
> 
> Don't we have functions that do this already?
> 

I will use pack_hex_byte(), thanks.

>> +
>> +	page_83 = kmalloc(MAX_BUFFER_LEN, GFP_KERNEL);
>> +	if (!page_83)
>> +		return;
>> +
>> +	if (scsi_get_vpd_page(sdev, 0x83, page_83, MAX_BUFFER_LEN))
>> +		goto err;
>> +
>> +	page_len = ((page_83[2] << 8) | page_83[3]) + 4;
>> +	if (page_len > 0) {
>> +		if ((page_83[5] & 0x30) != 0)
>> +			goto err;
>> +
>> +		id_len = page_83[7];
>> +		if (id_len > 0) {
>> +			switch (page_83[4] & 0x0f) {
>> +			case SCSI_ID_BINARY:
>> +				while (i < id_len) {
>> +					disk_id[j++] = hex_str[(page_83[i]
>> +						& 0xf0) >> 4];
>> +					disk_id[j++] = hex_str[page_83[i]
>> +						& 0x0f];
>> +					i++;
>> +				}
>> +				break;
>> +			case SCSI_ID_ASCII:
>> +			case SCSI_ID_UTF8:
>> +				strncpy(disk_id, strim(page_83 + 8), id_len);
>> +				break;
>> +			default:
>> +				break;
>> +			}
>> +		}
>> +	}
>> +
>> +err:
>> +	kfree(page_83);
>> +	return;
>> +}
>> +
>> +static ssize_t show_disk_name(struct device *dev,
>> +			struct device_attribute *attr, char *buf)
>> +{
>> +	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_name);
>> +}
>> +
>> +static ssize_t show_disk_lun(struct device *dev,
>> +			struct device_attribute *attr, char *buf)
>> +{
>> +	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_lun);
>> +}
>> +
>> +static ssize_t show_disk_id(struct device *dev,
>> +			struct device_attribute *attr, char *buf)
>> +{
>> +	return sprintf(buf, "%s\n", to_scsi_unnamed(dev)->disk_id);
>> +}
>> +
>> +/* Assign a persistent device name */
>> +static ssize_t store_disk_name(struct device *dev,
>> +		struct device_attribute *attr, char *buf, size_t count)
>> +{
>> +	struct scsi_unnamed *su = to_scsi_unnamed(dev);
>> +	struct scsi_unnamed *tmp;
>> +	struct device *lu = dev->parent;
>> +	int ret = -EINVAL;
>> +
>> +	if (count >= DISK_NAME_LEN) {
>> +		printk(KERN_WARNING "su: Too long a persistent name!\n");
>> +		return -EINVAL;
>> +	}
>> +
>> +	if (su->assigned) {
>> +		printk(KERN_WARNING "su: Already assigned a persistent name!\n");
>> +		return -EINVAL;
>> +	}
>> +
>> +	if (strncmp(lu->driver->name, buf, 2)) {
>> +		printk(KERN_WARNING "su: Wrong prefix!\n");
>> +		return -EINVAL;
>> +	}
>> +
>> +	mutex_lock(&su_list_lock);
>> +	list_for_each_entry(tmp, &su_list, list) {
>> +		if (!strncmp(tmp->disk_name, buf, DISK_NAME_LEN)) {
>> +			printk(KERN_WARNING "su: Duplicate name exsists!\n");
>> +			return -EINVAL;
>> +		}
>> +	}
>> +	strncpy(su->disk_name, buf, DISK_NAME_LEN);
>> +	mutex_unlock(&su_list_lock);
>> +
>> +	if (!lu->driver->probe)
>> +		return -EINVAL;
>> +
>> +	lu->init_name = buf;
>> +
>> +	ret = lu->driver->probe(lu);
>> +	if (ret) {
>> +		lu->init_name = NULL;
>> +		su->disk_name[0] = '\0';
>> +		return ret;
>> +	}
>> +
>> +	su->assigned = true;
>> +	return count;
>> +}
>> +
>> +static DEVICE_ATTR(disk_name, S_IRUGO|S_IWUSR, show_disk_name,
>> +			store_disk_name);
>> +static DEVICE_ATTR(disk_lun, S_IRUGO, show_disk_lun, NULL);
>> +static DEVICE_ATTR(disk_id, S_IRUGO, show_disk_id, NULL);
>> +
>> +/* Confirm the driver name and the device type */
>> +static int check_device_type(char type, const char *name)
>> +{
>> +	switch (type) {
>> +	case TYPE_DISK:
>> +	case TYPE_MOD:
>> +	case TYPE_RBC:
>> +		if (strncmp("sd", name, 2))
>> +			return -ENODEV;
>> +		break;
>> +	case TYPE_ROM:
>> +	case TYPE_WORM:
>> +		if (strncmp("sr", name, 2))
>> +			return -ENODEV;
>> +		break;
>> +	case TYPE_TAPE:
>> +		if (strncmp("st", name, 2))
>> +			return -ENODEV;
>> +		break;
>> +	default:
>> +		break;
>> +	}
>> +	return 0;
>> +}
>> +
>> +/**
>> + * scsi_unnamed_probe - Setup the unnamed device.
>> + * @dev: parent scsi device
>> + *
>> + * This function adds a unnamed device to the device model and
>> + * gets a number of device information by scsi inquiry commands.
>> + * Udev identify a device by those information.
>> + *
>> + * Unnamed devices:
>> + * This device is not a block device and user can not read/write
>> + * this device. But it can advertise device information in sysfs.
>> + */
>> +int scsi_unnamed_probe(struct device *dev)
>> +{
>> +	struct scsi_unnamed *su;
>> +	struct scsi_device *sdev = to_scsi_device(dev);
>> +	int ret = -EINVAL;
>> +	static int i;
>> +
>> +	if (check_device_type(sdev->type, dev->driver->name))
>> +		return -ENODEV;
>> +
>> +	su = kzalloc(sizeof(*su), GFP_KERNEL);
>> +	if (!su)
>> +		return -ENOMEM;
>> +
>> +	device_initialize(&su->dev);
>> +	su->dev.parent = dev;
>> +	su->dev.class = &su_sysfs_class;
> 
> You just created a device that can not be removed from the system (i.e.
> you have no release function.)  This is a major bug and as per the
> documentation for kobjects and the driver model in the kernel tree, I am
> allowed to mock this code mercilessly :)
> 

Oh... sorry :(


>> +	dev_set_name(&su->dev, "su%d", i++);
>> +	strncpy(su->disk_lun, dev_name(dev), MAX_BUFFER_LEN);
>> +
>> +	ret = device_add(&su->dev);
>> +	if (ret)
>> +		goto err;
>> +
>> +	ret = device_create_file(&su->dev, &dev_attr_disk_name);
> 
> Nope, you just raced with userspace here.  NEVER create a sysfs file
> after you have added it to the system.  Userspace just got notified of
> the device and is already starting to read the file.  As it's not there
> yet, you just failed :(
> 
> Use attributes properly to keep this race from happening.
> 

OK. I'll try to be more careful in future


> 
>> +	if (ret)
>> +		goto err_disk_name;
>> +
>> +	ret = device_create_file(&su->dev, &dev_attr_disk_lun);
>> +	if (ret)
>> +		goto err_disk_lun;
>> +
>> +	store_disk_id(sdev, su->disk_id);
>> +	if (su->disk_id[0] != '\0') {
>> +		ret = device_create_file(&su->dev, &dev_attr_disk_id);
>> +		if (ret)
>> +			goto err_disk_id;
>> +	}
>> +
>> +	su->assigned = false;
>> +	mutex_lock(&su_list_lock);
>> +	list_add(&su->list, &su_list);
>> +	mutex_unlock(&su_list_lock);
>> +
>> +	return 0;
>> +
>> +err_disk_id:
>> +	device_remove_file(&su->dev, &dev_attr_disk_lun);
>> +
>> +err_disk_lun:
>> +	device_remove_file(&su->dev, &dev_attr_disk_name);
>> +
>> +err_disk_name:
>> +	device_del(&su->dev);
>> +
>> +err:
>> +	kfree(su);
>> +	return ret;
>> +}
>> +
>> +/* Remove a unnamed device from su_list and release resources */
>> +void scsi_unnamed_remove(struct device *dev)
>> +{
>> +	struct scsi_unnamed *tmp;
>> +
>> +	mutex_lock(&su_list_lock);
>> +	list_for_each_entry(tmp, &su_list, list) {
>> +		if (dev = tmp->dev.parent) {
>> +			list_del(&tmp->list);
>> +			break;
>> +		}
>> +	}
>> +	mutex_unlock(&su_list_lock);
>> +
>> +	if (tmp->disk_id[0] != '\0')
>> +		device_remove_file(&tmp->dev, &dev_attr_disk_id);
>> +	device_remove_file(&tmp->dev, &dev_attr_disk_name);
>> +	device_remove_file(&tmp->dev, &dev_attr_disk_lun);
>> +	device_del(&tmp->dev);
> 
> Your kerrnel just spit out some very nasty messages when this function
> was called, right?  Why are you ignoring them?
> 

Sorry. I will check it.


>> +
>> +	device_release_driver(dev);
>> +
>> +	kfree(tmp);
>> +}
>> +
>> +/**
>> + * copy_persistent_name - Copy the device name
>> + * @disk_name: allocate to
>> + * @dev: scsi device
>> + *
>> + * Copy an initial name of the device to disk_name.
>> + */
>> +int copy_persistent_name(char *disk_name, struct device *dev)
>> +{
>> +	if (persistent_name) {
>> +		strncpy(disk_name, dev->init_name, DISK_NAME_LEN);
>> +		return 1;
>> +	}
>> +	return 0;
>> +}
>> +EXPORT_SYMBOL(copy_persistent_name);
> 
> That's a very bad global function name.
> 

I have a bad sense :(
I will name this function scsi_unnamed_copy_persistent_name.


> EXPORT_SYMBOL_GPL?  And why is it exported at all?  Who would ever need
> to call this from a module?
> 

Please see the patch 2/2. This function is called by external

>> +
>> +int scsi_unnamed_register(struct bus_type *bus)
>> +{
>> +	if (persistent_name) {
>> +		bus->probe = scsi_unnamed_probe;
>> +		bus->remove = scsi_unnamed_remove;
>> +		return class_register(&su_sysfs_class);
>> +	}
>> +	return 0;
>> +}
>> +EXPORT_SYMBOL(scsi_unnamed_register);
> 
> Same here, why is this exported?
> 
>> +
>> +void scsi_unnamed_unregister(void)
>> +{
>> +	if (persistent_name)
>> +		class_unregister(&su_sysfs_class);
>> +}
>> +EXPORT_SYMBOL(scsi_unnamed_unregister);
> 
> And here.
> 
>> diff --git a/drivers/scsi/scsi_unnamed.h b/drivers/scsi/scsi_unnamed.h
>> new file mode 100644
>> index 0000000..ca4e852
>> --- /dev/null
>> +++ b/drivers/scsi/scsi_unnamed.h
>> @@ -0,0 +1,25 @@
>> +/*
>> + * scsi_unnamed.h - SCSI driver for unnmaed device
>> + *
>> + * Copyright: Copyright (c) Hitachi, Ltd. 2011
>> + *            Authors: Nao Nishijima <nao.nishijima.xt@hitachi.com>
>> + *
>> + * This program is free software; you can redistribute it and/or modify
>> + * it under the terms of the GNU General Public License as published by
>> + * the Free Software Foundation; either version 2 of the License, or
>> + * (at your option) any later version.
> 
> Same comment as above.
> 
>> + *
>> + * This program is distributed in the hope that it will be useful,
>> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
>> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
>> + * GNU General Public License for more details.
>> + *
>> + * You should have received a copy of the GNU General Public License
>> + * along with this program; if not, write to the Free Software
>> + * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111 USA
> 
> And again, same comment as above.
> 
> thanks,
> 
> greg k-h
> 

Thanks,

-- 
Nao NISHIJIMA
Software Platform Research Dept. Linux Technology Center
Hitachi, Ltd., YOKOHAMA Research  Laboratory
Email: nao.nishijima.xt@hitachi.com

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Hannes Reinecke @ 2011-04-08 14:33 UTC (permalink / raw)
  To: Nao Nishijima
  Cc: Greg KH, linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <4D9F17DF.5030601@hitachi.com>

On 04/08/2011 07:12 AM, Nao Nishijima wrote:
> Hi,
> 
> (2011/04/06 1:14), Greg KH wrote:
>> On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
>>> This patch series provides a SCSI option for persistent device
>>> names in kernel. With this option, user can always assign a
>>> same device name (e.g. sda) to a specific device according to
>>> udev rules and device id.
>>>
>>> Issue:
>>> Recently, kernel registers block devices in parallel. As a result,
>>> different device names will be assigned at each boot time. This
>>> will confuse file-system mounter, thus we usually use persistent
>>> symbolic links provided by udev.
>>
>> Yes, that is what you should use if you care about this.
>>
>>> However, dmesg and procfs outputs
>>> show device names instead of the symbolic link names. This causes
>>> a serious problem when managing multiple devices (e.g. on a
>>> large-scale storage), because usually, device errors are output
>>> with device names on dmesg.
>>
>> Then fix your tools that read the output of these files to point to the
>> proper persistent name instead of trying to get the kernel to solve the
>> problem.
>>
> 
> Yes, the tools should be revised if users get a device name using them.
> 
> The problem I would like to discuss here is that users can not identify
> a disk from kernel messages when they DIRECTLY refer to these messages.
> For example, a device name is used instead of a symbolic link names in
> bootup messages, I/O devices errors and /proc/partitions …etc.
> 
> In particular, users can not identify an appropriate device from a
> device name in syslog since different device name may be assigned to it
> at each boot time.
> 
> My idea is able to fix this issue with small changes in scsi subsystem.
> Also, it is implemented as an option. Therefore, it does not affect
> users who do not select this option.
> 
We have been discussing this problem several times in the past, and
indeed on these very mailing list.

The conclusion we arrived at is that the kernel-provided device node
name is inherently unstable and impossible to fix within the existing
'sdX' naming scheme.
So the choices have been to either move to a totally different naming
scheme or keep the naming scheme and provide the required information
by other means.
We have decided on the latter, and agreed on using udev to provide
persistent device names.
We are fully aware that any kernel related messages are subject to
chance after reboot, but then most kernel related messages are
(PID number, timestamps, login tty etc).
And also we are aware that any kernel messages need to be matched
against the current system layout to figure out any hardware-related
issue.

But then basically all products requiring to filter out information
from kernel messages already do so I don't see a problem with that.

Just adding an in-kernel identifier to the LUN will only be an
incomplete solution, as other identifiers will still be volatile.

So I would prefer by keeping the in-kernel information as small
as possible to reduce memory consumption and rely on out-of-band
programs to provide the required mapping.

Cheers,

Hannes
--
Dr. Hannes Reinecke              zSeries & Storage
hare@suse.de                  +49 911 74053 688
SUSE LINUX Products GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: Markus Rex, HRB 16746 (AG Nürnberg)



^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device
From: James Bottomley @ 2011-04-08 15:14 UTC (permalink / raw)
  To: Hannes Reinecke
  Cc: Nao Nishijima, Greg KH, linux-kernel, linux-scsi, linux-hotplug,
	Kay Sievers, Jon Masters, 2nddept-manager
In-Reply-To: <4D9F1CD1.2020600@suse.de>

On Fri, 2011-04-08 at 07:33 -0700, Hannes Reinecke wrote:
> > The problem I would like to discuss here is that users can not identify
> > a disk from kernel messages when they DIRECTLY refer to these messages.
> > For example, a device name is used instead of a symbolic link names in
> > bootup messages, I/O devices errors and /proc/partitions …etc.
> > 
> > In particular, users can not identify an appropriate device from a
> > device name in syslog since different device name may be assigned to it
> > at each boot time.
> > 
> > My idea is able to fix this issue with small changes in scsi subsystem.
> > Also, it is implemented as an option. Therefore, it does not affect
> > users who do not select this option.
> > 
> We have been discussing this problem several times in the past, and
> indeed on these very mailing list.
> 
> The conclusion we arrived at is that the kernel-provided device node
> name is inherently unstable and impossible to fix within the existing
> 'sdX' naming scheme.
> So the choices have been to either move to a totally different naming
> scheme or keep the naming scheme and provide the required information
> by other means.
> We have decided on the latter, and agreed on using udev to provide
> persistent device names.
> We are fully aware that any kernel related messages are subject to
> chance after reboot, but then most kernel related messages are
> (PID number, timestamps, login tty etc).
> And also we are aware that any kernel messages need to be matched
> against the current system layout to figure out any hardware-related
> issue.
> 
> But then basically all products requiring to filter out information
> from kernel messages already do so I don't see a problem with that.
> 
> Just adding an in-kernel identifier to the LUN will only be an
> incomplete solution, as other identifiers will still be volatile.
> 
> So I would prefer by keeping the in-kernel information as small
> as possible to reduce memory consumption and rely on out-of-band
> programs to provide the required mapping.

So, while I agree totally with the above: udev and userspace is the way
to go, I'm not totally opposed to having a non-invasive mechanism for
indicating a user's preferred name for a device.  I think there are a
couple of ways to do this:

     1. Entirely in userspace: just have udev consult a preferred name
        file and create say /dev/disk/by-preferred.  Then have all the
        tools that normally output device information do the same (i.e.
        since real name to preferred name is 1:1, they could all do a
        reverse lookup).
     2. have a writeable sysfs preferred_name field, either in the
        generic device or just in SCSI.  The preferred name would be
        used by outbound only (i.e. kernel dev_printk messages and
        possibly /proc/partitions).  All inbound uses of the device
        would come via the standard udev mechanisms
        (i.e. /dev/disk/by-preferred would be the usual symlink).  This
        means from the kernel point of view, no renaming has happened.
        We'd just try to print out the preferred name in certain
        circumstances, which should solve most of the described problem.

James



^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Greg KH @ 2011-04-08 16:12 UTC (permalink / raw)
  To: Nao Nishijima
  Cc: linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <4D9F16AD.2090408@hitachi.com>

On Fri, Apr 08, 2011 at 11:07:41PM +0900, Nao Nishijima wrote:
> Hi,
> 
> (2011/04/06 1:14), Greg KH wrote:
> > On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
> >> This patch series provides a SCSI option for persistent device
> >> names in kernel. With this option, user can always assign a
> >> same device name (e.g. sda) to a specific device according to
> >> udev rules and device id.
> >>
> >> Issue:
> >> Recently, kernel registers block devices in parallel. As a result,
> >> different device names will be assigned at each boot time. This
> >> will confuse file-system mounter, thus we usually use persistent
> >> symbolic links provided by udev. However, dmesg and procfs outputs
> >> show device names instead of the symbolic link names. This causes
> >> a serious problem when managing multiple devices (e.g. on a
> >> large-scale storage), because usually, device errors are output
> >> with device names on dmesg. We also concern about some commands
> >> which output device names, as well as kernel messages.
> >>
> >> Solution:
> >> To assign a persistent device name, I create unnamed devices (not
> >> a block device, but an intermediate device. users cannot read/write
> >> this device). When scsi device driver finds a LU, the LU is registered
> >> as an unnamed device and inform to udev. After udev finds the unnamed
> >> device, udev assigns a persistent device name to a specific device
> >> according to udev rules and registers it as a block device. Hence,
> >> this is just a naming, not a renaming.
> >>
> >> Some users are satisfied with current udev solution. Therefore, my
> >> proposal is implemented as an option.
> >>
> >> If using this option, add the following kernel parameter.
> >>
> >> 	scsi_mod.persistent_name=1
> >>
> >> Also, if you want to assign a device name with sda, add the
> >> following udev rules.
> >>
> >> SUBSYSTEM="scsi_unnamed", ATTR{disk_id}="xxx", PROGRAM="/bin/sh
> >> -c 'echo -n sda > /sys/%p/disk_name'"
> > 
> > Also, where is the "real" program you have created to properly name
> > devices from userspace?  You need that to properly test this patch,
> > right?
> > 
> 
> In the udev rule described above, notation “xxx” indicated by
> ATTR(disk_id) is scsi id given by disk. Then, when udev finds this rule,
> "/bin/sh -c 'echo -n sda>  /sys/%p/disk_name'" indicated by PROGRAM is
> operated using xxx (scsi id) if udev find the disk with scic id xxx.
> Thus, persistent device name is assigned.
> 
> I have tested this patch using the udev rule. and It works well.

That's nice, but it's a "toy".  What have you used to test this with
20000 scsi devices to properly work like it does today?  Where is the
program that will name them in a deterministic manner?

We have that functionality today, you can't break it.

thanks,

greg k-h

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Greg KH @ 2011-04-08 16:14 UTC (permalink / raw)
  To: James Bottomley
  Cc: Hannes Reinecke, Nao Nishijima, linux-kernel, linux-scsi,
	linux-hotplug, Kay Sievers, Jon Masters, 2nddept-manager
In-Reply-To: <1302275652.4090.10.camel@mulgrave.site>

On Fri, Apr 08, 2011 at 08:14:12AM -0700, James Bottomley wrote:
> So, while I agree totally with the above: udev and userspace is the way
> to go, I'm not totally opposed to having a non-invasive mechanism for
> indicating a user's preferred name for a device.  I think there are a
> couple of ways to do this:
> 
>      1. Entirely in userspace: just have udev consult a preferred name
>         file and create say /dev/disk/by-preferred.  Then have all the
>         tools that normally output device information do the same (i.e.
>         since real name to preferred name is 1:1, they could all do a
>         reverse lookup).
>      2. have a writeable sysfs preferred_name field, either in the
>         generic device or just in SCSI.  The preferred name would be
>         used by outbound only (i.e. kernel dev_printk messages and
>         possibly /proc/partitions).  All inbound uses of the device
>         would come via the standard udev mechanisms
>         (i.e. /dev/disk/by-preferred would be the usual symlink).  This
>         means from the kernel point of view, no renaming has happened.
>         We'd just try to print out the preferred name in certain
>         circumstances, which should solve most of the described problem.

Either, or both, of those options are fine with me as well.

thanks,

greg k-h

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Kay Sievers @ 2011-04-08 16:43 UTC (permalink / raw)
  To: Greg KH
  Cc: James Bottomley, Hannes Reinecke, Nao Nishijima, linux-kernel,
	linux-scsi, linux-hotplug, Jon Masters, 2nddept-manager
In-Reply-To: <20110408161420.GB12111@kroah.com>

On Fri, Apr 8, 2011 at 18:14, Greg KH <greg@kroah.com> wrote:
> On Fri, Apr 08, 2011 at 08:14:12AM -0700, James Bottomley wrote:
>> So, while I agree totally with the above: udev and userspace is the way
>> to go, I'm not totally opposed to having a non-invasive mechanism for
>> indicating a user's preferred name for a device.  I think there are a
>> couple of ways to do this:
>>
>>      1. Entirely in userspace: just have udev consult a preferred name
>>         file and create say /dev/disk/by-preferred.  Then have all the
>>         tools that normally output device information do the same (i.e.
>>         since real name to preferred name is 1:1, they could all do a
>>         reverse lookup).
>>      2. have a writeable sysfs preferred_name field, either in the
>>         generic device or just in SCSI.  The preferred name would be
>>         used by outbound only (i.e. kernel dev_printk messages and
>>         possibly /proc/partitions).  All inbound uses of the device
>>         would come via the standard udev mechanisms
>>         (i.e. /dev/disk/by-preferred would be the usual symlink).  This
>>         means from the kernel point of view, no renaming has happened.
>>         We'd just try to print out the preferred name in certain
>>         circumstances, which should solve most of the described problem.
>
> Either, or both, of those options are fine with me as well.

I guess a generic sysfs file, that can carry a user-given name for a
device, and which is looked-up with dev_printk() macro, and maybe
/proc/partitions is all what we would need if we want to involve the
kernel here.

Kay

^ permalink raw reply

* Re: [PATCH 1/2] SCSI: Add a SCSI option for persistent device names
From: Stefan Richter @ 2011-04-08 17:21 UTC (permalink / raw)
  To: Nao Nishijima
  Cc: Greg KH, linux-kernel, linux-scsi, linux-hotplug, Kay Sievers,
	James Bottomley, Jon Masters, 2nddept-manager
In-Reply-To: <4D9F17DF.5030601@hitachi.com>

On Apr 08 Nao Nishijima wrote:
> (2011/04/06 1:14), Greg KH wrote:
> > On Tue, Apr 05, 2011 at 09:49:46PM +0900, Nao Nishijima wrote:
> >> Todo:
> >> - usb support
> > 
> > Why?  USB uses scsi, so why would it not work as-is today?  What about
> > libata devices?
> > 
> 
> Sorry, my explanation was not sufficient.
> It is required to get scsi id using a scsi inguiry command in order to
> create the udev rule, especially in ATTR(disk_id) item in it. The USB
> devices, however, do not respond to the command and we can not get their
> scsi id.

Identifiers and names of target ports and of logical units (per SAM-2 and
later, Annex A) --- whether they are persistent, in which scope they are
unique, how they look like, and how they can be obtained --- are transport
specific.

Neither the INQUIRY command (per SPC) nor any other command is generally
useful to obtain e.g. logical unit identifiers.  Any tool that needs to
obtain identifiers or names of target ports and of logical units must talk
with the transport driver through driver-specific interfaces.

Years ago it was suggested on this list that scsi-mod exposes standard
sysfs attributes for target and LU identifiers and names for all devices,
so that tools that need identfiers or names have a single place where they
can look them up.  (The read() method of these attributes would have to
be provided kernel-internally by transport drivers; and tools that read
these attributes need to be aware that there is not a single format for
identifiers and names.)

The SCSI folks were not interested in such a more standardized sysfs ABI
at that time.  (There was only a proposal anyway, not a patch.)  Hence,
tools have to dig at various places for these SAM-2 artifacts.  These ABIs
have been defined ad hoc by the transport driver implementers.

Anyway.  /How/ to obtain identifiers is just a side issue.  Back to the
proposal of letting userland tell the kernel how to name devices:

> >> I create unnamed devices (not
> >> a block device, but an intermediate device.
[...]
> >> After udev finds the unnamed
> >> device, udev assigns a persistent device name to a specific device
> >> according to udev rules and registers it as a block device. Hence,
> >> this is just a naming, not a renaming.

I disagree to this conclusion.  The "unnamed" device most definitely will
have a name before it can be shown to userland.  This preliminary name
fulfills the very same requirement that "s[drt][a-z]+[0-9]*" fulfill
today:  It is unique within the system during the lifetime of the
device.  So, this /is/ renaming, only that the first name is only exposed
to special tools that know of this new ABI.

It seems to me that today's procedure of /not/ renaming devices but of
providing as many alternative additional names as anyone could ever need
(symlinks within /dev/) is more robust.

If the contents of /var/log/messages or the output of iostat etc. is not
what is needed, how about simply filtering that through a grep/ sed based
script that rewrites names?  (This needs to be run during the lifetime of
the device of course, otherwise a wrong name could be put in.)  The fine
symlinks that udev provides can be used in such a text filter.
-- 
Stefan Richter
-===-=-= -=-- -=---
http://arcgraph.de/sr/

^ permalink raw reply

* [PULL] Docs: README: Copyediting
From: Michael Witten @ 2011-04-11  6:22 UTC (permalink / raw)
  To: linux-hotplug

I did some copyediting whilst looking through the README;
this email contains a pull request as well as the inlined
diff of all the changes squashed together.

The changes apply cleanly to 960250952193db522b8ced336bf998bd7e8e4a31:

  selinux: firmware - do not label files in runtime dir (2011-04-08 03:08:16 +0200)

and are available here:

  git://github.com/mfwitten/udev.git docs/README

Squash them if desired.

      Docs: README: `to replace' -> `replacing'
      Docs: README: `,' -> `;'
      Docs: README: Clean up a sentence
      Docs: README: Use present tense
      Docs: README: Add missing `and'
      Docs: README: Remove commas and use subjective mood
      Docs: README: Clean up `udev extras' requirements
      Docs: README: Clarify configuration of existing devices
      Docs: README: `does never apply' -> `never applies'
      Docs: README: Flip sentence structure to improve wording
      Docs: README: `set up' is the verb; `setup' is a noun
      Docs: README: Add a comma to offset the modifier

 README |   44 ++++++++++++++++++++++----------------------
 1 files changed, 22 insertions(+), 22 deletions(-)

diff --git a/README b/README
index 7878746..4520f3d 100644
--- a/README
+++ b/README
@@ -3,17 +3,17 @@ udev - Linux userspace device management
 Integrating udev in the system has complex dependencies and may differ from
 distribution to distribution. A system may not be able to boot up or work
 reliably without a properly installed udev version. The upstream udev project
-does not recommend to replace a distro's udev installation with the upstream
+does not recommend replacing a distro's udev installation with the upstream
 version.
 
 The upstream udev project's set of default rules may require a most recent
 kernel release to work properly. This is currently version 2.6.31.
 
 Tools and rules shipped by udev are not public API and may change at any time.
-Never call any private tool in /lib/udev from any external application, it might
+Never call any private tool in /lib/udev from any external application; it might
 just go away in the next release. Access to udev information is only offered
-by udevadm and libudev. Tools and rules in /lib/udev, and the entire content of
+by udevadm and libudev. Tools and rules in /lib/udev and the entire contents of
-the /dev/.udev directory is private to udev and does change whenever needed.
+the /dev/.udev directory are private to udev and do change whenever needed.
 
 Requirements:
   - Version 2.6.27 of the Linux kernel with sysfs, procfs, signalfd, inotify,
@@ -31,7 +31,7 @@ Requirements:
       CONFIG_TMPFS_POSIX_ACL=y (user ACLs for device nodes)
       CONFIG_BLK_DEV_BSG=y (SCSI devices)
 
-  - Udev will not work with the CONFIG_SYSFS_DEPRECATED* option.
+  - Udev does not work with the CONFIG_SYSFS_DEPRECATED* option.
 
   - Unix domain sockets (CONFIG_UNIX) as a loadable kernel module may work,
     but it is not supported.
@@ -41,46 +41,46 @@ Requirements:
     unusable because the kernel may create too many processes in parallel
     so that the system runs out-of-memory.
 
-  - The proc filesystem must be mounted on /proc, the sysfs filesystem must
+  - The proc filesystem must be mounted on /proc, and the sysfs filesystem must
     be mounted at /sys. No other locations are supported by a standard
     udev installation.
 
   - The system must have the following group names resolvable at udev startup:
-      disk, cdrom, floppy, tape, audio, video, lp, tty, dialout, kmem.
+      disk, cdrom, floppy, tape, audio, video, lp, tty, dialout, and kmem.
-    Especially in LDAP setups, it is required, that getgrnam() is able to resolve
+    Especially in LDAP setups, it is required that getgrnam() be able to resolve
-    these group names with only the rootfs mounted, and while no network is
+    these group names with only the rootfs mounted and while no network is
     available.
 
-  - To build all 'udev extras', libacl, libglib2, libusb, usbutils, pciutils,
-    gperf are needed. These dependencies can be disabled with the
-    --disable-extras configure option.
+  - The 'udev extras' has the following dependencies:
+      libacl, libglib2, libusb, usbutils, pciutils, and gperf.
+    These dependencies can be disabled with the --disable-extras configure option.
 
 Setup:
   - At bootup, the /dev directory should get the 'devtmpfs' filesystem
-    mounted. Udev will manage permissions and ownership of the kernel-created
+    mounted. Udev manages the permissions and ownership of the kernel-created
-    device nodes, and possibly create additional symlinks. If needed, udev also
+    device nodes, and udev possibly creates additional symlinks. If needed, udev also
     works on an empty 'tmpfs' filesystem, but some static device nodes like
     /dev/null, /dev/console, /dev/kmsg are needed to be able to start udev itself.
 
   - The udev daemon should be started to handle device events sent by the kernel.
     During bootup, the kernel can be asked to send events for all already existing
-    devices, to apply the configuration to these devices. This is usually done by:
+    devices so that they too can be configured by udev. This is usually done by:
       /sbin/udevadm trigger --type=subsystems
       /sbin/udevadm trigger --typefivices
 
-  - Restarting the daemon does never apply any rules to existing devices.
+  - Restarting the daemon never applies any rules to existing devices.
 
-  - New/changed rule files are picked up automatically, there is no daemon
+  - New/changed rule files are picked up automatically; there is no daemon
     restart or signal needed.
 
 Operation:
-  - Udev creates/removes device nodes in /dev, based on events the kernel
-    sends out on device creation/removal.
+  - Based on events the kernel sends out on device creation/removal, udev
+    creates/removes device nodes in the /dev directory.
 
   - All kernel events are matched against a set of specified rules, which
     possibly hook into the event processing and load required kernel
-    modules to setup devices. For all devices the kernel exports a major/minor
+    modules to set up devices. For all devices, the kernel exports a major/minor
-    number, if needed, udev will create a device node with the default kernel
+    number; if needed, udev creates a device node with the default kernel
     name. If specified, udev applies permissions/ownership to the device
     node, creates additional symlinks pointing to the node, and executes
     programs to handle the device.
@@ -90,7 +90,7 @@ Operation:
       http://www.kernel.org/pub/linux/utils/kernel/hotplug/libudev/
       http://www.kernel.org/pub/linux/utils/kernel/hotplug/gudev/
 
-For more details about udev and udev rules see the udev(7) man page.
+For more details about udev and udev rules, see the udev(7) man page.
 
 Please direct any comment/question to the linux-hotplug mailing list at:
   linux-hotplug@vger.kernel.org
--
To unsubscribe from this list: send the line "unsubscribe linux-hotplug" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox