Merge ~waveform/ubuntu-release-upgrader:lp2065051-noble into ubuntu-release-upgrader:ubuntu/noble
- Git
- lp:~waveform/ubuntu-release-upgrader
- lp2065051-noble
- Merge into ubuntu/noble
Proposed by
Dave Jones
Status: | Merged | ||||
---|---|---|---|---|---|
Merge reported by: | Nick Rosbrook | ||||
Merged at revision: | 86ae724556643768d0f68a08feedbefb867d18ee | ||||
Proposed branch: | ~waveform/ubuntu-release-upgrader:lp2065051-noble | ||||
Merge into: | ubuntu-release-upgrader:ubuntu/noble | ||||
Diff against target: |
261 lines (+179/-28) 3 files modified
DistUpgrade/DistUpgradeQuirks.py (+93/-28) debian/changelog (+7/-0) tests/test_quirks.py (+79/-0) |
||||
Related bugs: |
|
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Nick Rosbrook | Approve | ||
Review via email:
|
Commit message
Description of the change
To post a comment you must log in.
Revision history for this message
![](/+icing/build/overlay/assets/skins/sam/images/close.gif)
Nick Rosbrook (enr0n) : | # |
review:
Approve
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | diff --git a/DistUpgrade/DistUpgradeQuirks.py b/DistUpgrade/DistUpgradeQuirks.py | |||
2 | index d3a0bbd..292394b 100644 | |||
3 | --- a/DistUpgrade/DistUpgradeQuirks.py | |||
4 | +++ b/DistUpgrade/DistUpgradeQuirks.py | |||
5 | @@ -156,6 +156,9 @@ class DistUpgradeQuirks(object): | |||
6 | 156 | if 'ubuntu-desktop-raspi' in cache: | 156 | if 'ubuntu-desktop-raspi' in cache: |
7 | 157 | if cache['ubuntu-desktop-raspi'].is_installed: | 157 | if cache['ubuntu-desktop-raspi'].is_installed: |
8 | 158 | self._replace_fkms_overlay() | 158 | self._replace_fkms_overlay() |
9 | 159 | if 'ubuntu-server-raspi' in cache: | ||
10 | 160 | if cache['ubuntu-server-raspi'].is_installed: | ||
11 | 161 | self._add_kms_overlay() | ||
12 | 159 | if 'linux-firmware-raspi2' in cache: | 162 | if 'linux-firmware-raspi2' in cache: |
13 | 160 | if cache['linux-firmware-raspi2'].is_installed: | 163 | if cache['linux-firmware-raspi2'].is_installed: |
14 | 161 | self._remove_uboot_on_rpi() | 164 | self._remove_uboot_on_rpi() |
15 | @@ -1284,6 +1287,23 @@ class DistUpgradeQuirks(object): | |||
16 | 1284 | self._snap_list[snap] = snap_object | 1287 | self._snap_list[snap] = snap_object |
17 | 1285 | return self._snap_list | 1288 | return self._snap_list |
18 | 1286 | 1289 | ||
19 | 1290 | def _replace_pi_boot_config(self, old_config, new_config, | ||
20 | 1291 | boot_config_filename, failure_action): | ||
21 | 1292 | try: | ||
22 | 1293 | boot_backup_filename = boot_config_filename + '.distUpgrade' | ||
23 | 1294 | with open(boot_backup_filename, 'w', encoding='utf-8') as f: | ||
24 | 1295 | f.write(old_config) | ||
25 | 1296 | except IOError as exc: | ||
26 | 1297 | logging.error("unable to write boot config backup to %s: %s; %s", | ||
27 | 1298 | boot_backup_filename, exc, failure_action) | ||
28 | 1299 | return | ||
29 | 1300 | try: | ||
30 | 1301 | with open(boot_config_filename, 'w', encoding='utf-8') as f: | ||
31 | 1302 | f.write(new_config) | ||
32 | 1303 | except IOError as exc: | ||
33 | 1304 | logging.error("unable to write new boot config to %s: %s; %s", | ||
34 | 1305 | boot_config_filename, exc, failure_action) | ||
35 | 1306 | |||
36 | 1287 | def _replace_fkms_overlay(self, boot_dir='/boot/firmware'): | 1307 | def _replace_fkms_overlay(self, boot_dir='/boot/firmware'): |
37 | 1288 | failure_action = ( | 1308 | failure_action = ( |
38 | 1289 | "You may need to replace the vc4-fkms-v3d overlay with " | 1309 | "You may need to replace the vc4-fkms-v3d overlay with " |
39 | @@ -1318,22 +1338,80 @@ class DistUpgradeQuirks(object): | |||
40 | 1318 | logging.warning("no fkms overlay or camera firmware line found " | 1338 | logging.warning("no fkms overlay or camera firmware line found " |
41 | 1319 | "in %s", boot_config_filename) | 1339 | "in %s", boot_config_filename) |
42 | 1320 | return | 1340 | return |
43 | 1341 | self._replace_pi_boot_config( | ||
44 | 1342 | boot_config, new_config, boot_config_filename, failure_action) | ||
45 | 1321 | 1343 | ||
46 | 1344 | def _add_kms_overlay(self, boot_dir='/boot/firmware'): | ||
47 | 1345 | failure_action = ( | ||
48 | 1346 | "You may need to add dtoverlay=vc4-kms-v3d to an [all] section " | ||
49 | 1347 | "in config.txt on your boot partition") | ||
50 | 1348 | added_lines = [ | ||
51 | 1349 | '# added by do-release-upgrade (LP: #2065051)', | ||
52 | 1350 | 'dtoverlay=vc4-kms-v3d', | ||
53 | 1351 | 'disable_fw_kms_setup=1', | ||
54 | 1352 | '', | ||
55 | 1353 | '[pi3+]', | ||
56 | 1354 | 'dtoverlay=vc4-kms-v3d,cma-128', | ||
57 | 1355 | '', | ||
58 | 1356 | '[pi02]', | ||
59 | 1357 | 'dtoverlay=vc4-kms-v3d,cma-128', | ||
60 | 1358 | '', | ||
61 | 1359 | '[all]', | ||
62 | 1360 | ] | ||
63 | 1322 | try: | 1361 | try: |
71 | 1323 | boot_backup_filename = os.path.join( | 1362 | boot_config_filename = os.path.join(boot_dir, 'config.txt') |
72 | 1324 | boot_dir, 'config.txt.distUpgrade') | 1363 | with open(boot_config_filename, 'r', encoding='utf-8') as f: |
73 | 1325 | with open(boot_backup_filename, 'w', encoding='utf-8') as f: | 1364 | boot_config = f.read() |
74 | 1326 | f.write(boot_config) | 1365 | except FileNotFoundError: |
75 | 1327 | except IOError as exc: | 1366 | logging.error("failed to open boot configuration in %s; %s", |
76 | 1328 | logging.error("unable to write boot config backup to %s: %s; %s", | 1367 | boot_config_filename, failure_action) |
70 | 1329 | boot_backup_filename, exc, failure_action) | ||
77 | 1330 | return | 1368 | return |
84 | 1331 | try: | 1369 | |
85 | 1332 | with open(boot_config_filename, 'w', encoding='utf-8') as f: | 1370 | def find_insertion_point(lines): |
86 | 1333 | f.write(new_config) | 1371 | # Returns the zero-based index of the dtoverlay=vc4-kms-v3d line in |
87 | 1334 | except IOError as exc: | 1372 | # an [all] section, if one exists, or the last line of the last |
88 | 1335 | logging.error("unable to write new boot config to %s: %s; %s", | 1373 | # [all] section of the file, if one does not exist |
89 | 1336 | boot_config_filename, exc, failure_action) | 1374 | in_all = True |
90 | 1375 | last = 0 | ||
91 | 1376 | for index, line in enumerate(lines): | ||
92 | 1377 | line = line.rstrip() | ||
93 | 1378 | if in_all: | ||
94 | 1379 | last = index | ||
95 | 1380 | # startswith used to cope with any trailing dtparams | ||
96 | 1381 | if line.startswith('dtoverlay=vc4-kms-v3d'): | ||
97 | 1382 | return last | ||
98 | 1383 | elif line.startswith('[') and line.endswith(']'): | ||
99 | 1384 | in_all = line == '[all]' | ||
100 | 1385 | elif line.startswith('include '): | ||
101 | 1386 | # [sections] are included from includes verbatim, hence | ||
102 | 1387 | # (without reading the included file) we must assume | ||
103 | 1388 | # we're no longer in an [all] section | ||
104 | 1389 | in_all = False | ||
105 | 1390 | else: | ||
106 | 1391 | in_all = line == '[all]' | ||
107 | 1392 | return last | ||
108 | 1393 | |||
109 | 1394 | def add_kms_overlay(lines): | ||
110 | 1395 | insert_point = find_insertion_point(lines) | ||
111 | 1396 | try: | ||
112 | 1397 | if lines[insert_point].startswith('dtoverlay=vc4-kms-v3d'): | ||
113 | 1398 | return lines | ||
114 | 1399 | except IndexError: | ||
115 | 1400 | # Empty config, apparently! | ||
116 | 1401 | pass | ||
117 | 1402 | lines[insert_point:insert_point] = added_lines | ||
118 | 1403 | return lines | ||
119 | 1404 | |||
120 | 1405 | lines = [line.rstrip() for line in boot_config.splitlines()] | ||
121 | 1406 | lines = add_kms_overlay(lines) | ||
122 | 1407 | new_config = ''.join(line + '\n' for line in lines) | ||
123 | 1408 | |||
124 | 1409 | if new_config == boot_config: | ||
125 | 1410 | logging.warning("no addition of KMS overlay required in %s", | ||
126 | 1411 | boot_config_filename) | ||
127 | 1412 | return | ||
128 | 1413 | self._replace_pi_boot_config( | ||
129 | 1414 | boot_config, new_config, boot_config_filename, failure_action) | ||
130 | 1337 | 1415 | ||
131 | 1338 | def _remove_uboot_on_rpi(self, boot_dir='/boot/firmware'): | 1416 | def _remove_uboot_on_rpi(self, boot_dir='/boot/firmware'): |
132 | 1339 | kernel_line = 'kernel=vmlinuz' | 1417 | kernel_line = 'kernel=vmlinuz' |
133 | @@ -1452,21 +1530,8 @@ class DistUpgradeQuirks(object): | |||
134 | 1452 | logging.warning("no u-boot removal performed in %s", | 1530 | logging.warning("no u-boot removal performed in %s", |
135 | 1453 | boot_config_filename) | 1531 | boot_config_filename) |
136 | 1454 | return | 1532 | return |
152 | 1455 | 1533 | self._replace_pi_boot_config( | |
153 | 1456 | try: | 1534 | boot_config, new_config, boot_config_filename, failure_action) |
139 | 1457 | boot_backup_filename = boot_config_filename + '.distUpgrade' | ||
140 | 1458 | with open(boot_backup_filename, 'w', encoding='utf-8') as f: | ||
141 | 1459 | f.write(boot_config) | ||
142 | 1460 | except IOError as exc: | ||
143 | 1461 | logging.error("unable to write boot config backup to %s: %s; %s", | ||
144 | 1462 | boot_backup_filename, exc, failure_action) | ||
145 | 1463 | return | ||
146 | 1464 | try: | ||
147 | 1465 | with open(boot_config_filename, 'w', encoding='utf-8') as f: | ||
148 | 1466 | f.write(new_config) | ||
149 | 1467 | except IOError as exc: | ||
150 | 1468 | logging.error("unable to write new boot config to %s: %s; %s", | ||
151 | 1469 | boot_config_filename, exc, failure_action) | ||
154 | 1470 | 1535 | ||
155 | 1471 | def _set_generic_font(self): | 1536 | def _set_generic_font(self): |
156 | 1472 | """ Due to changes to the Ubuntu font we enable a generic font | 1537 | """ Due to changes to the Ubuntu font we enable a generic font |
157 | diff --git a/debian/changelog b/debian/changelog | |||
158 | index 862afb2..825a2d7 100644 | |||
159 | --- a/debian/changelog | |||
160 | +++ b/debian/changelog | |||
161 | @@ -1,3 +1,10 @@ | |||
162 | 1 | ubuntu-release-upgrader (1:24.04.18) noble; urgency=medium | ||
163 | 2 | |||
164 | 3 | * DistUpgradeQuirks: add quirk to migrate Pi server users to the KMS | ||
165 | 4 | overlay (LP: #2065051) | ||
166 | 5 | |||
167 | 6 | -- Dave Jones <dave.jones@canonical.com> Tue, 07 May 2024 18:54:12 +0100 | ||
168 | 7 | |||
169 | 1 | ubuntu-release-upgrader (1:24.04.17) noble; urgency=medium | 8 | ubuntu-release-upgrader (1:24.04.17) noble; urgency=medium |
170 | 2 | 9 | ||
171 | 3 | [ Nick Rosbrook ] | 10 | [ Nick Rosbrook ] |
172 | diff --git a/tests/test_quirks.py b/tests/test_quirks.py | |||
173 | index f40d502..a3fabec 100644 | |||
174 | --- a/tests/test_quirks.py | |||
175 | +++ b/tests/test_quirks.py | |||
176 | @@ -522,6 +522,85 @@ dtoverlay=vc4-kms-v3d,cma-256 | |||
177 | 522 | with open(os.path.join(boot_dir, 'config.txt')) as f: | 522 | with open(os.path.join(boot_dir, 'config.txt')) as f: |
178 | 523 | self.assertTrue(f.read() == expected_config) | 523 | self.assertTrue(f.read() == expected_config) |
179 | 524 | 524 | ||
180 | 525 | def test_add_kms_overlay_no_config(self): | ||
181 | 526 | with tempfile.TemporaryDirectory() as boot_dir: | ||
182 | 527 | mock_controller = mock.Mock() | ||
183 | 528 | |||
184 | 529 | q = DistUpgradeQuirks(mock_controller, mock.Mock()) | ||
185 | 530 | |||
186 | 531 | q._add_kms_overlay(boot_dir) | ||
187 | 532 | self.assertFalse(os.path.exists(os.path.join( | ||
188 | 533 | boot_dir, 'config.txt.distUpgrade'))) | ||
189 | 534 | |||
190 | 535 | def test_add_kms_overlay_no_changes(self): | ||
191 | 536 | with tempfile.TemporaryDirectory() as boot_dir: | ||
192 | 537 | boot_config = """\ | ||
193 | 538 | arm_64bit=1 | ||
194 | 539 | kernel=vmlinuz | ||
195 | 540 | initramfs initrd.img followkernel | ||
196 | 541 | |||
197 | 542 | # This line is implicitly in an [all] section and | ||
198 | 543 | # should prevent the quirk from doing anything | ||
199 | 544 | dtoverlay=vc4-kms-v3d,cma-128 | ||
200 | 545 | |||
201 | 546 | [pi4] | ||
202 | 547 | max_framebuffers=2 | ||
203 | 548 | """ | ||
204 | 549 | with open(os.path.join(boot_dir, 'config.txt'), 'w') as f: | ||
205 | 550 | f.write(boot_config) | ||
206 | 551 | |||
207 | 552 | mock_controller = mock.Mock() | ||
208 | 553 | q = DistUpgradeQuirks(mock_controller, mock.Mock()) | ||
209 | 554 | q._add_kms_overlay(boot_dir) | ||
210 | 555 | |||
211 | 556 | self.assertFalse(os.path.exists(os.path.join( | ||
212 | 557 | boot_dir, 'config.txt.distUpgrade'))) | ||
213 | 558 | with open(os.path.join(boot_dir, 'config.txt')) as f: | ||
214 | 559 | self.assertTrue(f.read() == boot_config) | ||
215 | 560 | |||
216 | 561 | def test_add_kms_overlay_with_changes(self): | ||
217 | 562 | with tempfile.TemporaryDirectory() as boot_dir: | ||
218 | 563 | config_txt = """\ | ||
219 | 564 | arm_64bit=1 | ||
220 | 565 | kernel=vmlinuz | ||
221 | 566 | initramfs initrd.img followkernel | ||
222 | 567 | |||
223 | 568 | [pi4] | ||
224 | 569 | max_framebuffers=2 | ||
225 | 570 | """ | ||
226 | 571 | expected_config_txt = """\ | ||
227 | 572 | arm_64bit=1 | ||
228 | 573 | kernel=vmlinuz | ||
229 | 574 | initramfs initrd.img followkernel | ||
230 | 575 | |||
231 | 576 | # added by do-release-upgrade (LP: #2065051) | ||
232 | 577 | dtoverlay=vc4-kms-v3d | ||
233 | 578 | disable_fw_kms_setup=1 | ||
234 | 579 | |||
235 | 580 | [pi3+] | ||
236 | 581 | dtoverlay=vc4-kms-v3d,cma-128 | ||
237 | 582 | |||
238 | 583 | [pi02] | ||
239 | 584 | dtoverlay=vc4-kms-v3d,cma-128 | ||
240 | 585 | |||
241 | 586 | [all] | ||
242 | 587 | [pi4] | ||
243 | 588 | max_framebuffers=2 | ||
244 | 589 | """ | ||
245 | 590 | with open(os.path.join(boot_dir, 'config.txt'), 'w') as f: | ||
246 | 591 | f.write(config_txt) | ||
247 | 592 | |||
248 | 593 | mock_controller = mock.Mock() | ||
249 | 594 | q = DistUpgradeQuirks(mock_controller, mock.Mock()) | ||
250 | 595 | q._add_kms_overlay(boot_dir) | ||
251 | 596 | |||
252 | 597 | self.assertTrue(os.path.exists(os.path.join( | ||
253 | 598 | boot_dir, 'config.txt.distUpgrade'))) | ||
254 | 599 | self.assertTrue(os.path.exists(os.path.join( | ||
255 | 600 | boot_dir, 'config.txt'))) | ||
256 | 601 | with open(os.path.join(boot_dir, 'config.txt')) as f: | ||
257 | 602 | self.assertTrue(f.read() == expected_config_txt) | ||
258 | 603 | |||
259 | 525 | def test_remove_uboot_no_config(self): | 604 | def test_remove_uboot_no_config(self): |
260 | 526 | with tempfile.TemporaryDirectory() as boot_dir: | 605 | with tempfile.TemporaryDirectory() as boot_dir: |
261 | 527 | mock_controller = mock.Mock() | 606 | mock_controller = mock.Mock() |