Skip to content

Commit

Permalink
Import UEFI Code file if specified in machine yaml
Browse files Browse the repository at this point in the history
Due to different sized (and possibly incompatible firmware changes)
machine definitions allow specifying a UEFI Code blob as well as the
vars.  UEFI Code and Vars should be delivered in pairs and imported
as such.

Signed-off-by: Ryan Harper <[email protected]>
  • Loading branch information
raharper committed Sep 6, 2023
1 parent e8cb140 commit 703f802
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 6 deletions.
19 changes: 17 additions & 2 deletions cmd/machine/cmd/init.go
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ func DoCreateMachine(machineName, machineType, fileName string, editFile bool) e
return fmt.Errorf("Error calling editor: %s", err)
}
}
log.Debug("Got config:\n%s", string(machineBytes))
log.Debugf("Got config:\n%s", string(machineBytes))

for {
if err = yaml.Unmarshal(machineBytes, &newMachine); err == nil {
Expand All @@ -195,7 +195,9 @@ func DoCreateMachine(machineName, machineType, fileName string, editFile bool) e
}
}

checkMachineFilePaths(&newMachine)
if err := checkMachineFilePaths(&newMachine); err != nil {
return fmt.Errorf("Error while checking machine fiel paths: %s", err)
}

// persist config if not ephemeral
err = postMachine(newMachine)
Expand Down Expand Up @@ -264,6 +266,14 @@ func checkMachineFilePaths(newMachine *api.Machine) error {
log.Infof("Fully qualified uefi-vars path %s", newPath)
newMachine.Config.UEFIVars = newPath
}
if newMachine.Config.UEFICode != "" {
newPath, err := verifyPath(cwd, newMachine.Config.UEFICode)
if err != nil {
return fmt.Errorf("Failed to verify path to uefi-code: %q: %s", newMachine.Config.UEFICode, err)
}
log.Infof("Fully qualified uefi-code path %s", newPath)
newMachine.Config.UEFICode = newPath
}
return nil
}

Expand Down Expand Up @@ -301,6 +311,10 @@ func doInitArgsValidate(cmd *cobra.Command, args []string) error {
cmd.SilenceUsage = true
return fmt.Errorf("Invalid machine-type '%s', must be one of: %s", mType, strings.Join(mTypes, ", "))
}
debug, _ := cmd.Flags().GetBool("debug")
if debug {
log.SetLevel(log.DebugLevel)
}
return nil
}

Expand All @@ -309,5 +323,6 @@ func init() {
rootCmd.AddCommand(initCmd)
initCmd.PersistentFlags().StringP("file", "f", "", "yaml file to import. If unspecified, use stdin")
initCmd.PersistentFlags().BoolP("edit", "e", false, "edit the yaml file inline")
initCmd.PersistentFlags().BoolP("debug", "D", false, "enable debug logging")
initCmd.PersistentFlags().StringP("machine-type", "m", defaultMachineType, fmt.Sprintf("specify the machine type, one of [%s]", strings.Join(mTypes, ", ")))
}
28 changes: 24 additions & 4 deletions pkg/api/qconfig.go
Original file line number Diff line number Diff line change
Expand Up @@ -364,21 +364,41 @@ func (nd NicDef) QNetDevice(qti *qcli.QemuTypeIndex) (qcli.NetDevice, error) {
return ndev, nil
}

func ConfigureUEFIVars(c *qcli.Config, srcVars, runDir string, secureBoot bool) error {
func ConfigureUEFIVars(c *qcli.Config, srcCode, srcVars, runDir string, secureBoot bool) error {
uefiDev, err := qcli.NewSystemUEFIFirmwareDevice(secureBoot)
if err != nil {
return fmt.Errorf("failed to create a UEFI Firmware Device: %s", err)
}
src := uefiDev.Vars
// Import source UEFI Code (if provided)
src := uefiDev.Code
if len(srcCode) > 0 {
src = srcCode
}
// FIXME: create a qcli.UEFICodeFileName
dest := filepath.Join(runDir, "uefi-code.fd")
log.Infof("Importing UEFI Code from '%s' to '%q'", src, dest)
if err := CopyFileBits(src, dest); err != nil {
return fmt.Errorf("Failed to import UEFI Code from '%s' to '%q': %s", src, dest, err)
}
uefiDev.Code = dest

// Import source UEFI Vxrs (if provided)
src = uefiDev.Vars
if len(srcVars) > 0 {
src = srcVars
}
dest := filepath.Join(runDir, qcli.UEFIVarsFileName)
dest = filepath.Join(runDir, qcli.UEFIVarsFileName)
log.Infof("Importing UEFI Vars from '%s' to '%q'", src, dest)
// FIXME: should we skip re-import of srcVars, the imported Vars may have
// had changes that a new import would clobber, warning for now
if PathExists(dest) {
log.Warnf("Already imported UEFI Vars file %q to %q, overwriting...", src, dest)
}
if err := CopyFileBits(src, dest); err != nil {
return fmt.Errorf("Failed to import UEFI Vars from '%s' to '%q': %s", src, dest, err)
}
uefiDev.Vars = dest

c.UEFIFirmwareDevices = []qcli.UEFIFirmwareDevice{*uefiDev}
return nil
}
Expand All @@ -397,7 +417,7 @@ func GenerateQConfig(runDir, sockDir string, v VMDef) (*qcli.Config, error) {
return c, err
}

err = ConfigureUEFIVars(c, v.UEFIVars, runDir, v.SecureBoot)
err = ConfigureUEFIVars(c, v.UEFICode, v.UEFIVars, runDir, v.SecureBoot)
if err != nil {
return c, fmt.Errorf("Error configuring UEFI Vars: %s", err)
}
Expand Down
1 change: 1 addition & 0 deletions pkg/api/vm.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,7 @@ type VMDef struct {
Disks []QemuDisk `yaml:"disks"`
Boot string `yaml:"boot"`
Cdrom string `yaml:"cdrom"`
UEFICode string `yaml:"uefi-code"`
UEFIVars string `yaml:"uefi-vars"`
TPM bool `yaml:"tpm"`
TPMVersion string `yaml:"tpm-version"`
Expand Down

0 comments on commit 703f802

Please sign in to comment.