2021-11-18 17:09:30 +03:00
#!/usr/bin/env python3
# SPDX-License-Identifier: LGPL-2.1-or-later
import re
import sys
import uuid
2023-08-09 22:43:08 +03:00
HEADER = ''' \
2022-02-21 04:46:57 +03:00
| Name | Partition Type UUID | Allowed File Systems | Explanation |
| - - - - - - | - - - - - - - - - - - - - - - - - - - - - | - - - - - - - - - - - - - - - - - - - - - - | - - - - - - - - - - - - - |
2021-11-18 17:09:30 +03:00
'''
ARCHITECTURES = {
' ALPHA ' : ' Alpha ' ,
' ARC ' : ' ARC ' ,
' ARM ' : ' 32-bit ARM ' ,
' ARM64 ' : ' 64-bit ARM/AArch64 ' ,
' IA64 ' : ' Itanium/IA-64 ' ,
' LOONGARCH64 ' : ' LoongArch 64-bit ' ,
' MIPS_LE ' : ' 32-bit MIPS LittleEndian (mipsel) ' ,
' MIPS64_LE ' : ' 64-bit MIPS LittleEndian (mips64el) ' ,
2022-09-15 18:57:24 +03:00
' PARISC ' : ' HPPA/PARISC ' ,
2021-11-18 17:09:30 +03:00
' PPC ' : ' 32-bit PowerPC ' ,
' PPC64 ' : ' 64-bit PowerPC BigEndian ' ,
2021-11-23 19:34:05 +03:00
' PPC64_LE ' : ' 64-bit PowerPC LittleEndian ' ,
2021-11-18 17:09:30 +03:00
' RISCV32 ' : ' RISC-V 32-bit ' ,
' RISCV64 ' : ' RISC-V 64-bit ' ,
' S390 ' : ' s390 ' ,
' S390X ' : ' s390x ' ,
' TILEGX ' : ' TILE-Gx ' ,
' X86 ' : ' x86 ' ,
' X86_64 ' : ' amd64/x86_64 ' ,
}
TYPES = {
' ROOT ' : ' Root Partition ' ,
' ROOT_VERITY ' : ' Root Verity Partition ' ,
' ROOT_VERITY_SIG ' : ' Root Verity Signature Partition ' ,
' USR ' : ' `/usr/` Partition ' ,
' USR_VERITY ' : ' `/usr/` Verity Partition ' ,
' USR_VERITY_SIG ' : ' `/usr/` Verity Signature Partition ' ,
' ESP ' : ' EFI System Partition ' ,
' SRV ' : ' Server Data Partition ' ,
' VAR ' : ' Variable Data Partition ' ,
' TMP ' : ' Temporary Data Partition ' ,
' SWAP ' : ' Swap ' ,
' HOME ' : ' Home Partition ' ,
2021-11-18 17:16:20 +03:00
' USER_HOME ' : ' Per-user Home Partition ' ,
2021-11-18 17:09:30 +03:00
' LINUX_GENERIC ' : ' Generic Linux Data Partition ' ,
' XBOOTLDR ' : ' Extended Boot Loader Partition ' ,
}
DESCRIPTIONS = {
' ROOT ' : (
' Any native, optionally in LUKS ' ,
' On systems with matching architecture, the first partition with this type UUID on the disk '
2022-09-15 18:57:24 +03:00
' containing the active EFI ESP is automatically mounted to the root directory `/`. '
2021-11-18 17:09:30 +03:00
' If the partition is encrypted with LUKS or has dm-verity integrity data (see below), the '
' device mapper file will be named `/dev/mapper/root`. ' ) ,
' USR ' : (
2021-11-27 15:10:38 +03:00
' Any native, optionally in LUKS ' ,
' Similar semantics to root partition, but just the `/usr/` partition. ' ) ,
' ROOT_VERITY ' : (
2021-11-18 17:09:30 +03:00
' A dm-verity superblock followed by hash data ' ,
' Contains dm-verity integrity hash data for the matching root partition. If this feature is '
' used the partition UUID of the root partition should be the first 128 bits of the root hash '
' of the dm-verity hash data, and the partition UUID of this dm-verity partition should be the '
' final 128 bits of it, so that the root partition and its Verity partition can be discovered '
' easily, simply by specifying the root hash. ' ) ,
' USR_VERITY ' : (
' A dm-verity superblock followed by hash data ' ,
' Similar semantics to root Verity partition, but just for the `/usr/` partition. ' ) ,
2021-11-27 15:10:38 +03:00
' ROOT_VERITY_SIG ' : (
' A serialized JSON object, see below ' ,
' Contains a root hash and a PKCS#7 signature for it, permitting signed dm-verity GPT images. ' ) ,
2021-11-18 17:09:30 +03:00
' USR_VERITY_SIG ' : (
' A serialized JSON object, see below ' ,
' Similar semantics to root Verity signature partition, but just for the `/usr/` partition. ' ) ,
' ESP ' : (
' VFAT ' ,
' The ESP used for the current boot is automatically mounted to `/efi/` (or `/boot/` as '
' fallback), unless a different partition is mounted there (possibly via `/etc/fstab`, or '
' because the Extended Boot Loader Partition — see below — exists) or the directory is '
' non-empty on the root disk. This partition type is defined by the '
' [UEFI Specification](http://www.uefi.org/specifications). ' ) ,
' XBOOTLDR ' : (
' Typically VFAT ' ,
' The Extended Boot Loader Partition (XBOOTLDR) used for the current boot is automatically '
2022-09-15 18:57:24 +03:00
' mounted to `/boot/`, unless a different partition is mounted there (possibly via '
' `/etc/fstab`) or the directory is non-empty on the root disk. This partition type '
2022-11-14 11:44:39 +03:00
' is defined by the [Boot Loader '
' Specification](https://uapi-group.org/specifications/specs/boot_loader_specification). ' ) ,
2021-11-18 17:09:30 +03:00
' SWAP ' : (
' Swap, optionally in LUKS ' ,
' All swap partitions on the disk containing the root partition are automatically enabled. '
' If the partition is encrypted with LUKS, the device mapper file will be named '
' `/dev/mapper/swap`. This partition type predates the Discoverable Partitions Specification. ' ) ,
' HOME ' : (
' Any native, optionally in LUKS ' ,
' The first partition with this type UUID on the disk containing the root partition is '
' automatically mounted to `/home/`. If the partition is encrypted with LUKS, the device '
' mapper file will be named `/dev/mapper/home`. ' ) ,
' SRV ' : (
' Any native, optionally in LUKS ' ,
' The first partition with this type UUID on the disk containing the root partition is '
' automatically mounted to `/srv/`. If the partition is encrypted with LUKS, the device '
' mapper file will be named `/dev/mapper/srv`. ' ) ,
' VAR ' : (
' Any native, optionally in LUKS ' ,
' The first partition with this type UUID on the disk containing the root partition is '
' automatically mounted to `/var/` — under the condition that its partition UUID matches '
' the first 128 bits of `HMAC-SHA256(machine-id, 0x4d21b016b53445c2a9fb5c16e091fd2d)` '
' (i.e. the SHA256 HMAC hash of the binary type UUID keyed by the machine ID as read from '
' [`/etc/machine-id`](https://www.freedesktop.org/software/systemd/man/machine-id.html). '
' This special requirement is made because `/var/` (unlike the other partition types '
' listed here) is inherently private to a specific installation and cannot possibly be '
' shared between multiple OS installations on the same disk, and thus should be bound to '
' a specific instance of the OS, identified by its machine ID. If the partition is '
' encrypted with LUKS, the device mapper file will be named `/dev/mapper/var`. ' ) ,
' TMP ' : (
' Any native, optionally in LUKS ' ,
' The first partition with this type UUID on the disk containing the root partition is '
' automatically mounted to `/var/tmp/`. If the partition is encrypted with LUKS, the '
' device mapper file will be named `/dev/mapper/tmp`. Note that the intended mount point '
' is indeed `/var/tmp/`, not `/tmp/`. The latter is typically maintained in memory via '
2022-09-15 18:57:24 +03:00
' `tmpfs` and does not require a partition on disk. In some cases it might be '
2021-11-18 17:09:30 +03:00
' desirable to make `/tmp/` persistent too, in which case it is recommended to make it '
' a symlink or bind mount to `/var/tmp/`, thus not requiring its own partition type UUID. ' ) ,
2021-11-18 17:16:20 +03:00
' USER_HOME ' : (
' Any native, optionally in LUKS ' ,
' A home partition of a user, managed by '
' [`systemd-homed`](https://www.freedesktop.org/software/systemd/man/systemd-homed.html). ' ) ,
2021-11-18 17:09:30 +03:00
' LINUX_GENERIC ' : (
' Any native, optionally in LUKS ' ,
' No automatic mounting takes place for other Linux data partitions. This partition type '
' should be used for all partitions that carry Linux file systems. The installer needs '
2022-09-15 18:57:24 +03:00
' to mount them explicitly via entries in `/etc/fstab`. Optionally, these partitions may '
' be encrypted with LUKS. This partition type predates the Discoverable Partitions Specification. ' ) ,
2021-11-18 17:09:30 +03:00
}
def extract ( file ) :
for line in file :
# print(line)
2022-09-15 18:57:24 +03:00
m = re . match ( r ' ^#define \ s+SD_GPT_(.*SD_ID128_MAKE \ (.* \ )) ' , line )
2021-11-18 17:09:30 +03:00
if not m :
continue
2022-09-17 14:01:11 +03:00
name = line . split ( ) [ 1 ]
2021-11-23 19:34:05 +03:00
if m2 := re . match ( r ' ^(ROOT|USR)_([A-Z0-9]+|X86_64|PPC64_LE|MIPS_LE|MIPS64_LE)(|_VERITY|_VERITY_SIG) \ s+SD_ID128_MAKE \ ((.*) \ ) ' , m . group ( 1 ) ) :
2023-08-09 22:43:08 +03:00
ptype , arch , suffix , u = m2 . groups ( )
2021-11-18 17:09:30 +03:00
u = uuid . UUID ( u . replace ( ' , ' , ' ' ) )
2022-09-15 18:57:24 +03:00
assert arch in ARCHITECTURES , f ' { arch } not in f { ARCHITECTURES } '
2023-08-09 22:43:08 +03:00
ptype = f ' { type } { suffix } '
assert ptype in TYPES
2021-11-18 17:09:30 +03:00
2023-08-09 22:43:08 +03:00
yield name , ptype , arch , u
2021-11-18 17:09:30 +03:00
elif m2 := re . match ( r ' ( \ w+) \ s+SD_ID128_MAKE \ ((.*) \ ) ' , m . group ( 1 ) ) :
2023-08-09 22:43:08 +03:00
ptype , u = m2 . groups ( )
2021-11-18 17:09:30 +03:00
u = uuid . UUID ( u . replace ( ' , ' , ' ' ) )
2023-08-09 22:43:08 +03:00
yield name , ptype , None , u
2021-11-18 17:09:30 +03:00
else :
2023-08-09 22:43:08 +03:00
raise ValueError ( f ' Failed to match: { m . group ( 1 ) } ' )
2021-11-18 17:09:30 +03:00
def generate ( defines ) :
prevtype = None
print ( HEADER , end = ' ' )
2021-11-19 19:26:36 +03:00
uuids = set ( )
2023-08-09 22:43:08 +03:00
for name , ptype , arch , puuid in defines :
tdesc = TYPES [ ptype ]
2021-11-18 17:09:30 +03:00
adesc = ' ' if arch is None else f ' ( { ARCHITECTURES [ arch ] } ) '
2021-11-19 19:26:36 +03:00
# Let's make sure that we didn't select&paste the same value twice
2023-08-09 22:43:08 +03:00
assert puuid not in uuids
uuids . add ( puuid )
2021-11-19 19:26:36 +03:00
2023-08-09 22:43:08 +03:00
if ptype != prevtype :
prevtype = ptype
morea , moreb = DESCRIPTIONS [ ptype ]
2021-11-18 17:09:30 +03:00
else :
morea = moreb = ' ditto '
2023-08-09 22:43:08 +03:00
print ( f ' | _ { tdesc } { adesc } _ | ` { puuid } ` ` { name } ` | { morea } | { moreb } | ' )
2021-11-18 17:09:30 +03:00
if __name__ == ' __main__ ' :
known = extract ( sys . stdin )
generate ( known )