]> git.ipfire.org Git - thirdparty/systemd.git/blame - src/shared/base-filesystem.c
fix gcc warnings about uninitialized variables
[thirdparty/systemd.git] / src / shared / base-filesystem.c
CommitLineData
3577de7a
KS
1/*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3/***
4 This file is part of systemd.
5
6 Copyright 2014 Kay Sievers
7
8 systemd is free software; you can redistribute it and/or modify it
9 under the terms of the GNU Lesser General Public License as published by
10 the Free Software Foundation; either version 2.1 of the License, or
11 (at your option) any later version.
12
13 systemd is distributed in the hope that it will be useful, but
14 WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Lesser General Public License for more details.
17
18 You should have received a copy of the GNU Lesser General Public License
19 along with systemd; If not, see <http://www.gnu.org/licenses/>.
20***/
21
22#include <errno.h>
23#include <sys/stat.h>
24#include <stdlib.h>
3577de7a
KS
25#include <unistd.h>
26
27#include "base-filesystem.h"
28#include "log.h"
29#include "macro.h"
30#include "util.h"
3577de7a
KS
31
32typedef struct BaseFilesystem {
33 const char *dir;
34 mode_t mode;
35 const char *target;
3fd165e5 36 const char *exists;
3577de7a
KS
37} BaseFilesystem;
38
39static const BaseFilesystem table[] = {
30d7c9c4
HH
40 { "bin", 0, "usr/bin\0", NULL },
41 { "lib", 0, "usr/lib\0", NULL },
42 { "root", 0755, NULL, NULL },
43 { "sbin", 0, "usr/sbin\0", NULL },
e1ae9755 44#if defined(__i386__) || defined(__x86_64__)
30d7c9c4
HH
45 { "lib64", 0, "usr/lib/x86_64-linux-gnu\0"
46 "usr/lib64\0", "ld-linux-x86-64.so.2" },
e1ae9755 47#endif
3577de7a
KS
48};
49
50int base_filesystem_create(const char *root) {
51 _cleanup_close_ int fd = -1;
52 unsigned i;
a7f7d1bd 53 int r = 0;
3577de7a
KS
54
55 fd = open(root, O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC|O_NOFOLLOW);
4a62c710
MS
56 if (fd < 0)
57 return log_error_errno(errno, "Failed to open root file system: %m");
3577de7a
KS
58
59 for (i = 0; i < ELEMENTSOF(table); i ++) {
6f4f8056
HH
60 if (faccessat(fd, table[i].dir, F_OK, AT_SYMLINK_NOFOLLOW) >= 0)
61 continue;
62
3577de7a 63 if (table[i].target) {
6dc2852c 64 const char *target = NULL, *s;
e1ae9755
KS
65
66 /* check if one of the targets exists */
67 NULSTR_FOREACH(s, table[i].target) {
68 if (faccessat(fd, s, F_OK, AT_SYMLINK_NOFOLLOW) < 0)
69 continue;
70
3fd165e5
KS
71 /* check if a specific file exists at the target path */
72 if (table[i].exists) {
73 _cleanup_free_ char *p = NULL;
74
75 p = strjoin(s, "/", table[i].exists, NULL);
76 if (!p)
77 return log_oom();
78
79 if (faccessat(fd, p, F_OK, AT_SYMLINK_NOFOLLOW) < 0)
80 continue;
81 }
82
e1ae9755
KS
83 target = s;
84 break;
85 }
86
87 if (!target)
3577de7a
KS
88 continue;
89
e1ae9755 90 r = symlinkat(target, fd, table[i].dir);
4a62c710
MS
91 if (r < 0 && errno != EEXIST)
92 return log_error_errno(errno, "Failed to create symlink at %s/%s: %m", root, table[i].dir);
3577de7a
KS
93 continue;
94 }
95
96 RUN_WITH_UMASK(0000)
97 r = mkdirat(fd, table[i].dir, table[i].mode);
4a62c710
MS
98 if (r < 0 && errno != EEXIST)
99 return log_error_errno(errno, "Failed to create directory at %s/%s: %m", root, table[i].dir);
3577de7a
KS
100 }
101
102 return 0;
103}