1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
|
Purpose of rules file:
This rules file provides nonvolatile, unique names (in the form of symlinks)
for various types of storage devices -- both IDE/ATA and SCSI.
Description of rules:
First, similar to the 60-persistent-input.rules file, we skip the entire file
for uevents that this rules file should not apply to, as an optimization. The
file does not apply to removal uevents or non-block devices. It does not apply
to ramdisks, loopback-mount devices, floppy disks, netblock devices, or device-
mapper devices. It also should not apply to removable devices (that is, non-
partition devices with attributes named "removable" with the value "1", or
partition devices whose parents have "removable" set to "1" -- partition
kobjects don't have the "removable" attribute, only whole-disk kobjects do).
For partition devices, we use the IMPORT{parent} option to pull in all the
environment variables that get set for the parent device. (The parent of a
partition device is the containing whole-disk device.) The IMPORT{parent}
option is documented in the udev(7) manpage, but basically the value that we
assign is used as a filter of environment variable names to import.
Now, we start with rules to create by-ID symlinks (similar to the by-ID links
created for input devices). For hd* whole-disk devices (they're IDE/ATA, since
they start with hd), we run the ata_id program in --export mode. The ata_id
program requires a device node to be passed, so we also use the $tempnode Udev
variable -- this causes Udev to create a temporary device node somewhere and
substitute its name where $tempnode appears in the program command line.
The ata_id program, in --export mode, prints several ID_* values. If we're
looking at a whole-disk device, and if ID_SERIAL is among those, we add a
symlink containing the device's ID_MODEL and ID_SERIAL values. If we're
looking at a partition device, we create an ID_MODEL- and ID_SERIAL-based
symlink also, but we add -partX to the end of the link name (where X is the
partition number).
For SCSI devices, we first make some modifications to the environment. If the
device's kobject has a parent with a non-empty "ieee1394_id" attribute, then
the device is Firewire, so we set the ID_SERIAL environment variable to the
value of that attribute, and we set ID_BUS to "ieee1394". Now, if ID_SERIAL is
not set, we run usb_id, which (if this is a USB storage device) will print
various values. If ID_SERIAL is still unset, we run scsi_id with a set of
parameters designed to get an ID_SERIAL by querying the device itself. If that
still fails, we try running scsi_id in a mode that prints the information even
if the disk doesn't support so-called "vital product data" pages. If the
uevent is for a DASD device, we run dasd_id.
If one of these *_id programs gave us an ID_SERIAL, then for whole-disk devices
we create a by-ID symlink using the ID_BUS and ID_SERIAL. For partition
devices, we create a by-ID symlink that has the same form except we add -partX
to the end (just like for IDE/ATA devices).
Now we have some rules to create by-path persistent symlinks. We start by
running the path_id program on the DEVPATH (%p) value. For whole-disk devices
and SCSI ROM type devices, we create a symlink directly, using the environment
variable ID_PATH, under the /dev/disk/by-path directory. But for SCSI tape
devices, we create a by-path symlink in the /dev/tape/by-path directory (we
base the symlink on the same information, though: the ID_PATH value printed by
path_id). Now, for both SCSI ROM and SCSI tape devices, we skip everything
that's left in the rules file (this is another optimization: neither SCSI ROM
nor SCSI tape devices have UUIDs, labels, or EDD information).
For partition devices, we now create a by-path symlink of the same form as the
other partition device persistent symlinks (that is, with the same name as the
parent device, but with -partX added). We know that ID_PATH is set whenever it
applies, because we ran the path_id program on the parent device, and we did an
IMPORT{parent} on ID_* earlier in the rules file.
Now we create by-label and by-uuid symlinks. These use properties of various
filesystems to generate a persistent name for a partition. For instance, if
you use the ext2 filesystem, you can use e2label to assign a label, and mke2fs
assigns a UUID when the filesystem is created. MS-DOS compatible filesystems
also assign a "UUID" (actually it's just a serial number, created based on the
date and time the partition was formatted, so it is not unique), which these
rules will also use. But for removable partitions, we skip the rules (for the
same reason as we skipped them above for removable disks).
We run the vol_id program to get ID_FS_USAGE, ID_FS_UUID, and ID_FS_LABEL_SAFE
values. (vol_id supports other values as well, but we do not use them here.)
ID_FS_USAGE corresponds to the way the filesystem is supposed to be used; if it
gets set to "filesystem", "other", or "crypto", we create a symlink. If
ID_FS_UUID is set, we use it in a by-uuid symlink. If ID_FS_LABEL_SAFE is set,
we use it in a by-label symlink.
Finally, we create EDD-based symlinks in the by-id directory. For whole-disk
devices, we run edd_id to get the EDD-generated ID string. (For partition
devices, we import this string from the parent.) If edd_id yields an ID_EDD
value, we use it in a symlink, for both whole disks and partitions.
The last rule in the file is merely a LABEL that various other rules use to
bypass the file (or the rest of the file) when needed.
|