]> git.ipfire.org Git - thirdparty/systemd.git/blob - src/hibernate-resume/hibernate-resume-generator.c
Merge pull request #4510 from keszybz/tree-wide-cleanups
[thirdparty/systemd.git] / src / hibernate-resume / hibernate-resume-generator.c
1 /***
2 This file is part of systemd.
3
4 Copyright 2014 Ivan Shapovalov
5
6 systemd is free software; you can redistribute it and/or modify it
7 under the terms of the GNU Lesser General Public License as published by
8 the Free Software Foundation; either version 2.1 of the License, or
9 (at your option) any later version.
10
11 systemd is distributed in the hope that it will be useful, but
12 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 License
17 along with systemd; If not, see <http://www.gnu.org/licenses/>.
18 ***/
19
20 #include <errno.h>
21 #include <stdio.h>
22
23 #include "alloc-util.h"
24 #include "fstab-util.h"
25 #include "log.h"
26 #include "mkdir.h"
27 #include "proc-cmdline.h"
28 #include "special.h"
29 #include "string-util.h"
30 #include "unit-name.h"
31 #include "util.h"
32
33 static const char *arg_dest = "/tmp";
34 static char *arg_resume_dev = NULL;
35
36 static int parse_proc_cmdline_item(const char *key, const char *value, void *data) {
37
38 if (streq(key, "resume") && value) {
39 free(arg_resume_dev);
40 arg_resume_dev = fstab_node_to_udev_node(value);
41 if (!arg_resume_dev)
42 return log_oom();
43 }
44
45 return 0;
46 }
47
48 static int process_resume(void) {
49 _cleanup_free_ char *name = NULL, *lnk = NULL;
50 int r;
51
52 if (!arg_resume_dev)
53 return 0;
54
55 r = unit_name_from_path_instance("systemd-hibernate-resume", arg_resume_dev, ".service", &name);
56 if (r < 0)
57 return log_error_errno(r, "Failed to generate unit name: %m");
58
59 lnk = strjoin(arg_dest, "/" SPECIAL_SYSINIT_TARGET ".wants/", name);
60 if (!lnk)
61 return log_oom();
62
63 mkdir_parents_label(lnk, 0755);
64 if (symlink(SYSTEM_DATA_UNIT_PATH "/systemd-hibernate-resume@.service", lnk) < 0)
65 return log_error_errno(errno, "Failed to create symlink %s: %m", lnk);
66
67 return 0;
68 }
69
70 int main(int argc, char *argv[]) {
71 int r = 0;
72
73 if (argc > 1 && argc != 4) {
74 log_error("This program takes three or no arguments.");
75 return EXIT_FAILURE;
76 }
77
78 if (argc > 1)
79 arg_dest = argv[1];
80
81 log_set_target(LOG_TARGET_SAFE);
82 log_parse_environment();
83 log_open();
84
85 umask(0022);
86
87 /* Don't even consider resuming outside of initramfs. */
88 if (!in_initrd())
89 return EXIT_SUCCESS;
90
91 r = parse_proc_cmdline(parse_proc_cmdline_item, NULL, false);
92 if (r < 0)
93 log_warning_errno(r, "Failed to parse kernel command line, ignoring: %m");
94
95 r = process_resume();
96 free(arg_resume_dev);
97
98 return r < 0 ? EXIT_FAILURE : EXIT_SUCCESS;
99 }