diff options
Diffstat (limited to 'pkg/machine/qemu/machine.go')
-rw-r--r-- | pkg/machine/qemu/machine.go | 148 |
1 files changed, 105 insertions, 43 deletions
diff --git a/pkg/machine/qemu/machine.go b/pkg/machine/qemu/machine.go index 78c621111..30e64e44e 100644 --- a/pkg/machine/qemu/machine.go +++ b/pkg/machine/qemu/machine.go @@ -332,8 +332,7 @@ func (v *MachineVM) Init(opts machine.InitOptions) (bool, error) { } } } - switch volumeType { - case VolumeTypeVirtfs: + if volumeType == VolumeTypeVirtfs { virtfsOptions := fmt.Sprintf("local,path=%s,mount_tag=%s,security_model=mapped-xattr", source, tag) if readonly { virtfsOptions += ",readonly" @@ -391,25 +390,9 @@ func (v *MachineVM) Init(opts machine.InitOptions) (bool, error) { if err != nil { return false, err } - // Resize the disk image to input disk size - // only if the virtualdisk size is less than - // the given disk size - if opts.DiskSize<<(10*3) > originalDiskSize { - // Find the qemu executable - cfg, err := config.Default() - if err != nil { - return false, err - } - resizePath, err := cfg.FindHelperBinary("qemu-img", true) - if err != nil { - return false, err - } - resize := exec.Command(resizePath, []string{"resize", v.getImageFile(), strconv.Itoa(int(opts.DiskSize)) + "G"}...) - resize.Stdout = os.Stdout - resize.Stderr = os.Stderr - if err := resize.Run(); err != nil { - return false, errors.Errorf("resizing image: %q", err) - } + + if err := v.resizeDisk(opts.DiskSize, originalDiskSize>>(10*3)); err != nil { + return false, err } // If the user provides an ignition file, we need to // copy it into the conf dir @@ -433,14 +416,14 @@ func (v *MachineVM) Init(opts machine.InitOptions) (bool, error) { return err == nil, err } -func (v *MachineVM) Set(_ string, opts machine.SetOptions) error { - if v.Rootful == opts.Rootful { - return nil - } +func (v *MachineVM) Set(_ string, opts machine.SetOptions) ([]error, error) { + // If one setting fails to be applied, the others settings will not fail and still be applied. + // The setting(s) that failed to be applied will have its errors returned in setErrors + var setErrors []error state, err := v.State(false) if err != nil { - return err + return setErrors, err } if state == machine.Running { @@ -448,26 +431,45 @@ func (v *MachineVM) Set(_ string, opts machine.SetOptions) error { if v.Name != machine.DefaultMachineName { suffix = " " + v.Name } - return errors.Errorf("cannot change setting while the vm is running, run 'podman machine stop%s' first", suffix) + return setErrors, errors.Errorf("cannot change settings while the vm is running, run 'podman machine stop%s' first", suffix) } - changeCon, err := machine.AnyConnectionDefault(v.Name, v.Name+"-root") - if err != nil { - return err + if opts.Rootful != nil && v.Rootful != *opts.Rootful { + if err := v.setRootful(*opts.Rootful); err != nil { + setErrors = append(setErrors, errors.Wrapf(err, "failed to set rootful option")) + } else { + v.Rootful = *opts.Rootful + } } - if changeCon { - newDefault := v.Name - if opts.Rootful { - newDefault += "-root" - } - if err := machine.ChangeDefault(newDefault); err != nil { - return err + if opts.CPUs != nil && v.CPUs != *opts.CPUs { + v.CPUs = *opts.CPUs + v.editCmdLine("-smp", strconv.Itoa(int(v.CPUs))) + } + + if opts.Memory != nil && v.Memory != *opts.Memory { + v.Memory = *opts.Memory + v.editCmdLine("-m", strconv.Itoa(int(v.Memory))) + } + + if opts.DiskSize != nil && v.DiskSize != *opts.DiskSize { + if err := v.resizeDisk(*opts.DiskSize, v.DiskSize); err != nil { + setErrors = append(setErrors, errors.Wrapf(err, "failed to resize disk")) + } else { + v.DiskSize = *opts.DiskSize } } - v.Rootful = opts.Rootful - return v.writeConfig() + err = v.writeConfig() + if err != nil { + setErrors = append(setErrors, err) + } + + if len(setErrors) > 0 { + return setErrors, setErrors[0] + } + + return setErrors, nil } // Start executes the qemu command line and forks it @@ -783,7 +785,7 @@ func (v *MachineVM) Stop(_ string, _ machine.StopOptions) error { break } time.Sleep(waitInternal) - waitInternal = waitInternal * 2 + waitInternal *= 2 } return v.ReadySocket.Delete() @@ -799,8 +801,7 @@ func NewQMPMonitor(network, name string, timeout time.Duration) (Monitor, error) rtDir = "/run" } rtDir = filepath.Join(rtDir, "podman") - if _, err := os.Stat(filepath.Join(rtDir)); os.IsNotExist(err) { - // TODO 0644 is fine on linux but macos is weird + if _, err := os.Stat(rtDir); os.IsNotExist(err) { if err := os.MkdirAll(rtDir, 0755); err != nil { return Monitor{}, err } @@ -872,7 +873,7 @@ func (v *MachineVM) Remove(_ string, opts machine.RemoveOptions) (string, func() confirmationMessage += msg + "\n" } - //remove socket and pid file if any: warn at low priority if things fail + // remove socket and pid file if any: warn at low priority if things fail // Remove the pidfile if err := v.PidFilePath.Delete(); err != nil { logrus.Debugf("Error while removing pidfile: %v", err) @@ -1464,3 +1465,64 @@ func (v *MachineVM) getImageFile() string { func (v *MachineVM) getIgnitionFile() string { return v.IgnitionFilePath.GetPath() } + +// resizeDisk increases the size of the machine's disk in GB. +func (v *MachineVM) resizeDisk(diskSize uint64, oldSize uint64) error { + // Resize the disk image to input disk size + // only if the virtualdisk size is less than + // the given disk size + if diskSize < oldSize { + return errors.Errorf("new disk size must be larger than current disk size: %vGB", oldSize) + } + + // Find the qemu executable + cfg, err := config.Default() + if err != nil { + return err + } + resizePath, err := cfg.FindHelperBinary("qemu-img", true) + if err != nil { + return err + } + resize := exec.Command(resizePath, []string{"resize", v.getImageFile(), strconv.Itoa(int(diskSize)) + "G"}...) + resize.Stdout = os.Stdout + resize.Stderr = os.Stderr + if err := resize.Run(); err != nil { + return errors.Errorf("resizing image: %q", err) + } + + return nil +} + +func (v *MachineVM) setRootful(rootful bool) error { + changeCon, err := machine.AnyConnectionDefault(v.Name, v.Name+"-root") + if err != nil { + return err + } + + if changeCon { + newDefault := v.Name + if rootful { + newDefault += "-root" + } + err := machine.ChangeDefault(newDefault) + if err != nil { + return err + } + } + return nil +} + +func (v *MachineVM) editCmdLine(flag string, value string) { + found := false + for i, val := range v.CmdLine { + if val == flag { + found = true + v.CmdLine[i+1] = value + break + } + } + if !found { + v.CmdLine = append(v.CmdLine, []string{flag, value}...) + } +} |