bug#35714: Parted destroys mbr_signature (Disk Identifier) when adding MBR bootcode

Matthijs Kooijman <[email protected]> Mon, 13 May 2019 10:52:12 +0200
Newsgroups gmane.comp.gnu.parted.bugs
Message-ID <[email protected]>
Hi folks,

I believe I found a bug in the dos partition table writer. Let me start
with the cause. There's this bit of code:

	if (!table->boot_code[0]) {
		memset (table->boot_code, 0, 512);
		memcpy (table->boot_code, MBR_BOOT_CODE, sizeof (MBR_BOOT_CODE));
	}

When a disk has no MBR bootcode, this adds some. However, it also starts
with clearing the *entire* MBR sector. I believe this should just clear
the bootcode, e.g.

	- memset (table->boot_code, 0, 512);
	+ memset (table->boot_code, 0, sizeof(table->boot_code));

The current code clears the mbr_signature, partition table and magic at
the end. The partition table is rewritten from the table in memory, the
magic value is simply replaced with a fixed value, but the mbr_signature
is replaced by newly randomly generated value.

Effectively, this means that when modifying a partition table without
any boot code, the mbr_signature will be changed.

I've noticed this problem on a Raspberry pi. The default raspbian images
are generated using fdisk, without any boot code (which is not needed on
a pi). Modifying the partition table using parted then generates a new
mbr_signature. Since this signature (called Disk Identifier by fdisk) is
used to generate the PARTUUID for partitions [1], and the PARTUUID is used
to locate the root filesystem, this effectively makes the system
unbootable.

It seems this has been known for a while, since a workaround [2] has
been (silently, without mentioning it in the commend message) introduced
two years ago [3] in the raspberry pi resizing code (probably at the
same time they started using PARTUUID I suspect).

Also note that the disk identifier is only changes once, since then the
MBR has bootcode and parted no longer needs to clear things.

Gr.

Matthijs

[1]: https://raspberrypi.stackexchange.com/a/95436/70022
[2]: https://github.com/RPi-Distro/raspi-config/blob/master/init_resize.sh#L77-L82
[3]: https://github.com/RPi-Distro/raspi-config/commit/44a2e6188c004de50b6c25c8bace2872d672cdd1
signature.asc (application/pgp-signature, 833 B)
-----BEGIN PGP SIGNATURE-----

iQIzBAABCAAdFiEEMyF3AetYrDfGJ9el6ZMxy91tJYwFAlzZMDkACgkQ6ZMxy91t
JYxtnhAAvC6YkCNIBEVrLZRzpqKfy5jRbDUBXZQ+P78utrPkOcmhIyPqdoG0G7SK
bO+++51aDIbhJ1d/dpApiQqUkx0WHYloo2YI1sISOflBvP6+fRc5YP9OMqwINQyt
CahL+gMFaVztf6IlDsMEN8TGFoqIAK0BP2wVW06kUvV5VOuzZ5BV+qiNGZ2nF3Dh
0zN6baoCz/uU7z3KP7tQ5+7kVIG7i4hghOtRqL9/HnCbBON41W9Dv6sgEnj/Zj+I
sMUSgoA7uX2xJAAqJq6PsTswpN53sHeNmi/Du+1EwckuyPM8gutD8Ij2hG2akJYj
63ZweuJbmW3vYl8VO24XDOU/UiZOA5qOeeosdT9uJqYL7VPTKNMBKXjto2v8qwcP
lb6Ygv3he4m1WhwyA4axAt9do0UqVgU3fNhX4MfvKFXgk9pD1e4D/i0dnfjxB71Y
UYK1RP/Irj6a0G/pUNux61SvujZUz9bVwIuDHrypH2HPmsZpofiZKF8NmDP5kneN
hGOVAObhJGmj9KgPOOqAw+qapkgXyMb7iFKIjOpC9SEPS/q9/votzfL8wPs3Z0rv
O3gCgtwBQIDOI311dJT27RQB42q5BgOju2Qy/jFxJmKipo3WPteHNNarVAzvHISx
vevHnuzh0NjfdOlLcGoSWB9MR+OGWlB2A1VS3Xs3K4XbQ3GDSi8=
=YCga
-----END PGP SIGNATURE-----