]> git.proxmox.com Git - mirror_lxc.git/blame - src/lxc/lxccontainer.c
storage: rename files "bdev" -> "storage"
[mirror_lxc.git] / src / lxc / lxccontainer.c
CommitLineData
72d0e1cb
SG
1/* liblxcapi
2 *
3 * Copyright © 2012 Serge Hallyn <serge.hallyn@ubuntu.com>.
4 * Copyright © 2012 Canonical Ltd.
5 *
d75462e4
SH
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
72d0e1cb
SG
19 */
20
9be53773 21#define _GNU_SOURCE
38683db4 22#include <dirent.h>
9be53773 23#include <errno.h>
93dc5327 24#include <fcntl.h>
38683db4 25#include <grp.h>
f2363e38 26#include <libgen.h>
38683db4
CB
27#include <pthread.h>
28#include <sched.h>
29#include <stdarg.h>
d659597e 30#include <stdint.h>
9fc7f8c0 31#include <stdio.h>
38683db4
CB
32#include <unistd.h>
33#include <arpa/inet.h>
66c1f8c2 34#include <sys/sysmacros.h>
38683db4
CB
35#include <sys/mman.h>
36#include <sys/mount.h>
5f7eba0b 37#include <sys/syscall.h>
38683db4
CB
38#include <sys/types.h>
39#include <sys/wait.h>
f2363e38 40
5e5576a4 41#include "af_unix.h"
38683db4 42#include "attach.h"
38683db4 43#include "cgroup.h"
72d0e1cb 44#include "conf.h"
38683db4
CB
45#include "config.h"
46#include "commands.h"
92e35018 47#include "commands_utils.h"
72d0e1cb 48#include "confile.h"
953fe44f 49#include "confile_legacy.h"
4222a9f4 50#include "confile_utils.h"
b5159817 51#include "console.h"
e29fe1dd 52#include "criu.h"
72d0e1cb 53#include "log.h"
38683db4
CB
54#include "lxc.h"
55#include "lxccontainer.h"
56#include "lxclock.h"
f2363e38
ÇO
57#include "monitor.h"
58#include "namespace.h"
fed29fad 59#include "network.h"
aa460476 60#include "start.h"
38683db4 61#include "state.h"
28d832c4
CB
62#include "storage.h"
63#include "storage/btrfs.h"
64#include "storage/overlay.h"
65#include "sync.h"
38683db4
CB
66#include "utils.h"
67#include "version.h"
4ba0d9af 68
af6824fc
ST
69/* major()/minor() */
70#ifdef MAJOR_IN_MKDEV
71# include <sys/mkdev.h>
72#endif
af6824fc 73
4ba0d9af 74#if HAVE_IFADDRS_H
9c83a661 75#include <ifaddrs.h>
4ba0d9af
SG
76#else
77#include <../include/ifaddrs.h>
78#endif
72d0e1cb 79
684f79a5
SG
80#if IS_BIONIC
81#include <../include/lxcmntent.h>
82#else
83#include <mntent.h>
84#endif
85
a9a0ed90
ÇO
86#define MAX_BUFFER 4096
87
c868b261
ÇO
88#define NOT_SUPPORTED_ERROR "the requested function %s is not currently supported with unprivileged containers"
89
5f7eba0b
SG
90/* Define faccessat() if missing from the C library */
91#ifndef HAVE_FACCESSAT
92static int faccessat(int __fd, const char *__file, int __type, int __flag)
93{
94#ifdef __NR_faccessat
95return syscall(__NR_faccessat, __fd, __file, __type, __flag);
96#else
97errno = ENOSYS;
98return -1;
99#endif
100}
101#endif
102
72d0e1cb
SG
103lxc_log_define(lxc_container, lxc);
104
858377e4
SH
105static bool do_lxcapi_destroy(struct lxc_container *c);
106static const char *lxcapi_get_config_path(struct lxc_container *c);
107#define do_lxcapi_get_config_path(c) lxcapi_get_config_path(c)
108static bool do_lxcapi_set_config_item(struct lxc_container *c, const char *key, const char *v);
109static bool container_destroy(struct lxc_container *c);
110static bool get_snappath_dir(struct lxc_container *c, char *snappath);
111static bool lxcapi_snapshot_destroy_all(struct lxc_container *c);
112static bool do_lxcapi_save_config(struct lxc_container *c, const char *alt_file);
113
a41f104b
SH
114static bool config_file_exists(const char *lxcpath, const char *cname)
115{
116 /* $lxcpath + '/' + $cname + '/config' + \0 */
117 int ret, len = strlen(lxcpath) + strlen(cname) + 9;
118 char *fname = alloca(len);
119
120 ret = snprintf(fname, len, "%s/%s/config", lxcpath, cname);
121 if (ret < 0 || ret >= len)
122 return false;
123
124 return file_exists(fname);
125}
126
3e625e2d
SH
127/*
128 * A few functions to help detect when a container creation failed.
129 * If a container creation was killed partway through, then trying
130 * to actually start that container could harm the host. We detect
131 * this by creating a 'partial' file under the container directory,
132 * and keeping an advisory lock. When container creation completes,
133 * we remove that file. When we load or try to start a container, if
134 * we find that file, without a flock, we remove the container.
135 */
74a3920a 136static int ongoing_create(struct lxc_container *c)
3e625e2d
SH
137{
138 int len = strlen(c->config_path) + strlen(c->name) + 10;
139 char *path = alloca(len);
140 int fd, ret;
93dc5327
SH
141 struct flock lk;
142
3e625e2d
SH
143 ret = snprintf(path, len, "%s/%s/partial", c->config_path, c->name);
144 if (ret < 0 || ret >= len) {
145 ERROR("Error writing partial pathname");
146 return -1;
147 }
148
149 if (!file_exists(path))
150 return 0;
025ed0f3 151 fd = open(path, O_RDWR);
025ed0f3 152 if (fd < 0) {
3e625e2d
SH
153 // give benefit of the doubt
154 SYSERROR("Error opening partial file");
3e625e2d
SH
155 return 0;
156 }
93dc5327
SH
157 lk.l_type = F_WRLCK;
158 lk.l_whence = SEEK_SET;
159 lk.l_start = 0;
160 lk.l_len = 0;
161 lk.l_pid = -1;
162 if (fcntl(fd, F_GETLK, &lk) == 0 && lk.l_pid != -1) {
3e625e2d
SH
163 // create is still ongoing
164 close(fd);
3e625e2d
SH
165 return 1;
166 }
167 // create completed but partial is still there.
168 close(fd);
3e625e2d
SH
169 return 2;
170}
171
74a3920a 172static int create_partial(struct lxc_container *c)
3e625e2d
SH
173{
174 // $lxcpath + '/' + $name + '/partial' + \0
175 int len = strlen(c->config_path) + strlen(c->name) + 10;
176 char *path = alloca(len);
177 int fd, ret;
93dc5327
SH
178 struct flock lk;
179
3e625e2d
SH
180 ret = snprintf(path, len, "%s/%s/partial", c->config_path, c->name);
181 if (ret < 0 || ret >= len) {
182 ERROR("Error writing partial pathname");
183 return -1;
184 }
93dc5327 185 if ((fd=open(path, O_RDWR | O_CREAT | O_EXCL, 0755)) < 0) {
740fe426 186 SYSERROR("Error creating partial file");
3e625e2d
SH
187 return -1;
188 }
93dc5327
SH
189 lk.l_type = F_WRLCK;
190 lk.l_whence = SEEK_SET;
191 lk.l_start = 0;
192 lk.l_len = 0;
193 if (fcntl(fd, F_SETLKW, &lk) < 0) {
3e625e2d
SH
194 SYSERROR("Error locking partial file %s", path);
195 close(fd);
3e625e2d
SH
196 return -1;
197 }
3e625e2d
SH
198
199 return fd;
200}
201
74a3920a 202static void remove_partial(struct lxc_container *c, int fd)
3e625e2d
SH
203{
204 // $lxcpath + '/' + $name + '/partial' + \0
205 int len = strlen(c->config_path) + strlen(c->name) + 10;
206 char *path = alloca(len);
207 int ret;
208
209 close(fd);
210 ret = snprintf(path, len, "%s/%s/partial", c->config_path, c->name);
211 if (ret < 0 || ret >= len) {
212 ERROR("Error writing partial pathname");
213 return;
214 }
3e625e2d
SH
215 if (unlink(path) < 0)
216 SYSERROR("Error unlink partial file %s", path);
3e625e2d
SH
217}
218
72d0e1cb 219/* LOCKING
3bc449ed
SH
220 * 1. container_mem_lock(c) protects the struct lxc_container from multiple threads.
221 * 2. container_disk_lock(c) protects the on-disk container data - in particular the
222 * container configuration file.
223 * The container_disk_lock also takes the container_mem_lock.
224 * 3. thread_mutex protects process data (ex: fd table) from multiple threads.
72d0e1cb
SG
225 * NOTHING mutexes two independent programs with their own struct
226 * lxc_container for the same c->name, between API calls. For instance,
227 * c->config_read(); c->start(); Between those calls, data on disk
228 * could change (which shouldn't bother the caller unless for instance
229 * the rootfs get moved). c->config_read(); update; c->config_write();
230 * Two such updaters could race. The callers should therefore check their
231 * results. Trying to prevent that would necessarily expose us to deadlocks
232 * due to hung callers. So I prefer to keep the locks only within our own
233 * functions, not across functions.
234 *
3bc449ed 235 * If you're going to clone while holding a lxccontainer, increment
72d0e1cb
SG
236 * c->numthreads (under privlock) before forking. When deleting,
237 * decrement numthreads under privlock, then if it hits 0 you can delete.
238 * Do not ever use a lxccontainer whose numthreads you did not bump.
239 */
240
241static void lxc_container_free(struct lxc_container *c)
242{
243 if (!c)
244 return;
245
f10fad2f
ME
246 free(c->configfile);
247 c->configfile = NULL;
248 free(c->error_string);
249 c->error_string = NULL;
d95db067 250 if (c->slock) {
df271a59 251 lxc_putlock(c->slock);
d95db067
DE
252 c->slock = NULL;
253 }
72d0e1cb 254 if (c->privlock) {
df271a59 255 lxc_putlock(c->privlock);
72d0e1cb
SG
256 c->privlock = NULL;
257 }
f10fad2f
ME
258 free(c->name);
259 c->name = NULL;
d95db067
DE
260 if (c->lxc_conf) {
261 lxc_conf_free(c->lxc_conf);
262 c->lxc_conf = NULL;
263 }
f10fad2f
ME
264 free(c->config_path);
265 c->config_path = NULL;
72cf75fa 266
72d0e1cb
SG
267 free(c);
268}
269
43d1aa34
SH
270/*
271 * Consider the following case:
272freer | racing get()er
273==================================================================
274lxc_container_put() | lxc_container_get()
275\ lxclock(c->privlock) | c->numthreads < 1? (no)
276\ c->numthreads = 0 | \ lxclock(c->privlock) -> waits
277\ lxcunlock() | \
278\ lxc_container_free() | \ lxclock() returns
279 | \ c->numthreads < 1 -> return 0
280\ \ (free stuff) |
281\ \ sem_destroy(privlock) |
282
283 * When the get()er checks numthreads the first time, one of the following
284 * is true:
285 * 1. freer has set numthreads = 0. get() returns 0
286 * 2. freer is between lxclock and setting numthreads to 0. get()er will
287 * sem_wait on privlock, get lxclock after freer() drops it, then see
288 * numthreads is 0 and exit without touching lxclock again..
289 * 3. freer has not yet locked privlock. If get()er runs first, then put()er
290 * will see --numthreads = 1 and not call lxc_container_free().
291*/
292
72d0e1cb
SG
293int lxc_container_get(struct lxc_container *c)
294{
295 if (!c)
296 return 0;
297
43d1aa34
SH
298 // if someone else has already started freeing the container, don't
299 // try to take the lock, which may be invalid
300 if (c->numthreads < 1)
301 return 0;
302
5cee8c50 303 if (container_mem_lock(c))
72d0e1cb
SG
304 return 0;
305 if (c->numthreads < 1) {
306 // bail without trying to unlock, bc the privlock is now probably
307 // in freed memory
308 return 0;
309 }
310 c->numthreads++;
5cee8c50 311 container_mem_unlock(c);
72d0e1cb
SG
312 return 1;
313}
314
315int lxc_container_put(struct lxc_container *c)
316{
317 if (!c)
318 return -1;
5cee8c50 319 if (container_mem_lock(c))
72d0e1cb
SG
320 return -1;
321 if (--c->numthreads < 1) {
5cee8c50 322 container_mem_unlock(c);
72d0e1cb
SG
323 lxc_container_free(c);
324 return 1;
325 }
5cee8c50 326 container_mem_unlock(c);
72d0e1cb
SG
327 return 0;
328}
329
858377e4 330static bool do_lxcapi_is_defined(struct lxc_container *c)
72d0e1cb
SG
331{
332 struct stat statbuf;
333 bool ret = false;
334 int statret;
335
336 if (!c)
337 return false;
338
5cee8c50 339 if (container_mem_lock(c))
72d0e1cb
SG
340 return false;
341 if (!c->configfile)
342 goto out;
343 statret = stat(c->configfile, &statbuf);
344 if (statret != 0)
345 goto out;
346 ret = true;
347
348out:
5cee8c50 349 container_mem_unlock(c);
72d0e1cb
SG
350 return ret;
351}
352
858377e4
SH
353#define WRAP_API(rettype, fnname) \
354static rettype fnname(struct lxc_container *c) \
355{ \
356 rettype ret; \
8164f0e2
TA
357 bool reset_config = false; \
358 \
359 if (!current_config && c && c->lxc_conf) { \
360 current_config = c->lxc_conf; \
361 reset_config = true; \
362 } \
363 \
858377e4 364 ret = do_##fnname(c); \
8164f0e2
TA
365 if (reset_config) \
366 current_config = NULL; \
367 \
858377e4
SH
368 return ret; \
369}
370
371#define WRAP_API_1(rettype, fnname, t1) \
372static rettype fnname(struct lxc_container *c, t1 a1) \
373{ \
374 rettype ret; \
8164f0e2
TA
375 bool reset_config = false; \
376 \
377 if (!current_config && c && c->lxc_conf) { \
378 current_config = c->lxc_conf; \
379 reset_config = true; \
380 } \
381 \
858377e4 382 ret = do_##fnname(c, a1); \
8164f0e2
TA
383 if (reset_config) \
384 current_config = NULL; \
385 \
858377e4
SH
386 return ret; \
387}
388
389#define WRAP_API_2(rettype, fnname, t1, t2) \
390static rettype fnname(struct lxc_container *c, t1 a1, t2 a2) \
391{ \
392 rettype ret; \
8164f0e2
TA
393 bool reset_config = false; \
394 \
395 if (!current_config && c && c->lxc_conf) { \
396 current_config = c->lxc_conf; \
397 reset_config = true; \
398 } \
399 \
858377e4 400 ret = do_##fnname(c, a1, a2); \
8164f0e2
TA
401 if (reset_config) \
402 current_config = NULL; \
403 \
858377e4
SH
404 return ret; \
405}
406
407#define WRAP_API_3(rettype, fnname, t1, t2, t3) \
408static rettype fnname(struct lxc_container *c, t1 a1, t2 a2, t3 a3) \
409{ \
410 rettype ret; \
8164f0e2
TA
411 bool reset_config = false; \
412 \
413 if (!current_config && c && c->lxc_conf) { \
414 current_config = c->lxc_conf; \
415 reset_config = true; \
416 } \
417 \
858377e4 418 ret = do_##fnname(c, a1, a2, a3); \
8164f0e2
TA
419 if (reset_config) \
420 current_config = NULL; \
421 \
858377e4
SH
422 return ret; \
423}
424
425WRAP_API(bool, lxcapi_is_defined)
426
427static const char *do_lxcapi_state(struct lxc_container *c)
72d0e1cb 428{
72d0e1cb
SG
429 lxc_state_t s;
430
431 if (!c)
432 return NULL;
13f5be62 433 s = lxc_getstate(c->name, c->config_path);
39dc698c 434 return lxc_state2str(s);
72d0e1cb
SG
435}
436
858377e4
SH
437WRAP_API(const char *, lxcapi_state)
438
39dc698c 439static bool is_stopped(struct lxc_container *c)
794dd120
SH
440{
441 lxc_state_t s;
13f5be62 442 s = lxc_getstate(c->name, c->config_path);
794dd120
SH
443 return (s == STOPPED);
444}
445
858377e4 446static bool do_lxcapi_is_running(struct lxc_container *c)
72d0e1cb
SG
447{
448 const char *s;
449
450 if (!c)
451 return false;
858377e4 452 s = do_lxcapi_state(c);
72d0e1cb
SG
453 if (!s || strcmp(s, "STOPPED") == 0)
454 return false;
455 return true;
456}
457
858377e4
SH
458WRAP_API(bool, lxcapi_is_running)
459
460static bool do_lxcapi_freeze(struct lxc_container *c)
72d0e1cb
SG
461{
462 int ret;
463 if (!c)
464 return false;
465
9123e471 466 ret = lxc_freeze(c->name, c->config_path);
72d0e1cb
SG
467 if (ret)
468 return false;
469 return true;
470}
471
858377e4
SH
472WRAP_API(bool, lxcapi_freeze)
473
474static bool do_lxcapi_unfreeze(struct lxc_container *c)
72d0e1cb
SG
475{
476 int ret;
477 if (!c)
478 return false;
479
9123e471 480 ret = lxc_unfreeze(c->name, c->config_path);
72d0e1cb
SG
481 if (ret)
482 return false;
483 return true;
484}
485
858377e4
SH
486WRAP_API(bool, lxcapi_unfreeze)
487
488static int do_lxcapi_console_getfd(struct lxc_container *c, int *ttynum, int *masterfd)
0115f8fd
DE
489{
490 int ttyfd;
491 if (!c)
492 return -1;
493
b5159817 494 ttyfd = lxc_console_getfd(c, ttynum, masterfd);
0115f8fd
DE
495 return ttyfd;
496}
497
858377e4
SH
498WRAP_API_2(int, lxcapi_console_getfd, int *, int *)
499
b5159817
DE
500static int lxcapi_console(struct lxc_container *c, int ttynum, int stdinfd,
501 int stdoutfd, int stderrfd, int escape)
502{
858377e4
SH
503 int ret;
504
505 if (!c)
506 return -1;
507
508 current_config = c->lxc_conf;
509 ret = lxc_console(c, ttynum, stdinfd, stdoutfd, stderrfd, escape);
510 current_config = NULL;
511 return ret;
b5159817
DE
512}
513
858377e4 514static pid_t do_lxcapi_init_pid(struct lxc_container *c)
72d0e1cb 515{
72d0e1cb
SG
516 if (!c)
517 return -1;
518
5cee8c50 519 return lxc_cmd_get_init_pid(c->name, c->config_path);
72d0e1cb
SG
520}
521
858377e4
SH
522WRAP_API(pid_t, lxcapi_init_pid)
523
12a50cc6 524static bool load_config_locked(struct lxc_container *c, const char *fname)
8eb5694b
SH
525{
526 if (!c->lxc_conf)
527 c->lxc_conf = lxc_conf_init();
6b0d5538
SH
528 if (!c->lxc_conf)
529 return false;
d08779d4
SH
530 if (lxc_config_read(fname, c->lxc_conf, false) != 0)
531 return false;
d08779d4 532 return true;
8eb5694b
SH
533}
534
858377e4 535static bool do_lxcapi_load_config(struct lxc_container *c, const char *alt_file)
72d0e1cb 536{
39dc698c
SH
537 bool ret = false, need_disklock = false;
538 int lret;
12a50cc6 539 const char *fname;
72d0e1cb
SG
540 if (!c)
541 return false;
542
543 fname = c->configfile;
544 if (alt_file)
545 fname = alt_file;
546 if (!fname)
547 return false;
39dc698c
SH
548 /*
549 * If we're reading something other than the container's config,
550 * we only need to lock the in-memory container. If loading the
551 * container's config file, take the disk lock.
552 */
553 if (strcmp(fname, c->configfile) == 0)
554 need_disklock = true;
555
556 if (need_disklock)
557 lret = container_disk_lock(c);
558 else
559 lret = container_mem_lock(c);
560 if (lret)
72d0e1cb 561 return false;
39dc698c 562
8eb5694b 563 ret = load_config_locked(c, fname);
39dc698c
SH
564
565 if (need_disklock)
566 container_disk_unlock(c);
567 else
568 container_mem_unlock(c);
72d0e1cb
SG
569 return ret;
570}
571
858377e4
SH
572WRAP_API_1(bool, lxcapi_load_config, const char *)
573
574static bool do_lxcapi_want_daemonize(struct lxc_container *c, bool state)
72d0e1cb 575{
497a2995 576 if (!c || !c->lxc_conf)
540f932a 577 return false;
f02abefe 578 if (container_mem_lock(c)) {
3bc449ed 579 ERROR("Error getting mem lock");
540f932a 580 return false;
3bc449ed 581 }
a2739df5 582 c->daemonize = state;
3bc449ed 583 container_mem_unlock(c);
540f932a 584 return true;
72d0e1cb
SG
585}
586
858377e4
SH
587WRAP_API_1(bool, lxcapi_want_daemonize, bool)
588
589static bool do_lxcapi_want_close_all_fds(struct lxc_container *c, bool state)
130a1888
ÇO
590{
591 if (!c || !c->lxc_conf)
49badbbe 592 return false;
130a1888
ÇO
593 if (container_mem_lock(c)) {
594 ERROR("Error getting mem lock");
49badbbe 595 return false;
130a1888 596 }
540f932a 597 c->lxc_conf->close_all_fds = state;
130a1888 598 container_mem_unlock(c);
49badbbe 599 return true;
130a1888
ÇO
600}
601
858377e4
SH
602WRAP_API_1(bool, lxcapi_want_close_all_fds, bool)
603
604static bool do_lxcapi_wait(struct lxc_container *c, const char *state, int timeout)
7a44c8b4
SG
605{
606 int ret;
607
608 if (!c)
609 return false;
610
67e571de 611 ret = lxc_wait(c->name, state, timeout, c->config_path);
7a44c8b4
SG
612 return ret == 0;
613}
614
858377e4 615WRAP_API_2(bool, lxcapi_wait, const char *, int)
7a44c8b4 616
2d834aa8
SH
617static bool am_single_threaded(void)
618{
74f96976 619 struct dirent *direntp;
2d834aa8
SH
620 DIR *dir;
621 int count=0;
622
2d834aa8 623 dir = opendir("/proc/self/task");
2d834aa8
SH
624 if (!dir) {
625 INFO("failed to open /proc/self/task");
626 return false;
627 }
628
74f96976 629 while ((direntp = readdir(dir))) {
2d834aa8
SH
630 if (!direntp)
631 break;
632
633 if (!strcmp(direntp->d_name, "."))
634 continue;
635
636 if (!strcmp(direntp->d_name, ".."))
637 continue;
638 if (++count > 1)
639 break;
640 }
2d834aa8 641 closedir(dir);
2d834aa8
SH
642 return count == 1;
643}
644
fd51a89b
SH
645static void push_arg(char ***argp, char *arg, int *nargs)
646{
647 char **argv;
648 char *copy;
649
650 do {
651 copy = strdup(arg);
652 } while (!copy);
653 do {
654 argv = realloc(*argp, (*nargs + 2) * sizeof(char *));
655 } while (!argv);
656 *argp = argv;
657 argv[*nargs] = copy;
658 (*nargs)++;
659 argv[*nargs] = NULL;
660}
661
662static char **split_init_cmd(const char *incmd)
663{
664 size_t len;
665 int nargs = 0;
5590a671 666 char *copy, *p, *saveptr = NULL;
fd51a89b
SH
667 char **argv;
668
669 if (!incmd)
670 return NULL;
671
672 len = strlen(incmd) + 1;
673 copy = alloca(len);
674 strncpy(copy, incmd, len);
675 copy[len-1] = '\0';
676
677 do {
678 argv = malloc(sizeof(char *));
679 } while (!argv);
680 argv[0] = NULL;
681 for (p = strtok_r(copy, " ", &saveptr); p != NULL;
682 p = strtok_r(NULL, " ", &saveptr))
683 push_arg(&argv, p, &nargs);
684
685 if (nargs == 0) {
686 free(argv);
687 return NULL;
688 }
689 return argv;
690}
691
692static void free_init_cmd(char **argv)
693{
694 int i = 0;
695
696 if (!argv)
697 return;
698 while (argv[i])
699 free(argv[i++]);
700 free(argv);
701}
702
5e5576a4
CB
703static int lxc_rcv_status(int state_socket)
704{
705 int ret;
ee8377bd 706 int state = -1;
5e5576a4
CB
707 struct timeval timeout = {0};
708
709 /* Set 5 second timeout to prevent hanging forever in case something
710 * goes wrong. 5 seconds is a long time to get into RUNNING state.
711 */
712 timeout.tv_sec = 5;
713 ret = setsockopt(state_socket, SOL_SOCKET, SO_RCVTIMEO,
714 (const void *)&timeout, sizeof(timeout));
715 if (ret < 0) {
716 SYSERROR("Failed to set 5s timeout on containter state socket");
717 return -1;
718 }
719
ee8377bd 720again:
5e5576a4
CB
721 /* Receive container state. */
722 ret = lxc_abstract_unix_rcv_credential(state_socket, &state,
ee8377bd
CB
723 sizeof(int));
724 if (ret <= 0) {
725 if (errno != EINTR)
726 return -1;
727 TRACE("Caught EINTR; retrying");
728 goto again;
729 }
5e5576a4
CB
730
731 return state;
732}
733
734static bool wait_on_daemonized_start(struct lxc_handler *handler, int pid)
735{
736 int state, status;
737
738 /* Close write end of the socket pair. */
739 close(handler->state_socket_pair[1]);
740 handler->state_socket_pair[1] = -1;
741
742 state = lxc_rcv_status(handler->state_socket_pair[0]);
743
744 /* Close read end of the socket pair. */
745 close(handler->state_socket_pair[0]);
746 handler->state_socket_pair[0] = -1;
747
748 /* The first child is going to fork() again and then exits. So we reap
749 * the first child here.
750 */
751 if (waitpid(pid, &status, 0) < 0)
752 DEBUG("Failed waiting on first child");
753 else if (!WIFEXITED(status))
754 DEBUG("Failed to retrieve exit status of first child");
755 else if (WEXITSTATUS(status) != 0)
756 DEBUG("First child exited with: %d", WEXITSTATUS(status));
757
758 if (state < 0) {
759 SYSERROR("Failed to receive the container state");
760 return false;
761 }
762
763 /* If we receive anything else then running we know that the container
764 * failed to start.
765 */
766 if (state != RUNNING) {
767 ERROR("Received container state \"%s\" instead of \"RUNNING\"",
768 lxc_state2str(state));
769 return false;
770 }
771
772 TRACE("Container is in \"RUNNING\" state");
773 return true;
774}
775
858377e4 776static bool do_lxcapi_start(struct lxc_container *c, int useinit, char * const argv[])
72d0e1cb
SG
777{
778 int ret;
aa460476 779 struct lxc_handler *handler;
72d0e1cb 780 struct lxc_conf *conf;
540f932a 781 bool daemonize = false;
6eaac303 782 FILE *pid_fp = NULL;
72d0e1cb
SG
783 char *default_args[] = {
784 "/sbin/init",
13aad0ae 785 NULL,
72d0e1cb 786 };
fd51a89b 787 char **init_cmd = NULL;
72d0e1cb 788
7cb19d44 789 /* container does exist */
72d0e1cb
SG
790 if (!c)
791 return false;
120146b9 792
7cb19d44
CB
793 /* If anything fails before we set error_num, we want an error in there.
794 */
120146b9
SG
795 c->error_num = 1;
796
7cb19d44 797 /* Container has not been setup. */
72d0e1cb
SG
798 if (!c->lxc_conf)
799 return false;
800
c47eafec
CB
801 ret = ongoing_create(c);
802 if (ret < 0) {
7cb19d44 803 ERROR("Failed checking for incomplete container creation");
3e625e2d 804 return false;
3e625e2d 805 } else if (ret == 1) {
7cb19d44 806 ERROR("Ongoing container creation detected");
3e625e2d 807 return false;
c47eafec 808 } else if (ret == 2) {
7cb19d44 809 ERROR("Failed to create container");
c47eafec
CB
810 do_lxcapi_destroy(c);
811 return false;
3e625e2d
SH
812 }
813
7cb19d44 814 /* Is this app meant to be run through lxcinit, as in lxc-execute? */
72d0e1cb
SG
815 if (useinit && !argv)
816 return false;
817
5cee8c50 818 if (container_mem_lock(c))
72d0e1cb
SG
819 return false;
820 conf = c->lxc_conf;
821 daemonize = c->daemonize;
72d0e1cb 822
aa460476 823 /* initialize handler */
5e5576a4 824 handler = lxc_init_handler(c->name, conf, c->config_path, daemonize);
dbc9832d 825 container_mem_unlock(c);
aa460476
CB
826 if (!handler)
827 return false;
828
72d0e1cb 829 if (useinit) {
aa460476
CB
830 TRACE("calling \"lxc_execute\"");
831 ret = lxc_execute(c->name, argv, 1, handler, c->config_path,
832 daemonize);
833 c->error_num = ret;
7cb19d44
CB
834
835 if (ret != 0)
836 return false;
837
838 return true;
72d0e1cb
SG
839 }
840
7cb19d44
CB
841 /* If no argv was passed in, use lxc.init_cmd if provided in the
842 * configuration
843 */
fd51a89b
SH
844 if (!argv)
845 argv = init_cmd = split_init_cmd(conf->init_cmd);
846
7cb19d44 847 /* ... otherwise use default_args. */
fd51a89b
SH
848 if (!argv)
849 argv = default_args;
72d0e1cb 850
7cb19d44
CB
851 /* I'm not sure what locks we want here.Any? Is liblxc's locking enough
852 * here to protect the on disk container? We don't want to exclude
853 * things like lxc_info while the container is running.
854 */
72d0e1cb 855 if (daemonize) {
a6b6ad7b 856 bool started;
0a4be28d 857 char title[2048];
c47eafec 858 pid_t pid;
71454076 859
c47eafec 860 pid = fork();
f2e07cb6 861 if (pid < 0) {
c47eafec 862 free_init_cmd(init_cmd);
f2e07cb6 863 lxc_free_handler(handler);
72d0e1cb 864 return false;
f2e07cb6 865 }
6eaac303 866
7cb19d44 867 /* first parent */
6eaac303
QH
868 if (pid != 0) {
869 /* Set to NULL because we don't want father unlink
870 * the PID file, child will do the free and unlink.
871 */
872 c->pidfile = NULL;
5e5576a4 873
7cb19d44
CB
874 /* Wait for container to tell us whether it started
875 * successfully.
876 */
a6b6ad7b
CB
877 started = wait_on_daemonized_start(handler, pid);
878
879 free_init_cmd(init_cmd);
880 lxc_free_handler(handler);
881 return started;
6eaac303 882 }
025ed0f3 883
7cb19d44
CB
884 /* first child */
885
0a4be28d 886 /* We don't really care if this doesn't print all the
7cb19d44
CB
887 * characters. All that it means is that the proctitle will be
888 * ugly. Similarly, we also don't care if setproctitle() fails.
889 * */
0a4be28d
TA
890 snprintf(title, sizeof(title), "[lxc monitor] %s %s", c->config_path, c->name);
891 INFO("Attempting to set proc title to %s", title);
892 setproctitle(title);
893
7cb19d44
CB
894 /* We fork() a second time to be reparented to init. Like
895 * POSIX's daemon() function we change to "/" and redirect
896 * std{in,out,err} to /dev/null.
897 */
697fa639
SH
898 pid = fork();
899 if (pid < 0) {
7cb19d44
CB
900 SYSERROR("Failed to fork first child process");
901 exit(EXIT_FAILURE);
697fa639 902 }
a6b6ad7b 903
7cb19d44 904 /* second parent */
a6b6ad7b
CB
905 if (pid != 0) {
906 free_init_cmd(init_cmd);
907 lxc_free_handler(handler);
7cb19d44 908 exit(EXIT_SUCCESS);
a6b6ad7b
CB
909 }
910
7cb19d44
CB
911 /* second child */
912
913 /* change to / directory */
914 ret = chdir("/");
915 if (ret < 0) {
916 SYSERROR("Failed to change to \"/\" directory");
917 exit(EXIT_FAILURE);
c278cef2 918 }
7cb19d44
CB
919
920 ret = lxc_check_inherited(conf, true,
921 (int[]){handler->conf->maincmd_fd,
922 handler->state_socket_pair[0],
923 handler->state_socket_pair[1]},
5e5576a4 924 3);
7cb19d44
CB
925 if (ret < 0)
926 exit(EXIT_FAILURE);
927
928 /* redirect std{in,out,err} to /dev/null */
929 ret = null_stdfds();
930 if (ret < 0) {
931 ERROR("Failed to redirect std{in,out,err} to /dev/null");
932 exit(EXIT_FAILURE);
69aeabac 933 }
7cb19d44
CB
934
935 /* become session leader */
936 ret = setsid();
937 if (ret < 0)
938 TRACE("Process %d is already process group leader", getpid());
2d834aa8
SH
939 } else {
940 if (!am_single_threaded()) {
941 ERROR("Cannot start non-daemonized container when threaded");
a6b6ad7b 942 free_init_cmd(init_cmd);
f2e07cb6 943 lxc_free_handler(handler);
2d834aa8
SH
944 return false;
945 }
72d0e1cb
SG
946 }
947
aa460476 948 /* We need to write PID file after daemonize, so we always
6eaac303
QH
949 * write the right PID.
950 */
951 if (c->pidfile) {
952 pid_fp = fopen(c->pidfile, "w");
953 if (pid_fp == NULL) {
954 SYSERROR("Failed to create pidfile '%s' for '%s'",
955 c->pidfile, c->name);
c47eafec 956 free_init_cmd(init_cmd);
f2e07cb6 957 lxc_free_handler(handler);
13353dc4 958 if (daemonize)
7cb19d44 959 exit(EXIT_FAILURE);
6eaac303
QH
960 return false;
961 }
962
963 if (fprintf(pid_fp, "%d\n", getpid()) < 0) {
964 SYSERROR("Failed to write '%s'", c->pidfile);
965 fclose(pid_fp);
966 pid_fp = NULL;
c47eafec 967 free_init_cmd(init_cmd);
f2e07cb6 968 lxc_free_handler(handler);
13353dc4 969 if (daemonize)
7cb19d44 970 exit(EXIT_FAILURE);
6eaac303
QH
971 return false;
972 }
973
974 fclose(pid_fp);
975 pid_fp = NULL;
976 }
977
72d0e1cb 978 conf->reboot = 0;
d2cf4c37 979
a8dfe4e0
WB
980 /* Unshare the mount namespace if requested */
981 if (conf->monitor_unshare) {
7cb19d44
CB
982 ret = unshare(CLONE_NEWNS);
983 if (ret < 0) {
a8dfe4e0 984 SYSERROR("failed to unshare mount namespace");
f2e07cb6 985 lxc_free_handler(handler);
a6b6ad7b 986 ret = 1;
7cb19d44 987 goto on_error;
a8dfe4e0 988 }
7cb19d44
CB
989
990 ret = mount(NULL, "/", NULL, MS_SLAVE|MS_REC, NULL);
991 if (ret < 0) {
a8dfe4e0 992 SYSERROR("Failed to make / rslave at startup");
f2e07cb6 993 lxc_free_handler(handler);
a6b6ad7b 994 ret = 1;
7cb19d44 995 goto on_error;
a8dfe4e0
WB
996 }
997 }
998
8bee8851 999reboot:
aa460476
CB
1000 if (conf->reboot == 2) {
1001 /* initialize handler */
5e5576a4 1002 handler = lxc_init_handler(c->name, conf, c->config_path, daemonize);
a6b6ad7b
CB
1003 if (!handler) {
1004 ret = 1;
7cb19d44 1005 goto on_error;
a6b6ad7b 1006 }
aa460476
CB
1007 }
1008
7cb19d44
CB
1009 ret = lxc_check_inherited(conf, daemonize,
1010 (int[]){handler->conf->maincmd_fd,
1011 handler->state_socket_pair[0],
1012 handler->state_socket_pair[1]},
1013 3);
1014 if (ret < 0) {
f2e07cb6 1015 lxc_free_handler(handler);
d2cf4c37 1016 ret = 1;
7cb19d44 1017 goto on_error;
d2cf4c37
SH
1018 }
1019
aa460476 1020 ret = lxc_start(c->name, argv, handler, c->config_path, daemonize);
d4ef230c 1021 c->error_num = ret;
72d0e1cb 1022
8bee8851 1023 if (conf->reboot == 1) {
7cb19d44 1024 INFO("Container requested reboot");
8bee8851 1025 conf->reboot = 2;
72d0e1cb
SG
1026 goto reboot;
1027 }
1028
7cb19d44 1029on_error:
487d8008
QH
1030 if (c->pidfile) {
1031 unlink(c->pidfile);
1032 free(c->pidfile);
1033 c->pidfile = NULL;
1034 }
fd51a89b
SH
1035 free_init_cmd(init_cmd);
1036
7cb19d44
CB
1037 if (daemonize && ret != 0)
1038 exit(EXIT_FAILURE);
1039 else if (daemonize)
1040 exit(EXIT_SUCCESS);
1041
1042 if (ret != 0)
1043 return false;
1044
1045 return true;
72d0e1cb
SG
1046}
1047
858377e4
SH
1048static bool lxcapi_start(struct lxc_container *c, int useinit, char * const argv[])
1049{
1050 bool ret;
1051 current_config = c ? c->lxc_conf : NULL;
1052 ret = do_lxcapi_start(c, useinit, argv);
1053 current_config = NULL;
1054 return ret;
1055}
1056
72d0e1cb
SG
1057/*
1058 * note there MUST be an ending NULL
1059 */
1060static bool lxcapi_startl(struct lxc_container *c, int useinit, ...)
1061{
1062 va_list ap;
a0e93eeb 1063 char **inargs = NULL;
72d0e1cb
SG
1064 bool bret = false;
1065
1066 /* container exists */
1067 if (!c)
1068 return false;
1069
858377e4
SH
1070 current_config = c->lxc_conf;
1071
72d0e1cb 1072 va_start(ap, useinit);
a0e93eeb 1073 inargs = lxc_va_arg_list_to_argv(ap, 0, 1);
72d0e1cb
SG
1074 va_end(ap);
1075
a0e93eeb
CS
1076 if (!inargs) {
1077 ERROR("Memory allocation error.");
1078 goto out;
72d0e1cb
SG
1079 }
1080
a0e93eeb 1081 /* pass NULL if no arguments were supplied */
858377e4 1082 bret = do_lxcapi_start(c, useinit, *inargs ? inargs : NULL);
72d0e1cb
SG
1083
1084out:
1085 if (inargs) {
4e03ae57
DE
1086 char **arg;
1087 for (arg = inargs; *arg; arg++)
1088 free(*arg);
72d0e1cb
SG
1089 free(inargs);
1090 }
1091
858377e4 1092 current_config = NULL;
72d0e1cb
SG
1093 return bret;
1094}
1095
858377e4 1096static bool do_lxcapi_stop(struct lxc_container *c)
72d0e1cb
SG
1097{
1098 int ret;
1099
1100 if (!c)
1101 return false;
1102
ef6e34ee 1103 ret = lxc_cmd_stop(c->name, c->config_path);
72d0e1cb 1104
d775f21b 1105 return ret == 0;
72d0e1cb
SG
1106}
1107
858377e4
SH
1108WRAP_API(bool, lxcapi_stop)
1109
d5752559
SH
1110static int do_create_container_dir(const char *path, struct lxc_conf *conf)
1111{
1112 int ret = -1, lasterr;
1113 char *p = alloca(strlen(path)+1);
1114 mode_t mask = umask(0002);
1115 ret = mkdir(path, 0770);
1116 lasterr = errno;
1117 umask(mask);
1118 errno = lasterr;
1119 if (ret) {
1120 if (errno == EEXIST)
1121 ret = 0;
1122 else {
1123 SYSERROR("failed to create container path %s", path);
1124 return -1;
1125 }
1126 }
1127 strcpy(p, path);
1128 if (!lxc_list_empty(&conf->id_map) && chown_mapped_root(p, conf) != 0) {
1129 ERROR("Failed to chown container dir");
1130 ret = -1;
1131 }
1132 return ret;
1133}
1134
72d0e1cb
SG
1135/*
1136 * create the standard expected container dir
1137 */
1138static bool create_container_dir(struct lxc_container *c)
1139{
1140 char *s;
1141 int len, ret;
1142
2a59a681 1143 len = strlen(c->config_path) + strlen(c->name) + 2;
72d0e1cb
SG
1144 s = malloc(len);
1145 if (!s)
1146 return false;
2a59a681 1147 ret = snprintf(s, len, "%s/%s", c->config_path, c->name);
72d0e1cb
SG
1148 if (ret < 0 || ret >= len) {
1149 free(s);
1150 return false;
1151 }
d5752559 1152 ret = do_create_container_dir(s, c->lxc_conf);
72d0e1cb
SG
1153 free(s);
1154 return ret == 0;
1155}
1156
1157/*
1897e3bc
SH
1158 * do_bdev_create: thin wrapper around bdev_create(). Like bdev_create(),
1159 * it returns a mounted bdev on success, NULL on error.
72d0e1cb 1160 */
1897e3bc 1161static struct bdev *do_bdev_create(struct lxc_container *c, const char *type,
f7ac4459 1162 struct bdev_specs *specs)
1897e3bc
SH
1163{
1164 char *dest;
1897e3bc
SH
1165 size_t len;
1166 struct bdev *bdev;
1167 int ret;
1168
cd219ae6 1169 /* rootfs.path or lxcpath/lxcname/rootfs */
f7ac4459 1170 if (c->lxc_conf->rootfs.path && !access(c->lxc_conf->rootfs.path, F_OK)) {
cf465fe4
SH
1171 const char *rpath = c->lxc_conf->rootfs.path;
1172 len = strlen(rpath) + 1;
cd219ae6 1173 dest = alloca(len);
cf465fe4 1174 ret = snprintf(dest, len, "%s", rpath);
cd219ae6 1175 } else {
858377e4 1176 const char *lxcpath = do_lxcapi_get_config_path(c);
cd219ae6
SY
1177 len = strlen(c->name) + strlen(lxcpath) + 9;
1178 dest = alloca(len);
1179 ret = snprintf(dest, len, "%s/%s/rootfs", lxcpath, c->name);
1180 }
1897e3bc
SH
1181 if (ret < 0 || ret >= len)
1182 return NULL;
1183
1184 bdev = bdev_create(dest, type, c->name, specs);
d44e88c2 1185 if (!bdev) {
959aee9c 1186 ERROR("Failed to create backing store type %s", type);
1897e3bc 1187 return NULL;
d44e88c2
SH
1188 }
1189
7a96a068
CB
1190 if (!c->set_config_item(c, "lxc.rootfs.path", bdev->src)) {
1191 ERROR("Failed to set config item \"lxc.rootfs.path\" to \"%s\"",
f7ac4459
CB
1192 bdev->src);
1193 return NULL;
1194 }
cf3ef16d 1195
f7ac4459
CB
1196 /* If we are not root, chown the rootfs dir to root in the
1197 * target uidmap.
1198 */
0e6e3a41 1199 if (geteuid() != 0 || (c->lxc_conf && !lxc_list_empty(&c->lxc_conf->id_map))) {
c4d10a05 1200 if (chown_mapped_root(bdev->dest, c->lxc_conf) < 0) {
959aee9c 1201 ERROR("Error chowning %s to container root", bdev->dest);
97e9cfa0 1202 suggest_default_idmap();
cf3ef16d
SH
1203 bdev_put(bdev);
1204 return NULL;
1205 }
1206 }
1207
1897e3bc
SH
1208 return bdev;
1209}
1210
96b3cb40 1211static char *lxcbasename(char *path)
72d0e1cb 1212{
96b3cb40
SH
1213 char *p = path + strlen(path) - 1;
1214 while (*p != '/' && p > path)
1215 p--;
1216 return p;
1217}
72d0e1cb 1218
69aeabac 1219static bool create_run_template(struct lxc_container *c, char *tpath, bool need_null_stdfds,
96b3cb40
SH
1220 char *const argv[])
1221{
1222 pid_t pid;
72d0e1cb 1223
72d0e1cb 1224 if (!tpath)
96b3cb40 1225 return true;
72d0e1cb
SG
1226
1227 pid = fork();
1228 if (pid < 0) {
959aee9c 1229 SYSERROR("failed to fork task for container creation template");
96b3cb40 1230 return false;
72d0e1cb
SG
1231 }
1232
1233 if (pid == 0) { // child
39460be8 1234 char *patharg, *namearg, *rootfsarg;
1897e3bc 1235 struct bdev *bdev = NULL;
72d0e1cb 1236 int i;
96b3cb40
SH
1237 int ret, len, nargs = 0;
1238 char **newargv;
cf3ef16d 1239 struct lxc_conf *conf = c->lxc_conf;
72d0e1cb 1240
69aeabac
TA
1241 if (need_null_stdfds && null_stdfds() < 0) {
1242 exit(1);
dc23c1c8 1243 }
1897e3bc 1244
39460be8 1245 bdev = bdev_init(c->lxc_conf, c->lxc_conf->rootfs.path, c->lxc_conf->rootfs.mount, NULL);
1897e3bc
SH
1246 if (!bdev) {
1247 ERROR("Error opening rootfs");
1248 exit(1);
1249 }
1250
4de2791f 1251 if (geteuid() == 0) {
cf3ef16d
SH
1252 if (unshare(CLONE_NEWNS) < 0) {
1253 ERROR("error unsharing mounts");
1254 exit(1);
1255 }
4de2791f 1256 if (detect_shared_rootfs()) {
c597baa8 1257 if (mount(NULL, "/", NULL, MS_SLAVE|MS_REC, NULL)) {
4de2791f
SH
1258 SYSERROR("Failed to make / rslave to run template");
1259 ERROR("Continuing...");
1260 }
1261 }
1262 }
2659c7cb 1263 if (strcmp(bdev->type, "dir") && strcmp(bdev->type, "btrfs")) {
4de2791f 1264 if (geteuid() != 0) {
2659c7cb 1265 ERROR("non-root users can only create btrfs and directory-backed containers");
241978fa 1266 exit(EXIT_FAILURE);
4de2791f 1267 }
241978fa
CB
1268
1269 if (!strcmp(bdev->type, "overlay") || !strcmp(bdev->type, "overlayfs")) {
1270 /* If we create an overlay container we need to
1271 * rsync the contents into
1272 * <container-path>/<container-name>/rootfs.
1273 * However, the overlay mount function will
1274 * mount will mount
1275 * <container-path>/<container-name>/delta0
1276 * over
1277 * <container-path>/<container-name>/rootfs
1278 * which means we would rsync the rootfs into
1279 * the delta directory. That doesn't make sense
1280 * since the delta directory only exists to
1281 * record the differences to
1282 * <container-path>/<container-name>/rootfs. So
1283 * let's simply bind-mount here and then rsync
1284 * directly into
1285 * <container-path>/<container-name>/rootfs.
1286 */
1287 char *src;
1288
1289 src = ovl_get_rootfs(bdev->src, &(size_t){0});
1290 if (!src) {
1291 ERROR("Failed to get rootfs");
1292 exit(EXIT_FAILURE);
1293 }
1294
1295 ret = mount(src, bdev->dest, "bind", MS_BIND | MS_REC, NULL);
1296 if (ret < 0) {
1297 ERROR("Failed to mount rootfs");
1298 return -1;
1299 }
1300 } else {
1301 if (bdev->ops->mount(bdev) < 0) {
1302 ERROR("Failed to mount rootfs");
1303 exit(EXIT_FAILURE);
1304 }
cf3ef16d
SH
1305 }
1306 } else { // TODO come up with a better way here!
e9705550 1307 char *src;
f10fad2f 1308 free(bdev->dest);
e9705550
CB
1309 src = lxc_storage_get_path(bdev->src, bdev->type);
1310 bdev->dest = strdup(src);
1897e3bc
SH
1311 }
1312
72d0e1cb
SG
1313 /*
1314 * create our new array, pre-pend the template name and
1315 * base args
1316 */
1317 if (argv)
1897e3bc 1318 for (nargs = 0; argv[nargs]; nargs++) ;
6849cb5b 1319 nargs += 4; // template, path, rootfs and name args
cf3ef16d 1320
72d0e1cb
SG
1321 newargv = malloc(nargs * sizeof(*newargv));
1322 if (!newargv)
1323 exit(1);
96b3cb40 1324 newargv[0] = lxcbasename(tpath);
72d0e1cb 1325
2a59a681 1326 len = strlen(c->config_path) + strlen(c->name) + strlen("--path=") + 2;
72d0e1cb
SG
1327 patharg = malloc(len);
1328 if (!patharg)
1329 exit(1);
2a59a681 1330 ret = snprintf(patharg, len, "--path=%s/%s", c->config_path, c->name);
72d0e1cb
SG
1331 if (ret < 0 || ret >= len)
1332 exit(1);
1333 newargv[1] = patharg;
1334 len = strlen("--name=") + strlen(c->name) + 1;
1335 namearg = malloc(len);
1336 if (!namearg)
1337 exit(1);
1338 ret = snprintf(namearg, len, "--name=%s", c->name);
1339 if (ret < 0 || ret >= len)
1340 exit(1);
1341 newargv[2] = namearg;
1342
1897e3bc
SH
1343 len = strlen("--rootfs=") + 1 + strlen(bdev->dest);
1344 rootfsarg = malloc(len);
1345 if (!rootfsarg)
1346 exit(1);
1347 ret = snprintf(rootfsarg, len, "--rootfs=%s", bdev->dest);
1348 if (ret < 0 || ret >= len)
1349 exit(1);
1350 newargv[3] = rootfsarg;
1351
72d0e1cb
SG
1352 /* add passed-in args */
1353 if (argv)
1897e3bc
SH
1354 for (i = 4; i < nargs; i++)
1355 newargv[i] = argv[i-4];
72d0e1cb
SG
1356
1357 /* add trailing NULL */
1358 nargs++;
1359 newargv = realloc(newargv, nargs * sizeof(*newargv));
1360 if (!newargv)
1361 exit(1);
1362 newargv[nargs - 1] = NULL;
1363
cf3ef16d
SH
1364 /*
1365 * If we're running the template in a mapped userns, then
1366 * we prepend the template command with:
1367 * lxc-usernsexec <-m map1> ... <-m mapn> --
57d116ab
SH
1368 * and we append "--mapped-uid x", where x is the mapped uid
1369 * for our geteuid()
cf3ef16d 1370 */
0e6e3a41 1371 if (!lxc_list_empty(&conf->id_map)) {
cf3ef16d 1372 int n2args = 1;
57d116ab 1373 char txtuid[20];
2133f58c 1374 char txtgid[20];
cf3ef16d
SH
1375 char **n2 = malloc(n2args * sizeof(*n2));
1376 struct lxc_list *it;
1377 struct id_map *map;
1378
57d116ab
SH
1379 if (!n2) {
1380 SYSERROR("out of memory");
1381 exit(1);
1382 }
cf3ef16d
SH
1383 newargv[0] = tpath;
1384 tpath = "lxc-usernsexec";
1385 n2[0] = "lxc-usernsexec";
1386 lxc_list_for_each(it, &conf->id_map) {
1387 map = it->elem;
1388 n2args += 2;
57d116ab 1389 n2 = realloc(n2, n2args * sizeof(char *));
cf3ef16d
SH
1390 if (!n2)
1391 exit(1);
1392 n2[n2args-2] = "-m";
1393 n2[n2args-1] = malloc(200);
1394 if (!n2[n2args-1])
1395 exit(1);
1396 ret = snprintf(n2[n2args-1], 200, "%c:%lu:%lu:%lu",
1397 map->idtype == ID_TYPE_UID ? 'u' : 'g',
1398 map->nsid, map->hostid, map->range);
1399 if (ret < 0 || ret >= 200)
1400 exit(1);
1401 }
2133f58c 1402 int hostid_mapped = mapped_hostid(geteuid(), conf, ID_TYPE_UID);
6849cb5b 1403 int extraargs = hostid_mapped >= 0 ? 1 : 3;
57d116ab 1404 n2 = realloc(n2, (nargs + n2args + extraargs) * sizeof(char *));
cf3ef16d
SH
1405 if (!n2)
1406 exit(1);
57d116ab 1407 if (hostid_mapped < 0) {
339efad9 1408 hostid_mapped = find_unmapped_nsid(conf, ID_TYPE_UID);
cf3ef16d 1409 n2[n2args++] = "-m";
57d116ab 1410 if (hostid_mapped < 0) {
cf3ef16d
SH
1411 ERROR("Could not find free uid to map");
1412 exit(1);
1413 }
1414 n2[n2args++] = malloc(200);
1415 if (!n2[n2args-1]) {
1416 SYSERROR("out of memory");
1417 exit(1);
1418 }
1419 ret = snprintf(n2[n2args-1], 200, "u:%d:%d:1",
57d116ab 1420 hostid_mapped, geteuid());
cf3ef16d
SH
1421 if (ret < 0 || ret >= 200) {
1422 ERROR("string too long");
1423 exit(1);
1424 }
1425 }
2133f58c
SH
1426 int hostgid_mapped = mapped_hostid(getegid(), conf, ID_TYPE_GID);
1427 extraargs = hostgid_mapped >= 0 ? 1 : 3;
1428 n2 = realloc(n2, (nargs + n2args + extraargs) * sizeof(char *));
1429 if (!n2)
1430 exit(1);
1431 if (hostgid_mapped < 0) {
339efad9 1432 hostgid_mapped = find_unmapped_nsid(conf, ID_TYPE_GID);
2133f58c
SH
1433 n2[n2args++] = "-m";
1434 if (hostgid_mapped < 0) {
1435 ERROR("Could not find free uid to map");
1436 exit(1);
1437 }
1438 n2[n2args++] = malloc(200);
1439 if (!n2[n2args-1]) {
1440 SYSERROR("out of memory");
1441 exit(1);
1442 }
1443 ret = snprintf(n2[n2args-1], 200, "g:%d:%d:1",
1444 hostgid_mapped, getegid());
1445 if (ret < 0 || ret >= 200) {
1446 ERROR("string too long");
1447 exit(1);
1448 }
1449 }
cf3ef16d
SH
1450 n2[n2args++] = "--";
1451 for (i = 0; i < nargs; i++)
1452 n2[i + n2args] = newargv[i];
57d116ab
SH
1453 n2args += nargs;
1454 // Finally add "--mapped-uid $uid" to tell template what to chown
1455 // cached images to
2133f58c 1456 n2args += 4;
57d116ab
SH
1457 n2 = realloc(n2, n2args * sizeof(char *));
1458 if (!n2) {
1459 SYSERROR("out of memory");
1460 exit(1);
1461 }
1462 // note n2[n2args-1] is NULL
2133f58c 1463 n2[n2args-5] = "--mapped-uid";
57d116ab 1464 snprintf(txtuid, 20, "%d", hostid_mapped);
2133f58c
SH
1465 n2[n2args-4] = txtuid;
1466 n2[n2args-3] = "--mapped-gid";
1467 snprintf(txtgid, 20, "%d", hostgid_mapped);
1468 n2[n2args-2] = txtgid;
57d116ab 1469 n2[n2args-1] = NULL;
cf3ef16d
SH
1470 free(newargv);
1471 newargv = n2;
1472 }
72d0e1cb 1473 /* execute */
cf3ef16d 1474 execvp(tpath, newargv);
e9705550 1475 SYSERROR("Failed to execute template %s", tpath);
72d0e1cb
SG
1476 exit(1);
1477 }
1478
9be53773 1479 if (wait_for_pid(pid) != 0) {
959aee9c 1480 ERROR("container creation template for %s failed", c->name);
96b3cb40
SH
1481 return false;
1482 }
1483
1484 return true;
1485}
1486
74a3920a 1487static bool prepend_lxc_header(char *path, const char *t, char *const argv[])
3ce74686 1488{
1fd9bd50 1489 long flen;
b4569e93 1490 char *contents;
3ce74686 1491 FILE *f;
025ed0f3 1492 int ret = -1;
52026772 1493#if HAVE_LIBGNUTLS
025ed0f3 1494 int i;
3ce74686 1495 unsigned char md_value[SHA_DIGEST_LENGTH];
b4569e93 1496 char *tpath;
52026772 1497#endif
3ce74686 1498
025ed0f3 1499 f = fopen(path, "r");
025ed0f3 1500 if (f == NULL)
3ce74686 1501 return false;
025ed0f3
SH
1502
1503 if (fseek(f, 0, SEEK_END) < 0)
1504 goto out_error;
1505 if ((flen = ftell(f)) < 0)
1506 goto out_error;
1507 if (fseek(f, 0, SEEK_SET) < 0)
1508 goto out_error;
1509 if ((contents = malloc(flen + 1)) == NULL)
1510 goto out_error;
1511 if (fread(contents, 1, flen, f) != flen)
1512 goto out_free_contents;
1513
3ce74686 1514 contents[flen] = '\0';
025ed0f3 1515 ret = fclose(f);
025ed0f3
SH
1516 f = NULL;
1517 if (ret < 0)
1518 goto out_free_contents;
3ce74686 1519
b4569e93 1520#if HAVE_LIBGNUTLS
01efd4d3 1521 tpath = get_template_path(t);
85db5535 1522 if (!tpath) {
959aee9c 1523 ERROR("bad template: %s", t);
025ed0f3 1524 goto out_free_contents;
3ce74686
SH
1525 }
1526
85db5535
DE
1527 ret = sha1sum_file(tpath, md_value);
1528 if (ret < 0) {
1529 ERROR("Error getting sha1sum of %s", tpath);
3ce74686 1530 free(tpath);
85db5535 1531 goto out_free_contents;
3ce74686 1532 }
85db5535 1533 free(tpath);
3ce74686
SH
1534#endif
1535
025ed0f3 1536 f = fopen(path, "w");
025ed0f3 1537 if (f == NULL) {
3ce74686
SH
1538 SYSERROR("reopening config for writing");
1539 free(contents);
1540 return false;
1541 }
1542 fprintf(f, "# Template used to create this container: %s\n", t);
1543 if (argv) {
1544 fprintf(f, "# Parameters passed to the template:");
1545 while (*argv) {
1546 fprintf(f, " %s", *argv);
1547 argv++;
1548 }
1549 fprintf(f, "\n");
1550 }
1551#if HAVE_LIBGNUTLS
56698177
SH
1552 fprintf(f, "# Template script checksum (SHA-1): ");
1553 for (i=0; i<SHA_DIGEST_LENGTH; i++)
1554 fprintf(f, "%02x", md_value[i]);
1555 fprintf(f, "\n");
3ce74686 1556#endif
0520c252 1557 fprintf(f, "# For additional config options, please look at lxc.container.conf(5)\n");
49a2ed80
SH
1558 fprintf(f, "\n# Uncomment the following line to support nesting containers:\n");
1559 fprintf(f, "#lxc.include = " LXCTEMPLATECONFIG "/nesting.conf\n");
1560 fprintf(f, "# (Be aware this has security implications)\n\n");
3ce74686
SH
1561 if (fwrite(contents, 1, flen, f) != flen) {
1562 SYSERROR("Writing original contents");
1563 free(contents);
1564 fclose(f);
1565 return false;
1566 }
025ed0f3
SH
1567 ret = 0;
1568out_free_contents:
3ce74686 1569 free(contents);
025ed0f3
SH
1570out_error:
1571 if (f) {
1572 int newret;
025ed0f3 1573 newret = fclose(f);
025ed0f3
SH
1574 if (ret == 0)
1575 ret = newret;
1576 }
1577 if (ret < 0) {
1578 SYSERROR("Error prepending header");
3ce74686
SH
1579 return false;
1580 }
1581 return true;
1582}
1583
4df7f012
SH
1584static void lxcapi_clear_config(struct lxc_container *c)
1585{
f979ac15
SH
1586 if (c) {
1587 if (c->lxc_conf) {
1588 lxc_conf_free(c->lxc_conf);
1589 c->lxc_conf = NULL;
1590 }
4df7f012
SH
1591 }
1592}
1593
858377e4
SH
1594#define do_lxcapi_clear_config(c) lxcapi_clear_config(c)
1595
96b3cb40
SH
1596/*
1597 * lxcapi_create:
1598 * create a container with the given parameters.
1599 * @c: container to be created. It has the lxcpath, name, and a starting
1600 * configuration already set
1601 * @t: the template to execute to instantiate the root filesystem and
1602 * adjust the configuration.
1603 * @bdevtype: backing store type to use. If NULL, dir will be used.
1604 * @specs: additional parameters for the backing store, i.e. LVM vg to
1605 * use.
1606 *
1607 * @argv: the arguments to pass to the template, terminated by NULL. If no
1608 * arguments, you can just pass NULL.
1609 */
858377e4 1610static bool do_lxcapi_create(struct lxc_container *c, const char *t,
dc23c1c8 1611 const char *bdevtype, struct bdev_specs *specs, int flags,
96b3cb40
SH
1612 char *const argv[])
1613{
a69aad27 1614 bool ret = false;
96b3cb40 1615 pid_t pid;
85db5535 1616 char *tpath = NULL;
cbee8106 1617 int partial_fd;
96b3cb40
SH
1618
1619 if (!c)
1620 return false;
1621
85db5535
DE
1622 if (t) {
1623 tpath = get_template_path(t);
1624 if (!tpath) {
959aee9c 1625 ERROR("bad template: %s", t);
85db5535
DE
1626 goto out;
1627 }
96b3cb40
SH
1628 }
1629
cf465fe4
SH
1630 /*
1631 * If a template is passed in, and the rootfs already is defined in
1632 * the container config and exists, then * caller is trying to create
1633 * an existing container. Return an error, but do NOT delete the
1634 * container.
1635 */
858377e4 1636 if (do_lxcapi_is_defined(c) && c->lxc_conf && c->lxc_conf->rootfs.path &&
cf465fe4
SH
1637 access(c->lxc_conf->rootfs.path, F_OK) == 0 && tpath) {
1638 ERROR("Container %s:%s already exists", c->config_path, c->name);
6c6892b5 1639 goto free_tpath;
cf465fe4
SH
1640 }
1641
6c6892b5 1642 if (!c->lxc_conf) {
858377e4 1643 if (!do_lxcapi_load_config(c, lxc_global_config_value("lxc.default_config"))) {
959aee9c 1644 ERROR("Error loading default configuration file %s", lxc_global_config_value("lxc.default_config"));
6c6892b5
DE
1645 goto free_tpath;
1646 }
96b3cb40
SH
1647 }
1648
6c6892b5
DE
1649 if (!create_container_dir(c))
1650 goto free_tpath;
1651
0590e82c 1652 /*
0590e82c
SH
1653 * if both template and rootfs.path are set, template is setup as rootfs.path.
1654 * container is already created if we have a config and rootfs.path is accessible
1655 */
00370edd
DW
1656 if (!c->lxc_conf->rootfs.path && !tpath) {
1657 /* no template passed in and rootfs does not exist */
1658 if (!c->save_config(c, NULL)) {
1659 ERROR("failed to save starting configuration for %s\n", c->name);
1660 goto out;
1661 }
1662 ret = true;
0590e82c 1663 goto out;
00370edd 1664 }
0590e82c
SH
1665 if (c->lxc_conf->rootfs.path && access(c->lxc_conf->rootfs.path, F_OK) != 0)
1666 /* rootfs passed into configuration, but does not exist: error */
1667 goto out;
858377e4 1668 if (do_lxcapi_is_defined(c) && c->lxc_conf->rootfs.path && !tpath) {
0590e82c
SH
1669 /* Rootfs already existed, user just wanted to save the
1670 * loaded configuration */
0f4cdd77
DW
1671 if (!c->save_config(c, NULL))
1672 ERROR("failed to save starting configuration for %s\n", c->name);
0590e82c
SH
1673 ret = true;
1674 goto out;
a69aad27 1675 }
96b3cb40
SH
1676
1677 /* Mark that this container is being created */
1678 if ((partial_fd = create_partial(c)) < 0)
1679 goto out;
1680
1681 /* no need to get disk lock bc we have the partial locked */
1682
1683 /*
1684 * Create the backing store
1685 * Note we can't do this in the same task as we use to execute the
1686 * template because of the way zfs works.
1687 * After you 'zfs create', zfs mounts the fs only in the initial
1688 * namespace.
1689 */
1690 pid = fork();
1691 if (pid < 0) {
959aee9c 1692 SYSERROR("failed to fork task for container creation template");
8eb5694b
SH
1693 goto out_unlock;
1694 }
1695
96b3cb40
SH
1696 if (pid == 0) { // child
1697 struct bdev *bdev = NULL;
1698
1699 if (!(bdev = do_bdev_create(c, bdevtype, specs))) {
1700 ERROR("Error creating backing store type %s for %s",
1701 bdevtype ? bdevtype : "(none)", c->name);
1702 exit(1);
1703 }
1704
1705 /* save config file again to store the new rootfs location */
858377e4 1706 if (!do_lxcapi_save_config(c, NULL)) {
959aee9c 1707 ERROR("failed to save starting configuration for %s", c->name);
96b3cb40
SH
1708 // parent task won't see bdev in config so we delete it
1709 bdev->ops->umount(bdev);
1710 bdev->ops->destroy(bdev);
1711 exit(1);
1712 }
1713 exit(0);
1714 }
1715 if (wait_for_pid(pid) != 0)
a09295f8 1716 goto out_unlock;
96b3cb40
SH
1717
1718 /* reload config to get the rootfs */
a3b47c09 1719 lxc_conf_free(c->lxc_conf);
96b3cb40
SH
1720 c->lxc_conf = NULL;
1721 if (!load_config_locked(c, c->configfile))
a09295f8 1722 goto out_unlock;
96b3cb40 1723
dc23c1c8 1724 if (!create_run_template(c, tpath, !!(flags & LXC_CREATE_QUIET), argv))
96b3cb40
SH
1725 goto out_unlock;
1726
8eb5694b
SH
1727 // now clear out the lxc_conf we have, reload from the created
1728 // container
858377e4 1729 do_lxcapi_clear_config(c);
3ce74686 1730
9d65a487
KY
1731 if (t) {
1732 if (!prepend_lxc_header(c->configfile, tpath, argv)) {
1733 ERROR("Error prepending header to configuration file");
1734 goto out_unlock;
1735 }
3ce74686 1736 }
a69aad27 1737 ret = load_config_locked(c, c->configfile);
72d0e1cb
SG
1738
1739out_unlock:
3e625e2d
SH
1740 if (partial_fd >= 0)
1741 remove_partial(c, partial_fd);
72d0e1cb 1742out:
c55d4505 1743 if (!ret)
18aa217b 1744 container_destroy(c);
6c6892b5 1745free_tpath:
f10fad2f 1746 free(tpath);
a69aad27 1747 return ret;
72d0e1cb
SG
1748}
1749
858377e4
SH
1750static bool lxcapi_create(struct lxc_container *c, const char *t,
1751 const char *bdevtype, struct bdev_specs *specs, int flags,
1752 char *const argv[])
1753{
1754 bool ret;
1755 current_config = c ? c->lxc_conf : NULL;
1756 ret = do_lxcapi_create(c, t, bdevtype, specs, flags, argv);
1757 current_config = NULL;
1758 return ret;
1759}
1760
1761static bool do_lxcapi_reboot(struct lxc_container *c)
3e625e2d
SH
1762{
1763 pid_t pid;
dd267776 1764 int rebootsignal = SIGINT;
3e625e2d
SH
1765
1766 if (!c)
1767 return false;
858377e4 1768 if (!do_lxcapi_is_running(c))
3e625e2d 1769 return false;
858377e4 1770 pid = do_lxcapi_init_pid(c);
3e625e2d
SH
1771 if (pid <= 0)
1772 return false;
dd267776
BP
1773 if (c->lxc_conf && c->lxc_conf->rebootsignal)
1774 rebootsignal = c->lxc_conf->rebootsignal;
591614a7
CB
1775 if (kill(pid, rebootsignal) < 0) {
1776 WARN("Could not send signal %d to pid %d.", rebootsignal, pid);
3e625e2d 1777 return false;
591614a7 1778 }
3e625e2d
SH
1779 return true;
1780
1781}
1782
858377e4
SH
1783WRAP_API(bool, lxcapi_reboot)
1784
1785static bool do_lxcapi_shutdown(struct lxc_container *c, int timeout)
72d0e1cb 1786{
92e35018
CB
1787 int ret, state_client_fd = -1;
1788 bool retv = false;
72d0e1cb 1789 pid_t pid;
f0f1d8c0 1790 int haltsignal = SIGPWR;
92e35018 1791 lxc_state_t states[MAX_STATE] = {0};
72d0e1cb
SG
1792
1793 if (!c)
1794 return false;
1795
858377e4 1796 if (!do_lxcapi_is_running(c))
72d0e1cb 1797 return true;
858377e4 1798 pid = do_lxcapi_init_pid(c);
72d0e1cb
SG
1799 if (pid <= 0)
1800 return true;
330ae3d3
CB
1801
1802 /* Detect whether we should send SIGRTMIN + 3 (e.g. systemd). */
1803 if (task_blocking_signal(pid, (SIGRTMIN + 3)))
1804 haltsignal = (SIGRTMIN + 3);
1805
b0227444 1806 if (c->lxc_conf && c->lxc_conf->haltsignal)
f0f1d8c0 1807 haltsignal = c->lxc_conf->haltsignal;
330ae3d3
CB
1808
1809 INFO("Using signal number '%d' as halt signal.", haltsignal);
1810
92e35018
CB
1811 /* Add a new state client before sending the shutdown signal so that we
1812 * don't miss a state.
1813 */
1814 states[STOPPED] = 1;
1815 ret = lxc_cmd_add_state_client(c->name, c->config_path, states,
1816 &state_client_fd);
1817
1818 /* Send shutdown signal to container. */
591614a7
CB
1819 if (kill(pid, haltsignal) < 0)
1820 WARN("Could not send signal %d to pid %d.", haltsignal, pid);
1821
92e35018
CB
1822 /* Retrieve the state. */
1823 if (state_client_fd >= 0) {
1824 int state;
1825 state = lxc_cmd_sock_rcv_state(state_client_fd, timeout);
1826 close(state_client_fd);
1827 if (state != STOPPED)
1828 return false;
1829 retv = true;
1830 } else if (ret == STOPPED) {
1831 TRACE("Container is already stopped");
1832 retv = true;
1833 } else {
1834 TRACE("Received state \"%s\" instead of expected \"STOPPED\"",
1835 lxc_state2str(ret));
1836 }
1837
72d0e1cb
SG
1838 return retv;
1839}
1840
858377e4
SH
1841WRAP_API_1(bool, lxcapi_shutdown, int)
1842
1897e3bc 1843static bool lxcapi_createl(struct lxc_container *c, const char *t,
dc23c1c8 1844 const char *bdevtype, struct bdev_specs *specs, int flags, ...)
72d0e1cb
SG
1845{
1846 bool bret = false;
a0e93eeb 1847 char **args = NULL;
72d0e1cb 1848 va_list ap;
72d0e1cb
SG
1849
1850 if (!c)
1851 return false;
1852
858377e4
SH
1853 current_config = c->lxc_conf;
1854
72d0e1cb
SG
1855 /*
1856 * since we're going to wait for create to finish, I don't think we
1857 * need to get a copy of the arguments.
1858 */
dc23c1c8 1859 va_start(ap, flags);
a0e93eeb 1860 args = lxc_va_arg_list_to_argv(ap, 0, 0);
72d0e1cb 1861 va_end(ap);
a0e93eeb
CS
1862 if (!args) {
1863 ERROR("Memory allocation error.");
1864 goto out;
1865 }
72d0e1cb 1866
858377e4 1867 bret = do_lxcapi_create(c, t, bdevtype, specs, flags, args);
72d0e1cb
SG
1868
1869out:
a0e93eeb 1870 free(args);
858377e4 1871 current_config = NULL;
72d0e1cb
SG
1872 return bret;
1873}
1874
6b0d5538
SH
1875static void do_clear_unexp_config_line(struct lxc_conf *conf, const char *key)
1876{
4222a9f4
CB
1877 if (!strcmp(key, "lxc.cgroup"))
1878 return clear_unexp_config_line(conf, key, true);
1879
1880 if (!strcmp(key, "lxc.network"))
1881 return clear_unexp_config_line(conf, key, true);
1882
1883 if (!strcmp(key, "lxc.net"))
1884 return clear_unexp_config_line(conf, key, true);
1885
1886 /* Clear a network with a specific index. */
1887 if (!strncmp(key, "lxc.net.", 8)) {
1888 int ret;
1889 const char *idx;
1890
1891 idx = key + 8;
1892 ret = lxc_safe_uint(idx, &(unsigned int){0});
1893 if (!ret)
1894 return clear_unexp_config_line(conf, key, true);
1895 }
1896
1897 if (!strcmp(key, "lxc.hook"))
1898 return clear_unexp_config_line(conf, key, true);
1899
1900 return clear_unexp_config_line(conf, key, false);
6b0d5538
SH
1901}
1902
6afd673f
CB
1903static bool do_lxcapi_clear_config_item(struct lxc_container *c,
1904 const char *key)
72d0e1cb 1905{
6afd673f
CB
1906 int ret = 1;
1907 struct lxc_config_t *config;
72d0e1cb
SG
1908
1909 if (!c || !c->lxc_conf)
1910 return false;
6afd673f 1911
5cee8c50 1912 if (container_mem_lock(c))
72d0e1cb 1913 return false;
6afd673f
CB
1914
1915 config = lxc_getconfig(key);
1916 /* Verify that the config key exists and that it has a callback
1917 * implemented.
1918 */
1919 if (config && config->clr)
26471403 1920 ret = config->clr(key, c->lxc_conf, NULL);
6b0d5538
SH
1921 if (!ret)
1922 do_clear_unexp_config_line(c->lxc_conf, key);
6afd673f 1923
5cee8c50 1924 container_mem_unlock(c);
72d0e1cb
SG
1925 return ret == 0;
1926}
1927
858377e4
SH
1928WRAP_API_1(bool, lxcapi_clear_config_item, const char *)
1929
e0f59189 1930static inline bool enter_net_ns(struct lxc_container *c)
51d0854c 1931{
858377e4 1932 pid_t pid = do_lxcapi_init_pid(c);
ae22a220 1933
0e6e3a41 1934 if ((geteuid() != 0 || (c->lxc_conf && !lxc_list_empty(&c->lxc_conf->id_map))) && access("/proc/self/ns/user", F_OK) == 0) {
51d0854c
DY
1935 if (!switch_to_ns(pid, "user"))
1936 return false;
9c83a661 1937 }
51d0854c 1938 return switch_to_ns(pid, "net");
799f29ab
ÇO
1939}
1940
9c88ff1f
ÇO
1941// used by qsort and bsearch functions for comparing names
1942static inline int string_cmp(char **first, char **second)
1943{
1944 return strcmp(*first, *second);
1945}
1946
1947// used by qsort and bsearch functions for comparing container names
1948static inline int container_cmp(struct lxc_container **first, struct lxc_container **second)
1949{
1950 return strcmp((*first)->name, (*second)->name);
1951}
1952
1953static bool add_to_array(char ***names, char *cname, int pos)
1954{
1955 char **newnames = realloc(*names, (pos+1) * sizeof(char *));
1956 if (!newnames) {
1957 ERROR("Out of memory");
1958 return false;
1959 }
1960
1961 *names = newnames;
1962 newnames[pos] = strdup(cname);
1963 if (!newnames[pos])
1964 return false;
1965
1966 // sort the arrray as we will use binary search on it
1967 qsort(newnames, pos + 1, sizeof(char *), (int (*)(const void *,const void *))string_cmp);
1968
1969 return true;
1970}
1971
2871830a 1972static bool add_to_clist(struct lxc_container ***list, struct lxc_container *c, int pos, bool sort)
9c88ff1f
ÇO
1973{
1974 struct lxc_container **newlist = realloc(*list, (pos+1) * sizeof(struct lxc_container *));
1975 if (!newlist) {
1976 ERROR("Out of memory");
1977 return false;
1978 }
1979
1980 *list = newlist;
1981 newlist[pos] = c;
1982
1983 // sort the arrray as we will use binary search on it
2871830a
DE
1984 if (sort)
1985 qsort(newlist, pos + 1, sizeof(struct lxc_container *), (int (*)(const void *,const void *))container_cmp);
9c88ff1f
ÇO
1986
1987 return true;
1988}
1989
1990static char** get_from_array(char ***names, char *cname, int size)
1991{
1992 return (char **)bsearch(&cname, *names, size, sizeof(char *), (int (*)(const void *, const void *))string_cmp);
1993}
1994
1995
1996static bool array_contains(char ***names, char *cname, int size) {
1997 if(get_from_array(names, cname, size) != NULL)
1998 return true;
1999 return false;
2000}
2001
2002static bool remove_from_array(char ***names, char *cname, int size)
2003{
2004 char **result = get_from_array(names, cname, size);
2005 if (result != NULL) {
2006 free(result);
2007 return true;
2008 }
2009 return false;
2010}
2011
858377e4 2012static char ** do_lxcapi_get_interfaces(struct lxc_container *c)
799f29ab 2013{
ae22a220
ÇO
2014 pid_t pid;
2015 int i, count = 0, pipefd[2];
9c88ff1f 2016 char **interfaces = NULL;
ae22a220 2017 char interface[IFNAMSIZ];
799f29ab 2018
ae22a220
ÇO
2019 if(pipe(pipefd) < 0) {
2020 SYSERROR("pipe failed");
2021 return NULL;
c868b261
ÇO
2022 }
2023
ae22a220
ÇO
2024 pid = fork();
2025 if (pid < 0) {
959aee9c 2026 SYSERROR("failed to fork task to get interfaces information");
ae22a220
ÇO
2027 close(pipefd[0]);
2028 close(pipefd[1]);
2029 return NULL;
2030 }
799f29ab 2031
ae22a220
ÇO
2032 if (pid == 0) { // child
2033 int ret = 1, nbytes;
2034 struct ifaddrs *interfaceArray = NULL, *tempIfAddr = NULL;
2035
2036 /* close the read-end of the pipe */
2037 close(pipefd[0]);
2038
e0f59189 2039 if (!enter_net_ns(c)) {
ae22a220
ÇO
2040 SYSERROR("failed to enter namespace");
2041 goto out;
2042 }
2043
2044 /* Grab the list of interfaces */
2045 if (getifaddrs(&interfaceArray)) {
2046 SYSERROR("failed to get interfaces list");
2047 goto out;
2048 }
2049
2050 /* Iterate through the interfaces */
2051 for (tempIfAddr = interfaceArray; tempIfAddr != NULL; tempIfAddr = tempIfAddr->ifa_next) {
2052 nbytes = write(pipefd[1], tempIfAddr->ifa_name, IFNAMSIZ);
2053 if (nbytes < 0) {
2054 ERROR("write failed");
2055 goto out;
2056 }
2057 count++;
2058 }
2059 ret = 0;
2060
2061 out:
2062 if (interfaceArray)
2063 freeifaddrs(interfaceArray);
2064
2065 /* close the write-end of the pipe, thus sending EOF to the reader */
2066 close(pipefd[1]);
2067 exit(ret);
799f29ab
ÇO
2068 }
2069
ae22a220
ÇO
2070 /* close the write-end of the pipe */
2071 close(pipefd[1]);
2072
358afd84 2073 while (read(pipefd[0], &interface, IFNAMSIZ) == IFNAMSIZ) {
ae22a220
ÇO
2074 if (array_contains(&interfaces, interface, count))
2075 continue;
799f29ab 2076
ae22a220
ÇO
2077 if(!add_to_array(&interfaces, interface, count))
2078 ERROR("PARENT: add_to_array failed");
9c88ff1f
ÇO
2079 count++;
2080 }
799f29ab 2081
ae22a220
ÇO
2082 if (wait_for_pid(pid) != 0) {
2083 for(i=0;i<count;i++)
2084 free(interfaces[i]);
2085 free(interfaces);
2086 interfaces = NULL;
2087 }
9c88ff1f 2088
ae22a220
ÇO
2089 /* close the read-end of the pipe */
2090 close(pipefd[0]);
799f29ab 2091
9c88ff1f
ÇO
2092 /* Append NULL to the array */
2093 if(interfaces)
2094 interfaces = (char **)lxc_append_null_to_array((void **)interfaces, count);
799f29ab 2095
9c88ff1f 2096 return interfaces;
799f29ab
ÇO
2097}
2098
858377e4
SH
2099WRAP_API(char **, lxcapi_get_interfaces)
2100
2101static char** do_lxcapi_get_ips(struct lxc_container *c, const char* interface, const char* family, int scope)
799f29ab 2102{
ae22a220
ÇO
2103 pid_t pid;
2104 int i, count = 0, pipefd[2];
9c88ff1f 2105 char **addresses = NULL;
ae22a220 2106 char address[INET6_ADDRSTRLEN];
799f29ab 2107
ae22a220
ÇO
2108 if(pipe(pipefd) < 0) {
2109 SYSERROR("pipe failed");
2110 return NULL;
c868b261
ÇO
2111 }
2112
ae22a220
ÇO
2113 pid = fork();
2114 if (pid < 0) {
959aee9c 2115 SYSERROR("failed to fork task to get container ips");
ae22a220
ÇO
2116 close(pipefd[0]);
2117 close(pipefd[1]);
2118 return NULL;
9c83a661
SG
2119 }
2120
ae22a220
ÇO
2121 if (pid == 0) { // child
2122 int ret = 1, nbytes;
2123 struct ifaddrs *interfaceArray = NULL, *tempIfAddr = NULL;
2124 char addressOutputBuffer[INET6_ADDRSTRLEN];
2125 void *tempAddrPtr = NULL;
2126 char *address = NULL;
fe218ca3 2127
ae22a220
ÇO
2128 /* close the read-end of the pipe */
2129 close(pipefd[0]);
2130
e0f59189 2131 if (!enter_net_ns(c)) {
ae22a220
ÇO
2132 SYSERROR("failed to enter namespace");
2133 goto out;
9c83a661 2134 }
ae22a220
ÇO
2135
2136 /* Grab the list of interfaces */
2137 if (getifaddrs(&interfaceArray)) {
2138 SYSERROR("failed to get interfaces list");
2139 goto out;
2140 }
2141
2142 /* Iterate through the interfaces */
2143 for (tempIfAddr = interfaceArray; tempIfAddr != NULL; tempIfAddr = tempIfAddr->ifa_next) {
2144 if (tempIfAddr->ifa_addr == NULL)
9c83a661
SG
2145 continue;
2146
ae22a220
ÇO
2147 if(tempIfAddr->ifa_addr->sa_family == AF_INET) {
2148 if (family && strcmp(family, "inet"))
2149 continue;
2150 tempAddrPtr = &((struct sockaddr_in *)tempIfAddr->ifa_addr)->sin_addr;
2151 }
2152 else {
2153 if (family && strcmp(family, "inet6"))
2154 continue;
2155
2156 if (((struct sockaddr_in6 *)tempIfAddr->ifa_addr)->sin6_scope_id != scope)
2157 continue;
2158
2159 tempAddrPtr = &((struct sockaddr_in6 *)tempIfAddr->ifa_addr)->sin6_addr;
2160 }
2161
2162 if (interface && strcmp(interface, tempIfAddr->ifa_name))
2163 continue;
2164 else if (!interface && strcmp("lo", tempIfAddr->ifa_name) == 0)
9c83a661
SG
2165 continue;
2166
ae22a220
ÇO
2167 address = (char *)inet_ntop(tempIfAddr->ifa_addr->sa_family,
2168 tempAddrPtr,
2169 addressOutputBuffer,
2170 sizeof(addressOutputBuffer));
2171 if (!address)
2172 continue;
2173
2174 nbytes = write(pipefd[1], address, INET6_ADDRSTRLEN);
2175 if (nbytes < 0) {
2176 ERROR("write failed");
2177 goto out;
2178 }
2179 count++;
9c83a661 2180 }
ae22a220 2181 ret = 0;
9c83a661 2182
ae22a220
ÇO
2183 out:
2184 if(interfaceArray)
2185 freeifaddrs(interfaceArray);
9c83a661 2186
ae22a220
ÇO
2187 /* close the write-end of the pipe, thus sending EOF to the reader */
2188 close(pipefd[1]);
2189 exit(ret);
6849cb5b 2190 }
9c83a661 2191
ae22a220
ÇO
2192 /* close the write-end of the pipe */
2193 close(pipefd[1]);
2194
358afd84 2195 while (read(pipefd[0], &address, INET6_ADDRSTRLEN) == INET6_ADDRSTRLEN) {
9c88ff1f 2196 if(!add_to_array(&addresses, address, count))
ae22a220 2197 ERROR("PARENT: add_to_array failed");
9c88ff1f 2198 count++;
9c83a661
SG
2199 }
2200
ae22a220
ÇO
2201 if (wait_for_pid(pid) != 0) {
2202 for(i=0;i<count;i++)
2203 free(addresses[i]);
2204 free(addresses);
2205 addresses = NULL;
2206 }
9c83a661 2207
ae22a220
ÇO
2208 /* close the read-end of the pipe */
2209 close(pipefd[0]);
9c83a661
SG
2210
2211 /* Append NULL to the array */
9c88ff1f
ÇO
2212 if(addresses)
2213 addresses = (char **)lxc_append_null_to_array((void **)addresses, count);
9c83a661
SG
2214
2215 return addresses;
2216}
2217
858377e4
SH
2218WRAP_API_3(char **, lxcapi_get_ips, const char *, const char *, int)
2219
2220static int do_lxcapi_get_config_item(struct lxc_container *c, const char *key, char *retv, int inlen)
72d0e1cb 2221{
fce687aa
CB
2222 int ret = -1;
2223 struct lxc_config_t *config;
72d0e1cb
SG
2224
2225 if (!c || !c->lxc_conf)
2226 return -1;
fce687aa 2227
5cee8c50 2228 if (container_mem_lock(c))
72d0e1cb 2229 return -1;
fce687aa
CB
2230
2231 config = lxc_getconfig(key);
2232 /* Verify that the config key exists and that it has a callback
2233 * implemented.
2234 */
2235 if (config && config->get)
cccd2219 2236 ret = config->get(key, retv, inlen, c->lxc_conf, NULL);
fce687aa 2237
5cee8c50 2238 container_mem_unlock(c);
72d0e1cb
SG
2239 return ret;
2240}
2241
858377e4
SH
2242WRAP_API_3(int, lxcapi_get_config_item, const char *, char *, int)
2243
2244static char* do_lxcapi_get_running_config_item(struct lxc_container *c, const char *key)
8ac18377
ÇO
2245{
2246 char *ret;
2247
2248 if (!c || !c->lxc_conf)
2249 return NULL;
2250 if (container_mem_lock(c))
2251 return NULL;
858377e4 2252 ret = lxc_cmd_get_config_item(c->name, key, do_lxcapi_get_config_path(c));
8ac18377
ÇO
2253 container_mem_unlock(c);
2254 return ret;
2255}
2256
858377e4
SH
2257WRAP_API_1(char *, lxcapi_get_running_config_item, const char *)
2258
2259static int do_lxcapi_get_keys(struct lxc_container *c, const char *key, char *retv, int inlen)
72d0e1cb
SG
2260{
2261 if (!key)
2262 return lxc_listconfigs(retv, inlen);
2263 /*
7fa3f2e9 2264 * Support 'lxc.net.<idx>', i.e. 'lxc.net.0'
72d0e1cb
SG
2265 * This is an intelligent result to show which keys are valid given
2266 * the type of nic it is
2267 */
2268 if (!c || !c->lxc_conf)
2269 return -1;
5cee8c50 2270 if (container_mem_lock(c))
72d0e1cb
SG
2271 return -1;
2272 int ret = -1;
f9373e40 2273 if (strncmp(key, "lxc.net.", 8) == 0)
6849cb5b 2274 ret = lxc_list_nicconfigs(c->lxc_conf, key, retv, inlen);
f9373e40
CB
2275 else if (strncmp(key, "lxc.network.", 12) == 0)
2276 ret = lxc_list_nicconfigs_legacy(c->lxc_conf, key, retv, inlen);
5cee8c50 2277 container_mem_unlock(c);
72d0e1cb
SG
2278 return ret;
2279}
2280
858377e4
SH
2281WRAP_API_3(int, lxcapi_get_keys, const char *, char *, int)
2282
2283static bool do_lxcapi_save_config(struct lxc_container *c, const char *alt_file)
72d0e1cb 2284{
39dc698c
SH
2285 FILE *fout;
2286 bool ret = false, need_disklock = false;
2287 int lret;
2288
72d0e1cb
SG
2289 if (!alt_file)
2290 alt_file = c->configfile;
2291 if (!alt_file)
6849cb5b 2292 return false; // should we write to stdout if no file is specified?
39dc698c
SH
2293
2294 // If we haven't yet loaded a config, load the stock config
2295 if (!c->lxc_conf) {
858377e4 2296 if (!do_lxcapi_load_config(c, lxc_global_config_value("lxc.default_config"))) {
959aee9c 2297 ERROR("Error loading default configuration file %s while saving %s", lxc_global_config_value("lxc.default_config"), c->name);
72d0e1cb
SG
2298 return false;
2299 }
39dc698c 2300 }
72d0e1cb 2301
5a3d2e1e
SG
2302 if (!create_container_dir(c))
2303 return false;
2304
39dc698c
SH
2305 /*
2306 * If we're writing to the container's config file, take the
2307 * disk lock. Otherwise just take the memlock to protect the
2308 * struct lxc_container while we're traversing it.
2309 */
2310 if (strcmp(c->configfile, alt_file) == 0)
2311 need_disklock = true;
2312
2313 if (need_disklock)
2314 lret = container_disk_lock(c);
2315 else
2316 lret = container_mem_lock(c);
2317
2318 if (lret)
72d0e1cb 2319 return false;
39dc698c
SH
2320
2321 fout = fopen(alt_file, "w");
2322 if (!fout)
2323 goto out;
6b0d5538 2324 write_config(fout, c->lxc_conf);
72d0e1cb 2325 fclose(fout);
39dc698c
SH
2326 ret = true;
2327
2328out:
2329 if (need_disklock)
2330 container_disk_unlock(c);
2331 else
2332 container_mem_unlock(c);
2333 return ret;
72d0e1cb
SG
2334}
2335
858377e4
SH
2336WRAP_API_1(bool, lxcapi_save_config, const char *)
2337
0ea055b3
CB
2338
2339static bool mod_rdep(struct lxc_container *c0, struct lxc_container *c, bool inc)
dfb31b25 2340{
0ea055b3
CB
2341 FILE *f1;
2342 struct stat fbuf;
42342bed
CB
2343 void *buf = NULL;
2344 char *del = NULL;
dfb31b25 2345 char path[MAXPATHLEN];
0ea055b3
CB
2346 char newpath[MAXPATHLEN];
2347 int fd, ret, n = 0, v = 0;
dfb31b25 2348 bool bret = false;
42342bed 2349 size_t len = 0, bytes = 0;
dfb31b25 2350
0ea055b3 2351 if (container_disk_lock(c0))
dfb31b25 2352 return false;
0ea055b3
CB
2353
2354 ret = snprintf(path, MAXPATHLEN, "%s/%s/lxc_snapshots", c0->config_path, c0->name);
dfb31b25
SH
2355 if (ret < 0 || ret > MAXPATHLEN)
2356 goto out;
0ea055b3
CB
2357 ret = snprintf(newpath, MAXPATHLEN, "%s\n%s\n", c->config_path, c->name);
2358 if (ret < 0 || ret > MAXPATHLEN)
dfb31b25 2359 goto out;
0ea055b3
CB
2360
2361 /* If we find an lxc-snapshot file using the old format only listing the
2362 * number of snapshots we will keep using it. */
2363 f1 = fopen(path, "r");
2364 if (f1) {
2365 n = fscanf(f1, "%d", &v);
2366 fclose(f1);
2367 if (n == 1 && v == 0) {
2368 remove(path);
2369 n = 0;
2370 }
dfb31b25 2371 }
0ea055b3
CB
2372 if (n == 1) {
2373 v += inc ? 1 : -1;
2374 f1 = fopen(path, "w");
2375 if (!f1)
2376 goto out;
2377 if (fprintf(f1, "%d\n", v) < 0) {
2378 ERROR("Error writing new snapshots value");
2379 fclose(f1);
2380 goto out;
2381 }
2382 ret = fclose(f1);
2383 if (ret != 0) {
2384 SYSERROR("Error writing to or closing snapshots file");
2385 goto out;
2386 }
2387 } else {
2388 /* Here we know that we have or can use an lxc-snapshot file
2389 * using the new format. */
2390 if (inc) {
2391 f1 = fopen(path, "a");
2392 if (!f1)
2393 goto out;
2394
2395 if (fprintf(f1, "%s", newpath) < 0) {
2396 ERROR("Error writing new snapshots entry");
2397 ret = fclose(f1);
2398 if (ret != 0)
2399 SYSERROR("Error writing to or closing snapshots file");
2400 goto out;
2401 }
2402
2403 ret = fclose(f1);
2404 if (ret != 0) {
2405 SYSERROR("Error writing to or closing snapshots file");
2406 goto out;
2407 }
2408 } else if (!inc) {
d028235d
SG
2409 if ((fd = open(path, O_RDWR | O_CLOEXEC)) < 0)
2410 goto out;
2411
2412 if (fstat(fd, &fbuf) < 0) {
2413 close(fd);
2414 goto out;
2415 }
2416
2417 if (fbuf.st_size != 0) {
d028235d 2418
25086a5f 2419 buf = lxc_strmmap(NULL, fbuf.st_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
d028235d
SG
2420 if (buf == MAP_FAILED) {
2421 SYSERROR("Failed to create mapping %s", path);
2422 close(fd);
2423 goto out;
2424 }
2425
2426 len = strlen(newpath);
2427 while ((del = strstr((char *)buf, newpath))) {
2428 memmove(del, del + len, strlen(del) - len + 1);
2429 bytes += len;
2430 }
2431
25086a5f 2432 lxc_strmunmap(buf, fbuf.st_size);
d028235d
SG
2433 if (ftruncate(fd, fbuf.st_size - bytes) < 0) {
2434 SYSERROR("Failed to truncate file %s", path);
2435 close(fd);
2436 goto out;
2437 }
2438 }
2439 close(fd);
2440 }
0ea055b3
CB
2441
2442 /* If the lxc-snapshot file is empty, remove it. */
2443 if (stat(path, &fbuf) < 0)
2444 goto out;
d028235d
SG
2445 if (!fbuf.st_size) {
2446 remove(path);
0ea055b3 2447 }
dfb31b25
SH
2448 }
2449
2450 bret = true;
2451
2452out:
0ea055b3 2453 container_disk_unlock(c0);
dfb31b25
SH
2454 return bret;
2455}
2456
2457static void strip_newline(char *p)
2458{
2459 size_t len = strlen(p);
2460 if (len < 1)
2461 return;
2462 if (p[len-1] == '\n')
2463 p[len-1] = '\0';
2464}
2465
d825fff3 2466void mod_all_rdeps(struct lxc_container *c, bool inc)
dfb31b25
SH
2467{
2468 struct lxc_container *p;
2469 char *lxcpath = NULL, *lxcname = NULL, path[MAXPATHLEN];
2470 size_t pathlen = 0, namelen = 0;
2471 FILE *f;
2472 int ret;
2473
2474 ret = snprintf(path, MAXPATHLEN, "%s/%s/lxc_rdepends",
2475 c->config_path, c->name);
2476 if (ret < 0 || ret >= MAXPATHLEN) {
2477 ERROR("Path name too long");
2478 return;
2479 }
025ed0f3 2480 f = fopen(path, "r");
025ed0f3 2481 if (f == NULL)
dfb31b25
SH
2482 return;
2483 while (getline(&lxcpath, &pathlen, f) != -1) {
2484 if (getline(&lxcname, &namelen, f) == -1) {
959aee9c 2485 ERROR("badly formatted file %s", path);
dfb31b25
SH
2486 goto out;
2487 }
2488 strip_newline(lxcpath);
2489 strip_newline(lxcname);
2490 if ((p = lxc_container_new(lxcname, lxcpath)) == NULL) {
2491 ERROR("Unable to find dependent container %s:%s",
2492 lxcpath, lxcname);
2493 continue;
2494 }
0ea055b3
CB
2495 if (!mod_rdep(p, c, inc))
2496 ERROR("Failed to update snapshots file for %s:%s",
dfb31b25
SH
2497 lxcpath, lxcname);
2498 lxc_container_put(p);
2499 }
2500out:
f10fad2f
ME
2501 free(lxcpath);
2502 free(lxcname);
dfb31b25
SH
2503 fclose(f);
2504}
2505
18aa217b 2506static bool has_fs_snapshots(struct lxc_container *c)
dfb31b25 2507{
0ea055b3 2508 FILE *f;
dfb31b25
SH
2509 char path[MAXPATHLEN];
2510 int ret, v;
0ea055b3 2511 struct stat fbuf;
dfb31b25
SH
2512 bool bret = false;
2513
2514 ret = snprintf(path, MAXPATHLEN, "%s/%s/lxc_snapshots", c->config_path,
2515 c->name);
2516 if (ret < 0 || ret > MAXPATHLEN)
2517 goto out;
0ea055b3
CB
2518 /* If the file doesn't exist there are no snapshots. */
2519 if (stat(path, &fbuf) < 0)
dfb31b25 2520 goto out;
0ea055b3
CB
2521 v = fbuf.st_size;
2522 if (v != 0) {
2523 f = fopen(path, "r");
2524 if (!f)
2525 goto out;
2526 ret = fscanf(f, "%d", &v);
2527 fclose(f);
2528 // TODO: Figure out what to do with the return value of fscanf.
2529 if (ret != 1)
2530 INFO("Container uses new lxc-snapshots format %s", path);
2531 }
dfb31b25
SH
2532 bret = v != 0;
2533
2534out:
2535 return bret;
2536}
2537
18aa217b
SH
2538static bool has_snapshots(struct lxc_container *c)
2539{
2540 char path[MAXPATHLEN];
74f96976 2541 struct dirent *direntp;
18aa217b
SH
2542 int count=0;
2543 DIR *dir;
2544
2545 if (!get_snappath_dir(c, path))
2546 return false;
2547 dir = opendir(path);
2548 if (!dir)
2549 return false;
74f96976 2550 while ((direntp = readdir(dir))) {
18aa217b
SH
2551 if (!direntp)
2552 break;
2553
2554 if (!strcmp(direntp->d_name, "."))
2555 continue;
2556
2557 if (!strcmp(direntp->d_name, ".."))
2558 continue;
2559 count++;
2560 break;
2561 }
2562 closedir(dir);
2563 return count > 0;
2564}
2565
297c2d58 2566static bool do_destroy_container(struct lxc_conf *conf) {
d028235d 2567 if (am_unpriv()) {
c9b7c33e
CB
2568 if (userns_exec_1(conf, bdev_destroy_wrapper, conf,
2569 "bdev_destroy_wrapper") < 0)
d028235d
SG
2570 return false;
2571 return true;
2572 }
2573 return bdev_destroy(conf);
297c2d58
CB
2574}
2575
4355ab5f
SH
2576static int lxc_rmdir_onedev_wrapper(void *data)
2577{
2578 char *arg = (char *) data;
18aa217b 2579 return lxc_rmdir_onedev(arg, "snaps");
4355ab5f
SH
2580}
2581
18aa217b 2582static bool container_destroy(struct lxc_container *c)
72d0e1cb 2583{
c868b261 2584 bool bret = false;
297c2d58 2585 int ret = 0;
a70a69e8 2586 struct lxc_conf *conf;
72d0e1cb 2587
858377e4 2588 if (!c || !do_lxcapi_is_defined(c))
5a3d2e1e
SG
2589 return false;
2590
a70a69e8 2591 conf = c->lxc_conf;
3bc449ed 2592 if (container_disk_lock(c))
72d0e1cb 2593 return false;
72d0e1cb 2594
39dc698c 2595 if (!is_stopped(c)) {
60bf62d4
SH
2596 // we should queue some sort of error - in c->error_string?
2597 ERROR("container %s is not stopped", c->name);
2598 goto out;
72d0e1cb
SG
2599 }
2600
a70a69e8 2601 if (conf && !lxc_list_empty(&conf->hooks[LXCHOOK_DESTROY])) {
37cf711b 2602 /* Start of environment variable setup for hooks */
ab7efcf5 2603 if (c->name && setenv("LXC_NAME", c->name, 1)) {
37cf711b
SY
2604 SYSERROR("failed to set environment variable for container name");
2605 }
ab7efcf5 2606 if (conf->rcfile && setenv("LXC_CONFIG_FILE", conf->rcfile, 1)) {
37cf711b
SY
2607 SYSERROR("failed to set environment variable for config path");
2608 }
ab7efcf5 2609 if (conf->rootfs.mount && setenv("LXC_ROOTFS_MOUNT", conf->rootfs.mount, 1)) {
37cf711b
SY
2610 SYSERROR("failed to set environment variable for rootfs mount");
2611 }
ab7efcf5 2612 if (conf->rootfs.path && setenv("LXC_ROOTFS_PATH", conf->rootfs.path, 1)) {
37cf711b
SY
2613 SYSERROR("failed to set environment variable for rootfs mount");
2614 }
2615 if (conf->console.path && setenv("LXC_CONSOLE", conf->console.path, 1)) {
2616 SYSERROR("failed to set environment variable for console path");
2617 }
2618 if (conf->console.log_path && setenv("LXC_CONSOLE_LOGPATH", conf->console.log_path, 1)) {
2619 SYSERROR("failed to set environment variable for console log");
2620 }
2621 /* End of environment variable setup for hooks */
2622
2623 if (run_lxc_hooks(c->name, "destroy", conf, c->get_config_path(c), NULL)) {
2624 ERROR("Error executing clone hook for %s", c->name);
2625 goto out;
2626 }
2627 }
2628
2629 if (current_config && conf == current_config) {
858377e4 2630 current_config = NULL;
37cf711b
SY
2631 if (conf->logfd != -1) {
2632 close(conf->logfd);
2633 conf->logfd = -1;
858377e4
SH
2634 }
2635 }
2636
d028235d
SG
2637 if (conf && conf->rootfs.path && conf->rootfs.mount) {
2638 if (!do_destroy_container(conf)) {
2639 ERROR("Error destroying rootfs for %s", c->name);
2640 goto out;
2641 }
2642 INFO("Destroyed rootfs for %s", c->name);
2643 }
60bf62d4 2644
dfb31b25
SH
2645 mod_all_rdeps(c, false);
2646
858377e4 2647 const char *p1 = do_lxcapi_get_config_path(c);
60bf62d4
SH
2648 char *path = alloca(strlen(p1) + strlen(c->name) + 2);
2649 sprintf(path, "%s/%s", p1, c->name);
c868b261 2650 if (am_unpriv())
c9b7c33e
CB
2651 ret = userns_exec_1(conf, lxc_rmdir_onedev_wrapper, path,
2652 "lxc_rmdir_onedev_wrapper");
4355ab5f 2653 else
18aa217b 2654 ret = lxc_rmdir_onedev(path, "snaps");
4355ab5f 2655 if (ret < 0) {
60bf62d4
SH
2656 ERROR("Error destroying container directory for %s", c->name);
2657 goto out;
2658 }
d028235d 2659 INFO("Destroyed directory for %s", c->name);
297c2d58 2660
fef48dc9 2661 bret = true;
60bf62d4
SH
2662
2663out:
3bc449ed 2664 container_disk_unlock(c);
fef48dc9 2665 return bret;
72d0e1cb
SG
2666}
2667
858377e4 2668static bool do_lxcapi_destroy(struct lxc_container *c)
18aa217b
SH
2669{
2670 if (!c || !lxcapi_is_defined(c))
2671 return false;
2672 if (has_snapshots(c)) {
2673 ERROR("Container %s has snapshots; not removing", c->name);
2674 return false;
2675 }
2676
2677 if (has_fs_snapshots(c)) {
2678 ERROR("container %s has snapshots on its rootfs", c->name);
2679 return false;
2680 }
2681
2682 return container_destroy(c);
2683}
2684
858377e4 2685WRAP_API(bool, lxcapi_destroy)
18aa217b 2686
858377e4 2687static bool do_lxcapi_destroy_with_snapshots(struct lxc_container *c)
18aa217b
SH
2688{
2689 if (!c || !lxcapi_is_defined(c))
2690 return false;
2691 if (!lxcapi_snapshot_destroy_all(c)) {
2692 ERROR("Error deleting all snapshots");
2693 return false;
2694 }
2695 return lxcapi_destroy(c);
2696}
2697
858377e4
SH
2698WRAP_API(bool, lxcapi_destroy_with_snapshots)
2699
96532523
SH
2700static bool set_config_item_locked(struct lxc_container *c, const char *key, const char *v)
2701{
2702 struct lxc_config_t *config;
2703
2704 if (!c->lxc_conf)
2705 c->lxc_conf = lxc_conf_init();
4222a9f4 2706
6b0d5538 2707 if (!c->lxc_conf)
96532523 2708 return false;
4222a9f4 2709
96532523
SH
2710 config = lxc_getconfig(key);
2711 if (!config)
2712 return false;
4222a9f4 2713
c7e27aaf 2714 if (config->set(key, v, c->lxc_conf, NULL) != 0)
f979ac15 2715 return false;
4222a9f4
CB
2716
2717 if (lxc_config_value_empty(v)) {
2718 do_clear_unexp_config_line(c->lxc_conf, key);
2719 return true;
2720 }
2721
6b0d5538 2722 return do_append_unexp_config_line(c->lxc_conf, key, v);
96532523
SH
2723}
2724
858377e4 2725static bool do_lxcapi_set_config_item(struct lxc_container *c, const char *key, const char *v)
72d0e1cb 2726{
72d0e1cb 2727 bool b = false;
72d0e1cb
SG
2728
2729 if (!c)
2730 return false;
2731
5cee8c50 2732 if (container_mem_lock(c))
72d0e1cb
SG
2733 return false;
2734
96532523 2735 b = set_config_item_locked(c, key, v);
72d0e1cb 2736
5cee8c50 2737 container_mem_unlock(c);
72d0e1cb
SG
2738 return b;
2739}
2740
858377e4
SH
2741WRAP_API_2(bool, lxcapi_set_config_item, const char *, const char *)
2742
72d0e1cb
SG
2743static char *lxcapi_config_file_name(struct lxc_container *c)
2744{
2745 if (!c || !c->configfile)
2746 return NULL;
2747 return strdup(c->configfile);
2748}
2749
2a59a681
SH
2750static const char *lxcapi_get_config_path(struct lxc_container *c)
2751{
2752 if (!c || !c->config_path)
2753 return NULL;
2754 return (const char *)(c->config_path);
2755}
2756
afeecbba
SH
2757/*
2758 * not for export
2759 * Just recalculate the c->configfile based on the
2760 * c->config_path, which must be set.
2761 * The lxc_container must be locked or not yet public.
2762 */
2763static bool set_config_filename(struct lxc_container *c)
2764{
2765 char *newpath;
2766 int len, ret;
2767
2768 if (!c->config_path)
2769 return false;
2770
2771 /* $lxc_path + "/" + c->name + "/" + "config" + '\0' */
2772 len = strlen(c->config_path) + strlen(c->name) + strlen("config") + 3;
2773 newpath = malloc(len);
2774 if (!newpath)
2775 return false;
2776
2777 ret = snprintf(newpath, len, "%s/%s/config", c->config_path, c->name);
2778 if (ret < 0 || ret >= len) {
2779 fprintf(stderr, "Error printing out config file name\n");
2780 free(newpath);
2781 return false;
2782 }
2783
f10fad2f 2784 free(c->configfile);
afeecbba
SH
2785 c->configfile = newpath;
2786
2787 return true;
2788}
2789
858377e4 2790static bool do_lxcapi_set_config_path(struct lxc_container *c, const char *path)
2a59a681
SH
2791{
2792 char *p;
2793 bool b = false;
afeecbba 2794 char *oldpath = NULL;
2a59a681
SH
2795
2796 if (!c)
2797 return b;
2798
5cee8c50 2799 if (container_mem_lock(c))
2a59a681
SH
2800 return b;
2801
2802 p = strdup(path);
afeecbba
SH
2803 if (!p) {
2804 ERROR("Out of memory setting new lxc path");
2a59a681 2805 goto err;
afeecbba
SH
2806 }
2807
2a59a681
SH
2808 b = true;
2809 if (c->config_path)
afeecbba 2810 oldpath = c->config_path;
2a59a681 2811 c->config_path = p;
afeecbba
SH
2812
2813 /* Since we've changed the config path, we have to change the
2814 * config file name too */
2815 if (!set_config_filename(c)) {
2816 ERROR("Out of memory setting new config filename");
2817 b = false;
2818 free(c->config_path);
2819 c->config_path = oldpath;
2820 oldpath = NULL;
2821 }
2a59a681 2822err:
f10fad2f 2823 free(oldpath);
5cee8c50 2824 container_mem_unlock(c);
2a59a681
SH
2825 return b;
2826}
2827
858377e4 2828WRAP_API_1(bool, lxcapi_set_config_path, const char *)
2a59a681 2829
858377e4 2830static bool do_lxcapi_set_cgroup_item(struct lxc_container *c, const char *subsys, const char *value)
794dd120
SH
2831{
2832 int ret;
794dd120
SH
2833
2834 if (!c)
2835 return false;
2836
3bc449ed 2837 if (is_stopped(c))
794dd120
SH
2838 return false;
2839
3bc449ed
SH
2840 if (container_disk_lock(c))
2841 return false;
794dd120 2842
33ad9f1a 2843 ret = lxc_cgroup_set(subsys, value, c->name, c->config_path);
3bc449ed
SH
2844
2845 container_disk_unlock(c);
2846 return ret == 0;
794dd120
SH
2847}
2848
858377e4
SH
2849WRAP_API_2(bool, lxcapi_set_cgroup_item, const char *, const char *)
2850
2851static int do_lxcapi_get_cgroup_item(struct lxc_container *c, const char *subsys, char *retv, int inlen)
794dd120 2852{
3bc449ed 2853 int ret;
794dd120 2854
6502006a 2855 if (!c)
794dd120
SH
2856 return -1;
2857
3bc449ed 2858 if (is_stopped(c))
794dd120
SH
2859 return -1;
2860
3bc449ed
SH
2861 if (container_disk_lock(c))
2862 return -1;
794dd120 2863
33ad9f1a 2864 ret = lxc_cgroup_get(subsys, retv, inlen, c->name, c->config_path);
794dd120 2865
3bc449ed 2866 container_disk_unlock(c);
794dd120
SH
2867 return ret;
2868}
2869
858377e4
SH
2870WRAP_API_3(int, lxcapi_get_cgroup_item, const char *, char *, int)
2871
593e8478 2872const char *lxc_get_global_config_item(const char *key)
83c98d82 2873{
593e8478 2874 return lxc_global_config_value(key);
a8428dfa
SH
2875}
2876
b6b918a1
SG
2877const char *lxc_get_version(void)
2878{
95ee490b 2879 return LXC_VERSION;
b6b918a1
SG
2880}
2881
f0ca2726 2882static int copy_file(const char *old, const char *new)
9be53773
SH
2883{
2884 int in, out;
2885 ssize_t len, ret;
2886 char buf[8096];
2887 struct stat sbuf;
2888
2889 if (file_exists(new)) {
2890 ERROR("copy destination %s exists", new);
2891 return -1;
2892 }
2893 ret = stat(old, &sbuf);
2894 if (ret < 0) {
dfb31b25 2895 INFO("Error stat'ing %s", old);
9be53773
SH
2896 return -1;
2897 }
2898
2899 in = open(old, O_RDONLY);
2900 if (in < 0) {
dfb31b25 2901 SYSERROR("Error opening original file %s", old);
9be53773
SH
2902 return -1;
2903 }
2904 out = open(new, O_CREAT | O_EXCL | O_WRONLY, 0644);
2905 if (out < 0) {
dfb31b25 2906 SYSERROR("Error opening new file %s", new);
9be53773
SH
2907 close(in);
2908 return -1;
2909 }
2910
2911 while (1) {
2912 len = read(in, buf, 8096);
2913 if (len < 0) {
dfb31b25 2914 SYSERROR("Error reading old file %s", old);
9be53773
SH
2915 goto err;
2916 }
2917 if (len == 0)
2918 break;
2919 ret = write(out, buf, len);
6849cb5b 2920 if (ret < len) { // should we retry?
dfb31b25 2921 SYSERROR("Error: write to new file %s was interrupted", new);
9be53773
SH
2922 goto err;
2923 }
2924 }
2925 close(in);
2926 close(out);
2927
2928 // we set mode, but not owner/group
2929 ret = chmod(new, sbuf.st_mode);
2930 if (ret) {
dfb31b25 2931 SYSERROR("Error setting mode on %s", new);
9be53773
SH
2932 return -1;
2933 }
2934
2935 return 0;
2936
2937err:
2938 close(in);
2939 close(out);
2940 return -1;
2941}
2942
9be53773
SH
2943static int copyhooks(struct lxc_container *oldc, struct lxc_container *c)
2944{
619256b5 2945 int i, len, ret;
9be53773 2946 struct lxc_list *it;
619256b5
ÇO
2947 char *cpath;
2948
2949 len = strlen(oldc->config_path) + strlen(oldc->name) + 3;
2950 cpath = alloca(len);
2951 ret = snprintf(cpath, len, "%s/%s/", oldc->config_path, oldc->name);
2952 if (ret < 0 || ret >= len)
2953 return -1;
9be53773
SH
2954
2955 for (i=0; i<NUM_LXC_HOOKS; i++) {
2956 lxc_list_for_each(it, &c->lxc_conf->hooks[i]) {
2957 char *hookname = it->elem;
c32981c3 2958 char *fname = strrchr(hookname, '/');
9be53773
SH
2959 char tmppath[MAXPATHLEN];
2960 if (!fname) // relative path - we don't support, but maybe we should
2961 return 0;
619256b5
ÇO
2962 if (strncmp(hookname, cpath, len - 1) != 0) {
2963 // this hook is public - ignore
2964 continue;
2965 }
9be53773
SH
2966 // copy the script, and change the entry in confile
2967 ret = snprintf(tmppath, MAXPATHLEN, "%s/%s/%s",
2968 c->config_path, c->name, fname+1);
2969 if (ret < 0 || ret >= MAXPATHLEN)
2970 return -1;
2971 ret = copy_file(it->elem, tmppath);
2972 if (ret < 0)
2973 return -1;
2974 free(it->elem);
2975 it->elem = strdup(tmppath);
2976 if (!it->elem) {
2977 ERROR("out of memory copying hook path");
2978 return -1;
2979 }
9be53773
SH
2980 }
2981 }
2982
67702c21
SH
2983 if (!clone_update_unexp_hooks(c->lxc_conf, oldc->config_path,
2984 c->config_path, oldc->name, c->name)) {
6b0d5538
SH
2985 ERROR("Error saving new hooks in clone");
2986 return -1;
2987 }
858377e4 2988 do_lxcapi_save_config(c, NULL);
9be53773
SH
2989 return 0;
2990}
2991
9be53773
SH
2992
2993static int copy_fstab(struct lxc_container *oldc, struct lxc_container *c)
2994{
2995 char newpath[MAXPATHLEN];
2996 char *oldpath = oldc->lxc_conf->fstab;
2997 int ret;
2998
2999 if (!oldpath)
3000 return 0;
3001
47148e96
CB
3002 /* REMOVE IN LXC 3.0
3003 legacy mount key
3004 */
6b0d5538
SH
3005 clear_unexp_config_line(c->lxc_conf, "lxc.mount", false);
3006
47148e96
CB
3007 clear_unexp_config_line(c->lxc_conf, "lxc.mount.fstab", false);
3008
c32981c3 3009 char *p = strrchr(oldpath, '/');
9be53773
SH
3010 if (!p)
3011 return -1;
3012 ret = snprintf(newpath, MAXPATHLEN, "%s/%s%s",
3013 c->config_path, c->name, p);
3014 if (ret < 0 || ret >= MAXPATHLEN) {
3015 ERROR("error printing new path for %s", oldpath);
3016 return -1;
3017 }
3018 if (file_exists(newpath)) {
3019 ERROR("error: fstab file %s exists", newpath);
3020 return -1;
3021 }
3022
3023 if (copy_file(oldpath, newpath) < 0) {
3024 ERROR("error: copying %s to %s", oldpath, newpath);
3025 return -1;
3026 }
3027 free(c->lxc_conf->fstab);
3028 c->lxc_conf->fstab = strdup(newpath);
3029 if (!c->lxc_conf->fstab) {
3030 ERROR("error: allocating pathname");
3031 return -1;
3032 }
47148e96 3033 if (!do_append_unexp_config_line(c->lxc_conf, "lxc.mount.fstab", newpath)) {
6b0d5538
SH
3034 ERROR("error saving new lxctab");
3035 return -1;
3036 }
9be53773
SH
3037
3038 return 0;
3039}
3040
dfb31b25
SH
3041static void copy_rdepends(struct lxc_container *c, struct lxc_container *c0)
3042{
3043 char path0[MAXPATHLEN], path1[MAXPATHLEN];
3044 int ret;
3045
3046 ret = snprintf(path0, MAXPATHLEN, "%s/%s/lxc_rdepends", c0->config_path,
3047 c0->name);
3048 if (ret < 0 || ret >= MAXPATHLEN) {
3049 WARN("Error copying reverse dependencies");
3050 return;
3051 }
3052 ret = snprintf(path1, MAXPATHLEN, "%s/%s/lxc_rdepends", c->config_path,
3053 c->name);
3054 if (ret < 0 || ret >= MAXPATHLEN) {
3055 WARN("Error copying reverse dependencies");
3056 return;
3057 }
3058 if (copy_file(path0, path1) < 0) {
3059 INFO("Error copying reverse dependencies");
3060 return;
3061 }
3062}
3063
3064static bool add_rdepends(struct lxc_container *c, struct lxc_container *c0)
3065{
3066 int ret;
3067 char path[MAXPATHLEN];
3068 FILE *f;
3069 bool bret;
3070
3071 ret = snprintf(path, MAXPATHLEN, "%s/%s/lxc_rdepends", c->config_path,
3072 c->name);
3073 if (ret < 0 || ret >= MAXPATHLEN)
3074 return false;
3075 f = fopen(path, "a");
3076 if (!f)
3077 return false;
3078 bret = true;
3079 // if anything goes wrong, just return an error
3080 if (fprintf(f, "%s\n%s\n", c0->config_path, c0->name) < 0)
3081 bret = false;
3082 if (fclose(f) != 0)
3083 bret = false;
3084 return bret;
3085}
3086
15a90a10
SH
3087/*
3088 * If the fs natively supports snapshot clones with no penalty,
3089 * then default to those even if not requested.
3090 * Currently we only do this for btrfs.
3091 */
3092bool should_default_to_snapshot(struct lxc_container *c0,
3093 struct lxc_container *c1)
3094{
3095 size_t l0 = strlen(c0->config_path) + strlen(c0->name) + 2;
3096 size_t l1 = strlen(c1->config_path) + strlen(c1->name) + 2;
3097 char *p0 = alloca(l0 + 1);
3098 char *p1 = alloca(l1 + 1);
6e0fa6a0 3099 char *rootfs = c0->lxc_conf->rootfs.path;
15a90a10
SH
3100
3101 snprintf(p0, l0, "%s/%s", c0->config_path, c0->name);
3102 snprintf(p1, l1, "%s/%s", c1->config_path, c1->name);
9a09badc
CB
3103
3104 if (!is_btrfs_fs(p0) || !is_btrfs_fs(p1))
3105 return false;
3106
6e0fa6a0
CB
3107 if (is_btrfs_subvol(rootfs) <= 0)
3108 return false;
3109
15a90a10
SH
3110 return btrfs_same_fs(p0, p1) == 0;
3111}
3112
9be53773 3113static int copy_storage(struct lxc_container *c0, struct lxc_container *c,
763429b6
CB
3114 const char *newtype, int flags, const char *bdevdata,
3115 uint64_t newsize)
9be53773
SH
3116{
3117 struct bdev *bdev;
dfb31b25 3118 int need_rdep;
9be53773 3119
15a90a10
SH
3120 if (should_default_to_snapshot(c0, c))
3121 flags |= LXC_CLONE_SNAPSHOT;
3122
763429b6
CB
3123 bdev = bdev_copy(c0, c->name, c->config_path, newtype, flags, bdevdata,
3124 newsize, &need_rdep);
9be53773 3125 if (!bdev) {
763429b6 3126 ERROR("Error copying storage.");
9be53773
SH
3127 return -1;
3128 }
763429b6
CB
3129
3130 /* Set new rootfs. */
9be53773
SH
3131 free(c->lxc_conf->rootfs.path);
3132 c->lxc_conf->rootfs.path = strdup(bdev->src);
3133 bdev_put(bdev);
763429b6 3134
dfb31b25 3135 if (!c->lxc_conf->rootfs.path) {
763429b6
CB
3136 ERROR("Out of memory while setting storage path.");
3137 return -1;
3138 }
763429b6 3139
7a96a068
CB
3140 /* REMOVE IN LXC 3.0
3141 * legacy rootfs key
3142 */
6b0d5538 3143 clear_unexp_config_line(c->lxc_conf, "lxc.rootfs", false);
7a96a068
CB
3144
3145 /* Append a new lxc.rootfs.path entry to the unexpanded config. */
3146 clear_unexp_config_line(c->lxc_conf, "lxc.rootfs.path", false);
3147 if (!do_append_unexp_config_line(c->lxc_conf, "lxc.rootfs.path",
763429b6
CB
3148 c->lxc_conf->rootfs.path)) {
3149 ERROR("Error saving new rootfs to cloned config.");
d0218321
SH
3150 return -1;
3151 }
763429b6 3152
7a96a068
CB
3153 /* REMOVE IN LXC 3.0
3154 * legacy rootfs.backend key
3155 */
8869eb5f 3156 clear_unexp_config_line(c->lxc_conf, "lxc.rootfs.backend", false);
763429b6 3157
eee59f94
SH
3158 if (flags & LXC_CLONE_SNAPSHOT)
3159 copy_rdepends(c, c0);
dfb31b25
SH
3160 if (need_rdep) {
3161 if (!add_rdepends(c, c0))
3162 WARN("Error adding reverse dependency from %s to %s",
763429b6 3163 c->name, c0->name);
dfb31b25
SH
3164 }
3165
3166 mod_all_rdeps(c, true);
3167
9be53773
SH
3168 return 0;
3169}
3170
1354955b
SH
3171struct clone_update_data {
3172 struct lxc_container *c0;
3173 struct lxc_container *c1;
3174 int flags;
3175 char **hookargs;
3176};
3177
3178static int clone_update_rootfs(struct clone_update_data *data)
9be53773 3179{
1354955b
SH
3180 struct lxc_container *c0 = data->c0;
3181 struct lxc_container *c = data->c1;
3182 int flags = data->flags;
3183 char **hookargs = data->hookargs;
9be53773
SH
3184 int ret = -1;
3185 char path[MAXPATHLEN];
3186 struct bdev *bdev;
3187 FILE *fout;
148e91f5 3188 struct lxc_conf *conf = c->lxc_conf;
9be53773
SH
3189
3190 /* update hostname in rootfs */
3191 /* we're going to mount, so run in a clean namespace to simplify cleanup */
3192
1354955b
SH
3193 if (setgid(0) < 0) {
3194 ERROR("Failed to setgid to 0");
3195 return -1;
3196 }
3197 if (setuid(0) < 0) {
3198 ERROR("Failed to setuid to 0");
9be53773 3199 return -1;
1354955b 3200 }
c476bdce
SH
3201 if (setgroups(0, NULL) < 0)
3202 WARN("Failed to clear groups");
9be53773 3203
1354955b
SH
3204 if (unshare(CLONE_NEWNS) < 0)
3205 return -1;
76a26f55 3206 bdev = bdev_init(c->lxc_conf, c->lxc_conf->rootfs.path, c->lxc_conf->rootfs.mount, NULL);
9be53773 3207 if (!bdev)
1354955b 3208 return -1;
cf3ef16d
SH
3209 if (strcmp(bdev->type, "dir") != 0) {
3210 if (unshare(CLONE_NEWNS) < 0) {
3211 ERROR("error unsharing mounts");
e7de366c 3212 bdev_put(bdev);
1354955b 3213 return -1;
cf3ef16d 3214 }
2c6f3fc9
SH
3215 if (detect_shared_rootfs()) {
3216 if (mount(NULL, "/", NULL, MS_SLAVE|MS_REC, NULL)) {
3217 SYSERROR("Failed to make / rslave");
3218 ERROR("Continuing...");
3219 }
3220 }
e7de366c
SG
3221 if (bdev->ops->mount(bdev) < 0) {
3222 bdev_put(bdev);
1354955b 3223 return -1;
e7de366c 3224 }
cf3ef16d 3225 } else { // TODO come up with a better way
f10fad2f 3226 free(bdev->dest);
cf3ef16d
SH
3227 bdev->dest = strdup(bdev->src);
3228 }
148e91f5
SH
3229
3230 if (!lxc_list_empty(&conf->hooks[LXCHOOK_CLONE])) {
3231 /* Start of environment variable setup for hooks */
ab7efcf5 3232 if (c0->name && setenv("LXC_SRC_NAME", c0->name, 1)) {
1143ed39
DE
3233 SYSERROR("failed to set environment variable for source container name");
3234 }
ab7efcf5 3235 if (c->name && setenv("LXC_NAME", c->name, 1)) {
148e91f5
SH
3236 SYSERROR("failed to set environment variable for container name");
3237 }
ab7efcf5 3238 if (conf->rcfile && setenv("LXC_CONFIG_FILE", conf->rcfile, 1)) {
148e91f5
SH
3239 SYSERROR("failed to set environment variable for config path");
3240 }
ab7efcf5 3241 if (bdev->dest && setenv("LXC_ROOTFS_MOUNT", bdev->dest, 1)) {
148e91f5
SH
3242 SYSERROR("failed to set environment variable for rootfs mount");
3243 }
ab7efcf5 3244 if (conf->rootfs.path && setenv("LXC_ROOTFS_PATH", conf->rootfs.path, 1)) {
148e91f5
SH
3245 SYSERROR("failed to set environment variable for rootfs mount");
3246 }
3247
283678ed 3248 if (run_lxc_hooks(c->name, "clone", conf, c->get_config_path(c), hookargs)) {
148e91f5 3249 ERROR("Error executing clone hook for %s", c->name);
e7de366c 3250 bdev_put(bdev);
1354955b 3251 return -1;
148e91f5
SH
3252 }
3253 }
3254
3255 if (!(flags & LXC_CLONE_KEEPNAME)) {
3256 ret = snprintf(path, MAXPATHLEN, "%s/etc/hostname", bdev->dest);
e7de366c
SG
3257 bdev_put(bdev);
3258
148e91f5 3259 if (ret < 0 || ret >= MAXPATHLEN)
1354955b 3260 return -1;
8058be39 3261 if (!file_exists(path))
1354955b 3262 return 0;
148e91f5 3263 if (!(fout = fopen(path, "w"))) {
959aee9c 3264 SYSERROR("unable to open %s: ignoring", path);
1354955b 3265 return 0;
148e91f5 3266 }
a684f0b7
ÇO
3267 if (fprintf(fout, "%s", c->name) < 0) {
3268 fclose(fout);
1354955b 3269 return -1;
6849cb5b 3270 }
148e91f5 3271 if (fclose(fout) < 0)
1354955b 3272 return -1;
9be53773 3273 }
e7de366c
SG
3274 else
3275 bdev_put(bdev);
3276
1354955b
SH
3277 return 0;
3278}
3279
3280static int clone_update_rootfs_wrapper(void *data)
3281{
3282 struct clone_update_data *arg = (struct clone_update_data *) data;
3283 return clone_update_rootfs(arg);
9be53773
SH
3284}
3285
3286/*
3287 * We want to support:
3288sudo lxc-clone -o o1 -n n1 -s -L|-fssize fssize -v|--vgname vgname \
3289 -p|--lvprefix lvprefix -t|--fstype fstype -B backingstore
3290
ba115175
CB
3291-s [ implies overlay]
3292-s -B overlay
9be53773
SH
3293-s -B aufs
3294
3295only rootfs gets converted (copied/snapshotted) on clone.
3296*/
3297
d5752559 3298static int create_file_dirname(char *path, struct lxc_conf *conf)
9be53773 3299{
c32981c3 3300 char *p = strrchr(path, '/');
d5752559 3301 int ret = -1;
9be53773
SH
3302
3303 if (!p)
3304 return -1;
3305 *p = '\0';
d028235d 3306 ret = do_create_container_dir(path, conf);
9be53773
SH
3307 *p = '/';
3308 return ret;
3309}
3310
858377e4 3311static struct lxc_container *do_lxcapi_clone(struct lxc_container *c, const char *newname,
9be53773 3312 const char *lxcpath, int flags,
d659597e 3313 const char *bdevtype, const char *bdevdata, uint64_t newsize,
148e91f5 3314 char **hookargs)
9be53773
SH
3315{
3316 struct lxc_container *c2 = NULL;
3317 char newpath[MAXPATHLEN];
176d9acb 3318 int ret, storage_copied = 0;
5eea90e8 3319 char *origroot = NULL, *saved_unexp_conf = NULL;
1354955b 3320 struct clone_update_data data;
3b392519 3321 size_t saved_unexp_len;
9be53773 3322 FILE *fout;
1354955b 3323 pid_t pid;
9be53773 3324
858377e4 3325 if (!c || !do_lxcapi_is_defined(c))
9be53773
SH
3326 return NULL;
3327
5cee8c50 3328 if (container_mem_lock(c))
9be53773
SH
3329 return NULL;
3330
39dc698c 3331 if (!is_stopped(c)) {
9be53773
SH
3332 ERROR("error: Original container (%s) is running", c->name);
3333 goto out;
3334 }
3335
3336 // Make sure the container doesn't yet exist.
05d53f4c
SH
3337 if (!newname)
3338 newname = c->name;
3339 if (!lxcpath)
858377e4 3340 lxcpath = do_lxcapi_get_config_path(c);
05d53f4c 3341 ret = snprintf(newpath, MAXPATHLEN, "%s/%s/config", lxcpath, newname);
6849cb5b 3342 if (ret < 0 || ret >= MAXPATHLEN) {
9be53773
SH
3343 SYSERROR("clone: failed making config pathname");
3344 goto out;
3345 }
3346 if (file_exists(newpath)) {
3347 ERROR("error: clone: %s exists", newpath);
3348 goto out;
3349 }
3350
d5752559 3351 ret = create_file_dirname(newpath, c->lxc_conf);
96532523 3352 if (ret < 0 && errno != EEXIST) {
9be53773
SH
3353 ERROR("Error creating container dir for %s", newpath);
3354 goto out;
3355 }
3356
3357 // copy the configuration, tweak it as needed,
8d2efe40
SH
3358 if (c->lxc_conf->rootfs.path) {
3359 origroot = c->lxc_conf->rootfs.path;
3360 c->lxc_conf->rootfs.path = NULL;
3361 }
9be53773
SH
3362 fout = fopen(newpath, "w");
3363 if (!fout) {
3364 SYSERROR("open %s", newpath);
3365 goto out;
3366 }
5eea90e8
SH
3367
3368 saved_unexp_conf = c->lxc_conf->unexpanded_config;
3b392519 3369 saved_unexp_len = c->lxc_conf->unexpanded_len;
5eea90e8
SH
3370 c->lxc_conf->unexpanded_config = strdup(saved_unexp_conf);
3371 if (!c->lxc_conf->unexpanded_config) {
3372 ERROR("Out of memory");
7d72b959 3373 fclose(fout);
5eea90e8
SH
3374 goto out;
3375 }
7a96a068
CB
3376
3377 /* REMOVE IN LXC 3.0
3378 * legacy rootfs key
3379 */
5eea90e8 3380 clear_unexp_config_line(c->lxc_conf, "lxc.rootfs", false);
7a96a068
CB
3381
3382 clear_unexp_config_line(c->lxc_conf, "lxc.rootfs.path", false);
6b0d5538 3383 write_config(fout, c->lxc_conf);
9be53773 3384 fclose(fout);
8d2efe40 3385 c->lxc_conf->rootfs.path = origroot;
5eea90e8
SH
3386 free(c->lxc_conf->unexpanded_config);
3387 c->lxc_conf->unexpanded_config = saved_unexp_conf;
3388 saved_unexp_conf = NULL;
3b392519 3389 c->lxc_conf->unexpanded_len = saved_unexp_len;
9be53773 3390
90b366fc
CB
3391 ret = snprintf(newpath, MAXPATHLEN, "%s/%s/rootfs", lxcpath, newname);
3392 if (ret < 0 || ret >= MAXPATHLEN) {
3393 SYSERROR("clone: failed making rootfs pathname");
3394 goto out;
3395 }
9be53773
SH
3396 if (mkdir(newpath, 0755) < 0) {
3397 SYSERROR("error creating %s", newpath);
3398 goto out;
3399 }
3400
1354955b
SH
3401 if (am_unpriv()) {
3402 if (chown_mapped_root(newpath, c->lxc_conf) < 0) {
959aee9c 3403 ERROR("Error chowning %s to container root", newpath);
1354955b
SH
3404 goto out;
3405 }
3406 }
3407
05d53f4c 3408 c2 = lxc_container_new(newname, lxcpath);
375c2258 3409 if (!c2) {
05d53f4c
SH
3410 ERROR("clone: failed to create new container (%s %s)", newname,
3411 lxcpath);
9be53773
SH
3412 goto out;
3413 }
8d2efe40
SH
3414
3415 // copy/snapshot rootfs's
3416 ret = copy_storage(c, c2, bdevtype, flags, bdevdata, newsize);
3417 if (ret < 0)
3418 goto out;
9be53773 3419
6b0d5538 3420
96532523 3421 // update utsname
3d7ad474
CB
3422 if (!(flags & LXC_CLONE_KEEPNAME)) {
3423 clear_unexp_config_line(c2->lxc_conf, "lxc.utsname", false);
b67771bc 3424 clear_unexp_config_line(c2->lxc_conf, "lxc.uts.name", false);
3d7ad474 3425
b67771bc 3426 if (!set_config_item_locked(c2, "lxc.uts.name", newname)) {
3d7ad474
CB
3427 ERROR("Error setting new hostname");
3428 goto out;
3429 }
96532523
SH
3430 }
3431
619256b5
ÇO
3432 // copy hooks
3433 ret = copyhooks(c, c2);
3434 if (ret < 0) {
3435 ERROR("error copying hooks");
3436 goto out;
9be53773
SH
3437 }
3438
3439 if (copy_fstab(c, c2) < 0) {
3440 ERROR("error copying fstab");
9be53773
SH
3441 goto out;
3442 }
3443
3444 // update macaddrs
6b0d5538 3445 if (!(flags & LXC_CLONE_KEEPMACADDR)) {
67702c21
SH
3446 if (!network_new_hwaddrs(c2->lxc_conf)) {
3447 ERROR("Error updating mac addresses");
6b0d5538
SH
3448 goto out;
3449 }
3450 }
9be53773 3451
030ce9a9 3452 // update absolute paths for overlay mount directories
83e79752 3453 if (ovl_update_abs_paths(c2->lxc_conf, c->config_path, c->name, lxcpath, newname) < 0)
030ce9a9
CB
3454 goto out;
3455
176d9acb
SH
3456 // We've now successfully created c2's storage, so clear it out if we
3457 // fail after this
3458 storage_copied = 1;
3459
375c2258 3460 if (!c2->save_config(c2, NULL))
9be53773 3461 goto out;
9be53773 3462
1354955b
SH
3463 if ((pid = fork()) < 0) {
3464 SYSERROR("fork");
9be53773 3465 goto out;
1354955b
SH
3466 }
3467 if (pid > 0) {
3468 ret = wait_for_pid(pid);
3469 if (ret)
3470 goto out;
3471 container_mem_unlock(c);
3472 return c2;
3473 }
3474 data.c0 = c;
3475 data.c1 = c2;
3476 data.flags = flags;
3477 data.hookargs = hookargs;
3478 if (am_unpriv())
3479 ret = userns_exec_1(c->lxc_conf, clone_update_rootfs_wrapper,
c9b7c33e 3480 &data, "clone_update_rootfs_wrapper");
1354955b
SH
3481 else
3482 ret = clone_update_rootfs(&data);
3483 if (ret < 0)
3484 exit(1);
9be53773 3485
5cee8c50 3486 container_mem_unlock(c);
1354955b 3487 exit(0);
9be53773
SH
3488
3489out:
5cee8c50 3490 container_mem_unlock(c);
375c2258 3491 if (c2) {
176d9acb
SH
3492 if (!storage_copied)
3493 c2->lxc_conf->rootfs.path = NULL;
375c2258 3494 c2->destroy(c2);
9be53773 3495 lxc_container_put(c2);
375c2258 3496 }
9be53773
SH
3497
3498 return NULL;
3499}
3500
858377e4
SH
3501static struct lxc_container *lxcapi_clone(struct lxc_container *c, const char *newname,
3502 const char *lxcpath, int flags,
3503 const char *bdevtype, const char *bdevdata, uint64_t newsize,
3504 char **hookargs)
3505{
3506 struct lxc_container * ret;
3507 current_config = c ? c->lxc_conf : NULL;
3508 ret = do_lxcapi_clone(c, newname, lxcpath, flags, bdevtype, bdevdata, newsize, hookargs);
3509 current_config = NULL;
3510 return ret;
3511}
3512
3513static bool do_lxcapi_rename(struct lxc_container *c, const char *newname)
06e5650e
ÇO
3514{
3515 struct bdev *bdev;
3516 struct lxc_container *newc;
06e5650e 3517
d693cf93 3518 if (!c || !c->name || !c->config_path || !c->lxc_conf)
06e5650e
ÇO
3519 return false;
3520
18aa217b
SH
3521 if (has_fs_snapshots(c) || has_snapshots(c)) {
3522 ERROR("Renaming a container with snapshots is not supported");
3523 return false;
3524 }
76a26f55 3525 bdev = bdev_init(c->lxc_conf, c->lxc_conf->rootfs.path, c->lxc_conf->rootfs.mount, NULL);
06e5650e
ÇO
3526 if (!bdev) {
3527 ERROR("Failed to find original backing store type");
3528 return false;
3529 }
3530
619256b5 3531 newc = lxcapi_clone(c, newname, c->config_path, LXC_CLONE_KEEPMACADDR, NULL, bdev->type, 0, NULL);
06e5650e
ÇO
3532 bdev_put(bdev);
3533 if (!newc) {
3534 lxc_container_put(newc);
3535 return false;
3536 }
3537
3538 if (newc && lxcapi_is_defined(newc))
3539 lxc_container_put(newc);
3540
18aa217b 3541 if (!container_destroy(c)) {
06e5650e
ÇO
3542 ERROR("Could not destroy existing container %s", c->name);
3543 return false;
3544 }
3545 return true;
3546}
3547
858377e4
SH
3548WRAP_API_1(bool, lxcapi_rename, const char *)
3549
a0e93eeb
CS
3550static int lxcapi_attach(struct lxc_container *c, lxc_attach_exec_t exec_function, void *exec_payload, lxc_attach_options_t *options, pid_t *attached_process)
3551{
858377e4
SH
3552 int ret;
3553
a0e93eeb
CS
3554 if (!c)
3555 return -1;
3556
858377e4
SH
3557 current_config = c->lxc_conf;
3558
3559 ret = lxc_attach(c->name, c->config_path, exec_function, exec_payload, options, attached_process);
3560 current_config = NULL;
3561 return ret;
a0e93eeb
CS
3562}
3563
858377e4 3564static int do_lxcapi_attach_run_wait(struct lxc_container *c, lxc_attach_options_t *options, const char *program, const char * const argv[])
a0e93eeb
CS
3565{
3566 lxc_attach_command_t command;
3567 pid_t pid;
3568 int r;
3569
3570 if (!c)
3571 return -1;
3572
3573 command.program = (char*)program;
3574 command.argv = (char**)argv;
3575 r = lxc_attach(c->name, c->config_path, lxc_attach_run_command, &command, options, &pid);
3576 if (r < 0) {
3577 ERROR("ups");
3578 return r;
3579 }
3580 return lxc_wait_for_pid_status(pid);
3581}
3582
858377e4
SH
3583static int lxcapi_attach_run_wait(struct lxc_container *c, lxc_attach_options_t *options, const char *program, const char * const argv[])
3584{
3585 int ret;
3586 current_config = c ? c->lxc_conf : NULL;
3587 ret = do_lxcapi_attach_run_wait(c, options, program, argv);
3588 current_config = NULL;
3589 return ret;
3590}
3591
74a3920a 3592static int get_next_index(const char *lxcpath, char *cname)
f5dd1d53
SH
3593{
3594 char *fname;
3595 struct stat sb;
3596 int i = 0, ret;
3597
3598 fname = alloca(strlen(lxcpath) + 20);
3599 while (1) {
3600 sprintf(fname, "%s/snap%d", lxcpath, i);
3601 ret = stat(fname, &sb);
3602 if (ret != 0)
3603 return i;
3604 i++;
3605 }
3606}
3607
18aa217b
SH
3608static bool get_snappath_dir(struct lxc_container *c, char *snappath)
3609{
3610 int ret;
3611 /*
3612 * If the old style snapshot path exists, use it
3613 * /var/lib/lxc -> /var/lib/lxcsnaps
3614 */
3615 ret = snprintf(snappath, MAXPATHLEN, "%ssnaps", c->config_path);
3616 if (ret < 0 || ret >= MAXPATHLEN)
3617 return false;
3618 if (dir_exists(snappath)) {
3619 ret = snprintf(snappath, MAXPATHLEN, "%ssnaps/%s", c->config_path, c->name);
3620 if (ret < 0 || ret >= MAXPATHLEN)
3621 return false;
3622 return true;
3623 }
3624
3625 /*
3626 * Use the new style path
3627 * /var/lib/lxc -> /var/lib/lxc + c->name + /snaps + \0
3628 */
3629 ret = snprintf(snappath, MAXPATHLEN, "%s/%s/snaps", c->config_path, c->name);
3630 if (ret < 0 || ret >= MAXPATHLEN)
3631 return false;
3632 return true;
3633}
3634
858377e4 3635static int do_lxcapi_snapshot(struct lxc_container *c, const char *commentfile)
f5dd1d53
SH
3636{
3637 int i, flags, ret;
3638 struct lxc_container *c2;
3639 char snappath[MAXPATHLEN], newname[20];
3640
840f05df
SH
3641 if (!c || !lxcapi_is_defined(c))
3642 return -1;
3643
cdd01be2
SH
3644 if (!bdev_can_backup(c->lxc_conf)) {
3645 ERROR("%s's backing store cannot be backed up.", c->name);
3646 ERROR("Your container must use another backing store type.");
3647 return -1;
3648 }
3649
18aa217b 3650 if (!get_snappath_dir(c, snappath))
f5dd1d53 3651 return -1;
18aa217b 3652
f5dd1d53
SH
3653 i = get_next_index(snappath, c->name);
3654
3655 if (mkdir_p(snappath, 0755) < 0) {
3656 ERROR("Failed to create snapshot directory %s", snappath);
3657 return -1;
3658 }
3659
3660 ret = snprintf(newname, 20, "snap%d", i);
3661 if (ret < 0 || ret >= 20)
3662 return -1;
3663
0a83cbbb
SH
3664 /*
3665 * We pass LXC_CLONE_SNAPSHOT to make sure that a rdepends file entry is
3666 * created in the original container
3667 */
3668 flags = LXC_CLONE_SNAPSHOT | LXC_CLONE_KEEPMACADDR | LXC_CLONE_KEEPNAME |
3669 LXC_CLONE_KEEPBDEVTYPE | LXC_CLONE_MAYBE_SNAPSHOT;
76a26f55 3670 if (bdev_is_dir(c->lxc_conf, c->lxc_conf->rootfs.path)) {
8c39f7a4
SH
3671 ERROR("Snapshot of directory-backed container requested.");
3672 ERROR("Making a copy-clone. If you do want snapshots, then");
ba115175 3673 ERROR("please create an aufs or overlay clone first, snapshot that");
8c39f7a4
SH
3674 ERROR("and keep the original container pristine.");
3675 flags &= ~LXC_CLONE_SNAPSHOT | LXC_CLONE_MAYBE_SNAPSHOT;
3676 }
858377e4 3677 c2 = do_lxcapi_clone(c, newname, snappath, flags, NULL, NULL, 0, NULL);
f5dd1d53 3678 if (!c2) {
959aee9c 3679 ERROR("clone of %s:%s failed", c->config_path, c->name);
f5dd1d53
SH
3680 return -1;
3681 }
3682
3683 lxc_container_put(c2);
3684
3685 // Now write down the creation time
3686 time_t timer;
3687 char buffer[25];
3688 struct tm* tm_info;
025ed0f3 3689 FILE *f;
f5dd1d53
SH
3690
3691 time(&timer);
3692 tm_info = localtime(&timer);
3693
3694 strftime(buffer, 25, "%Y:%m:%d %H:%M:%S", tm_info);
3695
3696 char *dfnam = alloca(strlen(snappath) + strlen(newname) + 5);
3697 sprintf(dfnam, "%s/%s/ts", snappath, newname);
025ed0f3 3698 f = fopen(dfnam, "w");
f5dd1d53 3699 if (!f) {
959aee9c 3700 ERROR("Failed to open %s", dfnam);
f5dd1d53
SH
3701 return -1;
3702 }
3703 if (fprintf(f, "%s", buffer) < 0) {
3704 SYSERROR("Writing timestamp");
3705 fclose(f);
3706 return -1;
3707 }
025ed0f3 3708 ret = fclose(f);
025ed0f3 3709 if (ret != 0) {
f5dd1d53
SH
3710 SYSERROR("Writing timestamp");
3711 return -1;
3712 }
3713
3714 if (commentfile) {
3715 // $p / $name / comment \0
3716 int len = strlen(snappath) + strlen(newname) + 10;
3717 char *path = alloca(len);
3718 sprintf(path, "%s/%s/comment", snappath, newname);
3719 return copy_file(commentfile, path) < 0 ? -1 : i;
3720 }
3721
3722 return i;
3723}
3724
858377e4
SH
3725WRAP_API_1(int, lxcapi_snapshot, const char *)
3726
f5dd1d53
SH
3727static void lxcsnap_free(struct lxc_snapshot *s)
3728{
f10fad2f
ME
3729 free(s->name);
3730 free(s->comment_pathname);
3731 free(s->timestamp);
3732 free(s->lxcpath);
f5dd1d53
SH
3733}
3734
3735static char *get_snapcomment_path(char* snappath, char *name)
3736{
3737 // $snappath/$name/comment
3738 int ret, len = strlen(snappath) + strlen(name) + 10;
3739 char *s = malloc(len);
3740
3741 if (s) {
3742 ret = snprintf(s, len, "%s/%s/comment", snappath, name);
3743 if (ret < 0 || ret >= len) {
3744 free(s);
3745 s = NULL;
3746 }
3747 }
3748 return s;
3749}
3750
3751static char *get_timestamp(char* snappath, char *name)
3752{
3753 char path[MAXPATHLEN], *s = NULL;
3754 int ret, len;
3755 FILE *fin;
3756
3757 ret = snprintf(path, MAXPATHLEN, "%s/%s/ts", snappath, name);
3758 if (ret < 0 || ret >= MAXPATHLEN)
3759 return NULL;
025ed0f3 3760 fin = fopen(path, "r");
025ed0f3 3761 if (!fin)
f5dd1d53
SH
3762 return NULL;
3763 (void) fseek(fin, 0, SEEK_END);
3764 len = ftell(fin);
3765 (void) fseek(fin, 0, SEEK_SET);
3766 if (len > 0) {
3767 s = malloc(len+1);
3768 if (s) {
3769 s[len] = '\0';
3770 if (fread(s, 1, len, fin) != len) {
3771 SYSERROR("reading timestamp");
3772 free(s);
3773 s = NULL;
3774 }
3775 }
3776 }
3777 fclose(fin);
3778 return s;
3779}
3780
858377e4 3781static int do_lxcapi_snapshot_list(struct lxc_container *c, struct lxc_snapshot **ret_snaps)
f5dd1d53
SH
3782{
3783 char snappath[MAXPATHLEN], path2[MAXPATHLEN];
18aa217b 3784 int count = 0, ret;
74f96976 3785 struct dirent *direntp;
f5dd1d53
SH
3786 struct lxc_snapshot *snaps =NULL, *nsnaps;
3787 DIR *dir;
3788
3789 if (!c || !lxcapi_is_defined(c))
3790 return -1;
c868b261 3791
18aa217b 3792 if (!get_snappath_dir(c, snappath)) {
f5dd1d53
SH
3793 ERROR("path name too long");
3794 return -1;
3795 }
025ed0f3 3796 dir = opendir(snappath);
025ed0f3 3797 if (!dir) {
f5dd1d53
SH
3798 INFO("failed to open %s - assuming no snapshots", snappath);
3799 return 0;
3800 }
3801
74f96976 3802 while ((direntp = readdir(dir))) {
f5dd1d53
SH
3803 if (!direntp)
3804 break;
3805
3806 if (!strcmp(direntp->d_name, "."))
3807 continue;
3808
3809 if (!strcmp(direntp->d_name, ".."))
3810 continue;
3811
3812 ret = snprintf(path2, MAXPATHLEN, "%s/%s/config", snappath, direntp->d_name);
3813 if (ret < 0 || ret >= MAXPATHLEN) {
3814 ERROR("pathname too long");
3815 goto out_free;
3816 }
3817 if (!file_exists(path2))
3818 continue;
3819 nsnaps = realloc(snaps, (count + 1)*sizeof(*snaps));
3820 if (!nsnaps) {
3821 SYSERROR("Out of memory");
3822 goto out_free;
3823 }
3824 snaps = nsnaps;
3825 snaps[count].free = lxcsnap_free;
3826 snaps[count].name = strdup(direntp->d_name);
3827 if (!snaps[count].name)
3828 goto out_free;
3829 snaps[count].lxcpath = strdup(snappath);
3830 if (!snaps[count].lxcpath) {
3831 free(snaps[count].name);
3832 goto out_free;
3833 }
3834 snaps[count].comment_pathname = get_snapcomment_path(snappath, direntp->d_name);
3835 snaps[count].timestamp = get_timestamp(snappath, direntp->d_name);
3836 count++;
3837 }
3838
3839 if (closedir(dir))
3840 WARN("failed to close directory");
3841
3842 *ret_snaps = snaps;
3843 return count;
3844
3845out_free:
3846 if (snaps) {
3847 int i;
3848 for (i=0; i<count; i++)
3849 lxcsnap_free(&snaps[i]);
3850 free(snaps);
3851 }
9baa57bd
SH
3852 if (closedir(dir))
3853 WARN("failed to close directory");
f5dd1d53
SH
3854 return -1;
3855}
3856
858377e4
SH
3857WRAP_API_1(int, lxcapi_snapshot_list, struct lxc_snapshot **)
3858
3859static bool do_lxcapi_snapshot_restore(struct lxc_container *c, const char *snapname, const char *newname)
f5dd1d53
SH
3860{
3861 char clonelxcpath[MAXPATHLEN];
18aa217b 3862 int flags = 0;
f5dd1d53
SH
3863 struct lxc_container *snap, *rest;
3864 struct bdev *bdev;
3865 bool b = false;
3866
3867 if (!c || !c->name || !c->config_path)
3868 return false;
3869
18aa217b
SH
3870 if (has_fs_snapshots(c)) {
3871 ERROR("container rootfs has dependent snapshots");
3872 return false;
3873 }
3874
76a26f55 3875 bdev = bdev_init(c->lxc_conf, c->lxc_conf->rootfs.path, c->lxc_conf->rootfs.mount, NULL);
f5dd1d53
SH
3876 if (!bdev) {
3877 ERROR("Failed to find original backing store type");
3878 return false;
3879 }
3880
3881 if (!newname)
3882 newname = c->name;
7e36f87e 3883
18aa217b 3884 if (!get_snappath_dir(c, clonelxcpath)) {
f5dd1d53
SH
3885 bdev_put(bdev);
3886 return false;
3887 }
3888 // how should we lock this?
3889
3890 snap = lxc_container_new(snapname, clonelxcpath);
3891 if (!snap || !lxcapi_is_defined(snap)) {
3892 ERROR("Could not open snapshot %s", snapname);
3893 if (snap) lxc_container_put(snap);
3894 bdev_put(bdev);
3895 return false;
3896 }
3897
7e36f87e 3898 if (strcmp(c->name, newname) == 0) {
18aa217b 3899 if (!container_destroy(c)) {
7e36f87e
ÇO
3900 ERROR("Could not destroy existing container %s", newname);
3901 lxc_container_put(snap);
3902 bdev_put(bdev);
3903 return false;
3904 }
3905 }
3906
de269ee8
SH
3907 if (strcmp(bdev->type, "dir") != 0 && strcmp(bdev->type, "loop") != 0)
3908 flags = LXC_CLONE_SNAPSHOT | LXC_CLONE_MAYBE_SNAPSHOT;
3909 rest = lxcapi_clone(snap, newname, c->config_path, flags,
3910 bdev->type, NULL, 0, NULL);
f5dd1d53
SH
3911 bdev_put(bdev);
3912 if (rest && lxcapi_is_defined(rest))
3913 b = true;
3914 if (rest)
3915 lxc_container_put(rest);
3916 lxc_container_put(snap);
3917 return b;
3918}
3919
858377e4
SH
3920WRAP_API_2(bool, lxcapi_snapshot_restore, const char *, const char *)
3921
18aa217b 3922static bool do_snapshot_destroy(const char *snapname, const char *clonelxcpath)
771d96b3 3923{
771d96b3 3924 struct lxc_container *snap = NULL;
18aa217b 3925 bool bret = false;
771d96b3
ÇO
3926
3927 snap = lxc_container_new(snapname, clonelxcpath);
18aa217b 3928 if (!snap) {
771d96b3
ÇO
3929 ERROR("Could not find snapshot %s", snapname);
3930 goto err;
3931 }
3932
858377e4 3933 if (!do_lxcapi_destroy(snap)) {
771d96b3
ÇO
3934 ERROR("Could not destroy snapshot %s", snapname);
3935 goto err;
3936 }
18aa217b 3937 bret = true;
771d96b3 3938
771d96b3
ÇO
3939err:
3940 if (snap)
3941 lxc_container_put(snap);
18aa217b
SH
3942 return bret;
3943}
3944
3945static bool remove_all_snapshots(const char *path)
3946{
3947 DIR *dir;
74f96976 3948 struct dirent *direntp;
18aa217b
SH
3949 bool bret = true;
3950
3951 dir = opendir(path);
3952 if (!dir) {
3953 SYSERROR("opendir on snapshot path %s", path);
3954 return false;
3955 }
74f96976 3956 while ((direntp = readdir(dir))) {
18aa217b
SH
3957 if (!direntp)
3958 break;
3959 if (!strcmp(direntp->d_name, "."))
3960 continue;
3961 if (!strcmp(direntp->d_name, ".."))
3962 continue;
3963 if (!do_snapshot_destroy(direntp->d_name, path)) {
3964 bret = false;
3965 continue;
3966 }
3967 }
3968
3969 closedir(dir);
3970
3971 if (rmdir(path))
3972 SYSERROR("Error removing directory %s", path);
3973
3974 return bret;
3975}
3976
858377e4 3977static bool do_lxcapi_snapshot_destroy(struct lxc_container *c, const char *snapname)
18aa217b
SH
3978{
3979 char clonelxcpath[MAXPATHLEN];
3980
3981 if (!c || !c->name || !c->config_path || !snapname)
3982 return false;
3983
3984 if (!get_snappath_dir(c, clonelxcpath))
3985 return false;
3986
3987 return do_snapshot_destroy(snapname, clonelxcpath);
3988}
3989
858377e4
SH
3990WRAP_API_1(bool, lxcapi_snapshot_destroy, const char *)
3991
3992static bool do_lxcapi_snapshot_destroy_all(struct lxc_container *c)
18aa217b
SH
3993{
3994 char clonelxcpath[MAXPATHLEN];
3995
3996 if (!c || !c->name || !c->config_path)
3997 return false;
3998
3999 if (!get_snappath_dir(c, clonelxcpath))
4000 return false;
4001
4002 return remove_all_snapshots(clonelxcpath);
771d96b3
ÇO
4003}
4004
858377e4
SH
4005WRAP_API(bool, lxcapi_snapshot_destroy_all)
4006
4007static bool do_lxcapi_may_control(struct lxc_container *c)
b494d2dd
SH
4008{
4009 return lxc_try_cmd(c->name, c->config_path) == 0;
4010}
4011
858377e4
SH
4012WRAP_API(bool, lxcapi_may_control)
4013
d5aa23e6
SH
4014static bool do_add_remove_node(pid_t init_pid, const char *path, bool add,
4015 struct stat *st)
4016{
4017 char chrootpath[MAXPATHLEN];
4018 char *directory_path = NULL;
4019 pid_t pid;
4020 int ret;
4021
4022 if ((pid = fork()) < 0) {
4023 SYSERROR("failed to fork a child helper");
4024 return false;
4025 }
4026 if (pid) {
4027 if (wait_for_pid(pid) != 0) {
4028 ERROR("Failed to create note in guest");
4029 return false;
4030 }
4031 return true;
4032 }
4033
4034 /* prepare the path */
4035 ret = snprintf(chrootpath, MAXPATHLEN, "/proc/%d/root", init_pid);
4036 if (ret < 0 || ret >= MAXPATHLEN)
4037 return false;
4038
6b9324bd 4039 if (chroot(chrootpath) < 0)
d5aa23e6 4040 exit(1);
6b9324bd 4041 if (chdir("/") < 0)
d5aa23e6
SH
4042 exit(1);
4043 /* remove path if it exists */
4044 if(faccessat(AT_FDCWD, path, F_OK, AT_SYMLINK_NOFOLLOW) == 0) {
4045 if (unlink(path) < 0) {
4046 ERROR("unlink failed");
4047 exit(1);
4048 }
4049 }
4050 if (!add)
4051 exit(0);
4052
4053 /* create any missing directories */
4054 directory_path = dirname(strdup(path));
4055 if (mkdir_p(directory_path, 0755) < 0 && errno != EEXIST) {
4056 ERROR("failed to create directory");
4057 exit(1);
4058 }
4059
4060 /* create the device node */
4061 if (mknod(path, st->st_mode, st->st_rdev) < 0) {
4062 ERROR("mknod failed");
4063 exit(1);
4064 }
4065
4066 exit(0);
4067}
4068
f0ca2726 4069static bool add_remove_device_node(struct lxc_container *c, const char *src_path, const char *dest_path, bool add)
a9a0ed90
ÇO
4070{
4071 int ret;
4072 struct stat st;
a9a0ed90 4073 char value[MAX_BUFFER];
f0ca2726 4074 const char *p;
a9a0ed90
ÇO
4075
4076 /* make sure container is running */
858377e4 4077 if (!do_lxcapi_is_running(c)) {
a9a0ed90 4078 ERROR("container is not running");
d5aa23e6 4079 return false;
a9a0ed90
ÇO
4080 }
4081
4082 /* use src_path if dest_path is NULL otherwise use dest_path */
4083 p = dest_path ? dest_path : src_path;
4084
a9a0ed90
ÇO
4085 /* make sure we can access p */
4086 if(access(p, F_OK) < 0 || stat(p, &st) < 0)
d5aa23e6 4087 return false;
a9a0ed90
ÇO
4088
4089 /* continue if path is character device or block device */
c6a9b0d7 4090 if (S_ISCHR(st.st_mode))
a9a0ed90 4091 ret = snprintf(value, MAX_BUFFER, "c %d:%d rwm", major(st.st_rdev), minor(st.st_rdev));
c6a9b0d7 4092 else if (S_ISBLK(st.st_mode))
a9a0ed90
ÇO
4093 ret = snprintf(value, MAX_BUFFER, "b %d:%d rwm", major(st.st_rdev), minor(st.st_rdev));
4094 else
d5aa23e6 4095 return false;
a9a0ed90
ÇO
4096
4097 /* check snprintf return code */
4098 if (ret < 0 || ret >= MAX_BUFFER)
d5aa23e6 4099 return false;
a9a0ed90 4100
858377e4 4101 if (!do_add_remove_node(do_lxcapi_init_pid(c), p, add, &st))
d5aa23e6 4102 return false;
a9a0ed90 4103
d5aa23e6 4104 /* add or remove device to/from cgroup access list */
a9a0ed90 4105 if (add) {
858377e4 4106 if (!do_lxcapi_set_cgroup_item(c, "devices.allow", value)) {
a9a0ed90 4107 ERROR("set_cgroup_item failed while adding the device node");
d5aa23e6 4108 return false;
a9a0ed90
ÇO
4109 }
4110 } else {
858377e4 4111 if (!do_lxcapi_set_cgroup_item(c, "devices.deny", value)) {
a9a0ed90 4112 ERROR("set_cgroup_item failed while removing the device node");
d5aa23e6 4113 return false;
a9a0ed90
ÇO
4114 }
4115 }
d5aa23e6 4116
a9a0ed90 4117 return true;
a9a0ed90
ÇO
4118}
4119
858377e4 4120static bool do_lxcapi_add_device_node(struct lxc_container *c, const char *src_path, const char *dest_path)
a9a0ed90 4121{
c868b261
ÇO
4122 if (am_unpriv()) {
4123 ERROR(NOT_SUPPORTED_ERROR, __FUNCTION__);
4124 return false;
4125 }
a9a0ed90
ÇO
4126 return add_remove_device_node(c, src_path, dest_path, true);
4127}
4128
858377e4
SH
4129WRAP_API_2(bool, lxcapi_add_device_node, const char *, const char *)
4130
4131static bool do_lxcapi_remove_device_node(struct lxc_container *c, const char *src_path, const char *dest_path)
a9a0ed90 4132{
c868b261
ÇO
4133 if (am_unpriv()) {
4134 ERROR(NOT_SUPPORTED_ERROR, __FUNCTION__);
4135 return false;
4136 }
a9a0ed90
ÇO
4137 return add_remove_device_node(c, src_path, dest_path, false);
4138}
4139
858377e4
SH
4140WRAP_API_2(bool, lxcapi_remove_device_node, const char *, const char *)
4141
4142static bool do_lxcapi_attach_interface(struct lxc_container *c, const char *ifname,
e58fae8f
DY
4143 const char *dst_ifname)
4144{
4145 int ret = 0;
4146 if (am_unpriv()) {
4147 ERROR(NOT_SUPPORTED_ERROR, __FUNCTION__);
4148 return false;
4149 }
4150
4151 if (!ifname) {
4152 ERROR("No source interface name given");
4153 return false;
4154 }
4155
4156 ret = lxc_netdev_isup(ifname);
e58fae8f 4157
e5848d39
SH
4158 if (ret > 0) {
4159 /* netdev of ifname is up. */
e58fae8f
DY
4160 ret = lxc_netdev_down(ifname);
4161 if (ret)
4162 goto err;
4163 }
4164
858377e4 4165 ret = lxc_netdev_move_by_name(ifname, do_lxcapi_init_pid(c), dst_ifname);
e58fae8f
DY
4166 if (ret)
4167 goto err;
4168
4169 return true;
e5848d39 4170
e58fae8f 4171err:
e58fae8f
DY
4172 return false;
4173}
4174
858377e4
SH
4175WRAP_API_2(bool, lxcapi_attach_interface, const char *, const char *)
4176
4177static bool do_lxcapi_detach_interface(struct lxc_container *c, const char *ifname,
e58fae8f
DY
4178 const char *dst_ifname)
4179{
4180 pid_t pid, pid_outside;
4181
4182 if (am_unpriv()) {
4183 ERROR(NOT_SUPPORTED_ERROR, __FUNCTION__);
4184 return false;
4185 }
4186
4187 if (!ifname) {
4188 ERROR("No source interface name given");
4189 return false;
4190 }
4191
4192 pid_outside = getpid();
4193 pid = fork();
4194 if (pid < 0) {
4195 ERROR("failed to fork task to get interfaces information");
4196 return false;
4197 }
4198
4199 if (pid == 0) { // child
4200 int ret = 0;
e0f59189 4201 if (!enter_net_ns(c)) {
e58fae8f
DY
4202 ERROR("failed to enter namespace");
4203 exit(-1);
4204 }
4205
4206 ret = lxc_netdev_isup(ifname);
4207 if (ret < 0)
4208 exit(ret);
4209
4210 /* netdev of ifname is up. */
4211 if (ret) {
4212 ret = lxc_netdev_down(ifname);
4213 if (ret)
4214 exit(ret);
4215 }
4216
4217 ret = lxc_netdev_move_by_name(ifname, pid_outside, dst_ifname);
4218
4219 /* -EINVAL means there is no netdev named as ifanme. */
4220 if (ret == -EINVAL) {
4221 ERROR("No network device named as %s.", ifname);
4222 }
4223 exit(ret);
4224 }
4225
4226 if (wait_for_pid(pid) != 0)
4227 return false;
4228
4229 return true;
4230}
4231
858377e4
SH
4232WRAP_API_2(bool, lxcapi_detach_interface, const char *, const char *)
4233
aef3d51e
TA
4234static int do_lxcapi_migrate(struct lxc_container *c, unsigned int cmd,
4235 struct migrate_opts *opts, unsigned int size)
bbd4e13e 4236{
aef3d51e 4237 int ret;
2cb80427 4238 struct migrate_opts *valid_opts = opts;
85c50991 4239
aef3d51e
TA
4240 /* If the caller has a bigger (newer) struct migrate_opts, let's make
4241 * sure that the stuff on the end is zero, i.e. that they didn't ask us
4242 * to do anything special.
4243 */
4244 if (size > sizeof(*opts)) {
4245 unsigned char *addr;
4246 unsigned char *end;
4247
4248 addr = (void *)opts + sizeof(*opts);
4249 end = (void *)opts + size;
4250 for (; addr < end; addr++) {
4251 if (*addr) {
4252 return -E2BIG;
4253 }
4254 }
85c50991
TA
4255 }
4256
2cb80427
TA
4257 /* If the caller has a smaller struct, let's zero out the end for them
4258 * so we don't accidentally use bits of it that they didn't know about
4259 * to initialize.
4260 */
4261 if (size < sizeof(*opts)) {
4262 valid_opts = malloc(sizeof(*opts));
4263 if (!valid_opts)
4264 return -ENOMEM;
4265
4266 memset(valid_opts, 0, sizeof(*opts));
4267 memcpy(valid_opts, opts, size);
4268 }
4269
aef3d51e
TA
4270 switch (cmd) {
4271 case MIGRATE_PRE_DUMP:
7ad13c91
TA
4272 if (!do_lxcapi_is_running(c)) {
4273 ERROR("container is not running");
4274 return false;
4275 }
2cb80427 4276 ret = !__criu_pre_dump(c, valid_opts);
aef3d51e
TA
4277 break;
4278 case MIGRATE_DUMP:
7ad13c91
TA
4279 if (!do_lxcapi_is_running(c)) {
4280 ERROR("container is not running");
4281 return false;
4282 }
2cb80427 4283 ret = !__criu_dump(c, valid_opts);
aef3d51e
TA
4284 break;
4285 case MIGRATE_RESTORE:
7ad13c91
TA
4286 if (do_lxcapi_is_running(c)) {
4287 ERROR("container is already running");
4288 return false;
4289 }
2cb80427 4290 ret = !__criu_restore(c, valid_opts);
aef3d51e
TA
4291 break;
4292 default:
4293 ERROR("invalid migrate command %u", cmd);
4294 ret = -EINVAL;
4295 }
735f2c6e 4296
f686506d
TA
4297 if (size < sizeof(*opts))
4298 free(valid_opts);
4299
aef3d51e
TA
4300 return ret;
4301}
735f2c6e 4302
aef3d51e 4303WRAP_API_3(int, lxcapi_migrate, unsigned int, struct migrate_opts *, unsigned int)
735f2c6e 4304
aef3d51e
TA
4305static bool do_lxcapi_checkpoint(struct lxc_container *c, char *directory, bool stop, bool verbose)
4306{
ebb088e1
AR
4307 struct migrate_opts opts;
4308
4309 memset(&opts, 0, sizeof(opts));
4310
4311 opts.directory = directory;
4312 opts.stop = stop;
4313 opts.verbose = verbose;
735f2c6e 4314
aef3d51e 4315 return !do_lxcapi_migrate(c, MIGRATE_DUMP, &opts, sizeof(opts));
735f2c6e
TA
4316}
4317
858377e4
SH
4318WRAP_API_3(bool, lxcapi_checkpoint, char *, bool, bool)
4319
4320static bool do_lxcapi_restore(struct lxc_container *c, char *directory, bool verbose)
c9d8f2ee 4321{
ebb088e1
AR
4322 struct migrate_opts opts;
4323
4324 memset(&opts, 0, sizeof(opts));
4325
4326 opts.directory = directory;
4327 opts.verbose = verbose;
c9d8f2ee 4328
aef3d51e 4329 return !do_lxcapi_migrate(c, MIGRATE_RESTORE, &opts, sizeof(opts));
735f2c6e
TA
4330}
4331
858377e4
SH
4332WRAP_API_2(bool, lxcapi_restore, char *, bool)
4333
a0e93eeb
CS
4334static int lxcapi_attach_run_waitl(struct lxc_container *c, lxc_attach_options_t *options, const char *program, const char *arg, ...)
4335{
4336 va_list ap;
4337 const char **argv;
4338 int ret;
4339
4340 if (!c)
4341 return -1;
4342
858377e4
SH
4343 current_config = c->lxc_conf;
4344
a0e93eeb
CS
4345 va_start(ap, arg);
4346 argv = lxc_va_arg_list_to_argv_const(ap, 1);
4347 va_end(ap);
4348
4349 if (!argv) {
4350 ERROR("Memory allocation error.");
858377e4
SH
4351 ret = -1;
4352 goto out;
a0e93eeb
CS
4353 }
4354 argv[0] = arg;
4355
858377e4 4356 ret = do_lxcapi_attach_run_wait(c, options, program, (const char * const *)argv);
a0e93eeb 4357 free((void*)argv);
858377e4
SH
4358out:
4359 current_config = NULL;
a0e93eeb
CS
4360 return ret;
4361}
4362
afeecbba 4363struct lxc_container *lxc_container_new(const char *name, const char *configpath)
72d0e1cb
SG
4364{
4365 struct lxc_container *c;
72d0e1cb 4366
18aa217b
SH
4367 if (!name)
4368 return NULL;
4369
72d0e1cb
SG
4370 c = malloc(sizeof(*c));
4371 if (!c) {
4372 fprintf(stderr, "failed to malloc lxc_container\n");
4373 return NULL;
4374 }
4375 memset(c, 0, sizeof(*c));
4376
afeecbba
SH
4377 if (configpath)
4378 c->config_path = strdup(configpath);
4379 else
593e8478 4380 c->config_path = strdup(lxc_global_config_value("lxc.lxcpath"));
afeecbba 4381
2a59a681 4382 if (!c->config_path) {
03fadd16 4383 fprintf(stderr, "Out of memory\n");
2a59a681
SH
4384 goto err;
4385 }
4386
f5dd1d53 4387 remove_trailing_slashes(c->config_path);
72d0e1cb
SG
4388 c->name = malloc(strlen(name)+1);
4389 if (!c->name) {
4390 fprintf(stderr, "Error allocating lxc_container name\n");
4391 goto err;
4392 }
4393 strcpy(c->name, name);
4394
4395 c->numthreads = 1;
df271a59 4396 if (!(c->slock = lxc_newlock(c->config_path, name))) {
72d0e1cb
SG
4397 fprintf(stderr, "failed to create lock\n");
4398 goto err;
4399 }
4400
df271a59 4401 if (!(c->privlock = lxc_newlock(NULL, NULL))) {
72d0e1cb
SG
4402 fprintf(stderr, "failed to alloc privlock\n");
4403 goto err;
4404 }
4405
afeecbba 4406 if (!set_config_filename(c)) {
72d0e1cb
SG
4407 fprintf(stderr, "Error allocating config file pathname\n");
4408 goto err;
4409 }
72d0e1cb 4410
bac806d1
SH
4411 if (file_exists(c->configfile) && !lxcapi_load_config(c, NULL))
4412 goto err;
72d0e1cb 4413
3e625e2d
SH
4414 if (ongoing_create(c) == 2) {
4415 ERROR("Error: %s creation was not completed", c->name);
18aa217b 4416 container_destroy(c);
4df7f012 4417 lxcapi_clear_config(c);
3e625e2d 4418 }
a2739df5 4419 c->daemonize = true;
72cf75fa 4420 c->pidfile = NULL;
3e625e2d 4421
72d0e1cb
SG
4422 // assign the member functions
4423 c->is_defined = lxcapi_is_defined;
4424 c->state = lxcapi_state;
4425 c->is_running = lxcapi_is_running;
4426 c->freeze = lxcapi_freeze;
4427 c->unfreeze = lxcapi_unfreeze;
0115f8fd 4428 c->console = lxcapi_console;
b5159817 4429 c->console_getfd = lxcapi_console_getfd;
72d0e1cb
SG
4430 c->init_pid = lxcapi_init_pid;
4431 c->load_config = lxcapi_load_config;
4432 c->want_daemonize = lxcapi_want_daemonize;
130a1888 4433 c->want_close_all_fds = lxcapi_want_close_all_fds;
72d0e1cb
SG
4434 c->start = lxcapi_start;
4435 c->startl = lxcapi_startl;
4436 c->stop = lxcapi_stop;
4437 c->config_file_name = lxcapi_config_file_name;
4438 c->wait = lxcapi_wait;
4439 c->set_config_item = lxcapi_set_config_item;
4440 c->destroy = lxcapi_destroy;
18aa217b 4441 c->destroy_with_snapshots = lxcapi_destroy_with_snapshots;
06e5650e 4442 c->rename = lxcapi_rename;
72d0e1cb
SG
4443 c->save_config = lxcapi_save_config;
4444 c->get_keys = lxcapi_get_keys;
4445 c->create = lxcapi_create;
4446 c->createl = lxcapi_createl;
4447 c->shutdown = lxcapi_shutdown;
3e625e2d 4448 c->reboot = lxcapi_reboot;
4df7f012 4449 c->clear_config = lxcapi_clear_config;
72d0e1cb
SG
4450 c->clear_config_item = lxcapi_clear_config_item;
4451 c->get_config_item = lxcapi_get_config_item;
8ac18377 4452 c->get_running_config_item = lxcapi_get_running_config_item;
794dd120
SH
4453 c->get_cgroup_item = lxcapi_get_cgroup_item;
4454 c->set_cgroup_item = lxcapi_set_cgroup_item;
2a59a681
SH
4455 c->get_config_path = lxcapi_get_config_path;
4456 c->set_config_path = lxcapi_set_config_path;
9be53773 4457 c->clone = lxcapi_clone;
799f29ab 4458 c->get_interfaces = lxcapi_get_interfaces;
9c83a661 4459 c->get_ips = lxcapi_get_ips;
a0e93eeb
CS
4460 c->attach = lxcapi_attach;
4461 c->attach_run_wait = lxcapi_attach_run_wait;
4462 c->attach_run_waitl = lxcapi_attach_run_waitl;
f5dd1d53
SH
4463 c->snapshot = lxcapi_snapshot;
4464 c->snapshot_list = lxcapi_snapshot_list;
4465 c->snapshot_restore = lxcapi_snapshot_restore;
771d96b3 4466 c->snapshot_destroy = lxcapi_snapshot_destroy;
18aa217b 4467 c->snapshot_destroy_all = lxcapi_snapshot_destroy_all;
b494d2dd 4468 c->may_control = lxcapi_may_control;
a9a0ed90
ÇO
4469 c->add_device_node = lxcapi_add_device_node;
4470 c->remove_device_node = lxcapi_remove_device_node;
e58fae8f
DY
4471 c->attach_interface = lxcapi_attach_interface;
4472 c->detach_interface = lxcapi_detach_interface;
735f2c6e
TA
4473 c->checkpoint = lxcapi_checkpoint;
4474 c->restore = lxcapi_restore;
aef3d51e 4475 c->migrate = lxcapi_migrate;
72d0e1cb 4476
72d0e1cb
SG
4477 return c;
4478
4479err:
4480 lxc_container_free(c);
4481 return NULL;
4482}
4483
4a7c7daa 4484int lxc_get_wait_states(const char **states)
72d0e1cb
SG
4485{
4486 int i;
4487
4488 if (states)
4489 for (i=0; i<MAX_STATE; i++)
4490 states[i] = lxc_state2str(i);
4491 return MAX_STATE;
4492}
a41f104b 4493
a41f104b
SH
4494/*
4495 * These next two could probably be done smarter with reusing a common function
4496 * with different iterators and tests...
4497 */
4498int list_defined_containers(const char *lxcpath, char ***names, struct lxc_container ***cret)
4499{
4500 DIR *dir;
4501 int i, cfound = 0, nfound = 0;
74f96976 4502 struct dirent *direntp;
a41f104b
SH
4503 struct lxc_container *c;
4504
4505 if (!lxcpath)
593e8478 4506 lxcpath = lxc_global_config_value("lxc.lxcpath");
a41f104b 4507
a41f104b 4508 dir = opendir(lxcpath);
a41f104b
SH
4509 if (!dir) {
4510 SYSERROR("opendir on lxcpath");
4511 return -1;
4512 }
4513
4514 if (cret)
4515 *cret = NULL;
4516 if (names)
4517 *names = NULL;
4518
74f96976 4519 while ((direntp = readdir(dir))) {
a41f104b
SH
4520 if (!direntp)
4521 break;
e4ebeab1
CALP
4522
4523 // Ignore '.', '..' and any hidden directory
4524 if (!strncmp(direntp->d_name, ".", 1))
a41f104b
SH
4525 continue;
4526
4527 if (!config_file_exists(lxcpath, direntp->d_name))
4528 continue;
4529
4530 if (names) {
9c88ff1f 4531 if (!add_to_array(names, direntp->d_name, cfound))
a41f104b
SH
4532 goto free_bad;
4533 }
4534 cfound++;
4535
4536 if (!cret) {
4537 nfound++;
4538 continue;
4539 }
4540
4541 c = lxc_container_new(direntp->d_name, lxcpath);
4542 if (!c) {
4543 INFO("Container %s:%s has a config but could not be loaded",
4544 lxcpath, direntp->d_name);
4545 if (names)
9c88ff1f
ÇO
4546 if(!remove_from_array(names, direntp->d_name, cfound--))
4547 goto free_bad;
a41f104b
SH
4548 continue;
4549 }
858377e4 4550 if (!do_lxcapi_is_defined(c)) {
a41f104b
SH
4551 INFO("Container %s:%s has a config but is not defined",
4552 lxcpath, direntp->d_name);
4553 if (names)
9c88ff1f
ÇO
4554 if(!remove_from_array(names, direntp->d_name, cfound--))
4555 goto free_bad;
a41f104b
SH
4556 lxc_container_put(c);
4557 continue;
4558 }
4559
2871830a 4560 if (!add_to_clist(cret, c, nfound, true)) {
a41f104b
SH
4561 lxc_container_put(c);
4562 goto free_bad;
4563 }
4564 nfound++;
4565 }
4566
a41f104b 4567 closedir(dir);
a41f104b
SH
4568 return nfound;
4569
4570free_bad:
4571 if (names && *names) {
4572 for (i=0; i<cfound; i++)
4573 free((*names)[i]);
4574 free(*names);
4575 }
4576 if (cret && *cret) {
4577 for (i=0; i<nfound; i++)
4578 lxc_container_put((*cret)[i]);
4579 free(*cret);
4580 }
a41f104b 4581 closedir(dir);
a41f104b
SH
4582 return -1;
4583}
4584
148a9d27
DE
4585int list_active_containers(const char *lxcpath, char ***nret,
4586 struct lxc_container ***cret)
a41f104b 4587{
148a9d27 4588 int i, ret = -1, cret_cnt = 0, ct_name_cnt = 0;
a41f104b
SH
4589 int lxcpath_len;
4590 char *line = NULL;
148a9d27 4591 char **ct_name = NULL;
a41f104b 4592 size_t len = 0;
97bc2422 4593 struct lxc_container *c = NULL;
88556fd7 4594 bool is_hashed;
a41f104b
SH
4595
4596 if (!lxcpath)
593e8478 4597 lxcpath = lxc_global_config_value("lxc.lxcpath");
a41f104b
SH
4598 lxcpath_len = strlen(lxcpath);
4599
4600 if (cret)
4601 *cret = NULL;
148a9d27
DE
4602 if (nret)
4603 *nret = NULL;
a41f104b 4604
a41f104b 4605 FILE *f = fopen("/proc/net/unix", "r");
a41f104b
SH
4606 if (!f)
4607 return -1;
4608
4609 while (getline(&line, &len, f) != -1) {
88556fd7 4610
0f8f9c8a 4611 char *p = strrchr(line, ' '), *p2;
a41f104b
SH
4612 if (!p)
4613 continue;
4614 p++;
4615 if (*p != 0x40)
4616 continue;
4617 p++;
88556fd7
ÇO
4618
4619 is_hashed = false;
4620 if (strncmp(p, lxcpath, lxcpath_len) == 0) {
4621 p += lxcpath_len;
4622 } else if (strncmp(p, "lxc/", 4) == 0) {
4623 p += 4;
4624 is_hashed = true;
4625 } else {
a41f104b 4626 continue;
88556fd7
ÇO
4627 }
4628
a41f104b
SH
4629 while (*p == '/')
4630 p++;
4631
4632 // Now p is the start of lxc_name
46cd2845 4633 p2 = strchr(p, '/');
a41f104b
SH
4634 if (!p2 || strncmp(p2, "/command", 8) != 0)
4635 continue;
4636 *p2 = '\0';
4637
88556fd7 4638 if (is_hashed) {
899a9f55
CB
4639 char *recvpath = lxc_cmd_get_lxcpath(p);
4640 if (!recvpath)
4641 continue;
4642 if (strncmp(lxcpath, recvpath, lxcpath_len) != 0)
88556fd7
ÇO
4643 continue;
4644 p = lxc_cmd_get_name(p);
4645 }
4646
148a9d27 4647 if (array_contains(&ct_name, p, ct_name_cnt))
9c88ff1f
ÇO
4648 continue;
4649
148a9d27
DE
4650 if (!add_to_array(&ct_name, p, ct_name_cnt))
4651 goto free_cret_list;
9c88ff1f 4652
148a9d27 4653 ct_name_cnt++;
a41f104b 4654
148a9d27 4655 if (!cret)
a41f104b 4656 continue;
a41f104b
SH
4657
4658 c = lxc_container_new(p, lxcpath);
4659 if (!c) {
4660 INFO("Container %s:%s is running but could not be loaded",
4661 lxcpath, p);
148a9d27 4662 remove_from_array(&ct_name, p, ct_name_cnt--);
a41f104b
SH
4663 continue;
4664 }
4665
4666 /*
4667 * If this is an anonymous container, then is_defined *can*
4668 * return false. So we don't do that check. Count on the
4669 * fact that the command socket exists.
4670 */
4671
148a9d27 4672 if (!add_to_clist(cret, c, cret_cnt, true)) {
a41f104b 4673 lxc_container_put(c);
148a9d27 4674 goto free_cret_list;
a41f104b 4675 }
148a9d27 4676 cret_cnt++;
a41f104b
SH
4677 }
4678
97bc2422
CB
4679 if (nret && cret && cret_cnt != ct_name_cnt) {
4680 if (c)
4681 lxc_container_put(c);
4682 goto free_cret_list;
4683 }
4684
148a9d27
DE
4685 ret = ct_name_cnt;
4686 if (nret)
4687 *nret = ct_name;
4688 else
4689 goto free_ct_name;
4690 goto out;
a41f104b 4691
148a9d27 4692free_cret_list:
a41f104b 4693 if (cret && *cret) {
148a9d27 4694 for (i = 0; i < cret_cnt; i++)
a41f104b
SH
4695 lxc_container_put((*cret)[i]);
4696 free(*cret);
4697 }
148a9d27
DE
4698
4699free_ct_name:
4700 if (ct_name) {
4701 for (i = 0; i < ct_name_cnt; i++)
4702 free(ct_name[i]);
4703 free(ct_name);
4704 }
4705
4706out:
f10fad2f 4707 free(line);
e853a32d 4708
a41f104b 4709 fclose(f);
148a9d27 4710 return ret;
a41f104b 4711}
2871830a
DE
4712
4713int list_all_containers(const char *lxcpath, char ***nret,
4714 struct lxc_container ***cret)
4715{
4716 int i, ret, active_cnt, ct_cnt, ct_list_cnt;
4717 char **active_name;
4718 char **ct_name;
4719 struct lxc_container **ct_list = NULL;
4720
4721 ct_cnt = list_defined_containers(lxcpath, &ct_name, NULL);
4722 if (ct_cnt < 0)
4723 return ct_cnt;
4724
4725 active_cnt = list_active_containers(lxcpath, &active_name, NULL);
4726 if (active_cnt < 0) {
4727 ret = active_cnt;
4728 goto free_ct_name;
4729 }
4730
4731 for (i = 0; i < active_cnt; i++) {
4732 if (!array_contains(&ct_name, active_name[i], ct_cnt)) {
4733 if (!add_to_array(&ct_name, active_name[i], ct_cnt)) {
4734 ret = -1;
4735 goto free_active_name;
4736 }
4737 ct_cnt++;
4738 }
4739 free(active_name[i]);
4740 active_name[i] = NULL;
4741 }
4742 free(active_name);
4743 active_name = NULL;
4744 active_cnt = 0;
4745
4746 for (i = 0, ct_list_cnt = 0; i < ct_cnt && cret; i++) {
4747 struct lxc_container *c;
4748
4749 c = lxc_container_new(ct_name[i], lxcpath);
4750 if (!c) {
4751 WARN("Container %s:%s could not be loaded", lxcpath, ct_name[i]);
4752 remove_from_array(&ct_name, ct_name[i], ct_cnt--);
4753 continue;
4754 }
4755
4756 if (!add_to_clist(&ct_list, c, ct_list_cnt, false)) {
4757 lxc_container_put(c);
4758 ret = -1;
4759 goto free_ct_list;
4760 }
4761 ct_list_cnt++;
4762 }
4763
4764 if (cret)
4765 *cret = ct_list;
4766
4767 if (nret)
4768 *nret = ct_name;
4769 else {
4770 ret = ct_cnt;
4771 goto free_ct_name;
4772 }
4773 return ct_cnt;
4774
4775free_ct_list:
4776 for (i = 0; i < ct_list_cnt; i++) {
4777 lxc_container_put(ct_list[i]);
4778 }
f10fad2f 4779 free(ct_list);
2871830a
DE
4780
4781free_active_name:
4782 for (i = 0; i < active_cnt; i++) {
f10fad2f 4783 free(active_name[i]);
2871830a 4784 }
f10fad2f 4785 free(active_name);
2871830a
DE
4786
4787free_ct_name:
4788 for (i = 0; i < ct_cnt; i++) {
4789 free(ct_name[i]);
4790 }
4791 free(ct_name);
4792 return ret;
4793}
12461428
CB
4794
4795bool lxc_config_item_is_supported(const char *key)
4796{
4797 return !!lxc_getconfig(key);
4798}