mirror of
https://github.com/containers/podman.git
synced 2026-02-05 06:45:31 +01:00
Merge pull request #27885 from lstocchi/i27615
Prevent starting and stopping legacy hyperv machines when not elevated
This commit is contained in:
@@ -5,13 +5,37 @@ import (
|
||||
"fmt"
|
||||
"io/fs"
|
||||
"strconv"
|
||||
"time"
|
||||
|
||||
"github.com/containers/podman/v6/pkg/machine/define"
|
||||
)
|
||||
|
||||
const (
|
||||
pidFileWaitTimeout = 2 * time.Second
|
||||
pidFileCheckInterval = 50 * time.Millisecond
|
||||
)
|
||||
|
||||
func readPIDFileWithRetry(f define.VMFile) ([]byte, error) {
|
||||
deadline := time.Now().Add(pidFileWaitTimeout)
|
||||
|
||||
for time.Now().Before(deadline) {
|
||||
gvPid, err := f.Read()
|
||||
if err == nil {
|
||||
return gvPid, nil
|
||||
}
|
||||
if !errors.Is(err, fs.ErrNotExist) {
|
||||
return nil, err
|
||||
}
|
||||
time.Sleep(pidFileCheckInterval)
|
||||
}
|
||||
|
||||
// Final attempt after timeout
|
||||
return f.Read()
|
||||
}
|
||||
|
||||
// CleanupGVProxy reads the --pid-file for gvproxy attempts to stop it
|
||||
func CleanupGVProxy(f define.VMFile) error {
|
||||
gvPid, err := f.Read()
|
||||
gvPid, err := readPIDFileWithRetry(f)
|
||||
if err != nil {
|
||||
// The file will also be removed by gvproxy when it exits so
|
||||
// we need to account for the race and can just ignore it here.
|
||||
|
||||
@@ -15,6 +15,7 @@ var (
|
||||
ErrHypervRegistryInitRequiresElevation = errors.New("the first time Podman initializes a Hyper-V machine, it requires admin rights. Please run Podman as an administrator")
|
||||
ErrHypervRegistryRemoveRequiresElevation = errors.New("removing this Hyper-V machine requires admin rights to clean up the Windows Registry. Please run Podman as an administrator")
|
||||
ErrHypervRegistryUpdateRequiresElevation = errors.New("this machine's configuration requires additional Hyper-V networking (hvsock) entries in the Windows Registry. Please run Podman as an administrator")
|
||||
ErrHypervLegacyMachineRequiresElevation = errors.New("starting or stopping Hyper-V machines created with Podman 5.x or earlier requires admin rights. Please run Podman as an administrator")
|
||||
)
|
||||
|
||||
func HasHyperVAdminRights() bool {
|
||||
|
||||
@@ -265,6 +265,21 @@ func (h HyperVStubber) canRemove(mc *vmconfigs.MachineConfig) error {
|
||||
return ErrHypervRegistryRemoveRequiresElevation
|
||||
}
|
||||
|
||||
// canStartOrStop checks if the machine can be started or stopped.
|
||||
// Legacy machines require admin rights to start or stop.
|
||||
func (h HyperVStubber) canStartOrStop(mc *vmconfigs.MachineConfig) error {
|
||||
if windows.HasAdminRights() {
|
||||
return nil
|
||||
}
|
||||
|
||||
// if machine is legacy (machineName field), require admin rights to start or stop
|
||||
if isLegacyMachine(mc) {
|
||||
return ErrHypervLegacyMachineRequiresElevation
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// countMachinesWithToolname counts only machines that have a toolname field with value "podman".
|
||||
func (h HyperVStubber) countMachinesWithToolname() (int, error) {
|
||||
dirs, err := env.GetMachineDirs(h.VMType())
|
||||
@@ -345,7 +360,9 @@ func (h HyperVStubber) StartNetworking(mc *vmconfigs.MachineConfig, cmd *gvproxy
|
||||
}
|
||||
|
||||
func (h HyperVStubber) StartVM(mc *vmconfigs.MachineConfig) (func() error, func() error, error) {
|
||||
var err error
|
||||
if err := h.canStartOrStop(mc); err != nil {
|
||||
return nil, nil, err
|
||||
}
|
||||
|
||||
_, vm, err := GetVMFromMC(mc)
|
||||
if err != nil {
|
||||
@@ -412,6 +429,10 @@ func (h HyperVStubber) State(mc *vmconfigs.MachineConfig, _ bool) (define.Status
|
||||
}
|
||||
|
||||
func (h HyperVStubber) StopVM(mc *vmconfigs.MachineConfig, hardStop bool) error {
|
||||
if err := h.canStartOrStop(mc); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
vmm := hypervctl.NewVirtualMachineManager()
|
||||
vm, err := vmm.GetMachine(mc.Name)
|
||||
if err != nil {
|
||||
|
||||
Reference in New Issue
Block a user