428
|
1 /* TTY device functions.
|
|
2 Copyright (C) 1994, 1995 Board of Trustees, University of Illinois.
|
|
3 Copyright (C) 1994, 1995 Free Software Foundation, Inc.
|
|
4 Copyright (C) 1996 Ben Wing.
|
|
5
|
|
6 This file is part of XEmacs.
|
|
7
|
|
8 XEmacs is free software; you can redistribute it and/or modify it
|
|
9 under the terms of the GNU General Public License as published by the
|
|
10 Free Software Foundation; either version 2, or (at your option) any
|
|
11 later version.
|
|
12
|
|
13 XEmacs is distributed in the hope that it will be useful, but WITHOUT
|
|
14 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
|
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
|
|
16 for more details.
|
|
17
|
|
18 You should have received a copy of the GNU General Public License
|
|
19 along with XEmacs; see the file COPYING. If not, write to
|
|
20 the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
|
|
21 Boston, MA 02111-1307, USA. */
|
|
22
|
|
23 /* Synched up with: Not in FSF. */
|
|
24
|
|
25 /* Authors: Ben Wing and Chuck Thompson. */
|
|
26
|
|
27 #include <config.h>
|
|
28 #include "lisp.h"
|
|
29
|
872
|
30 #include "device-impl.h"
|
428
|
31 #include "events.h"
|
|
32 #include "faces.h"
|
|
33 #include "frame.h"
|
|
34 #include "lstream.h"
|
|
35 #include "redisplay.h"
|
|
36 #include "sysdep.h"
|
|
37
|
872
|
38 #include "console-tty-impl.h"
|
800
|
39 #include "console-stream.h"
|
|
40
|
558
|
41 #include "sysfile.h"
|
428
|
42 #include "syssignal.h" /* for SIGWINCH */
|
|
43
|
|
44 Lisp_Object Qinit_pre_tty_win, Qinit_post_tty_win;
|
|
45
|
|
46
|
3092
|
47 #ifdef NEW_GC
|
|
48 static const struct memory_description tty_device_data_description_1 [] = {
|
|
49 { XD_END }
|
|
50 };
|
|
51
|
|
52 DEFINE_LRECORD_IMPLEMENTATION ("tty-device", tty_device,
|
|
53 1, /*dumpable-flag*/
|
|
54 0, 0, 0, 0, 0,
|
|
55 tty_device_data_description_1,
|
|
56 Lisp_Tty_Device);
|
|
57 #endif /* NEW_GC */
|
|
58
|
428
|
59 static void
|
|
60 allocate_tty_device_struct (struct device *d)
|
|
61 {
|
3092
|
62 #ifdef NEW_GC
|
|
63 d->device_data = alloc_lrecord_type (struct tty_device, &lrecord_tty_device);
|
|
64 #else /* not NEW_GC */
|
428
|
65 d->device_data = xnew_and_zero (struct tty_device);
|
3092
|
66 #endif /* not NEW_GC */
|
428
|
67 }
|
|
68
|
|
69 static void
|
2286
|
70 tty_init_device (struct device *d, Lisp_Object UNUSED (props))
|
428
|
71 {
|
|
72 struct console *con = XCONSOLE (DEVICE_CONSOLE (d));
|
|
73 Lisp_Object terminal_type = CONSOLE_TTY_DATA (con)->terminal_type;
|
|
74
|
|
75 DEVICE_INFD (d) = CONSOLE_TTY_DATA (con)->infd;
|
|
76 DEVICE_OUTFD (d) = CONSOLE_TTY_DATA (con)->outfd;
|
|
77
|
|
78 allocate_tty_device_struct (d);
|
|
79 init_baud_rate (d);
|
|
80
|
|
81 switch (init_tty_for_redisplay (d, (char *) XSTRING_DATA (terminal_type)))
|
|
82 {
|
|
83 #if 0
|
|
84 case TTY_UNABLE_OPEN_DATABASE:
|
|
85 suppress_early_error_handler_backtrace = 1;
|
563
|
86 signal_error (Qio_error, "Can't access terminal information database", Qunbound);
|
428
|
87 break;
|
|
88 #endif
|
|
89 case TTY_TYPE_UNDEFINED:
|
|
90 suppress_early_error_handler_backtrace = 1;
|
563
|
91 signal_error (Qio_error, "Terminal type undefined (or can't access database?)",
|
|
92 terminal_type);
|
428
|
93 break;
|
|
94 case TTY_TYPE_INSUFFICIENT:
|
|
95 suppress_early_error_handler_backtrace = 1;
|
563
|
96 signal_error (Qio_error, "Terminal type not powerful enough to run Emacs",
|
|
97 terminal_type);
|
428
|
98 break;
|
|
99 case TTY_SIZE_UNSPECIFIED:
|
|
100 suppress_early_error_handler_backtrace = 1;
|
563
|
101 signal_error (Qio_error, "Can't determine window size of terminal", Qunbound);
|
428
|
102 break;
|
|
103 case TTY_INIT_SUCCESS:
|
|
104 break;
|
|
105 default:
|
2500
|
106 ABORT ();
|
428
|
107 }
|
|
108
|
|
109 init_one_device (d);
|
|
110
|
|
111 /* Run part of the elisp side of the TTY device initialization.
|
|
112 The post-init is run in the tty_after_init_frame() method. */
|
|
113 call0 (Qinit_pre_tty_win);
|
|
114 }
|
|
115
|
3092
|
116 #ifndef NEW_GC
|
428
|
117 static void
|
|
118 free_tty_device_struct (struct device *d)
|
|
119 {
|
1726
|
120 if (d->device_data)
|
|
121 xfree (d->device_data, void *);
|
428
|
122 }
|
|
123
|
|
124 static void
|
|
125 tty_delete_device (struct device *d)
|
|
126 {
|
|
127 free_tty_device_struct (d);
|
|
128 }
|
3092
|
129 #endif /* not NEW_GC */
|
428
|
130
|
|
131 #ifdef SIGWINCH
|
|
132
|
|
133 static SIGTYPE
|
2286
|
134 tty_device_size_change_signal (int UNUSED (signo))
|
428
|
135 {
|
|
136 int old_errno = errno;
|
|
137 asynch_device_change_pending++;
|
|
138 #ifdef HAVE_UNIXOID_EVENT_LOOP
|
|
139 signal_fake_event ();
|
|
140 #endif
|
|
141 EMACS_REESTABLISH_SIGNAL (SIGWINCH, tty_device_size_change_signal);
|
|
142 errno = old_errno;
|
|
143 SIGRETURN;
|
|
144 }
|
|
145
|
|
146 /* frame_change_signal does nothing but set a flag that it was called.
|
|
147 When redisplay is called, it will notice that the flag is set and
|
|
148 call handle_pending_device_size_change to do the actual work. */
|
|
149 static void
|
|
150 tty_asynch_device_change (void)
|
|
151 {
|
|
152 Lisp_Object devcons, concons;
|
|
153
|
|
154 DEVICE_LOOP_NO_BREAK (devcons, concons)
|
|
155 {
|
|
156 int width, height;
|
|
157 Lisp_Object tail;
|
|
158 struct device *d = XDEVICE (XCAR (devcons));
|
|
159 struct console *con = XCONSOLE (DEVICE_CONSOLE (d));
|
|
160
|
|
161 if (!DEVICE_TTY_P (d))
|
|
162 continue;
|
|
163
|
|
164 get_tty_device_size (d, &width, &height);
|
|
165 if (width > 0 && height > 0
|
|
166 && (CONSOLE_TTY_DATA (con)->width != width
|
|
167 || CONSOLE_TTY_DATA (con)->height != height))
|
|
168 {
|
|
169 CONSOLE_TTY_DATA (con)->width = width;
|
|
170 CONSOLE_TTY_DATA (con)->height = height;
|
|
171
|
|
172 for (tail = DEVICE_FRAME_LIST (d);
|
|
173 !NILP (tail);
|
|
174 tail = XCDR (tail))
|
|
175 {
|
|
176 struct frame *f = XFRAME (XCAR (tail));
|
|
177
|
|
178 /* We know the frame is tty because we made sure that the
|
|
179 device is tty. */
|
|
180 change_frame_size (f, height, width, 1);
|
|
181 }
|
|
182 }
|
|
183 }
|
|
184 }
|
|
185
|
|
186 #endif /* SIGWINCH */
|
|
187
|
|
188 static Lisp_Object
|
|
189 tty_device_system_metrics (struct device *d,
|
|
190 enum device_metrics m)
|
|
191 {
|
|
192 struct console *con = XCONSOLE (DEVICE_CONSOLE (d));
|
|
193 switch (m)
|
|
194 {
|
|
195 case DM_size_device:
|
|
196 return Fcons (make_int (CONSOLE_TTY_DATA (con)->width),
|
|
197 make_int (CONSOLE_TTY_DATA (con)->height));
|
|
198 default: /* No such device metric property for TTY devices */
|
|
199 return Qunbound;
|
|
200 }
|
|
201 }
|
|
202
|
|
203 /************************************************************************/
|
|
204 /* initialization */
|
|
205 /************************************************************************/
|
|
206
|
|
207 void
|
|
208 syms_of_device_tty (void)
|
|
209 {
|
3092
|
210 #ifdef NEW_GC
|
|
211 INIT_LRECORD_IMPLEMENTATION (tty_device);
|
|
212 #endif /* NEW_GC */
|
|
213
|
563
|
214 DEFSYMBOL (Qinit_pre_tty_win);
|
|
215 DEFSYMBOL (Qinit_post_tty_win);
|
428
|
216 }
|
|
217
|
|
218 void
|
|
219 console_type_create_device_tty (void)
|
|
220 {
|
|
221 /* device methods */
|
|
222 CONSOLE_HAS_METHOD (tty, init_device);
|
3092
|
223 #ifndef NEW_GC
|
428
|
224 CONSOLE_HAS_METHOD (tty, delete_device);
|
3092
|
225 #endif /* not NEW_GC */
|
428
|
226 #ifdef SIGWINCH
|
|
227 CONSOLE_HAS_METHOD (tty, asynch_device_change);
|
|
228 #endif /* SIGWINCH */
|
|
229 CONSOLE_HAS_METHOD (tty, device_system_metrics);
|
|
230 }
|
|
231
|
|
232 void
|
|
233 init_device_tty (void)
|
|
234 {
|
|
235 #ifdef SIGWINCH
|
|
236 if (initialized && !noninteractive)
|
613
|
237 EMACS_SIGNAL (SIGWINCH, tty_device_size_change_signal);
|
428
|
238 #endif /* SIGWINCH */
|
|
239 }
|