Newer
Older
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
/* Copyright (C) 2014 Cloudius Systems, Ltd.
*
* This work is open source software, licensed under the terms of the
* BSD license as described in the LICENSE file in the top-level directory.
*/
#include <osv/device.h>
#include <osv/debug.hh>
#include <signal.h>
#include "console-multiplexer.hh"
namespace console {
ConsoleMultiplexer::ConsoleMultiplexer(const termios *tio, ConsoleDriver *early_driver)
: _tio(tio)
, _early_driver(early_driver)
{
}
void ConsoleMultiplexer::driver_add(ConsoleDriver *driver)
{
_drivers.push_back(driver);
}
void ConsoleMultiplexer::start()
{
_ldisc = new LineDiscipline(_tio);
for (auto driver : _drivers)
driver->start([&] { _ldisc->read_poll(driver); });
_started = true;
}
void ConsoleMultiplexer::read(struct uio *uio, int ioflag) {
if (!_started)
return;
_ldisc->read(uio, ioflag);
}
void ConsoleMultiplexer::drivers_write(const char *str, size_t len)
{
for (auto driver : _drivers)
driver->write(str, len);
}
void ConsoleMultiplexer::drivers_flush()
{
for (auto driver : _drivers)
driver->flush();
}
void ConsoleMultiplexer::write_ll(const char *str, size_t len)
{
if (!_started) {
if (_early_driver != nullptr) {
_early_driver->write(str, len);
_early_driver->flush();
}
} else {
_ldisc->write(str, len,
[&] (const char *str, size_t len) { drivers_write(str, len); });
drivers_flush();
}
}
void ConsoleMultiplexer::write(const char *str, size_t len)
{
if (!_started) {
WITH_LOCK(_early_lock) {
write_ll(str, len);
}
} else {
WITH_LOCK(_mutex) {
write_ll(str, len);
}
}
}
void ConsoleMultiplexer::write(struct uio *uio, int ioflag)
{
linearize_uio_write(uio, ioflag, [&] (const char *str, size_t len) {
write(str, len);
});
}
int ConsoleMultiplexer::read_queue_size()
{
if (!_started)
return -1;
return _ldisc->read_queue_size();
}
}