summaryrefslogtreecommitdiffstats
path: root/sys/kern/tty.c
diff options
context:
space:
mode:
authored <ed@FreeBSD.org>2009-02-05 14:21:09 +0000
committered <ed@FreeBSD.org>2009-02-05 14:21:09 +0000
commite085cfc4851a368e9eeca99b5977b66c163ff7ee (patch)
treee926c85860710dfb0757c5d76805dc86e28e6080 /sys/kern/tty.c
parent8f639d4b9ab34b25f907b609cbfdc7610647394f (diff)
downloadFreeBSD-src-e085cfc4851a368e9eeca99b5977b66c163ff7ee.zip
FreeBSD-src-e085cfc4851a368e9eeca99b5977b66c163ff7ee.tar.gz
Don't leave the console TTY constantly open.
When we leave the console TTY constantly open, we never reset the termios attributes. This causes output processing, echoing, etc. not to be reset to the proper values when going into single user mode after the system has booted. It also causes nl-to-crnl-conversion not to take place during shutdown, which causes a `staircase effect'. This patch adds a new TTY flag, TF_OPENED_CONS, which is set when the TTY is opened through /dev/console. Because the flags are only used by the kernel and the pstat(8) utility, I've decided to renumber the TTY flags. This shouldn't be an issue, because the TTY layer is not yet part of a stable release. Reported by: Mark Atkinson <atkin901 yahoo com> Tested by: sepotvin
Diffstat (limited to 'sys/kern/tty.c')
-rw-r--r--sys/kern/tty.c71
1 files changed, 40 insertions, 31 deletions
diff --git a/sys/kern/tty.c b/sys/kern/tty.c
index 25d44e8..d73683c 100644
--- a/sys/kern/tty.c
+++ b/sys/kern/tty.c
@@ -291,11 +291,12 @@ ttydev_open(struct cdev *dev, int oflags, int devtype, struct thread *td)
}
}
- if (TTY_CALLOUT(tp, dev)) {
+ if (dev == dev_console)
+ tp->t_flags |= TF_OPENED_CONS;
+ else if (TTY_CALLOUT(tp, dev))
tp->t_flags |= TF_OPENED_OUT;
- } else {
+ else
tp->t_flags |= TF_OPENED_IN;
- }
done: tp->t_flags &= ~TF_OPENCLOSE;
ttydev_leave(tp);
@@ -308,22 +309,28 @@ ttydev_close(struct cdev *dev, int fflag, int devtype, struct thread *td)
{
struct tty *tp = dev->si_drv1;
+ tty_lock(tp);
+
/*
* Don't actually close the device if it is being used as the
* console.
*/
- if (dev_console_filename != NULL &&
- strcmp(dev_console_filename, tty_devname(tp)) == 0)
- return (0);
+ MPASS((tp->t_flags & TF_OPENED) != TF_OPENED);
+ if (dev == dev_console)
+ tp->t_flags &= ~TF_OPENED_CONS;
+ else
+ tp->t_flags &= ~(TF_OPENED_IN|TF_OPENED_OUT);
- tty_lock(tp);
+ if (tp->t_flags & TF_OPENED) {
+ tty_unlock(tp);
+ return (0);
+ }
/*
* This can only be called once. The callin and the callout
* devices cannot be opened at the same time.
*/
- MPASS((tp->t_flags & TF_OPENED) != TF_OPENED);
- tp->t_flags &= ~(TF_OPENED|TF_EXCLUDE|TF_STOPPED);
+ tp->t_flags &= ~(TF_EXCLUDE|TF_STOPPED);
/* Properly wake up threads that are stuck - revoke(). */
tp->t_revokecnt++;
@@ -1797,13 +1804,14 @@ ttyconsdev_write(struct cdev *dev, struct uio *uio, int ioflag)
}
/*
- * /dev/console is a little different than normal TTY's. Unlike regular
- * TTY device nodes, this device node will not revoke the entire TTY
- * upon closure and all data written to it will be logged.
+ * /dev/console is a little different than normal TTY's. When opened,
+ * it determines which TTY to use. When data gets written to it, it
+ * will be logged in the kernel message buffer.
*/
static struct cdevsw ttyconsdev_cdevsw = {
.d_version = D_VERSION,
.d_open = ttyconsdev_open,
+ .d_close = ttydev_close,
.d_read = ttydev_read,
.d_write = ttyconsdev_write,
.d_ioctl = ttydev_ioctl,
@@ -1845,33 +1853,34 @@ static struct {
char val;
} ttystates[] = {
#if 0
- { TF_NOPREFIX, 'N' },
+ { TF_NOPREFIX, 'N' },
#endif
- { TF_INITLOCK, 'I' },
- { TF_CALLOUT, 'C' },
+ { TF_INITLOCK, 'I' },
+ { TF_CALLOUT, 'C' },
/* Keep these together -> 'Oi' and 'Oo'. */
- { TF_OPENED, 'O' },
- { TF_OPENED_IN, 'i' },
- { TF_OPENED_OUT,'o' },
+ { TF_OPENED, 'O' },
+ { TF_OPENED_IN, 'i' },
+ { TF_OPENED_OUT, 'o' },
+ { TF_OPENED_CONS, 'c' },
- { TF_GONE, 'G' },
- { TF_OPENCLOSE, 'B' },
- { TF_ASYNC, 'Y' },
- { TF_LITERAL, 'L' },
+ { TF_GONE, 'G' },
+ { TF_OPENCLOSE, 'B' },
+ { TF_ASYNC, 'Y' },
+ { TF_LITERAL, 'L' },
/* Keep these together -> 'Hi' and 'Ho'. */
- { TF_HIWAT, 'H' },
- { TF_HIWAT_IN, 'i' },
- { TF_HIWAT_OUT, 'o' },
+ { TF_HIWAT, 'H' },
+ { TF_HIWAT_IN, 'i' },
+ { TF_HIWAT_OUT, 'o' },
- { TF_STOPPED, 'S' },
- { TF_EXCLUDE, 'X' },
- { TF_BYPASS, 'l' },
- { TF_ZOMBIE, 'Z' },
- { TF_HOOK, 's' },
+ { TF_STOPPED, 'S' },
+ { TF_EXCLUDE, 'X' },
+ { TF_BYPASS, 'l' },
+ { TF_ZOMBIE, 'Z' },
+ { TF_HOOK, 's' },
- { 0, '\0' },
+ { 0, '\0'},
};
#define TTY_FLAG_BITS \
OpenPOWER on IntegriCloud