Skip to content

Commit 5e8e829

Browse files
Merge pull request #25945 from ninja-quokka/podman_machine_swap
feat: Add support for configuring swap in Podman machine
2 parents b5befcd + 7b1055a commit 5e8e829

File tree

13 files changed

+81
-17
lines changed

13 files changed

+81
-17
lines changed

cmd/podman/machine/init.go

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,14 @@ func init() {
8383
)
8484
_ = initCmd.RegisterFlagCompletionFunc(memoryFlagName, completion.AutocompleteNone)
8585

86+
swapFlagName := "swap"
87+
flags.Uint64VarP(
88+
&initOpts.Swap,
89+
swapFlagName, "s", 0,
90+
"Swap in MiB",
91+
)
92+
_ = initCmd.RegisterFlagCompletionFunc(swapFlagName, completion.AutocompleteNone)
93+
8694
flags.BoolVar(
8795
&now,
8896
"now", false,

cmd/podman/machine/list.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,7 @@ func outputTemplate(cmd *cobra.Command, responses []*entities.ListReporter) erro
119119
"CPUs": "CPUS",
120120
"Memory": "MEMORY",
121121
"DiskSize": "DISK SIZE",
122+
"Swap": "SWAP",
122123
})
123124

124125
rpt := report.New(os.Stdout, cmd.Name())
@@ -182,6 +183,7 @@ func toMachineFormat(vms []*machine.ListResponse, defaultCon *config.Connection)
182183
response.VMType = vm.VMType
183184
response.CPUs = vm.CPUs
184185
response.Memory = strUint(uint64(vm.Memory.ToBytes()))
186+
response.Swap = strUint(uint64(vm.Swap.ToBytes()))
185187
response.DiskSize = strUint(uint64(vm.DiskSize.ToBytes()))
186188
response.Port = vm.Port
187189
response.RemoteUsername = vm.RemoteUsername
@@ -225,6 +227,7 @@ func toHumanFormat(vms []*machine.ListResponse, defaultCon *config.Connection) [
225227
response.VMType = vm.VMType
226228
response.CPUs = vm.CPUs
227229
response.Memory = units.BytesSize(float64(vm.Memory.ToBytes()))
230+
response.Swap = units.BytesSize(float64(vm.Swap.ToBytes()))
228231
response.DiskSize = units.BytesSize(float64(vm.DiskSize.ToBytes()))
229232

230233
humanResponses = append(humanResponses, response)

docs/source/markdown/podman-machine-init.1.md.in

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,12 @@ if there is no existing remote connection configurations.
104104

105105
API forwarding, if available, follows this setting.
106106

107+
#### **--swap**, **-s**=*number*
108+
109+
Swap (in MiB). Note: 1024MiB = 1GiB.
110+
111+
Renders a `zram-generator.conf` file with zram-size set to the value passed to --swap
112+
107113
#### **--timezone**
108114

109115
Set the timezone for the machine and containers. Valid values are `local` or

docs/source/markdown/podman-machine-list.1.md.in

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ Valid placeholders for the Go template are listed below:
5050
| .RemoteUsername | VM Username for rootless Podman |
5151
| .Running | Is machine running |
5252
| .Stream | Stream name |
53+
| .Swap | Allocated swap for machine |
5354
| .UserModeNetworking | Whether machine uses user-mode networking |
5455
| .VMType | VM type |
5556

pkg/domain/entities/machine.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ type ListReporter struct {
1313
VMType string
1414
CPUs uint64
1515
Memory string
16+
Swap string
1617
DiskSize string
1718
Port int
1819
RemoteUsername string

pkg/machine/config.go

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -22,9 +22,7 @@ import (
2222

2323
const apiUpTimeout = 20 * time.Second
2424

25-
var (
26-
ForwarderBinaryName = "gvproxy"
27-
)
25+
var ForwarderBinaryName = "gvproxy"
2826

2927
type Download struct {
3028
Arch string
@@ -55,6 +53,7 @@ type ListResponse struct {
5553
VMType string
5654
CPUs uint64
5755
Memory strongunits.MiB
56+
Swap strongunits.MiB
5857
DiskSize strongunits.GiB
5958
Port int
6059
RemoteUsername string

pkg/machine/define/initopts.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ type InitOptions struct {
1111
Volumes []string
1212
IsDefault bool
1313
Memory uint64
14+
Swap uint64
1415
Name string
1516
TimeZone string
1617
URI url.URL

pkg/machine/e2e/config_init_test.go

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ type initMachine struct {
2828
playbook string
2929
cpus *uint
3030
diskSize *uint
31+
swap *uint
3132
ignitionPath string
3233
username string
3334
image string
@@ -81,6 +82,9 @@ func (i *initMachine) buildCmd(m *machineTestBuilder) []string {
8182
if i.userModeNetworking {
8283
cmd = append(cmd, "--user-mode-networking")
8384
}
85+
if i.swap != nil {
86+
cmd = append(cmd, "--swap", strconv.Itoa(int(*i.swap)))
87+
}
8488
name := m.name
8589
cmd = append(cmd, name)
8690

@@ -112,11 +116,17 @@ func (i *initMachine) withCPUs(num uint) *initMachine {
112116
i.cpus = &num
113117
return i
114118
}
119+
115120
func (i *initMachine) withDiskSize(size uint) *initMachine {
116121
i.diskSize = &size
117122
return i
118123
}
119124

125+
func (i *initMachine) withSwap(size uint) *initMachine {
126+
i.swap = &size
127+
return i
128+
}
129+
120130
func (i *initMachine) withIgnitionPath(path string) *initMachine {
121131
i.ignitionPath = path
122132
return i

pkg/machine/e2e/init_test.go

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -238,7 +238,6 @@ var _ = Describe("podman machine init", func() {
238238
Expect(testMachine.Resources.Memory).To(BeEquivalentTo(uint64(2048)))
239239
}
240240
Expect(testMachine.SSHConfig.RemoteUsername).To(Equal(remoteUsername))
241-
242241
})
243242

244243
It("machine init with cpus, disk size, memory, timezone", func() {
@@ -282,6 +281,23 @@ var _ = Describe("podman machine init", func() {
282281
Expect(timezoneSession.outputToString()).To(ContainSubstring("HST"))
283282
})
284283

284+
It("machine init with swap", func() {
285+
skipIfWSL("Configuring swap is not supported on WSL")
286+
name := randomString()
287+
i := new(initMachine)
288+
session, err := mb.setName(name).setCmd(i.withImage(mb.imagePath).withSwap(2048).withNow()).run()
289+
Expect(err).ToNot(HaveOccurred())
290+
Expect(session).To(Exit(0))
291+
292+
ssh := &sshMachine{}
293+
sshSession, err := mb.setName(name).setCmd(ssh.withSSHCommand([]string{"zramctl -bo DISKSIZE"})).run()
294+
Expect(err).ToNot(HaveOccurred())
295+
Expect(sshSession).To(Exit(0))
296+
297+
// 2147483648 bytes = 2048MiB
298+
Expect(sshSession.outputToString()).To(ContainSubstring("2147483648"))
299+
})
300+
285301
It("machine init with volume", func() {
286302
if testProvider.VMType() == define.HyperVVirt {
287303
Skip("volumes are not supported on hyperv yet")
@@ -373,7 +389,6 @@ var _ = Describe("podman machine init", func() {
373389
output := strings.TrimSpace(sshSession2.outputToString())
374390
Expect(output).To(HavePrefix("/run/user"))
375391
Expect(output).To(HaveSuffix("/podman/podman.sock"))
376-
377392
})
378393

379394
It("machine init rootful with docker.sock check", func() {

pkg/machine/ignition/ignition.go

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,7 @@ type DynamicIgnition struct {
6767
Rootful bool
6868
NetRecover bool
6969
Rosetta bool
70+
Swap uint64
7071
}
7172

7273
func (ign *DynamicIgnition) Write() error {
@@ -136,7 +137,7 @@ func (ign *DynamicIgnition) GenerateIgnitionConfig() error {
136137

137138
ignStorage := Storage{
138139
Directories: getDirs(ign.Name),
139-
Files: getFiles(ign.Name, ign.UID, ign.Rootful, ign.VMType, ign.NetRecover),
140+
Files: getFiles(ign.Name, ign.UID, ign.Rootful, ign.VMType, ign.NetRecover, ign.Swap),
140141
Links: getLinks(ign.Name),
141142
}
142143

@@ -293,7 +294,7 @@ func getDirs(usrName string) []Directory {
293294
return dirs
294295
}
295296

296-
func getFiles(usrName string, uid int, rootful bool, vmtype define.VMType, _ bool) []File {
297+
func getFiles(usrName string, uid int, rootful bool, vmtype define.VMType, _ bool, swap uint64) []File {
297298
files := make([]File, 0)
298299

299300
lingerExample := parser.NewUnitFile()
@@ -407,6 +408,21 @@ pids_limit=0
407408
},
408409
})
409410

411+
if swap > 0 {
412+
files = append(files, File{
413+
Node: Node{
414+
Path: "/etc/systemd/zram-generator.conf",
415+
},
416+
FileEmbedded1: FileEmbedded1{
417+
Append: nil,
418+
Contents: Resource{
419+
Source: EncodeDataURLPtr(fmt.Sprintf("[zram0]\nzram-size=%d\n", swap)),
420+
},
421+
Mode: IntToPtr(0644),
422+
},
423+
})
424+
}
425+
410426
// get certs for current user
411427
userHome, err := os.UserHomeDir()
412428
if err != nil {

0 commit comments

Comments
 (0)