]> git.proxmox.com Git - mirror_qemu.git/blame - system/qemu-seccomp.c
bswap.h: Fix const_le64() macro
[mirror_qemu.git] / system / qemu-seccomp.c
CommitLineData
2f668be7
EO
1/*
2 * QEMU seccomp mode 2 support with libseccomp
3 *
4 * Copyright IBM, Corp. 2012
5 *
6 * Authors:
7 * Eduardo Otubo <eotubo@br.ibm.com>
8 *
9 * This work is licensed under the terms of the GNU GPL, version 2. See
10 * the COPYING file in the top-level directory.
11 *
12 * Contributions after 2012-01-13 are licensed under the terms of the
13 * GNU GPL, version 2 or (at your option) any later version.
14 */
65484597 15
d38ea87a 16#include "qemu/osdep.h"
65484597 17#include "qapi/error.h"
9d0fdecb
YMZ
18#include "qemu/config-file.h"
19#include "qemu/option.h"
20#include "qemu/module.h"
9d0fdecb 21#include <sys/prctl.h>
2f668be7 22#include <seccomp.h>
9c17d615 23#include "sysemu/seccomp.h"
bda08a57 24#include <linux/seccomp.h>
2f668be7 25
81bed73b
JH
26/* For some architectures (notably ARM) cacheflush is not supported until
27 * libseccomp 2.2.3, but configure enforces that we are using a more recent
28 * version on those hosts, so it is OK for this check to be less strict.
29 */
47d2067a
AJ
30#if SCMP_VER_MAJOR >= 3
31 #define HAVE_CACHEFLUSH
81bed73b 32#elif SCMP_VER_MAJOR == 2 && SCMP_VER_MINOR >= 2
47d2067a
AJ
33 #define HAVE_CACHEFLUSH
34#endif
35
2f668be7
EO
36struct QemuSeccompSyscall {
37 int32_t num;
1bd6152a 38 uint8_t set;
056de1e8
MAL
39 uint8_t narg;
40 const struct scmp_arg_cmp *arg_cmp;
8f46f562 41 uint32_t action;
056de1e8
MAL
42};
43
44const struct scmp_arg_cmp sched_setscheduler_arg[] = {
e81e7b52
TH
45 /* was SCMP_A1(SCMP_CMP_NE, SCHED_IDLE), but expanded due to GCC 4.x bug */
46 { .arg = 1, .op = SCMP_CMP_NE, .datum_a = SCHED_IDLE }
2f668be7
EO
47};
48
5a2f693f
DB
49/*
50 * See 'NOTES' in 'man 2 clone' - s390 & cross have 'flags' in
51 * different position to other architectures
52 */
53#if defined(HOST_S390X) || defined(HOST_S390) || defined(HOST_CRIS)
54#define CLONE_FLAGS_ARG 1
55#else
56#define CLONE_FLAGS_ARG 0
57#endif
58
59#ifndef CLONE_PIDFD
60# define CLONE_PIDFD 0x00001000
61#endif
62
63#define REQUIRE_CLONE_FLAG(flag) \
64 const struct scmp_arg_cmp clone_arg ## flag[] = { \
65 { .arg = CLONE_FLAGS_ARG, \
66 .op = SCMP_CMP_MASKED_EQ, \
67 .datum_a = flag, .datum_b = 0 } }
68
69#define FORBID_CLONE_FLAG(flag) \
70 const struct scmp_arg_cmp clone_arg ## flag[] = { \
71 { .arg = CLONE_FLAGS_ARG, \
72 .op = SCMP_CMP_MASKED_EQ, \
73 .datum_a = flag, .datum_b = flag } }
74
75#define RULE_CLONE_FLAG(flag) \
76 { SCMP_SYS(clone), QEMU_SECCOMP_SET_SPAWN, \
77 ARRAY_SIZE(clone_arg ## flag), clone_arg ## flag, SCMP_ACT_TRAP }
78
79/* If no CLONE_* flags are set, except CSIGNAL, deny */
80const struct scmp_arg_cmp clone_arg_none[] = {
81 { .arg = CLONE_FLAGS_ARG,
82 .op = SCMP_CMP_MASKED_EQ,
83 .datum_a = ~(CSIGNAL), .datum_b = 0 }
84};
85
86/*
87 * pthread_create should always set all of these.
88 */
89REQUIRE_CLONE_FLAG(CLONE_VM);
90REQUIRE_CLONE_FLAG(CLONE_FS);
91REQUIRE_CLONE_FLAG(CLONE_FILES);
92REQUIRE_CLONE_FLAG(CLONE_SIGHAND);
93REQUIRE_CLONE_FLAG(CLONE_THREAD);
94REQUIRE_CLONE_FLAG(CLONE_SYSVSEM);
95REQUIRE_CLONE_FLAG(CLONE_SETTLS);
96REQUIRE_CLONE_FLAG(CLONE_PARENT_SETTID);
97REQUIRE_CLONE_FLAG(CLONE_CHILD_CLEARTID);
98/*
99 * Musl sets this in pthread_create too, but it is
100 * obsolete and harmless since its behaviour is
101 * subsumed under CLONE_THREAD
102 */
103/*REQUIRE_CLONE_FLAG(CLONE_DETACHED);*/
104
105
106/*
107 * These all indicate an attempt to spawn a process
108 * instead of a thread, or other undesirable scenarios
109 */
110FORBID_CLONE_FLAG(CLONE_PIDFD);
111FORBID_CLONE_FLAG(CLONE_PTRACE);
112FORBID_CLONE_FLAG(CLONE_VFORK);
113FORBID_CLONE_FLAG(CLONE_PARENT);
114FORBID_CLONE_FLAG(CLONE_NEWNS);
115FORBID_CLONE_FLAG(CLONE_UNTRACED);
116FORBID_CLONE_FLAG(CLONE_NEWCGROUP);
117FORBID_CLONE_FLAG(CLONE_NEWUTS);
118FORBID_CLONE_FLAG(CLONE_NEWIPC);
119FORBID_CLONE_FLAG(CLONE_NEWUSER);
120FORBID_CLONE_FLAG(CLONE_NEWPID);
121FORBID_CLONE_FLAG(CLONE_NEWNET);
122FORBID_CLONE_FLAG(CLONE_IO);
123
124
a202d75a
PMD
125static const struct QemuSeccompSyscall denylist[] = {
126 /* default set of syscalls that should get blocked */
8f46f562
DB
127 { SCMP_SYS(reboot), QEMU_SECCOMP_SET_DEFAULT,
128 0, NULL, SCMP_ACT_TRAP },
129 { SCMP_SYS(swapon), QEMU_SECCOMP_SET_DEFAULT,
130 0, NULL, SCMP_ACT_TRAP },
131 { SCMP_SYS(swapoff), QEMU_SECCOMP_SET_DEFAULT,
132 0, NULL, SCMP_ACT_TRAP },
133 { SCMP_SYS(syslog), QEMU_SECCOMP_SET_DEFAULT,
134 0, NULL, SCMP_ACT_TRAP },
135 { SCMP_SYS(mount), QEMU_SECCOMP_SET_DEFAULT,
136 0, NULL, SCMP_ACT_TRAP },
137 { SCMP_SYS(umount), QEMU_SECCOMP_SET_DEFAULT,
138 0, NULL, SCMP_ACT_TRAP },
139 { SCMP_SYS(kexec_load), QEMU_SECCOMP_SET_DEFAULT,
140 0, NULL, SCMP_ACT_TRAP },
141 { SCMP_SYS(afs_syscall), QEMU_SECCOMP_SET_DEFAULT,
142 0, NULL, SCMP_ACT_TRAP },
143 { SCMP_SYS(break), QEMU_SECCOMP_SET_DEFAULT,
144 0, NULL, SCMP_ACT_TRAP },
145 { SCMP_SYS(ftime), QEMU_SECCOMP_SET_DEFAULT,
146 0, NULL, SCMP_ACT_TRAP },
147 { SCMP_SYS(getpmsg), QEMU_SECCOMP_SET_DEFAULT,
148 0, NULL, SCMP_ACT_TRAP },
149 { SCMP_SYS(gtty), QEMU_SECCOMP_SET_DEFAULT,
150 0, NULL, SCMP_ACT_TRAP },
151 { SCMP_SYS(lock), QEMU_SECCOMP_SET_DEFAULT,
152 0, NULL, SCMP_ACT_TRAP },
153 { SCMP_SYS(mpx), QEMU_SECCOMP_SET_DEFAULT,
154 0, NULL, SCMP_ACT_TRAP },
155 { SCMP_SYS(prof), QEMU_SECCOMP_SET_DEFAULT,
156 0, NULL, SCMP_ACT_TRAP },
157 { SCMP_SYS(profil), QEMU_SECCOMP_SET_DEFAULT,
158 0, NULL, SCMP_ACT_TRAP },
159 { SCMP_SYS(putpmsg), QEMU_SECCOMP_SET_DEFAULT,
160 0, NULL, SCMP_ACT_TRAP },
161 { SCMP_SYS(security), QEMU_SECCOMP_SET_DEFAULT,
162 0, NULL, SCMP_ACT_TRAP },
163 { SCMP_SYS(stty), QEMU_SECCOMP_SET_DEFAULT,
164 0, NULL, SCMP_ACT_TRAP },
165 { SCMP_SYS(tuxcall), QEMU_SECCOMP_SET_DEFAULT,
166 0, NULL, SCMP_ACT_TRAP },
167 { SCMP_SYS(ulimit), QEMU_SECCOMP_SET_DEFAULT,
168 0, NULL, SCMP_ACT_TRAP },
169 { SCMP_SYS(vserver), QEMU_SECCOMP_SET_DEFAULT,
170 0, NULL, SCMP_ACT_TRAP },
2b716fa6 171 /* obsolete */
8f46f562
DB
172 { SCMP_SYS(readdir), QEMU_SECCOMP_SET_OBSOLETE,
173 0, NULL, SCMP_ACT_TRAP },
174 { SCMP_SYS(_sysctl), QEMU_SECCOMP_SET_OBSOLETE,
175 0, NULL, SCMP_ACT_TRAP },
176 { SCMP_SYS(bdflush), QEMU_SECCOMP_SET_OBSOLETE,
177 0, NULL, SCMP_ACT_TRAP },
178 { SCMP_SYS(create_module), QEMU_SECCOMP_SET_OBSOLETE,
179 0, NULL, SCMP_ACT_TRAP },
180 { SCMP_SYS(get_kernel_syms), QEMU_SECCOMP_SET_OBSOLETE,
181 0, NULL, SCMP_ACT_TRAP },
182 { SCMP_SYS(query_module), QEMU_SECCOMP_SET_OBSOLETE,
183 0, NULL, SCMP_ACT_TRAP },
184 { SCMP_SYS(sgetmask), QEMU_SECCOMP_SET_OBSOLETE,
185 0, NULL, SCMP_ACT_TRAP },
186 { SCMP_SYS(ssetmask), QEMU_SECCOMP_SET_OBSOLETE,
187 0, NULL, SCMP_ACT_TRAP },
188 { SCMP_SYS(sysfs), QEMU_SECCOMP_SET_OBSOLETE,
189 0, NULL, SCMP_ACT_TRAP },
190 { SCMP_SYS(uselib), QEMU_SECCOMP_SET_OBSOLETE,
191 0, NULL, SCMP_ACT_TRAP },
192 { SCMP_SYS(ustat), QEMU_SECCOMP_SET_OBSOLETE,
193 0, NULL, SCMP_ACT_TRAP },
73a1e647 194 /* privileged */
8f46f562
DB
195 { SCMP_SYS(setuid), QEMU_SECCOMP_SET_PRIVILEGED,
196 0, NULL, SCMP_ACT_TRAP },
197 { SCMP_SYS(setgid), QEMU_SECCOMP_SET_PRIVILEGED,
198 0, NULL, SCMP_ACT_TRAP },
199 { SCMP_SYS(setpgid), QEMU_SECCOMP_SET_PRIVILEGED,
200 0, NULL, SCMP_ACT_TRAP },
201 { SCMP_SYS(setsid), QEMU_SECCOMP_SET_PRIVILEGED,
202 0, NULL, SCMP_ACT_TRAP },
203 { SCMP_SYS(setreuid), QEMU_SECCOMP_SET_PRIVILEGED,
204 0, NULL, SCMP_ACT_TRAP },
205 { SCMP_SYS(setregid), QEMU_SECCOMP_SET_PRIVILEGED,
206 0, NULL, SCMP_ACT_TRAP },
207 { SCMP_SYS(setresuid), QEMU_SECCOMP_SET_PRIVILEGED,
208 0, NULL, SCMP_ACT_TRAP },
209 { SCMP_SYS(setresgid), QEMU_SECCOMP_SET_PRIVILEGED,
210 0, NULL, SCMP_ACT_TRAP },
211 { SCMP_SYS(setfsuid), QEMU_SECCOMP_SET_PRIVILEGED,
212 0, NULL, SCMP_ACT_TRAP },
213 { SCMP_SYS(setfsgid), QEMU_SECCOMP_SET_PRIVILEGED,
214 0, NULL, SCMP_ACT_TRAP },
995a226f 215 /* spawn */
8f46f562
DB
216 { SCMP_SYS(fork), QEMU_SECCOMP_SET_SPAWN,
217 0, NULL, SCMP_ACT_TRAP },
218 { SCMP_SYS(vfork), QEMU_SECCOMP_SET_SPAWN,
219 0, NULL, SCMP_ACT_TRAP },
220 { SCMP_SYS(execve), QEMU_SECCOMP_SET_SPAWN,
221 0, NULL, SCMP_ACT_TRAP },
5a2f693f
DB
222 { SCMP_SYS(clone), QEMU_SECCOMP_SET_SPAWN,
223 ARRAY_SIZE(clone_arg_none), clone_arg_none, SCMP_ACT_TRAP },
224 RULE_CLONE_FLAG(CLONE_VM),
225 RULE_CLONE_FLAG(CLONE_FS),
226 RULE_CLONE_FLAG(CLONE_FILES),
227 RULE_CLONE_FLAG(CLONE_SIGHAND),
228 RULE_CLONE_FLAG(CLONE_THREAD),
229 RULE_CLONE_FLAG(CLONE_SYSVSEM),
230 RULE_CLONE_FLAG(CLONE_SETTLS),
231 RULE_CLONE_FLAG(CLONE_PARENT_SETTID),
232 RULE_CLONE_FLAG(CLONE_CHILD_CLEARTID),
233 /*RULE_CLONE_FLAG(CLONE_DETACHED),*/
234 RULE_CLONE_FLAG(CLONE_PIDFD),
235 RULE_CLONE_FLAG(CLONE_PTRACE),
236 RULE_CLONE_FLAG(CLONE_VFORK),
237 RULE_CLONE_FLAG(CLONE_PARENT),
238 RULE_CLONE_FLAG(CLONE_NEWNS),
239 RULE_CLONE_FLAG(CLONE_UNTRACED),
240 RULE_CLONE_FLAG(CLONE_NEWCGROUP),
241 RULE_CLONE_FLAG(CLONE_NEWUTS),
242 RULE_CLONE_FLAG(CLONE_NEWIPC),
243 RULE_CLONE_FLAG(CLONE_NEWUSER),
244 RULE_CLONE_FLAG(CLONE_NEWPID),
245 RULE_CLONE_FLAG(CLONE_NEWNET),
246 RULE_CLONE_FLAG(CLONE_IO),
c542b302
DB
247#ifdef __SNR_clone3
248 { SCMP_SYS(clone3), QEMU_SECCOMP_SET_SPAWN,
249 0, NULL, SCMP_ACT_ERRNO(ENOSYS) },
250#endif
46380571
DB
251#ifdef __SNR_execveat
252 { SCMP_SYS(execveat), QEMU_SECCOMP_SET_SPAWN },
253#endif
254 { SCMP_SYS(setns), QEMU_SECCOMP_SET_SPAWN },
255 { SCMP_SYS(unshare), QEMU_SECCOMP_SET_SPAWN },
24f8cdc5 256 /* resource control */
8f46f562
DB
257 { SCMP_SYS(setpriority), QEMU_SECCOMP_SET_RESOURCECTL,
258 0, NULL, SCMP_ACT_ERRNO(EPERM) },
259 { SCMP_SYS(sched_setparam), QEMU_SECCOMP_SET_RESOURCECTL,
260 0, NULL, SCMP_ACT_ERRNO(EPERM) },
056de1e8 261 { SCMP_SYS(sched_setscheduler), QEMU_SECCOMP_SET_RESOURCECTL,
8f46f562
DB
262 ARRAY_SIZE(sched_setscheduler_arg), sched_setscheduler_arg,
263 SCMP_ACT_ERRNO(EPERM) },
264 { SCMP_SYS(sched_setaffinity), QEMU_SECCOMP_SET_RESOURCECTL,
265 0, NULL, SCMP_ACT_ERRNO(EPERM) },
2f668be7
EO
266};
267
bda08a57
MAL
268static inline __attribute__((unused)) int
269qemu_seccomp(unsigned int operation, unsigned int flags, void *args)
270{
271#ifdef __NR_seccomp
272 return syscall(__NR_seccomp, operation, flags, args);
273#else
274 errno = ENOSYS;
275 return -1;
276#endif
277}
278
8f46f562 279static uint32_t qemu_seccomp_update_action(uint32_t action)
bda08a57
MAL
280{
281#if defined(SECCOMP_GET_ACTION_AVAIL) && defined(SCMP_ACT_KILL_PROCESS) && \
282 defined(SECCOMP_RET_KILL_PROCESS)
8f46f562 283 if (action == SCMP_ACT_TRAP) {
9a1565a0
DB
284 static int kill_process = -1;
285 if (kill_process == -1) {
0d57919a 286 uint32_t testaction = SECCOMP_RET_KILL_PROCESS;
bda08a57 287
0d57919a 288 if (qemu_seccomp(SECCOMP_GET_ACTION_AVAIL, 0, &testaction) == 0) {
9a1565a0 289 kill_process = 1;
e474e3aa
DB
290 } else {
291 kill_process = 0;
9a1565a0 292 }
9a1565a0
DB
293 }
294 if (kill_process == 1) {
bda08a57
MAL
295 return SCMP_ACT_KILL_PROCESS;
296 }
9a1565a0 297 }
8f46f562
DB
298#endif
299 return action;
bda08a57
MAL
300}
301
2b716fa6 302
035121d2 303static int seccomp_start(uint32_t seccomp_opts, Error **errp)
2f668be7 304{
035121d2 305 int rc = -1;
2f668be7
EO
306 unsigned int i = 0;
307 scmp_filter_ctx ctx;
308
1bd6152a 309 ctx = seccomp_init(SCMP_ACT_ALLOW);
2f668be7 310 if (ctx == NULL) {
035121d2 311 error_setg(errp, "failed to initialize seccomp context");
2f668be7
EO
312 goto seccomp_return;
313 }
314
73422d95
MP
315#if defined(CONFIG_SECCOMP_SYSRAWRC)
316 /*
317 * This must be the first seccomp_attr_set() call to have full
318 * error propagation from subsequent seccomp APIs.
319 */
320 rc = seccomp_attr_set(ctx, SCMP_FLTATR_API_SYSRAWRC, 1);
321 if (rc != 0) {
322 error_setg_errno(errp, -rc,
323 "failed to set seccomp rawrc attribute");
324 goto seccomp_return;
325 }
326#endif
327
70dfabea
MAL
328 rc = seccomp_attr_set(ctx, SCMP_FLTATR_CTL_TSYNC, 1);
329 if (rc != 0) {
035121d2
DB
330 error_setg_errno(errp, -rc,
331 "failed to set seccomp thread synchronization");
70dfabea
MAL
332 goto seccomp_return;
333 }
334
a202d75a 335 for (i = 0; i < ARRAY_SIZE(denylist); i++) {
9a1565a0 336 uint32_t action;
a202d75a 337 if (!(seccomp_opts & denylist[i].set)) {
2b716fa6
EO
338 continue;
339 }
340
8f46f562 341 action = qemu_seccomp_update_action(denylist[i].action);
a202d75a
PMD
342 rc = seccomp_rule_add_array(ctx, action, denylist[i].num,
343 denylist[i].narg, denylist[i].arg_cmp);
2f668be7 344 if (rc < 0) {
035121d2 345 error_setg_errno(errp, -rc,
a202d75a 346 "failed to add seccomp denylist rules");
2f668be7
EO
347 goto seccomp_return;
348 }
349 }
350
351 rc = seccomp_load(ctx);
035121d2
DB
352 if (rc < 0) {
353 error_setg_errno(errp, -rc,
354 "failed to load seccomp syscall filter in kernel");
355 }
2f668be7
EO
356
357 seccomp_return:
358 seccomp_release(ctx);
035121d2 359 return rc < 0 ? -1 : 0;
2f668be7 360}
9d0fdecb 361
9d0fdecb
YMZ
362int parse_sandbox(void *opaque, QemuOpts *opts, Error **errp)
363{
364 if (qemu_opt_get_bool(opts, "enable", false)) {
365 uint32_t seccomp_opts = QEMU_SECCOMP_SET_DEFAULT
366 | QEMU_SECCOMP_SET_OBSOLETE;
367 const char *value = NULL;
368
369 value = qemu_opt_get(opts, "obsolete");
370 if (value) {
371 if (g_str_equal(value, "allow")) {
372 seccomp_opts &= ~QEMU_SECCOMP_SET_OBSOLETE;
373 } else if (g_str_equal(value, "deny")) {
374 /* this is the default option, this if is here
375 * to provide a little bit of consistency for
376 * the command line */
377 } else {
65484597 378 error_setg(errp, "invalid argument for obsolete");
9d0fdecb
YMZ
379 return -1;
380 }
381 }
382
383 value = qemu_opt_get(opts, "elevateprivileges");
384 if (value) {
385 if (g_str_equal(value, "deny")) {
386 seccomp_opts |= QEMU_SECCOMP_SET_PRIVILEGED;
387 } else if (g_str_equal(value, "children")) {
388 seccomp_opts |= QEMU_SECCOMP_SET_PRIVILEGED;
389
390 /* calling prctl directly because we're
391 * not sure if host has CAP_SYS_ADMIN set*/
392 if (prctl(PR_SET_NO_NEW_PRIVS, 1)) {
65484597 393 error_setg(errp, "failed to set no_new_privs aborting");
9d0fdecb
YMZ
394 return -1;
395 }
396 } else if (g_str_equal(value, "allow")) {
397 /* default value */
398 } else {
65484597 399 error_setg(errp, "invalid argument for elevateprivileges");
9d0fdecb
YMZ
400 return -1;
401 }
402 }
403
404 value = qemu_opt_get(opts, "spawn");
405 if (value) {
406 if (g_str_equal(value, "deny")) {
407 seccomp_opts |= QEMU_SECCOMP_SET_SPAWN;
408 } else if (g_str_equal(value, "allow")) {
409 /* default value */
410 } else {
65484597 411 error_setg(errp, "invalid argument for spawn");
9d0fdecb
YMZ
412 return -1;
413 }
414 }
415
416 value = qemu_opt_get(opts, "resourcecontrol");
417 if (value) {
418 if (g_str_equal(value, "deny")) {
419 seccomp_opts |= QEMU_SECCOMP_SET_RESOURCECTL;
420 } else if (g_str_equal(value, "allow")) {
421 /* default value */
422 } else {
65484597 423 error_setg(errp, "invalid argument for resourcecontrol");
9d0fdecb
YMZ
424 return -1;
425 }
426 }
427
035121d2 428 if (seccomp_start(seccomp_opts, errp) < 0) {
9d0fdecb
YMZ
429 return -1;
430 }
431 }
432
433 return 0;
434}
435
436static QemuOptsList qemu_sandbox_opts = {
437 .name = "sandbox",
438 .implied_opt_name = "enable",
439 .head = QTAILQ_HEAD_INITIALIZER(qemu_sandbox_opts.head),
440 .desc = {
441 {
442 .name = "enable",
443 .type = QEMU_OPT_BOOL,
444 },
445 {
446 .name = "obsolete",
447 .type = QEMU_OPT_STRING,
448 },
449 {
450 .name = "elevateprivileges",
451 .type = QEMU_OPT_STRING,
452 },
453 {
454 .name = "spawn",
455 .type = QEMU_OPT_STRING,
456 },
457 {
458 .name = "resourcecontrol",
459 .type = QEMU_OPT_STRING,
460 },
461 { /* end of list */ }
462 },
463};
464
465static void seccomp_register(void)
466{
5780760f
MAL
467 bool add = false;
468
469 /* FIXME: use seccomp_api_get() >= 2 check when released */
470
471#if defined(SECCOMP_FILTER_FLAG_TSYNC)
472 int check;
473
474 /* check host TSYNC capability, it returns errno == ENOSYS if unavailable */
475 check = qemu_seccomp(SECCOMP_SET_MODE_FILTER,
476 SECCOMP_FILTER_FLAG_TSYNC, NULL);
477 if (check < 0 && errno == EFAULT) {
478 add = true;
479 }
480#endif
481
482 if (add) {
483 qemu_add_opts(&qemu_sandbox_opts);
484 }
9d0fdecb
YMZ
485}
486opts_init(seccomp_register);