--- gforth/engine/io.c 2006/04/09 07:39:07 1.20 +++ gforth/engine/io.c 2007/07/01 19:05:00 1.28 @@ -1,6 +1,6 @@ /* direct key io driver - Copyright (C) 1995,1996,1997,1998,1999,2002,2003 Free Software Foundation, Inc. + Copyright (C) 1995,1996,1997,1998,1999,2002,2003,2006 Free Software Foundation, Inc. This file is part of Gforth. @@ -475,6 +475,7 @@ void prep_terminal () } /* added by MdG */ setlocale(LC_ALL, ""); + setlocale(LC_NUMERIC, "C"); /* Try to keep this function from being INTerrupted. We can do it on POSIX and systems with BSD-like signal handling. */ @@ -617,58 +618,20 @@ void deprep_terminal () } #endif /* NEW_TTY_DRIVER */ -/* If a character is available to be read, then read it - and stuff it into IBUFFER. Otherwise, just return. */ -long pending = -1L; -/* !! This is a bug: if key_avail(file1) is followed by getkey(file2), - the getkey(file2) can return the character from file1. - anton */ - -/* Moreover, key_avail and getkey bypass the buffering of the FILE *, - leading to unpleasant effects if KEY-FILE and KEY?-FILE are mixed - with READ-FILE and READ-LINE */ - long key_avail (FILE * stream) { int tty = fileno (stream); - int chars_avail = pending; - int result; + fd_set selin; + static struct timespec now = { 0 , 0 }; + int res; + setvbuf(stream, NULL, _IONBF, 0); if(!terminal_prepped && stream == stdin) prep_terminal(); -#if defined(FIONREAD) && !defined(_WIN32) - /* !! What is the point of this part? it does not affect - chars_avail, and "result" is never used - anton */ - if(isatty (tty)) { - result = ioctl (tty, FIONREAD, &chars_avail); - } -#else - { - fd_set selin; - static int now[2] = { 0 , 0 }; - int res; - - FD_ZERO(&selin); - FD_SET(tty, &selin); - chars_avail=select(1, &selin, NULL, NULL, now); - } -#endif - - if(chars_avail == -1L) { - unsigned char inchar; - - fcntl(tty, F_SETFL, O_NDELAY); - result = read(tty, &inchar, sizeof(char)); - if(result == sizeof(char)) { - chars_avail = 1; - pending = (long)inchar; - } else { - chars_avail = 0; - } - fcntl(tty, F_SETFL, 0); - } - - return chars_avail; + FD_ZERO(&selin); + FD_SET(tty, &selin); + return select(1, &selin, NULL, NULL, &now); } /* Get a key from the buffer of characters to be read. @@ -683,35 +646,25 @@ Cell getkey(FILE * stream) Cell result; unsigned char c; - if(!terminal_prepped) + setvbuf(stream, NULL, _IONBF, 0); + if(!terminal_prepped && stream == stdin) prep_terminal(); - while (pending < 0) - { - result = read (fileno (stream), &c, sizeof (char)); - - if (result == sizeof (char)) - return /* (c == 0x7F ? 0x08 :*/ c /*)*/; - - /* If zero characters are returned, then the file that we are - reading from is empty! Return EOF in that case. */ - if (result == 0) - return (EOF); - - /* If the error that we received was SIGINT, then try again, - this is simply an interrupted system call to read (). - Otherwise, some error ocurred, also signifying EOF. */ - if (errno != EINTR) - return (EOF); - } + result = fread(&c, sizeof(c), 1, stream); + return result==0 ? EOF : c; +} - /* otherwise there is a character pending; - return it and delete pending char */ - result = (Cell) pending; - pending = -1L; +#ifdef STANDALONE +void emit_char(char x) +{ + putc(x, stdout); +} - return result; +void type_chars(char *addr, unsigned int l) +{ + fwrite(addr, l, 1, stdout); } +#endif #ifdef TEST