Repository navigation
Expand file tree
/
Copy pathutils.h
More file actions
322 lines (275 loc) · 8.54 KB
/
Copy pathutils.h
File metadata and controls
322 lines (275 loc) · 8.54 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
/* bubblewrap
* Copyright (C) 2016 Alexander Larsson
* SPDX-License-Identifier: LGPL-2.0-or-later
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
*
*/
#pragma once
#include <assert.h>
#include <dirent.h>
#include <errno.h>
#include <fcntl.h>
#include <stdarg.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <syslog.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#ifdef BWRAP_DEBUG
extern bool bwrap_is_debugging;
#define debug(...) bwrap_log (LOG_DEBUG, __VA_ARGS__)
#else
#define debug(...)
#endif
#define UNUSED __attribute__((__unused__))
#define BWRAP_KERNEL_VERSION(a, b, c) (((a) << 16) + ((b) << 8) + (c))
#ifdef HAVE_ASSUMED_KERNEL
# define ASSUMED_KERNEL \
BWRAP_KERNEL_VERSION (ASSUMED_KERNEL_MAJOR, ASSUMED_KERNEL_MINOR, ASSUMED_KERNEL_PATCH)
#else
# define ASSUMED_KERNEL 0
#endif
#define N_ELEMENTS(arr) (sizeof (arr) / sizeof ((arr)[0]))
#ifndef TEMP_FAILURE_RETRY
#define TEMP_FAILURE_RETRY(expression) \
(__extension__ \
({ long int __result; \
do __result = (long int) (expression); \
while (__result == -1L && errno == EINTR); \
__result; }))
#endif
#define PIPE_READ_END 0
#define PIPE_WRITE_END 1
#ifndef PR_SET_CHILD_SUBREAPER
#define PR_SET_CHILD_SUBREAPER 36
#endif
extern bool bwrap_level_prefix;
extern int proc_fd;
void bwrap_log (int severity,
const char *format,
...) __attribute__((format (printf, 2, 3)));
#define warn(...) bwrap_log (LOG_WARNING, __VA_ARGS__)
void die_with_error (const char *format,
...) __attribute__((__noreturn__)) __attribute__((format (printf, 1, 2)));
void die_with_mount_error (const char *format,
...) __attribute__((__noreturn__)) __attribute__((format (printf, 1, 2)));
void die (const char *format,
...) __attribute__((__noreturn__)) __attribute__((format (printf, 1, 2)));
void die_oom (void) __attribute__((__noreturn__));
void die_unless_label_valid (const char *label);
void fork_intermediate_child (void);
void *xmalloc (size_t size);
void *xcalloc (size_t nmemb, size_t size);
void *xrealloc (void *ptr,
size_t size);
char *xstrdup (const char *str);
char *xstrndup(const char *str, size_t n);
void strfreev (char **str_array);
void xclearenv (void);
void xsetenv (const char *name,
const char *value,
int overwrite);
void xunsetenv (const char *name);
char *strconcat (const char *s1,
const char *s2);
char *strconcat3 (const char *s1,
const char *s2,
const char *s3);
char * xasprintf (const char *format,
...) __attribute__((format (printf, 1, 2)));
bool has_prefix (const char *str,
const char *prefix);
bool has_path_prefix (const char *str,
const char *prefix);
bool path_equal (const char *path1,
const char *path2);
int fdwalk (int (*cb)(void *data,
int fd),
void *data);
char *load_file_data (int fd,
size_t *size);
char *load_file_at (int dirfd,
const char *path);
int write_file_at (int dirfd,
const char *path,
const char *content);
int write_to_fd (int fd,
const char *content,
ssize_t len);
int copy_file_data (int sfd,
int dfd);
int copy_file (const char *src_path,
const char *dst_path,
mode_t mode);
int create_file (const char *path,
mode_t mode,
const char *content);
int ensure_file (const char *path,
mode_t mode);
int ensure_dir (const char *path,
mode_t mode);
int get_file_mode (int fd);
int mkdir_with_parents (const char *pathname,
mode_t mode,
bool create_last);
void create_pid_socketpair (int sockets[2]);
void send_pid_on_socket (int socket);
int read_pid_from_socket (int socket);
char *get_oldroot_path (const char *path);
char *readlink_malloc (const char *pathname);
char *fd_to_proc_path (int fd);
/* syscall wrappers */
int raw_clone (unsigned long flags,
void *child_stack);
int pivot_root (const char *new_root,
const char *put_old);
char *label_mount (const char *opt,
const char *mount_label);
int label_exec (const char *exec_label);
int label_create_file (const char *file_label);
extern bool opt_force_openat_fallback;
extern bool opt_force_mount_setattr_fallback;
int safe_openat (int dirfd,
const char *rootfs,
const char *path,
int flags,
int mode);
char *chroot_realpath (const char *chroot,
const char *path,
char resolved_path[]);
static inline bool
is_empty_string (const char *s)
{
return s == NULL || s[0] == '\0';
}
const char *mount_strerror (int errsv);
static inline void
cleanup_freep (void *p)
{
void **pp = (void **) p;
if (*pp)
free (*pp);
}
static inline void
cleanup_strvp (void *p)
{
void **pp = (void **) p;
strfreev (*pp);
}
static inline void
cleanup_fdp (int *fdp)
{
int fd;
assert (fdp);
fd = *fdp;
if (fd != -1)
(void) close (fd);
}
#define cleanup_free __attribute__((cleanup (cleanup_freep)))
#define cleanup_fd __attribute__((cleanup (cleanup_fdp)))
#define cleanup_strv __attribute__((cleanup (cleanup_strvp)))
static inline int
steal_fd (int *fdp)
{
int fd = *fdp;
*fdp = -1;
return fd;
}
static inline void *
steal_pointer (void *pp)
{
void **ptr = (void **) pp;
void *ref;
ref = *ptr;
*ptr = NULL;
return ref;
}
/* type safety */
#define steal_pointer(pp) \
(0 ? (*(pp)) : (steal_pointer) (pp))
typedef struct {
int *fds;
size_t len;
size_t alloc;
} FdSet;
static inline int
fdset_add (FdSet *set, int fd)
{
if (set->len == set->alloc)
{
set->alloc = set->alloc ? set->alloc * 2 : 4;
set->fds = xrealloc (set->fds, set->alloc * sizeof (int));
}
set->fds[set->len++] = fd;
return fd;
}
static inline void
cleanup_fdsetp (FdSet *set)
{
size_t i;
for (i = 0; i < set->len; i++)
if (set->fds[i] >= 0)
close (set->fds[i]);
free (set->fds);
}
#define cleanup_fdset __attribute__((cleanup (cleanup_fdsetp)))
static inline char *
fdset_add_to_proc_path (FdSet *set, int fd)
{
return fd_to_proc_path (fdset_add (set, fd));
}
typedef struct _StringBuilder StringBuilder;
struct _StringBuilder
{
char * str;
size_t size;
size_t offset;
};
void strappend (StringBuilder *dest,
const char *src);
void strappendf (StringBuilder *dest,
const char *fmt,
...);
void strappend_escape_for_mount_options (StringBuilder *dest,
const char *src);
#ifndef MOUNT_ATTR_RDONLY
#include <linux/types.h>
struct mount_attr
{
__u64 attr_set;
__u64 attr_clr;
__u64 propagation;
__u64 userns_fd;
};
#define MOUNT_ATTR_RDONLY 0x00000001
#define MOUNT_ATTR_NOSUID 0x00000002
#define MOUNT_ATTR_NODEV 0x00000004
#define MOUNT_ATTR_NOEXEC 0x00000008
#define MOUNT_ATTR__ATIME 0x00000070
#define MOUNT_ATTR_RELATIME 0x00000000
#define MOUNT_ATTR_NOATIME 0x00000010
#define MOUNT_ATTR_STRICTATIME 0x00000020
#define MOUNT_ATTR_NODIRATIME 0x00000080
#define MOUNT_ATTR_IDMAP 0x00100000
#define MOUNT_ATTR_NOSYMFOLLOW 0x00200000
#endif
#ifndef AT_RECURSIVE
#define AT_RECURSIVE 0x8000
#endif
int mount_setattr_wrapper (int dirfd, const char *path, unsigned int flags,
struct mount_attr *attr, size_t size);