Lines Matching full:port
3 * u_serial.c - utilities for USB gadget "serial port"/TTY support
39 * "serial port" functionality through the USB gadget stack. Each such
40 * port is exposed through a /dev/ttyGS* node.
42 * After this module has been loaded, the individual TTY port can be requested
46 * host issues a config change event. Data can only flow when the port is
49 * A given TTY port can be made available in multiple configurations.
56 * Configurations may expose more than one TTY port. For example, if
101 * The port structure holds info for each port, one for each minor number
105 struct tty_port port; member
129 bool suspended; /* port suspended */
139 struct gs_port *port; member
210 gs_send_packet(struct gs_port *port, char *packet, unsigned size) in gs_send_packet() argument
214 len = kfifo_len(&port->port_write_buf); in gs_send_packet()
218 size = kfifo_out(&port->port_write_buf, packet, size); in gs_send_packet()
233 static int gs_start_tx(struct gs_port *port) in gs_start_tx() argument
235 __releases(&port->port_lock) in gs_start_tx()
236 __acquires(&port->port_lock) in gs_start_tx()
239 struct list_head *pool = &port->write_pool; in gs_start_tx()
244 if (!port->port_usb) in gs_start_tx()
247 in = port->port_usb->in; in gs_start_tx()
249 while (!port->write_busy && !list_empty(pool)) { in gs_start_tx()
253 if (port->write_started >= QUEUE_SIZE) in gs_start_tx()
257 len = gs_send_packet(port, req->buf, in->maxpacket); in gs_start_tx()
259 wake_up_interruptible(&port->drain_wait); in gs_start_tx()
263 port->icount.tx += len; in gs_start_tx()
267 req->zero = kfifo_is_empty(&port->port_write_buf); in gs_start_tx()
269 pr_vdebug("ttyGS%d: tx len=%d, %3ph ...\n", port->port_num, len, req->buf); in gs_start_tx()
278 port->write_busy = true; in gs_start_tx()
279 spin_unlock(&port->port_lock); in gs_start_tx()
281 spin_lock(&port->port_lock); in gs_start_tx()
282 port->write_busy = false; in gs_start_tx()
291 port->write_started++; in gs_start_tx()
294 if (!port->port_usb) in gs_start_tx()
298 if (do_tty_wake && port->port.tty) in gs_start_tx()
299 tty_wakeup(port->port.tty); in gs_start_tx()
306 static unsigned gs_start_rx(struct gs_port *port) in gs_start_rx() argument
308 __releases(&port->port_lock) in gs_start_rx()
309 __acquires(&port->port_lock) in gs_start_rx()
312 struct list_head *pool = &port->read_pool; in gs_start_rx()
313 struct usb_ep *out = port->port_usb->out; in gs_start_rx()
321 tty = port->port.tty; in gs_start_rx()
325 if (port->read_started >= QUEUE_SIZE) in gs_start_rx()
335 spin_unlock(&port->port_lock); in gs_start_rx()
337 spin_lock(&port->port_lock); in gs_start_rx()
345 port->read_started++; in gs_start_rx()
348 if (!port->port_usb) in gs_start_rx()
351 return port->read_started; in gs_start_rx()
367 struct gs_port *port = container_of(w, struct gs_port, push); in gs_rx_push() local
369 struct list_head *queue = &port->read_queue; in gs_rx_push()
374 spin_lock_irq(&port->port_lock); in gs_rx_push()
375 tty = port->port.tty; in gs_rx_push()
388 pr_vdebug("ttyGS%d: shutdown\n", port->port_num); in gs_rx_push()
394 port->port_num, req->status); in gs_rx_push()
409 n = port->n_read; in gs_rx_push()
415 port->icount.rx += size; in gs_rx_push()
416 count = tty_insert_flip_string(&port->port, packet, in gs_rx_push()
422 port->n_read += count; in gs_rx_push()
424 port->port_num, count, req->actual); in gs_rx_push()
427 port->n_read = 0; in gs_rx_push()
430 list_move(&req->list, &port->read_pool); in gs_rx_push()
431 port->read_started--; in gs_rx_push()
438 tty_flip_buffer_push(&port->port); in gs_rx_push()
449 schedule_delayed_work(&port->push, 1); in gs_rx_push()
452 if (!disconnect && port->port_usb) in gs_rx_push()
453 gs_start_rx(port); in gs_rx_push()
455 spin_unlock_irq(&port->port_lock); in gs_rx_push()
460 struct gs_port *port = ep->driver_data; in gs_read_complete() local
463 spin_lock(&port->port_lock); in gs_read_complete()
464 list_add_tail(&req->list, &port->read_queue); in gs_read_complete()
465 schedule_delayed_work(&port->push, 0); in gs_read_complete()
466 spin_unlock(&port->port_lock); in gs_read_complete()
471 struct gs_port *port = ep->driver_data; in gs_write_complete() local
473 spin_lock(&port->port_lock); in gs_write_complete()
474 list_add(&req->list, &port->write_pool); in gs_write_complete()
475 port->write_started--; in gs_write_complete()
485 gs_start_tx(port); in gs_write_complete()
494 spin_unlock(&port->port_lock); in gs_write_complete()
537 * @port: port to use
541 * this port. If nothing is listening on the host side, we may
544 static int gs_start_io(struct gs_port *port) in gs_start_io() argument
546 struct list_head *head = &port->read_pool; in gs_start_io()
551 if (!port->port_usb || !port->port.tty) in gs_start_io()
557 * configurations may use different endpoints with a given port; in gs_start_io()
560 ep = port->port_usb->out; in gs_start_io()
562 &port->read_allocated); in gs_start_io()
566 status = gs_alloc_requests(port->port_usb->in, &port->write_pool, in gs_start_io()
567 gs_write_complete, &port->write_allocated); in gs_start_io()
569 gs_free_requests(ep, head, &port->read_allocated); in gs_start_io()
574 port->n_read = 0; in gs_start_io()
575 started = gs_start_rx(port); in gs_start_io()
578 gs_start_tx(port); in gs_start_io()
581 tty_wakeup(port->port.tty); in gs_start_io()
584 if (port->port_usb) { in gs_start_io()
585 gs_free_requests(ep, head, &port->read_allocated); in gs_start_io()
586 gs_free_requests(port->port_usb->in, &port->write_pool, in gs_start_io()
587 &port->write_allocated); in gs_start_io()
607 struct gs_port *port; in gs_open() local
611 port = ports[port_num].port; in gs_open()
612 if (!port) { in gs_open()
617 spin_lock_irq(&port->port_lock); in gs_open()
620 if (!kfifo_initialized(&port->port_write_buf)) { in gs_open()
622 spin_unlock_irq(&port->port_lock); in gs_open()
629 status = kfifo_alloc(&port->port_write_buf, in gs_open()
637 spin_lock_irq(&port->port_lock); in gs_open()
641 if (port->port.count++) in gs_open()
644 tty->driver_data = port; in gs_open()
645 port->port.tty = tty; in gs_open()
648 if (port->port_usb) { in gs_open()
649 /* if port is suspended, wait resume to start I/0 stream */ in gs_open()
650 if (!port->suspended) { in gs_open()
651 struct gserial *gser = port->port_usb; in gs_open()
653 pr_debug("gs_open: start ttyGS%d\n", port->port_num); in gs_open()
654 gs_start_io(port); in gs_open()
659 pr_debug("delay start of ttyGS%d\n", port->port_num); in gs_open()
660 port->start_delayed = true; in gs_open()
664 pr_debug("gs_open: ttyGS%d (%p,%p)\n", port->port_num, tty, file); in gs_open()
667 spin_unlock_irq(&port->port_lock); in gs_open()
680 p->port.count > 1; in gs_close_flush_done()
688 struct gs_port *port = tty->driver_data; in gs_close() local
691 spin_lock_irq(&port->port_lock); in gs_close()
693 if (port->port.count != 1) { in gs_close()
695 if (port->port.count == 0) in gs_close()
698 --port->port.count; in gs_close()
702 pr_debug("gs_close: ttyGS%d (%p,%p) ...\n", port->port_num, tty, file); in gs_close()
704 gser = port->port_usb; in gs_close()
705 if (gser && !port->suspended && gser->disconnect) in gs_close()
711 if (kfifo_len(&port->port_write_buf) > 0 && gser) { in gs_close()
712 spin_unlock_irq(&port->port_lock); in gs_close()
713 wait_event_interruptible_timeout(port->drain_wait, in gs_close()
714 gs_close_flush_done(port), in gs_close()
716 spin_lock_irq(&port->port_lock); in gs_close()
718 if (port->port.count != 1) in gs_close()
721 gser = port->port_usb; in gs_close()
729 kfifo_free(&port->port_write_buf); in gs_close()
731 kfifo_reset(&port->port_write_buf); in gs_close()
733 port->start_delayed = false; in gs_close()
734 port->port.count = 0; in gs_close()
735 port->port.tty = NULL; in gs_close()
738 port->port_num, tty, file); in gs_close()
740 wake_up(&port->close_wait); in gs_close()
742 spin_unlock_irq(&port->port_lock); in gs_close()
747 struct gs_port *port = tty->driver_data; in gs_write() local
751 port->port_num, tty, count); in gs_write()
753 spin_lock_irqsave(&port->port_lock, flags); in gs_write()
755 count = kfifo_in(&port->port_write_buf, buf, count); in gs_write()
757 if (port->port_usb) in gs_write()
758 gs_start_tx(port); in gs_write()
759 spin_unlock_irqrestore(&port->port_lock, flags); in gs_write()
766 struct gs_port *port = tty->driver_data; in gs_put_char() local
771 port->port_num, tty, ch, __builtin_return_address(0)); in gs_put_char()
773 spin_lock_irqsave(&port->port_lock, flags); in gs_put_char()
774 status = kfifo_put(&port->port_write_buf, ch); in gs_put_char()
775 spin_unlock_irqrestore(&port->port_lock, flags); in gs_put_char()
782 struct gs_port *port = tty->driver_data; in gs_flush_chars() local
785 pr_vdebug("gs_flush_chars: (%d,%p)\n", port->port_num, tty); in gs_flush_chars()
787 spin_lock_irqsave(&port->port_lock, flags); in gs_flush_chars()
788 if (port->port_usb) in gs_flush_chars()
789 gs_start_tx(port); in gs_flush_chars()
790 spin_unlock_irqrestore(&port->port_lock, flags); in gs_flush_chars()
795 struct gs_port *port = tty->driver_data; in gs_write_room() local
799 spin_lock_irqsave(&port->port_lock, flags); in gs_write_room()
800 if (port->port_usb) in gs_write_room()
801 room = kfifo_avail(&port->port_write_buf); in gs_write_room()
802 spin_unlock_irqrestore(&port->port_lock, flags); in gs_write_room()
805 port->port_num, tty, room); in gs_write_room()
812 struct gs_port *port = tty->driver_data; in gs_chars_in_buffer() local
816 spin_lock_irqsave(&port->port_lock, flags); in gs_chars_in_buffer()
817 chars = kfifo_len(&port->port_write_buf); in gs_chars_in_buffer()
818 spin_unlock_irqrestore(&port->port_lock, flags); in gs_chars_in_buffer()
821 port->port_num, tty, chars); in gs_chars_in_buffer()
829 struct gs_port *port = tty->driver_data; in gs_unthrottle() local
832 spin_lock_irqsave(&port->port_lock, flags); in gs_unthrottle()
833 if (port->port_usb) { in gs_unthrottle()
838 pr_vdebug("ttyGS%d: unthrottle\n", port->port_num); in gs_unthrottle()
839 schedule_delayed_work(&port->push, 0); in gs_unthrottle()
841 spin_unlock_irqrestore(&port->port_lock, flags); in gs_unthrottle()
846 struct gs_port *port = tty->driver_data; in gs_break_ctl() local
851 port->port_num, duration); in gs_break_ctl()
853 spin_lock_irq(&port->port_lock); in gs_break_ctl()
854 gser = port->port_usb; in gs_break_ctl()
857 spin_unlock_irq(&port->port_lock); in gs_break_ctl()
865 struct gs_port *port = tty->driver_data; in gs_get_icount() local
869 spin_lock_irqsave(&port->port_lock, flags); in gs_get_icount()
870 cnow = port->icount; in gs_get_icount()
871 spin_unlock_irqrestore(&port->port_lock, flags); in gs_get_icount()
992 static int gs_console_connect(struct gs_port *port) in gs_console_connect() argument
994 struct gs_console *cons = port->console; in gs_console_connect()
1001 ep = port->port_usb->in; in gs_console_connect()
1014 pr_debug("ttyGS%d: console connected!\n", port->port_num); in gs_console_connect()
1021 static void gs_console_disconnect(struct gs_port *port) in gs_console_disconnect() argument
1023 struct gs_console *cons = port->console; in gs_console_disconnect()
1045 static int gs_console_init(struct gs_port *port) in gs_console_init() argument
1050 if (port->console) in gs_console_init()
1053 cons = kzalloc(sizeof(*port->console), GFP_KERNEL); in gs_console_init()
1061 cons->console.index = port->port_num; in gs_console_init()
1068 pr_err("ttyGS%d: allocate console buffer failed\n", port->port_num); in gs_console_init()
1073 port->console = cons; in gs_console_init()
1076 spin_lock_irq(&port->port_lock); in gs_console_init()
1077 if (port->port_usb) in gs_console_init()
1078 gs_console_connect(port); in gs_console_init()
1079 spin_unlock_irq(&port->port_lock); in gs_console_init()
1084 static void gs_console_exit(struct gs_port *port) in gs_console_exit() argument
1086 struct gs_console *cons = port->console; in gs_console_exit()
1093 spin_lock_irq(&port->port_lock); in gs_console_exit()
1095 gs_console_disconnect(port); in gs_console_exit()
1096 spin_unlock_irq(&port->port_lock); in gs_console_exit()
1101 port->console = NULL; in gs_console_exit()
1106 struct gs_port *port; in gserial_set_console() local
1115 port = ports[port_num].port; in gserial_set_console()
1117 if (WARN_ON(port == NULL)) { in gserial_set_console()
1123 ret = gs_console_init(port); in gserial_set_console()
1125 gs_console_exit(port); in gserial_set_console()
1135 struct gs_port *port; in gserial_get_console() local
1139 port = ports[port_num].port; in gserial_get_console()
1141 if (WARN_ON(port == NULL)) in gserial_get_console()
1144 ret = sprintf(page, "%u\n", !!port->console); in gserial_get_console()
1154 static int gs_console_connect(struct gs_port *port) in gs_console_connect() argument
1159 static void gs_console_disconnect(struct gs_port *port) in gs_console_disconnect() argument
1163 static int gs_console_init(struct gs_port *port) in gs_console_init() argument
1168 static void gs_console_exit(struct gs_port *port) in gs_console_exit() argument
1177 struct gs_port *port; in gs_port_alloc() local
1181 if (ports[port_num].port) { in gs_port_alloc()
1186 port = kzalloc(sizeof(struct gs_port), GFP_KERNEL); in gs_port_alloc()
1187 if (port == NULL) { in gs_port_alloc()
1192 tty_port_init(&port->port); in gs_port_alloc()
1193 spin_lock_init(&port->port_lock); in gs_port_alloc()
1194 init_waitqueue_head(&port->drain_wait); in gs_port_alloc()
1195 init_waitqueue_head(&port->close_wait); in gs_port_alloc()
1197 INIT_DELAYED_WORK(&port->push, gs_rx_push); in gs_port_alloc()
1199 INIT_LIST_HEAD(&port->read_pool); in gs_port_alloc()
1200 INIT_LIST_HEAD(&port->read_queue); in gs_port_alloc()
1201 INIT_LIST_HEAD(&port->write_pool); in gs_port_alloc()
1203 port->port_num = port_num; in gs_port_alloc()
1204 port->port_line_coding = *coding; in gs_port_alloc()
1206 ports[port_num].port = port; in gs_port_alloc()
1212 static int gs_closed(struct gs_port *port) in gs_closed() argument
1216 spin_lock_irq(&port->port_lock); in gs_closed()
1217 cond = port->port.count == 0; in gs_closed()
1218 spin_unlock_irq(&port->port_lock); in gs_closed()
1223 static void gserial_free_port(struct gs_port *port) in gserial_free_port() argument
1225 cancel_delayed_work_sync(&port->push); in gserial_free_port()
1227 wait_event(port->close_wait, gs_closed(port)); in gserial_free_port()
1228 WARN_ON(port->port_usb != NULL); in gserial_free_port()
1229 tty_port_destroy(&port->port); in gserial_free_port()
1230 kfree(port); in gserial_free_port()
1235 struct gs_port *port; in gserial_free_line() local
1238 if (!ports[port_num].port) { in gserial_free_line()
1242 port = ports[port_num].port; in gserial_free_line()
1243 gs_console_exit(port); in gserial_free_line()
1244 ports[port_num].port = NULL; in gserial_free_line()
1247 gserial_free_port(port); in gserial_free_line()
1255 struct gs_port *port; in gserial_alloc_line_no_console() local
1278 port = ports[port_num].port; in gserial_alloc_line_no_console()
1279 tty_dev = tty_port_register_device(&port->port, in gserial_alloc_line_no_console()
1282 pr_err("%s: failed to register tty for port %d, err %ld\n", in gserial_alloc_line_no_console()
1287 ports[port_num].port = NULL; in gserial_alloc_line_no_console()
1289 gserial_free_port(port); in gserial_alloc_line_no_console()
1303 gs_console_init(ports[*line_num].port); in gserial_alloc_line()
1312 * @port_num: which port is active
1332 struct gs_port *port; in gserial_connect() local
1339 port = ports[port_num].port; in gserial_connect()
1340 if (!port) { in gserial_connect()
1344 if (port->port_usb) { in gserial_connect()
1353 gser->in->driver_data = port; in gserial_connect()
1358 gser->out->driver_data = port; in gserial_connect()
1361 spin_lock_irqsave(&port->port_lock, flags); in gserial_connect()
1362 gser->ioport = port; in gserial_connect()
1363 port->port_usb = gser; in gserial_connect()
1368 gser->port_line_coding = port->port_line_coding; in gserial_connect()
1375 if (port->port.count) { in gserial_connect()
1376 pr_debug("gserial_connect: start ttyGS%d\n", port->port_num); in gserial_connect()
1377 gs_start_io(port); in gserial_connect()
1385 status = gs_console_connect(port); in gserial_connect()
1386 spin_unlock_irqrestore(&port->port_lock, flags); in gserial_connect()
1408 struct gs_port *port = gser->ioport; in gserial_disconnect() local
1411 if (!port) in gserial_disconnect()
1417 spin_lock(&port->port_lock); in gserial_disconnect()
1419 gs_console_disconnect(port); in gserial_disconnect()
1422 port->port_line_coding = gser->port_line_coding; in gserial_disconnect()
1424 port->port_usb = NULL; in gserial_disconnect()
1426 if (port->port.count > 0) { in gserial_disconnect()
1427 wake_up_interruptible(&port->drain_wait); in gserial_disconnect()
1428 if (port->port.tty) in gserial_disconnect()
1429 tty_hangup(port->port.tty); in gserial_disconnect()
1431 port->suspended = false; in gserial_disconnect()
1432 spin_unlock(&port->port_lock); in gserial_disconnect()
1440 spin_lock_irqsave(&port->port_lock, flags); in gserial_disconnect()
1441 if (port->port.count == 0) in gserial_disconnect()
1442 kfifo_free(&port->port_write_buf); in gserial_disconnect()
1443 gs_free_requests(gser->out, &port->read_pool, NULL); in gserial_disconnect()
1444 gs_free_requests(gser->out, &port->read_queue, NULL); in gserial_disconnect()
1445 gs_free_requests(gser->in, &port->write_pool, NULL); in gserial_disconnect()
1447 port->read_allocated = port->read_started = in gserial_disconnect()
1448 port->write_allocated = port->write_started = 0; in gserial_disconnect()
1450 spin_unlock_irqrestore(&port->port_lock, flags); in gserial_disconnect()
1456 struct gs_port *port; in gserial_suspend() local
1460 port = gser->ioport; in gserial_suspend()
1462 if (!port) { in gserial_suspend()
1467 spin_lock(&port->port_lock); in gserial_suspend()
1469 port->suspended = true; in gserial_suspend()
1470 port->start_delayed = true; in gserial_suspend()
1471 spin_unlock_irqrestore(&port->port_lock, flags); in gserial_suspend()
1477 struct gs_port *port; in gserial_resume() local
1481 port = gser->ioport; in gserial_resume()
1483 if (!port) { in gserial_resume()
1488 spin_lock(&port->port_lock); in gserial_resume()
1490 port->suspended = false; in gserial_resume()
1491 if (!port->start_delayed) { in gserial_resume()
1492 spin_unlock_irqrestore(&port->port_lock, flags); in gserial_resume()
1496 pr_debug("delayed start ttyGS%d\n", port->port_num); in gserial_resume()
1497 gs_start_io(port); in gserial_resume()
1500 port->start_delayed = false; in gserial_resume()
1501 spin_unlock_irqrestore(&port->port_lock, flags); in gserial_resume()
1566 MODULE_DESCRIPTION("utilities for USB gadget \"serial port\"/TTY support");