git: 890adccde076 - stable/14 - gpart: More nuance for GPT support

From: Warner Losh <imp_at_FreeBSD.org>
Date: Sun, 12 Apr 2026 22:17:11 UTC
The branch stable/14 has been updated by imp:

URL: https://cgit.FreeBSD.org/src/commit/?id=890adccde0763536189cc1995e49f753e8d00497

commit 890adccde0763536189cc1995e49f753e8d00497
Author:     Warner Losh <imp@FreeBSD.org>
AuthorDate: 2024-10-15 23:15:17 +0000
Commit:     Warner Losh <imp@FreeBSD.org>
CommitDate: 2026-04-12 22:08:16 +0000

    gpart: More nuance for GPT support
    
    A careful reading of the GPT standard shows that one may have fewer than
    128 entries in your GPT table. While the standard requires that we
    reserve enough space (32 512-byte-LBAs or 4 4096-byte-LBAs), it also
    explicitly allows one to specify fewer actual partitions (since that
    controls what is in the CRC). It requires that the first LBA to be 32
    (512 sectors) or 6 (4k sectors) or larger. That requirement is not
    enforced (it's not listed as one of validation criteria for the GPT).
    We should likely do so in the future.
    
    To that end, allow a default number of entries to use (defent) on
    creation to be different (larger) than the minimum number of legal
    entries. For gpt, these numbers work out to 128 and 1 respectively.  For
    all the others, make minent == defent so this is a nop for those
    partitioning schemes.
    
    Sponsored by:           Netflix
    Reviewed by:            zlei, emaste
    Differential Revision:  https://reviews.freebsd.org/D42246
    
    (cherry picked from commit 09c999b1557a8031d2b60435d71a0a5ed4f0f016)
---
 sys/geom/part/g_part.c       | 2 +-
 sys/geom/part/g_part.h       | 5 +++--
 sys/geom/part/g_part_apm.c   | 1 +
 sys/geom/part/g_part_bsd.c   | 1 +
 sys/geom/part/g_part_bsd64.c | 1 +
 sys/geom/part/g_part_ebr.c   | 1 +
 sys/geom/part/g_part_gpt.c   | 3 ++-
 sys/geom/part/g_part_mbr.c   | 1 +
 8 files changed, 11 insertions(+), 4 deletions(-)

diff --git a/sys/geom/part/g_part.c b/sys/geom/part/g_part.c
index 10305ee940fe..02c550d74620 100644
--- a/sys/geom/part/g_part.c
+++ b/sys/geom/part/g_part.c
@@ -1006,7 +1006,7 @@ g_part_ctl_create(struct gctl_req *req, struct g_part_parms *gpp)
 	table->gpt_gp = gp;
 	table->gpt_scheme = gpp->gpp_scheme;
 	table->gpt_entries = (gpp->gpp_parms & G_PART_PARM_ENTRIES) ?
-	    gpp->gpp_entries : scheme->gps_minent;
+	    gpp->gpp_entries : scheme->gps_defent;
 	LIST_INIT(&table->gpt_entry);
 	if (null == NULL) {
 		cp = g_new_consumer(gp);
diff --git a/sys/geom/part/g_part.h b/sys/geom/part/g_part.h
index 13bbb1e4126a..575d97623e9b 100644
--- a/sys/geom/part/g_part.h
+++ b/sys/geom/part/g_part.h
@@ -118,8 +118,9 @@ const char *g_part_alias_name(enum g_part_alias);
 struct g_part_scheme {
 	KOBJ_CLASS_FIELDS;
 	size_t		gps_entrysz;
-	int		gps_minent;
-	int		gps_maxent;
+	int		gps_minent;		/* Minimum number of entries possible */
+	int		gps_defent;		/* Default number of entries to create */
+	int		gps_maxent;		/* Maximum number of entries possible */
 	int		gps_bootcodesz;
 	TAILQ_ENTRY(g_part_scheme) scheme_list;
 };
diff --git a/sys/geom/part/g_part_apm.c b/sys/geom/part/g_part_apm.c
index 9ee48168b1e8..5f9cb64eab02 100644
--- a/sys/geom/part/g_part_apm.c
+++ b/sys/geom/part/g_part_apm.c
@@ -102,6 +102,7 @@ static struct g_part_scheme g_part_apm_scheme = {
 	sizeof(struct g_part_apm_table),
 	.gps_entrysz = sizeof(struct g_part_apm_entry),
 	.gps_minent = 16,
+	.gps_defent = 16,
 	.gps_maxent = 4096,
 };
 G_PART_SCHEME_DECLARE(g_part_apm);
diff --git a/sys/geom/part/g_part_bsd.c b/sys/geom/part/g_part_bsd.c
index 625cdb4c727e..d1bee3f6c5e9 100644
--- a/sys/geom/part/g_part_bsd.c
+++ b/sys/geom/part/g_part_bsd.c
@@ -107,6 +107,7 @@ static struct g_part_scheme g_part_bsd_scheme = {
 	sizeof(struct g_part_bsd_table),
 	.gps_entrysz = sizeof(struct g_part_bsd_entry),
 	.gps_minent = 8,
+	.gps_defent = 8,
 	.gps_maxent = 20,	/* Only 22 entries fit in 512 byte sectors */
 	.gps_bootcodesz = BBSIZE,
 };
diff --git a/sys/geom/part/g_part_bsd64.c b/sys/geom/part/g_part_bsd64.c
index 4a1481f97c3e..14f8d0cde476 100644
--- a/sys/geom/part/g_part_bsd64.c
+++ b/sys/geom/part/g_part_bsd64.c
@@ -161,6 +161,7 @@ static struct g_part_scheme g_part_bsd64_scheme = {
 	sizeof(struct g_part_bsd64_table),
 	.gps_entrysz = sizeof(struct g_part_bsd64_entry),
 	.gps_minent = MAXPARTITIONS64,
+	.gps_defent = MAXPARTITIONS64,
 	.gps_maxent = MAXPARTITIONS64
 };
 G_PART_SCHEME_DECLARE(g_part_bsd64);
diff --git a/sys/geom/part/g_part_ebr.c b/sys/geom/part/g_part_ebr.c
index 6be64f58287c..9c1a46111b16 100644
--- a/sys/geom/part/g_part_ebr.c
+++ b/sys/geom/part/g_part_ebr.c
@@ -125,6 +125,7 @@ static struct g_part_scheme g_part_ebr_scheme = {
 	sizeof(struct g_part_ebr_table),
 	.gps_entrysz = sizeof(struct g_part_ebr_entry),
 	.gps_minent = 1,
+	.gps_defent = 1,
 	.gps_maxent = INT_MAX,
 };
 G_PART_SCHEME_DECLARE(g_part_ebr);
diff --git a/sys/geom/part/g_part_gpt.c b/sys/geom/part/g_part_gpt.c
index d795ccf4332b..de22d385af41 100644
--- a/sys/geom/part/g_part_gpt.c
+++ b/sys/geom/part/g_part_gpt.c
@@ -155,7 +155,8 @@ static struct g_part_scheme g_part_gpt_scheme = {
 	g_part_gpt_methods,
 	sizeof(struct g_part_gpt_table),
 	.gps_entrysz = sizeof(struct g_part_gpt_entry),
-	.gps_minent = 128,
+	.gps_minent = 1,
+	.gps_defent = 128,
 	.gps_maxent = 4096,
 	.gps_bootcodesz = MBRSIZE,
 };
diff --git a/sys/geom/part/g_part_mbr.c b/sys/geom/part/g_part_mbr.c
index 36862c8ff018..e0e764bbaae9 100644
--- a/sys/geom/part/g_part_mbr.c
+++ b/sys/geom/part/g_part_mbr.c
@@ -116,6 +116,7 @@ static struct g_part_scheme g_part_mbr_scheme = {
 	sizeof(struct g_part_mbr_table),
 	.gps_entrysz = sizeof(struct g_part_mbr_entry),
 	.gps_minent = NDOSPART,
+	.gps_defent = NDOSPART,
 	.gps_maxent = NDOSPART,
 	.gps_bootcodesz = MBRSIZE,
 };