sfdisk: add --label-nested for hybrid GPT

regular disk label:
	# sfdisk --list /dev/sdb
	..
	Disklabel type: gpt
	Disk identifier: 9DF9A9F1-0654-4E7A-9A5E-36E66D60FD79

	Device     Start    End Sectors Size Type
	/dev/sdb1   2048  22527   20480  10M Linux filesystem
	/dev/sdb2  22528  43007   20480  10M Linux swap
	/dev/sdb3  43008 204766  161759  79M Linux filesystem

nested (PMBR):
	# sfdisk --list --label-nested dos /dev/sdb
	...
	Disklabel type: dos
	Disk identifier: 0x00000000

	Device     Boot Start    End Sectors  Size Id Type
	/dev/sdb1           1 204799  204799  100M ee GPT

and for example:
        # sfdisk --label-nested dos /dev/sdb <<EOF
        1, 2047, ee
        , 10M, L
        , 10M, S
        ,,

creates hybrid GPT (PMBR partitions point to the same location as GPT)

Signed-off-by: Karel Zak <kzak@redhat.com>
This commit is contained in:
Karel Zak 2014-10-06 14:53:25 +02:00
parent 11eee4c477
commit e1422de3d8
2 changed files with 27 additions and 1 deletions

View File

@ -147,6 +147,10 @@ Specify disk label type (e.g. dos, gpt, ...). If no label specified then sfdisk
defaults to an existing label. If there is no label on the device than defaults
to "dos".
.TP
.BR \-Y , " \-\-label-nested \fItype\fR
Force sfdisk to edit nested disk label. The primary disk label has to already exist.
This option allows to edit for example hybrid/protective MBR on devices with GPT.
.TP
.BR \-h , " \-\-help"
Display help text and exit.
.TP

View File

@ -79,6 +79,7 @@ struct sfdisk {
int act; /* action */
int partno; /* -N <partno>, default -1 */
const char *label; /* --label <label> */
const char *label_nested; /* --label-nested <label> */
const char *backup_file; /* -O <path> */
struct fdisk_context *cxt; /* libfdisk context */
@ -189,15 +190,31 @@ static void sfdisk_init(struct sfdisk *sf)
if (!sf->cxt)
err(EXIT_FAILURE, _("failed to allocate libfdisk context"));
fdisk_set_ask(sf->cxt, ask_callback, (void *) sf);
if (sf->label_nested) {
struct fdisk_context *x = fdisk_new_nested_context(sf->cxt,
sf->label_nested);
if (!x)
err(EXIT_FAILURE, _("failed to allocate nested libfdisk context"));
/* the original context is available by fdisk_get_parent() */
sf->cxt = x;
}
}
static int sfdisk_deinit(struct sfdisk *sf)
{
struct fdisk_context *parent;
int rc;
assert(sf);
assert(sf->cxt);
parent = fdisk_get_parent(sf->cxt);
if (parent) {
fdisk_unref_context(sf->cxt);
sf->cxt = parent;
}
fdisk_unref_context(sf->cxt);
memset(sf, 0, sizeof(*sf));
@ -1315,6 +1332,7 @@ static void __attribute__ ((__noreturn__)) usage(FILE *out)
fputs(_(" -O, --backup-file <path> override default backout file name\n"), out);
fputs(_(" -N, --partno <num> specify partition number\n"), out);
fputs(_(" -X, --label <name> specify label type (dos, gpt, ...)\n"), out);
fputs(_(" -Y, --label-nested <name> specify nested label type (dos, bsd)\n"), out);
fputs(_(" -q, --quiet suppress extra info messages\n"), out);
fputs(_(" -n, --no-act do everything except write to device\n"), out);
fputs(_(" --no-reread do not check whether the device is in use\n"), out);
@ -1361,6 +1379,7 @@ int main(int argc, char *argv[])
{ "help", no_argument, NULL, 'h' },
{ "force", no_argument, NULL, 'f' },
{ "label", required_argument, NULL, 'X' },
{ "label-nested", required_argument, NULL, 'Y' },
{ "list", no_argument, NULL, 'l' },
{ "list-types", no_argument, NULL, 'T' },
{ "no-act", no_argument, NULL, 'n' },
@ -1393,7 +1412,7 @@ int main(int argc, char *argv[])
textdomain(PACKAGE);
atexit(close_stdout);
while ((c = getopt_long(argc, argv, "aAbcdfghlLo:O:nN:qsTu:vVX:",
while ((c = getopt_long(argc, argv, "aAbcdfghlLo:O:nN:qsTu:vVX:Y:",
longopts, &longidx)) != -1) {
switch(c) {
case 'a':
@ -1471,6 +1490,9 @@ int main(int argc, char *argv[])
case 'X':
sf->label = optarg;
break;
case 'Y':
sf->label_nested = optarg;
break;
case OPT_PARTUUID:
sf->act = ACT_PARTUUID;