[CRIU] [PATCH] parasite/mem: unprotect VMAs if page dumping failed

Dmitry Safonov dsafonov at virtuozzo.com
Tue Mar 29 03:15:11 PDT 2016


On 03/28/2016 10:38 PM, Dmitry Safonov wrote:
> Before patch parasite_dump_pages_seized tried to unprotect pages
> by parasite command. But it had two issues:
> 1. parasite doesn't wait any command, except PARASITE_CMD_FINI after
>     it failed;
> 2. return code for parasite_dump_pages_seized was not set according
>     to __parasite_dump_pages_seized failure.
>
> During fixing compatible patches set troubles, I saw the following picture,
> which the patch fixes:
>
> (00.010992) Sent msg to daemon 8 0 0
> pie: __fetched msg: 8 0 0
> (00.010995) Wait for ack 8 on daemon socket
> pie: Error (pie/parasite.c:82): Can't splice pages to pipe (0/16)
> pie: __sent ack msg: 8 8 -1
> pie: Error (pie/parasite.c:721): Close the control socket for writing
> pie: Daemon waits for command
> (00.011023) Fetched ack: 8 8 -1
> (00.011025) Error (parasite-syscall.c:345): Command 8 for daemon failed with -1
> (00.011131) page-pipe: Killing page pipe
> (00.011150) ----------------------------------------
> (00.011151) Error (mem.c:375): Can't dump page with parasite
> (00.011155) Sent msg to daemon 7 0 0
> (00.011156) Wait for ack 7 on daemon socket
> pie: __fetched msg: 7 0 0
> (00.011157) Error (parasite-syscall.c:318): Message reply from daemon is trimmed (12/0)
> pie: Error (pie/parasite.c:665): Command rejected
> (00.011159) Error (mem.c:379): Can't rollback unprotected vmas with parasite
> pie: Daemon waits for command
Cc: Cyrill Gorcunov <gorcunov at openvz.org>
not intentionally cc-ed your gmail.
> Signed-off-by: Dmitry Safonov <dsafonov at virtuozzo.com>
> ---
>   criu/mem.c          |  4 +++-
>   criu/pie/parasite.c | 21 ++++++++++++++++++++-
>   2 files changed, 23 insertions(+), 2 deletions(-)
>
> diff --git a/criu/mem.c b/criu/mem.c
> index 5a7b5bb96ba9..a8e3953769d0 100644
> --- a/criu/mem.c
> +++ b/criu/mem.c
> @@ -371,8 +371,10 @@ int parasite_dump_pages_seized(struct parasite_ctl *ctl,
>   	}
>   
>   	ret = __parasite_dump_pages_seized(ctl, pargs, vma_area_list, pp);
> -	if (ret)
> +	if (ret) {
>   		pr_err("Can't dump page with parasite\n");
> +		ret = -1;
> +	}
>   
>   	pargs->add_prot = 0;
>   	if (parasite_execute_daemon(PARASITE_CMD_MPROTECT_VMAS, ctl)) {
> diff --git a/criu/pie/parasite.c b/criu/pie/parasite.c
> index 9d822bb2a93a..b1808bc7ed5c 100644
> --- a/criu/pie/parasite.c
> +++ b/criu/pie/parasite.c
> @@ -644,6 +644,25 @@ static int fini()
>   	return -1;
>   }
>   
> +static inline bool after_fail_cmd_allowed(struct ctl_msg *m, void *args)
> +{
> +	if (m->cmd == PARASITE_CMD_FINI)
> +		return true;
> +
> +	if (m->cmd == PARASITE_CMD_MPROTECT_VMAS) {
> +		struct parasite_dump_pages_args *dp_args = args;
> +
> +		/*
> +		 * We should allow parasite to unprotect VMAs back
> +		 * from PROT_READ after failed pages dumping.
> +		 */
> +		if (!dp_args->add_prot)
> +			return true;
> +	}
> +
> +	return false;
> +}
> +
>   static noinline __used int noinline parasite_daemon(void *args)
>   {
>   	struct ctl_msg m = { };
> @@ -661,7 +680,7 @@ static noinline __used int noinline parasite_daemon(void *args)
>   		if (__parasite_daemon_wait_msg(&m))
>   			break;
>   
> -		if (ret && m.cmd != PARASITE_CMD_FINI) {
> +		if (ret && !after_fail_cmd_allowed(&m, args)) {
>   			pr_err("Command rejected\n");
>   			continue;
>   		}


-- 
Regards,
Dmitry Safonov



More information about the CRIU mailing list