We need to prevent that libudev parses half-written database files.
Also for "change" events, we need to make sure, that database files
always exist to be read by libudev, and that they are not first deleted
before they are re-created.
# libudev
# ------------------------------------------------------------------------------
LIBUDEV_CURRENT=6
# libudev
# ------------------------------------------------------------------------------
LIBUDEV_CURRENT=6
LIBUDEV_AGE=6
SUBDIRS += libudev/docs
LIBUDEV_AGE=6
SUBDIRS += libudev/docs
{
struct udev *udev = udev_device_get_udev(udev_device);
char filename[UTIL_PATH_SIZE];
{
struct udev *udev = udev_device_get_udev(udev_device);
char filename[UTIL_PATH_SIZE];
+ char filename_tmp[UTIL_PATH_SIZE];
FILE *f;
char target[232]; /* on 64bit, tmpfs inlines up to 239 bytes */
size_t devlen = strlen(udev_get_dev_path(udev))+1;
FILE *f;
char target[232]; /* on 64bit, tmpfs inlines up to 239 bytes */
size_t devlen = strlen(udev_get_dev_path(udev))+1;
util_strscpyl(filename, sizeof(filename), udev_get_dev_path(udev), "/.udev/db/",
udev_device_get_subsystem(udev_device), ":", udev_device_get_sysname(udev_device), NULL);
util_strscpyl(filename, sizeof(filename), udev_get_dev_path(udev), "/.udev/db/",
udev_device_get_subsystem(udev_device), ":", udev_device_get_sysname(udev_device), NULL);
+ util_strscpyl(filename_tmp, sizeof(filename_tmp), filename, ".tmp", NULL);
udev_list_entry_foreach(list_entry, udev_device_get_properties_list_entry(udev_device))
if (udev_list_entry_get_flag(list_entry))
udev_list_entry_foreach(list_entry, udev_device_get_properties_list_entry(udev_device))
if (udev_list_entry_get_flag(list_entry))
- info(udev, "create db link (%s)\n", target);
- udev_selinux_setfscreatecon(udev, filename, S_IFLNK);
- util_create_path(udev, filename);
- ret = symlink(target, filename);
+ udev_selinux_setfscreatecon(udev, filename_tmp, S_IFLNK);
+ util_create_path(udev, filename_tmp);
+ ret = symlink(target, filename_tmp);
udev_selinux_resetfscreatecon(udev);
udev_selinux_resetfscreatecon(udev);
- if (ret == 0)
- goto out;
+ if (ret != 0)
+ goto file;
+ ret = rename(filename_tmp, filename);
+ if (ret != 0)
+ goto file;
+ info(udev, "created db link (%s)\n", target);
+ goto out;
- util_create_path(udev, filename);
- f = fopen(filename, "w");
+ util_create_path(udev, filename_tmp);
+ f = fopen(filename_tmp, "w");
- err(udev, "unable to create db file '%s': %m\n", filename);
+ err(udev, "unable to create temporary db file '%s': %m\n", filename_tmp);
- info(udev, "created db file for '%s' in '%s'\n", udev_device_get_devpath(udev_device), filename);
if (udev_device_get_devnode(udev_device) != NULL) {
fprintf(f, "N:%s\n", &udev_device_get_devnode(udev_device)[devlen]);
if (udev_device_get_devnode(udev_device) != NULL) {
fprintf(f, "N:%s\n", &udev_device_get_devnode(udev_device)[devlen]);
udev_list_entry_get_value(list_entry));
}
fclose(f);
udev_list_entry_get_value(list_entry));
}
fclose(f);
+ rename(filename_tmp, filename);
+ info(udev, "created db file for '%s' in '%s'\n", udev_device_get_devpath(udev_device), filename);