linux/arch/um/drivers/tty.c
<<
>>
Prefs
   1/*
   2 * Copyright (C) 2001 - 2007 Jeff Dike (jdike@{linux.intel,addtoit}.com)
   3 * Licensed under the GPL
   4 */
   5
   6#include <errno.h>
   7#include <fcntl.h>
   8#include <termios.h>
   9#include "chan_user.h"
  10#include "kern_constants.h"
  11#include "os.h"
  12#include "um_malloc.h"
  13#include "user.h"
  14
  15struct tty_chan {
  16        char *dev;
  17        int raw;
  18        struct termios tt;
  19};
  20
  21static void *tty_chan_init(char *str, int device, const struct chan_opts *opts)
  22{
  23        struct tty_chan *data;
  24
  25        if (*str != ':') {
  26                printk(UM_KERN_ERR "tty_init : channel type 'tty' must specify "
  27                       "a device\n");
  28                return NULL;
  29        }
  30        str++;
  31
  32        data = uml_kmalloc(sizeof(*data), UM_GFP_KERNEL);
  33        if (data == NULL)
  34                return NULL;
  35        *data = ((struct tty_chan) { .dev       = str,
  36                                     .raw       = opts->raw });
  37
  38        return data;
  39}
  40
  41static int tty_open(int input, int output, int primary, void *d,
  42                    char **dev_out)
  43{
  44        struct tty_chan *data = d;
  45        int fd, err, mode = 0;
  46
  47        if (input && output)
  48                mode = O_RDWR;
  49        else if (input)
  50                mode = O_RDONLY;
  51        else if (output)
  52                mode = O_WRONLY;
  53
  54        fd = open(data->dev, mode);
  55        if (fd < 0)
  56                return -errno;
  57
  58        if (data->raw) {
  59                CATCH_EINTR(err = tcgetattr(fd, &data->tt));
  60                if (err)
  61                        return err;
  62
  63                err = raw(fd);
  64                if (err)
  65                        return err;
  66        }
  67
  68        *dev_out = data->dev;
  69        return fd;
  70}
  71
  72const struct chan_ops tty_ops = {
  73        .type           = "tty",
  74        .init           = tty_chan_init,
  75        .open           = tty_open,
  76        .close          = generic_close,
  77        .read           = generic_read,
  78        .write          = generic_write,
  79        .console_write  = generic_console_write,
  80        .window_size    = generic_window_size,
  81        .free           = generic_free,
  82        .winch          = 0,
  83};
  84