URI: 
       t9term manages to turn off echo at the right times under SunOS ? - plan9port - [fork] Plan 9 from user space
  HTML git clone git://src.adamsgaard.dk/plan9port
   DIR Log
   DIR Files
   DIR Refs
   DIR README
   DIR LICENSE
       ---
   DIR commit 4dcd9af228643d37bb63ab1642c5128b3b30f4bd
   DIR parent aeb54c0efed03187235820c73b7feef2260951cf
  HTML Author: rsc <devnull@localhost>
       Date:   Thu, 15 Apr 2004 02:04:30 +0000
       
       9term manages to turn off echo at the right times under SunOS ?
       
       Diffstat:
         M src/cmd/9term/9term.c               |      19 ++++++++++++++++++-
         M src/cmd/9term/Darwin.c              |      12 ++++++++++++
         M src/cmd/9term/FreeBSD.c             |      12 ++++++++++++
         M src/cmd/9term/Linux.c               |      17 +++++++++++++++++
         M src/cmd/9term/OpenBSD.c             |      13 +++++++++++++
         M src/cmd/9term/SunOS.c               |      84 +++++++++++++++++++++++++++++--
         M src/cmd/9term/rcstart.c             |      20 ++++++++++++++++----
         M src/cmd/9term/term.h                |       4 +++-
         M src/cmd/9term/win.c                 |       2 +-
       
       9 files changed, 173 insertions(+), 10 deletions(-)
       ---
   DIR diff --git a/src/cmd/9term/9term.c b/src/cmd/9term/9term.c
       t@@ -124,6 +124,7 @@ int                scrolling;        /* window scrolls */
        int                clickmsec;        /* time of last click */
        uint                clickq0;        /* point of last click */
        int                rcfd;
       +int                sfd;        /* slave fd, to get/set terminal mode */
        int                rcpid;
        int                maxtab;
        int                use9wm;
       t@@ -223,7 +224,7 @@ threadmain(int argc, char *argv[])
        
                mc = initmouse(nil, screen);
                kc = initkeyboard(nil);
       -        rcpid = rcstart(argc, argv, &rcfd);
       +        rcpid = rcstart(argc, argv, &rcfd, &sfd);
                hoststart();
                plumbstart();
        
       t@@ -270,6 +271,10 @@ hangupnote(void *a, char *msg)
                        postnote(PNGROUP, rcpid, "hangup");
                        noted(NDFLT);
                }
       +        if(strstr(msg, "child")){
       +                /* bug: do better */
       +                exits(0);
       +        }
                noted(NDFLT);
        }
        
       t@@ -284,6 +289,8 @@ hostproc(void *arg)
                i = 0;
                for(;;){
                        /* Let typing have a go -- maybe there's a rubout waiting. */
       +                yield();
       +
                        i = 1-i;        /* toggle */
                        n = threadread(rcfd, rcbuf[i].data, sizeof rcbuf[i].data);
                        if(n <= 0){
       t@@ -828,6 +835,7 @@ key(Rune r)
                        return;
                }
        
       +        rawon = israw(sfd);
                if(rawon && t.q0==t.nr){
                        addraw(&r, 1);
                        consread();
       t@@ -837,6 +845,7 @@ key(Rune r)
                if(r==ESC || (holdon && r==0x7F)){        /* toggle hold */
                        holdon = !holdon;
                        drawhold(holdon);
       +        //        replaceintegerproperty("_9WM_HOLD_MODE", 1, 32, holdon);
                        if(!holdon)
                                consread();
                        if(r==ESC)
       t@@ -918,6 +927,7 @@ consready(void)
                if(holdon)
                        return 0;
        
       +        rawon = israw(sfd);
                if(rawon) 
                        return t.nraw != 0;
        
       t@@ -936,6 +946,7 @@ consread(void)
        {
                char buf[8000], *p;
                int c, width, n;
       +        int echo;
        
                for(;;) {
                        if(!consready())
       t@@ -954,13 +965,18 @@ consread(void)
                                c = *p;
                                p += width;
                                n -= width;
       +                        rawon = israw(sfd);
                                if(!rawon && (c == '\n' || c == '\004' || c == '\x7F'))
                                        break;
                        }
                        /* take out control-d when not doing a zero length write */
                        n = p-buf;
       +                if(0) fprint(2, "write buf\n");
       +                /* temporarily disable echo for buf. sensitive to race? Axel. */
       +        //        echo = setecho(sfd, 0);
                        if(write(rcfd, buf, n) < 0)
                                exits(0);
       +        //        setecho(sfd, echo);
        /*                mallocstats(); */
                }
        }
       t@@ -1242,6 +1258,7 @@ paste(Rune *r, int n, int advance)
        {
                Rune *rbuf;
        
       +        rawon = israw(sfd);
                if(rawon && t.q0==t.nr){
                        addraw(r, n);
                        return;
   DIR diff --git a/src/cmd/9term/Darwin.c b/src/cmd/9term/Darwin.c
       t@@ -133,3 +133,15 @@ myopenpty(int fd[], char *name)
        
        }
        
       +int
       +israw(int fd)
       +{
       +        return 0;
       +}
       +
       +int
       +setecho(int fd, int on)
       +{
       +        return 0;
       +}
       +
   DIR diff --git a/src/cmd/9term/FreeBSD.c b/src/cmd/9term/FreeBSD.c
       t@@ -44,3 +44,15 @@ updatewinsize(int row, int col, int dx, int dy)
                ows = ws;
        }
        
       +int
       +israw(int fd)
       +{
       +        return 0;
       +}
       +
       +int
       +setecho(int fd, int on)
       +{
       +        return 0;
       +}
       +
   DIR diff --git a/src/cmd/9term/Linux.c b/src/cmd/9term/Linux.c
       t@@ -44,3 +44,20 @@ updatewinsize(int row, int col, int dx, int dy)
                ows = ws;
        }
        
       +
       +int
       +israw(int fd)
       +{
       +        return 0;
       +/*
       +        if(tcgetattr(fd, &ttmode) < 0)
       +                fprint(2, "tcgetattr: %r\n");
       +        return !(ttmode.c_lflag&(ICANON|ECHO));
       +*/
       +}
       +
       +int
       +setecho(int fd, int on)
       +{
       +        return 0;
       +}
   DIR diff --git a/src/cmd/9term/OpenBSD.c b/src/cmd/9term/OpenBSD.c
       t@@ -44,3 +44,16 @@ updatewinsize(int row, int col, int dx, int dy)
                        fprint(2, "ioctl: %r\n");
                ows = ws;
        }
       +
       +int
       +israw(int fd)
       +{
       +        return 0;
       +}
       +
       +int
       +setecho(int fd, int on)
       +{
       +        return 0;
       +}
       +
   DIR diff --git a/src/cmd/9term/SunOS.c b/src/cmd/9term/SunOS.c
       t@@ -1,6 +1,6 @@
        #include <u.h>
        #include <termios.h>
       -#include <sys/termios.h>
       +#include <stropts.h>
        #include <libc.h>
        #include "term.h"
        
       t@@ -11,8 +11,17 @@ getpts(int fd[], char *slave)
                if ((grantpt(fd[1]) < 0) || (unlockpt(fd[1]) < 0))
                        return -1;
                fchmod(fd[1], 0622);
       +
                strcpy(slave, ptsname(fd[1]));
       -        fd[0] = open(slave, OREAD);
       +
       +        fd[0] = open(slave, ORDWR);
       +        if(fd[0] < 0)
       +                sysfatal("open %s: %r\n", slave);
       +
       +        /* set up the right streams modules for a tty */
       +        ioctl(fd[0], I_PUSH, "ptem");        /* push ptem */
       +        ioctl(fd[0], I_PUSH, "ldterm");      /* push ldterm */
       +
                return 0;
        }
        
       t@@ -42,7 +51,76 @@ updatewinsize(int row, int col, int dx, int dy)
                ws.ws_ypixel = dy;
                if(ws.ws_row != ows.ws_row || ws.ws_col != ows.ws_col)
                if(ioctl(rcfd, TIOCSWINSZ, &ws) < 0)
       -                fprint(2, "ioctl: %r\n");
       +                fprint(2, "ioctl TIOCSWINSZ: %r\n");
                ows = ws;
        }
        
       +/*
       + * israw has been inspired by Matty Farrow's 9term.
       + * The code below is probably a gross simplification --
       + * for the few cases tested it seems to be enough.
       + * However, for example, Matty's code also looks at ISIG,
       + * whereas, we do not (yet?). Axel.
       + *
       + *Note: I guess only the get/set terminal mode attribute
       + * code needs to be here; the logic around it could be
       + * elswhere (9term.c) - but if the code below is split,
       + * the question is what a nice interface would be. Axel.
       + */
       +
       +static struct termios ttmode;
       +
       +int
       +israw(int fd)
       +{
       +        int e, c, i;
       +
       +        tcgetattr(fd, &ttmode);
       +        c = (ttmode.c_lflag & ICANON) ? 1 : 0;
       +        e = (ttmode.c_lflag & ECHO) ? 1 : 0;
       +        i = (ttmode.c_lflag & ISIG) ? 1 : 0;
       +
       +        if(0) fprint(2, "israw: icanon=%d echo=%d isig=%d\n", c, e, i);
       +
       +        return !c || !e ;
       +}
       +
       +
       +int
       +setecho(int fd, int on)
       +{
       +        int e, c, i;
       +        int oldecho;
       +
       +        tcgetattr(fd, &ttmode);
       +        c = (ttmode.c_lflag & ICANON) ? 1 : 0;
       +        e = (ttmode.c_lflag & ECHO) ? 1 : 0;
       +        i = (ttmode.c_lflag & ISIG) ? 1 : 0;
       +
       +        if(0) fprint(2, "setecho(%d) pre: icanon=%d echo=%d isig=%d\n", on, c, e, i);
       +
       +        oldecho = e;
       +
       +        if (oldecho == on)
       +                return  oldecho;
       +
       +        if (on) {
       +                ttmode.c_lflag |= ECHO;
       +                tcsetattr(fd, TCSANOW, &ttmode);
       +        } else {
       +                ttmode.c_lflag &= ~ECHO;
       +                tcsetattr(fd, TCSANOW, &ttmode);
       +        }
       +
       +        if (0){
       +                tcgetattr(fd, &ttmode);
       +                c = (ttmode.c_lflag & ICANON) ? 1 : 0;
       +                e =  (ttmode.c_lflag & ECHO) ? 1 : 0;
       +                i = (ttmode.c_lflag & ISIG) ? 1 : 0;
       +
       +                fprint(2, "setecho(%d) post: icanon=%d echo=%d isig=%d\n", on, c, e, i);
       +        }
       +
       +        return oldecho;
       +}
       +
   DIR diff --git a/src/cmd/9term/rcstart.c b/src/cmd/9term/rcstart.c
       t@@ -1,11 +1,21 @@
        #include <u.h>
        #include <libc.h>
       +#if 0
       +#include <sys/wait.h>
       +#endif
       +#include <signal.h>
        #include "term.h"
        
       +/*
       + * Somehow we no longer automatically exit
       + * when the shell exits; hence the SIGCHLD stuff.
       + * Something that can be fixed? Axel.
       + */
       +static int pid;
       +
        int
       -rcstart(int argc, char **argv, int *pfd)
       +rcstart(int argc, char **argv, int *pfd, int *tfd)
        {
       -        int pid;
                int fd[2];
                char *xargv[3];
                char slave[256];
       t@@ -27,7 +37,6 @@ rcstart(int argc, char **argv, int *pfd)
                if(getpts(fd, slave) < 0)
                        sysfatal("getpts: %r\n");
        
       -
                switch(pid = fork()) {
                case 0:
                        putenv("TERM", "9term");
       t@@ -44,8 +53,11 @@ rcstart(int argc, char **argv, int *pfd)
                        sysfatal("proc failed: %r");
                        break;
                }
       -        close(fd[0]);
                *pfd = fd[1];
       +        if(tfd)
       +                *tfd = fd[0];
       +        else
       +                close(fd[0]);
                return pid;
        }
        
   DIR diff --git a/src/cmd/9term/term.h b/src/cmd/9term/term.h
       t@@ -2,4 +2,6 @@ extern int getpts(int[], char*);
        extern int childpty(int[], char*);
        extern void updatewinsize(int, int, int, int);
        extern int rcfd;
       -extern int rcstart(int, char*[], int*);
       +extern int rcstart(int, char*[], int*, int*);
       +extern int israw(int);
       +extern int setecho(int, int);
   DIR diff --git a/src/cmd/9term/win.c b/src/cmd/9term/win.c
       t@@ -161,7 +161,7 @@ threadmain(int argc, char **argv)
        
                cwait = threadwaitchan();
                threadcreate(waitthread, nil, STACK);
       -        pid = rcstart(argc, argv, &rcfd);
       +        pid = rcstart(argc, argv, &rcfd, nil);
                if(pid == -1)
                        sysfatal("exec failed");