[CRIU] [PATCH 3/4] timerfd: Add support of timerfd files

Pavel Emelyanov xemul at parallels.com
Tue Jun 24 11:38:08 PDT 2014


On 06/23/2014 09:54 PM, Cyrill Gorcunov wrote:
> 
> Signed-off-by: Cyrill Gorcunov <gorcunov at openvz.org>
> ---
>  Makefile.crtools     |   1 +
>  cr-restore.c         |   2 +
>  files.c              |   3 +
>  include/proc_parse.h |   2 +
>  include/timerfd.h    |  15 +++++
>  proc_parse.c         |  60 ++++++++++++++++++
>  timerfd.c            | 173 +++++++++++++++++++++++++++++++++++++++++++++++++++
>  7 files changed, 256 insertions(+)
>  create mode 100644 include/timerfd.h
>  create mode 100644 timerfd.c
> 
> +static int timerfd_open(struct file_desc *d)
> +{
> +	struct itimerspec v = { };
> +	struct timerfd_info *info;
> +	TimerfdEntry *tfe;
> +	int tmp = -1;
> +
> +	info = container_of(d, struct timerfd_info, d);
> +	tfe = info->tfe;
> +	pr_info("Restoring id %#x clockid %d settime_flags %x ticks %llu "
> +		"it_value(%llu, %llu) it_interval(%llu, %llu)\n",
> +		tfe->id, tfe->clockid, tfe->settime_flags, (unsigned long long)tfe->ticks,
> +		(unsigned long long)tfe->vsec, (unsigned long long)tfe->vnsec,
> +		(unsigned long long)tfe->isec, (unsigned long long)tfe->insec);
> +
> +	tmp = timerfd_create(tfe->clockid, 0);
> +	if (tmp < 0) {
> +		pr_perror("Can't create for %#x\n", tfe->id);
> +		return -1;
> +	}
> +
> +	v.it_interval.tv_sec	= (time_t)tfe->isec;
> +	v.it_interval.tv_nsec	= (long)tfe->insec;
> +
> +	v.it_value.tv_sec	= (time_t)tfe->vsec;
> +	v.it_value.tv_nsec	= (long)tfe->vnsec;
> +
> +	if (tfe->settime_flags & TFD_TIMER_ABSTIME) {
> +		struct timespec ts = { };
> +
> +		/*
> +		 * We might need to adjust value because the checkpoint
> +		 * and restore procedure takes some time itself. Note
> +		 * we don't adjust nanoseconds, since the result may
> +		 * overflow the limit NSEC_PER_SEC FIXME
> +		 */
> +		if (clock_gettime(tfe->clockid, &ts)) {
> +			pr_perror("Can't get current time");
> +			goto err_close;
> +		}
> +
> +		v.it_value.tv_sec += (time_t)ts.tv_sec;
> +
> +		pr_debug("Ajust id %#x it_value(%llu, %llu) -> it_value(%llu, %llu)\n",
> +			 tfe->id, (unsigned long long)ts.tv_sec,
> +			 (unsigned long long)ts.tv_nsec,
> +			 (unsigned long long)v.it_value.tv_sec,
> +			 (unsigned long long)v.it_value.tv_nsec);
> +	}
> +
> +	if (timerfd_settime(tmp, tfe->settime_flags, &v, NULL)) {

Not cool. Arming the timer at fd restore time may result in timer firing
before we jump into restorer code.

> +		pr_perror("Can't settime for %#x", tfe->id);
> +		goto err_close;
> +	}
> +
> +	if (tfe->ticks) {
> +		if (ioctl(tmp, TFD_IOC_SET_TICKS, &tfe->ticks)) {
> +			pr_perror("Can't restore ticks for %#x", tfe->id);
> +			goto err_close;
> +		}
> +	}
> +
> +	if (rst_file_params(tmp, tfe->fown, tfe->flags)) {
> +		pr_perror("Can't restore params for %#x", tfe->id);
> +		goto err_close;
> +	}
> +
> +	return tmp;
> +
> +err_close:
> +	close_safe(&tmp);
> +	return -1;
> +}




More information about the CRIU mailing list