summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLennart Poettering <lennart@poettering.net>2010-10-27 05:47:48 +0200
committerLennart Poettering <lennart@poettering.net>2010-10-27 05:47:48 +0200
commit5c0532d1cc989d2f78d2cd4a18058daa58143705 (patch)
tree9bdd6af7a17d9ddb8931a551992d77a61c65c4ed
parentc4dcdb9f4785937f2b73700e66b8cafa452f60a7 (diff)
mounts: automatically create /dev/stderr and friends early on boot so that they are around when we run shell scripts before udevd
-rw-r--r--src/label.c25
-rw-r--r--src/label.h1
-rw-r--r--src/mount-setup.c35
-rw-r--r--src/util.h3
4 files changed, 64 insertions, 0 deletions
diff --git a/src/label.c b/src/label.c
index 01f36eb6cc..d037c4c932 100644
--- a/src/label.c
+++ b/src/label.c
@@ -173,6 +173,31 @@ int label_fifofile_set(const char *path) {
return r;
}
+int label_symlinkfile_set(const char *path) {
+ int r = 0;
+
+#ifdef HAVE_SELINUX
+ security_context_t filecon = NULL;
+
+ if (!use_selinux() || !label_hnd)
+ return 0;
+
+ if ((r = selabel_lookup_raw(label_hnd, &filecon, path, S_IFLNK)) == 0) {
+ if ((r = setfscreatecon(filecon)) < 0) {
+ log_error("Failed to set SELinux file context on %s: %m", path);
+ r = -errno;
+ }
+
+ freecon(filecon);
+ }
+
+ if (r < 0 && security_getenforce() == 0)
+ r = 0;
+#endif
+
+ return r;
+}
+
int label_socket_set(const char *label) {
#ifdef HAVE_SELINUX
diff --git a/src/label.h b/src/label.h
index 0c59da1f1c..f1bf5d6d5e 100644
--- a/src/label.h
+++ b/src/label.h
@@ -33,6 +33,7 @@ int label_socket_set(const char *label);
void label_socket_clear(void);
int label_fifofile_set(const char *path);
+int label_symlinkfile_set(const char *path);
void label_file_clear(void);
void label_free(const char *label);
diff --git a/src/mount-setup.c b/src/mount-setup.c
index d2f05bc5cf..fe99f58b66 100644
--- a/src/mount-setup.c
+++ b/src/mount-setup.c
@@ -26,6 +26,7 @@
#include <string.h>
#include <libgen.h>
#include <assert.h>
+#include <unistd.h>
#include "mount-setup.h"
#include "log.h"
@@ -171,13 +172,47 @@ finish:
return r;
}
+static int symlink_and_label(const char *old_path, const char *new_path) {
+ int r;
+
+ assert(old_path);
+ assert(new_path);
+
+ if ((r = label_symlinkfile_set(new_path)) < 0)
+ return r;
+
+ if (symlink(old_path, new_path) < 0)
+ r = -errno;
+
+ label_file_clear();
+
+ return r;
+}
+
int mount_setup(void) {
+
+ const char *symlinks =
+ "/proc/kcore\0" "/dev/core\0"
+ "/proc/self/fd\0" "/dev/fd\0"
+ "/proc/self/fd/0\0" "/dev/stdin\0"
+ "/proc/self/fd/1\0" "/dev/stdout\0"
+ "/proc/self/fd/2\0" "/dev/stderr\0"
+ "\0";
+
int r;
unsigned i;
+ const char *j, *k;
for (i = 0; i < ELEMENTSOF(mount_table); i ++)
if ((r = mount_one(mount_table+i)) < 0)
return r;
+ /* Create a few default symlinks, which are normally created
+ * bei udevd, but some scripts might need them before we start
+ * udevd. */
+
+ NULSTR_FOREACH_PAIR(j, k, symlinks)
+ symlink_and_label(j, k);
+
return mount_cgroup_controllers();
}
diff --git a/src/util.h b/src/util.h
index ddf089cfe7..3256fbaafc 100644
--- a/src/util.h
+++ b/src/util.h
@@ -373,6 +373,9 @@ void dual_timestamp_deserialize(FILE *f, const char *line, dual_timestamp *t);
#define NULSTR_FOREACH(i, l) \
for ((i) = (l); (i) && *(i); (i) = strchr((i), 0)+1)
+#define NULSTR_FOREACH_PAIR(i, j, l) \
+ for ((i) = (l), (j) = strchr((i), 0)+1; (i) && *(i); (i) = strchr((j), 0)+1, (j) = *(i) ? strchr((i), 0)+1 : (i))
+
const char *ioprio_class_to_string(int i);
int ioprio_class_from_string(const char *s);