[CRIU] [PATCH] tty: Restore controlling terminal once per session
Cyrill Gorcunov
gorcunov at openvz.org
Thu Nov 5 09:06:48 PST 2015
There might be several same terminals opened (say
tty6 or whatever) which gonna look as a seaprate
files but actually pointing into same tty kernel
instance. Moreover if it's a controlling terminal
we will be trying to restore it as many times as
find non zero sid on the peer.
Instead lets do a simple trick first: choose a leader
from the terminal group and use it only for controlling
terminal restoration.
https://jira.sw.ru/browse/PSBM-40969
Signed-off-by: Cyrill Gorcunov <gorcunov at openvz.org>
---
tty.c | 28 ++++++++++++++++++++++++++++
1 file changed, 28 insertions(+)
diff --git a/tty.c b/tty.c
index 63a6ba24eb73..6d239548248e 100644
--- a/tty.c
+++ b/tty.c
@@ -92,6 +92,8 @@ struct tty_info {
bool create;
bool inherit;
+
+ struct tty_info *ctl_tty;
};
struct tty_dump_info {
@@ -1072,6 +1074,8 @@ static int tty_find_restoring_task(struct tty_info *info)
return 0;
if (info->tie->sid) {
+ if (info->ctl_tty != info)
+ return 0;
if (!tty_is_master(info)) {
if (tty_has_active_pair(info))
return 0;
@@ -1159,6 +1163,29 @@ int tty_setup_slavery(void)
{
struct tty_info *info, *peer, *m;
+ /*
+ * The image may carry several terminals opened
+ * belonging to the same session, so choose the
+ * leader which gonna be setting up the controlling
+ * terminal.
+ */
+ list_for_each_entry(info, &all_ttys, list) {
+ if (!info->tie->sid || info->ctl_tty)
+ continue;
+
+ info->ctl_tty = info;
+ pr_debug("ctl tty master %x\n", info->tfe->id);
+ peer = info;
+ list_for_each_entry_safe_continue(peer, m, &all_ttys, list) {
+ if (!peer->tie->sid || peer->ctl_tty)
+ continue;
+ if (peer->tie->sid == info->tie->sid) {
+ pr_debug(" `- slave %x\n", peer->tfe->id);
+ peer->ctl_tty = info;
+ }
+ }
+ }
+
list_for_each_entry(info, &all_ttys, list) {
if (tty_find_restoring_task(info))
return -1;
@@ -1316,6 +1343,7 @@ static int collect_one_tty(void *obj, ProtobufCMessage *msg)
info->driver = get_tty_driver(major(info->tie->rdev), minor(info->tie->rdev));
info->create = tty_is_master(info);
info->inherit = false;
+ info->ctl_tty = NULL;
if (verify_info(info))
return -1;
--
2.4.3
More information about the CRIU
mailing list