@@ -523,34 +523,9 @@ func (c *Container) restoreNetwork(req *criurpc.CriuReq, criuOpts *CriuOpts) {
523
523
}
524
524
}
525
525
526
- // makeCriuRestoreMountpoints makes the actual mountpoints for the
527
- // restore using CRIU. This function is inspired from the code in
528
- // rootfs_linux.go.
529
- func (c * Container ) makeCriuRestoreMountpoints (m * configs.Mount ) error {
530
- if m .Device == "cgroup" {
531
- // No mount point(s) need to be created:
532
- //
533
- // * for v1, mount points are saved by CRIU because
534
- // /sys/fs/cgroup is a tmpfs mount
535
- //
536
- // * for v2, /sys/fs/cgroup is a real mount, but
537
- // the mountpoint appears as soon as /sys is mounted
538
- return nil
539
- }
540
- // TODO: pass srcFD? Not sure if criu is impacted by issue #2484.
541
- me := mountEntry {Mount : m }
542
- // For all other filesystems, just make the target.
543
- if _ , err := createMountpoint (c .config .Rootfs , me ); err != nil {
544
- return fmt .Errorf ("create criu restore mountpoint for %s mount: %w" , me .Destination , err )
545
- }
546
- return nil
547
- }
548
-
549
- // isPathInPrefixList is a small function for CRIU restore to make sure
550
- // mountpoints, which are on a tmpfs, are not created in the roofs.
551
- func isPathInPrefixList (path string , prefix []string ) bool {
552
- for _ , p := range prefix {
553
- if strings .HasPrefix (path , p + "/" ) {
526
+ func isOnTmpfs (path string , mounts []* configs.Mount ) bool {
527
+ for _ , m := range mounts {
528
+ if m .Device == "tmpfs" && strings .HasPrefix (path , m .Destination + "/" ) {
554
529
return true
555
530
}
556
531
}
@@ -564,17 +539,6 @@ func isPathInPrefixList(path string, prefix []string) bool {
564
539
// This function also creates missing mountpoints as long as they
565
540
// are not on top of a tmpfs, as CRIU will restore tmpfs content anyway.
566
541
func (c * Container ) prepareCriuRestoreMounts (mounts []* configs.Mount ) error {
567
- // First get a list of a all tmpfs mounts
568
- tmpfs := []string {}
569
- for _ , m := range mounts {
570
- switch m .Device {
571
- case "tmpfs" :
572
- tmpfs = append (tmpfs , m .Destination )
573
- }
574
- }
575
- // Now go through all mounts and create the mountpoints
576
- // if the mountpoints are not on a tmpfs, as CRIU will
577
- // restore the complete tmpfs content from its checkpoint.
578
542
umounts := []string {}
579
543
defer func () {
580
544
for _ , u := range umounts {
@@ -590,28 +554,40 @@ func (c *Container) prepareCriuRestoreMounts(mounts []*configs.Mount) error {
590
554
})
591
555
}
592
556
}()
557
+ // Now go through all mounts and create the required mountpoints.
593
558
for _ , m := range mounts {
594
- if ! isPathInPrefixList (m .Destination , tmpfs ) {
595
- if err := c .makeCriuRestoreMountpoints (m ); err != nil {
559
+ // No cgroup mount point(s) need to be created:
560
+ // * for v1, mount points are saved by CRIU because
561
+ // /sys/fs/cgroup is a tmpfs mount;
562
+ // * for v2, /sys/fs/cgroup is a real mount, but
563
+ // the mountpoint appears as soon as /sys is mounted.
564
+ if m .Device == "cgroup" {
565
+ continue
566
+ }
567
+ // If the mountpoint is on a tmpfs, skip it as CRIU will
568
+ // restore the complete tmpfs content from its checkpoint.
569
+ if isOnTmpfs (m .Destination , mounts ) {
570
+ continue
571
+ }
572
+ if _ , err := createMountpoint (c .config .Rootfs , mountEntry {Mount : m }); err != nil {
573
+ return fmt .Errorf ("create criu restore mountpoint for %s mount: %w" , m .Destination , err )
574
+ }
575
+ // If the mount point is a bind mount, we need to mount
576
+ // it now so that runc can create the necessary mount
577
+ // points for mounts in bind mounts.
578
+ // This also happens during initial container creation.
579
+ // Without this CRIU restore will fail
580
+ // See: https://github.com/opencontainers/runc/issues/2748
581
+ // It is also not necessary to order the mount points
582
+ // because during initial container creation mounts are
583
+ // set up in the order they are configured.
584
+ if m .Device == "bind" {
585
+ if err := utils .WithProcfd (c .config .Rootfs , m .Destination , func (dstFd string ) error {
586
+ return mountViaFds (m .Source , nil , m .Destination , dstFd , "" , unix .MS_BIND | unix .MS_REC , "" )
587
+ }); err != nil {
596
588
return err
597
589
}
598
- // If the mount point is a bind mount, we need to mount
599
- // it now so that runc can create the necessary mount
600
- // points for mounts in bind mounts.
601
- // This also happens during initial container creation.
602
- // Without this CRIU restore will fail
603
- // See: https://github.com/opencontainers/runc/issues/2748
604
- // It is also not necessary to order the mount points
605
- // because during initial container creation mounts are
606
- // set up in the order they are configured.
607
- if m .Device == "bind" {
608
- if err := utils .WithProcfd (c .config .Rootfs , m .Destination , func (dstFd string ) error {
609
- return mountViaFds (m .Source , nil , m .Destination , dstFd , "" , unix .MS_BIND | unix .MS_REC , "" )
610
- }); err != nil {
611
- return err
612
- }
613
- umounts = append (umounts , m .Destination )
614
- }
590
+ umounts = append (umounts , m .Destination )
615
591
}
616
592
}
617
593
return nil
0 commit comments