extern int tty_write(uint8_t minor, uint8_t rawflag, uint8_t flag);
extern int tty_open(uint8_t minor, uint16_t flag);
extern int tty_close(uint8_t minor);
+extern void tty_exit(void);
extern int tty_ioctl(uint8_t minor, uarg_t request, char *data);
extern void tty_hangup(uint8_t minor);
#undef DEBUGREALLYHARD /* turn on getproc dumping */
#include <kernel.h>
+#include <tty.h>
#include <kdata.h>
#include <printf.h>
#include <audio.h>
udata.u_error = ENOMEM;
newp = NULL;
}
+ newp->p_pgrp = udata.u_ptab->p_pgrp;
}
irqrestore(irq);
if (newp)
memcpy(&(udata.u_ptab->p_priority), &udata.u_utime,
2 * sizeof(clock_t));
- /* See if we have any children. Set child's parents to our parent */
for (p = ptab; p < ptab_end; ++p) {
- if (p->p_status && p->p_pptr == udata.u_ptab
- && p != udata.u_ptab)
+ if (p == udata.u_ptab)
+ continue;
+ /* Set any child's parents to our parent */
+ if (p->p_status && p->p_pptr == udata.u_ptab)
p->p_pptr = udata.u_ptab->p_pptr;
+ /* Send SIGHUP to any pgrp members and remove
+ them from our pgrp */
+ if (p->p_pgrp == udata.u_ptab->p_pid) {
+ p->p_pgrp = 0;
+ ssig(p, SIGHUP);
+ }
}
+ tty_exit();
irqrestore(irq);
#ifdef DEBUG
kprintf
return -1;
}
-
/* If there is no controlling tty for the process, establish it */
- if (!udata.u_ptab->p_tty && !(flag & O_NOCTTY)) {
+ if (!udata.u_ptab->p_tty && !t->pgrp && !(flag & O_NOCTTY)) {
udata.u_ptab->p_tty = minor;
t->pgrp = udata.u_ptab->p_pgrp;
}
int tty_close(uint8_t minor)
{
/* If we are closing the controlling tty, make note */
- if (minor == udata.u_ptab->p_tty)
+ if (minor == udata.u_ptab->p_tty) {
udata.u_ptab->p_tty = 0;
+ ttydata[minor].pgrp = 0;
+ }
/* If we were hung up then the last opener has gone away */
ttydata[minor].flag &= ~TTYF_DEAD;
return (0);
}
+/* If the group owner for the tty dies, the tty loses its group */
+void tty_exit(void)
+{
+ uint8_t t = udata.u_ptab->p_tty;
+ uint16_t *pgrp = &ttydata[t].pgrp;
+ if (t && *pgrp == udata.u_ptab->p_pgrp && *pgrp == udata.u_ptab->p_pid)
+ *pgrp = 0;
+}
+
int tty_ioctl(uint8_t minor, uarg_t request, char *data)
{ /* Data in User Space */
struct tty *t;
struct tty *t = &ttydata[minor];
/* Kill users */
sgrpsig(t->pgrp, SIGHUP);
+ t->pgrp = 0;
/* Stop any new I/O with errors */
t->flag |= TTYF_DEAD;
/* Wake up read/write */