[CRIU] [PATCH] Add inherit fd support

Andrew Vagin avagin at parallels.com
Thu Dec 4 01:44:07 PST 2014


On Wed, Dec 03, 2014 at 01:04:18PM -0800, Saied Kazemi wrote:
> There are cases where a process's file descriptor cannot be restored
> from the checkpointed image.  For example, a pipe file descriptor with
> one end in the checkpointed process and the other end in a separate
> process (that was not part of the checkpointed process tree) cannot be
> restored because after checkpoint the pipe would be broken and removed.
> 
> There are also cases where the user wants to use a new file during
> restore instead of the original file in the checkpointed image.  For
> example, the user wants to change the log file of a process from
> /path/to/oldlog to /path/to/newlog.
> 
> In these cases, criu's caller should set up a new file descriptor to be
> inherited by the restored process and specify it with the --inherit-fd
> command line option.  The argument of --inherit-fd has the format
> fd[%d]:%s, where %d tells criu which of its own file descriptor to use
> for restoring file identified by %s.
> 
> As a debugging aid, if the argument has the format debug[%d]:%s, it tells
> criu to write out the string after colon to the file descriptor %d.  This
> can be used to leave a "restore marker" in the output stream of the process.
> 
> It's important to note that inherit fd support breaks applications
> that depend on the state of the file descriptor being inherited.  So,
> consider inherit fd only for specific use cases that you know for sure
> won't break the application.
> 
> For examples please visit http://criu.org/Category:HOWTO.
> 
> Signed-off-by: Saied Kazemi <saied at google.com>
> ---
>  crtools.c            |  15 +++++
>  files-reg.c          |   7 +++
>  files.c              | 170 ++++++++++++++++++++++++++++++++++++++++++++++++++-
>  include/cr_options.h |   1 +
>  include/files.h      |   6 ++
>  pipes.c              |  29 +++++++++
>  util.c               |   5 ++
>  7 files changed, 232 insertions(+), 1 deletion(-)
> 

...

> diff --git a/pipes.c b/pipes.c
> index ddcc5cf..437a1f9 100644
> --- a/pipes.c
> +++ b/pipes.c
> @@ -293,8 +293,20 @@ static int recv_pipe_fd(struct pipe_info *pi)
>  	return fd;
>  }
>  
> +static char *pipe_id_string(int pipe_id)
> +{
> +	static char idstr[16];
> +
> +	if (snprintf(idstr, sizeof idstr, "pipe:[%d]", pipe_id) >= sizeof idstr) {
> +		pr_err("Not enough room for pipe %d identifier string\n", pipe_id);
> +		return NULL;
> +	}

>>> os.pipe()
(3, 4)

lr-x------ 1 avagin avagin 64 Dec  4 11:20 3 -> pipe:[1157357]
l-wx------ 1 avagin avagin 64 Dec  4 11:20 4 -> pipe:[1157357]

You can see that both ends of pipes have the same pipe_id. Maybe we need to
add r or w in pipe_id_string.

> +	return idstr;
> +}
> +
>  static int open_pipe(struct file_desc *d)
>  {
> +	char *pipe_name;
>  	struct pipe_info *pi, *p;
>  	int ret, tmp;
>  	int pfd[2];
> @@ -302,6 +314,20 @@ static int open_pipe(struct file_desc *d)
>  
>  	pi = container_of(d, struct pipe_info, d);
>  
> +	/*
> +	 * If the pipe is in the inherit fd list,
> +	 * it should be inherited rather than created.
> +	 */
> +	pipe_name = pipe_id_string(pi->pe->pipe_id);
> +	if (pipe_name == NULL)
> +		return -1;
> +	tmp = inherit_fd_lookup_id(pipe_name);
> +	if (tmp >= 0) {
> +		pr_info("Pipe %s will be restored from inherit fd %d\n",
> +			pipe_name, tmp);

Why Do we not need to call rst_file_params() here?

> +		return tmp;
> +	}
> +
>  	pr_info("\t\tCreating pipe pipe_id=%#x id=%#x\n", pi->pe->pipe_id, pi->pe->id);
>  
>  	if (!pi->create)


More information about the CRIU mailing list