Merge ~mitchdz/ubuntu/+source/ec2-hibinit-agent:mitch/xenial-imdsv2 into ubuntu/+source/ec2-hibinit-agent:ubuntu/xenial-devel
- Git
- lp:~mitchdz/ubuntu/+source/ec2-hibinit-agent
- mitch/xenial-imdsv2
- Merge into ubuntu/xenial-devel
Proposed by
Mitchell Dzurick
Status: | Merged | ||||
---|---|---|---|---|---|
Merge reported by: | Mitchell Dzurick | ||||
Merged at revision: | 577603dc5c8a0c3bce9c6992f28532985a514c2e | ||||
Proposed branch: | ~mitchdz/ubuntu/+source/ec2-hibinit-agent:mitch/xenial-imdsv2 | ||||
Merge into: | ubuntu/+source/ec2-hibinit-agent:ubuntu/xenial-devel | ||||
Diff against target: |
375 lines (+312/-2) 8 files modified
debian/changelog (+16/-0) debian/ec2-hibinit-agent.install (+1/-0) debian/hibinit-agent.system-sleep (+1/-2) debian/hibinit-resume (+48/-0) debian/patches/lp1941785-Add-support-for-IMDSv2.patch (+161/-0) debian/patches/lp1968805-Swapon-with-maximum-priority-before-hibernation.patch (+63/-0) debian/patches/lp2023924-remove-quotes-from-state-dir.patch (+19/-0) debian/patches/series (+3/-0) |
||||
Related bugs: |
|
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
git-ubuntu import | Pending | ||
Review via email: mp+456027@code.launchpad.net |
Commit message
Description of the change
To post a comment you must log in.
- 92c89f4... by Mitchell Dzurick
-
debian/
hibinit- resume: Add extra steps around swapoff to avoid OOM errors. - 4054ec8... by Mitchell Dzurick
-
d/p/lp1968805-
Swapon- with-maximum- priority- before- hibernation. patch: Swapon with maximum priority right before hibernation. - 13f7bf9... by Mitchell Dzurick
-
d/p/{lp1941785,
lp2023924} *: add IMDSv2, fix quotes bug created from IMDSv2 patch
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | diff --git a/debian/changelog b/debian/changelog |
2 | index b366dca..b4f95a5 100644 |
3 | --- a/debian/changelog |
4 | +++ b/debian/changelog |
5 | @@ -1,3 +1,19 @@ |
6 | +ec2-hibinit-agent (1.0.0-0ubuntu4~16.04.5) xenial; urgency=medium |
7 | + |
8 | + * d/p/lp2023924-remove-quotes-from-state-dir.patch: fixes an issue where a |
9 | + weird directory would be created in root (LP: #2023924) |
10 | + * d/p/lp1941785-Add-support-for-IMDSv2.patch: allow hibernation of |
11 | + AWS EC2 instances with IMDSv2 (LP: #1941785) |
12 | + * Swapon with maximum priority right before hibernation. This resolves |
13 | + swapfile priority issues with additional or multiple swapfiles enabled. |
14 | + (LP: #1968805) |
15 | + - d/p/lp1968805-Swapon-with-maximum-priority-before-hibernation.patch |
16 | + * debian/hibinit-resume: Add extra steps around swapoff to avoid OOM errors. |
17 | + Also work around xen-netfront not resuming properly. |
18 | + Thanks to Francis Ginther for the initial patch (LP: #1863242, #1864041) |
19 | + |
20 | + -- Mitchell Dzurick <mitchell.dzurick@canonical.com> Tue, 21 Nov 2023 15:31:14 -0700 |
21 | + |
22 | ec2-hibinit-agent (1.0.0-0ubuntu4~16.04.4) xenial; urgency=medium |
23 | |
24 | * Always set resume device by PARTUUID instead of by device name. |
25 | diff --git a/debian/ec2-hibinit-agent.install b/debian/ec2-hibinit-agent.install |
26 | index b140d28..5b1b272 100755 |
27 | --- a/debian/ec2-hibinit-agent.install |
28 | +++ b/debian/ec2-hibinit-agent.install |
29 | @@ -5,5 +5,6 @@ debian/ec2-hibinit-agent-ignore-powerkey.conf usr/lib/systemd/logind.conf.d/ |
30 | debian/hibinit-agent.system-sleep => lib/systemd/system-sleep/hibinit-agent |
31 | debian/hibinit-power etc/acpi/events |
32 | debian/hibinit-power.sh etc/acpi/actions |
33 | +debian/hibinit-resume usr/lib/ec2-hibinit-agent |
34 | etc/hibinit-config.cfg |
35 | agent/* usr/bin/ |
36 | diff --git a/debian/hibinit-agent.system-sleep b/debian/hibinit-agent.system-sleep |
37 | index 914161b..62db7bd 100755 |
38 | --- a/debian/hibinit-agent.system-sleep |
39 | +++ b/debian/hibinit-agent.system-sleep |
40 | @@ -4,8 +4,7 @@ set -e |
41 | if [ "$2" = "hibernate" ] || [ "$2" = "hybrid-sleep" ]; then |
42 | case "$1" in |
43 | post) |
44 | - systemctl restart --no-block systemd-networkd |
45 | - systemd-run --no-block --service-type=oneshot swapoff /swap-hibinit |
46 | + systemd-run --no-block --service-type=oneshot /usr/lib/ec2-hibinit-agent/hibinit-resume |
47 | ;; |
48 | esac |
49 | fi |
50 | diff --git a/debian/hibinit-resume b/debian/hibinit-resume |
51 | new file mode 100755 |
52 | index 0000000..e83fe2c |
53 | --- /dev/null |
54 | +++ b/debian/hibinit-resume |
55 | @@ -0,0 +1,48 @@ |
56 | +#!/bin/bash |
57 | +# |
58 | +# Resume from hibernation on EC2 and apply workarounds for various issues |
59 | +# |
60 | +# Copyright (C) 2020 Canonical Ltd. |
61 | +# |
62 | + |
63 | +set -e |
64 | + |
65 | +# Starting hibinit resume actions |
66 | +echo "hibinit-resume: begin" >> /var/log/hibinit-resume.log |
67 | + |
68 | +# Give some time to make sure the system is fully up and running, see LP: #1864041 |
69 | +sleep 2 |
70 | + |
71 | +# Make sure the network is properly resumed |
72 | +echo "restarting network" >> /var/log/hibinit-resume.log |
73 | +if grep -q xen_netfront /proc/modules; then |
74 | + # Xen netfront workaround LP: #1864041 |
75 | + modprobe -r xen_netfront |
76 | + modprobe xen_netfront |
77 | +fi |
78 | +systemctl restart --no-block systemd-networkd |
79 | + |
80 | +# Temporarily set memory allocation policy to "always overcommit". With |
81 | +# the default overcommit policy some applications might experience |
82 | +# out-of-memory errors. Setting the policy to "always overcommit" seems |
83 | +# to be a safe way to prevent these errors. |
84 | +OVERCOMMIT_POLICY=$(cat /proc/sys/vm/overcommit_memory) |
85 | +echo 1 > /proc/sys/vm/overcommit_memory |
86 | +# Start swapoff and make sure swap file is gone |
87 | +while :; do |
88 | + echo "starting swapoff" >> /var/log/hibinit-resume.log |
89 | + swapoff /swap-hibinit |
90 | + if grep -q swap-hibinit /proc/swaps; then |
91 | + echo "swap still active" >> /var/log/hibinit-resume.log |
92 | + sleep 10 |
93 | + else |
94 | + break |
95 | + fi |
96 | +done |
97 | +echo "swap disabled" >> /var/log/hibinit-resume.log |
98 | +cat /proc/swaps >> /var/log/hibinit-resume.log |
99 | +# Restore previou overcommit policy |
100 | +echo "$OVERCOMMIT_POLICY" > /proc/sys/vm/overcommit_memory |
101 | + |
102 | +# All done |
103 | +echo "hibinit-resume: completed " >> /var/log/hibinit-resume.log |
104 | diff --git a/debian/patches/lp1941785-Add-support-for-IMDSv2.patch b/debian/patches/lp1941785-Add-support-for-IMDSv2.patch |
105 | new file mode 100644 |
106 | index 0000000..6855eb2 |
107 | --- /dev/null |
108 | +++ b/debian/patches/lp1941785-Add-support-for-IMDSv2.patch |
109 | @@ -0,0 +1,161 @@ |
110 | +Description: Add support for IMDSv2 |
111 | +Author: Frederick Lefebvre <fredlef@amazon.com> |
112 | +Origin: backport, https://github.com/aws/amazon-ec2-hibinit-agent/commit/9d9bca5c61fa9256289e68c88bd3747af2f62e28 |
113 | +Bug-Ubuntu: https://bugs.launchpad.net/ubuntu/+source/ec2-hibinit-agent/+bug/1941785 |
114 | +Last-Update: 2023-05-16 |
115 | +--- |
116 | +This patch header follows DEP-3: http://dep.debian.net/deps/dep3/ |
117 | +--- a/agent/hibinit-agent |
118 | ++++ b/agent/hibinit-agent |
119 | +@@ -18,6 +18,7 @@ |
120 | + import sys |
121 | + import syslog |
122 | + import math |
123 | ++import requests |
124 | + from subprocess import check_call, check_output, STDOUT |
125 | + from threading import Thread |
126 | + from math import ceil |
127 | +@@ -25,11 +26,6 @@ |
128 | + |
129 | + |
130 | + try: |
131 | +- from urllib.request import urlopen, Request |
132 | +-except ImportError: |
133 | +- from urllib2 import urlopen, Request, HTTPError |
134 | +- |
135 | +-try: |
136 | + from ConfigParser import ConfigParser, NoSectionError, NoOptionError |
137 | + except: |
138 | + from configparser import ConfigParser, NoSectionError, NoOptionError |
139 | +@@ -41,7 +37,12 @@ |
140 | + log_to_syslog = True |
141 | + log_to_stderr = True |
142 | + SWAP_FILE = '/swap-hibinit' |
143 | +-URL = "http://169.254.169.254/latest/meta-data/hibernation/configured" |
144 | ++ |
145 | ++DEFAULT_STATE_DIR = '/var/lib/hibinit-agent' |
146 | ++HIB_ENABLED_FILE = "hibernation-enabled" |
147 | ++IMDS_BASEURL = 'http://169.254.169.254' |
148 | ++IMDS_API_TOKEN_PATH = 'latest/api/token' |
149 | ++IMDS_SPOT_ACTION_PATH = 'latest/meta-data/hibernation/configured' |
150 | + |
151 | + def log(message): |
152 | + if log_to_syslog: |
153 | +@@ -314,6 +315,9 @@ |
154 | + get_int('swap', 'percentage-of-ram'), args.swap_ram_percentage, 100) |
155 | + self.swap_mb = self.merge( |
156 | + get_int('swap', 'target-size-mb'), args.swap_target_size_mb, 4000) |
157 | ++ self.state_dir = get('core', 'state-dir') |
158 | ++ if self.state_dir is None: |
159 | ++ self.state_dir = DEFAULT_STATE_DIR |
160 | + |
161 | + |
162 | + def merge(self, cf_value, arg_value, def_val): |
163 | +@@ -337,31 +341,55 @@ |
164 | + def __str__(self): |
165 | + return str(self.__dict__) |
166 | + |
167 | +-def hibernationEnabled(): |
168 | +- """Returns a boolean indicating whether hibernation is enabled or not.""" |
169 | +- response = None |
170 | +- try: |
171 | +- response = urlopen(URL) |
172 | +- data = response.read() |
173 | +- if data.lower() in ('false', b'false'): |
174 | +- return False |
175 | +- except: |
176 | +- return False |
177 | +- finally: |
178 | +- if response: |
179 | +- response.close() |
180 | +- return True |
181 | ++def get_imds_token(seconds=21600): |
182 | ++ """ Get a token to access instance metadata. """ |
183 | ++ log("Requesting new IMDSv2 token.") |
184 | ++ request_header = {'X-aws-ec2-metadata-token-ttl-seconds': str(seconds)} |
185 | ++ token_url = '{}/{}'.format(IMDS_BASEURL, IMDS_API_TOKEN_PATH) |
186 | ++ response = requests.put(token_url, headers=request_header) |
187 | ++ response.close() |
188 | ++ if response.status_code != 200: |
189 | ++ return None |
190 | ++ |
191 | ++ return response.text |
192 | ++ |
193 | ++def create_state_dir(state_dir): |
194 | ++ """ Create agent run dir if it doesn't exists.""" |
195 | ++ if not os.path.isdir(state_dir): |
196 | ++ os.makedirs(state_dir) |
197 | ++ |
198 | ++def hibernation_enabled(state_dir): |
199 | ++ """Returns a boolean indicating whether hibernation is enabled or not. |
200 | ++ Hibernation can't be enabled/disabled the instance launch. If we find |
201 | ++ hibernation to be enabled, we create a semephore file so that we don't |
202 | ++ have to probe IMDS again. That is useful when a instance is rebooted |
203 | ++ after/if the IMDS http endpoint has been disabled. |
204 | ++ """ |
205 | ++ hib_sem_file = os.path.join(state_dir, HIB_ENABLED_FILE) |
206 | ++ if os.path.isfile(hib_sem_file): |
207 | ++ log("Found {!r}, configuring hibernation".format(hib_sem_file)) |
208 | ++ return True |
209 | ++ |
210 | ++ imds_token = get_imds_token() |
211 | ++ if imds_token is None: |
212 | ++ # IMDS http endpoint is disabled |
213 | ++ return False |
214 | ++ |
215 | ++ request_header = {'X-aws-ec2-metadata-token': imds_token} |
216 | ++ response = requests.get("{}/{}".format(IMDS_BASEURL, IMDS_SPOT_ACTION_PATH), |
217 | ++ headers=request_header) |
218 | ++ response.close() |
219 | ++ if response.status_code != 200 or response.text.lower() == "false": |
220 | ++ return False |
221 | ++ |
222 | ++ log("Hibernation Configured Flag found") |
223 | ++ os.mknod(hib_sem_file) |
224 | ++ |
225 | ++ return True |
226 | ++ |
227 | + |
228 | + def main(): |
229 | + |
230 | +- if not hibernationEnabled(): |
231 | +- log("Instance Launch has not enabled Hibernation Configured Flag. hibinit-agent exiting!!") |
232 | +- exit(0) |
233 | +- # Validate if disk space>total RAM |
234 | +- ram_bytes = os.sysconf('SC_PAGE_SIZE') * os.sysconf('SC_PHYS_PAGES') |
235 | +- if get_rootfs_size()<=(math.ceil(float(ram_bytes)/(1024*1024*1024))): |
236 | +- log("Insufficient disk space. Cannot create setup for hibernation. Please allocate a larger root device") |
237 | +- exit(1) |
238 | + # Parse arguments |
239 | + parser = argparse.ArgumentParser(description="An EC2 background process that creates a setup for instance hibernation " |
240 | + "at instance launch and also registers ACPI sleep event/actions") |
241 | +@@ -388,6 +416,17 @@ |
242 | + log_to_syslog = config.log_to_syslog |
243 | + |
244 | + log("Effective config: %s" % config) |
245 | ++ create_state_dir(config.state_dir) |
246 | ++ |
247 | ++ # Let's first check if we even need to run |
248 | ++ if not hibernation_enabled(config.state_dir): |
249 | ++ log("Instance Launch has not enabled Hibernation Configured Flag. hibinit-agent exiting!!") |
250 | ++ exit(0) |
251 | ++ # Validate if disk space>total RAM |
252 | ++ ram_bytes = os.sysconf('SC_PAGE_SIZE') * os.sysconf('SC_PHYS_PAGES') |
253 | ++ if get_rootfs_size()<=(math.ceil(float(ram_bytes)/(1024*1024*1024))): |
254 | ++ log("Insufficient disk space. Cannot create setup for hibernation. Please allocate a larger root device") |
255 | ++ exit(1) |
256 | + |
257 | + target_swap_size = config.swap_mb * 1024 * 1024 |
258 | + swap_percentage_size = ram_bytes * config.swap_percentage // 100 |
259 | +--- a/etc/hibinit-config.cfg |
260 | ++++ b/etc/hibinit-config.cfg |
261 | +@@ -11,6 +11,9 @@ |
262 | + # filesystems. |
263 | + touch-swap = False |
264 | + |
265 | ++# Location where to create any state files |
266 | ++state-dir = "/var/lib/hibinit-agent" |
267 | ++ |
268 | + [swap] |
269 | + # If there's no swap then we create it to be equal to the specified |
270 | + # percentage of RAM or to the target size, whichever is greater |
271 | diff --git a/debian/patches/lp1968805-Swapon-with-maximum-priority-before-hibernation.patch b/debian/patches/lp1968805-Swapon-with-maximum-priority-before-hibernation.patch |
272 | new file mode 100644 |
273 | index 0000000..5ed11c1 |
274 | --- /dev/null |
275 | +++ b/debian/patches/lp1968805-Swapon-with-maximum-priority-before-hibernation.patch |
276 | @@ -0,0 +1,63 @@ |
277 | +Author: Matthew Ruffell <matthew.ruffell@canonical.com> |
278 | +Date: Wed 13 Apr 2022 15:39:15 +1200 |
279 | +Description: |
280 | + |
281 | + Swapon with maximum priority before hibernation |
282 | + |
283 | + Since Focal, on systems with additional or multiple swapfiles |
284 | + configured, swapon on /swap-hibinit will be added with the next |
285 | + lowest priority for the system. |
286 | + |
287 | + For example, if we have /swapfile configured with a default priority |
288 | + of -2, swapon /swap-hibinit will be added with priority -3. |
289 | + |
290 | + $ sudo swapon /swapfile |
291 | + $ swapon --show |
292 | + NAME TYPE SIZE USED PRIO |
293 | + /swapfile file 4G 0B -2 |
294 | + $ sudo swapon /swap-hibinit |
295 | + $ swapon --show |
296 | + NAME TYPE SIZE USED PRIO |
297 | + /swapfile file 4G 0B -2 |
298 | + /swap-hibinit file 3.9G 0B -3 |
299 | + |
300 | + This causes hibernation to fail, since hibernation targets the |
301 | + highest priority swapfile, which is no longer /swap-hibinit, and the |
302 | + kernel command line is specifically configured to resume from the |
303 | + UUID and offset for /swap-hibinit. |
304 | + |
305 | + The result is that EC2 console says "Stopping" for 20 minutes before |
306 | + the instance is force stopped. |
307 | + |
308 | + Fix this by setting /swap-hibinit to maximum possible priority, |
309 | + 32767, as we swapon right before hibernation takes place. |
310 | + |
311 | +Bug-Ubuntu: https://bugs.launchpad.net/bugs/1968805 |
312 | +Forwarded: yes, https://github.com/aws/amazon-ec2-hibinit-agent/commit/a2303d269610a6e7415c5045766da605eaa7e30f |
313 | +Last-Update: 2022-04-13 |
314 | + |
315 | +Index: ec2-hibinit-agent-1.0.0/acpid.sleep.sh |
316 | +=================================================================== |
317 | +--- ec2-hibinit-agent-1.0.0.orig/acpid.sleep.sh 2022-04-13 15:55:57.642062380 +1200 |
318 | ++++ ec2-hibinit-agent-1.0.0/acpid.sleep.sh 2022-04-13 15:55:57.642062380 +1200 |
319 | +@@ -2,6 +2,11 @@ |
320 | + |
321 | + #PATH=/sbin:/bin:/usr/bin |
322 | + |
323 | ++# Hibernation selects the swapfile with highest priority. Since there may be |
324 | ++# other swapfiles configured, ensure /swap-hibinit is selected as hibernation |
325 | ++# target by setting to maximum priority. See LP#1968805. |
326 | ++swap_priority=32767 |
327 | ++ |
328 | + do_hibernate() { |
329 | + if [ -d /run/systemd/system ]; then |
330 | + systemctl hibernate |
331 | +@@ -14,7 +19,7 @@ |
332 | + |
333 | + case "$2" in |
334 | + SBTN) |
335 | +- swapon /swap-hibinit && do_hibernate |
336 | ++ swapon --priority=$swap_priority /swap-hibinit && do_hibernate |
337 | + ;; |
338 | + *) |
339 | + logger "ACPI action undefined: $2" ;; |
340 | diff --git a/debian/patches/lp2023924-remove-quotes-from-state-dir.patch b/debian/patches/lp2023924-remove-quotes-from-state-dir.patch |
341 | new file mode 100644 |
342 | index 0000000..d178d21 |
343 | --- /dev/null |
344 | +++ b/debian/patches/lp2023924-remove-quotes-from-state-dir.patch |
345 | @@ -0,0 +1,19 @@ |
346 | +Description: Remove quotes in config file for state_dir value |
347 | +It creates strange directory /" |
348 | +Author: Anchal Agarwal <anchalag@amazon.com> |
349 | +Origin: backport, https://github.com/aws/amazon-ec2-hibinit-agent/commit/d87d6365009f1663247fd8595b487c59d9b121f1 |
350 | +Bug-Ubuntu: https://bugs.launchpad.net/ubuntu/+source/ec2-hibinit-agent/+bug/2023924 |
351 | +Last-Update: 2023-06-20 |
352 | +--- |
353 | +This patch header follows DEP-3: http://dep.debian.net/deps/dep3/ |
354 | +--- a/etc/hibinit-config.cfg |
355 | ++++ b/etc/hibinit-config.cfg |
356 | +@@ -12,7 +12,7 @@ |
357 | + touch-swap = False |
358 | + |
359 | + # Location where to create any state files |
360 | +-state-dir = "/var/lib/hibinit-agent" |
361 | ++state-dir = /var/lib/hibinit-agent |
362 | + |
363 | + [swap] |
364 | + # If there's no swap then we create it to be equal to the specified |
365 | diff --git a/debian/patches/series b/debian/patches/series |
366 | index 136d930..1555533 100644 |
367 | --- a/debian/patches/series |
368 | +++ b/debian/patches/series |
369 | @@ -7,3 +7,6 @@ detect-hibernate-cmd-by-default.patch |
370 | 0008-Detect-disabled-hibernation-with-Python-3-s-urllib-t.patch |
371 | 0008-Always-set-resume-device-by-PARTUUID-instead-of-by-d.patch |
372 | 0010-Update-grub-configuration-when-it-needs-an-update.patch |
373 | +lp1968805-Swapon-with-maximum-priority-before-hibernation.patch |
374 | +lp1941785-Add-support-for-IMDSv2.patch |
375 | +lp2023924-remove-quotes-from-state-dir.patch |