@@ -1263,22 +1263,29 @@ func (o *ops) CopyRegistryData(liveLogger io.Writer, device string) error {
12631263 return err
12641264 }
12651265
1266- // Calculate the target free percent of the device
1267- freePercent , err := o .calculateFreePercent (device , & registryDataSize )
1266+ // Calculate the target free percent of the device. Reserve at least 2.5 times
1267+ // the current data registry size.
1268+ requestedSize := registryDataSize * 5 / 2
1269+ freePercent , err := o .calculateFreePercent (device , & requestedSize )
12681270 if err != nil {
12691271 return err
12701272 }
1271- if freePercent == 0 {
1272- return errors .Errorf ("device %s is not large enough to fit the registry data" , device )
1273+ o .log .Infof ("Requesting at least %d bytes for the root partition on device %s (current registry size: %d bytes)" , requestedSize , device , registryDataSize )
1274+ // Ensure to have at least some minimum free space available otherwise coreos-gpt-setup.service may fail on the next reboot,
1275+ // since it requires at least some free blocks at the end of the disk.
1276+ minAllowedFreePercent := int64 (1 )
1277+ if freePercent < minAllowedFreePercent {
1278+ return errors .Errorf ("device %s is not large enough to fit the registry data (%d bytes)" , device , requestedSize )
12731279 }
12741280
1275- // Generate command for growing root partition to fit the registry data
1276- growPartCmd := makecmd (nil , "growpart" , fmt .Sprintf ("--free-percent=%d" , freePercent ), device , "4" )
1281+ // Generate command for growing root partition to fit the requested size
1282+ partIndex := "4"
1283+ growPartCmd := makecmd (nil , "growpart" , fmt .Sprintf ("--free-percent=%d" , freePercent ), device , partIndex )
12771284
12781285 // Get root partition path
1279- partition4 , err := o .getPartitionPathFromLsblk (device , "4" )
1286+ partition4 , err := o .getPartitionPathFromLsblk (device , partIndex )
12801287 if err != nil {
1281- return errors .Wrapf (err , "failed to find partition 4 for device %s" , device )
1288+ return errors .Wrapf (err , "failed to find partition %s for device %s" , partIndex , device )
12821289 }
12831290
12841291 // Generate the path to the registry data directory on the mounted root partitio
@@ -1289,18 +1296,43 @@ func (o *ops) CopyRegistryData(liveLogger io.Writer, device string) error {
12891296
12901297 // Generate the command for unfreezing the root partition (frozen by OverwriteOsImage func)
12911298 // Ignoring errors if the partition is already unfrozen
1292- fsUnfreezeCmd := makecmd (nil , "sh" , "-c" , "fsfreeze --unfreeze /mnt/root || true" )
1299+ mntTmpPath := "/mnt/root"
1300+ fsUnfreezeCmd := makecmd (nil , "sh" , "-c" , fmt .Sprintf ("fsfreeze --unfreeze %s || true" , mntTmpPath ))
1301+ fsFreezeCmd := makecmd (nil , "fsfreeze" , "--freeze" , mntTmpPath )
1302+ mountCmd := makecmd (nil , "mount" , partition4 , mntTmpPath )
1303+ unmountCmd := makecmd (nil , "umount" , mntTmpPath )
1304+
1305+ ignTransposeScript := "/usr/lib/dracut/modules.d/40ignition-ostree/ignition-ostree-transposefs.sh"
1306+ // The transposefs script does not have a way to apply unconditionally the autosave-xfs command
1307+ xfsForceAutosaveCmd := makecmd (nil , "bash" , "-c" , fmt .Sprintf (`sed 's/threshold=[0-9]*/threshold=0/' %s | bash -s autosave-xfs` , ignTransposeScript ))
1308+ xfsRestoreCommand := makecmd (nil , "bash" , "-c" , fmt .Sprintf ("%s restore" , ignTransposeScript ))
1309+ xfsCleanupCommand := makecmd (nil , "bash" , "-c" , fmt .Sprintf ("%s cleanup" , ignTransposeScript ))
12931310
12941311 cmds := []* cmd {
1295- makecmd (nil , "mkdir" , "-p" , "/mnt/root" ),
1296- makecmd (nil , "mount" , partition4 , "/mnt/root" ),
1312+ makecmd (nil , "mkdir" , "-p" , mntTmpPath ),
1313+
1314+ // Unfreeze
1315+ mountCmd ,
12971316 fsUnfreezeCmd ,
1317+ unmountCmd , // This is required before invoking the autosave-xfs
1318+
1319+ // Extend the root partition to allow the autosave-xfs command to recalculate the new AG size
1320+ // before copying the InternalReleaseImage registry data.
1321+ // See https://github.com/coreos/fedora-coreos-tracker/issues/1183 for more details.
12981322 growPartCmd ,
1299- makecmd (nil , "xfs_growfs" , "/mnt/root" ),
1323+ xfsForceAutosaveCmd ,
1324+ xfsRestoreCommand ,
1325+ xfsCleanupCommand ,
1326+
1327+ // Copy registry data
1328+ mountCmd , // Re-mount before copying data
1329+ makecmd (nil , "xfs_growfs" , mntTmpPath ),
13001330 makecmd (nil , "mkdir" , "-p" , registryDataDirOnRoot ),
13011331 copyCmd ,
1302- makecmd (nil , "fsfreeze" , "--freeze" , "/mnt/root" ),
1303- makecmd (nil , "umount" , "/mnt/root" ),
1332+
1333+ // Freeze
1334+ fsFreezeCmd ,
1335+ unmountCmd ,
13041336 }
13051337 for i := range cmds {
13061338 c := cmds [i ]
0 commit comments