[PATCH v2 021/113] partitions: have parsers record bootable bits

Ahmad Fatoum a.fatoum at pengutronix.de
Mon Mar 4 10:59:06 PST 2024


barebox as EFI loader can use the information about which partitions are
bootable to guide its decision. Record this information.

Signed-off-by: Ahmad Fatoum <a.fatoum at pengutronix.de>
---
 common/partitions.c     |  4 ++--
 common/partitions/dos.c | 10 ++++++++++
 common/partitions/efi.c | 18 ++++++++++++++++++
 include/driver.h        |  5 +++++
 include/efi/partition.h |  6 ++++--
 include/partitions.h    |  2 ++
 6 files changed, 41 insertions(+), 4 deletions(-)

diff --git a/common/partitions.c b/common/partitions.c
index 7bcd0973b8ff..5b861c40fca3 100644
--- a/common/partitions.c
+++ b/common/partitions.c
@@ -50,8 +50,8 @@ static int register_one_partition(struct block_device *blk, struct partition *pa
 		goto out;
 	}
 
-	cdev->flags |= DEVFS_PARTITION_FROM_TABLE;
-
+	cdev->flags |= DEVFS_PARTITION_FROM_TABLE | part->flags;
+	cdev->typeflags |= part->typeflags;
 	cdev->typeuuid = part->typeuuid;
 	strcpy(cdev->partuuid, part->partuuid);
 
diff --git a/common/partitions/dos.c b/common/partitions/dos.c
index 1b0051f9784f..8e4edd885bfa 100644
--- a/common/partitions/dos.c
+++ b/common/partitions/dos.c
@@ -189,6 +189,15 @@ static void dos_extended_partition(struct block_device *blk, struct dos_partitio
 	return;
 }
 
+static void extract_flags(const struct partition_entry *p,
+			  struct partition *pentry)
+{
+	if (p->boot_indicator == 0x80)
+		pentry->flags |= DEVFS_PARTITION_BOOTABLE_LEGACY;
+	if (p->type == 0xef)
+		pentry->flags |= DEVFS_PARTITION_BOOTABLE_ESP;
+}
+
 /**
  * Check if a DOS like partition describes this block device
  * @param blk Block device to register to
@@ -237,6 +246,7 @@ static struct partition_desc *dos_partition(void *buf, struct block_device *blk)
 		pentry->first_sec = first_sec;
 		pentry->size = get_unaligned_le32(&table[i].partition_size);
 		pentry->dos_partition_type = table[i].type;
+		extract_flags(&table[i], pentry);
 		pentry->num = i;
 
 		sprintf(pentry->partuuid, "%08x-%02d", signature, i + 1);
diff --git a/common/partitions/efi.c b/common/partitions/efi.c
index 703d23c71524..9df40e3c15f3 100644
--- a/common/partitions/efi.c
+++ b/common/partitions/efi.c
@@ -444,6 +444,23 @@ static void part_set_efi_name(gpt_entry *pte, char *dest)
 	dest[i] = 0;
 }
 
+static void extract_flags(const gpt_entry *p, struct partition *pentry)
+{
+	static const guid_t system_guid = PARTITION_SYSTEM_GUID;
+
+	if (p->attributes.required_to_function)
+		pentry->flags |= DEVFS_PARTITION_REQUIRED;
+	if (p->attributes.no_block_io_protocol)
+		pentry->flags |= DEVFS_PARTITION_NO_EXPORT;
+	if (p->attributes.legacy_bios_bootable)
+		pentry->flags |= DEVFS_PARTITION_BOOTABLE_LEGACY;
+
+	if (guid_equal(&p->partition_type_guid, &system_guid))
+		pentry->flags |=  DEVFS_PARTITION_BOOTABLE_ESP;
+
+	pentry->typeflags = p->attributes.type_guid_specific;
+}
+
 static void part_get_efi_name(gpt_entry *pte, const char *src)
 {
 	int i;
@@ -498,6 +515,7 @@ static struct partition_desc *efi_partition(void *buf, struct block_device *blk)
 		epart = xzalloc(sizeof(*epart));
 		epart->pte = &ptes[i];
 		pentry = &epart->part;
+		extract_flags(&ptes[i], pentry);
 		pentry->first_sec = le64_to_cpu(ptes[i].starting_lba);
 		pentry->size = le64_to_cpu(ptes[i].ending_lba) - pentry->first_sec;
 		pentry->size++;
diff --git a/include/driver.h b/include/driver.h
index cda1dfac9dac..54b30d9921e0 100644
--- a/include/driver.h
+++ b/include/driver.h
@@ -565,6 +565,7 @@ struct cdev {
 	loff_t offset;
 	loff_t size;
 	unsigned int flags;
+	u16 typeflags; /* GPT type-specific attributes */
 	int open;
 	struct mtd_info *mtd;
 	struct cdev *link;
@@ -637,6 +638,10 @@ extern struct list_head cdev_list;
 #define DEVFS_PARTITION_FROM_TABLE	(1U << 6)
 #define DEVFS_IS_MBR_PARTITIONED	(1U << 7)
 #define DEVFS_IS_GPT_PARTITIONED	(1U << 8)
+#define DEVFS_PARTITION_REQUIRED	(1U << 9)
+#define DEVFS_PARTITION_NO_EXPORT	(1U << 10)
+#define DEVFS_PARTITION_BOOTABLE_LEGACY	(1U << 11)
+#define DEVFS_PARTITION_BOOTABLE_ESP	(1U << 12)
 
 static inline bool cdev_is_mbr_partitioned(const struct cdev *master)
 {
diff --git a/include/efi/partition.h b/include/efi/partition.h
index 184b4fd961dd..8ce62c859b12 100644
--- a/include/efi/partition.h
+++ b/include/efi/partition.h
@@ -101,8 +101,10 @@ typedef struct _gpt_header {
 
 typedef struct _gpt_entry_attributes {
 	u64 required_to_function:1;
-	u64 reserved:47;
-        u64 type_guid_specific:16;
+	u64 no_block_io_protocol:1;
+	u64 legacy_bios_bootable:1;
+	u64 reserved:45;
+	u64 type_guid_specific:16;
 } __attribute__ ((packed)) gpt_entry_attributes;
 
 #define GPT_PARTNAME_MAX_SIZE	(72 / sizeof (wchar_t))
diff --git a/include/partitions.h b/include/partitions.h
index b5379db92a03..785fb77ab167 100644
--- a/include/partitions.h
+++ b/include/partitions.h
@@ -26,6 +26,8 @@ struct partition {
 	};
 	struct list_head list;
 	int num;
+	unsigned int flags;
+	unsigned int typeflags;
 };
 
 struct partition_parser;
-- 
2.39.2




More information about the barebox mailing list