mirror of
https://github.com/systemd/systemd-stable.git
synced 2025-01-12 09:17:44 +03:00
[PATCH] allow multiple symlinks
Here is a patch to allow the creation of multiple symlinks. The names must be separated by a space character. REPLACE, KERNEL="ttyUSB0", NAME="visor", SYMLINK="first-%n second-%n third-%n" results in: Dec 9 05:28:51 pim udev[12019]: create_node: mknod(udev-root/visor, 020666, 188, 0) Dec 9 05:28:51 pim udev[12019]: create_node: symlink 'udev-root/first-0' to node 'visor' requested Dec 9 05:28:51 pim udev[12019]: create_node: symlink(./visor, udev-root/first-0) Dec 9 05:28:51 pim udev[12019]: create_node: symlink 'udev-root/second-0' to node 'visor' requested Dec 9 05:28:51 pim udev[12019]: create_node: symlink(./visor, udev-root/second-0) Dec 9 05:28:51 pim udev[12019]: create_node: symlink 'udev-root/third-0' to node 'visor' requested Dec 9 05:28:51 pim udev[12019]: create_node: symlink(./visor, udev-root/third-0)
This commit is contained in:
parent
10a479f5e6
commit
4763256c65
@ -215,6 +215,15 @@ EOF
|
||||
expected => "1/2/c/d/symlink" ,
|
||||
conf => <<EOF
|
||||
LABEL, BUS="scsi", vendor="IBM-ESXS", NAME="1/2/a/b/node", SYMLINK="1/2/c/d/symlink"
|
||||
EOF
|
||||
},
|
||||
{
|
||||
desc => "multiple symlinks",
|
||||
subsys => "tty",
|
||||
devpath => "class/tty/ttyUSB0",
|
||||
expected => "second-0" ,
|
||||
conf => <<EOF
|
||||
REPLACE, KERNEL="ttyUSB0", NAME="visor", SYMLINK="first-%n second-%n third-%n"
|
||||
EOF
|
||||
},
|
||||
);
|
||||
|
66
udev-add.c
66
udev-add.c
@ -102,6 +102,8 @@ static int create_node(struct udevice *dev)
|
||||
{
|
||||
char filename[255];
|
||||
char linktarget[255];
|
||||
char *linkname;
|
||||
char *symlinks;
|
||||
int retval = 0;
|
||||
uid_t uid = 0;
|
||||
gid_t gid = 0;
|
||||
@ -186,39 +188,45 @@ static int create_node(struct udevice *dev)
|
||||
filename, uid, gid, strerror(errno));
|
||||
}
|
||||
|
||||
|
||||
/* create symlink if requested */
|
||||
if (*dev->symlink) {
|
||||
strncpy(filename, udev_root, sizeof(filename));
|
||||
strncat(filename, dev->symlink, sizeof(filename));
|
||||
dbg("symlink '%s' to node '%s' requested", filename, dev->name);
|
||||
if (strrchr(dev->symlink, '/'))
|
||||
create_path(filename);
|
||||
symlinks = dev->symlink;
|
||||
while (1) {
|
||||
linkname = strsep(&symlinks, " ");
|
||||
if (linkname == NULL)
|
||||
break;
|
||||
|
||||
/* optimize relative link */
|
||||
linktarget[0] = '\0';
|
||||
i = 0;
|
||||
tail = 0;
|
||||
while ((dev->name[i] == dev->symlink[i]) && dev->name[i]) {
|
||||
if (dev->name[i] == '/')
|
||||
tail = i+1;
|
||||
i++;
|
||||
strncpy(filename, udev_root, sizeof(filename));
|
||||
strncat(filename, linkname, sizeof(filename));
|
||||
dbg("symlink '%s' to node '%s' requested", filename, dev->name);
|
||||
if (strrchr(linkname, '/'))
|
||||
create_path(filename);
|
||||
|
||||
/* optimize relative link */
|
||||
linktarget[0] = '\0';
|
||||
i = 0;
|
||||
tail = 0;
|
||||
while ((dev->name[i] == linkname[i]) && dev->name[i]) {
|
||||
if (dev->name[i] == '/')
|
||||
tail = i+1;
|
||||
i++;
|
||||
}
|
||||
while (linkname[i]) {
|
||||
if (linkname[i] == '/')
|
||||
strcat(linktarget, "../");
|
||||
i++;
|
||||
}
|
||||
|
||||
if (*linktarget == '\0')
|
||||
strcpy(linktarget, "./");
|
||||
strcat(linktarget, &dev->name[tail]);
|
||||
|
||||
dbg("symlink(%s, %s)", linktarget, filename);
|
||||
retval = symlink(linktarget, filename);
|
||||
if (retval)
|
||||
dbg("symlink(%s, %s) failed with error '%s'",
|
||||
linktarget, filename, strerror(errno));
|
||||
}
|
||||
while (dev->symlink[i]) {
|
||||
if (dev->symlink[i] == '/')
|
||||
strcat(linktarget, "../");
|
||||
i++;
|
||||
}
|
||||
|
||||
if (*linktarget == '\0')
|
||||
strcpy(linktarget, "./");
|
||||
strcat(linktarget, &dev->name[tail]);
|
||||
|
||||
dbg("symlink(%s, %s)", linktarget, filename);
|
||||
retval = symlink(linktarget, filename);
|
||||
if (retval)
|
||||
dbg("symlink(%s, %s) failed with error '%s'",
|
||||
linktarget, filename, strerror(errno));
|
||||
}
|
||||
|
||||
return retval;
|
||||
|
@ -66,6 +66,8 @@ static int delete_path(char *path)
|
||||
static int delete_node(struct udevice *dev)
|
||||
{
|
||||
char filename[255];
|
||||
char *symlinks;
|
||||
char *linkname;
|
||||
int retval;
|
||||
|
||||
strncpy(filename, udev_root, sizeof(filename));
|
||||
@ -84,17 +86,25 @@ static int delete_node(struct udevice *dev)
|
||||
delete_path(filename);
|
||||
|
||||
if (*dev->symlink) {
|
||||
strncpy(filename, udev_root, sizeof(filename));
|
||||
strncat(filename, dev->symlink, sizeof(filename));
|
||||
dbg("unlinking symlink '%s'", filename);
|
||||
retval = unlink(filename);
|
||||
if (retval) {
|
||||
dbg("unlink(%s) failed with error '%s'",
|
||||
filename, strerror(errno));
|
||||
return retval;
|
||||
}
|
||||
if (strchr(dev->symlink, '/')) {
|
||||
delete_path(filename);
|
||||
symlinks = dev->symlink;
|
||||
while (1) {
|
||||
linkname = strsep(&symlinks, " ");
|
||||
if (linkname == NULL)
|
||||
break;
|
||||
|
||||
strncpy(filename, udev_root, sizeof(filename));
|
||||
strncat(filename, linkname, sizeof(filename));
|
||||
|
||||
dbg("unlinking symlink '%s'", filename);
|
||||
retval = unlink(filename);
|
||||
if (retval) {
|
||||
dbg("unlink(%s) failed with error '%s'",
|
||||
filename, strerror(errno));
|
||||
return retval;
|
||||
}
|
||||
if (strchr(dev->symlink, '/')) {
|
||||
delete_path(filename);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user