Revision 1f51470d qemu-char.c
b/qemu-char.c | ||
---|---|---|
218 | 218 |
return len; |
219 | 219 |
} |
220 | 220 |
|
221 |
static int qemu_chr_open_null(QemuOpts *opts, CharDriverState **_chr)
|
|
221 |
static CharDriverState *qemu_chr_open_null(QemuOpts *opts)
|
|
222 | 222 |
{ |
223 | 223 |
CharDriverState *chr; |
224 | 224 |
|
225 | 225 |
chr = g_malloc0(sizeof(CharDriverState)); |
226 | 226 |
chr->chr_write = null_chr_write; |
227 |
|
|
228 |
*_chr= chr; |
|
229 |
return 0; |
|
227 |
return chr; |
|
230 | 228 |
} |
231 | 229 |
|
232 | 230 |
/* MUX driver for serial I/O splitting */ |
... | ... | |
636 | 634 |
return chr; |
637 | 635 |
} |
638 | 636 |
|
639 |
static int qemu_chr_open_file_out(QemuOpts *opts, CharDriverState **_chr)
|
|
637 |
static CharDriverState *qemu_chr_open_file_out(QemuOpts *opts)
|
|
640 | 638 |
{ |
641 | 639 |
int fd_out; |
642 | 640 |
|
643 | 641 |
TFR(fd_out = qemu_open(qemu_opt_get(opts, "path"), |
644 | 642 |
O_WRONLY | O_TRUNC | O_CREAT | O_BINARY, 0666)); |
645 |
if (fd_out < 0) { |
|
646 |
return -errno; |
|
647 |
} |
|
648 |
|
|
649 |
*_chr = qemu_chr_open_fd(-1, fd_out); |
|
650 |
return 0; |
|
643 |
if (fd_out < 0) |
|
644 |
return NULL; |
|
645 |
return qemu_chr_open_fd(-1, fd_out); |
|
651 | 646 |
} |
652 | 647 |
|
653 |
static int qemu_chr_open_pipe(QemuOpts *opts, CharDriverState **_chr)
|
|
648 |
static CharDriverState *qemu_chr_open_pipe(QemuOpts *opts)
|
|
654 | 649 |
{ |
655 | 650 |
int fd_in, fd_out; |
656 | 651 |
char filename_in[256], filename_out[256]; |
... | ... | |
658 | 653 |
|
659 | 654 |
if (filename == NULL) { |
660 | 655 |
fprintf(stderr, "chardev: pipe: no filename given\n"); |
661 |
return -EINVAL;
|
|
656 |
return NULL;
|
|
662 | 657 |
} |
663 | 658 |
|
664 | 659 |
snprintf(filename_in, 256, "%s.in", filename); |
... | ... | |
670 | 665 |
close(fd_in); |
671 | 666 |
if (fd_out >= 0) |
672 | 667 |
close(fd_out); |
673 |
TFR(fd_in = fd_out = qemu_open(filename, O_RDWR | O_BINARY)); |
|
674 |
if (fd_in < 0) { |
|
675 |
return -errno; |
|
676 |
} |
|
668 |
TFR(fd_in = fd_out = open(filename, O_RDWR | O_BINARY)); |
|
669 |
if (fd_in < 0) |
|
670 |
return NULL; |
|
677 | 671 |
} |
678 |
|
|
679 |
*_chr = qemu_chr_open_fd(fd_in, fd_out); |
|
680 |
return 0; |
|
672 |
return qemu_chr_open_fd(fd_in, fd_out); |
|
681 | 673 |
} |
682 | 674 |
|
683 | 675 |
|
... | ... | |
768 | 760 |
fd_chr_close(chr); |
769 | 761 |
} |
770 | 762 |
|
771 |
static int qemu_chr_open_stdio(QemuOpts *opts, CharDriverState **_chr)
|
|
763 |
static CharDriverState *qemu_chr_open_stdio(QemuOpts *opts)
|
|
772 | 764 |
{ |
773 | 765 |
CharDriverState *chr; |
774 | 766 |
|
775 |
if (stdio_nb_clients >= STDIO_MAX_CLIENTS) { |
|
776 |
return -EBUSY; |
|
777 |
} |
|
778 |
|
|
767 |
if (stdio_nb_clients >= STDIO_MAX_CLIENTS) |
|
768 |
return NULL; |
|
779 | 769 |
if (stdio_nb_clients == 0) { |
780 | 770 |
old_fd0_flags = fcntl(0, F_GETFL); |
781 | 771 |
tcgetattr (0, &oldtty); |
... | ... | |
792 | 782 |
display_type != DT_NOGRAPHIC); |
793 | 783 |
qemu_chr_fe_set_echo(chr, false); |
794 | 784 |
|
795 |
*_chr = chr; |
|
796 |
return 0; |
|
785 |
return chr; |
|
797 | 786 |
} |
798 | 787 |
|
799 | 788 |
#ifdef __sun__ |
... | ... | |
980 | 969 |
qemu_chr_be_event(chr, CHR_EVENT_CLOSED); |
981 | 970 |
} |
982 | 971 |
|
983 |
static int qemu_chr_open_pty(QemuOpts *opts, CharDriverState **_chr)
|
|
972 |
static CharDriverState *qemu_chr_open_pty(QemuOpts *opts)
|
|
984 | 973 |
{ |
985 | 974 |
CharDriverState *chr; |
986 | 975 |
PtyCharDriver *s; |
... | ... | |
995 | 984 |
#endif |
996 | 985 |
|
997 | 986 |
if (openpty(&master_fd, &slave_fd, pty_name, NULL, NULL) < 0) { |
998 |
return -errno;
|
|
987 |
return NULL;
|
|
999 | 988 |
} |
1000 | 989 |
|
1001 | 990 |
/* Set raw attributes on the pty. */ |
... | ... | |
1021 | 1010 |
s->fd = master_fd; |
1022 | 1011 |
s->timer = qemu_new_timer_ms(rt_clock, pty_chr_timer, chr); |
1023 | 1012 |
|
1024 |
*_chr = chr; |
|
1025 |
return 0; |
|
1013 |
return chr; |
|
1026 | 1014 |
} |
1027 | 1015 |
|
1028 | 1016 |
static void tty_serial_init(int fd, int speed, |
... | ... | |
1223 | 1211 |
} |
1224 | 1212 |
} |
1225 | 1213 |
|
1226 |
static int qemu_chr_open_tty(QemuOpts *opts, CharDriverState **_chr)
|
|
1214 |
static CharDriverState *qemu_chr_open_tty(QemuOpts *opts)
|
|
1227 | 1215 |
{ |
1228 | 1216 |
const char *filename = qemu_opt_get(opts, "path"); |
1229 | 1217 |
CharDriverState *chr; |
1230 | 1218 |
int fd; |
1231 | 1219 |
|
1232 |
TFR(fd = qemu_open(filename, O_RDWR | O_NONBLOCK));
|
|
1220 |
TFR(fd = open(filename, O_RDWR | O_NONBLOCK)); |
|
1233 | 1221 |
if (fd < 0) { |
1234 |
return -errno;
|
|
1222 |
return NULL;
|
|
1235 | 1223 |
} |
1236 | 1224 |
tty_serial_init(fd, 115200, 'N', 8, 1); |
1237 | 1225 |
chr = qemu_chr_open_fd(fd, fd); |
1226 |
if (!chr) { |
|
1227 |
close(fd); |
|
1228 |
return NULL; |
|
1229 |
} |
|
1238 | 1230 |
chr->chr_ioctl = tty_serial_ioctl; |
1239 | 1231 |
chr->chr_close = qemu_chr_close_tty; |
1240 |
|
|
1241 |
*_chr = chr; |
|
1242 |
return 0; |
|
1232 |
return chr; |
|
1243 | 1233 |
} |
1244 | 1234 |
#else /* ! __linux__ && ! __sun__ */ |
1245 |
static int qemu_chr_open_pty(QemuOpts *opts, CharDriverState **_chr)
|
|
1235 |
static CharDriverState *qemu_chr_open_pty(QemuOpts *opts)
|
|
1246 | 1236 |
{ |
1247 |
return -ENOTSUP;
|
|
1237 |
return NULL;
|
|
1248 | 1238 |
} |
1249 | 1239 |
#endif /* __linux__ || __sun__ */ |
1250 | 1240 |
|
... | ... | |
1358 | 1348 |
qemu_chr_be_event(chr, CHR_EVENT_CLOSED); |
1359 | 1349 |
} |
1360 | 1350 |
|
1361 |
static int qemu_chr_open_pp(QemuOpts *opts, CharDriverState **_chr)
|
|
1351 |
static CharDriverState *qemu_chr_open_pp(QemuOpts *opts)
|
|
1362 | 1352 |
{ |
1363 | 1353 |
const char *filename = qemu_opt_get(opts, "path"); |
1364 | 1354 |
CharDriverState *chr; |
... | ... | |
1366 | 1356 |
int fd; |
1367 | 1357 |
|
1368 | 1358 |
TFR(fd = open(filename, O_RDWR)); |
1369 |
if (fd < 0) { |
|
1370 |
return -errno; |
|
1371 |
} |
|
1359 |
if (fd < 0) |
|
1360 |
return NULL; |
|
1372 | 1361 |
|
1373 | 1362 |
if (ioctl(fd, PPCLAIM) < 0) { |
1374 | 1363 |
close(fd); |
1375 |
return -errno;
|
|
1364 |
return NULL;
|
|
1376 | 1365 |
} |
1377 | 1366 |
|
1378 | 1367 |
drv = g_malloc0(sizeof(ParallelCharDriver)); |
... | ... | |
1387 | 1376 |
|
1388 | 1377 |
qemu_chr_generic_open(chr); |
1389 | 1378 |
|
1390 |
*_chr = chr; |
|
1391 |
return 0; |
|
1379 |
return chr; |
|
1392 | 1380 |
} |
1393 | 1381 |
#endif /* __linux__ */ |
1394 | 1382 |
|
... | ... | |
1430 | 1418 |
return 0; |
1431 | 1419 |
} |
1432 | 1420 |
|
1433 |
static int qemu_chr_open_pp(QemuOpts *opts, CharDriverState **_chr)
|
|
1421 |
static CharDriverState *qemu_chr_open_pp(QemuOpts *opts)
|
|
1434 | 1422 |
{ |
1435 | 1423 |
const char *filename = qemu_opt_get(opts, "path"); |
1436 | 1424 |
CharDriverState *chr; |
1437 | 1425 |
int fd; |
1438 | 1426 |
|
1439 |
fd = qemu_open(filename, O_RDWR); |
|
1440 |
if (fd < 0) { |
|
1441 |
return -errno; |
|
1442 |
} |
|
1427 |
fd = open(filename, O_RDWR); |
|
1428 |
if (fd < 0) |
|
1429 |
return NULL; |
|
1443 | 1430 |
|
1444 | 1431 |
chr = g_malloc0(sizeof(CharDriverState)); |
1445 | 1432 |
chr->opaque = (void *)(intptr_t)fd; |
1446 | 1433 |
chr->chr_write = null_chr_write; |
1447 | 1434 |
chr->chr_ioctl = pp_ioctl; |
1448 |
|
|
1449 |
*_chr = chr; |
|
1450 |
return 0; |
|
1435 |
return chr; |
|
1451 | 1436 |
} |
1452 | 1437 |
#endif |
1453 | 1438 |
|
... | ... | |
1663 | 1648 |
return 0; |
1664 | 1649 |
} |
1665 | 1650 |
|
1666 |
static int qemu_chr_open_win(QemuOpts *opts, CharDriverState **_chr)
|
|
1651 |
static CharDriverState *qemu_chr_open_win(QemuOpts *opts)
|
|
1667 | 1652 |
{ |
1668 | 1653 |
const char *filename = qemu_opt_get(opts, "path"); |
1669 | 1654 |
CharDriverState *chr; |
... | ... | |
1678 | 1663 |
if (win_chr_init(chr, filename) < 0) { |
1679 | 1664 |
g_free(s); |
1680 | 1665 |
g_free(chr); |
1681 |
return -EIO;
|
|
1666 |
return NULL;
|
|
1682 | 1667 |
} |
1683 | 1668 |
qemu_chr_generic_open(chr); |
1684 |
|
|
1685 |
*_chr = chr; |
|
1686 |
return 0; |
|
1669 |
return chr; |
|
1687 | 1670 |
} |
1688 | 1671 |
|
1689 | 1672 |
static int win_chr_pipe_poll(void *opaque) |
... | ... | |
1765 | 1748 |
} |
1766 | 1749 |
|
1767 | 1750 |
|
1768 |
static int qemu_chr_open_win_pipe(QemuOpts *opts, CharDriverState **_chr)
|
|
1751 |
static CharDriverState *qemu_chr_open_win_pipe(QemuOpts *opts)
|
|
1769 | 1752 |
{ |
1770 | 1753 |
const char *filename = qemu_opt_get(opts, "path"); |
1771 | 1754 |
CharDriverState *chr; |
... | ... | |
1780 | 1763 |
if (win_chr_pipe_init(chr, filename) < 0) { |
1781 | 1764 |
g_free(s); |
1782 | 1765 |
g_free(chr); |
1783 |
return -EIO;
|
|
1766 |
return NULL;
|
|
1784 | 1767 |
} |
1785 | 1768 |
qemu_chr_generic_open(chr); |
1786 |
|
|
1787 |
*_chr = chr; |
|
1788 |
return 0; |
|
1769 |
return chr; |
|
1789 | 1770 |
} |
1790 | 1771 |
|
1791 |
static int qemu_chr_open_win_file(HANDLE fd_out, CharDriverState **pchr)
|
|
1772 |
static CharDriverState *qemu_chr_open_win_file(HANDLE fd_out)
|
|
1792 | 1773 |
{ |
1793 | 1774 |
CharDriverState *chr; |
1794 | 1775 |
WinCharState *s; |
... | ... | |
1799 | 1780 |
chr->opaque = s; |
1800 | 1781 |
chr->chr_write = win_chr_write; |
1801 | 1782 |
qemu_chr_generic_open(chr); |
1802 |
*pchr = chr; |
|
1803 |
return 0; |
|
1783 |
return chr; |
|
1804 | 1784 |
} |
1805 | 1785 |
|
1806 |
static int qemu_chr_open_win_con(QemuOpts *opts, CharDriverState **chr)
|
|
1786 |
static CharDriverState *qemu_chr_open_win_con(QemuOpts *opts)
|
|
1807 | 1787 |
{ |
1808 |
return qemu_chr_open_win_file(GetStdHandle(STD_OUTPUT_HANDLE), chr);
|
|
1788 |
return qemu_chr_open_win_file(GetStdHandle(STD_OUTPUT_HANDLE)); |
|
1809 | 1789 |
} |
1810 | 1790 |
|
1811 |
static int qemu_chr_open_win_file_out(QemuOpts *opts, CharDriverState **_chr)
|
|
1791 |
static CharDriverState *qemu_chr_open_win_file_out(QemuOpts *opts)
|
|
1812 | 1792 |
{ |
1813 | 1793 |
const char *file_out = qemu_opt_get(opts, "path"); |
1814 | 1794 |
HANDLE fd_out; |
1815 | 1795 |
|
1816 | 1796 |
fd_out = CreateFile(file_out, GENERIC_WRITE, FILE_SHARE_READ, NULL, |
1817 | 1797 |
OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); |
1818 |
if (fd_out == INVALID_HANDLE_VALUE) { |
|
1819 |
return -EIO; |
|
1820 |
} |
|
1798 |
if (fd_out == INVALID_HANDLE_VALUE) |
|
1799 |
return NULL; |
|
1821 | 1800 |
|
1822 |
return qemu_chr_open_win_file(fd_out, _chr);
|
|
1801 |
return qemu_chr_open_win_file(fd_out); |
|
1823 | 1802 |
} |
1824 | 1803 |
|
1825 | 1804 |
static int win_stdio_write(CharDriverState *chr, const uint8_t *buf, int len) |
... | ... | |
1960 | 1939 |
stdio_nb_clients--; |
1961 | 1940 |
} |
1962 | 1941 |
|
1963 |
static int qemu_chr_open_win_stdio(QemuOpts *opts, CharDriverState **_chr)
|
|
1942 |
static CharDriverState *qemu_chr_open_win_stdio(QemuOpts *opts)
|
|
1964 | 1943 |
{ |
1965 | 1944 |
CharDriverState *chr; |
1966 | 1945 |
WinStdioCharState *stdio; |
... | ... | |
1969 | 1948 |
|
1970 | 1949 |
if (stdio_nb_clients >= STDIO_MAX_CLIENTS |
1971 | 1950 |
|| ((display_type != DT_NOGRAPHIC) && (stdio_nb_clients != 0))) { |
1972 |
return -EIO;
|
|
1951 |
return NULL;
|
|
1973 | 1952 |
} |
1974 | 1953 |
|
1975 | 1954 |
chr = g_malloc0(sizeof(CharDriverState)); |
... | ... | |
2028 | 2007 |
chr->chr_set_echo = qemu_chr_set_echo_win_stdio; |
2029 | 2008 |
qemu_chr_fe_set_echo(chr, false); |
2030 | 2009 |
|
2031 |
*_chr = chr; |
|
2032 |
|
|
2033 |
return 0; |
|
2010 |
return chr; |
|
2034 | 2011 |
} |
2035 | 2012 |
#endif /* !_WIN32 */ |
2036 | 2013 |
|
... | ... | |
2111 | 2088 |
qemu_chr_be_event(chr, CHR_EVENT_CLOSED); |
2112 | 2089 |
} |
2113 | 2090 |
|
2114 |
static int qemu_chr_open_udp(QemuOpts *opts, CharDriverState **_chr)
|
|
2091 |
static CharDriverState *qemu_chr_open_udp(QemuOpts *opts)
|
|
2115 | 2092 |
{ |
2116 | 2093 |
CharDriverState *chr = NULL; |
2117 | 2094 |
NetCharDriver *s = NULL; |
2118 | 2095 |
int fd = -1; |
2119 |
int ret; |
|
2120 | 2096 |
|
2121 | 2097 |
chr = g_malloc0(sizeof(CharDriverState)); |
2122 | 2098 |
s = g_malloc0(sizeof(NetCharDriver)); |
... | ... | |
2124 | 2100 |
fd = inet_dgram_opts(opts); |
2125 | 2101 |
if (fd < 0) { |
2126 | 2102 |
fprintf(stderr, "inet_dgram_opts failed\n"); |
2127 |
ret = -errno; |
|
2128 | 2103 |
goto return_err; |
2129 | 2104 |
} |
2130 | 2105 |
|
... | ... | |
2135 | 2110 |
chr->chr_write = udp_chr_write; |
2136 | 2111 |
chr->chr_update_read_handler = udp_chr_update_read_handler; |
2137 | 2112 |
chr->chr_close = udp_chr_close; |
2138 |
|
|
2139 |
*_chr = chr; |
|
2140 |
return 0; |
|
2113 |
return chr; |
|
2141 | 2114 |
|
2142 | 2115 |
return_err: |
2143 | 2116 |
g_free(chr); |
... | ... | |
2145 | 2118 |
if (fd >= 0) { |
2146 | 2119 |
closesocket(fd); |
2147 | 2120 |
} |
2148 |
return ret;
|
|
2121 |
return NULL;
|
|
2149 | 2122 |
} |
2150 | 2123 |
|
2151 | 2124 |
/***********************************************************/ |
... | ... | |
2436 | 2409 |
qemu_chr_be_event(chr, CHR_EVENT_CLOSED); |
2437 | 2410 |
} |
2438 | 2411 |
|
2439 |
static int qemu_chr_open_socket(QemuOpts *opts, CharDriverState **_chr)
|
|
2412 |
static CharDriverState *qemu_chr_open_socket(QemuOpts *opts)
|
|
2440 | 2413 |
{ |
2441 | 2414 |
CharDriverState *chr = NULL; |
2442 | 2415 |
TCPCharDriver *s = NULL; |
... | ... | |
2446 | 2419 |
int do_nodelay; |
2447 | 2420 |
int is_unix; |
2448 | 2421 |
int is_telnet; |
2449 |
int ret; |
|
2450 | 2422 |
|
2451 | 2423 |
is_listen = qemu_opt_get_bool(opts, "server", 0); |
2452 | 2424 |
is_waitconnect = qemu_opt_get_bool(opts, "wait", 1); |
... | ... | |
2472 | 2444 |
fd = inet_connect_opts(opts); |
2473 | 2445 |
} |
2474 | 2446 |
} |
2475 |
if (fd < 0) { |
|
2476 |
ret = -errno; |
|
2447 |
if (fd < 0) |
|
2477 | 2448 |
goto fail; |
2478 |
} |
|
2479 | 2449 |
|
2480 | 2450 |
if (!is_waitconnect) |
2481 | 2451 |
socket_set_nonblock(fd); |
... | ... | |
2528 | 2498 |
tcp_chr_accept(chr); |
2529 | 2499 |
socket_set_nonblock(s->listen_fd); |
2530 | 2500 |
} |
2531 |
|
|
2532 |
*_chr = chr; |
|
2533 |
return 0; |
|
2501 |
return chr; |
|
2534 | 2502 |
|
2535 | 2503 |
fail: |
2536 | 2504 |
if (fd >= 0) |
2537 | 2505 |
closesocket(fd); |
2538 | 2506 |
g_free(s); |
2539 | 2507 |
g_free(chr); |
2540 |
return ret;
|
|
2508 |
return NULL;
|
|
2541 | 2509 |
} |
2542 | 2510 |
|
2543 | 2511 |
/***********************************************************/ |
... | ... | |
2730 | 2698 |
|
2731 | 2699 |
static const struct { |
2732 | 2700 |
const char *name; |
2733 |
int (*open)(QemuOpts *opts, CharDriverState **chr);
|
|
2701 |
CharDriverState *(*open)(QemuOpts *opts);
|
|
2734 | 2702 |
} backend_table[] = { |
2735 | 2703 |
{ .name = "null", .open = qemu_chr_open_null }, |
2736 | 2704 |
{ .name = "socket", .open = qemu_chr_open_socket }, |
... | ... | |
2771 | 2739 |
{ |
2772 | 2740 |
CharDriverState *chr; |
2773 | 2741 |
int i; |
2774 |
int ret; |
|
2775 | 2742 |
|
2776 | 2743 |
if (qemu_opts_id(opts) == NULL) { |
2777 | 2744 |
fprintf(stderr, "chardev: no id specified\n"); |
... | ... | |
2793 | 2760 |
return NULL; |
2794 | 2761 |
} |
2795 | 2762 |
|
2796 |
ret = backend_table[i].open(opts, &chr);
|
|
2797 |
if (ret < 0) {
|
|
2798 |
fprintf(stderr, "chardev: opening backend \"%s\" failed: %s\n",
|
|
2799 |
qemu_opt_get(opts, "backend"), strerror(-ret));
|
|
2763 |
chr = backend_table[i].open(opts);
|
|
2764 |
if (!chr) {
|
|
2765 |
fprintf(stderr, "chardev: opening backend \"%s\" failed\n", |
|
2766 |
qemu_opt_get(opts, "backend")); |
|
2800 | 2767 |
return NULL; |
2801 | 2768 |
} |
2802 | 2769 |
|
Also available in: Unified diff