summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNicolas Schodet2013-03-02 23:25:00 +0100
committerNicolas Schodet2013-03-02 23:25:00 +0100
commite216af2da56613367622ca5b8cb28a9f181de754 (patch)
tree4cc77e5a38f03d6eeb2a5941771238dd8a7b88c2
parentbf2856a0e14daed33e1055ab5f24393d53e40250 (diff)
digital/ucoolib/ucoolib/arch/host: add pty host stream
-rw-r--r--digital/ucoolib/ucoolib/arch/host/Module1
-rw-r--r--digital/ucoolib/ucoolib/arch/host/host_stream.hh2
-rw-r--r--digital/ucoolib/ucoolib/arch/host/host_stream.host.cc45
3 files changed, 47 insertions, 1 deletions
diff --git a/digital/ucoolib/ucoolib/arch/host/Module b/digital/ucoolib/ucoolib/arch/host/Module
index 6c5a9fad..2c7fead9 100644
--- a/digital/ucoolib/ucoolib/arch/host/Module
+++ b/digital/ucoolib/ucoolib/arch/host/Module
@@ -1 +1,2 @@
arch_host_SOURCES := host.host.cc host_stream.host.cc
+host_LIBS += -lutil
diff --git a/digital/ucoolib/ucoolib/arch/host/host_stream.hh b/digital/ucoolib/ucoolib/arch/host/host_stream.hh
index 53512250..9739e6bb 100644
--- a/digital/ucoolib/ucoolib/arch/host/host_stream.hh
+++ b/digital/ucoolib/ucoolib/arch/host/host_stream.hh
@@ -32,6 +32,8 @@ class HostStream : public Stream
public:
/// Default constructor, use stdin/stdout.
HostStream ();
+ /// PTY constructor, will make a link to PTY at the given name.
+ HostStream (const char *name);
/// Close if needed.
~HostStream ();
/// See Stream::block.
diff --git a/digital/ucoolib/ucoolib/arch/host/host_stream.host.cc b/digital/ucoolib/ucoolib/arch/host/host_stream.host.cc
index 6bf5f8b9..3b99a429 100644
--- a/digital/ucoolib/ucoolib/arch/host/host_stream.host.cc
+++ b/digital/ucoolib/ucoolib/arch/host/host_stream.host.cc
@@ -25,24 +25,67 @@
#include "ucoolib/common.hh"
+#include <stdlib.h>
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>
+#include <pty.h>
#include <fcntl.h>
#include <errno.h>
namespace ucoo {
+/// Setup non canonical mode.
+static void
+setup_raw (int fd)
+{
+ struct termios tc;
+ tcgetattr (fd, &tc);
+ tc.c_iflag &= ~(IGNPAR | PARMRK | ISTRIP | IGNBRK | BRKINT | IGNCR |
+ ICRNL | INLCR | IXON | IXOFF | IXANY | IMAXBEL);
+ tc.c_iflag |= INPCK;
+ tc.c_oflag &= ~(OPOST);
+ tc.c_cflag &= ~(HUPCL | CSTOPB | PARENB | PARODD | CSIZE);
+ tc.c_cflag |= CS8 | CLOCAL | CREAD;
+ tc.c_lflag &= ~(ICANON | ECHO | ISIG | IEXTEN | NOFLSH | TOSTOP);
+ tc.c_cc[VTIME] = 0;
+ tc.c_cc[VMIN] = 1;
+ tcflush (fd, TCIFLUSH);
+ tcsetattr (fd, TCSANOW, &tc);
+}
+
HostStream::HostStream ()
: fdi_ (0), fdo_ (1)
{
}
+HostStream::HostStream (const char *name)
+ : fdi_ (-1), fdo_ (-1)
+{
+ int fd, slave_fd, r;
+ // Open and unlock pt.
+ if (openpty (&fd, &slave_fd, 0, 0, 0) == -1
+ || grantpt (fd) == -1
+ || unlockpt (fd) == -1)
+ halt_perror ();
+ // Make a link to the slave pts.
+ unlink (name);
+ const char *slave_name = ptsname (fd);
+ assert (slave_name);
+ r = symlink (slave_name, name);
+ assert_perror (r != -1);
+ // Make slave raw.
+ setup_raw (slave_fd);
+ // Use as both in and out.
+ fdi_ = fdo_ = fd;
+ // slave_fd is left open.
+}
+
HostStream::~HostStream ()
{
if (fdi_ != -1 && fdi_ != 0)
close (fdi_);
- if (fdo_ != -1 && fdo_ != 1)
+ if (fdo_ != -1 && fdo_ != 1 && fdo_ != fdi_)
close (fdo_);
}