Bug Summary

File:build-scan/../src/sleep/sleep.c
Warning:line 346, column 13
Null pointer passed to 1st parameter expecting 'nonnull'

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-unknown-linux-gnu -analyze -disable-free -disable-llvm-verifier -discard-value-names -main-file-name sleep.c -analyzer-store=region -analyzer-opt-analyze-nested-blocks -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model static -mframe-pointer=all -relaxed-aliasing -menable-no-infs -menable-no-nans -menable-unsafe-fp-math -fno-signed-zeros -mreassociate -freciprocal-math -fdenormal-fp-math=preserve-sign,preserve-sign -ffp-contract=fast -fno-rounding-math -ffast-math -ffinite-math-only -mconstructor-aliases -munwind-tables -target-cpu x86-64 -tune-cpu generic -fno-split-dwarf-inlining -debugger-tuning=gdb -resource-dir /usr/lib64/clang/12.0.0 -include config.h -I systemd-sleep.p -I . -I .. -I src/basic -I ../src/basic -I src/shared -I ../src/shared -I src/systemd -I ../src/systemd -I src/journal -I ../src/journal -I src/journal-remote -I ../src/journal-remote -I src/nspawn -I ../src/nspawn -I src/resolve -I ../src/resolve -I src/timesync -I ../src/timesync -I ../src/time-wait-sync -I src/login -I ../src/login -I src/udev -I ../src/udev -I src/libudev -I ../src/libudev -I src/core -I ../src/core -I ../src/libsystemd/sd-bus -I ../src/libsystemd/sd-device -I ../src/libsystemd/sd-hwdb -I ../src/libsystemd/sd-id128 -I ../src/libsystemd/sd-netlink -I ../src/libsystemd/sd-network -I src/libsystemd-network -I ../src/libsystemd-network -D _FILE_OFFSET_BITS=64 -internal-isystem /usr/local/include -internal-isystem /usr/lib64/clang/12.0.0/include -internal-externc-isystem /include -internal-externc-isystem /usr/include -Wwrite-strings -Wno-unused-parameter -Wno-missing-field-initializers -Wno-unused-result -Wno-format-signedness -Wno-error=nonnull -std=gnu99 -fconst-strings -fdebug-compilation-dir /home/mrc0mmand/repos/@redhat-plumbers/systemd-rhel8/build-scan -ferror-limit 19 -fvisibility hidden -stack-protector 2 -fgnuc-version=4.2.1 -fcolor-diagnostics -analyzer-output=html -faddrsig -o /tmp/scan-build-2021-07-16-221226-1465241-1 -x c ../src/sleep/sleep.c
1/* SPDX-License-Identifier: LGPL-2.1+ */
2/***
3 Copyright © 2010-2017 Canonical
4 Copyright © 2018 Dell Inc.
5***/
6
7#include <errno(*__errno_location ()).h>
8#include <getopt.h>
9#include <linux1/fiemap.h>
10#include <stdio.h>
11
12#include "sd-messages.h"
13
14#include "parse-util.h"
15#include "def.h"
16#include "exec-util.h"
17#include "fd-util.h"
18#include "fileio.h"
19#include "log.h"
20#include "sleep-config.h"
21#include "stdio-util.h"
22#include "string-util.h"
23#include "strv.h"
24#include "util.h"
25
26static char* arg_verb = NULL((void*)0);
27
28static int write_hibernate_location_info(void) {
29 _cleanup_free___attribute__((cleanup(freep))) char *device = NULL((void*)0), *type = NULL((void*)0);
30 _cleanup_free___attribute__((cleanup(freep))) struct fiemap *fiemap = NULL((void*)0);
31 char offset_str[DECIMAL_STR_MAX(uint64_t)(2+(sizeof(uint64_t) <= 1 ? 3 : sizeof(uint64_t) <= 2 ?
5 : sizeof(uint64_t) <= 4 ? 10 : sizeof(uint64_t) <= 8
? 20 : sizeof(int[-2*(sizeof(uint64_t) > 8)])))
];
32 char device_str[DECIMAL_STR_MAX(uint64_t)(2+(sizeof(uint64_t) <= 1 ? 3 : sizeof(uint64_t) <= 2 ?
5 : sizeof(uint64_t) <= 4 ? 10 : sizeof(uint64_t) <= 8
? 20 : sizeof(int[-2*(sizeof(uint64_t) > 8)])))
];
33 _cleanup_close___attribute__((cleanup(closep))) int fd = -1;
34 struct stat stb;
35 uint64_t offset;
36 int r;
37
38 r = find_hibernate_location(&device, &type, NULL((void*)0), NULL((void*)0));
39 if (r < 0)
40 return log_debug_errno(r, "Unable to find hibernation location: %m")({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 40, __func__, "Unable to find hibernation location: %m"
) : -abs(_e); })
;
41
42 /* if it's a swap partition, we just write the disk to /sys/power/resume */
43 if (streq(type, "partition")(strcmp((type),("partition")) == 0))
44 return write_string_file("/sys/power/resume", device, 0);
45 else if (!streq(type, "file")(strcmp((type),("file")) == 0))
46 return log_debug_errno(EINVAL, "Invalid hibernate type %s: %m",({ int _level = ((7)), _e = ((22)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 47, __func__, "Invalid hibernate type %s: %m"
, type) : -abs(_e); })
47 type)({ int _level = ((7)), _e = ((22)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 47, __func__, "Invalid hibernate type %s: %m"
, type) : -abs(_e); })
;
48
49 /* Only available in 4.17+ */
50 if (access("/sys/power/resume_offset", F_OK0) < 0) {
51 if (errno(*__errno_location ()) == ENOENT2)
52 return 0;
53 return log_debug_errno(errno, "/sys/power/resume_offset unavailable: %m")({ int _level = ((7)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 53, __func__, "/sys/power/resume_offset unavailable: %m"
) : -abs(_e); })
;
54 }
55
56 r = access("/sys/power/resume_offset", W_OK2);
57 if (r < 0)
58 return log_debug_errno(errno, "/sys/power/resume_offset not writeable: %m")({ int _level = ((7)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 58, __func__, "/sys/power/resume_offset not writeable: %m"
) : -abs(_e); })
;
59
60 fd = open(device, O_RDONLY00 | O_CLOEXEC02000000 | O_NONBLOCK04000);
61 if (fd < 0)
62 return log_debug_errno(errno, "Unable to open '%s': %m", device)({ int _level = ((7)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 62, __func__, "Unable to open '%s': %m"
, device) : -abs(_e); })
;
63 r = fstat(fd, &stb);
64 if (r < 0)
65 return log_debug_errno(errno, "Unable to stat %s: %m", device)({ int _level = ((7)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 65, __func__, "Unable to stat %s: %m"
, device) : -abs(_e); })
;
66 r = read_fiemap(fd, &fiemap);
67 if (r < 0)
68 return log_debug_errno(r, "Unable to read extent map for '%s': %m",({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 69, __func__, "Unable to read extent map for '%s': %m"
, device) : -abs(_e); })
69 device)({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 69, __func__, "Unable to read extent map for '%s': %m"
, device) : -abs(_e); })
;
70 if (fiemap->fm_mapped_extents == 0) {
71 log_debug("No extents found in '%s'", device)({ int _level = (((7))), _e = ((0)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 71, __func__, "No extents found in '%s'"
, device) : -abs(_e); })
;
72 return -EINVAL22;
73 }
74 offset = fiemap->fm_extents[0].fe_physical / page_size();
75 xsprintf(offset_str, "%" PRIu64, offset)do { if ((__builtin_expect(!!(!(((size_t) snprintf(offset_str
, __extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(offset_str), typeof(&*(offset_str))), sizeof(offset_str
)/sizeof((offset_str)[0]), ((void)0))), "%" "l" "u", offset) <
(__extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(offset_str), typeof(&*(offset_str))), sizeof(offset_str
)/sizeof((offset_str)[0]), ((void)0))))))),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("xsprintf: " "offset_str" "[] must be big enough"
), "../src/sleep/sleep.c", 75, __PRETTY_FUNCTION__); } while (
0)
;
76 r = write_string_file("/sys/power/resume_offset", offset_str, 0);
77 if (r < 0)
78 return log_debug_errno(r, "Failed to write offset '%s': %m",({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 79, __func__, "Failed to write offset '%s': %m"
, offset_str) : -abs(_e); })
79 offset_str)({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 79, __func__, "Failed to write offset '%s': %m"
, offset_str) : -abs(_e); })
;
80
81 xsprintf(device_str, "%lx", (unsigned long)stb.st_dev)do { if ((__builtin_expect(!!(!(((size_t) snprintf(device_str
, __extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(device_str), typeof(&*(device_str))), sizeof(device_str
)/sizeof((device_str)[0]), ((void)0))), "%lx", (unsigned long
)stb.st_dev) < (__extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(device_str), typeof(&*(device_str))), sizeof(device_str
)/sizeof((device_str)[0]), ((void)0))))))),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("xsprintf: " "device_str" "[] must be big enough"
), "../src/sleep/sleep.c", 81, __PRETTY_FUNCTION__); } while (
0)
;
82 r = write_string_file("/sys/power/resume", device_str, 0);
83 if (r < 0)
84 return log_debug_errno(r, "Failed to write device '%s': %m",({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 85, __func__, "Failed to write device '%s': %m"
, device_str) : -abs(_e); })
85 device_str)({ int _level = ((7)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 85, __func__, "Failed to write device '%s': %m"
, device_str) : -abs(_e); })
;
86 return 0;
87}
88
89static int write_mode(char **modes) {
90 int r = 0;
91 char **mode;
92
93 STRV_FOREACH(mode, modes)for ((mode) = (modes); (mode) && *(mode); (mode)++) {
94 int k;
95
96 k = write_string_file("/sys/power/disk", *mode, 0);
97 if (k == 0)
98 return 0;
99
100 log_debug_errno(k, "Failed to write '%s' to /sys/power/disk: %m",({ int _level = ((7)), _e = ((k)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 101, __func__, "Failed to write '%s' to /sys/power/disk: %m"
, *mode) : -abs(_e); })
101 *mode)({ int _level = ((7)), _e = ((k)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 101, __func__, "Failed to write '%s' to /sys/power/disk: %m"
, *mode) : -abs(_e); })
;
102 if (r == 0)
103 r = k;
104 }
105
106 return r;
107}
108
109static int write_state(FILE **f, char **states) {
110 char **state;
111 int r = 0;
112
113 STRV_FOREACH(state, states)for ((state) = (states); (state) && *(state); (state)
++)
{
114 int k;
115
116 k = write_string_stream(*f, *state, 0);
117 if (k == 0)
118 return 0;
119 log_debug_errno(k, "Failed to write '%s' to /sys/power/state: %m",({ int _level = ((7)), _e = ((k)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 120, __func__, "Failed to write '%s' to /sys/power/state: %m"
, *state) : -abs(_e); })
120 *state)({ int _level = ((7)), _e = ((k)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 120, __func__, "Failed to write '%s' to /sys/power/state: %m"
, *state) : -abs(_e); })
;
121 if (r == 0)
122 r = k;
123
124 fclose(*f);
125 *f = fopen("/sys/power/state", "we");
126 if (!*f)
127 return -errno(*__errno_location ());
128 }
129
130 return r;
131}
132
133static int execute(char **modes, char **states) {
134
135 char *arguments[] = {
136 NULL((void*)0),
137 (char*) "pre",
138 arg_verb,
139 NULL((void*)0)
140 };
141 static const char* const dirs[] = {
142 SYSTEM_SLEEP_PATH"/usr/lib/systemd/system-sleep",
143 NULL((void*)0)
144 };
145
146 int r;
147 _cleanup_fclose___attribute__((cleanup(fclosep))) FILE *f = NULL((void*)0);
148
149 /* This file is opened first, so that if we hit an error,
150 * we can abort before modifying any state. */
151 f = fopen("/sys/power/state", "we");
152 if (!f)
153 return log_error_errno(errno, "Failed to open /sys/power/state: %m")({ int _level = ((3)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 153, __func__, "Failed to open /sys/power/state: %m"
) : -abs(_e); })
;
154
155 /* Configure the hibernation mode */
156 if (!strv_isempty(modes)) {
157 r = write_hibernate_location_info();
158 if (r < 0)
159 return log_error_errno(r, "Failed to write hibernation disk offset: %m")({ int _level = ((3)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 159, __func__, "Failed to write hibernation disk offset: %m"
) : -abs(_e); })
;
160 r = write_mode(modes);
161 if (r < 0)
162 return log_error_errno(r, "Failed to write mode to /sys/power/disk: %m")({ int _level = ((3)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 162, __func__, "Failed to write mode to /sys/power/disk: %m"
) : -abs(_e); })
;;
163 }
164
165 execute_directories(dirs, DEFAULT_TIMEOUT_USEC(90*((usec_t) 1000000ULL)), NULL((void*)0), NULL((void*)0), arguments);
166
167 log_struct(LOG_INFO,log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 170, __func__, "MESSAGE_ID=" "6b" "bd"
"95" "ee" "97" "79" "41" "e4" "97" "c4" "8b" "e2" "7c" "25" "41"
"28", "MESSAGE=" "Suspending system...", "SLEEP=%s", arg_verb
, ((void*)0))
168 "MESSAGE_ID=" SD_MESSAGE_SLEEP_START_STR,log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 170, __func__, "MESSAGE_ID=" "6b" "bd"
"95" "ee" "97" "79" "41" "e4" "97" "c4" "8b" "e2" "7c" "25" "41"
"28", "MESSAGE=" "Suspending system...", "SLEEP=%s", arg_verb
, ((void*)0))
169 LOG_MESSAGE("Suspending system..."),log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 170, __func__, "MESSAGE_ID=" "6b" "bd"
"95" "ee" "97" "79" "41" "e4" "97" "c4" "8b" "e2" "7c" "25" "41"
"28", "MESSAGE=" "Suspending system...", "SLEEP=%s", arg_verb
, ((void*)0))
170 "SLEEP=%s", arg_verb)log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 170, __func__, "MESSAGE_ID=" "6b" "bd"
"95" "ee" "97" "79" "41" "e4" "97" "c4" "8b" "e2" "7c" "25" "41"
"28", "MESSAGE=" "Suspending system...", "SLEEP=%s", arg_verb
, ((void*)0))
;
171
172 r = write_state(&f, states);
173 if (r < 0)
174 return log_error_errno(r, "Failed to write /sys/power/state: %m")({ int _level = ((3)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 174, __func__, "Failed to write /sys/power/state: %m"
) : -abs(_e); })
;
175
176 log_struct(LOG_INFO,log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 179, __func__, "MESSAGE_ID=" "88" "11"
"e6" "df" "2a" "8e" "40" "f5" "8a" "94" "ce" "a2" "6f" "8e" "bf"
"14", "MESSAGE=" "System resumed.", "SLEEP=%s", arg_verb, ((
void*)0))
177 "MESSAGE_ID=" SD_MESSAGE_SLEEP_STOP_STR,log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 179, __func__, "MESSAGE_ID=" "88" "11"
"e6" "df" "2a" "8e" "40" "f5" "8a" "94" "ce" "a2" "6f" "8e" "bf"
"14", "MESSAGE=" "System resumed.", "SLEEP=%s", arg_verb, ((
void*)0))
178 LOG_MESSAGE("System resumed."),log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 179, __func__, "MESSAGE_ID=" "88" "11"
"e6" "df" "2a" "8e" "40" "f5" "8a" "94" "ce" "a2" "6f" "8e" "bf"
"14", "MESSAGE=" "System resumed.", "SLEEP=%s", arg_verb, ((
void*)0))
179 "SLEEP=%s", arg_verb)log_struct_internal(((LOG_REALM_SYSTEMD) << 10 | (6)), 0
, "../src/sleep/sleep.c", 179, __func__, "MESSAGE_ID=" "88" "11"
"e6" "df" "2a" "8e" "40" "f5" "8a" "94" "ce" "a2" "6f" "8e" "bf"
"14", "MESSAGE=" "System resumed.", "SLEEP=%s", arg_verb, ((
void*)0))
;
180
181 arguments[1] = (char*) "post";
182 execute_directories(dirs, DEFAULT_TIMEOUT_USEC(90*((usec_t) 1000000ULL)), NULL((void*)0), NULL((void*)0), arguments);
183
184 return r;
185}
186
187static int read_wakealarm(uint64_t *result) {
188 _cleanup_free___attribute__((cleanup(freep))) char *t = NULL((void*)0);
189
190 if (read_one_line_file("/sys/class/rtc/rtc0/since_epoch", &t) >= 0)
191 return safe_atou64(t, result);
192 return -EBADF9;
193}
194
195static int write_wakealarm(const char *str) {
196
197 _cleanup_fclose___attribute__((cleanup(fclosep))) FILE *f = NULL((void*)0);
198 int r;
199
200 f = fopen("/sys/class/rtc/rtc0/wakealarm", "we");
201 if (!f)
202 return log_error_errno(errno, "Failed to open /sys/class/rtc/rtc0/wakealarm: %m")({ int _level = ((3)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 202, __func__, "Failed to open /sys/class/rtc/rtc0/wakealarm: %m"
) : -abs(_e); })
;
203
204 r = write_string_stream(f, str, 0);
205 if (r < 0)
206 return log_error_errno(r, "Failed to write '%s' to /sys/class/rtc/rtc0/wakealarm: %m", str)({ int _level = ((3)), _e = ((r)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 206, __func__, "Failed to write '%s' to /sys/class/rtc/rtc0/wakealarm: %m"
, str) : -abs(_e); })
;
207
208 return 0;
209}
210
211static int execute_s2h(usec_t hibernate_delay_sec) {
212
213 _cleanup_strv_free___attribute__((cleanup(strv_freep))) char **hibernate_modes = NULL((void*)0), **hibernate_states = NULL((void*)0),
214 **suspend_modes = NULL((void*)0), **suspend_states = NULL((void*)0);
215 usec_t orig_time, cmp_time;
216 char time_str[DECIMAL_STR_MAX(uint64_t)(2+(sizeof(uint64_t) <= 1 ? 3 : sizeof(uint64_t) <= 2 ?
5 : sizeof(uint64_t) <= 4 ? 10 : sizeof(uint64_t) <= 8
? 20 : sizeof(int[-2*(sizeof(uint64_t) > 8)])))
];
217 int r;
218
219 r = parse_sleep_config("suspend", &suspend_modes, &suspend_states,
220 NULL((void*)0));
221 if (r < 0)
222 return r;
223
224 r = parse_sleep_config("hibernate", &hibernate_modes,
225 &hibernate_states, NULL((void*)0));
226 if (r < 0)
227 return r;
228
229 r = read_wakealarm(&orig_time);
230 if (r < 0)
231 return log_error_errno(errno, "Failed to read time: %d", r)({ int _level = ((3)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 231, __func__, "Failed to read time: %d"
, r) : -abs(_e); })
;
232
233 orig_time += hibernate_delay_sec / USEC_PER_SEC((usec_t) 1000000ULL);
234 xsprintf(time_str, "%" PRIu64, orig_time)do { if ((__builtin_expect(!!(!(((size_t) snprintf(time_str, __extension__
(__builtin_choose_expr( !__builtin_types_compatible_p(typeof
(time_str), typeof(&*(time_str))), sizeof(time_str)/sizeof
((time_str)[0]), ((void)0))), "%" "l" "u", orig_time) < (__extension__
(__builtin_choose_expr( !__builtin_types_compatible_p(typeof
(time_str), typeof(&*(time_str))), sizeof(time_str)/sizeof
((time_str)[0]), ((void)0))))))),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("xsprintf: " "time_str" "[] must be big enough"
), "../src/sleep/sleep.c", 234, __PRETTY_FUNCTION__); } while
(0)
;
235
236 r = write_wakealarm(time_str);
237 if (r < 0)
238 return r;
239
240 log_debug("Set RTC wake alarm for %s", time_str)({ int _level = (((7))), _e = ((0)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 240, __func__, "Set RTC wake alarm for %s"
, time_str) : -abs(_e); })
;
241
242 r = execute(suspend_modes, suspend_states);
243 if (r < 0)
244 return r;
245
246 r = read_wakealarm(&cmp_time);
247 if (r < 0)
248 return log_error_errno(errno, "Failed to read time: %d", r)({ int _level = ((3)), _e = (((*__errno_location ()))), _realm
= (LOG_REALM_SYSTEMD); (log_get_max_level_realm(_realm) >=
((_level) & 0x07)) ? log_internal_realm(((_realm) <<
10 | (_level)), _e, "../src/sleep/sleep.c", 248, __func__, "Failed to read time: %d"
, r) : -abs(_e); })
;
249
250 /* reset RTC */
251 r = write_wakealarm("0");
252 if (r < 0)
253 return r;
254
255 log_debug("Woke up at %"PRIu64, cmp_time)({ int _level = (((7))), _e = ((0)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 255, __func__, "Woke up at %""l" "u"
, cmp_time) : -abs(_e); })
;
256
257 /* if woken up after alarm time, hibernate */
258 if (cmp_time >= orig_time)
259 r = execute(hibernate_modes, hibernate_states);
260
261 return r;
262}
263
264static void help(void) {
265 printf("%s COMMAND\n\n"
266 "Suspend the system, hibernate the system, or both.\n\n"
267 "Commands:\n"
268 " -h --help Show this help and exit\n"
269 " --version Print version string and exit\n"
270 " suspend Suspend the system\n"
271 " hibernate Hibernate the system\n"
272 " hybrid-sleep Both hibernate and suspend the system\n"
273 " suspend-then-hibernate Initially suspend and then hibernate\n"
274 " the system after a fixed period of time\n"
275 , program_invocation_short_name);
276}
277
278static int parse_argv(int argc, char *argv[]) {
279 enum {
280 ARG_VERSION = 0x100,
281 };
282
283 static const struct option options[] = {
284 { "help", no_argument0, NULL((void*)0), 'h' },
285 { "version", no_argument0, NULL((void*)0), ARG_VERSION },
286 {}
287 };
288
289 int c;
290
291 assert(argc >= 0)do { if ((__builtin_expect(!!(!(argc >= 0)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("argc >= 0"), "../src/sleep/sleep.c",
291, __PRETTY_FUNCTION__); } while (0)
;
292 assert(argv)do { if ((__builtin_expect(!!(!(argv)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("argv"), "../src/sleep/sleep.c", 292, __PRETTY_FUNCTION__
); } while (0)
;
293
294 while ((c = getopt_long(argc, argv, "h", options, NULL((void*)0))) >= 0)
295 switch(c) {
296 case 'h':
297 help();
298 return 0; /* done */
299
300 case ARG_VERSION:
301 return version();
302
303 case '?':
304 return -EINVAL22;
305
306 default:
307 assert_not_reached("Unhandled option")do { log_assert_failed_unreachable_realm(LOG_REALM_SYSTEMD, (
"Unhandled option"), "../src/sleep/sleep.c", 307, __PRETTY_FUNCTION__
); } while (0)
;
308 }
309
310 if (argc - optind != 1) {
311 log_error("Usage: %s COMMAND",({ int _level = (((3))), _e = ((0)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 312, __func__, "Usage: %s COMMAND",
program_invocation_short_name) : -abs(_e); })
312 program_invocation_short_name)({ int _level = (((3))), _e = ((0)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 312, __func__, "Usage: %s COMMAND",
program_invocation_short_name) : -abs(_e); })
;
313 return -EINVAL22;
314 }
315
316 arg_verb = argv[optind];
317
318 if (!streq(arg_verb, "suspend")(strcmp((arg_verb),("suspend")) == 0) &&
319 !streq(arg_verb, "hibernate")(strcmp((arg_verb),("hibernate")) == 0) &&
320 !streq(arg_verb, "hybrid-sleep")(strcmp((arg_verb),("hybrid-sleep")) == 0) &&
321 !streq(arg_verb, "suspend-then-hibernate")(strcmp((arg_verb),("suspend-then-hibernate")) == 0)) {
322 log_error("Unknown command '%s'.", arg_verb)({ int _level = (((3))), _e = ((0)), _realm = (LOG_REALM_SYSTEMD
); (log_get_max_level_realm(_realm) >= ((_level) & 0x07
)) ? log_internal_realm(((_realm) << 10 | (_level)), _e
, "../src/sleep/sleep.c", 322, __func__, "Unknown command '%s'."
, arg_verb) : -abs(_e); })
;
323 return -EINVAL22;
324 }
325
326 return 1 /* work to do */;
327}
328
329int main(int argc, char *argv[]) {
330 _cleanup_strv_free___attribute__((cleanup(strv_freep))) char **modes = NULL((void*)0), **states = NULL((void*)0);
331 usec_t delay = 0;
332 int r;
333
334 log_set_target(LOG_TARGET_AUTO);
335 log_parse_environment()log_parse_environment_realm(LOG_REALM_SYSTEMD);
336 log_open();
337
338 r = parse_argv(argc, argv);
339 if (r <= 0)
1
Assuming 'r' is > 0
2
Taking false branch
340 goto finish;
341
342 r = parse_sleep_config(arg_verb, &modes, &states, &delay);
343 if (r < 0)
3
Assuming 'r' is >= 0
4
Taking false branch
344 goto finish;
345
346 if (streq(arg_verb, "suspend-then-hibernate")(strcmp((arg_verb),("suspend-then-hibernate")) == 0))
5
Null pointer passed to 1st parameter expecting 'nonnull'
347 r = execute_s2h(delay);
348 else
349 r = execute(modes, states);
350finish:
351 return r < 0 ? EXIT_FAILURE1 : EXIT_SUCCESS0;
352}