[CRIU] [PATCH 11/14] files: dump fdinfo per files_id instead of pid (v2)

Andrey Vagin avagin at openvz.org
Fri Jan 11 04:22:42 EST 2013


A few processes can share one fdtable.

v2: fix backward compatiability

Signed-off-by: Andrey Vagin <avagin at openvz.org>
---
 cr-dump.c                | 26 ++++++++++++++++----------
 cr-restore.c             |  5 ++++-
 files.c                  | 23 ++++++++++++++++++-----
 image.c                  |  6 ++++++
 include/crtools.h        |  2 +-
 include/files.h          |  2 +-
 include/image.h          |  2 ++
 protobuf/inventory.proto |  1 +
 8 files changed, 49 insertions(+), 18 deletions(-)

diff --git a/cr-dump.c b/cr-dump.c
index 25ff91e..fb81bc4 100644
--- a/cr-dump.c
+++ b/cr-dump.c
@@ -354,10 +354,10 @@ static int dump_one_file(struct parasite_ctl *ctl, int fd, int lfd, struct fd_op
 	return dump_unsupp_fd(&p);
 }
 
-static int dump_task_files_seized(struct parasite_ctl *ctl, const int fdinfo,
+static int dump_task_files_seized(struct parasite_ctl *ctl, struct pstree_item *item,
 		struct parasite_drain_fd *dfds)
 {
-	int *lfds;
+	int *lfds, fdinfo;
 	struct fd_opts *opts;
 	int i, ret = -1;
 
@@ -377,13 +377,19 @@ static int dump_task_files_seized(struct parasite_ctl *ctl, const int fdinfo,
 	if (ret)
 		goto err2;
 
+	fdinfo = open_image(CR_FD_FDINFO, O_DUMP, item->ids->files_id);
+	if (fdinfo < 0)
+		goto err2;
+
 	for (i = 0; i < dfds->nr_fds; i++) {
 		ret = dump_one_file(ctl, dfds->fds[i], lfds[i], opts + i, fdinfo);
 		close(lfds[i]);
 		if (ret)
-			goto err2;
+			break;
 	}
 
+	close(fdinfo);
+
 	pr_info("----------------------------------------\n");
 err2:
 	xfree(opts);
@@ -1422,7 +1428,13 @@ static int dump_one_task(struct pstree_item *item)
 	if (!cr_fdset)
 		goto err_cure;
 
-	ret = dump_task_files_seized(parasite_ctl, fdset_fd(cr_fdset, CR_FD_FDINFO), dfds);
+	ret = dump_task_ids(item, cr_fdset);
+	if (ret) {
+		pr_err("Dump ids (pid: %d) failed with %d\n", pid, ret);
+		goto err_cure;
+	}
+
+	ret = dump_task_files_seized(parasite_ctl, item, dfds);
 	if (ret) {
 		pr_err("Dump files (pid: %d) failed with %d\n", pid, ret);
 		goto err_cure;
@@ -1453,12 +1465,6 @@ static int dump_one_task(struct pstree_item *item)
 		goto err_cure;
 	}
 
-	ret = dump_task_ids(item, cr_fdset);
-	if (ret) {
-		pr_err("Dump ids (pid: %d) failed with %d\n", pid, ret);
-		goto err_cure;
-	}
-
 	ret = dump_task_threads(parasite_ctl, item);
 	if (ret) {
 		pr_err("Can't dump threads\n");
diff --git a/cr-restore.c b/cr-restore.c
index 210347e..ccc404d 100644
--- a/cr-restore.c
+++ b/cr-restore.c
@@ -155,7 +155,7 @@ static int root_prepare_shared(void)
 		if (ret < 0)
 			break;
 
-		ret = prepare_fd_pid(pi->pid.virt, pi->rst);
+		ret = prepare_fd_pid(pi);
 		if (ret < 0)
 			break;
 	}
@@ -715,6 +715,9 @@ static int check_core(CoreEntry *core)
 		goto out;
 	}
 
+	if (!current->ids && core->ids)
+		current->ids = core->ids;
+
 	if (core->tc->task_state != TASK_DEAD) {
 		if (!current->ids) {
 			pr_err("Core IDS data missed for non-zombie\n");
diff --git a/files.c b/files.c
index 34eabfb..2a22c3a 100644
--- a/files.c
+++ b/files.c
@@ -217,19 +217,32 @@ int prepare_ctl_tty(int pid, struct rst_info *rst_info, u32 ctl_tty_id)
 	return 0;
 }
 
-int prepare_fd_pid(int pid, struct rst_info *rst_info)
+int prepare_fd_pid(struct pstree_item *item)
 {
 	int fdinfo_fd, ret = 0;
+	pid_t pid = item->pid.virt;
+	struct rst_info *rst_info = item->rst;
 
 	INIT_LIST_HEAD(&rst_info->fds);
 	INIT_LIST_HEAD(&rst_info->eventpoll);
 	INIT_LIST_HEAD(&rst_info->tty_slaves);
 
-	fdinfo_fd = open_image_ro(CR_FD_FDINFO, pid);
-	if (fdinfo_fd < 0) {
-		if (errno == ENOENT)
+	if (!fdinfo_per_id) {
+		fdinfo_fd = open_image_ro(CR_FD_FDINFO, pid);
+		if (fdinfo_fd < 0) {
+			if (errno == ENOENT)
+				return 0;
+			return -1;
+		}
+	} else {
+		if (item->ids == NULL) /* zombie */
 			return 0;
-		else
+
+		if (item->rst->fdt && item->rst->fdt->pid != item->pid.virt)
+			return 0;
+
+		fdinfo_fd = open_image_ro(CR_FD_FDINFO, item->ids->files_id);
+		if (fdinfo_fd < 0)
 			return -1;
 	}
 
diff --git a/image.c b/image.c
index d94c3de..fe85613 100644
--- a/image.c
+++ b/image.c
@@ -15,6 +15,8 @@
 #include "protobuf.h"
 #include "protobuf/inventory.pb-c.h"
 
+bool fdinfo_per_id = false;
+
 int check_img_inventory(void)
 {
 	int fd, ret;
@@ -29,6 +31,8 @@ int check_img_inventory(void)
 	if (ret < 0)
 		return ret;
 
+	fdinfo_per_id = he->has_fdinfo_per_id ?  he->fdinfo_per_id : false;
+
 	ret = he->img_version;
 	inventory_entry__free_unpacked(he, NULL);
 
@@ -52,6 +56,8 @@ int write_img_inventory(void)
 		return -1;
 
 	he.img_version = CRTOOLS_IMAGES_V1;
+	he.fdinfo_per_id = true;
+	he.has_fdinfo_per_id = true;
 
 	if (pb_write_one(fd, &he, PB_INVENTORY) < 0)
 		return -1;
diff --git a/include/crtools.h b/include/crtools.h
index 0afa2a1..00c917d 100644
--- a/include/crtools.h
+++ b/include/crtools.h
@@ -24,7 +24,6 @@ enum {
 	 */
 
 	_CR_FD_TASK_FROM,
-	CR_FD_FDINFO,
 	CR_FD_PAGES,
 	CR_FD_CORE,
 	CR_FD_IDS,
@@ -56,6 +55,7 @@ enum {
 	CR_FD_SHMEM_PAGES,
 	CR_FD_GHOST_FILE,
 	CR_FD_TCP_STREAM,
+	CR_FD_FDINFO,
 
 	_CR_FD_GLOB_FROM,
 	CR_FD_SK_QUEUES,
diff --git a/include/files.h b/include/files.h
index 9d829f2..f246da4 100644
--- a/include/files.h
+++ b/include/files.h
@@ -87,7 +87,7 @@ extern int rst_file_params(int fd, FownEntry *fown, int flags);
 extern void show_saved_files(void);
 
 extern int prepare_fds(struct pstree_item *me);
-extern int prepare_fd_pid(int pid, struct rst_info *rst_info);
+extern int prepare_fd_pid(struct pstree_item *me);
 extern int prepare_ctl_tty(int pid, struct rst_info *rst_info, u32 ctl_tty_id);
 extern int prepare_shared_fdinfo(void);
 extern int get_filemap_fd(int pid, VmaEntry *vma_entry);
diff --git a/include/image.h b/include/image.h
index ee75a5d..8ba25df 100644
--- a/include/image.h
+++ b/include/image.h
@@ -134,4 +134,6 @@ struct page_entry {
 #define GET_FILE_OFF(s, m)	(offsetof(s,m) + MAGIC_OFFSET)
 #define GET_FILE_OFF_AFTER(s)	(sizeof(s) + MAGIC_OFFSET)
 
+extern bool fdinfo_per_id;
+
 #endif /* __CR_IMAGE_H__ */
diff --git a/protobuf/inventory.proto b/protobuf/inventory.proto
index e9a40ee..9dff72c 100644
--- a/protobuf/inventory.proto
+++ b/protobuf/inventory.proto
@@ -1,3 +1,4 @@
 message inventory_entry {
 	required uint32	img_version = 1;
+	optional bool fdinfo_per_id = 2;
 }
-- 
1.7.11.7



More information about the CRIU mailing list