summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--namedev.c13
-rw-r--r--namedev.h2
-rw-r--r--namedev_parse.c6
-rw-r--r--test/udev-test.pl11
-rw-r--r--udev.8.in4
5 files changed, 35 insertions, 1 deletions
diff --git a/namedev.c b/namedev.c
index 3ab45d4ec6..8bf3c0e73e 100644
--- a/namedev.c
+++ b/namedev.c
@@ -604,7 +604,7 @@ static int match_rule(struct config_device *dev, struct sysfs_class_device *clas
}
}
- /* check for matching kernel name*/
+ /* check for matching kernel name */
if (dev->kernel[0] != '\0') {
dbg("check for " FIELD_KERNEL " dev->kernel='%s' class_dev->name='%s'", dev->kernel, class_dev->name);
if (strcmp_pattern(dev->kernel, class_dev->name) != 0) {
@@ -615,6 +615,17 @@ static int match_rule(struct config_device *dev, struct sysfs_class_device *clas
}
}
+ /* check for matching subsystem */
+ if (dev->subsystem[0] != '\0') {
+ dbg("check for " FIELD_SUBSYSTEM " dev->subsystem='%s' class_dev->name='%s'", dev->subsystem, class_dev->name);
+ if (strcmp_pattern(dev->subsystem, udev->subsystem) != 0) {
+ dbg(FIELD_SUBSYSTEM " is not matching");
+ goto try_parent;
+ } else {
+ dbg(FIELD_SUBSYSTEM " matches");
+ }
+ }
+
/* check for matching bus id */
if (dev->id[0] != '\0') {
dbg("check " FIELD_ID);
diff --git a/namedev.h b/namedev.h
index f1e0082241..3837e864a0 100644
--- a/namedev.h
+++ b/namedev.h
@@ -42,6 +42,7 @@ struct sysfs_class_device;
#define FIELD_PROGRAM "PROGRAM"
#define FIELD_RESULT "RESULT"
#define FIELD_KERNEL "KERNEL"
+#define FIELD_SUBSYSTEM "SUBSYSTEM"
#define FIELD_NAME "NAME"
#define FIELD_SYMLINK "SYMLINK"
#define FIELD_OWNER "OWNER"
@@ -78,6 +79,7 @@ struct config_device {
char kernel[NAME_SIZE];
char program[PROGRAM_SIZE];
char result[PROGRAM_SIZE];
+ char subsystem[SUBSYSTEM_SIZE];
char name[NAME_SIZE];
char symlink[NAME_SIZE];
struct sysfs_pair sysfs_pair[MAX_SYSFS_PAIRS];
diff --git a/namedev_parse.c b/namedev_parse.c
index 73828a83b2..cc02d25555 100644
--- a/namedev_parse.c
+++ b/namedev_parse.c
@@ -258,6 +258,12 @@ static int namedev_parse_rules(const char *filename, void *data)
continue;
}
+ if (strcasecmp(temp2, FIELD_SUBSYSTEM) == 0) {
+ strfieldcpy(dev.subsystem, temp3);
+ valid = 1;
+ continue;
+ }
+
if (strcasecmp(temp2, FIELD_PROGRAM) == 0) {
program_given = 1;
strfieldcpy(dev.program, temp3);
diff --git a/test/udev-test.pl b/test/udev-test.pl
index 2ba63fe83f..5f6f864df2 100644
--- a/test/udev-test.pl
+++ b/test/udev-test.pl
@@ -1104,6 +1104,17 @@ EOF
KERNEL="sda", NAME="cdrom%e"
EOF
},
+ {
+ desc => "SUBSYSTEM test",
+ subsys => "block",
+ devpath => "/block/sda",
+ exp_name => "node",
+ conf => <<EOF
+BUS="scsi", KERNEL="sda", NAME="should_not_match", SUBSYSTEM="vc"
+BUS="scsi", KERNEL="sda", NAME="node", SUBSYSTEM="block"
+BUS="scsi", KERNEL="sda", NAME="should_not_match2", SUBSYSTEM="vc"
+EOF
+ },
);
# set env
diff --git a/udev.8.in b/udev.8.in
index 168842d435..14a28d8dc2 100644
--- a/udev.8.in
+++ b/udev.8.in
@@ -171,6 +171,10 @@ Match the bus type of the device.
.B KERNEL
Match the kernel device name.
.TP
+.B SUBSYSTEM
+Match the kernel's subsystem name.
+.TP
+.TP
.B ID
Match the device number on the bus, like PCI bus id.
.TP