Commit e8ac085a authored by Pavel Emelyanov's avatar Pavel Emelyanov

Revert "crtools: close all desriptors only for the root task"

We have a race. Consider we have 3 tasks, A, B and C. A and B
share fdtable, C -- does not. Then we might be in a situation
when A is restoring memory reading mem images, and B -- forking
the C child. In that case descriptors held by A (for mem restore)
will be inherited by C and will not get closed.

This reverts commit d36e07aa.
parent 4bd119dd
...@@ -1213,24 +1213,15 @@ static int restore_task_with_children(void *_arg) ...@@ -1213,24 +1213,15 @@ static int restore_task_with_children(void *_arg)
current->pid.real, current->pid.virt); current->pid.real, current->pid.virt);
} }
if ( !(ca->clone_flags & CLONE_FILES))
close_safe(&ca->fd);
if (current->state != TASK_HELPER) { if (current->state != TASK_HELPER) {
ret = clone_service_fd(current->rst->service_fd_id); ret = clone_service_fd(current->rst->service_fd_id);
if (ret) if (ret)
exit(1); exit(1);
} }
if (!(ca->clone_flags & CLONE_FILES)) {
close_safe(&ca->fd);
if (current->parent && current->parent->rst->fdt)
/*
* We're the first child with our own fdtable of
* a parent which had it shared. From that parent
* we have extra service file descriptors left.
*/
close_old_servie_fd(current->parent->rst->fdt->nr);
}
pid = getpid(); pid = getpid();
if (current->pid.virt != pid) { if (current->pid.virt != pid) {
pr_err("Pid %d do not match expected %d\n", pid, current->pid.virt); pr_err("Pid %d do not match expected %d\n", pid, current->pid.virt);
...@@ -1286,6 +1277,12 @@ static int restore_task_with_children(void *_arg) ...@@ -1286,6 +1277,12 @@ static int restore_task_with_children(void *_arg)
if (prepare_mappings(pid)) if (prepare_mappings(pid))
exit(1); exit(1);
if (!(ca->clone_flags & CLONE_FILES)) {
ret = close_old_fds(current);
if (ret)
exit(1);
}
if (create_children_and_session()) if (create_children_and_session())
exit(1); exit(1);
......
...@@ -26,7 +26,6 @@ extern int get_service_fd(enum sfd_type type); ...@@ -26,7 +26,6 @@ extern int get_service_fd(enum sfd_type type);
extern int reserve_service_fd(enum sfd_type type); extern int reserve_service_fd(enum sfd_type type);
extern int install_service_fd(enum sfd_type type, int fd); extern int install_service_fd(enum sfd_type type, int fd);
extern int close_service_fd(enum sfd_type type); extern int close_service_fd(enum sfd_type type);
extern void close_old_servie_fd(int nr);
extern bool is_service_fd(int fd, enum sfd_type type); extern bool is_service_fd(int fd, enum sfd_type type);
extern bool is_any_service_fd(int fd); extern bool is_any_service_fd(int fd);
......
...@@ -341,18 +341,6 @@ int close_service_fd(enum sfd_type type) ...@@ -341,18 +341,6 @@ int close_service_fd(enum sfd_type type)
return 0; return 0;
} }
/* Close all unused service descriptors on a depth of nr. */
void close_old_servie_fd(int nr)
{
int level, i;
BUG_ON(service_fd_id != 0);
for (level = 1; level < nr; level++) {
for (i = SERVICE_FD_MIN + 1; i < SERVICE_FD_MAX; i++) {
close(__get_service_fd(i, level));
}
}
}
int clone_service_fd(int id) int clone_service_fd(int id)
{ {
int ret = -1, i; int ret = -1, i;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment