2 * Copyright (C) 2000, 2002 Jeff Dike (jdike@karaya.com)
3 * Licensed under the GPL
8 #include "linux/tty_driver.h"
9 #include "linux/major.h"
11 #include "linux/init.h"
12 #include "linux/console.h"
13 #include "asm/termbits.h"
19 #include "mconsole_kern.h"
21 static const int ssl_version
= 1;
23 /* Referenced only by tty_driver below - presumably it's locked correctly
27 static struct tty_driver
*ssl_driver
;
31 static void ssl_announce(char *dev_name
, int dev
)
33 printk(KERN_INFO
"Serial line %d assigned device '%s'\n", dev
,
37 /* Almost const, except that xterm_title may be changed in an initcall */
38 static struct chan_opts opts
= {
39 .announce
= ssl_announce
,
40 .xterm_title
= "Serial Line #%d",
44 static int ssl_config(char *str
, char **error_out
);
45 static int ssl_get_config(char *dev
, char *str
, int size
, char **error_out
);
46 static int ssl_remove(int n
, char **error_out
);
49 /* Const, except for .mc.list */
50 static struct line_driver driver
= {
51 .name
= "UML serial line",
52 .device_name
= "ttyS",
55 .type
= TTY_DRIVER_TYPE_SERIAL
,
58 .read_irq_name
= "ssl",
59 .write_irq
= SSL_WRITE_IRQ
,
60 .write_irq_name
= "ssl-write",
62 .list
= LIST_HEAD_INIT(driver
.mc
.list
),
65 .get_config
= ssl_get_config
,
71 /* The array is initialized by line_init, at initcall time. The
72 * elements are locked individually as needed.
74 static struct line serial_lines
[NR_PORTS
] =
75 { [0 ... NR_PORTS
- 1] = LINE_INIT(CONFIG_SSL_CHAN
, &driver
) };
77 static int ssl_config(char *str
, char **error_out
)
79 return line_config(serial_lines
, ARRAY_SIZE(serial_lines
), str
, &opts
,
83 static int ssl_get_config(char *dev
, char *str
, int size
, char **error_out
)
85 return line_get_config(dev
, serial_lines
, ARRAY_SIZE(serial_lines
), str
,
89 static int ssl_remove(int n
, char **error_out
)
91 return line_remove(serial_lines
, ARRAY_SIZE(serial_lines
), n
,
95 static int ssl_open(struct tty_struct
*tty
, struct file
*filp
)
97 int err
= line_open(serial_lines
, tty
);
100 printk(KERN_ERR
"Failed to open serial line %d, err = %d\n",
107 static void ssl_flush_buffer(struct tty_struct
*tty
)
112 static void ssl_stop(struct tty_struct
*tty
)
114 printk(KERN_ERR
"Someone should implement ssl_stop\n");
117 static void ssl_start(struct tty_struct
*tty
)
119 printk(KERN_ERR
"Someone should implement ssl_start\n");
122 void ssl_hangup(struct tty_struct
*tty
)
127 static const struct tty_operations ssl_ops
= {
131 .put_char
= line_put_char
,
132 .write_room
= line_write_room
,
133 .chars_in_buffer
= line_chars_in_buffer
,
134 .flush_buffer
= line_flush_buffer
,
135 .flush_chars
= line_flush_chars
,
136 .set_termios
= line_set_termios
,
138 .throttle
= line_throttle
,
139 .unthrottle
= line_unthrottle
,
143 .hangup
= ssl_hangup
,
147 /* Changed by ssl_init and referenced by ssl_exit, which are both serialized
148 * by being an initcall and exitcall, respectively.
150 static int ssl_init_done
= 0;
152 static void ssl_console_write(struct console
*c
, const char *string
,
155 struct line
*line
= &serial_lines
[c
->index
];
158 spin_lock_irqsave(&line
->lock
, flags
);
159 console_write_chan(&line
->chan_list
, string
, len
);
160 spin_unlock_irqrestore(&line
->lock
, flags
);
163 static struct tty_driver
*ssl_console_device(struct console
*c
, int *index
)
169 static int ssl_console_setup(struct console
*co
, char *options
)
171 struct line
*line
= &serial_lines
[co
->index
];
173 return console_open_chan(line
, co
);
176 /* No locking for register_console call - relies on single-threaded initcalls */
177 static struct console ssl_cons
= {
179 .write
= ssl_console_write
,
180 .device
= ssl_console_device
,
181 .setup
= ssl_console_setup
,
182 .flags
= CON_PRINTBUFFER
|CON_ANYTIME
,
186 static int ssl_init(void)
190 printk(KERN_INFO
"Initializing software serial port version %d\n",
192 ssl_driver
= register_lines(&driver
, &ssl_ops
, serial_lines
,
193 ARRAY_SIZE(serial_lines
));
195 new_title
= add_xterm_umid(opts
.xterm_title
);
196 if (new_title
!= NULL
)
197 opts
.xterm_title
= new_title
;
199 lines_init(serial_lines
, ARRAY_SIZE(serial_lines
), &opts
);
202 register_console(&ssl_cons
);
205 late_initcall(ssl_init
);
207 static void ssl_exit(void)
211 close_lines(serial_lines
, ARRAY_SIZE(serial_lines
));
213 __uml_exitcall(ssl_exit
);
215 static int ssl_chan_setup(char *str
)
220 ret
= line_setup(serial_lines
, ARRAY_SIZE(serial_lines
), str
, &error
);
222 printk(KERN_ERR
"Failed to set up serial line with "
223 "configuration string \"%s\" : %s\n", str
, error
);
228 __setup("ssl", ssl_chan_setup
);
229 __channel_help(ssl_chan_setup
, "ssl");