Print this page
Enable pty-based serial console emulation in ioemu.

Signed-off-by: John Levon <john.levon@sun.com>


  37 #include <termios.h>
  38 #include <sys/poll.h>
  39 #include <sys/mman.h>
  40 #include <sys/ioctl.h>
  41 #include <sys/socket.h>
  42 #include <netinet/in.h>
  43 #include <arpa/inet.h>
  44 #include <dirent.h>
  45 #include <netdb.h>
  46 #ifdef _BSD
  47 #include <sys/stat.h>
  48 #ifndef __APPLE__
  49 #include <libutil.h>
  50 #endif
  51 #else
  52 #ifdef __sun__
  53 #include <libdlpi.h>
  54 #include <sys/ethernet.h>
  55 #include <stropts.h>
  56 #include <sys/bufmod.h>

  57 #else
  58 #include <linux/if.h>
  59 #include <linux/if_tun.h>
  60 #include <pty.h>
  61 #include <malloc.h>
  62 #include <linux/rtc.h>
  63 #include <linux/ppdev.h>
  64 #endif
  65 #endif
  66 #endif
  67 
  68 #if defined(CONFIG_SLIRP)
  69 #include "libslirp.h"
  70 #endif
  71 
  72 #ifdef _WIN32
  73 #include <malloc.h>
  74 #include <sys/timeb.h>
  75 #include <windows.h>
  76 #define getopt_long_only getopt_long


1805         free(path); /* realloc errors leave old block */
1806         fprintf(logfile, "realloc error\n");
1807         return -1;
1808     }
1809     path = newpath;
1810 
1811     strcat(path, storeString);
1812     strcat(path, "/tty");
1813     if (!xs_write(xs, XBT_NULL, path, pts, strlen(pts))) {
1814         fprintf(logfile, "xs_write for '%s' fail", storeString);
1815         return -1;
1816     }
1817 
1818     free(path);
1819     xs_daemon_close(xs);
1820     close(xc_handle);
1821 
1822     return 0;
1823 }
1824 
1825 #if defined(__linux__)






























































1826 static CharDriverState *qemu_chr_open_pty(void)
1827 {
1828     struct termios tty;
1829     int master_fd, slave_fd;
1830     
1831     /* Not satisfying */
1832     if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) < 0) {
1833         return NULL;
1834     }
1835     
1836     /* Set raw attributes on the pty. */

1837     cfmakeraw(&tty);
1838     tcsetattr(slave_fd, TCSAFLUSH, &tty);
1839     
1840     fprintf(stderr, "char device redirected to %s\n", ptsname(master_fd));
1841 
1842     return qemu_chr_open_fd(master_fd, master_fd);
1843 }






1844 


1845 static void tty_serial_init(int fd, int speed, 
1846                             int parity, int data_bits, int stop_bits)
1847 {
1848     struct termios tty;
1849     speed_t spd;
1850 
1851 #if 0
1852     printf("tty_serial_init: speed=%d parity=%c data=%d stop=%d\n", 
1853            speed, parity, data_bits, stop_bits);
1854 #endif
1855     tcgetattr (fd, &tty);
1856 
1857     switch(speed) {
1858     case 50:
1859         spd = B50;
1860         break;
1861     case 75:
1862         spd = B75;
1863         break;
1864     case 300:


2025 
2026     if (ioctl(fd, PPCLAIM) < 0) {
2027         close(fd);
2028         return NULL;
2029     }
2030 
2031     chr = qemu_mallocz(sizeof(CharDriverState));
2032     if (!chr) {
2033         close(fd);
2034         return NULL;
2035     }
2036     chr->opaque = (void *)fd;
2037     chr->chr_write = null_chr_write;
2038     chr->chr_ioctl = pp_ioctl;
2039 
2040     qemu_chr_reset(chr);
2041 
2042     return chr;
2043 }
2044 
2045 #else
2046 static CharDriverState *qemu_chr_open_pty(void)
2047 {
2048     return NULL;
2049 }
2050 #endif
2051 
2052 #endif /* !defined(_WIN32) */
2053 
2054 #ifdef _WIN32
2055 typedef struct {
2056     CharDriverState *chr;
2057     int max_size;
2058     HANDLE hcom, hrecv, hsend;
2059     OVERLAPPED orecv, osend;
2060     BOOL fpipe;
2061     DWORD len;
2062 } WinCharState;
2063 
2064 #define NSENDBUF 2048
2065 #define NRECVBUF 2048
2066 #define MAXCONNECT 1
2067 #define NTIMEOUT 5000
2068 
2069 static int win_chr_poll(void *opaque);
2070 static int win_chr_pipe_poll(void *opaque);




  37 #include <termios.h>
  38 #include <sys/poll.h>
  39 #include <sys/mman.h>
  40 #include <sys/ioctl.h>
  41 #include <sys/socket.h>
  42 #include <netinet/in.h>
  43 #include <arpa/inet.h>
  44 #include <dirent.h>
  45 #include <netdb.h>
  46 #ifdef _BSD
  47 #include <sys/stat.h>
  48 #ifndef __APPLE__
  49 #include <libutil.h>
  50 #endif
  51 #else
  52 #ifdef __sun__
  53 #include <libdlpi.h>
  54 #include <sys/ethernet.h>
  55 #include <stropts.h>
  56 #include <sys/bufmod.h>
  57 #include <assert.h>
  58 #else
  59 #include <linux/if.h>
  60 #include <linux/if_tun.h>
  61 #include <pty.h>
  62 #include <malloc.h>
  63 #include <linux/rtc.h>
  64 #include <linux/ppdev.h>
  65 #endif
  66 #endif
  67 #endif
  68 
  69 #if defined(CONFIG_SLIRP)
  70 #include "libslirp.h"
  71 #endif
  72 
  73 #ifdef _WIN32
  74 #include <malloc.h>
  75 #include <sys/timeb.h>
  76 #include <windows.h>
  77 #define getopt_long_only getopt_long


1806         free(path); /* realloc errors leave old block */
1807         fprintf(logfile, "realloc error\n");
1808         return -1;
1809     }
1810     path = newpath;
1811 
1812     strcat(path, storeString);
1813     strcat(path, "/tty");
1814     if (!xs_write(xs, XBT_NULL, path, pts, strlen(pts))) {
1815         fprintf(logfile, "xs_write for '%s' fail", storeString);
1816         return -1;
1817     }
1818 
1819     free(path);
1820     xs_daemon_close(xs);
1821     close(xc_handle);
1822 
1823     return 0;
1824 }
1825 
1826 #ifdef __sun__
1827 static int openpty(int *amaster, int *aslave, char *name,
1828                    struct termios *termp, struct winsize *winp)
1829 {
1830         const char *slave;
1831         int mfd = -1, sfd = -1;
1832 
1833         *amaster = *aslave = -1;
1834 
1835         mfd = open("/dev/ptmx", O_RDWR | O_NOCTTY);
1836         if (mfd < 0)
1837                 goto err;
1838 
1839         if (grantpt(mfd) == -1 || unlockpt(mfd) == -1)
1840                 goto err;
1841 
1842         if ((slave = ptsname(mfd)) == NULL)
1843                 goto err;
1844 
1845         if ((sfd = open(slave, O_RDONLY | O_NOCTTY)) == -1)
1846                 goto err;
1847 
1848         if (ioctl(sfd, I_PUSH, "ptem") == -1 ||
1849             ioctl(sfd, I_PUSH, "ldterm") == -1)
1850                 goto err;
1851 
1852         if (amaster)
1853                 *amaster = mfd;
1854         if (aslave)
1855                 *aslave = sfd;
1856         if (winp)
1857                 ioctl(sfd, TIOCSWINSZ, winp);
1858 
1859         if (termp)
1860                 tcsetattr(sfd, TCSANOW, termp);
1861 
1862         assert(name == NULL);
1863 
1864         return 0;
1865 
1866 err:
1867         if (sfd != -1)
1868                 close(sfd);
1869         close(mfd);
1870         return -1;
1871 }
1872 
1873 void cfmakeraw (struct termios *termios_p)
1874 {
1875         termios_p->c_iflag &=
1876                 ~(IGNBRK|BRKINT|PARMRK|ISTRIP|INLCR|IGNCR|ICRNL|IXON);
1877         termios_p->c_oflag &= ~OPOST;
1878         termios_p->c_lflag &= ~(ECHO|ECHONL|ICANON|ISIG|IEXTEN);
1879         termios_p->c_cflag &= ~(CSIZE|PARENB);
1880         termios_p->c_cflag |= CS8;
1881 
1882         termios_p->c_cc[VMIN] = 0;
1883         termios_p->c_cc[VTIME] = 0;
1884 }
1885 
1886 #endif /* __sun__ */
1887 
1888 #if defined(__linux__) || defined(__sun__)
1889 static CharDriverState *qemu_chr_open_pty(void)
1890 {
1891     struct termios tty;
1892     int master_fd, slave_fd;
1893     

1894     if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) < 0) {
1895         return NULL;
1896     }
1897     
1898     /* Set raw attributes on the pty. */
1899     tcgetattr(slave_fd, &tty);
1900     cfmakeraw(&tty);
1901     tcsetattr(slave_fd, TCSANOW, &tty);
1902     
1903     fprintf(stderr, "char device redirected to %s\n", ptsname(master_fd));
1904 
1905     return qemu_chr_open_fd(master_fd, master_fd);
1906 }
1907 #else /* defined(__linux__) || defined(__sun__) */
1908 static CharDriverState *qemu_chr_open_pty(void)
1909 {
1910     return NULL;
1911 }
1912 #endif /* defined(__linux__) || defined(__sun__) */
1913 
1914 #ifdef __linux__
1915 
1916 static void tty_serial_init(int fd, int speed, 
1917                             int parity, int data_bits, int stop_bits)
1918 {
1919     struct termios tty;
1920     speed_t spd;
1921 
1922 #if 0
1923     printf("tty_serial_init: speed=%d parity=%c data=%d stop=%d\n", 
1924            speed, parity, data_bits, stop_bits);
1925 #endif
1926     tcgetattr (fd, &tty);
1927 
1928     switch(speed) {
1929     case 50:
1930         spd = B50;
1931         break;
1932     case 75:
1933         spd = B75;
1934         break;
1935     case 300:


2096 
2097     if (ioctl(fd, PPCLAIM) < 0) {
2098         close(fd);
2099         return NULL;
2100     }
2101 
2102     chr = qemu_mallocz(sizeof(CharDriverState));
2103     if (!chr) {
2104         close(fd);
2105         return NULL;
2106     }
2107     chr->opaque = (void *)fd;
2108     chr->chr_write = null_chr_write;
2109     chr->chr_ioctl = pp_ioctl;
2110 
2111     qemu_chr_reset(chr);
2112 
2113     return chr;
2114 }
2115 
2116 #endif /* __linux__ */





2117 
2118 #endif /* !defined(_WIN32) */
2119 
2120 #ifdef _WIN32
2121 typedef struct {
2122     CharDriverState *chr;
2123     int max_size;
2124     HANDLE hcom, hrecv, hsend;
2125     OVERLAPPED orecv, osend;
2126     BOOL fpipe;
2127     DWORD len;
2128 } WinCharState;
2129 
2130 #define NSENDBUF 2048
2131 #define NRECVBUF 2048
2132 #define MAXCONNECT 1
2133 #define NTIMEOUT 5000
2134 
2135 static int win_chr_poll(void *opaque);
2136 static int win_chr_pipe_poll(void *opaque);