chiark / gitweb /
7a1b411c7b67f48f0221db6e43b4a152062aa66f
[elogind.git] / src / core / mount.c
1 /*-*- Mode: C; c-basic-offset: 8; indent-tabs-mode: nil -*-*/
2
3 /***
4   This file is part of systemd.
5
6   Copyright 2010 Lennart Poettering
7
8   systemd is free software; you can redistribute it and/or modify it
9   under the terms of the GNU Lesser General Public License as published by
10   the Free Software Foundation; either version 2.1 of the License, or
11   (at your option) any later version.
12
13   systemd is distributed in the hope that it will be useful, but
14   WITHOUT ANY WARRANTY; without even the implied warranty of
15   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16   Lesser General Public License for more details.
17
18   You should have received a copy of the GNU Lesser General Public License
19   along with systemd; If not, see <http://www.gnu.org/licenses/>.
20 ***/
21
22 #include <errno.h>
23 #include <stdio.h>
24 #include <mntent.h>
25 #include <sys/epoll.h>
26 #include <signal.h>
27
28 #include "unit.h"
29 #include "mount.h"
30 #include "load-fragment.h"
31 #include "load-dropin.h"
32 #include "log.h"
33 #include "sd-messages.h"
34 #include "strv.h"
35 #include "mkdir.h"
36 #include "path-util.h"
37 #include "mount-setup.h"
38 #include "unit-name.h"
39 #include "dbus-mount.h"
40 #include "special.h"
41 #include "bus-errors.h"
42 #include "exit-status.h"
43 #include "def.h"
44
45 static const UnitActiveState state_translation_table[_MOUNT_STATE_MAX] = {
46         [MOUNT_DEAD] = UNIT_INACTIVE,
47         [MOUNT_MOUNTING] = UNIT_ACTIVATING,
48         [MOUNT_MOUNTING_DONE] = UNIT_ACTIVE,
49         [MOUNT_MOUNTED] = UNIT_ACTIVE,
50         [MOUNT_REMOUNTING] = UNIT_RELOADING,
51         [MOUNT_UNMOUNTING] = UNIT_DEACTIVATING,
52         [MOUNT_MOUNTING_SIGTERM] = UNIT_DEACTIVATING,
53         [MOUNT_MOUNTING_SIGKILL] = UNIT_DEACTIVATING,
54         [MOUNT_REMOUNTING_SIGTERM] = UNIT_RELOADING,
55         [MOUNT_REMOUNTING_SIGKILL] = UNIT_RELOADING,
56         [MOUNT_UNMOUNTING_SIGTERM] = UNIT_DEACTIVATING,
57         [MOUNT_UNMOUNTING_SIGKILL] = UNIT_DEACTIVATING,
58         [MOUNT_FAILED] = UNIT_FAILED
59 };
60
61 static void mount_init(Unit *u) {
62         Mount *m = MOUNT(u);
63
64         assert(u);
65         assert(u->load_state == UNIT_STUB);
66
67         m->timeout_usec = DEFAULT_TIMEOUT_USEC;
68         m->directory_mode = 0755;
69
70         exec_context_init(&m->exec_context);
71
72         if (unit_has_name(u, "-.mount")) {
73                 /* Don't allow start/stop for root directory */
74                 UNIT(m)->refuse_manual_start = true;
75                 UNIT(m)->refuse_manual_stop = true;
76         } else {
77                 /* The stdio/kmsg bridge socket is on /, in order to avoid a
78                  * dep loop, don't use kmsg logging for -.mount */
79                 m->exec_context.std_output = u->manager->default_std_output;
80                 m->exec_context.std_error = u->manager->default_std_error;
81         }
82
83         kill_context_init(&m->kill_context);
84
85         /* We need to make sure that /bin/mount is always called in
86          * the same process group as us, so that the autofs kernel
87          * side doesn't send us another mount request while we are
88          * already trying to comply its last one. */
89         m->exec_context.same_pgrp = true;
90
91         m->timer_watch.type = WATCH_INVALID;
92
93         m->control_command_id = _MOUNT_EXEC_COMMAND_INVALID;
94
95         UNIT(m)->ignore_on_isolate = true;
96 }
97
98 static void mount_unwatch_control_pid(Mount *m) {
99         assert(m);
100
101         if (m->control_pid <= 0)
102                 return;
103
104         unit_unwatch_pid(UNIT(m), m->control_pid);
105         m->control_pid = 0;
106 }
107
108 static void mount_parameters_done(MountParameters *p) {
109         assert(p);
110
111         free(p->what);
112         free(p->options);
113         free(p->fstype);
114
115         p->what = p->options = p->fstype = NULL;
116 }
117
118 static void mount_done(Unit *u) {
119         Mount *m = MOUNT(u);
120
121         assert(m);
122
123         free(m->where);
124         m->where = NULL;
125
126         mount_parameters_done(&m->parameters_proc_self_mountinfo);
127         mount_parameters_done(&m->parameters_fragment);
128
129         exec_context_done(&m->exec_context);
130         exec_command_done_array(m->exec_command, _MOUNT_EXEC_COMMAND_MAX);
131         m->control_command = NULL;
132
133         mount_unwatch_control_pid(m);
134
135         unit_unwatch_timer(u, &m->timer_watch);
136 }
137
138 static MountParameters* get_mount_parameters_fragment(Mount *m) {
139         assert(m);
140
141         if (m->from_fragment)
142                 return &m->parameters_fragment;
143
144         return NULL;
145 }
146
147 static MountParameters* get_mount_parameters(Mount *m) {
148         assert(m);
149
150         if (m->from_proc_self_mountinfo)
151                 return &m->parameters_proc_self_mountinfo;
152
153         return get_mount_parameters_fragment(m);
154 }
155
156 static int mount_add_mount_links(Mount *m) {
157         Unit *other;
158         int r;
159         MountParameters *pm;
160
161         assert(m);
162
163         pm = get_mount_parameters_fragment(m);
164
165         /* Adds in links to other mount points that might lie below or
166          * above us in the hierarchy */
167
168         LIST_FOREACH(units_by_type, other, UNIT(m)->manager->units_by_type[UNIT_MOUNT]) {
169                 Mount *n = MOUNT(other);
170                 MountParameters *pn;
171
172                 if (n == m)
173                         continue;
174
175                 if (UNIT(n)->load_state != UNIT_LOADED)
176                         continue;
177
178                 pn = get_mount_parameters_fragment(n);
179
180                 if (path_startswith(m->where, n->where)) {
181
182                         if ((r = unit_add_dependency(UNIT(m), UNIT_AFTER, UNIT(n), true)) < 0)
183                                 return r;
184
185                         if (pn)
186                                 if ((r = unit_add_dependency(UNIT(m), UNIT_REQUIRES, UNIT(n), true)) < 0)
187                                         return r;
188
189                 } else if (path_startswith(n->where, m->where)) {
190
191                         if ((r = unit_add_dependency(UNIT(n), UNIT_AFTER, UNIT(m), true)) < 0)
192                                 return r;
193
194                         if (pm)
195                                 if ((r = unit_add_dependency(UNIT(n), UNIT_REQUIRES, UNIT(m), true)) < 0)
196                                         return r;
197
198                 } else if (pm && pm->what && path_startswith(pm->what, n->where)) {
199
200                         if ((r = unit_add_dependency(UNIT(m), UNIT_AFTER, UNIT(n), true)) < 0)
201                                 return r;
202
203                         if ((r = unit_add_dependency(UNIT(m), UNIT_REQUIRES, UNIT(n), true)) < 0)
204                                 return r;
205
206                 } else if (pn && pn->what && path_startswith(pn->what, m->where)) {
207
208                         if ((r = unit_add_dependency(UNIT(n), UNIT_AFTER, UNIT(m), true)) < 0)
209                                 return r;
210
211                         if ((r = unit_add_dependency(UNIT(n), UNIT_REQUIRES, UNIT(m), true)) < 0)
212                                 return r;
213                 }
214         }
215
216         return 0;
217 }
218
219 static int mount_add_swap_links(Mount *m) {
220         Unit *other;
221         int r;
222
223         assert(m);
224
225         LIST_FOREACH(units_by_type, other, UNIT(m)->manager->units_by_type[UNIT_SWAP]) {
226                 r = swap_add_one_mount_link(SWAP(other), m);
227                 if (r < 0)
228                         return r;
229         }
230
231         return 0;
232 }
233
234 static int mount_add_path_links(Mount *m) {
235         Unit *other;
236         int r;
237
238         assert(m);
239
240         LIST_FOREACH(units_by_type, other, UNIT(m)->manager->units_by_type[UNIT_PATH]) {
241                 r = path_add_one_mount_link(PATH(other), m);
242                 if (r < 0)
243                         return r;
244         }
245
246         return 0;
247 }
248
249 static int mount_add_automount_links(Mount *m) {
250         Unit *other;
251         int r;
252
253         assert(m);
254
255         LIST_FOREACH(units_by_type, other, UNIT(m)->manager->units_by_type[UNIT_AUTOMOUNT]) {
256                 r = automount_add_one_mount_link(AUTOMOUNT(other), m);
257                 if (r < 0)
258                         return r;
259         }
260
261         return 0;
262 }
263
264 static int mount_add_socket_links(Mount *m) {
265         Unit *other;
266         int r;
267
268         assert(m);
269
270         LIST_FOREACH(units_by_type, other, UNIT(m)->manager->units_by_type[UNIT_SOCKET]) {
271                 r = socket_add_one_mount_link(SOCKET(other), m);
272                 if (r < 0)
273                         return r;
274         }
275
276         return 0;
277 }
278
279 static int mount_add_requires_mounts_links(Mount *m) {
280         Unit *other;
281         int r;
282
283         assert(m);
284
285         LIST_FOREACH(has_requires_mounts_for, other, UNIT(m)->manager->has_requires_mounts_for) {
286                 r = unit_add_one_mount_link(other, m);
287                 if (r < 0)
288                         return r;
289         }
290
291         return 0;
292 }
293
294 static char* mount_test_option(const char *haystack, const char *needle) {
295         struct mntent me;
296
297         assert(needle);
298
299         /* Like glibc's hasmntopt(), but works on a string, not a
300          * struct mntent */
301
302         if (!haystack)
303                 return NULL;
304
305         zero(me);
306         me.mnt_opts = (char*) haystack;
307
308         return hasmntopt(&me, needle);
309 }
310
311 static bool mount_is_network(MountParameters *p) {
312         assert(p);
313
314         if (mount_test_option(p->options, "_netdev"))
315                 return true;
316
317         if (p->fstype && fstype_is_network(p->fstype))
318                 return true;
319
320         return false;
321 }
322
323 static bool mount_is_bind(MountParameters *p) {
324         assert(p);
325
326         if (mount_test_option(p->options, "bind"))
327                 return true;
328
329         if (p->fstype && streq(p->fstype, "bind"))
330                 return true;
331
332         if (mount_test_option(p->options, "rbind"))
333                 return true;
334
335         if (p->fstype && streq(p->fstype, "rbind"))
336                 return true;
337
338         return false;
339 }
340
341 static bool needs_quota(MountParameters *p) {
342         assert(p);
343
344         if (mount_is_network(p))
345                 return false;
346
347         if (mount_is_bind(p))
348                 return false;
349
350         return mount_test_option(p->options, "usrquota") ||
351                 mount_test_option(p->options, "grpquota") ||
352                 mount_test_option(p->options, "quota") ||
353                 mount_test_option(p->options, "usrjquota") ||
354                 mount_test_option(p->options, "grpjquota");
355 }
356
357 static int mount_add_device_links(Mount *m) {
358         MountParameters *p;
359         int r;
360
361         assert(m);
362
363         p = get_mount_parameters_fragment(m);
364         if (!p)
365                 return 0;
366
367         if (!p->what)
368                 return 0;
369
370         if (mount_is_bind(p))
371                 return 0;
372
373         if (!is_device_path(p->what))
374                 return 0;
375
376         if (path_equal(m->where, "/"))
377                 return 0;
378
379         r = unit_add_node_link(UNIT(m), p->what, false);
380         if (r < 0)
381                 return r;
382
383         if (p->passno > 0 &&
384             UNIT(m)->manager->running_as == SYSTEMD_SYSTEM) {
385                 char *name;
386                 Unit *fsck;
387                 /* Let's add in the fsck service */
388
389                 /* aka SPECIAL_FSCK_SERVICE */
390                 name = unit_name_from_path_instance("systemd-fsck", p->what, ".service");
391                 if (!name)
392                         return -ENOMEM;
393
394                 r = manager_load_unit_prepare(UNIT(m)->manager, name, NULL, NULL, &fsck);
395                 if (r < 0) {
396                         log_warning_unit(name,
397                                          "Failed to prepare unit %s: %s", name, strerror(-r));
398                         free(name);
399                         return r;
400                 }
401                 free(name);
402
403                 SERVICE(fsck)->fsck_passno = p->passno;
404
405                 r = unit_add_two_dependencies(UNIT(m), UNIT_AFTER, UNIT_REQUIRES, fsck, true);
406                 if (r < 0)
407                         return r;
408         }
409
410         return 0;
411 }
412
413 static int mount_add_quota_links(Mount *m) {
414         int r;
415         MountParameters *p;
416
417         assert(m);
418
419         if (UNIT(m)->manager->running_as != SYSTEMD_SYSTEM)
420                 return 0;
421
422         p = get_mount_parameters_fragment(m);
423         if (!p)
424                 return 0;
425
426         if (!needs_quota(p))
427                 return 0;
428
429         r = unit_add_two_dependencies_by_name(UNIT(m), UNIT_BEFORE, UNIT_WANTS, SPECIAL_QUOTACHECK_SERVICE, NULL, true);
430         if (r < 0)
431                 return r;
432
433         r = unit_add_two_dependencies_by_name(UNIT(m), UNIT_BEFORE, UNIT_WANTS, SPECIAL_QUOTAON_SERVICE, NULL, true);
434         if (r < 0)
435                 return r;
436
437         return 0;
438 }
439
440 static int mount_add_default_dependencies(Mount *m) {
441         int r;
442         MountParameters *p;
443         const char *after;
444
445         assert(m);
446
447         if (UNIT(m)->manager->running_as != SYSTEMD_SYSTEM)
448                 return 0;
449
450         p = get_mount_parameters(m);
451
452         if (!p)
453                 return 0;
454
455         if (path_equal(m->where, "/"))
456                 return 0;
457
458         if (mount_is_network(p))
459                 after = SPECIAL_REMOTE_FS_PRE_TARGET;
460         else
461                 after = SPECIAL_LOCAL_FS_PRE_TARGET;
462
463         r = unit_add_two_dependencies_by_name(UNIT(m), UNIT_WANTS, UNIT_AFTER, after, NULL, true);
464         if (r < 0)
465                 return r;
466
467         r = unit_add_two_dependencies_by_name(UNIT(m), UNIT_BEFORE, UNIT_CONFLICTS, SPECIAL_UMOUNT_TARGET, NULL, true);
468         if (r < 0)
469                 return r;
470
471         return 0;
472 }
473
474 static int mount_fix_timeouts(Mount *m) {
475         MountParameters *p;
476         const char *timeout = NULL;
477         Unit *other;
478         Iterator i;
479         usec_t u;
480         char *t;
481         int r;
482
483         assert(m);
484
485         p = get_mount_parameters_fragment(m);
486         if (!p)
487                 return 0;
488
489         /* Allow configuration how long we wait for a device that
490          * backs a mount point to show up. This is useful to support
491          * endless device timeouts for devices that show up only after
492          * user input, like crypto devices. */
493
494         if ((timeout = mount_test_option(p->options, "comment=systemd.device-timeout")))
495                 timeout += 31;
496         else if ((timeout = mount_test_option(p->options, "x-systemd.device-timeout")))
497                 timeout += 25;
498         else
499                 return 0;
500
501         t = strndup(timeout, strcspn(timeout, ",;" WHITESPACE));
502         if (!t)
503                 return -ENOMEM;
504
505         r = parse_usec(t, &u);
506         free(t);
507
508         if (r < 0) {
509                 log_warning_unit(UNIT(m)->id,
510                                  "Failed to parse timeout for %s, ignoring: %s",
511                                  m->where, timeout);
512                 return r;
513         }
514
515         SET_FOREACH(other, UNIT(m)->dependencies[UNIT_AFTER], i) {
516                 if (other->type != UNIT_DEVICE)
517                         continue;
518
519                 other->job_timeout = u;
520         }
521
522         return 0;
523 }
524
525 static int mount_verify(Mount *m) {
526         bool b;
527         char *e;
528         assert(m);
529
530         if (UNIT(m)->load_state != UNIT_LOADED)
531                 return 0;
532
533         if (!m->from_fragment && !m->from_proc_self_mountinfo)
534                 return -ENOENT;
535
536         if (!(e = unit_name_from_path(m->where, ".mount")))
537                 return -ENOMEM;
538
539         b = unit_has_name(UNIT(m), e);
540         free(e);
541
542         if (!b) {
543                 log_error_unit(UNIT(m)->id,
544                                "%s's Where setting doesn't match unit name. Refusing.",
545                                UNIT(m)->id);
546                 return -EINVAL;
547         }
548
549         if (mount_point_is_api(m->where) || mount_point_ignore(m->where)) {
550                 log_error_unit(UNIT(m)->id,
551                                "Cannot create mount unit for API file system %s. Refusing.",
552                                m->where);
553                 return -EINVAL;
554         }
555
556         if (UNIT(m)->fragment_path && !m->parameters_fragment.what) {
557                 log_error_unit(UNIT(m)->id,
558                                "%s's What setting is missing. Refusing.", UNIT(m)->id);
559                 return -EBADMSG;
560         }
561
562         if (m->exec_context.pam_name && m->kill_context.kill_mode != KILL_CONTROL_GROUP) {
563                 log_error_unit(UNIT(m)->id,
564                                "%s has PAM enabled. Kill mode must be set to control-group'. Refusing.",
565                                UNIT(m)->id);
566                 return -EINVAL;
567         }
568
569         return 0;
570 }
571
572 static int mount_add_extras(Mount *m) {
573         Unit *u = UNIT(m);
574         int r;
575
576         if (UNIT(m)->fragment_path)
577                 m->from_fragment = true;
578
579         if (!m->where) {
580                 m->where = unit_name_to_path(u->id);
581                 if (!m->where)
582                         return -ENOMEM;
583         }
584
585         path_kill_slashes(m->where);
586
587         r = unit_add_exec_dependencies(u, &m->exec_context);
588         if (r < 0)
589                 return r;
590
591         if (!UNIT(m)->description) {
592                 r = unit_set_description(u, m->where);
593                 if (r < 0)
594                         return r;
595         }
596
597         r = mount_add_device_links(m);
598         if (r < 0)
599                 return r;
600
601         r = mount_add_mount_links(m);
602         if (r < 0)
603                 return r;
604
605         r = mount_add_socket_links(m);
606         if (r < 0)
607                 return r;
608
609         r = mount_add_swap_links(m);
610         if (r < 0)
611                 return r;
612
613         r = mount_add_path_links(m);
614         if (r < 0)
615                 return r;
616
617         r = mount_add_requires_mounts_links(m);
618         if (r < 0)
619                 return r;
620
621         r = mount_add_automount_links(m);
622         if (r < 0)
623                 return r;
624
625         r = mount_add_quota_links(m);
626         if (r < 0)
627                 return r;
628
629         if (UNIT(m)->default_dependencies) {
630                 r = mount_add_default_dependencies(m);
631                 if (r < 0)
632                         return r;
633         }
634
635         r = unit_add_default_cgroups(u);
636         if (r < 0)
637                 return r;
638
639         r = mount_fix_timeouts(m);
640         if (r < 0)
641                 return r;
642
643         return 0;
644 }
645
646 static int mount_load(Unit *u) {
647         Mount *m = MOUNT(u);
648         int r;
649
650         assert(u);
651         assert(u->load_state == UNIT_STUB);
652
653         if (m->from_proc_self_mountinfo)
654                 r = unit_load_fragment_and_dropin_optional(u);
655         else
656                 r = unit_load_fragment_and_dropin(u);
657
658         if (r < 0)
659                 return r;
660
661         /* This is a new unit? Then let's add in some extras */
662         if (u->load_state == UNIT_LOADED) {
663                 r = mount_add_extras(m);
664                 if (r < 0)
665                         return r;
666
667                 r = unit_exec_context_defaults(u, &m->exec_context);
668                 if (r < 0)
669                         return r;
670         }
671
672         return mount_verify(m);
673 }
674
675 static int mount_notify_automount(Mount *m, int status) {
676         Unit *p;
677         int r;
678         Iterator i;
679
680         assert(m);
681
682         SET_FOREACH(p, UNIT(m)->dependencies[UNIT_TRIGGERED_BY], i)
683                 if (p->type == UNIT_AUTOMOUNT) {
684                          r = automount_send_ready(AUTOMOUNT(p), status);
685                          if (r < 0)
686                                  return r;
687                 }
688
689         return 0;
690 }
691
692 static void mount_set_state(Mount *m, MountState state) {
693         MountState old_state;
694         assert(m);
695
696         old_state = m->state;
697         m->state = state;
698
699         if (state != MOUNT_MOUNTING &&
700             state != MOUNT_MOUNTING_DONE &&
701             state != MOUNT_REMOUNTING &&
702             state != MOUNT_UNMOUNTING &&
703             state != MOUNT_MOUNTING_SIGTERM &&
704             state != MOUNT_MOUNTING_SIGKILL &&
705             state != MOUNT_UNMOUNTING_SIGTERM &&
706             state != MOUNT_UNMOUNTING_SIGKILL &&
707             state != MOUNT_REMOUNTING_SIGTERM &&
708             state != MOUNT_REMOUNTING_SIGKILL) {
709                 unit_unwatch_timer(UNIT(m), &m->timer_watch);
710                 mount_unwatch_control_pid(m);
711                 m->control_command = NULL;
712                 m->control_command_id = _MOUNT_EXEC_COMMAND_INVALID;
713         }
714
715         if (state == MOUNT_MOUNTED ||
716             state == MOUNT_REMOUNTING)
717                 mount_notify_automount(m, 0);
718         else if (state == MOUNT_DEAD ||
719                  state == MOUNT_UNMOUNTING ||
720                  state == MOUNT_MOUNTING_SIGTERM ||
721                  state == MOUNT_MOUNTING_SIGKILL ||
722                  state == MOUNT_REMOUNTING_SIGTERM ||
723                  state == MOUNT_REMOUNTING_SIGKILL ||
724                  state == MOUNT_UNMOUNTING_SIGTERM ||
725                  state == MOUNT_UNMOUNTING_SIGKILL ||
726                  state == MOUNT_FAILED) {
727                 if (state != old_state)
728                         mount_notify_automount(m, -ENODEV);
729         }
730
731         if (state != old_state)
732                 log_debug_unit(UNIT(m)->id,
733                                "%s changed %s -> %s",
734                                UNIT(m)->id,
735                                mount_state_to_string(old_state),
736                                mount_state_to_string(state));
737
738         unit_notify(UNIT(m), state_translation_table[old_state], state_translation_table[state], m->reload_result == MOUNT_SUCCESS);
739         m->reload_result = MOUNT_SUCCESS;
740 }
741
742 static int mount_coldplug(Unit *u) {
743         Mount *m = MOUNT(u);
744         MountState new_state = MOUNT_DEAD;
745         int r;
746
747         assert(m);
748         assert(m->state == MOUNT_DEAD);
749
750         if (m->deserialized_state != m->state)
751                 new_state = m->deserialized_state;
752         else if (m->from_proc_self_mountinfo)
753                 new_state = MOUNT_MOUNTED;
754
755         if (new_state != m->state) {
756
757                 if (new_state == MOUNT_MOUNTING ||
758                     new_state == MOUNT_MOUNTING_DONE ||
759                     new_state == MOUNT_REMOUNTING ||
760                     new_state == MOUNT_UNMOUNTING ||
761                     new_state == MOUNT_MOUNTING_SIGTERM ||
762                     new_state == MOUNT_MOUNTING_SIGKILL ||
763                     new_state == MOUNT_UNMOUNTING_SIGTERM ||
764                     new_state == MOUNT_UNMOUNTING_SIGKILL ||
765                     new_state == MOUNT_REMOUNTING_SIGTERM ||
766                     new_state == MOUNT_REMOUNTING_SIGKILL) {
767
768                         if (m->control_pid <= 0)
769                                 return -EBADMSG;
770
771                         r = unit_watch_pid(UNIT(m), m->control_pid);
772                         if (r < 0)
773                                 return r;
774
775                         r = unit_watch_timer(UNIT(m), CLOCK_MONOTONIC, true, m->timeout_usec, &m->timer_watch);
776                         if (r < 0)
777                                 return r;
778                 }
779
780                 mount_set_state(m, new_state);
781         }
782
783         return 0;
784 }
785
786 static void mount_dump(Unit *u, FILE *f, const char *prefix) {
787         Mount *m = MOUNT(u);
788         MountParameters *p;
789
790         assert(m);
791         assert(f);
792
793         p = get_mount_parameters(m);
794
795         fprintf(f,
796                 "%sMount State: %s\n"
797                 "%sResult: %s\n"
798                 "%sWhere: %s\n"
799                 "%sWhat: %s\n"
800                 "%sFile System Type: %s\n"
801                 "%sOptions: %s\n"
802                 "%sFrom /proc/self/mountinfo: %s\n"
803                 "%sFrom fragment: %s\n"
804                 "%sDirectoryMode: %04o\n",
805                 prefix, mount_state_to_string(m->state),
806                 prefix, mount_result_to_string(m->result),
807                 prefix, m->where,
808                 prefix, strna(p->what),
809                 prefix, strna(p->fstype),
810                 prefix, strna(p->options),
811                 prefix, yes_no(m->from_proc_self_mountinfo),
812                 prefix, yes_no(m->from_fragment),
813                 prefix, m->directory_mode);
814
815         if (m->control_pid > 0)
816                 fprintf(f,
817                         "%sControl PID: %lu\n",
818                         prefix, (unsigned long) m->control_pid);
819
820         exec_context_dump(&m->exec_context, f, prefix);
821         kill_context_dump(&m->kill_context, f, prefix);
822 }
823
824 static int mount_spawn(Mount *m, ExecCommand *c, pid_t *_pid) {
825         pid_t pid;
826         int r;
827
828         assert(m);
829         assert(c);
830         assert(_pid);
831
832         r = unit_watch_timer(UNIT(m), CLOCK_MONOTONIC, true, m->timeout_usec, &m->timer_watch);
833         if (r < 0)
834                 goto fail;
835
836         if ((r = exec_spawn(c,
837                             NULL,
838                             &m->exec_context,
839                             NULL, 0,
840                             UNIT(m)->manager->environment,
841                             true,
842                             true,
843                             true,
844                             UNIT(m)->manager->confirm_spawn,
845                             UNIT(m)->cgroup_bondings,
846                             UNIT(m)->cgroup_attributes,
847                             NULL,
848                             UNIT(m)->id,
849                             NULL,
850                             &pid)) < 0)
851                 goto fail;
852
853         if ((r = unit_watch_pid(UNIT(m), pid)) < 0)
854                 /* FIXME: we need to do something here */
855                 goto fail;
856
857         *_pid = pid;
858
859         return 0;
860
861 fail:
862         unit_unwatch_timer(UNIT(m), &m->timer_watch);
863
864         return r;
865 }
866
867 static void mount_enter_dead(Mount *m, MountResult f) {
868         assert(m);
869
870         if (f != MOUNT_SUCCESS)
871                 m->result = f;
872
873         mount_set_state(m, m->result != MOUNT_SUCCESS ? MOUNT_FAILED : MOUNT_DEAD);
874 }
875
876 static void mount_enter_mounted(Mount *m, MountResult f) {
877         assert(m);
878
879         if (f != MOUNT_SUCCESS)
880                 m->result = f;
881
882         mount_set_state(m, MOUNT_MOUNTED);
883 }
884
885 static void mount_enter_signal(Mount *m, MountState state, MountResult f) {
886         int r;
887
888         assert(m);
889
890         if (f != MOUNT_SUCCESS)
891                 m->result = f;
892
893         r = unit_kill_context(
894                         UNIT(m),
895                         &m->kill_context,
896                         state != MOUNT_MOUNTING_SIGTERM && state != MOUNT_UNMOUNTING_SIGTERM && state != MOUNT_REMOUNTING_SIGTERM,
897                         -1,
898                         m->control_pid,
899                         false);
900         if (r < 0)
901                 goto fail;
902
903         if (r > 0) {
904                 r = unit_watch_timer(UNIT(m), CLOCK_MONOTONIC, true, m->timeout_usec, &m->timer_watch);
905                 if (r < 0)
906                         goto fail;
907
908                 mount_set_state(m, state);
909         } else if (state == MOUNT_REMOUNTING_SIGTERM || state == MOUNT_REMOUNTING_SIGKILL)
910                 mount_enter_mounted(m, MOUNT_SUCCESS);
911         else
912                 mount_enter_dead(m, MOUNT_SUCCESS);
913
914         return;
915
916 fail:
917         log_warning_unit(UNIT(m)->id,
918                          "%s failed to kill processes: %s", UNIT(m)->id, strerror(-r));
919
920         if (state == MOUNT_REMOUNTING_SIGTERM || state == MOUNT_REMOUNTING_SIGKILL)
921                 mount_enter_mounted(m, MOUNT_FAILURE_RESOURCES);
922         else
923                 mount_enter_dead(m, MOUNT_FAILURE_RESOURCES);
924 }
925
926 void warn_if_dir_nonempty(const char *unit, const char* where) {
927         assert(unit);
928         assert(where);
929
930         if (dir_is_empty(where) > 0)
931                 return;
932
933         log_struct_unit(LOG_NOTICE,
934                    unit,
935                    "MESSAGE=%s: Directory %s to mount over is not empty, mounting anyway.",
936                    unit, where,
937                    "WHERE=%s", where,
938                    MESSAGE_ID(SD_MESSAGE_OVERMOUNTING),
939                    NULL);
940 }
941
942 static void mount_enter_unmounting(Mount *m) {
943         int r;
944
945         assert(m);
946
947         m->control_command_id = MOUNT_EXEC_UNMOUNT;
948         m->control_command = m->exec_command + MOUNT_EXEC_UNMOUNT;
949
950         if ((r = exec_command_set(
951                              m->control_command,
952                              "/bin/umount",
953                              m->where,
954                              NULL)) < 0)
955                 goto fail;
956
957         mount_unwatch_control_pid(m);
958
959         if ((r = mount_spawn(m, m->control_command, &m->control_pid)) < 0)
960                 goto fail;
961
962         mount_set_state(m, MOUNT_UNMOUNTING);
963
964         return;
965
966 fail:
967         log_warning_unit(UNIT(m)->id,
968                          "%s failed to run 'umount' task: %s",
969                          UNIT(m)->id, strerror(-r));
970         mount_enter_mounted(m, MOUNT_FAILURE_RESOURCES);
971 }
972
973 static void mount_enter_mounting(Mount *m) {
974         int r;
975         MountParameters *p;
976
977         assert(m);
978
979         m->control_command_id = MOUNT_EXEC_MOUNT;
980         m->control_command = m->exec_command + MOUNT_EXEC_MOUNT;
981
982         mkdir_p_label(m->where, m->directory_mode);
983
984         warn_if_dir_nonempty(m->meta.id, m->where);
985
986         /* Create the source directory for bind-mounts if needed */
987         p = get_mount_parameters_fragment(m);
988         if (p && mount_is_bind(p))
989                 mkdir_p_label(p->what, m->directory_mode);
990
991         if (m->from_fragment)
992                 r = exec_command_set(
993                                 m->control_command,
994                                 "/bin/mount",
995                                 m->parameters_fragment.what,
996                                 m->where,
997                                 "-t", m->parameters_fragment.fstype ? m->parameters_fragment.fstype : "auto",
998                                 m->parameters_fragment.options ? "-o" : NULL, m->parameters_fragment.options,
999                                 NULL);
1000         else
1001                 r = -ENOENT;
1002
1003         if (r < 0)
1004                 goto fail;
1005
1006         mount_unwatch_control_pid(m);
1007
1008         r = mount_spawn(m, m->control_command, &m->control_pid);
1009         if (r < 0)
1010                 goto fail;
1011
1012         mount_set_state(m, MOUNT_MOUNTING);
1013
1014         return;
1015
1016 fail:
1017         log_warning_unit(UNIT(m)->id,
1018                          "%s failed to run 'mount' task: %s",
1019                          UNIT(m)->id, strerror(-r));
1020         mount_enter_dead(m, MOUNT_FAILURE_RESOURCES);
1021 }
1022
1023 static void mount_enter_mounting_done(Mount *m) {
1024         assert(m);
1025
1026         mount_set_state(m, MOUNT_MOUNTING_DONE);
1027 }
1028
1029 static void mount_enter_remounting(Mount *m) {
1030         int r;
1031
1032         assert(m);
1033
1034         m->control_command_id = MOUNT_EXEC_REMOUNT;
1035         m->control_command = m->exec_command + MOUNT_EXEC_REMOUNT;
1036
1037         if (m->from_fragment) {
1038                 char *buf = NULL;
1039                 const char *o;
1040
1041                 if (m->parameters_fragment.options) {
1042                         if (!(buf = strappend("remount,", m->parameters_fragment.options))) {
1043                                 r = -ENOMEM;
1044                                 goto fail;
1045                         }
1046
1047                         o = buf;
1048                 } else
1049                         o = "remount";
1050
1051                 r = exec_command_set(
1052                                 m->control_command,
1053                                 "/bin/mount",
1054                                 m->parameters_fragment.what,
1055                                 m->where,
1056                                 "-t", m->parameters_fragment.fstype ? m->parameters_fragment.fstype : "auto",
1057                                 "-o", o,
1058                                 NULL);
1059
1060                 free(buf);
1061         } else
1062                 r = -ENOENT;
1063
1064         if (r < 0)
1065                 goto fail;
1066
1067         mount_unwatch_control_pid(m);
1068
1069         if ((r = mount_spawn(m, m->control_command, &m->control_pid)) < 0)
1070                 goto fail;
1071
1072         mount_set_state(m, MOUNT_REMOUNTING);
1073
1074         return;
1075
1076 fail:
1077         log_warning_unit(UNIT(m)->id,
1078                          "%s failed to run 'remount' task: %s",
1079                          UNIT(m)->id, strerror(-r));
1080         m->reload_result = MOUNT_FAILURE_RESOURCES;
1081         mount_enter_mounted(m, MOUNT_SUCCESS);
1082 }
1083
1084 static int mount_start(Unit *u) {
1085         Mount *m = MOUNT(u);
1086
1087         assert(m);
1088
1089         /* We cannot fulfill this request right now, try again later
1090          * please! */
1091         if (m->state == MOUNT_UNMOUNTING ||
1092             m->state == MOUNT_UNMOUNTING_SIGTERM ||
1093             m->state == MOUNT_UNMOUNTING_SIGKILL ||
1094             m->state == MOUNT_MOUNTING_SIGTERM ||
1095             m->state == MOUNT_MOUNTING_SIGKILL)
1096                 return -EAGAIN;
1097
1098         /* Already on it! */
1099         if (m->state == MOUNT_MOUNTING)
1100                 return 0;
1101
1102         assert(m->state == MOUNT_DEAD || m->state == MOUNT_FAILED);
1103
1104         m->result = MOUNT_SUCCESS;
1105         m->reload_result = MOUNT_SUCCESS;
1106
1107         mount_enter_mounting(m);
1108         return 0;
1109 }
1110
1111 static int mount_stop(Unit *u) {
1112         Mount *m = MOUNT(u);
1113
1114         assert(m);
1115
1116         /* Already on it */
1117         if (m->state == MOUNT_UNMOUNTING ||
1118             m->state == MOUNT_UNMOUNTING_SIGKILL ||
1119             m->state == MOUNT_UNMOUNTING_SIGTERM ||
1120             m->state == MOUNT_MOUNTING_SIGTERM ||
1121             m->state == MOUNT_MOUNTING_SIGKILL)
1122                 return 0;
1123
1124         assert(m->state == MOUNT_MOUNTING ||
1125                m->state == MOUNT_MOUNTING_DONE ||
1126                m->state == MOUNT_MOUNTED ||
1127                m->state == MOUNT_REMOUNTING ||
1128                m->state == MOUNT_REMOUNTING_SIGTERM ||
1129                m->state == MOUNT_REMOUNTING_SIGKILL);
1130
1131         mount_enter_unmounting(m);
1132         return 0;
1133 }
1134
1135 static int mount_reload(Unit *u) {
1136         Mount *m = MOUNT(u);
1137
1138         assert(m);
1139
1140         if (m->state == MOUNT_MOUNTING_DONE)
1141                 return -EAGAIN;
1142
1143         assert(m->state == MOUNT_MOUNTED);
1144
1145         mount_enter_remounting(m);
1146         return 0;
1147 }
1148
1149 static int mount_serialize(Unit *u, FILE *f, FDSet *fds) {
1150         Mount *m = MOUNT(u);
1151
1152         assert(m);
1153         assert(f);
1154         assert(fds);
1155
1156         unit_serialize_item(u, f, "state", mount_state_to_string(m->state));
1157         unit_serialize_item(u, f, "result", mount_result_to_string(m->result));
1158         unit_serialize_item(u, f, "reload-result", mount_result_to_string(m->reload_result));
1159
1160         if (m->control_pid > 0)
1161                 unit_serialize_item_format(u, f, "control-pid", "%lu", (unsigned long) m->control_pid);
1162
1163         if (m->control_command_id >= 0)
1164                 unit_serialize_item(u, f, "control-command", mount_exec_command_to_string(m->control_command_id));
1165
1166         return 0;
1167 }
1168
1169 static int mount_deserialize_item(Unit *u, const char *key, const char *value, FDSet *fds) {
1170         Mount *m = MOUNT(u);
1171
1172         assert(u);
1173         assert(key);
1174         assert(value);
1175         assert(fds);
1176
1177         if (streq(key, "state")) {
1178                 MountState state;
1179
1180                 if ((state = mount_state_from_string(value)) < 0)
1181                         log_debug_unit(u->id, "Failed to parse state value %s", value);
1182                 else
1183                         m->deserialized_state = state;
1184         } else if (streq(key, "result")) {
1185                 MountResult f;
1186
1187                 f = mount_result_from_string(value);
1188                 if (f < 0)
1189                         log_debug_unit(UNIT(m)->id,
1190                                        "Failed to parse result value %s", value);
1191                 else if (f != MOUNT_SUCCESS)
1192                         m->result = f;
1193
1194         } else if (streq(key, "reload-result")) {
1195                 MountResult f;
1196
1197                 f = mount_result_from_string(value);
1198                 if (f < 0)
1199                         log_debug_unit(UNIT(m)->id,
1200                                        "Failed to parse reload result value %s", value);
1201                 else if (f != MOUNT_SUCCESS)
1202                         m->reload_result = f;
1203
1204         } else if (streq(key, "control-pid")) {
1205                 pid_t pid;
1206
1207                 if (parse_pid(value, &pid) < 0)
1208                         log_debug_unit(UNIT(m)->id,
1209                                        "Failed to parse control-pid value %s", value);
1210                 else
1211                         m->control_pid = pid;
1212         } else if (streq(key, "control-command")) {
1213                 MountExecCommand id;
1214
1215                 if ((id = mount_exec_command_from_string(value)) < 0)
1216                         log_debug_unit(UNIT(m)->id,
1217                                        "Failed to parse exec-command value %s", value);
1218                 else {
1219                         m->control_command_id = id;
1220                         m->control_command = m->exec_command + id;
1221                 }
1222
1223         } else
1224                 log_debug_unit(UNIT(m)->id,
1225                                "Unknown serialization key '%s'", key);
1226
1227         return 0;
1228 }
1229
1230 static UnitActiveState mount_active_state(Unit *u) {
1231         assert(u);
1232
1233         return state_translation_table[MOUNT(u)->state];
1234 }
1235
1236 static const char *mount_sub_state_to_string(Unit *u) {
1237         assert(u);
1238
1239         return mount_state_to_string(MOUNT(u)->state);
1240 }
1241
1242 static bool mount_check_gc(Unit *u) {
1243         Mount *m = MOUNT(u);
1244
1245         assert(m);
1246
1247         return m->from_proc_self_mountinfo;
1248 }
1249
1250 static void mount_sigchld_event(Unit *u, pid_t pid, int code, int status) {
1251         Mount *m = MOUNT(u);
1252         MountResult f;
1253
1254         assert(m);
1255         assert(pid >= 0);
1256
1257         if (pid != m->control_pid)
1258                 return;
1259
1260         m->control_pid = 0;
1261
1262         if (is_clean_exit(code, status, NULL))
1263                 f = MOUNT_SUCCESS;
1264         else if (code == CLD_EXITED)
1265                 f = MOUNT_FAILURE_EXIT_CODE;
1266         else if (code == CLD_KILLED)
1267                 f = MOUNT_FAILURE_SIGNAL;
1268         else if (code == CLD_DUMPED)
1269                 f = MOUNT_FAILURE_CORE_DUMP;
1270         else
1271                 assert_not_reached("Unknown code");
1272
1273         if (f != MOUNT_SUCCESS)
1274                 m->result = f;
1275
1276         if (m->control_command) {
1277                 exec_status_exit(&m->control_command->exec_status, &m->exec_context, pid, code, status);
1278
1279                 m->control_command = NULL;
1280                 m->control_command_id = _MOUNT_EXEC_COMMAND_INVALID;
1281         }
1282
1283         log_full_unit(f == MOUNT_SUCCESS ? LOG_DEBUG : LOG_NOTICE, u->id,
1284                       "%s mount process exited, code=%s status=%i",
1285                       u->id, sigchld_code_to_string(code), status);
1286
1287         /* Note that mount(8) returning and the kernel sending us a
1288          * mount table change event might happen out-of-order. If an
1289          * operation succeed we assume the kernel will follow soon too
1290          * and already change into the resulting state.  If it fails
1291          * we check if the kernel still knows about the mount. and
1292          * change state accordingly. */
1293
1294         switch (m->state) {
1295
1296         case MOUNT_MOUNTING:
1297         case MOUNT_MOUNTING_DONE:
1298         case MOUNT_MOUNTING_SIGKILL:
1299         case MOUNT_MOUNTING_SIGTERM:
1300
1301                 if (f == MOUNT_SUCCESS)
1302                         mount_enter_mounted(m, f);
1303                 else if (m->from_proc_self_mountinfo)
1304                         mount_enter_mounted(m, f);
1305                 else
1306                         mount_enter_dead(m, f);
1307                 break;
1308
1309         case MOUNT_REMOUNTING:
1310         case MOUNT_REMOUNTING_SIGKILL:
1311         case MOUNT_REMOUNTING_SIGTERM:
1312
1313                 m->reload_result = f;
1314                 if (m->from_proc_self_mountinfo)
1315                         mount_enter_mounted(m, MOUNT_SUCCESS);
1316                 else
1317                         mount_enter_dead(m, MOUNT_SUCCESS);
1318
1319                 break;
1320
1321         case MOUNT_UNMOUNTING:
1322         case MOUNT_UNMOUNTING_SIGKILL:
1323         case MOUNT_UNMOUNTING_SIGTERM:
1324
1325                 if (f == MOUNT_SUCCESS)
1326                         mount_enter_dead(m, f);
1327                 else if (m->from_proc_self_mountinfo)
1328                         mount_enter_mounted(m, f);
1329                 else
1330                         mount_enter_dead(m, f);
1331                 break;
1332
1333         default:
1334                 assert_not_reached("Uh, control process died at wrong time.");
1335         }
1336
1337         /* Notify clients about changed exit status */
1338         unit_add_to_dbus_queue(u);
1339 }
1340
1341 static void mount_timer_event(Unit *u, uint64_t elapsed, Watch *w) {
1342         Mount *m = MOUNT(u);
1343
1344         assert(m);
1345         assert(elapsed == 1);
1346         assert(w == &m->timer_watch);
1347
1348         switch (m->state) {
1349
1350         case MOUNT_MOUNTING:
1351         case MOUNT_MOUNTING_DONE:
1352                 log_warning_unit(u->id,
1353                                  "%s mounting timed out. Stopping.", u->id);
1354                 mount_enter_signal(m, MOUNT_MOUNTING_SIGTERM, MOUNT_FAILURE_TIMEOUT);
1355                 break;
1356
1357         case MOUNT_REMOUNTING:
1358                 log_warning_unit(u->id,
1359                                  "%s remounting timed out. Stopping.", u->id);
1360                 m->reload_result = MOUNT_FAILURE_TIMEOUT;
1361                 mount_enter_mounted(m, MOUNT_SUCCESS);
1362                 break;
1363
1364         case MOUNT_UNMOUNTING:
1365                 log_warning_unit(u->id,
1366                                  "%s unmounting timed out. Stopping.", u->id);
1367                 mount_enter_signal(m, MOUNT_UNMOUNTING_SIGTERM, MOUNT_FAILURE_TIMEOUT);
1368                 break;
1369
1370         case MOUNT_MOUNTING_SIGTERM:
1371                 if (m->kill_context.send_sigkill) {
1372                         log_warning_unit(u->id,
1373                                          "%s mounting timed out. Killing.", u->id);
1374                         mount_enter_signal(m, MOUNT_MOUNTING_SIGKILL, MOUNT_FAILURE_TIMEOUT);
1375                 } else {
1376                         log_warning_unit(u->id,
1377                                          "%s mounting timed out. Skipping SIGKILL. Ignoring.",
1378                                          u->id);
1379
1380                         if (m->from_proc_self_mountinfo)
1381                                 mount_enter_mounted(m, MOUNT_FAILURE_TIMEOUT);
1382                         else
1383                                 mount_enter_dead(m, MOUNT_FAILURE_TIMEOUT);
1384                 }
1385                 break;
1386
1387         case MOUNT_REMOUNTING_SIGTERM:
1388                 if (m->kill_context.send_sigkill) {
1389                         log_warning_unit(u->id,
1390                                          "%s remounting timed out. Killing.", u->id);
1391                         mount_enter_signal(m, MOUNT_REMOUNTING_SIGKILL, MOUNT_FAILURE_TIMEOUT);
1392                 } else {
1393                         log_warning_unit(u->id,
1394                                          "%s remounting timed out. Skipping SIGKILL. Ignoring.",
1395                                          u->id);
1396
1397                         if (m->from_proc_self_mountinfo)
1398                                 mount_enter_mounted(m, MOUNT_FAILURE_TIMEOUT);
1399                         else
1400                                 mount_enter_dead(m, MOUNT_FAILURE_TIMEOUT);
1401                 }
1402                 break;
1403
1404         case MOUNT_UNMOUNTING_SIGTERM:
1405                 if (m->kill_context.send_sigkill) {
1406                         log_warning_unit(u->id,
1407                                          "%s unmounting timed out. Killing.", u->id);
1408                         mount_enter_signal(m, MOUNT_UNMOUNTING_SIGKILL, MOUNT_FAILURE_TIMEOUT);
1409                 } else {
1410                         log_warning_unit(u->id,
1411                                          "%s unmounting timed out. Skipping SIGKILL. Ignoring.",
1412                                          u->id);
1413
1414                         if (m->from_proc_self_mountinfo)
1415                                 mount_enter_mounted(m, MOUNT_FAILURE_TIMEOUT);
1416                         else
1417                                 mount_enter_dead(m, MOUNT_FAILURE_TIMEOUT);
1418                 }
1419                 break;
1420
1421         case MOUNT_MOUNTING_SIGKILL:
1422         case MOUNT_REMOUNTING_SIGKILL:
1423         case MOUNT_UNMOUNTING_SIGKILL:
1424                 log_warning_unit(u->id,
1425                                  "%s mount process still around after SIGKILL. Ignoring.",
1426                                  u->id);
1427
1428                 if (m->from_proc_self_mountinfo)
1429                         mount_enter_mounted(m, MOUNT_FAILURE_TIMEOUT);
1430                 else
1431                         mount_enter_dead(m, MOUNT_FAILURE_TIMEOUT);
1432                 break;
1433
1434         default:
1435                 assert_not_reached("Timeout at wrong time.");
1436         }
1437 }
1438
1439 static int mount_add_one(
1440                 Manager *m,
1441                 const char *what,
1442                 const char *where,
1443                 const char *options,
1444                 const char *fstype,
1445                 int passno,
1446                 bool set_flags) {
1447         int r;
1448         Unit *u;
1449         bool delete;
1450         char *e, *w = NULL, *o = NULL, *f = NULL;
1451         MountParameters *p;
1452         bool load_extras = false;
1453
1454         assert(m);
1455         assert(what);
1456         assert(where);
1457         assert(options);
1458         assert(fstype);
1459
1460         /* Ignore API mount points. They should never be referenced in
1461          * dependencies ever. */
1462         if (mount_point_is_api(where) || mount_point_ignore(where))
1463                 return 0;
1464
1465         if (streq(fstype, "autofs"))
1466                 return 0;
1467
1468         /* probably some kind of swap, ignore */
1469         if (!is_path(where))
1470                 return 0;
1471
1472         e = unit_name_from_path(where, ".mount");
1473         if (!e)
1474                 return -ENOMEM;
1475
1476         u = manager_get_unit(m, e);
1477         if (!u) {
1478                 delete = true;
1479
1480                 u = unit_new(m, sizeof(Mount));
1481                 if (!u) {
1482                         free(e);
1483                         return -ENOMEM;
1484                 }
1485
1486                 r = unit_add_name(u, e);
1487                 free(e);
1488
1489                 if (r < 0)
1490                         goto fail;
1491
1492                 MOUNT(u)->where = strdup(where);
1493                 if (!MOUNT(u)->where) {
1494                         r = -ENOMEM;
1495                         goto fail;
1496                 }
1497
1498                 u->source_path = strdup("/proc/self/mountinfo");
1499                 if (!u->source_path) {
1500                         r = -ENOMEM;
1501                         goto fail;
1502                 }
1503
1504                 r = unit_add_dependency_by_name(u, UNIT_BEFORE, SPECIAL_LOCAL_FS_TARGET, NULL, true);
1505                 if (r < 0)
1506                         goto fail;
1507
1508                 r = unit_add_dependency_by_name(u, UNIT_CONFLICTS, SPECIAL_UMOUNT_TARGET, NULL, true);
1509                 if (r < 0)
1510                         goto fail;
1511
1512                 unit_add_to_load_queue(u);
1513         } else {
1514                 delete = false;
1515                 free(e);
1516
1517                 if (!MOUNT(u)->where) {
1518                         MOUNT(u)->where = strdup(where);
1519                         if (!MOUNT(u)->where) {
1520                                 r = -ENOMEM;
1521                                 goto fail;
1522                         }
1523                 }
1524
1525                 if (u->load_state == UNIT_ERROR) {
1526                         u->load_state = UNIT_LOADED;
1527                         u->load_error = 0;
1528
1529                         /* Load in the extras later on, after we
1530                          * finished initialization of the unit */
1531                         load_extras = true;
1532                 }
1533         }
1534
1535         if (!(w = strdup(what)) ||
1536             !(o = strdup(options)) ||
1537             !(f = strdup(fstype))) {
1538                 r = -ENOMEM;
1539                 goto fail;
1540         }
1541
1542         p = &MOUNT(u)->parameters_proc_self_mountinfo;
1543         if (set_flags) {
1544                 MOUNT(u)->is_mounted = true;
1545                 MOUNT(u)->just_mounted = !MOUNT(u)->from_proc_self_mountinfo;
1546                 MOUNT(u)->just_changed = !streq_ptr(p->options, o);
1547         }
1548
1549         MOUNT(u)->from_proc_self_mountinfo = true;
1550
1551         free(p->what);
1552         p->what = w;
1553
1554         free(p->options);
1555         p->options = o;
1556
1557         free(p->fstype);
1558         p->fstype = f;
1559
1560         p->passno = passno;
1561
1562         if (load_extras) {
1563                 r = mount_add_extras(MOUNT(u));
1564                 if (r < 0)
1565                         goto fail;
1566         }
1567
1568         unit_add_to_dbus_queue(u);
1569
1570         return 0;
1571
1572 fail:
1573         free(w);
1574         free(o);
1575         free(f);
1576
1577         if (delete && u)
1578                 unit_free(u);
1579
1580         return r;
1581 }
1582
1583 static int mount_load_proc_self_mountinfo(Manager *m, bool set_flags) {
1584         int r = 0;
1585         unsigned i;
1586         char *device, *path, *options, *options2, *fstype, *d, *p, *o;
1587
1588         assert(m);
1589
1590         rewind(m->proc_self_mountinfo);
1591
1592         for (i = 1;; i++) {
1593                 int k;
1594
1595                 device = path = options = options2 = fstype = d = p = o = NULL;
1596
1597                 if ((k = fscanf(m->proc_self_mountinfo,
1598                                 "%*s "       /* (1) mount id */
1599                                 "%*s "       /* (2) parent id */
1600                                 "%*s "       /* (3) major:minor */
1601                                 "%*s "       /* (4) root */
1602                                 "%ms "       /* (5) mount point */
1603                                 "%ms"        /* (6) mount options */
1604                                 "%*[^-]"     /* (7) optional fields */
1605                                 "- "         /* (8) separator */
1606                                 "%ms "       /* (9) file system type */
1607                                 "%ms"        /* (10) mount source */
1608                                 "%ms"        /* (11) mount options 2 */
1609                                 "%*[^\n]",   /* some rubbish at the end */
1610                                 &path,
1611                                 &options,
1612                                 &fstype,
1613                                 &device,
1614                                 &options2)) != 5) {
1615
1616                         if (k == EOF)
1617                                 break;
1618
1619                         log_warning("Failed to parse /proc/self/mountinfo:%u.", i);
1620                         goto clean_up;
1621                 }
1622
1623                 o = strjoin(options, ",", options2, NULL);
1624                 if (!o) {
1625                         r = -ENOMEM;
1626                         goto finish;
1627                 }
1628
1629                 if (!(d = cunescape(device)) ||
1630                     !(p = cunescape(path))) {
1631                         r = -ENOMEM;
1632                         goto finish;
1633                 }
1634
1635                 if ((k = mount_add_one(m, d, p, o, fstype, 0, set_flags)) < 0)
1636                         r = k;
1637
1638 clean_up:
1639                 free(device);
1640                 free(path);
1641                 free(options);
1642                 free(options2);
1643                 free(fstype);
1644                 free(d);
1645                 free(p);
1646                 free(o);
1647         }
1648
1649 finish:
1650         free(device);
1651         free(path);
1652         free(options);
1653         free(options2);
1654         free(fstype);
1655         free(d);
1656         free(p);
1657         free(o);
1658
1659         return r;
1660 }
1661
1662 static void mount_shutdown(Manager *m) {
1663         assert(m);
1664
1665         if (m->proc_self_mountinfo) {
1666                 fclose(m->proc_self_mountinfo);
1667                 m->proc_self_mountinfo = NULL;
1668         }
1669 }
1670
1671 static int mount_enumerate(Manager *m) {
1672         int r;
1673         struct epoll_event ev;
1674         assert(m);
1675
1676         if (!m->proc_self_mountinfo) {
1677                 if (!(m->proc_self_mountinfo = fopen("/proc/self/mountinfo", "re")))
1678                         return -errno;
1679
1680                 m->mount_watch.type = WATCH_MOUNT;
1681                 m->mount_watch.fd = fileno(m->proc_self_mountinfo);
1682
1683                 zero(ev);
1684                 ev.events = EPOLLPRI;
1685                 ev.data.ptr = &m->mount_watch;
1686
1687                 if (epoll_ctl(m->epoll_fd, EPOLL_CTL_ADD, m->mount_watch.fd, &ev) < 0)
1688                         return -errno;
1689         }
1690
1691         if ((r = mount_load_proc_self_mountinfo(m, false)) < 0)
1692                 goto fail;
1693
1694         return 0;
1695
1696 fail:
1697         mount_shutdown(m);
1698         return r;
1699 }
1700
1701 void mount_fd_event(Manager *m, int events) {
1702         Unit *u;
1703         int r;
1704
1705         assert(m);
1706         assert(events & EPOLLPRI);
1707
1708         /* The manager calls this for every fd event happening on the
1709          * /proc/self/mountinfo file, which informs us about mounting
1710          * table changes */
1711
1712         r = mount_load_proc_self_mountinfo(m, true);
1713         if (r < 0) {
1714                 log_error("Failed to reread /proc/self/mountinfo: %s", strerror(-r));
1715
1716                 /* Reset flags, just in case, for later calls */
1717                 LIST_FOREACH(units_by_type, u, m->units_by_type[UNIT_MOUNT]) {
1718                         Mount *mount = MOUNT(u);
1719
1720                         mount->is_mounted = mount->just_mounted = mount->just_changed = false;
1721                 }
1722
1723                 return;
1724         }
1725
1726         manager_dispatch_load_queue(m);
1727
1728         LIST_FOREACH(units_by_type, u, m->units_by_type[UNIT_MOUNT]) {
1729                 Mount *mount = MOUNT(u);
1730
1731                 if (!mount->is_mounted) {
1732                         /* This has just been unmounted. */
1733
1734                         mount->from_proc_self_mountinfo = false;
1735
1736                         switch (mount->state) {
1737
1738                         case MOUNT_MOUNTED:
1739                                 mount_enter_dead(mount, MOUNT_SUCCESS);
1740                                 break;
1741
1742                         default:
1743                                 mount_set_state(mount, mount->state);
1744                                 break;
1745
1746                         }
1747
1748                 } else if (mount->just_mounted || mount->just_changed) {
1749
1750                         /* New or changed mount entry */
1751
1752                         switch (mount->state) {
1753
1754                         case MOUNT_DEAD:
1755                         case MOUNT_FAILED:
1756                                 mount_enter_mounted(mount, MOUNT_SUCCESS);
1757                                 break;
1758
1759                         case MOUNT_MOUNTING:
1760                                 mount_enter_mounting_done(mount);
1761                                 break;
1762
1763                         default:
1764                                 /* Nothing really changed, but let's
1765                                  * issue an notification call
1766                                  * nonetheless, in case somebody is
1767                                  * waiting for this. (e.g. file system
1768                                  * ro/rw remounts.) */
1769                                 mount_set_state(mount, mount->state);
1770                                 break;
1771                         }
1772                 }
1773
1774                 /* Reset the flags for later calls */
1775                 mount->is_mounted = mount->just_mounted = mount->just_changed = false;
1776         }
1777 }
1778
1779 static void mount_reset_failed(Unit *u) {
1780         Mount *m = MOUNT(u);
1781
1782         assert(m);
1783
1784         if (m->state == MOUNT_FAILED)
1785                 mount_set_state(m, MOUNT_DEAD);
1786
1787         m->result = MOUNT_SUCCESS;
1788         m->reload_result = MOUNT_SUCCESS;
1789 }
1790
1791 static int mount_kill(Unit *u, KillWho who, int signo, DBusError *error) {
1792         return unit_kill_common(u, who, signo, -1, MOUNT(u)->control_pid, error);
1793 }
1794
1795 static const char* const mount_state_table[_MOUNT_STATE_MAX] = {
1796         [MOUNT_DEAD] = "dead",
1797         [MOUNT_MOUNTING] = "mounting",
1798         [MOUNT_MOUNTING_DONE] = "mounting-done",
1799         [MOUNT_MOUNTED] = "mounted",
1800         [MOUNT_REMOUNTING] = "remounting",
1801         [MOUNT_UNMOUNTING] = "unmounting",
1802         [MOUNT_MOUNTING_SIGTERM] = "mounting-sigterm",
1803         [MOUNT_MOUNTING_SIGKILL] = "mounting-sigkill",
1804         [MOUNT_REMOUNTING_SIGTERM] = "remounting-sigterm",
1805         [MOUNT_REMOUNTING_SIGKILL] = "remounting-sigkill",
1806         [MOUNT_UNMOUNTING_SIGTERM] = "unmounting-sigterm",
1807         [MOUNT_UNMOUNTING_SIGKILL] = "unmounting-sigkill",
1808         [MOUNT_FAILED] = "failed"
1809 };
1810
1811 DEFINE_STRING_TABLE_LOOKUP(mount_state, MountState);
1812
1813 static const char* const mount_exec_command_table[_MOUNT_EXEC_COMMAND_MAX] = {
1814         [MOUNT_EXEC_MOUNT] = "ExecMount",
1815         [MOUNT_EXEC_UNMOUNT] = "ExecUnmount",
1816         [MOUNT_EXEC_REMOUNT] = "ExecRemount",
1817 };
1818
1819 DEFINE_STRING_TABLE_LOOKUP(mount_exec_command, MountExecCommand);
1820
1821 static const char* const mount_result_table[_MOUNT_RESULT_MAX] = {
1822         [MOUNT_SUCCESS] = "success",
1823         [MOUNT_FAILURE_RESOURCES] = "resources",
1824         [MOUNT_FAILURE_TIMEOUT] = "timeout",
1825         [MOUNT_FAILURE_EXIT_CODE] = "exit-code",
1826         [MOUNT_FAILURE_SIGNAL] = "signal",
1827         [MOUNT_FAILURE_CORE_DUMP] = "core-dump"
1828 };
1829
1830 DEFINE_STRING_TABLE_LOOKUP(mount_result, MountResult);
1831
1832 const UnitVTable mount_vtable = {
1833         .object_size = sizeof(Mount),
1834
1835         .sections =
1836                 "Unit\0"
1837                 "Mount\0"
1838                 "Install\0",
1839
1840         .exec_context_offset = offsetof(Mount, exec_context),
1841         .exec_section = "Mount",
1842
1843         .no_alias = true,
1844         .no_instances = true,
1845
1846         .init = mount_init,
1847         .load = mount_load,
1848         .done = mount_done,
1849
1850         .coldplug = mount_coldplug,
1851
1852         .dump = mount_dump,
1853
1854         .start = mount_start,
1855         .stop = mount_stop,
1856         .reload = mount_reload,
1857
1858         .kill = mount_kill,
1859
1860         .serialize = mount_serialize,
1861         .deserialize_item = mount_deserialize_item,
1862
1863         .active_state = mount_active_state,
1864         .sub_state_to_string = mount_sub_state_to_string,
1865
1866         .check_gc = mount_check_gc,
1867
1868         .sigchld_event = mount_sigchld_event,
1869         .timer_event = mount_timer_event,
1870
1871         .reset_failed = mount_reset_failed,
1872
1873         .bus_interface = "org.freedesktop.systemd1.Mount",
1874         .bus_message_handler = bus_mount_message_handler,
1875         .bus_invalidating_properties =  bus_mount_invalidating_properties,
1876
1877         .enumerate = mount_enumerate,
1878         .shutdown = mount_shutdown,
1879
1880         .status_message_formats = {
1881                 .starting_stopping = {
1882                         [0] = "Mounting %s...",
1883                         [1] = "Unmounting %s...",
1884                 },
1885                 .finished_start_job = {
1886                         [JOB_DONE]       = "Mounted %s.",
1887                         [JOB_FAILED]     = "Failed to mount %s.",
1888                         [JOB_DEPENDENCY] = "Dependency failed for %s.",
1889                         [JOB_TIMEOUT]    = "Timed out mounting %s.",
1890                 },
1891                 .finished_stop_job = {
1892                         [JOB_DONE]       = "Unmounted %s.",
1893                         [JOB_FAILED]     = "Failed unmounting %s.",
1894                         [JOB_TIMEOUT]    = "Timed out unmounting %s.",
1895                 },
1896         },
1897 };