[CRIU] [PATCH 3/5] fown: Don't fail on dumping files opened with O_PATH

Andrey Vagin avagin at gmail.com
Tue Dec 11 09:19:30 MSK 2018


On Fri, Dec 07, 2018 at 03:29:46PM +0300, Cyrill Gorcunov wrote:
> O_PATH opened files are special: they have empty
> file operations in kernel space, so there not that
> much we can do with them, even setting position is
> not allowed. Same applies to a signal number for
> owner settings.
> 
> Signed-off-by: Cyrill Gorcunov <gorcunov at gmail.com>
> ---
>  criu/files-reg.c    | 16 +++++++++++-----
>  criu/files.c        |  5 ++++-
>  criu/pie/parasite.c | 13 +++++++++++++
>  3 files changed, 28 insertions(+), 6 deletions(-)
> 
> diff --git a/criu/files-reg.c b/criu/files-reg.c
> index c4f4e1616a85..a2042a512538 100644
> --- a/criu/files-reg.c
> +++ b/criu/files-reg.c
> @@ -1777,11 +1777,17 @@ static int do_open_reg(int ns_root_fd, struct reg_file_info *rfi, void *arg)
>  	if (fd < 0)
>  		return fd;
>  
> -	if ((rfi->rfe->pos != -1ULL) &&
> -			lseek(fd, rfi->rfe->pos, SEEK_SET) < 0) {
> -		pr_perror("Can't restore file pos");
> -		close(fd);
> -		return -1;
> +	/*
> +	 * O_PATH opened files carry empty fops in kernel,
> +	 * just ignore positioning at all.
> +	 */
> +	if (!(rfi->rfe->flags & O_PATH)) {
> +		if ((rfi->rfe->pos != -1ULL) &&
> +		    lseek(fd, rfi->rfe->pos, SEEK_SET) < 0) {
> +			pr_perror("Can't restore file pos");
> +			close(fd);
> +			return -1;
> +		}
>  	}
>  
>  	return fd;
> diff --git a/criu/files.c b/criu/files.c
> index b12258ad2654..d96358b558b4 100644
> --- a/criu/files.c
> +++ b/criu/files.c
> @@ -392,7 +392,10 @@ static int fill_fd_params(struct pid *owner_pid, int fd, int lfd,
>  	pr_info("%d fdinfo %d: pos: %#16"PRIx64" flags: %16o/%#x\n",
>  			owner_pid->real, fd, p->pos, p->flags, (int)p->fd_flags);
>  
> -	ret = fcntl(lfd, F_GETSIG, 0);
> +	if (p->flags & O_PATH)
> +		ret = 0;
> +	else
> +		ret = fcntl(lfd, F_GETSIG, 0);
>  	if (ret < 0) {
>  		pr_perror("Can't get owner signum on %d", lfd);
>  		return -1;
> diff --git a/criu/pie/parasite.c b/criu/pie/parasite.c
> index c32e31384fd8..f9e954484615 100644
> --- a/criu/pie/parasite.c
> +++ b/criu/pie/parasite.c
> @@ -325,6 +325,19 @@ static int fill_fds_opts(struct parasite_drain_fd *fds, struct fd_opts *opts)
>  

                if (flags < 0) {
                        pr_err("fcntl(%d, F_GETFD) -> %d\n", fd, flags);
                        return -1;
                }


>  		p->flags = (char)flags;
>  
> +		/*
> +		 * For O_PATH opened files there is no owner at all.
> +		 */
> +		if (flags < 0) {
> +			pr_err("fcntl(%d, F_GETFL) -> %d\n", fd, flags);
> +			return -1;
> +		}


We already have the same code

> +		flags = sys_fcntl(fd, F_GETFL, 0);
> +		if (flags & O_PATH) {
> +			p->fown.pid = 0;
> +			continue;
> +		}
> +
>  		ret = sys_fcntl(fd, F_GETOWN_EX, (long)&owner_ex);
>  		if (ret) {
>  			pr_err("fcntl(%d, F_GETOWN_EX) -> %d\n", fd, ret);
> -- 
> 2.17.2
> 


More information about the CRIU mailing list