This source file includes following definitions.
- pty_close
 
- pty_copy
 
- pty_write
 
- pty_open
 
   1 
   2 
   3 
   4 
   5 
   6 
   7 
   8 
   9 
  10 
  11 
  12 
  13 
  14 
  15 #include <linux/errno.h>
  16 #include <linux/sched.h>
  17 #include <linux/tty.h>
  18 #include <linux/fcntl.h>
  19 #include <linux/interrupt.h>
  20 #include <linux/string.h>
  21 
  22 #include <asm/system.h>
  23 #include <asm/bitops.h>
  24 
  25 #define MIN(a,b)        ((a) < (b) ? (a) : (b))
  26 
  27 static void pty_close(struct tty_struct * tty, struct file * filp)
     
  28 {
  29         if (!tty)
  30                 return;
  31         if (IS_A_PTY_MASTER(tty->line)) {
  32                 if (tty->count > 1)
  33                         printk("master pty_close: count = %d!!\n", tty->count);
  34         } else {
  35                 if (tty->count > 2)
  36                         return;
  37         }
  38         wake_up_interruptible(&tty->secondary.proc_list);
  39         wake_up_interruptible(&tty->read_q.proc_list);
  40         wake_up_interruptible(&tty->write_q.proc_list);
  41         if (!tty->link)
  42                 return;
  43         wake_up_interruptible(&tty->link->secondary.proc_list);
  44         wake_up_interruptible(&tty->link->read_q.proc_list);
  45         wake_up_interruptible(&tty->link->write_q.proc_list);
  46         if (IS_A_PTY_MASTER(tty->line))
  47                 tty_hangup(tty->link);
  48         else {
  49                 start_tty(tty);
  50                 set_bit(TTY_SLAVE_CLOSED, &tty->link->flags);
  51         }
  52 }
  53 
  54 static inline void pty_copy(struct tty_struct * from, struct tty_struct * to)
     
  55 {
  56         unsigned long count, n;
  57         struct tty_queue *fq, *tq;
  58 
  59         if (from->stopped || EMPTY(&from->write_q))
  60                 return;
  61         fq = &from->write_q;
  62         tq = &to->read_q;
  63         count = MIN(CHARS(fq), LEFT(tq));
  64         while (count) {
  65                 n = MIN(MIN(TTY_BUF_SIZE - fq->tail, TTY_BUF_SIZE - tq->head),
  66                         count);
  67                 memcpy(&tq->buf[tq->head], &fq->buf[fq->tail], n);
  68                 count -= n;
  69                 fq->tail = (fq->tail + n) & (TTY_BUF_SIZE - 1);
  70                 tq->head = (tq->head + n) & (TTY_BUF_SIZE - 1);
  71         }
  72         TTY_READ_FLUSH(to);
  73         if (LEFT(fq) > WAKEUP_CHARS)
  74                 wake_up_interruptible(&fq->proc_list);
  75         if (from->write_data_cnt) {
  76                 set_bit(from->line, &tty_check_write);
  77                 mark_bh(TTY_BH);
  78         }
  79 }
  80 
  81 
  82 
  83 
  84 
  85 
  86 static void pty_write(struct tty_struct * tty)
     
  87 {
  88         if (tty->link)
  89                 pty_copy(tty,tty->link);
  90 }
  91 
  92 int pty_open(struct tty_struct *tty, struct file * filp)
     
  93 {
  94         if (!tty || !tty->link)
  95                 return -ENODEV;
  96         if (IS_A_PTY_SLAVE(tty->line))
  97                 clear_bit(TTY_SLAVE_CLOSED, &tty->link->flags);
  98         tty->write = tty->link->write = pty_write;
  99         tty->close = tty->link->close = pty_close;
 100         wake_up_interruptible(&tty->read_q.proc_list);
 101         if (filp->f_flags & O_NDELAY)
 102                 return 0;
 103         while (!tty->link->count && !(current->signal & ~current->blocked))
 104                 interruptible_sleep_on(&tty->link->read_q.proc_list);
 105         if (!tty->link->count)
 106                 return -ERESTARTSYS;
 107         return 0;
 108 }