nix-community / disko

Declarative disk partitioning and formatting using nix [maintainer=@Lassulus]
MIT License
1.44k stars 157 forks source link

Real hybrid MBR/GPT partitioning scheme #166

Open oneingan opened 1 year ago

oneingan commented 1 year ago

i notice that every hybrid example is not an Hybrid partitioning scheme, only a GPT BIOS compatible. Am I wrong?

I need a real Hybrid where dos table have a first vfat (0x0C) partition and then a full disk gpt (0xEE) type partition:

$ fdisk -t dos -l /dev/sda
(...)
Device                    Boot Start   End Sectors  Size Id Type
/dev/sda1                 *       34 65569   65536   32M  c W95 FAT32 (LBA)
/dev/sda2                          1    33      33 16.5K ee GPT

And gpt table have the real partition info:

$ fdisk -t gpt -l /dev/sda
(...)
Device                    Start      End  Sectors Size Type
/dev/sda1                    34    65569    65536  32M EFI System
/dev/sda2                 65570 21037089 20971520  10G Linux root (ARM-64)

I guess a new interface similar to ones for lvm or mdraid will be needed to implement this.

Lassulus commented 1 year ago

well it's hybrid as it can be booted by bios or efi with grub. I wouldn't recommend the DOS table as it is quite limited and doesn't support big disks

oneingan commented 1 year ago

Sure, but then gpt-bios-compat.nix example looks enough and much less confusing. Because Hybrid MBR as in https://www.rodsbooks.com/gdisk/hybrid.html is a totally different beast and sometimes is required. For instance (my use case) to boot Raspberry Pi with Tow-Boot and whatever UEFI Vanilla Linux OS.

Thinking about implementation, If there is interest I could go with a PR using sgdisk.

Interface side will be as simple as adding a hybrid = true; in partitions attrset.

oneingan commented 1 year ago

What do you think about this tentative interface??

{
  type = "disk";
  device = builtins.elemAt disks 0;
  content = {
    type = "hybrid_table";
    efiGptPartitionFirst = false;
    extraMbrProtection = false;
    hybrid_partitions = [
      {
        type = "hybrid_partition";
        gptPartitionNumber = 1;
        mbrPartitionType = "0x0c";
        mbrBootableFlag = false;
      }
    ];
    content = {
      type = "table";
      format = "gpt";
      partitions = [
        #...
      ];
    };
  };
}

Also usable with sane defaults as:

{
  type = "disk";
  device = builtins.elemAt disks 0;
  content = {
    type = "hybrid_table";
    content = {
      type = "table";
      format = "gpt";
      partitions = [
        #...
      ];
    };
  };
}