@@ -563,15 +563,16 @@ int mount_all(const char *dest,
563563                  MOUNT_FATAL |MOUNT_MKDIR  },
564564                { "tmpfs" ,                  "/run" ,                         "tmpfs" , "mode=755"  TMPFS_LIMITS_RUN ,      MS_NOSUID |MS_NODEV |MS_STRICTATIME ,
565565                  MOUNT_FATAL |MOUNT_MKDIR  },
566-                 { "/usr/lib/os-release" ,    "/run/host/usr/lib/os-release" , NULL ,    NULL ,                             MS_BIND ,
567-                   MOUNT_FATAL |MOUNT_MKDIR |MOUNT_TOUCH  }, /* As per kernel interface requirements, bind mount first (creating mount points) and make read-only later */ 
568-                 { NULL ,                     "/run/host/usr/lib/os-release" , NULL ,    NULL ,                             MS_BIND |MS_RDONLY |MS_NOSUID |MS_NOEXEC |MS_NODEV |MS_REMOUNT ,
569-                   0  },
570-                 { "/etc/os-release" ,        "/run/host/etc/os-release" ,     NULL ,    NULL ,                             MS_BIND ,
571-                   MOUNT_MKDIR |MOUNT_TOUCH  },
572-                 { NULL ,                     "/run/host/etc/os-release" ,     NULL ,    NULL ,                             MS_BIND |MS_RDONLY |MS_NOSUID |MS_NOEXEC |MS_NODEV |MS_REMOUNT ,
573-                   0  },
574- 
566+                 { "/run/host" ,              "/run/host" ,                    NULL ,    NULL ,                             MS_BIND ,
567+                   MOUNT_FATAL |MOUNT_MKDIR |MOUNT_PREFIX_ROOT  }, /* Prepare this so that we can make it read-only when we are done */ 
568+                 { "/etc/os-release" ,        "/run/host/os-release" ,         NULL ,    NULL ,                             MS_BIND ,
569+                   MOUNT_TOUCH  }, /* As per kernel interface requirements, bind mount first (creating mount points) and make read-only later */ 
570+                 { "/usr/lib/os-release" ,    "/run/host/os-release" ,         NULL ,    NULL ,                             MS_BIND ,
571+                   MOUNT_FATAL  }, /* If /etc/os-release doesn't exist use the version in /usr/lib as fallback */ 
572+                 { NULL ,                     "/run/host/os-release" ,         NULL ,    NULL ,                             MS_BIND |MS_RDONLY |MS_NOSUID |MS_NOEXEC |MS_NODEV |MS_REMOUNT ,
573+                   MOUNT_FATAL  },
574+                 { NULL ,                     "/run/host" ,                    NULL ,    NULL ,                             MS_BIND |MS_RDONLY |MS_NOSUID |MS_NOEXEC |MS_NODEV |MS_REMOUNT ,
575+                   MOUNT_FATAL |MOUNT_IN_USERNS  },
575576#if  HAVE_SELINUX 
576577                { "/sys/fs/selinux" ,        "/sys/fs/selinux" ,              NULL ,    NULL ,                             MS_BIND ,
577578                  MOUNT_MKDIR  },  /* Bind mount first (mkdir/chown the mount point in case /sys/ is mounted as minimal skeleton tmpfs) */ 
@@ -589,9 +590,9 @@ int mount_all(const char *dest,
589590        int  r ;
590591
591592        for  (k  =  0 ; k  <  ELEMENTSOF (mount_table ); k ++ ) {
592-                 _cleanup_free_  char  * where  =  NULL , * options  =  NULL ;
593-                 const  char  * o ;
593+                 _cleanup_free_  char  * where  =  NULL , * options  =  NULL , * prefixed  =  NULL ;
594594                bool  fatal  =  FLAGS_SET (mount_table [k ].mount_settings , MOUNT_FATAL );
595+                 const  char  * o ;
595596
596597                if  (in_userns  !=  FLAGS_SET (mount_table [k ].mount_settings , MOUNT_IN_USERNS ))
597598                        continue ;
@@ -616,20 +617,9 @@ int mount_all(const char *dest,
616617                                return  log_error_errno (r , "Failed to detect whether %s is a mount point: %m" , where );
617618                        if  (r  >  0 )
618619                                continue ;
619- 
620-                         /* Shortcut for optional bind mounts: if the source can't be found skip ahead to avoid creating 
621-                          * empty and unused directories. */ 
622-                         if  (!fatal  &&  FLAGS_SET (mount_table [k ].mount_settings , MOUNT_MKDIR ) &&  FLAGS_SET (mount_table [k ].flags , MS_BIND )) {
623-                                 r  =  access (mount_table [k ].what , F_OK );
624-                                 if  (r  <  0 ) {
625-                                         if  (errno  ==  ENOENT )
626-                                                 continue ;
627-                                         return  log_error_errno (errno , "Failed to stat %s: %m" , mount_table [k ].what );
628-                                 }
629-                         }
630620                }
631621
632-                 if  (FLAGS_SET (mount_table [k ].mount_settings ,  MOUNT_MKDIR ) ) {
622+                 if  ((mount_table [k ].mount_settings   &  ( MOUNT_MKDIR | MOUNT_TOUCH ))  !=   0 ) {
633623                        uid_t  u  =  (use_userns  &&  !in_userns ) ? uid_shift  : UID_INVALID ;
634624
635625                        if  (FLAGS_SET (mount_table [k ].mount_settings , MOUNT_TOUCH ))
@@ -647,13 +637,17 @@ int mount_all(const char *dest,
647637                                if  (r  !=  - EROFS )
648638                                        continue ;
649639                        }
650-                         if  (FLAGS_SET (mount_table [k ].mount_settings , MOUNT_TOUCH )) {
651-                                 r  =  touch (where );
652-                                 if  (r  <  0  &&  r  !=  - EEXIST ) {
653-                                         if  (fatal )
654-                                                 return  log_error_errno (r , "Failed to create mount point %s: %m" , where );
655-                                         log_debug_errno (r , "Failed to create mount point %s: %m" , where );
656-                                 }
640+                 }
641+ 
642+                 if  (FLAGS_SET (mount_table [k ].mount_settings , MOUNT_TOUCH )) {
643+                         r  =  touch (where );
644+                         if  (r  <  0  &&  r  !=  - EEXIST ) {
645+                                 if  (fatal  &&  r  !=  - EROFS )
646+                                         return  log_error_errno (r , "Failed to create file %s: %m" , where );
647+ 
648+                                 log_debug_errno (r , "Failed to create file %s: %m" , where );
649+                                 if  (r  !=  - EROFS )
650+                                         continue ;
657651                        }
658652                }
659653
@@ -666,8 +660,18 @@ int mount_all(const char *dest,
666660                                o  =  options ;
667661                }
668662
663+                 if  (FLAGS_SET (mount_table [k ].mount_settings , MOUNT_PREFIX_ROOT )) {
664+                         /* Optionally prefix the mount source with the root dir. This is useful in bind 
665+                          * mounts to be created within the container image before we transition into it. Note 
666+                          * that MOUNT_IN_USERNS is run after we transitioned hence prefixing is not ncessary 
667+                          * for those. */ 
668+                         r  =  chase_symlinks (mount_table [k ].what , dest , CHASE_PREFIX_ROOT , & prefixed , NULL );
669+                         if  (r  <  0 )
670+                                 return  log_error_errno (r , "Failed to resolve %s/%s: %m" , dest , mount_table [k ].what );
671+                 }
672+ 
669673                r  =  mount_verbose (fatal  ? LOG_ERR  : LOG_DEBUG ,
670-                                   mount_table [k ].what ,
674+                                   prefixed  ?:  mount_table [k ].what ,
671675                                  where ,
672676                                  mount_table [k ].type ,
673677                                  mount_table [k ].flags ,
0 commit comments