mirror of
https://github.com/kairos-io/immucore.git
synced 2025-04-28 03:10:48 +00:00
Upgrade kcrypt partitions on boot (#122)
Co-authored-by: Dimitris Karakasilis <jimmykarily@gmail.com>
This commit is contained in:
parent
2e9e5de03e
commit
14426d39b4
@ -36,6 +36,7 @@ const (
|
||||
OpWaitForSysroot = "wait-for-sysroot"
|
||||
OpLvmActivate = "lvm-activation"
|
||||
OpKcryptUnlock = "unlock-all"
|
||||
OpKcryptUpgrade = "upgrade-kcrypt"
|
||||
PersistentStateTarget = "/usr/local/.state"
|
||||
LogDir = "/run/immucore"
|
||||
LinuxFs = "ext4"
|
||||
|
61
internal/utils/upgrade_kcrypt.go
Normal file
61
internal/utils/upgrade_kcrypt.go
Normal file
@ -0,0 +1,61 @@
|
||||
package utils
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"github.com/gofrs/uuid"
|
||||
"github.com/jaypipes/ghw"
|
||||
"github.com/kairos-io/kairos-sdk/utils"
|
||||
)
|
||||
|
||||
// UpgradeKcryptPartitions will try check for the uuid of the persistent partition and upgrade its uuid.
|
||||
func UpgradeKcryptPartitions() error {
|
||||
// Generate the predictable UUID
|
||||
persistentUUID := uuid.NewV5(uuid.NamespaceURL, "COS_PERSISTENT")
|
||||
// Check if there are any LUKS partitions, otherwise ignore
|
||||
blk, err := ghw.Block()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, disk := range blk.Disks {
|
||||
for _, p := range disk.Partitions {
|
||||
if p.Type == "crypto_LUKS" {
|
||||
// Check against known partition label on persistent
|
||||
Log.Debug().Str("label", p.Label).Str("dev", p.Name).Msg("found luks partition")
|
||||
if p.Label == "persistent" {
|
||||
// Get current UUID
|
||||
volumeUUID, err := utils.SH(fmt.Sprintf("cryptsetup luksUUID %s", filepath.Join("/dev", p.Name)))
|
||||
if err != nil {
|
||||
Log.Err(err).Send()
|
||||
return err
|
||||
}
|
||||
volumeUUID = strings.TrimSpace(volumeUUID)
|
||||
volumeUUIDParsed, err := uuid.FromString(volumeUUID)
|
||||
Log.Debug().Interface("volumeUUID", volumeUUIDParsed).Send()
|
||||
Log.Debug().Interface("persistentUUID", persistentUUID).Send()
|
||||
if err != nil {
|
||||
Log.Err(err).Send()
|
||||
return err
|
||||
}
|
||||
|
||||
// Check to see if it's the same already to not do anything
|
||||
if volumeUUIDParsed.String() != persistentUUID.String() {
|
||||
Log.Debug().Str("old", volumeUUIDParsed.String()).Str("new", persistentUUID.String()).Msg("Uuid is different, updating")
|
||||
out, err := utils.SH(fmt.Sprintf("cryptsetup luksUUID -q --uuid %s %s", persistentUUID, filepath.Join("/dev", p.Name)))
|
||||
if err != nil {
|
||||
Log.Err(err).Str("out", out).Msg("Updating uuid failed")
|
||||
return err
|
||||
}
|
||||
} else {
|
||||
Log.Debug().Msg("UUIDs are the same, not updating")
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
@ -24,11 +24,17 @@ func (s *State) RegisterNormalBoot(g *herd.Graph) error {
|
||||
// Mount Root (COS_STATE or COS_RECOVERY and then the image active/passive/recovery under s.Rootdir)
|
||||
s.LogIfError(s.MountRootDagStep(g), "running mount root stage")
|
||||
|
||||
// Run unlock. Depends on mount root because it needs the kcrypt-discovery-challenger available under /sysroot
|
||||
s.LogIfError(s.RunKcrypt(g, herd.WithDeps(cnst.OpMountRoot)), "kcrypt unlock")
|
||||
// Upgrade kcrypt partitions to kcrypt 0.6.0 if any
|
||||
// Depend on LVM in case the LVM is encrypted somehow? Not sure if possible.
|
||||
s.LogIfError(s.RunKcryptUpgrade(g, herd.WithDeps(cnst.OpLvmActivate)), "upgrade kcrypt partitions")
|
||||
|
||||
// Run unlock.
|
||||
// Depends on mount root because it needs the kcrypt-discovery-challenger available under /sysroot
|
||||
// Depends on OpKcryptUpgrade until we don't support upgrading from 1.X to the current version
|
||||
s.LogIfError(s.RunKcrypt(g, herd.WithDeps(cnst.OpMountRoot, cnst.OpKcryptUpgrade)), "kcrypt unlock")
|
||||
|
||||
// Mount COS_OEM (After root as it mounts under s.Rootdir/oem)
|
||||
s.LogIfError(s.MountOemDagStep(g, cnst.OpMountRoot, cnst.OpLvmActivate, cnst.OpKcryptUnlock), "oem mount")
|
||||
s.LogIfError(s.MountOemDagStep(g, cnst.OpMountRoot, cnst.OpLvmActivate), "oem mount")
|
||||
|
||||
// Run yip stage rootfs. Requires root+oem+sentinel to be mounted
|
||||
s.LogIfError(s.RootfsStageDagStep(g, herd.WithDeps(cnst.OpMountRoot, cnst.OpMountOEM, cnst.OpSentinel)), "running rootfs stage")
|
||||
|
@ -598,3 +598,12 @@ func (s *State) LVMActivation(g *herd.Graph) error {
|
||||
func (s *State) RunKcrypt(g *herd.Graph, opts ...herd.OpOption) error {
|
||||
return g.Add(cnst.OpKcryptUnlock, append(opts, herd.WithCallback(func(ctx context.Context) error { return kcrypt.UnlockAll() }))...)
|
||||
}
|
||||
|
||||
// RunKcryptUpgrade will upgrade encrypted partitions created with 1.x to the new 2.x format, where
|
||||
// we inspect the uuid of the partition directly to know which label to use for the key
|
||||
// As those old installs have an old agent the only way to do it is during the first boot after the upgrade to the newest immucore.
|
||||
func (s *State) RunKcryptUpgrade(g *herd.Graph, opts ...herd.OpOption) error {
|
||||
return g.Add(cnst.OpKcryptUpgrade, append(opts, herd.WithCallback(func(ctx context.Context) error {
|
||||
return internalUtils.UpgradeKcryptPartitions()
|
||||
}))...)
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user