[CRIU] [PATCH 2/2] img: Introduce v1.1 images (v2)

Kuprieiev Ruslan rkuprieiev at cloudlinux.com
Wed Apr 8 07:00:14 PDT 2015


Acked-by: Ruslan Kuprieiev <rkuprieiev at cloudlinux.com>

On 04/08/2015 04:37 PM, Pavel Emelyanov wrote:
> These images have common magic in front of per-image one. With
> this we have 3 "types" of images -- inventory (head), other
> images, service files. The latter would be stats (not an image,
> just happen to be in PB format) and irmap cache (not an image
> again, just auxiliary thing which is in PB for convenience).
>
> Since inventory file is the first one we read on restore it's
> OK to set the global "new images" flag there. Dump (write) is
> always in new format.
>
> Signed-off-by: Pavel Emelyanov <xemul at parallels.com>
> ---
>   image-desc.c            |  2 ++
>   image.c                 | 40 +++++++++++++++++++++++++++++++++++++---
>   include/image.h         | 11 ++++++-----
>   include/magic.h         | 18 +++++++++++++++++-
>   pycriu/images/images.py |  9 +++++++++
>   5 files changed, 71 insertions(+), 9 deletions(-)
>
> diff --git a/image-desc.c b/image-desc.c
> index 4be7551..8d74024 100644
> --- a/image-desc.c
> +++ b/image-desc.c
> @@ -93,11 +93,13 @@ struct cr_fd_desc_tmpl imgset_template[CR_FD_MAX] = {
>   	[CR_FD_STATS] = {
>   		.fmt	= "stats-%s",
>   		.magic	= STATS_MAGIC,
> +		.oflags = O_SERVICE,
>   	},
>   
>   	[CR_FD_IRMAP_CACHE] = {
>   		.fmt	= "irmap-cache",
>   		.magic	= IRMAP_CACHE_MAGIC,
> +		.oflags = O_SERVICE,
>   	},
>   
>   	[CR_FD_FILE_LOCKS_PID] = {
> diff --git a/image.c b/image.c
> index 1f6f15b..676a40e 100644
> --- a/image.c
> +++ b/image.c
> @@ -14,6 +14,7 @@
>   
>   bool fdinfo_per_id = false;
>   bool ns_per_id = false;
> +bool img_common_magic = false;
>   TaskKobjIdsEntry *root_ids;
>   u32 root_cg_set;
>   
> @@ -50,10 +51,19 @@ int check_img_inventory(void)
>   		root_cg_set = he->root_cg_set;
>   	}
>   
> -	if (he->img_version != CRTOOLS_IMAGES_V1) {
> +	switch (he->img_version) {
> +	case CRTOOLS_IMAGES_V1:
> +		/* good old images. OK */
> +		break;
> +	case CRTOOLS_IMAGES_V1_1:
> +		/* newer images with extra magic in the head */
> +		img_common_magic = true;
> +		break;
> +	default:
>   		pr_err("Not supported images version %u\n", he->img_version);
>   		goto out_err;
>   	}
> +
>   	ret = 0;
>   
>   out_err:
> @@ -78,7 +88,8 @@ int write_img_inventory(void)
>   	if (!img)
>   		return -1;
>   
> -	he.img_version = CRTOOLS_IMAGES_V1;
> +	img_common_magic = true;
> +	he.img_version = CRTOOLS_IMAGES_V1_1;
>   	he.fdinfo_per_id = true;
>   	he.has_fdinfo_per_id = true;
>   	he.ns_per_id = true;
> @@ -238,6 +249,11 @@ struct cr_img *open_image_at(int dfd, int type, unsigned long flags, ...)
>   	return do_open_image(img, dfd, type, oflags, path);
>   }
>   
> +static inline u32 head_magic(int oflags)
> +{
> +	return oflags & O_SERVICE ? IMG_SERVICE_MAGIC : IMG_COMMON_MAGIC;
> +}
> +
>   static int img_check_magic(struct cr_img *img, int oflags, int type, char *path)
>   {
>   	u32 magic;
> @@ -245,6 +261,16 @@ static int img_check_magic(struct cr_img *img, int oflags, int type, char *path)
>   	if (read_img(img, &magic) < 0)
>   		return -1;
>   
> +	if (img_common_magic && (type != CR_FD_INVENTORY)) {
> +		if (magic != head_magic(oflags)) {
> +			pr_err("Head magic doesn't match for %s\n", path);
> +			return -1;
> +		}
> +
> +		if (read_img(img, &magic) < 0)
> +			return -1;
> +	}
> +
>   	if (magic != imgset_template[type].magic) {
>   		pr_err("Magic doesn't match for %s\n", path);
>   		return -1;
> @@ -255,6 +281,14 @@ static int img_check_magic(struct cr_img *img, int oflags, int type, char *path)
>   
>   static int img_write_magic(struct cr_img *img, int oflags, int type)
>   {
> +	if (img_common_magic && (type != CR_FD_INVENTORY)) {
> +		u32 cmagic;
> +
> +		cmagic = head_magic(oflags);
> +		if (write_img(img, &cmagic))
> +			return -1;
> +	}
> +
>   	return write_img(img, &imgset_template[type].magic);
>   }
>   
> @@ -262,7 +296,7 @@ static struct cr_img *do_open_image(struct cr_img *img, int dfd, int type, unsig
>   {
>   	int ret, flags;
>   
> -	flags = oflags & ~(O_NOBUF);
> +	flags = oflags & ~(O_NOBUF | O_SERVICE);
>   
>   	ret = openat(dfd, path, flags, CR_FD_PERM);
>   	if (ret < 0) {
> diff --git a/include/image.h b/include/image.h
> index 9ec0238..55e63dd 100644
> --- a/include/image.h
> +++ b/include/image.h
> @@ -116,12 +116,13 @@
>   
>   extern bool fdinfo_per_id;
>   extern bool ns_per_id;
> +extern bool img_common_magic;
>   
> -#define O_NOBUF	(O_DIRECT)
> -
> -#define O_DUMP	(O_WRONLY | O_CREAT | O_TRUNC)
> -#define O_SHOW	(O_RDONLY | O_NOBUF)
> -#define O_RSTR	(O_RDONLY)
> +#define O_NOBUF		(O_DIRECT)
> +#define O_SERVICE	(O_DIRECTORY)
> +#define O_DUMP		(O_WRONLY | O_CREAT | O_TRUNC)
> +#define O_SHOW		(O_RDONLY | O_NOBUF)
> +#define O_RSTR		(O_RDONLY)
>   
>   struct cr_img {
>   	union {
> diff --git a/include/magic.h b/include/magic.h
> index d9af16c..57dd29b 100644
> --- a/include/magic.h
> +++ b/include/magic.h
> @@ -6,6 +6,11 @@
>    */
>   
>   #define CRTOOLS_IMAGES_V1	1
> +/*
> + * v1.1 has common magic in the head of each image file,
> + * except for inventory
> + */
> +#define CRTOOLS_IMAGES_V1_1	2
>   
>   /*
>    * Raw images are images in which data is stored in some
> @@ -15,13 +20,20 @@
>   #define RAW_IMAGE_MAGIC		0x0
>   
>   /*
> + * Images have the IMG_COMMON_MAGIC in the head. Service files
> + * such as stats and irmap-cache have the IMG_SERVICE_MAGIC.
> + */
> +
> +#define IMG_COMMON_MAGIC	0x54564319 /* Sarov (a.k.a. Arzamas-16) */
> +#define IMG_SERVICE_MAGIC	0x55105940 /* Zlatoust */
> +
> +/*
>    * The magic-s below correspond to coordinates
>    * of various Russian towns in the NNNNEEEE form.
>    */
>   
>   #define INVENTORY_MAGIC		0x58313116 /* Veliky Novgorod */
>   #define PSTREE_MAGIC		0x50273030 /* Kyiv */
> -#define STATS_MAGIC		0x57093306 /* Ostashkov */
>   #define FDINFO_MAGIC		0x56213732 /* Dmitrov */
>   #define PAGEMAP_MAGIC		0x56084025 /* Vladimir */
>   #define SHMEM_PAGEMAP_MAGIC	PAGEMAP_MAGIC
> @@ -86,6 +98,10 @@
>   #define PAGES_OLD_MAGIC		PAGEMAP_MAGIC
>   #define SHM_PAGES_OLD_MAGIC	PAGEMAP_MAGIC
>   
> +/*
> + * These are special files, not exactly images
> + */
> +#define STATS_MAGIC		0x57093306 /* Ostashkov */
>   #define IRMAP_CACHE_MAGIC	0x57004059 /* Ivanovo */
>   
>   #endif /* __CR_MAGIC_H__ */
> diff --git a/pycriu/images/images.py b/pycriu/images/images.py
> index f0bfe84..5dde50c 100644
> --- a/pycriu/images/images.py
> +++ b/pycriu/images/images.py
> @@ -287,6 +287,9 @@ def load(f, pretty = False):
>   
>   	img_magic, = struct.unpack('i', f.read(4))
>   
> +	if img_magic in (magic.by_name['IMG_COMMON'], magic.by_name['IMG_SERVICE']):
> +		img_magic, = struct.unpack('i', f.read(4))
> +
>   	try:
>   		m = magic.by_val[img_magic]
>   	except:
> @@ -320,6 +323,12 @@ def dump(img, f):
>   	m = img['magic']
>   	magic_val = magic.by_name[img['magic']]
>   
> +	if m != 'INVENTORY':
> +		if m in ('STATS', 'IRMAP_CACHE'):
> +			f.write(struct.pack('i', magic.by_name['IMG_COMMON']))
> +		else:
> +			f.write(struct.pack('i', magic.by_name['IMG_SERVICE']))
> +
>   	f.write(struct.pack('i', magic_val))
>   
>   	try:



More information about the CRIU mailing list