Merge pull request #24646 from yuwata/udev-node-symlink_atomic
udev: introduce symlink_atomic_full() and use it
This commit is contained in:
+11
-9
@@ -406,13 +406,7 @@ int symlink_idempotent(const char *from, const char *to, bool make_relative) {
|
||||
assert(to);
|
||||
|
||||
if (make_relative) {
|
||||
_cleanup_free_ char *parent = NULL;
|
||||
|
||||
r = path_extract_directory(to, &parent);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = path_make_relative(parent, from, &relpath);
|
||||
r = path_make_relative_parent(to, from, &relpath);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
@@ -438,13 +432,21 @@ int symlink_idempotent(const char *from, const char *to, bool make_relative) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int symlink_atomic(const char *from, const char *to) {
|
||||
_cleanup_free_ char *t = NULL;
|
||||
int symlink_atomic_full(const char *from, const char *to, bool make_relative) {
|
||||
_cleanup_free_ char *relpath = NULL, *t = NULL;
|
||||
int r;
|
||||
|
||||
assert(from);
|
||||
assert(to);
|
||||
|
||||
if (make_relative) {
|
||||
r = path_make_relative_parent(to, from, &relpath);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
from = relpath;
|
||||
}
|
||||
|
||||
r = tempfn_random(to, NULL, &t);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
+4
-1
@@ -58,7 +58,10 @@ static inline int touch(const char *path) {
|
||||
|
||||
int symlink_idempotent(const char *from, const char *to, bool make_relative);
|
||||
|
||||
int symlink_atomic(const char *from, const char *to);
|
||||
int symlink_atomic_full(const char *from, const char *to, bool make_relative);
|
||||
static inline int symlink_atomic(const char *from, const char *to) {
|
||||
return symlink_atomic_full(from, to, false);
|
||||
}
|
||||
int mknod_atomic(const char *path, mode_t mode, dev_t dev);
|
||||
int mkfifo_atomic(const char *path, mode_t mode);
|
||||
int mkfifoat_atomic(int dir_fd, const char *path, mode_t mode);
|
||||
|
||||
+2
-2
@@ -61,7 +61,7 @@ int symlink_label(const char *old_path, const char *new_path) {
|
||||
return mac_smack_fix(new_path, 0);
|
||||
}
|
||||
|
||||
int symlink_atomic_label(const char *from, const char *to) {
|
||||
int symlink_atomic_full_label(const char *from, const char *to, bool make_relative) {
|
||||
int r;
|
||||
|
||||
assert(from);
|
||||
@@ -71,7 +71,7 @@ int symlink_atomic_label(const char *from, const char *to) {
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
r = symlink_atomic(from, to);
|
||||
r = symlink_atomic_full(from, to, make_relative);
|
||||
mac_selinux_create_file_clear();
|
||||
|
||||
if (r < 0)
|
||||
|
||||
+4
-1
@@ -17,7 +17,10 @@ static inline int label_fix(const char *path, LabelFixFlags flags) {
|
||||
}
|
||||
|
||||
int symlink_label(const char *old_path, const char *new_path);
|
||||
int symlink_atomic_label(const char *from, const char *to);
|
||||
int symlink_atomic_full_label(const char *from, const char *to, bool make_relative);
|
||||
static inline int symlink_atomic_label(const char *from, const char *to) {
|
||||
return symlink_atomic_full_label(from, to, false);
|
||||
}
|
||||
int mknod_label(const char *pathname, mode_t mode, dev_t dev);
|
||||
|
||||
int btrfs_subvol_make_label(const char *path);
|
||||
|
||||
+8
-27
@@ -14,6 +14,7 @@
|
||||
#include "format-util.h"
|
||||
#include "fs-util.h"
|
||||
#include "hexdecoct.h"
|
||||
#include "label.h"
|
||||
#include "mkdir-label.h"
|
||||
#include "parse-util.h"
|
||||
#include "path-util.h"
|
||||
@@ -69,8 +70,6 @@ int udev_node_cleanup(void) {
|
||||
}
|
||||
|
||||
static int node_symlink(sd_device *dev, const char *devnode, const char *slink) {
|
||||
_cleanup_free_ char *target = NULL;
|
||||
const char *id, *slink_tmp;
|
||||
struct stat st;
|
||||
int r;
|
||||
|
||||
@@ -91,34 +90,16 @@ static int node_symlink(sd_device *dev, const char *devnode, const char *slink)
|
||||
} else if (errno != ENOENT)
|
||||
return log_device_debug_errno(dev, errno, "Failed to lstat() '%s': %m", slink);
|
||||
|
||||
r = mkdir_parents_label(slink, 0755);
|
||||
if (r < 0)
|
||||
return log_device_debug_errno(dev, r, "Failed to create parent directory of '%s': %m", slink);
|
||||
|
||||
/* use relative link */
|
||||
r = path_make_relative_parent(slink, devnode, &target);
|
||||
r = symlink_atomic_full_label(devnode, slink, /* make_relative = */ true);
|
||||
if (r < 0)
|
||||
return log_device_debug_errno(dev, r, "Failed to get relative path from '%s' to '%s': %m", slink, devnode);
|
||||
|
||||
r = device_get_device_id(dev, &id);
|
||||
if (r < 0)
|
||||
return log_device_debug_errno(dev, r, "Failed to get device id: %m");
|
||||
|
||||
slink_tmp = strjoina(slink, ".tmp-", id);
|
||||
(void) unlink(slink_tmp);
|
||||
|
||||
r = mkdir_parents_label(slink_tmp, 0755);
|
||||
if (r < 0)
|
||||
return log_device_debug_errno(dev, r, "Failed to create parent directory of '%s': %m", slink_tmp);
|
||||
|
||||
mac_selinux_create_file_prepare(slink_tmp, S_IFLNK);
|
||||
r = RET_NERRNO(symlink(target, slink_tmp));
|
||||
mac_selinux_create_file_clear();
|
||||
if (r < 0)
|
||||
return log_device_debug_errno(dev, r, "Failed to create symlink '%s' to '%s': %m", slink_tmp, target);
|
||||
|
||||
if (rename(slink_tmp, slink) < 0) {
|
||||
r = log_device_debug_errno(dev, errno, "Failed to rename '%s' to '%s': %m", slink_tmp, slink);
|
||||
(void) unlink(slink_tmp);
|
||||
return r;
|
||||
}
|
||||
return log_device_debug_errno(dev, r, "Failed to create symlink '%s' to '%s': %m", slink, devnode);
|
||||
|
||||
log_device_debug(dev, "Successfully created symlink '%s' to '%s'", slink, devnode);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user