("" < 3.4) always evaluates to true, which unconditionally
[dragonfly.git] / contrib / libreadline / input.c
blob64a55c6f90d4af4d5775eb7a397976a9a56a1a61
1 /* input.c -- character input functions for readline. */
3 /* Copyright (C) 1994 Free Software Foundation, Inc.
5 This file is part of the GNU Readline Library, a library for
6 reading lines of text with interactive input and history editing.
8 The GNU Readline Library is free software; you can redistribute it
9 and/or modify it under the terms of the GNU General Public License
10 as published by the Free Software Foundation; either version 2, or
11 (at your option) any later version.
13 The GNU Readline Library is distributed in the hope that it will be
14 useful, but WITHOUT ANY WARRANTY; without even the implied warranty
15 of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 The GNU General Public License is often shipped with GNU software, and
19 is generally kept in a file called COPYING or LICENSE. If you do not
20 have a copy of the license, write to the Free Software Foundation,
21 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
22 #define READLINE_LIBRARY
24 #if defined (HAVE_CONFIG_H)
25 # include <config.h>
26 #endif
28 #include <sys/types.h>
29 #include <fcntl.h>
30 #if defined (HAVE_SYS_FILE_H)
31 # include <sys/file.h>
32 #endif /* HAVE_SYS_FILE_H */
34 #if defined (HAVE_UNISTD_H)
35 # include <unistd.h>
36 #endif /* HAVE_UNISTD_H */
38 #if defined (HAVE_STDLIB_H)
39 # include <stdlib.h>
40 #else
41 # include "ansi_stdlib.h"
42 #endif /* HAVE_STDLIB_H */
44 #if defined (HAVE_SELECT)
45 # if !defined (HAVE_SYS_SELECT_H) || !defined (M_UNIX)
46 # include <sys/time.h>
47 # endif
48 #endif /* HAVE_SELECT */
49 #if defined (HAVE_SYS_SELECT_H)
50 # include <sys/select.h>
51 #endif
53 #if defined (FIONREAD_IN_SYS_IOCTL)
54 # include <sys/ioctl.h>
55 #endif
57 #include <stdio.h>
58 #include <errno.h>
60 #if !defined (errno)
61 extern int errno;
62 #endif /* !errno */
64 /* System-specific feature definitions and include files. */
65 #include "rldefs.h"
67 /* Some standard library routines. */
68 #include "readline.h"
70 #include "rlprivate.h"
71 #include "rlshell.h"
72 #include "xmalloc.h"
74 /* What kind of non-blocking I/O do we have? */
75 #if !defined (O_NDELAY) && defined (O_NONBLOCK)
76 # define O_NDELAY O_NONBLOCK /* Posix style */
77 #endif
79 /* Non-null means it is a pointer to a function to run while waiting for
80 character input. */
81 Function *rl_event_hook = (Function *)NULL;
83 Function *rl_getc_function = rl_getc;
85 /* **************************************************************** */
86 /* */
87 /* Character Input Buffering */
88 /* */
89 /* **************************************************************** */
91 static int pop_index, push_index;
92 static unsigned char ibuffer[512];
93 static int ibuffer_len = sizeof (ibuffer) - 1;
95 #define any_typein (push_index != pop_index)
97 int
98 _rl_any_typein ()
100 return any_typein;
103 /* Return the amount of space available in the buffer for stuffing
104 characters. */
105 static int
106 ibuffer_space ()
108 if (pop_index > push_index)
109 return (pop_index - push_index - 1);
110 else
111 return (ibuffer_len - (push_index - pop_index));
114 /* Get a key from the buffer of characters to be read.
115 Return the key in KEY.
116 Result is KEY if there was a key, or 0 if there wasn't. */
117 static int
118 rl_get_char (key)
119 int *key;
121 if (push_index == pop_index)
122 return (0);
124 *key = ibuffer[pop_index++];
126 if (pop_index >= ibuffer_len)
127 pop_index = 0;
129 return (1);
132 /* Stuff KEY into the *front* of the input buffer.
133 Returns non-zero if successful, zero if there is
134 no space left in the buffer. */
135 static int
136 rl_unget_char (key)
137 int key;
139 if (ibuffer_space ())
141 pop_index--;
142 if (pop_index < 0)
143 pop_index = ibuffer_len - 1;
144 ibuffer[pop_index] = key;
145 return (1);
147 return (0);
150 /* If a character is available to be read, then read it
151 and stuff it into IBUFFER. Otherwise, just return. */
152 static void
153 rl_gather_tyi ()
155 int tty;
156 register int tem, result;
157 int chars_avail;
158 char input;
159 #if defined(HAVE_SELECT)
160 fd_set readfds, exceptfds;
161 struct timeval timeout;
162 #endif
164 tty = fileno (rl_instream);
166 #if defined (HAVE_SELECT)
167 FD_ZERO (&readfds);
168 FD_ZERO (&exceptfds);
169 FD_SET (tty, &readfds);
170 FD_SET (tty, &exceptfds);
171 timeout.tv_sec = 0;
172 timeout.tv_usec = 100000; /* 0.1 seconds */
173 if (select (tty + 1, &readfds, (fd_set *)NULL, &exceptfds, &timeout) <= 0)
174 return; /* Nothing to read. */
175 #endif
177 result = -1;
178 #if defined (FIONREAD)
179 result = ioctl (tty, FIONREAD, &chars_avail);
180 #endif
182 #if defined (O_NDELAY)
183 if (result == -1)
185 tem = fcntl (tty, F_GETFL, 0);
187 fcntl (tty, F_SETFL, (tem | O_NDELAY));
188 chars_avail = read (tty, &input, 1);
190 fcntl (tty, F_SETFL, tem);
191 if (chars_avail == -1 && errno == EAGAIN)
192 return;
194 #endif /* O_NDELAY */
196 /* If there's nothing available, don't waste time trying to read
197 something. */
198 if (chars_avail <= 0)
199 return;
201 tem = ibuffer_space ();
203 if (chars_avail > tem)
204 chars_avail = tem;
206 /* One cannot read all of the available input. I can only read a single
207 character at a time, or else programs which require input can be
208 thwarted. If the buffer is larger than one character, I lose.
209 Damn! */
210 if (tem < ibuffer_len)
211 chars_avail = 0;
213 if (result != -1)
215 while (chars_avail--)
216 rl_stuff_char ((*rl_getc_function) (rl_instream));
218 else
220 if (chars_avail)
221 rl_stuff_char (input);
225 /* Is there input available to be read on the readline input file
226 descriptor? Only works if the system has select(2) or FIONREAD. */
228 _rl_input_available ()
230 #if defined(HAVE_SELECT)
231 fd_set readfds, exceptfds;
232 struct timeval timeout;
233 #endif
234 #if defined(FIONREAD)
235 int chars_avail;
236 #endif
237 int tty;
239 tty = fileno (rl_instream);
241 #if defined (HAVE_SELECT)
242 FD_ZERO (&readfds);
243 FD_ZERO (&exceptfds);
244 FD_SET (tty, &readfds);
245 FD_SET (tty, &exceptfds);
246 timeout.tv_sec = 0;
247 timeout.tv_usec = 100000; /* 0.1 seconds */
248 return (select (tty + 1, &readfds, (fd_set *)NULL, &exceptfds, &timeout) > 0);
249 #endif
251 #if defined (FIONREAD)
252 if (ioctl (tty, FIONREAD, &chars_avail) == 0)
253 return (chars_avail);
254 #endif
256 return 0;
259 void
260 _rl_insert_typein (c)
261 int c;
263 int key, t, i;
264 char *string;
266 i = key = 0;
267 string = xmalloc (ibuffer_len + 1);
268 string[i++] = (char) c;
270 while ((t = rl_get_char (&key)) &&
271 _rl_keymap[key].type == ISFUNC &&
272 _rl_keymap[key].function == rl_insert)
273 string[i++] = key;
275 if (t)
276 rl_unget_char (key);
278 string[i] = '\0';
279 rl_insert_text (string);
280 free (string);
283 /* Add KEY to the buffer of characters to be read. Returns 1 if the
284 character was stuffed correctly; 0 otherwise. */
286 rl_stuff_char (key)
287 int key;
289 if (ibuffer_space () == 0)
290 return 0;
292 if (key == EOF)
294 key = NEWLINE;
295 rl_pending_input = EOF;
297 ibuffer[push_index++] = key;
298 if (push_index >= ibuffer_len)
299 push_index = 0;
301 return 1;
304 /* Make C be the next command to be executed. */
306 rl_execute_next (c)
307 int c;
309 rl_pending_input = c;
310 return 0;
313 /* **************************************************************** */
314 /* */
315 /* Character Input */
316 /* */
317 /* **************************************************************** */
319 /* Read a key, including pending input. */
321 rl_read_key ()
323 int c;
325 rl_key_sequence_length++;
327 if (rl_pending_input)
329 c = rl_pending_input;
330 rl_pending_input = 0;
332 else
334 /* If input is coming from a macro, then use that. */
335 if (c = _rl_next_macro_key ())
336 return (c);
338 /* If the user has an event function, then call it periodically. */
339 if (rl_event_hook)
341 while (rl_event_hook && rl_get_char (&c) == 0)
343 (*rl_event_hook) ();
344 rl_gather_tyi ();
347 else
349 if (rl_get_char (&c) == 0)
350 c = (*rl_getc_function) (rl_instream);
354 return (c);
358 rl_getc (stream)
359 FILE *stream;
361 int result;
362 unsigned char c;
364 while (1)
366 result = read (fileno (stream), &c, sizeof (unsigned char));
368 if (result == sizeof (unsigned char))
369 return (c);
371 /* If zero characters are returned, then the file that we are
372 reading from is empty! Return EOF in that case. */
373 if (result == 0)
374 return (EOF);
376 #if defined (__BEOS__)
377 if (errno == EINTR)
378 continue;
379 #endif
381 #if defined (EWOULDBLOCK)
382 # define X_EWOULDBLOCK EWOULDBLOCK
383 #else
384 # define X_EWOULDBLOCK -99
385 #endif
387 #if defined (EAGAIN)
388 # define X_EAGAIN EAGAIN
389 #else
390 # define X_EAGAIN -99
391 #endif
393 if (errno == X_EWOULDBLOCK || errno == X_EAGAIN)
395 if (unset_nodelay_mode (fileno (stream)) < 0)
396 return (EOF);
397 continue;
400 #undef X_EWOULDBLOCK
401 #undef X_EAGAIN
403 /* If the error that we received was SIGINT, then try again,
404 this is simply an interrupted system call to read ().
405 Otherwise, some error ocurred, also signifying EOF. */
406 if (errno != EINTR)
407 return (EOF);