ed.init.c revision 59243
1/* $Header: /src/pub/tcsh/ed.init.c,v 3.41 1999/02/06 15:01:16 christos Exp $ */
2/*
3 * ed.init.c: Editor initializations
4 */
5/*-
6 * Copyright (c) 1980, 1991 The Regents of the University of California.
7 * All rights reserved.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 *    notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 *    notice, this list of conditions and the following disclaimer in the
16 *    documentation and/or other materials provided with the distribution.
17 * 3. All advertising materials mentioning features or use of this software
18 *    must display the following acknowledgement:
19 *	This product includes software developed by the University of
20 *	California, Berkeley and its contributors.
21 * 4. Neither the name of the University nor the names of its contributors
22 *    may be used to endorse or promote products derived from this software
23 *    without specific prior written permission.
24 *
25 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
26 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
29 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTS_ION)
32 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35 * SUCH DAMAGE.
36 */
37#include "sh.h"
38
39RCSID("$Id: ed.init.c,v 3.41 1999/02/06 15:01:16 christos Exp $")
40
41#include "ed.h"
42#include "ed.term.h"
43#include "tc.h"
44#include "ed.defns.h"
45
46/* ed.init.c -- init routines for the line editor */
47/* #define DEBUG_TTY */
48
49int     Tty_raw_mode = 0;	/* Last tty change was to raw mode */
50int     MacroLvl = -1;		/* pointer to current macro nesting level; */
51				/* (-1 == none) */
52static int Tty_quote_mode = 0;	/* Last tty change was to quote mode */
53static unsigned char vdisable;	/* The value of _POSIX_VDISABLE from
54				 * pathconf(2) */
55
56int     Tty_eight_bit = -1;	/* does the tty handle eight bits */
57
58extern bool GotTermCaps;
59
60static ttydata_t extty, edtty, tstty;
61#define qutty tstty
62
63extern int insource;
64#define SHTTY (insource ? OLDSTD : SHIN)
65
66#define uc unsigned char
67static unsigned char ttychars[NN_IO][C_NCC] = {
68    {
69	(uc)CINTR,	(uc)CQUIT, 	 (uc)CERASE, 	   (uc)CKILL,
70	(uc)CEOF, 	(uc)CEOL, 	 (uc)CEOL2, 	   (uc)CSWTCH,
71	(uc)CDSWTCH,	(uc)CERASE2,	 (uc)CSTART, 	   (uc)CSTOP,
72	(uc)CWERASE, 	(uc)CSUSP, 	 (uc)CDSUSP, 	   (uc)CREPRINT,
73	(uc)CDISCARD, 	(uc)CLNEXT,	 (uc)CSTATUS,	   (uc)CPAGE,
74	(uc)CPGOFF,	(uc)CKILL2, 	 (uc)CBRK, 	   (uc)CMIN,
75	(uc)CTIME
76    },
77    {
78	CINTR, 		 CQUIT, 	  CERASE, 	   CKILL,
79	_POSIX_VDISABLE, _POSIX_VDISABLE, _POSIX_VDISABLE, _POSIX_VDISABLE,
80	_POSIX_VDISABLE, CERASE2,	  CSTART, 	   CSTOP,
81	_POSIX_VDISABLE, _POSIX_VDISABLE, _POSIX_VDISABLE, _POSIX_VDISABLE,
82	CDISCARD, 	 _POSIX_VDISABLE, _POSIX_VDISABLE, _POSIX_VDISABLE,
83	_POSIX_VDISABLE, _POSIX_VDISABLE, _POSIX_VDISABLE, 1,
84	0
85    },
86    {
87	0,		 0,		  0,		   0,
88	0,		 0,		  0,		   0,
89	0,		 0,		  0,		   0,
90	0,		 0,		  0,		   0,
91	0,		 0,		  0,		   0,
92	0,		 0,		  0,		   0,
93	0
94    }
95};
96
97#ifdef SIG_WINDOW
98void
99check_window_size(force)
100    int     force;
101{
102#ifdef BSDSIGS
103    sigmask_t omask;
104#endif /* BSDSIGS */
105    int     lins, cols;
106
107    /* don't want to confuse things here */
108#ifdef BSDSIGS
109    omask = sigblock(sigmask(SIG_WINDOW)) & ~sigmask(SIG_WINDOW);
110#else /* BSDSIGS */
111    (void) sighold(SIG_WINDOW);
112#endif /* BSDSIGS */
113    /*
114     * From: bret@shark.agps.lanl.gov (Bret Thaeler) Avoid sunview bug, where a
115     * partially hidden window gets a SIG_WINDOW every time the text is
116     * scrolled
117     */
118    if (GetSize(&lins, &cols) || force) {
119	if (GettingInput) {
120	    ClearLines();
121	    ClearDisp();
122	    MoveToLine(0);
123	    MoveToChar(0);
124	    ChangeSize(lins, cols);
125	    Refresh();
126	}
127	else
128	    ChangeSize(lins, cols);
129    }
130#ifdef BSDSIGS
131    (void) sigsetmask(omask);	/* can change it again */
132#else				/* BSDSIGS */
133    (void) sigrelse(SIG_WINDOW);
134#endif /* BSDSIGS */
135}
136
137sigret_t
138/*ARGSUSED*/
139window_change(snum)
140int snum;
141{
142#ifdef UNRELSIGS
143    /* If we were called as a signal handler, restore it. */
144    if (snum > 0)
145      sigset(snum, window_change);
146#endif /* UNRELSIGS */
147    check_window_size(0);
148#ifndef SIGVOID
149    return (snum);
150#endif
151}
152
153#endif /* SIG_WINDOW */
154
155void
156ed_set_tty_eight_bit()
157{
158    if (tty_getty(SHTTY, &extty) == -1) {
159#ifdef DEBUG_TTY
160	xprintf("ed_set_tty_eight_bit: tty_getty: %s\n", strerror(errno));
161#endif /* DEBUG_TTY */
162	return;
163    }
164    Tty_eight_bit = tty_geteightbit(&extty);
165}
166
167
168int
169ed_Setup(rst)
170    int rst;
171{
172    static int havesetup = 0;
173    struct varent *imode;
174
175    if (havesetup) 	/* if we have never been called */
176	return(0);
177
178#if defined(POSIX) && defined(_PC_VDISABLE) && !defined(BSD4_4) && \
179    !defined(WINNT)
180    {
181	long pcret;
182
183	if ((pcret = fpathconf(SHTTY, _PC_VDISABLE)) == -1L)
184	    vdisable = (unsigned char) _POSIX_VDISABLE;
185	else
186	    vdisable = (unsigned char) pcret;
187	if (vdisable != (unsigned char) _POSIX_VDISABLE && rst != 0)
188	    for (rst = 0; rst < C_NCC; rst++) {
189		if (ttychars[ED_IO][rst] == (unsigned char) _POSIX_VDISABLE)
190		    ttychars[ED_IO][rst] = vdisable;
191		if (ttychars[EX_IO][rst] == (unsigned char) _POSIX_VDISABLE)
192		    ttychars[EX_IO][rst] = vdisable;
193	    }
194    }
195#else /* ! POSIX || !_PC_VDISABLE || BSD4_4 || WINNT */
196    vdisable = (unsigned char) _POSIX_VDISABLE;
197#endif /* POSIX && _PC_VDISABLE && !BSD4_4 && !WINNT */
198
199    if ((imode = adrof(STRinputmode)) != NULL) {
200	if (!Strcmp(*(imode->vec), STRinsert))
201	    inputmode = MODE_INSERT;
202	else if (!Strcmp(*(imode->vec), STRoverwrite))
203	    inputmode = MODE_REPLACE;
204    }
205    else
206	inputmode = MODE_INSERT;
207    ed_InitMaps();
208    Hist_num = 0;
209    Expand = 0;
210
211#ifndef WINNT
212    if (tty_getty(SHTTY, &extty) == -1) {
213# ifdef DEBUG_TTY
214	xprintf("ed_Setup: tty_getty: %s\n", strerror(errno));
215# endif /* DEBUG_TTY */
216	return(-1);
217    }
218
219    tstty = edtty = extty;
220
221    T_Speed = tty_getspeed(&extty);
222    T_Tabs = tty_gettabs(&extty);
223    Tty_eight_bit = tty_geteightbit(&extty);
224
225# if defined(POSIX) || defined(TERMIO)
226    extty.d_t.c_iflag &= ~ttylist[EX_IO][M_INPUT].t_clrmask;
227    extty.d_t.c_iflag |=  ttylist[EX_IO][M_INPUT].t_setmask;
228
229    extty.d_t.c_oflag &= ~ttylist[EX_IO][M_OUTPUT].t_clrmask;
230    extty.d_t.c_oflag |=  ttylist[EX_IO][M_OUTPUT].t_setmask;
231
232    extty.d_t.c_cflag &= ~ttylist[EX_IO][M_CONTROL].t_clrmask;
233    extty.d_t.c_cflag |=  ttylist[EX_IO][M_CONTROL].t_setmask;
234
235    extty.d_t.c_lflag &= ~ttylist[EX_IO][M_LINED].t_clrmask;
236    extty.d_t.c_lflag |=  ttylist[EX_IO][M_LINED].t_setmask;
237
238#  if defined(IRIX3_3) && SYSVREL < 4
239    extty.d_t.c_line = NTTYDISC;
240#  endif /* IRIX3_3 && SYSVREL < 4 */
241
242# else	/* GSTTY */		/* V7, Berkeley style tty */
243
244    if (T_Tabs) {	/* order of &= and |= is important to XTABS */
245	extty.d_t.sg_flags &= ~(ttylist[EX_IO][M_CONTROL].t_clrmask|XTABS);
246	extty.d_t.sg_flags |=   ttylist[EX_IO][M_CONTROL].t_setmask;
247    }
248    else {
249	extty.d_t.sg_flags &= ~ttylist[EX_IO][M_CONTROL].t_clrmask;
250	extty.d_t.sg_flags |= (ttylist[EX_IO][M_CONTROL].t_setmask|XTABS);
251    }
252
253    extty.d_lb &= ~ttylist[EX_IO][M_LOCAL].t_clrmask;
254    extty.d_lb |=  ttylist[EX_IO][M_LOCAL].t_setmask;
255
256# endif /* GSTTY */
257    /*
258     * Reset the tty chars to reasonable defaults
259     * If they are disabled, then enable them.
260     */
261    if (rst) {
262	if (tty_cooked_mode(&tstty)) {
263	    tty_getchar(&tstty, ttychars[TS_IO]);
264	    /*
265	     * Don't affect CMIN and CTIME for the editor mode
266	     */
267	    for (rst = 0; rst < C_NCC - 2; rst++)
268		if (ttychars[TS_IO][rst] != vdisable &&
269		    ttychars[ED_IO][rst] != vdisable)
270		    ttychars[ED_IO][rst] = ttychars[TS_IO][rst];
271	    for (rst = 0; rst < C_NCC; rst++)
272		if (ttychars[TS_IO][rst] != vdisable &&
273		    ttychars[EX_IO][rst] != vdisable)
274		    ttychars[EX_IO][rst] = ttychars[TS_IO][rst];
275	}
276	tty_setchar(&extty, ttychars[EX_IO]);
277	if (tty_setty(SHTTY, &extty) == -1) {
278# ifdef DEBUG_TTY
279	    xprintf("ed_Setup: tty_setty: %s\n", strerror(errno));
280# endif /* DEBUG_TTY */
281	    return(-1);
282	}
283    }
284    else
285	tty_setchar(&extty, ttychars[EX_IO]);
286
287# ifdef SIG_WINDOW
288    (void) sigset(SIG_WINDOW, window_change);	/* for window systems */
289# endif
290#else /* WINNT */
291# ifdef DEBUG
292    if (rst)
293	xprintf("rst received in ed_Setup() %d\n", rst);
294# endif
295#endif /* WINNT */
296    havesetup = 1;
297    return(0);
298}
299
300void
301ed_Init()
302{
303    ResetInLine(1);		/* reset the input pointers */
304    GettingInput = 0;		/* just in case */
305    LastKill = KillBuf;		/* no kill buffer */
306
307#ifdef DEBUG_EDIT
308    CheckMaps();		/* do a little error checking on key maps */
309#endif
310
311    if (ed_Setup(0) == -1)
312	return;
313
314    /*
315     * if we have been called before but GotTermCaps isn't set, our TERM has
316     * changed, so get new termcaps and try again
317     */
318
319    if (!GotTermCaps)
320	GetTermCaps();		/* does the obvious, but gets term type each
321				 * time */
322
323#ifndef WINNT
324# if defined(TERMIO) || defined(POSIX)
325    edtty.d_t.c_iflag &= ~ttylist[ED_IO][M_INPUT].t_clrmask;
326    edtty.d_t.c_iflag |=  ttylist[ED_IO][M_INPUT].t_setmask;
327
328    edtty.d_t.c_oflag &= ~ttylist[ED_IO][M_OUTPUT].t_clrmask;
329    edtty.d_t.c_oflag |=  ttylist[ED_IO][M_OUTPUT].t_setmask;
330
331    edtty.d_t.c_cflag &= ~ttylist[ED_IO][M_CONTROL].t_clrmask;
332    edtty.d_t.c_cflag |=  ttylist[ED_IO][M_CONTROL].t_setmask;
333
334    edtty.d_t.c_lflag &= ~ttylist[ED_IO][M_LINED].t_clrmask;
335    edtty.d_t.c_lflag |=  ttylist[ED_IO][M_LINED].t_setmask;
336
337
338#  if defined(IRIX3_3) && SYSVREL < 4
339    edtty.d_t.c_line = NTTYDISC;
340#  endif /* IRIX3_3 && SYSVREL < 4 */
341
342# else /* GSTTY */
343
344    if (T_Tabs) {	/* order of &= and |= is important to XTABS */
345	edtty.d_t.sg_flags &= ~(ttylist[ED_IO][M_CONTROL].t_clrmask | XTABS);
346	edtty.d_t.sg_flags |=   ttylist[ED_IO][M_CONTROL].t_setmask;
347    }
348    else {
349	edtty.d_t.sg_flags &= ~ttylist[ED_IO][M_CONTROL].t_clrmask;
350	edtty.d_t.sg_flags |= (ttylist[ED_IO][M_CONTROL].t_setmask | XTABS);
351    }
352
353    edtty.d_lb &= ~ttylist[ED_IO][M_LOCAL].t_clrmask;
354    edtty.d_lb |=  ttylist[ED_IO][M_LOCAL].t_setmask;
355# endif /* POSIX || TERMIO */
356
357    tty_setchar(&edtty, ttychars[ED_IO]);
358#endif /* WINNT */
359}
360
361/*
362 * Check and re-init the line. set the terminal into 1 char at a time mode.
363 */
364int
365Rawmode()
366{
367    if (Tty_raw_mode)
368	return (0);
369
370#ifdef WINNT
371    do_nt_raw_mode();
372#else /* !WINNT */
373# ifdef _IBMR2
374    tty_setdisc(SHTTY, ED_IO);
375# endif /* _IBMR2 */
376
377    if (tty_getty(SHTTY, &tstty) == -1) {
378# ifdef DEBUG_TTY
379	xprintf("Rawmode: tty_getty: %s\n", strerror(errno));
380# endif /* DEBUG_TTY */
381	return(-1);
382    }
383
384    /*
385     * We always keep up with the eight bit setting and the speed of the
386     * tty. But only we only believe changes that are made to cooked mode!
387     */
388# if defined(POSIX) || defined(TERMIO)
389    Tty_eight_bit = tty_geteightbit(&tstty);
390    T_Speed = tty_getspeed(&tstty);
391
392#  ifdef POSIX
393    /*
394     * Fix from: Steven (Steve) B. Green <xrsbg@charney.gsfc.nasa.gov>
395     * Speed was not being set up correctly under POSIX.
396     */
397    if (tty_getspeed(&extty) != T_Speed || tty_getspeed(&edtty) != T_Speed) {
398	(void) cfsetispeed(&extty.d_t, T_Speed);
399	(void) cfsetospeed(&extty.d_t, T_Speed);
400	(void) cfsetispeed(&edtty.d_t, T_Speed);
401	(void) cfsetospeed(&edtty.d_t, T_Speed);
402    }
403#  endif /* POSIX */
404# else /* GSTTY */
405
406    T_Speed = tty_getspeed(&tstty);
407    Tty_eight_bit = tty_geteightbit(&tstty);
408
409    if (extty.d_t.sg_ispeed != tstty.d_t.sg_ispeed) {
410	extty.d_t.sg_ispeed = tstty.d_t.sg_ispeed;
411	edtty.d_t.sg_ispeed = tstty.d_t.sg_ispeed;
412    }
413
414    if (extty.d_t.sg_ospeed != tstty.d_t.sg_ospeed) {
415	extty.d_t.sg_ospeed = tstty.d_t.sg_ospeed;
416	edtty.d_t.sg_ospeed = tstty.d_t.sg_ospeed;
417    }
418# endif /* POSIX || TERMIO */
419
420    if (tty_cooked_mode(&tstty)) {
421	/*
422	 * re-test for some things here (like maybe the user typed
423	 * "stty -tabs"
424	 */
425	if (tty_gettabs(&tstty) == 0)
426	    T_Tabs = 0;
427	else
428	    T_Tabs = CanWeTab();
429
430# if defined(POSIX) || defined(TERMIO)
431	extty.d_t.c_cflag  = tstty.d_t.c_cflag;
432	extty.d_t.c_cflag &= ~ttylist[EX_IO][M_CONTROL].t_clrmask;
433	extty.d_t.c_cflag |=  ttylist[EX_IO][M_CONTROL].t_setmask;
434
435	edtty.d_t.c_cflag  = tstty.d_t.c_cflag;
436	edtty.d_t.c_cflag &= ~ttylist[ED_IO][M_CONTROL].t_clrmask;
437	edtty.d_t.c_cflag |=  ttylist[ED_IO][M_CONTROL].t_setmask;
438
439	extty.d_t.c_lflag = tstty.d_t.c_lflag;
440	extty.d_t.c_lflag &= ~ttylist[EX_IO][M_LINED].t_clrmask;
441	extty.d_t.c_lflag |=  ttylist[EX_IO][M_LINED].t_setmask;
442
443	edtty.d_t.c_lflag = tstty.d_t.c_lflag;
444	edtty.d_t.c_lflag &= ~ttylist[ED_IO][M_LINED].t_clrmask;
445	edtty.d_t.c_lflag |=  ttylist[ED_IO][M_LINED].t_setmask;
446
447	extty.d_t.c_iflag = tstty.d_t.c_iflag;
448	extty.d_t.c_iflag &= ~ttylist[EX_IO][M_INPUT].t_clrmask;
449	extty.d_t.c_iflag |=  ttylist[EX_IO][M_INPUT].t_setmask;
450
451	edtty.d_t.c_iflag = tstty.d_t.c_iflag;
452	edtty.d_t.c_iflag &= ~ttylist[ED_IO][M_INPUT].t_clrmask;
453	edtty.d_t.c_iflag |=  ttylist[ED_IO][M_INPUT].t_setmask;
454
455	extty.d_t.c_oflag = tstty.d_t.c_oflag;
456	extty.d_t.c_oflag &= ~ttylist[EX_IO][M_OUTPUT].t_clrmask;
457	extty.d_t.c_oflag |=  ttylist[EX_IO][M_OUTPUT].t_setmask;
458
459	edtty.d_t.c_oflag = tstty.d_t.c_oflag;
460	edtty.d_t.c_oflag &= ~ttylist[ED_IO][M_OUTPUT].t_clrmask;
461	edtty.d_t.c_oflag |=  ttylist[ED_IO][M_OUTPUT].t_setmask;
462
463# else /* GSTTY */
464
465	extty.d_t.sg_flags = tstty.d_t.sg_flags;
466
467	extty.d_t.sg_flags &= ~ttylist[EX_IO][M_CONTROL].t_clrmask;
468	extty.d_t.sg_flags |=  ttylist[EX_IO][M_CONTROL].t_setmask;
469
470	if (T_Tabs)		/* order of &= and |= is important to XTABS */
471	    extty.d_t.sg_flags &= ~XTABS;
472	else
473	    extty.d_t.sg_flags |= XTABS;
474
475	extty.d_lb = tstty.d_lb;
476	extty.d_lb &= ~ttylist[EX_IO][M_LOCAL].t_clrmask;
477	extty.d_lb |= ttylist[EX_IO][M_LOCAL].t_setmask;
478
479	edtty.d_t.sg_flags = extty.d_t.sg_flags;
480	if (T_Tabs) {	/* order of &= and |= is important to XTABS */
481	    edtty.d_t.sg_flags &=
482		    ~(ttylist[ED_IO][M_CONTROL].t_clrmask|XTABS);
483	    edtty.d_t.sg_flags |=   ttylist[ED_IO][M_CONTROL].t_setmask;
484	}
485	else {
486	    edtty.d_t.sg_flags &= ~ttylist[ED_IO][M_CONTROL].t_clrmask;
487	    edtty.d_t.sg_flags |=
488		    (ttylist[ED_IO][M_CONTROL].t_setmask|XTABS);
489	}
490
491	edtty.d_lb = tstty.d_lb;
492	edtty.d_lb &= ~ttylist[ED_IO][M_LOCAL].t_clrmask;
493	edtty.d_lb |= ttylist[ED_IO][M_LOCAL].t_setmask;
494
495# endif /* TERMIO || POSIX */
496
497	{
498	    extern int didsetty;
499	    int i;
500
501	    tty_getchar(&tstty, ttychars[TS_IO]);
502	    /*
503	     * Check if the user made any changes.
504	     * If he did, then propagate the changes to the
505	     * edit and execute data structures.
506	     */
507	    for (i = 0; i < C_NCC; i++)
508		if (ttychars[TS_IO][i] != ttychars[EX_IO][i])
509		    break;
510
511	    if (i != C_NCC || didsetty) {
512		didsetty = 0;
513		/*
514		 * Propagate changes only to the unprotected chars
515		 * that have been modified just now.
516		 */
517		for (i = 0; i < C_NCC; i++) {
518		    if (!((ttylist[ED_IO][M_CHAR].t_setmask & C_SH(i))) &&
519			(ttychars[TS_IO][i] != ttychars[EX_IO][i]))
520			ttychars[ED_IO][i] = ttychars[TS_IO][i];
521		    if (ttylist[ED_IO][M_CHAR].t_clrmask & C_SH(i))
522			ttychars[ED_IO][i] = vdisable;
523		}
524		tty_setchar(&edtty, ttychars[ED_IO]);
525
526		for (i = 0; i < C_NCC; i++) {
527		    if (!((ttylist[EX_IO][M_CHAR].t_setmask & C_SH(i))) &&
528			(ttychars[TS_IO][i] != ttychars[EX_IO][i]))
529			ttychars[EX_IO][i] = ttychars[TS_IO][i];
530		    if (ttylist[EX_IO][M_CHAR].t_clrmask & C_SH(i))
531			ttychars[EX_IO][i] = vdisable;
532		}
533		tty_setchar(&extty, ttychars[EX_IO]);
534	    }
535
536	}
537    }
538    if (tty_setty(SHTTY, &edtty) == -1) {
539# ifdef DEBUG_TTY
540	xprintf("Rawmode: tty_setty: %s\n", strerror(errno));
541# endif /* DEBUG_TTY */
542	return(-1);
543    }
544#endif /* WINNT */
545    Tty_raw_mode = 1;
546    flush();			/* flush any buffered output */
547    return (0);
548}
549
550int
551Cookedmode()
552{				/* set tty in normal setup */
553#ifdef WINNT
554    do_nt_cooked_mode();
555#else
556    signalfun_t orig_intr;
557
558# ifdef _IBMR2
559    tty_setdisc(SHTTY, EX_IO);
560# endif /* _IBMR2 */
561
562    if (!Tty_raw_mode)
563	return (0);
564
565    /* hold this for reseting tty */
566# ifdef BSDSIGS
567    orig_intr = (signalfun_t) signal(SIGINT, SIG_IGN);
568# else
569#  ifdef SIG_HOLD
570    /*
571     * sigset doesn't return the previous handler if the signal is held,
572     * it will return SIG_HOLD instead. So instead of restoring the
573     * the signal we would end up installing a blocked SIGINT with a
574     * SIG_IGN signal handler. This is what happened when Cookedmode
575     * was called from sched_run, disabling interrupt for the rest
576     * of your session.
577     *
578     * This is what we do:
579     * - if the signal is blocked, keep it that way
580     * - else set it to SIG_IGN
581     *
582     * Casper Dik (casper@fwi.uva.nl)
583     */
584    orig_intr = (signalfun_t) sigset(SIGINT, SIG_HOLD);
585    if (orig_intr != SIG_HOLD)
586	(void) sigset(SIGINT, SIG_IGN); /* returns SIG_HOLD */
587#  else /* !SIG_HOLD */
588    /*
589     * No SIG_HOLD; probably no reliable signals as well.
590     */
591    orig_intr = (signalfun_t) sigset(SIGINT, SIG_IGN);
592#  endif /* SIG_HOLD */
593# endif /* BSDSIGS */
594    if (tty_setty(SHTTY, &extty) == -1) {
595# ifdef DEBUG_TTY
596	xprintf("Cookedmode: tty_setty: %s\n", strerror(errno));
597# endif /* DEBUG_TTY */
598	return -1;
599    }
600# ifdef BSDSIGS
601    (void) signal(SIGINT, orig_intr);	/* take these again */
602# else
603    (void) sigset(SIGINT, orig_intr);	/* take these again */
604# endif /* BSDSIGS */
605#endif /* WINNT */
606
607    Tty_raw_mode = 0;
608    return (0);
609}
610
611void
612ResetInLine(macro)
613    int macro;
614{
615    Cursor = InputBuf;		/* reset cursor */
616    LastChar = InputBuf;
617    InputLim = &InputBuf[INBUFSIZE - 2];
618    Mark = InputBuf;
619    MetaNext = 0;
620    CurrentKeyMap = CcKeyMap;
621    AltKeyMap = 0;
622    Hist_num = 0;
623    DoingArg = 0;
624    Argument = 1;
625#ifdef notdef
626    LastKill = KillBuf;		/* no kill buffer */
627#endif
628    LastCmd = F_UNASSIGNED;	/* previous command executed */
629    if (macro)
630	MacroLvl = -1;		/* no currently active macros */
631}
632
633static Char *Input_Line = NULL;
634int
635Load_input_line()
636{
637#ifdef SUNOS4
638    long chrs = 0;
639#else /* !SUNOS4 */
640    /*
641     * *Everyone* else has an int, but SunOS wants long!
642     * This breaks where int != long (alpha)
643     */
644    int chrs = 0;
645#endif /* SUNOS4 */
646
647    if (Input_Line)
648	xfree((ptr_t) Input_Line);
649    Input_Line = NULL;
650
651    if (Tty_raw_mode)
652	return 0;
653
654#if defined(FIONREAD) && !defined(OREO)
655    (void) ioctl(SHIN, FIONREAD, (ioctl_t) &chrs);
656    if (chrs > 0) {
657	char    buf[BUFSIZE];
658
659	chrs = read(SHIN, buf, (size_t) min(chrs, BUFSIZE - 1));
660	if (chrs > 0) {
661	    buf[chrs] = '\0';
662	    Input_Line = Strsave(str2short(buf));
663	    PushMacro(Input_Line);
664	}
665#ifdef convex
666        /* need to print errno message in case file is migrated */
667        if (chrs < 0)
668            stderror(ERR_SYSTEM, progname, strerror(errno));
669#endif
670    }
671#endif  /* FIONREAD && !OREO */
672    return chrs > 0;
673}
674
675/*
676 * Bugfix (in Swedish) by:
677 * Johan Widen
678 * SICS, PO Box 1263, S-163 13 SPANGA, SWEDEN
679 * {mcvax,munnari,cernvax,diku,inria,prlb2,penet,ukc,unido}!enea!sics.se!jw
680 * Internet: jw@sics.se
681 *
682 * (via Hans J Albertsson (thanks))
683 */
684void
685QuoteModeOn()
686{
687    if (MacroLvl >= 0)
688	return;
689
690#ifndef WINNT
691    qutty = edtty;
692
693#if defined(TERMIO) || defined(POSIX)
694    qutty.d_t.c_iflag &= ~ttylist[QU_IO][M_INPUT].t_clrmask;
695    qutty.d_t.c_iflag |=  ttylist[QU_IO][M_INPUT].t_setmask;
696
697    qutty.d_t.c_oflag &= ~ttylist[QU_IO][M_OUTPUT].t_clrmask;
698    qutty.d_t.c_oflag |=  ttylist[QU_IO][M_OUTPUT].t_setmask;
699
700    qutty.d_t.c_cflag &= ~ttylist[QU_IO][M_CONTROL].t_clrmask;
701    qutty.d_t.c_cflag |=  ttylist[QU_IO][M_CONTROL].t_setmask;
702
703    qutty.d_t.c_lflag &= ~ttylist[QU_IO][M_LINED].t_clrmask;
704    qutty.d_t.c_lflag |=  ttylist[QU_IO][M_LINED].t_setmask;
705#else /* GSTTY */
706    qutty.d_t.sg_flags &= ~ttylist[QU_IO][M_CONTROL].t_clrmask;
707    qutty.d_t.sg_flags |= ttylist[QU_IO][M_CONTROL].t_setmask;
708    qutty.d_lb &= ~ttylist[QU_IO][M_LOCAL].t_clrmask;
709    qutty.d_lb |= ttylist[QU_IO][M_LOCAL].t_setmask;
710
711#endif /* TERMIO || POSIX */
712    if (tty_setty(SHTTY, &qutty) == -1) {
713#ifdef DEBUG_TTY
714	xprintf("QuoteModeOn: tty_setty: %s\n", strerror(errno));
715#endif /* DEBUG_TTY */
716	return;
717    }
718#endif /* !WINNT */
719    Tty_quote_mode = 1;
720    return;
721}
722
723void
724QuoteModeOff()
725{
726    if (!Tty_quote_mode)
727	return;
728    Tty_quote_mode = 0;
729    if (tty_setty(SHTTY, &edtty) == -1) {
730#ifdef DEBUG_TTY
731	xprintf("QuoteModeOff: tty_setty: %s\n", strerror(errno));
732#endif /* DEBUG_TTY */
733	return;
734    }
735    return;
736}
737