लिनक्स/linux-0.01.tar/fs/tty ioctl.c
< लिनक्स | linux-0.01.tar
#include <errno.h> #include <termios.h> #include <linux/sched.h> #include <linux/kernel.h> #include <linux/tty.h> #include <asm/segment.h> #include <asm/system.h> static void flush(struct tty_queue * queue) { cli(); queue->head = queue->tail; sti(); } static void wait_until_sent(struct tty_struct * tty) { /* do nothing - not implemented */ } static void send_break(struct tty_struct * tty) { /* do nothing - not implemented */ } static int get_termios(struct tty_struct * tty, struct termios * termios) { int i; verify_area(termios, sizeof (*termios)); for (i=0 ; i< (sizeof (*termios)) ; i++) put_fs_byte( ((char *)&tty->termios)[i] , i+(char *)termios ); return 0; } static int set_termios(struct tty_struct * tty, struct termios * termios) { int i; for (i=0 ; i< (sizeof (*termios)) ; i++) ((char *)&tty->termios)[i]=get_fs_byte(i+(char *)termios); return 0; } static int get_termio(struct tty_struct * tty, struct termio * termio) { int i; struct termio tmp_termio; verify_area(termio, sizeof (*termio)); tmp_termio.c_iflag = tty->termios.c_iflag; tmp_termio.c_oflag = tty->termios.c_oflag; tmp_termio.c_cflag = tty->termios.c_cflag; tmp_termio.c_lflag = tty->termios.c_lflag; tmp_termio.c_line = tty->termios.c_line; for(i=0 ; i < NCC ; i++) tmp_termio.c_cc[i] = tty->termios.c_cc[i]; for (i=0 ; i< (sizeof (*termio)) ; i++) put_fs_byte( ((char *)&tmp_termio)[i] , i+(char *)termio ); return 0; } static int set_termio(struct tty_struct * tty, struct termio * termio) { int i; struct termio tmp_termio; for (i=0 ; i< (sizeof (*termio)) ; i++) ((char *)&tmp_termio)[i]=get_fs_byte(i+(char *)termio); *(unsigned short *)&tty->termios.c_iflag = tmp_termio.c_iflag; *(unsigned short *)&tty->termios.c_oflag = tmp_termio.c_oflag; *(unsigned short *)&tty->termios.c_cflag = tmp_termio.c_cflag; *(unsigned short *)&tty->termios.c_lflag = tmp_termio.c_lflag; tty->termios.c_line = tmp_termio.c_line; for(i=0 ; i < NCC ; i++) tty->termios.c_cc[i] = tmp_termio.c_cc[i]; return 0; } int tty_ioctl(int dev, int cmd, int arg) { struct tty_struct * tty; if (MAJOR(dev) == 5) { dev=current->tty; if (dev<0) panic("tty_ioctl: dev<0"); } else dev=MINOR(dev); tty = dev + tty_table; switch (cmd) { case TCGETS: return get_termios(tty,(struct termios *) arg); case TCSETSF: flush(&tty->read_q); /* fallthrough */ case TCSETSW: wait_until_sent(tty); /* fallthrough */ case TCSETS: return set_termios(tty,(struct termios *) arg); case TCGETA: return get_termio(tty,(struct termio *) arg); case TCSETAF: flush(&tty->read_q); /* fallthrough */ case TCSETAW: wait_until_sent(tty); /* fallthrough */ case TCSETA: return set_termio(tty,(struct termio *) arg); case TCSBRK: if (!arg) { wait_until_sent(tty); send_break(tty); } return 0; case TCXONC: return -EINVAL; /* not implemented */ case TCFLSH: if (arg==0) flush(&tty->read_q); else if (arg==1) flush(&tty->write_q); else if (arg==2) { flush(&tty->read_q); flush(&tty->write_q); } else return -EINVAL; return 0; case TIOCEXCL: return -EINVAL; /* not implemented */ case TIOCNXCL: return -EINVAL; /* not implemented */ case TIOCSCTTY: return -EINVAL; /* set controlling term NI */ case TIOCGPGRP: verify_area((void *) arg,4); put_fs_long(tty->pgrp,(unsigned long *) arg); return 0; case TIOCSPGRP: tty->pgrp=get_fs_long((unsigned long *) arg); return 0; case TIOCOUTQ: verify_area((void *) arg,4); put_fs_long(CHARS(tty->write_q),(unsigned long *) arg); return 0; case TIOCSTI: return -EINVAL; /* not implemented */ case TIOCGWINSZ: return -EINVAL; /* not implemented */ case TIOCSWINSZ: return -EINVAL; /* not implemented */ case TIOCMGET: return -EINVAL; /* not implemented */ case TIOCMBIS: return -EINVAL; /* not implemented */ case TIOCMBIC: return -EINVAL; /* not implemented */ case TIOCMSET: return -EINVAL; /* not implemented */ case TIOCGSOFTCAR: return -EINVAL; /* not implemented */ case TIOCSSOFTCAR: return -EINVAL; /* not implemented */ default: return -EINVAL; } }