--bug
[svn42.git] / go / termios / termios.go
1 package termios
2
3 import (
4     "fmt";
5     "os";
6     "syscall";
7     "unsafe"
8     "errors"
9 )
10
11 // termios types
12 type cc_t byte
13 type speed_t uint
14 type tcflag_t uint
15
16 // termios constants
17 const (
18     BRKINT = tcflag_t (0000002);
19     ICRNL = tcflag_t (0000400);
20     INPCK = tcflag_t (0000020);
21     ISTRIP = tcflag_t (0000040);
22     IXON = tcflag_t (0002000);
23     OPOST = tcflag_t (0000001);
24     CS8 = tcflag_t (0000060);
25     ECHO = tcflag_t (0000010);
26     ICANON = tcflag_t (0000002);
27     IEXTEN = tcflag_t (0100000);
28     ISIG = tcflag_t (0000001);
29     VTIME = tcflag_t (5);
30     VMIN = tcflag_t (6)
31 )
32
33 const NCCS = 32
34 type termios struct {
35     c_iflag, c_oflag, c_cflag, c_lflag tcflag_t;
36     c_line cc_t;
37     c_cc [NCCS]cc_t;
38     c_ispeed, c_ospeed speed_t
39 }
40
41 // ioctl constants
42 const (
43     TCGETS = 0x5401;
44     TCSETS = 0x5402
45 )
46
47 var (
48     orig_termios termios;
49     ttyfd uintptr = 0 // STDIN_FILENO
50 )
51
52 func Ttyfd(fd uintptr) {
53   ttyfd=fd
54 }
55
56 func getTermios (dst *termios) error {
57     r1, _, errno := syscall.Syscall (syscall.SYS_IOCTL,
58                                      uintptr (ttyfd), uintptr (TCGETS),
59                                      uintptr (unsafe.Pointer (dst)));
60
61     if err := os.NewSyscallError ("SYS_IOCTL", errno); errno!=0 && err != nil {
62         return err
63     }
64
65     if r1 != 0 {
66     //    return errors.New("Error")
67     }
68
69     return nil
70 }
71
72 func setTermios (src *termios) error {
73     r1, _, errno := syscall.Syscall (syscall.SYS_IOCTL,
74                                      uintptr (ttyfd), uintptr (TCSETS),
75                                      uintptr (unsafe.Pointer (src)));
76
77     if err := os.NewSyscallError ("SYS_IOCTL", errno); errno!=0 &&err != nil {
78         return err
79     }
80
81     if r1 != 0 {
82         return errors.New ("Error")
83     }
84
85     return nil
86 }
87
88 func tty_raw () error {
89     raw := orig_termios;
90
91     raw.c_iflag &= ^(BRKINT | ICRNL | INPCK | ISTRIP | IXON);
92     raw.c_oflag &= ^(OPOST);
93     raw.c_cflag |= (CS8);
94     raw.c_lflag &= ^(ECHO | ICANON | IEXTEN | ISIG);
95
96     raw.c_cc[VMIN] = 1;
97     raw.c_cc[VTIME] = 0;
98
99     if err := setTermios (&raw); err != nil { return err }
100
101     return nil
102 }
103
104 func SetRaw () {
105     var (
106         err error
107     )
108
109     defer func () {
110         if err != nil { fmt.Printf ("SetRaw Error: %v\n",err) }
111     } ();
112
113     if err = getTermios (&orig_termios); err != nil { return }
114
115 //    defer func () {
116 //        err = setTermios (&orig_termios)
117 //    } ();
118
119     if err = tty_raw (); err != nil { return }
120     //if err = screenio (); err != nil { return }
121 }