Skip to content

Commit c68fb31

Browse files
nybidarigvisor-bot
authored andcommitted
Save runsc version in the metadata during save to compare it during restore.
PiperOrigin-RevId: 736035156
1 parent f9b1ce2 commit c68fb31

File tree

4 files changed

+17
-27
lines changed

4 files changed

+17
-27
lines changed

runsc/boot/autosave.go

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,11 +25,11 @@ import (
2525
"gvisor.dev/gvisor/pkg/sentry/state"
2626
"gvisor.dev/gvisor/pkg/sentry/strace"
2727
"gvisor.dev/gvisor/pkg/sync"
28+
"gvisor.dev/gvisor/runsc/version"
2829
)
2930

3031
func getTargetForSaveResume(l *Loader) func(k *kernel.Kernel) {
3132
return func(k *kernel.Kernel) {
32-
l.addVersionToCheckpoint()
3333
l.addContainerSpecsToCheckpoint()
3434
// Store the state file contents in a buffer for save-resume.
3535
// There is no need to verify the state file, we just need the
@@ -39,6 +39,7 @@ func getTargetForSaveResume(l *Loader) func(k *kernel.Kernel) {
3939
Autosave: true,
4040
Resume: true,
4141
Destination: &buf,
42+
Metadata: map[string]string{VersionKey: version.Version()},
4243
}
4344
saveOpts.Save(k.SupervisorContext(), k, l.watchdog)
4445
}
@@ -52,18 +53,17 @@ func getTargetForSaveRestore(l *Loader, files []*fd.FD) func(k *kernel.Kernel) {
5253
var once sync.Once
5354
return func(k *kernel.Kernel) {
5455
once.Do(func() {
55-
l.addVersionToCheckpoint()
5656
l.addContainerSpecsToCheckpoint()
5757
saveOpts := state.SaveOpts{
5858
Autosave: true,
5959
Resume: false,
6060
Destination: files[0],
61+
Metadata: map[string]string{VersionKey: version.Version()},
6162
}
6263
if len(files) == 3 {
6364
saveOpts.PagesMetadata = files[1]
6465
saveOpts.PagesFile = files[2]
6566
}
66-
6767
saveOpts.Save(k.SupervisorContext(), k, l.watchdog)
6868
})
6969
}

runsc/boot/controller.go

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ import (
4242
"gvisor.dev/gvisor/runsc/boot/procfs"
4343
"gvisor.dev/gvisor/runsc/config"
4444
"gvisor.dev/gvisor/runsc/specutils"
45+
"gvisor.dev/gvisor/runsc/version"
4546
)
4647

4748
const (
@@ -570,7 +571,7 @@ func (cm *containerManager) Restore(o *RestoreOpts, _ *struct{}) error {
570571
return fmt.Errorf("reading metadata from statefile: %w", err)
571572
}
572573
var count int
573-
countStr, ok := metadata["container_count"]
574+
countStr, ok := metadata[ContainerCountKey]
574575
if !ok {
575576
// TODO(gvisor.dev/issue/1956): Add container count with syscall save
576577
// trigger. For now, assume that only a single container exists if metadata
@@ -594,6 +595,11 @@ func (cm *containerManager) Restore(o *RestoreOpts, _ *struct{}) error {
594595
return fmt.Errorf("rewinding state file: %w", err)
595596
}
596597

598+
checkpointVersion := metadata[VersionKey]
599+
currentVersion := version.Version()
600+
if checkpointVersion != currentVersion {
601+
return fmt.Errorf("runsc version does not match across checkpoint restore, checkpoint: %v current: %v", checkpointVersion, currentVersion)
602+
}
597603
return cm.restorer.restoreContainerInfo(cm.l, &cm.l.root)
598604
}
599605

runsc/boot/loader.go

Lines changed: 0 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,6 @@ import (
8484
"gvisor.dev/gvisor/runsc/profile"
8585
"gvisor.dev/gvisor/runsc/specutils"
8686
"gvisor.dev/gvisor/runsc/specutils/seccomp"
87-
"gvisor.dev/gvisor/runsc/version"
8887

8988
// Top-level inet providers.
9089
"gvisor.dev/gvisor/pkg/sentry/socket/hostinet"
@@ -379,10 +378,6 @@ const (
379378
// containerSpecsKey is the key used to add and pop the container specs to the
380379
// kernel during save/restore.
381380
containerSpecsKey = "container_specs"
382-
383-
// versionKey is the key used to add and pop runsc version to the kernel
384-
// during save/restore.
385-
versionKey = "runsc_version"
386381
)
387382

388383
func getRootCredentials(spec *specs.Spec, conf *config.Config, userNs *auth.UserNamespace) *auth.Credentials {
@@ -2048,13 +2043,3 @@ func popContainerSpecsFromCheckpoint(k *kernel.Kernel) (map[string]*specs.Spec,
20482043
}
20492044
return oldSpecs, nil
20502045
}
2051-
2052-
// addVersionToCheckpoint adds the runsc version to the kernel.
2053-
func (l *Loader) addVersionToCheckpoint() {
2054-
l.k.AddStateToCheckpoint(versionKey, version.Version())
2055-
}
2056-
2057-
// popVersionFromCheckpoint pops the runsc version from the kernel.
2058-
func popVersionFromCheckpoint(k *kernel.Kernel) string {
2059-
return (k.PopCheckpointState(versionKey)).(string)
2060-
}

runsc/boot/restore.go

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,11 @@ const (
5757
// CheckpointPagesFileName is the file within the given image-path's
5858
// directory containing the container's MemoryFile pages.
5959
CheckpointPagesFileName = "pages.img"
60+
// VersionKey is the key used to save runsc version in the save metadata and compare
61+
// it across checkpoint restore.
62+
VersionKey = "runsc_version"
63+
// ContainerCountKey is the key used to save number of containers in the save metadata.
64+
ContainerCountKey = "container_count"
6065
)
6166

6267
// restorer manages a restore session for a sandbox. It stores information about
@@ -239,12 +244,6 @@ func (r *restorer) restore(l *Loader) error {
239244
return fmt.Errorf("failed to load kernel: %w", err)
240245
}
241246

242-
checkpointVersion := popVersionFromCheckpoint(l.k)
243-
currentVersion := version.Version()
244-
if checkpointVersion != currentVersion {
245-
return fmt.Errorf("runsc version does not match across checkpoint restore, checkpoint: %v current: %v", checkpointVersion, currentVersion)
246-
}
247-
248247
oldSpecs, err := popContainerSpecsFromCheckpoint(l.k)
249248
if err != nil {
250249
return fmt.Errorf("failed to pop container specs from checkpoint: %w", err)
@@ -357,10 +356,10 @@ func (l *Loader) save(o *control.SaveOpts) (err error) {
357356
if o.Metadata == nil {
358357
o.Metadata = make(map[string]string)
359358
}
360-
o.Metadata["container_count"] = strconv.Itoa(l.containerCount())
359+
o.Metadata[ContainerCountKey] = strconv.Itoa(l.containerCount())
361360

362361
// Save runsc version.
363-
l.addVersionToCheckpoint()
362+
o.Metadata[VersionKey] = version.Version()
364363

365364
// Save container specs.
366365
l.addContainerSpecsToCheckpoint()

0 commit comments

Comments
 (0)