ncurses 5.9 - patch 20111126
[ncurses.git] / ncurses / tinfo / lib_raw.c
1 /****************************************************************************
2  * Copyright (c) 1998-2010,2011 Free Software Foundation, Inc.              *
3  *                                                                          *
4  * Permission is hereby granted, free of charge, to any person obtaining a  *
5  * copy of this software and associated documentation files (the            *
6  * "Software"), to deal in the Software without restriction, including      *
7  * without limitation the rights to use, copy, modify, merge, publish,      *
8  * distribute, distribute with modifications, sublicense, and/or sell       *
9  * copies of the Software, and to permit persons to whom the Software is    *
10  * furnished to do so, subject to the following conditions:                 *
11  *                                                                          *
12  * The above copyright notice and this permission notice shall be included  *
13  * in all copies or substantial portions of the Software.                   *
14  *                                                                          *
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS  *
16  * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF               *
17  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.   *
18  * IN NO EVENT SHALL THE ABOVE COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,   *
19  * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR    *
20  * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR    *
21  * THE USE OR OTHER DEALINGS IN THE SOFTWARE.                               *
22  *                                                                          *
23  * Except as contained in this notice, the name(s) of the above copyright   *
24  * holders shall not be used in advertising or otherwise to promote the     *
25  * sale, use or other dealings in this Software without prior written       *
26  * authorization.                                                           *
27  ****************************************************************************/
28
29 /****************************************************************************
30  *  Author: Zeyd M. Ben-Halim <zmbenhal@netcom.com> 1992,1995               *
31  *     and: Eric S. Raymond <esr@snark.thyrsus.com>                         *
32  *     and: Thomas E. Dickey                        1998-on                 *
33  *     and: Juergen Pfeifer                         2009                    *
34  ****************************************************************************/
35
36 /*
37  *      raw.c
38  *
39  *      Routines:
40  *              raw()
41  *              cbreak()
42  *              noraw()
43  *              nocbreak()
44  *              qiflush()
45  *              noqiflush()
46  *              intrflush()
47  *
48  */
49
50 #include <curses.priv.h>
51
52 MODULE_ID("$Id: lib_raw.c,v 1.20 2011/04/16 16:42:10 tom Exp $")
53
54 #if HAVE_SYS_TERMIO_H
55 #include <sys/termio.h>         /* needed for ISC */
56 #endif
57
58 #ifdef __EMX__
59 #include <io.h>
60 #define _nc_setmode(mode) setmode(SP_PARM->_ifd, mode)
61 #else
62 #define _nc_setmode(mode)       /* nothing */
63 #endif
64
65 #define COOKED_INPUT    (IXON|BRKINT|PARMRK)
66
67 #ifdef TRACE
68 #define BEFORE(N)       if (USE_TRACEF(TRACE_BITS)) _nc_locked_tracef("%s before bits: %s", N, _nc_tracebits())
69 #define AFTER(N)        if (USE_TRACEF(TRACE_BITS)) _nc_locked_tracef("%s after bits: %s", N, _nc_tracebits())
70 #else
71 #define BEFORE(s)
72 #define AFTER(s)
73 #endif /* TRACE */
74
75 NCURSES_EXPORT(int)
76 NCURSES_SP_NAME(raw) (NCURSES_SP_DCL0)
77 {
78     int result = ERR;
79     TERMINAL *termp;
80
81     T((T_CALLED("raw(%p)"), (void *) SP_PARM));
82     if ((termp = TerminalOf(SP_PARM)) != 0) {
83         TTY buf;
84
85         BEFORE("raw");
86         _nc_setmode(O_BINARY);
87
88         buf = termp->Nttyb;
89 #ifdef TERMIOS
90         buf.c_lflag &= (unsigned) ~(ICANON | ISIG | IEXTEN);
91         buf.c_iflag &= (unsigned) ~(COOKED_INPUT);
92         buf.c_cc[VMIN] = 1;
93         buf.c_cc[VTIME] = 0;
94 #else
95         buf.sg_flags |= RAW;
96 #endif
97         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
98         if (result == OK) {
99             SP_PARM->_raw = TRUE;
100             SP_PARM->_cbreak = 1;
101             termp->Nttyb = buf;
102         }
103         AFTER("raw");
104     }
105     returnCode(result);
106 }
107
108 #if NCURSES_SP_FUNCS
109 NCURSES_EXPORT(int)
110 raw(void)
111 {
112     return NCURSES_SP_NAME(raw) (CURRENT_SCREEN);
113 }
114 #endif
115
116 NCURSES_EXPORT(int)
117 NCURSES_SP_NAME(cbreak) (NCURSES_SP_DCL0)
118 {
119     int result = ERR;
120     TERMINAL *termp;
121
122     T((T_CALLED("cbreak(%p)"), (void *) SP_PARM));
123     if ((termp = TerminalOf(SP_PARM)) != 0) {
124         TTY buf;
125
126         BEFORE("cbreak");
127         _nc_setmode(O_BINARY);
128
129         buf = termp->Nttyb;
130 #ifdef TERMIOS
131         buf.c_lflag &= (unsigned) ~ICANON;
132         buf.c_iflag &= (unsigned) ~ICRNL;
133         buf.c_lflag |= ISIG;
134         buf.c_cc[VMIN] = 1;
135         buf.c_cc[VTIME] = 0;
136 #else
137         buf.sg_flags |= CBREAK;
138 #endif
139         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
140         if (result == OK) {
141             SP_PARM->_cbreak = 1;
142             termp->Nttyb = buf;
143         }
144         AFTER("cbreak");
145     }
146     returnCode(result);
147 }
148
149 #if NCURSES_SP_FUNCS
150 NCURSES_EXPORT(int)
151 cbreak(void)
152 {
153     return NCURSES_SP_NAME(cbreak) (CURRENT_SCREEN);
154 }
155 #endif
156
157 /*
158  * Note:
159  * this implementation may be wrong.  See the comment under intrflush().
160  */
161 NCURSES_EXPORT(void)
162 NCURSES_SP_NAME(qiflush) (NCURSES_SP_DCL0)
163 {
164     int result = ERR;
165     TERMINAL *termp;
166
167     T((T_CALLED("qiflush(%p)"), (void *) SP_PARM));
168     if ((termp = TerminalOf(SP_PARM)) != 0) {
169         TTY buf;
170
171         BEFORE("qiflush");
172         buf = termp->Nttyb;
173 #ifdef TERMIOS
174         buf.c_lflag &= (unsigned) ~(NOFLSH);
175         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
176 #else
177         /* FIXME */
178 #endif
179         if (result == OK)
180             termp->Nttyb = buf;
181         AFTER("qiflush");
182     }
183     returnVoid;
184 }
185
186 #if NCURSES_SP_FUNCS
187 NCURSES_EXPORT(void)
188 qiflush(void)
189 {
190     NCURSES_SP_NAME(qiflush) (CURRENT_SCREEN);
191 }
192 #endif
193
194 NCURSES_EXPORT(int)
195 NCURSES_SP_NAME(noraw) (NCURSES_SP_DCL0)
196 {
197     int result = ERR;
198     TERMINAL *termp;
199
200     T((T_CALLED("noraw(%p)"), (void *) SP_PARM));
201     if ((termp = TerminalOf(SP_PARM)) != 0) {
202         TTY buf;
203
204         BEFORE("noraw");
205         _nc_setmode(O_TEXT);
206
207         buf = termp->Nttyb;
208 #ifdef TERMIOS
209         buf.c_lflag |= ISIG | ICANON |
210             (termp->Ottyb.c_lflag & IEXTEN);
211         buf.c_iflag |= COOKED_INPUT;
212 #else
213         buf.sg_flags &= ~(RAW | CBREAK);
214 #endif
215         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
216         if (result == OK) {
217             SP_PARM->_raw = FALSE;
218             SP_PARM->_cbreak = 0;
219             termp->Nttyb = buf;
220         }
221         AFTER("noraw");
222     }
223     returnCode(result);
224 }
225
226 #if NCURSES_SP_FUNCS
227 NCURSES_EXPORT(int)
228 noraw(void)
229 {
230     return NCURSES_SP_NAME(noraw) (CURRENT_SCREEN);
231 }
232 #endif
233
234 NCURSES_EXPORT(int)
235 NCURSES_SP_NAME(nocbreak) (NCURSES_SP_DCL0)
236 {
237     int result = ERR;
238     TERMINAL *termp;
239
240     T((T_CALLED("nocbreak(%p)"), (void *) SP_PARM));
241     if ((termp = TerminalOf(SP_PARM)) != 0) {
242         TTY buf;
243
244         BEFORE("nocbreak");
245         _nc_setmode(O_TEXT);
246
247         buf = termp->Nttyb;
248 #ifdef TERMIOS
249         buf.c_lflag |= ICANON;
250         buf.c_iflag |= ICRNL;
251 #else
252         buf.sg_flags &= ~CBREAK;
253 #endif
254         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
255         if (result == OK) {
256             SP_PARM->_cbreak = 0;
257             termp->Nttyb = buf;
258         }
259         AFTER("nocbreak");
260     }
261     returnCode(result);
262 }
263
264 #if NCURSES_SP_FUNCS
265 NCURSES_EXPORT(int)
266 nocbreak(void)
267 {
268     return NCURSES_SP_NAME(nocbreak) (CURRENT_SCREEN);
269 }
270 #endif
271
272 NCURSES_EXPORT(void)
273 NCURSES_SP_NAME(noqiflush) (NCURSES_SP_DCL0)
274 {
275     int result = ERR;
276     TERMINAL *termp;
277
278     T((T_CALLED("noqiflush(%p)"), (void *) SP_PARM));
279     if ((termp = TerminalOf(SP_PARM)) != 0) {
280         TTY buf;
281
282         BEFORE("noqiflush");
283         buf = termp->Nttyb;
284 #ifdef TERMIOS
285         buf.c_lflag |= NOFLSH;
286         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
287 #else
288         /* FIXME */
289 #endif
290         if (result == OK)
291             termp->Nttyb = buf;
292         AFTER("noqiflush");
293     }
294     returnVoid;
295 }
296
297 #if NCURSES_SP_FUNCS
298 NCURSES_EXPORT(void)
299 noqiflush(void)
300 {
301     NCURSES_SP_NAME(noqiflush) (CURRENT_SCREEN);
302 }
303 #endif
304
305 /*
306  * This call does the same thing as the qiflush()/noqiflush() pair.  We know
307  * for certain that SVr3 intrflush() tweaks the NOFLSH bit; on the other hand,
308  * the match (in the SVr4 man pages) between the language describing NOFLSH in
309  * termio(7) and the language describing qiflush()/noqiflush() in
310  * curs_inopts(3x) is too exact to be coincidence.
311  */
312 NCURSES_EXPORT(int)
313 NCURSES_SP_NAME(intrflush) (NCURSES_SP_DCLx WINDOW *win GCC_UNUSED, bool flag)
314 {
315     int result = ERR;
316     TERMINAL *termp;
317
318     T((T_CALLED("intrflush(%p,%d)"), (void *) SP_PARM, flag));
319     if (SP_PARM == 0)
320         returnCode(ERR);
321
322     if ((termp = TerminalOf(SP_PARM)) != 0) {
323         TTY buf;
324
325         BEFORE("intrflush");
326         buf = termp->Nttyb;
327 #ifdef TERMIOS
328         if (flag)
329             buf.c_lflag &= (unsigned) ~(NOFLSH);
330         else
331             buf.c_lflag |= (NOFLSH);
332         result = NCURSES_SP_NAME(_nc_set_tty_mode) (NCURSES_SP_ARGx &buf);
333 #else
334         /* FIXME */
335 #endif
336         if (result == OK) {
337             termp->Nttyb = buf;
338         }
339         AFTER("intrflush");
340     }
341     returnCode(result);
342 }
343
344 #if NCURSES_SP_FUNCS
345 NCURSES_EXPORT(int)
346 intrflush(WINDOW *win GCC_UNUSED, bool flag)
347 {
348     return NCURSES_SP_NAME(intrflush) (CURRENT_SCREEN, win, flag);
349 }
350 #endif