add ga_inl, ga_inr
[ghc-base.git] / cbits / consUtils.c
index bb9e154..b20eb7a 100644 (file)
@@ -3,18 +3,40 @@
  *
  * Win32 Console API support
  */
-#include "ghcconfig.h"
-#if defined(mingw32_HOST_OS) || defined(cygwin32_HOST_OS) || defined(__MINGW32__) || defined(_MSC_VER)
+#if defined(_MSC_VER) || defined(__MINGW32__) || defined(_WIN32) || defined(__CYGWIN__)
 /* to the end */
 
 #include "consUtils.h"
 #include <windows.h>
 #include <io.h>
 
-#if defined(cygwin32_HOST_OS)
+#if defined(__CYGWIN__)
 #define _get_osfhandle get_osfhandle
 #endif
 
+int is_console__(int fd) {
+    DWORD st;
+    HANDLE h;
+    if (!_isatty(fd)) {
+        /* TTY must be a character device */
+        return 0;
+    }
+    h = (HANDLE)_get_osfhandle(fd);
+    if (h == INVALID_HANDLE_VALUE) {
+        /* Broken handle can't be terminal */
+        return 0;
+    }
+    if (!GetConsoleMode(h, &st)) {
+        /* GetConsoleMode appears to fail when it's not a TTY.  In
+           particular, it's what most of our terminal functions
+           assume works, so if it doesn't work for all intents
+           and purposes we're not dealing with a terminal. */
+        return 0;
+    }
+    return 1;
+}
+
+
 int
 set_console_buffering__(int fd, int cooked)
 {
@@ -67,8 +89,17 @@ get_console_echo__(int fd)
 int
 flush_input_console__(int fd)
 {
-    HANDLE h;
-    if ( (h = (HANDLE)_get_osfhandle(fd)) != INVALID_HANDLE_VALUE ) {
+    HANDLE h = (HANDLE)_get_osfhandle(fd);
+    
+    if ( h != INVALID_HANDLE_VALUE ) {
+       /* If the 'fd' isn't connected to a console; treat the flush
+        * operation as a NOP.
+        */
+       DWORD unused;
+       if ( !GetConsoleMode(h,&unused) &&
+            GetLastError() == ERROR_INVALID_HANDLE ) {
+           return 0;
+       }
        if ( FlushConsoleInputBuffer(h) ) {
            return 0;
        }
@@ -77,4 +108,4 @@ flush_input_console__(int fd)
     return -1;
 }
 
-#endif /* defined(mingw32_HOST_OS) || ... */
+#endif /* defined(__MINGW32__) || ... */