aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/char/vt_ioctl.c
diff options
context:
space:
mode:
authorEric W. Biederman <ebiederm@xmission.com>2007-02-10 04:44:34 -0500
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-02-11 13:51:24 -0500
commit8b6312f4dcc1efe7975731b6c47dd134282bd9ac (patch)
tree71c94b01bda940c5610d448d0f4a2aa3c7665b4c /drivers/char/vt_ioctl.c
parent0a7b35cb18c52d651f6ed9cd59edc979200ab880 (diff)
[PATCH] vt: refactor console SAK processing
This does several things. - It moves looking up of the current foreground console into process context where we can safely take the semaphore that protects this operation. - It uses the new flavor of work queue processing. - This generates a factor of do_SAK, __do_SAK that runs immediately. - This calls __do_SAK with the console semaphore held ensuring nothing else happens to the console while we process the SAK operation. - With the console SAK processing moved into process context this patch removes the xchg operations that I used to attempt to attomically update struct pid, because of the strange locking used in the SAK processing. With SAK using the normal console semaphore nothing special is needed. Cc: Oleg Nesterov <oleg@tv-sign.ru> Signed-off-by: Eric W. Biederman <ebiederm@xmission.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'drivers/char/vt_ioctl.c')
-rw-r--r--drivers/char/vt_ioctl.c28
1 files changed, 26 insertions, 2 deletions
diff --git a/drivers/char/vt_ioctl.c b/drivers/char/vt_ioctl.c
index dc8368ebb1ac..3a5d301e783b 100644
--- a/drivers/char/vt_ioctl.c
+++ b/drivers/char/vt_ioctl.c
@@ -672,7 +672,8 @@ int vt_ioctl(struct tty_struct *tty, struct file * file,
672 vc->vt_mode = tmp; 672 vc->vt_mode = tmp;
673 /* the frsig is ignored, so we set it to 0 */ 673 /* the frsig is ignored, so we set it to 0 */
674 vc->vt_mode.frsig = 0; 674 vc->vt_mode.frsig = 0;
675 put_pid(xchg(&vc->vt_pid, get_pid(task_pid(current)))); 675 put_pid(vc->vt_pid);
676 vc->vt_pid = get_pid(task_pid(current));
676 /* no switch is required -- saw@shade.msu.ru */ 677 /* no switch is required -- saw@shade.msu.ru */
677 vc->vt_newvt = -1; 678 vc->vt_newvt = -1;
678 release_console_sem(); 679 release_console_sem();
@@ -1063,12 +1064,35 @@ void reset_vc(struct vc_data *vc)
1063 vc->vt_mode.relsig = 0; 1064 vc->vt_mode.relsig = 0;
1064 vc->vt_mode.acqsig = 0; 1065 vc->vt_mode.acqsig = 0;
1065 vc->vt_mode.frsig = 0; 1066 vc->vt_mode.frsig = 0;
1066 put_pid(xchg(&vc->vt_pid, NULL)); 1067 put_pid(vc->vt_pid);
1068 vc->vt_pid = NULL;
1067 vc->vt_newvt = -1; 1069 vc->vt_newvt = -1;
1068 if (!in_interrupt()) /* Via keyboard.c:SAK() - akpm */ 1070 if (!in_interrupt()) /* Via keyboard.c:SAK() - akpm */
1069 reset_palette(vc); 1071 reset_palette(vc);
1070} 1072}
1071 1073
1074void vc_SAK(struct work_struct *work)
1075{
1076 struct vc *vc_con =
1077 container_of(work, struct vc, SAK_work);
1078 struct vc_data *vc;
1079 struct tty_struct *tty;
1080
1081 acquire_console_sem();
1082 vc = vc_con->d;
1083 if (vc) {
1084 tty = vc->vc_tty;
1085 /*
1086 * SAK should also work in all raw modes and reset
1087 * them properly.
1088 */
1089 if (tty)
1090 __do_SAK(tty);
1091 reset_vc(vc);
1092 }
1093 release_console_sem();
1094}
1095
1072/* 1096/*
1073 * Performs the back end of a vt switch 1097 * Performs the back end of a vt switch
1074 */ 1098 */