(DBL_MIN_REPLACEMENT): New macro.
[bpt/emacs.git] / src / sysdep.c
index 177f083..e8e1db8 100644 (file)
@@ -15,7 +15,8 @@ GNU General Public License for more details.
 
 You should have received a copy of the GNU General Public License
 along with GNU Emacs; see the file COPYING.  If not, write to
-the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
+the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+Boston, MA 02111-1307, USA.  */
 
 
 #include <signal.h>
@@ -75,11 +76,26 @@ extern int h_errno;
 #include <sys/stat.h>
 #include <errno.h>
 
+/* Get _POSIX_VDISABLE, if it is available.  */
+#ifdef HAVE_UNISTD_H
+#include <unistd.h>
+#endif
+
+/* Get SI_SRPC_DOMAIN, if it is available.  */
+#ifdef HAVE_SYS_SYSTEMINFO_H
+#include <sys/systeminfo.h>
+#endif
+
 #ifdef MSDOS   /* Demacs 1.1.2 91/10/20 Manabu Higashida, MW Aug 1993 */
 #include <dos.h>
 #include "dosfns.h"
 #include "msdos.h"
 #include <sys/param.h>
+
+#if __DJGPP__ > 1
+extern int etext;
+extern unsigned start __asm__ ("start");
+#endif
 #endif
 
 extern int errno;
@@ -108,7 +124,7 @@ extern int errno;
 #endif /* VMS */
 
 #ifndef BSD4_1
-#ifdef BSD /* this is done this way to avoid defined (BSD) || defined (USG)
+#ifdef BSD_SYSTEM /* avoid writing defined (BSD_SYSTEM) || defined (USG)
              because the vms compiler doesn't grok `defined' */
 #include <fcntl.h>
 #endif
@@ -122,6 +138,7 @@ extern int errno;
 #ifndef MSDOS
 #include <sys/ioctl.h>
 #endif
+
 #include "systty.h"
 #include "syswait.h"
 
@@ -186,6 +203,10 @@ struct utimbuf {
 #endif
 #endif
 
+#ifndef VFORK_RETURN_TYPE
+#define VFORK_RETURN_TYPE int
+#endif
+
 /* LPASS8 is new in 4.3, and makes cbreak mode provide all 8 bits.  */
 #ifndef LPASS8
 #define LPASS8 0
@@ -205,7 +226,18 @@ static int baud_convert[] =
   };
 #endif
 
+#if defined (HAVE_LIBNCURSES) && ! defined (NCURSES_OSPEED_T)
 extern short ospeed;
+#else
+#if defined (HAVE_TERMIOS_H) && defined (LINUX)
+#include <termios.h>
+/* HJL's version of libc is said to need this on the Alpha.
+   On the other hand, DEC OSF1 on the Alpha needs ospeed to be a short.  */
+extern speed_t ospeed;
+#else
+extern short ospeed;
+#endif
+#endif
 
 /* The file descriptor for Emacs's input terminal.
    Under Unix, this is normally zero except when using X;
@@ -287,6 +319,9 @@ init_baud_rate ()
     ospeed = 0;
   else
     {
+#ifdef INIT_BAUD_RATE
+      INIT_BAUD_RATE ();
+#else
 #ifdef DOS_NT
     ospeed = 15;
 #else  /* not DOS_NT */
@@ -330,6 +365,7 @@ init_baud_rate ()
 #endif /* not HAVE_TERMIOS */
 #endif /* not VMS */
 #endif /* not DOS_NT */
+#endif /* not INIT_BAUD_RATE */
     }
    
   baud_rate = (ospeed < sizeof baud_convert / sizeof baud_convert[0]
@@ -352,7 +388,7 @@ set_exclusive_use (fd)
 
 wait_without_blocking ()
 {
-#ifdef BSD
+#ifdef BSD_SYSTEM
   wait3 (0, WNOHANG | WUNTRACED, 0);
 #else
   croak ("wait_without_blocking");
@@ -384,7 +420,7 @@ wait_for_termination (pid)
       status = SYS$FORCEX (&pid, 0, 0);
       break;
 #else /* not VMS */
-#if defined (BSD) || (defined (HPUX) && !defined (HPUX_5))
+#if defined (BSD_SYSTEM) || (defined (HPUX) && !defined (HPUX_5))
       /* Note that kill returns -1 even if the process is just a zombie now.
         But inevitably a SIGCHLD interrupt should be generated
         and child_sig will do wait3 and make the process go away. */
@@ -403,12 +439,12 @@ wait_for_termination (pid)
        sleep (1);
       else
        sigpause (SIGEMPTYMASK);
-#else /* not BSD, and not HPUX version >= 6 */
+#else /* not BSD_SYSTEM, and not HPUX version >= 6 */
 #if defined (UNIPLUS)
       if (0 > kill (pid, 0))
        break;
       wait (0);
-#else /* neither BSD nor UNIPLUS: random sysV */
+#else /* neither BSD_SYSTEM nor UNIPLUS: random sysV */
 #ifdef POSIX_SIGNALS    /* would this work for LINUX as well? */
       sigblock (sigmask (SIGCHLD));
       if (0 > kill (pid, 0))
@@ -441,9 +477,12 @@ wait_for_termination (pid)
 #endif /* not HAVE_SYSV_SIGPAUSE */
 #endif /* not POSIX_SIGNALS */
 #endif /* not UNIPLUS */
-#endif /* not BSD, and not HPUX version >= 6 */
+#endif /* not BSD_SYSTEM, and not HPUX version >= 6 */
 #endif /* not VMS */
 #else /* not subprocesses */
+#if __DJGPP__ > 1
+      break;
+#else /* not __DJGPP__ > 1 */
 #ifndef BSD4_1
       if (kill (pid, 0) < 0)
        break;
@@ -454,6 +493,7 @@ wait_for_termination (pid)
       if (status == pid || status == -1)
        break;
 #endif /* BSD4_1 */
+#endif /* not __DJGPP__ > 1*/
 #endif /* not subprocesses */
     }
 }
@@ -512,9 +552,13 @@ child_setup_tty (out)
 #ifdef IUCLC
   s.main.c_iflag &= ~IUCLC;    /* Disable downcasing on input.  */
 #endif
+#ifdef ISTRIP
+  s.main.c_iflag &= ~ISTRIP;   /* don't strip 8th bit on input */
+#endif
 #ifdef OLCUC
   s.main.c_oflag &= ~OLCUC;    /* Disable upcasing on output.  */
 #endif
+  s.main.c_oflag &= ~TAB3;     /* Disable tab expansion */
   s.main.c_cflag = (s.main.c_cflag & ~CSIZE) | CS8; /* Don't strip 8th bit */
 #if 0
   /* Said to be unnecessary:  */
@@ -670,7 +714,7 @@ sys_suspend ()
 sys_subshell ()
 {
 #ifndef VMS
-#ifdef MSDOS   /* Demacs 1.1.2 91/10/20 Manabu Higashida */
+#ifdef DOS_NT  /* Demacs 1.1.2 91/10/20 Manabu Higashida */
   int st;
   char oldwd[MAXPATHLEN+1]; /* Fixed length is safe on MSDOS.  */
 #endif
@@ -708,22 +752,29 @@ sys_subshell ()
   str[len] = 0;
  xyzzy:
 
-#ifdef WINDOWSNT
-  pid = -1;
-#else /* not WINDOWSNT */
+#ifdef DOS_NT
+  pid = 0;
+#if __DJGPP__ > 1
+  save_signal_handlers (saved_handlers);
+  synch_process_alive = 1;
+#endif /* __DJGPP__ > 1 */
+#else  
   pid = vfork ();
-
   if (pid == -1)
     error ("Can't spawn subshell");
+#endif
+
   if (pid == 0)
-#endif /* not WINDOWSNT */
     {
-      char *sh;
+      char *sh = 0;
 
-#ifdef MSDOS    /* MW, Aug 1993 */
+#ifdef DOS_NT    /* MW, Aug 1993 */
       getwd (oldwd);
+      if (sh == 0)
+       sh = (char *) egetenv ("SUSPEND");      /* KFS, 1994-12-14 */
 #endif
-      sh = (char *) egetenv ("SHELL");
+      if (sh == 0)
+       sh = (char *) egetenv ("SHELL");
       if (sh == 0)
        sh = "sh";
 
@@ -747,16 +798,17 @@ sys_subshell ()
 #ifdef MSDOS    /* Demacs 1.1.2 91/10/20 Manabu Higashida */
       st = system (sh);
       chdir (oldwd);
+#if 0  /* This is also reported if last command executed in subshell failed, KFS */
       if (st)
        report_file_error ("Can't execute subshell", Fcons (build_string (sh), Qnil));
+#endif
 #else /* not MSDOS */
 #ifdef  WINDOWSNT
       /* Waits for process completion */
       pid = _spawnlp (_P_WAIT, sh, sh, NULL);
+      chdir (oldwd);
       if (pid == -1)
        write (1, "Can't execute subshell", 22);
-
-      take_console ();
 #else   /* not WINDOWSNT */
       execlp (sh, sh, 0);
       write (1, "Can't execute subshell", 22);
@@ -765,10 +817,17 @@ sys_subshell ()
 #endif /* not MSDOS */
     }
 
+  /* Do this now if we did not do it before.  */
+#if !defined (MSDOS) || __DJGPP__ == 1
   save_signal_handlers (saved_handlers);
   synch_process_alive = 1;
+#endif
+
+#ifndef DOS_NT
   wait_for_termination (pid);
+#endif
   restore_signal_handlers (saved_handlers);
+  synch_process_alive = 0;
 #endif /* !VMS */
 }
 
@@ -1026,15 +1085,14 @@ emacs_get_tty (fd, settings)
 
 
 /* Set the parameters of the tty on FD according to the contents of
-   *SETTINGS.  If WAITP is non-zero, we wait for all queued output to
-   be written before making the change; otherwise, we forget any
-   queued input and make the change immediately.
+   *SETTINGS.  If FLUSHP is non-zero, we discard input.
    Return 0 if all went well, and -1 if anything failed.  */
+
 int
-emacs_set_tty (fd, settings, waitp)
+emacs_set_tty (fd, settings, flushp)
      int fd;
      struct emacs_tty *settings;
-     int waitp;
+     int flushp;
 {
   /* Set the primary parameters - baud rate, character size, etcetera.  */
 #ifdef HAVE_TCATTR
@@ -1048,7 +1106,7 @@ emacs_set_tty (fd, settings, waitp)
      AIX requires this to keep tty from hanging occasionally."  */
   /* This make sure that we don't loop indefinitely in here.  */
   for (i = 0 ; i < 10 ; i++)
-    if (tcsetattr (fd, waitp ? TCSAFLUSH : TCSADRAIN, &settings->main) < 0)
+    if (tcsetattr (fd, flushp ? TCSAFLUSH : TCSADRAIN, &settings->main) < 0)
       {
        if (errno == EINTR)
          continue;
@@ -1078,7 +1136,7 @@ emacs_set_tty (fd, settings, waitp)
 #else
 #ifdef HAVE_TERMIO
   /* The SYSV-style interface?  */
-  if (ioctl (fd, waitp ? TCSETAW : TCSETAF, &settings->main) < 0)
+  if (ioctl (fd, flushp ? TCSETAF : TCSETAW, &settings->main) < 0)
     return -1;
 
 #else
@@ -1092,7 +1150,7 @@ emacs_set_tty (fd, settings, waitp)
 #else
 #ifndef DOS_NT
   /* I give up - I hope you have the BSD ioctls.  */
-  if (ioctl (fd, (waitp) ? TIOCSETP : TIOCSETN, &settings->main) < 0)
+  if (ioctl (fd, (flushp) ? TIOCSETP : TIOCSETN, &settings->main) < 0)
     return -1;
 #endif /* not DOS_NT */
 
@@ -1121,7 +1179,11 @@ emacs_set_tty (fd, settings, waitp)
 /* The initial tty mode bits */
 struct emacs_tty old_tty;
 
-int term_initted;              /* 1 if outer tty status has been recorded */
+/* 1 if we have been through init_sys_modes.  */
+int term_initted;
+
+/* 1 if outer tty status has been recorded.  */
+int old_tty_valid;
 
 #ifdef BSD4_1
 /* BSD 4.1 needs to keep track of the lmode bits in order to start
@@ -1149,7 +1211,7 @@ char _sobuf[BUFSIZ];
 static struct ltchars new_ltchars = {-1,-1,-1,-1,-1,-1};
 #endif
 #ifdef HAVE_TCHARS
-  static struct tchars new_tchars = {-1,-1,-1,-1,-1,-1};
+static struct tchars new_tchars = {-1,-1,-1,-1,-1,-1};
 #endif 
 
 init_sys_modes ()
@@ -1163,6 +1225,8 @@ init_sys_modes ()
 #endif
 #endif
 
+  Vtty_erase_char = Qnil;
+
   if (noninteractive)
     return;
 
@@ -1203,7 +1267,7 @@ init_sys_modes ()
     narrow_foreground_group ();
 #endif
 
-#ifdef HAVE_X_WINDOWS
+#ifdef HAVE_WINDOW_SYSTEM
   /* Emacs' window system on MSDOG uses the `internal terminal' and therefore
      needs the initialization code below.  */
   if (!read_socket_hook && EQ (Vwindow_system, Qnil))
@@ -1211,15 +1275,23 @@ init_sys_modes ()
     {
       EMACS_GET_TTY (input_fd, &old_tty);
 
+      old_tty_valid = 1;
+
       tty = old_tty;
 
 #if defined (HAVE_TERMIO) || defined (HAVE_TERMIOS)
+      XSETINT (Vtty_erase_char, old_tty.main.c_cc[VERASE]);
+
 #ifdef DGUX
       /* This allows meta to be sent on 8th bit.  */
       tty.main.c_iflag &= ~INPCK;      /* don't check input for parity */
 #endif
       tty.main.c_iflag |= (IGNBRK);    /* Ignore break condition */
       tty.main.c_iflag &= ~ICRNL;      /* Disable map of CR to NL on input */
+#ifdef INLCR  /* I'm just being cautious,
+                since I can't check how widespread INLCR is--rms.  */
+      tty.main.c_iflag &= ~INLCR;      /* Disable map of NL to CR on input */
+#endif
 #ifdef ISTRIP
       tty.main.c_iflag &= ~ISTRIP;     /* don't strip 8th bit on input */
 #endif
@@ -1259,6 +1331,7 @@ init_sys_modes ()
       tty.main.c_cc[VSWTCH] = CDISABLE;        /* Turn off shell layering use
                                           of C-z */
 #endif /* VSWTCH */
+
 #if defined (mips) || defined (HAVE_TCATTR)
 #ifdef VSUSP
       tty.main.c_cc[VSUSP] = CDISABLE; /* Turn off mips handling of C-z.  */
@@ -1281,15 +1354,29 @@ init_sys_modes ()
 #ifdef VDISCARD
       tty.main.c_cc[VDISCARD] = CDISABLE;
 #endif /* VDISCARD */
+
+      if (flow_control)
+       {
+#ifdef VSTART
+         tty.main.c_cc[VSTART] = '\021';
+#endif /* VSTART */
+#ifdef VSTOP
+         tty.main.c_cc[VSTOP] = '\023';
+#endif /* VSTOP */
+       }
+      else
+       {
 #ifdef VSTART
-      tty.main.c_cc[VSTART] = CDISABLE;
+         tty.main.c_cc[VSTART] = CDISABLE;
 #endif /* VSTART */
 #ifdef VSTOP
-      tty.main.c_cc[VSTOP] = CDISABLE;
+         tty.main.c_cc[VSTOP] = CDISABLE;
 #endif /* VSTOP */
+       }
 #endif /* mips or HAVE_TCATTR */
+
 #ifdef SET_LINE_DISCIPLINE
-      /* Need to explicitely request TERMIODISC line discipline or
+      /* Need to explicitly request TERMIODISC line discipline or
          Ultrix's termios does not work correctly.  */
       tty.main.c_line = SET_LINE_DISCIPLINE;
 #endif
@@ -1304,6 +1391,15 @@ init_sys_modes ()
       tty.main.c_cc[VSUSP] = 255;
       tty.main.c_cc[VDSUSP] = 255;
 #endif /* IBMR2AIX */
+      if (flow_control)
+       {
+#ifdef VSTART
+         tty.main.c_cc[VSTART] = '\021';
+#endif /* VSTART */
+#ifdef VSTOP
+         tty.main.c_cc[VSTOP] = '\023';
+#endif /* VSTOP */
+       }
       /* Also, PTY overloads NUL and BREAK.
         don't ignore break, but don't signal either, so it looks like NUL.
         This really serves a purpose only if running in an XTERM window
@@ -1323,6 +1419,7 @@ init_sys_modes ()
       tty.main.tt2_char |= TT2$M_PASTHRU | TT2$M_XON;
 #else /* not VMS (BSD, that is) */
 #ifndef DOS_NT
+      Vtty_erase_char = tty.main.sg_erase;
       tty.main.sg_flags &= ~(ECHO | CRMOD | XTABS);
       if (meta_key)
        tty.main.sg_flags |= ANYP;
@@ -1444,7 +1541,17 @@ init_sys_modes ()
 #else
   setbuf (stdout, _sobuf);
 #endif
-  if (! read_socket_hook && EQ (Vwindow_system, Qnil))
+#ifdef HAVE_WINDOW_SYSTEM
+  /* Emacs' window system on MSDOG uses the `internal terminal' and therefore
+     needs the initialization code below.  */
+  if (EQ (Vwindow_system, Qnil)
+#ifndef WINDOWSNT
+      /* When running in tty mode on NT/Win95, we have a read_socket
+        hook, but still need the rest of the initialization code below.  */
+      && (! read_socket_hook)
+#endif
+      )
+#endif
     set_terminal_modes ();
 
   if (term_initted && no_redraw_on_reenter)
@@ -1455,10 +1562,8 @@ init_sys_modes ()
   else
     {
       frame_garbaged = 1;
-#ifdef MULTI_FRAME
       if (FRAMEP (Vterminal_frame))
        FRAME_GARBAGED_P (XFRAME (Vterminal_frame)) = 1;
-#endif
     }
 
   term_initted = 1;
@@ -1583,22 +1688,19 @@ reset_sys_modes ()
     }
   if (!term_initted)
     return;
-#ifdef HAVE_X_WINDOWS
+#ifdef HAVE_WINDOW_SYSTEM
   /* Emacs' window system on MSDOG uses the `internal terminal' and therefore
      needs the clean-up code below.  */
-  if (read_socket_hook || !EQ (Vwindow_system, Qnil))
+  if (!EQ (Vwindow_system, Qnil)
+#ifndef WINDOWSNT
+      /* When running in tty mode on NT/Win95, we have a read_socket
+        hook, but still need the rest of the clean-up code below.  */
+      || read_socket_hook
+#endif
+      )
     return;
 #endif
   cursor_to (FRAME_HEIGHT (selected_frame) - 1, 0);
-#ifdef MSDOS
-  if (!EQ (Vwindow_system, Qnil))
-    {
-      /* Change to grey on white.  */
-      putchar ('\e');
-      putchar ('A');
-      putchar (7);
-    }
-#endif
   clear_end_of_line (FRAME_WIDTH (selected_frame));
   /* clear_end_of_line may move the cursor */
   cursor_to (FRAME_HEIGHT (selected_frame) - 1, 0);
@@ -1615,7 +1717,7 @@ reset_sys_modes ()
 
   reset_terminal_modes ();
   fflush (stdout);
-#ifdef BSD
+#ifdef BSD_SYSTEM
 #ifndef BSD4_1
   /* Avoid possible loss of output when changing terminal modes.  */
   fsync (fileno (stdout));
@@ -1641,8 +1743,9 @@ reset_sys_modes ()
     reset_sigio ();
 #endif /* BSD4_1 */
 
-  while (EMACS_SET_TTY (input_fd, &old_tty, 0) < 0 && errno == EINTR)
-    ;
+  if (old_tty_valid)
+    while (EMACS_SET_TTY (input_fd, &old_tty, 0) < 0 && errno == EINTR)
+      ;
 
 #ifdef MSDOS   /* Demacs 1.1.2 91/10/20 Manabu Higashida */
   dos_ttcooked ();
@@ -2008,7 +2111,7 @@ start_of_text ()
  *     at least on UniPlus, is temacs will have to be made unshared so
  *     that text and data are contiguous.  Then once loadup is complete,
  *     unexec will produce a shared executable where the data can be
- *     at the normal shared text boundry and the startofdata variable
+ *     at the normal shared text boundary and the startofdata variable
  *     will be patched by unexec to the correct value.
  *
  */
@@ -2112,7 +2215,7 @@ init_system_name ()
   uname (&uts);
   Vsystem_name = build_string (uts.nodename);
 #else /* HAVE_GETHOSTNAME */
-  int hostname_size = 256;
+  unsigned int hostname_size = 256;
   char *hostname = (char *) alloca (hostname_size);
 
   /* Try to get the host name; if the buffer is too short, try
@@ -2141,7 +2244,7 @@ init_system_name ()
     {
       struct hostent *hp;
       int count;
-      for (count = 0; count < 10; count++)
+      for (count = 0;; count++)
        {
 #ifdef TRY_AGAIN
          h_errno = 0;
@@ -2151,11 +2254,13 @@ init_system_name ()
          if (! (hp == 0 && h_errno == TRY_AGAIN))
 #endif
            break;
+         if (count >= 5)
+           break;
          Fsleep_for (make_number (1), Qnil);
        }
       if (hp)
        {
-         char *fqdn = hp->h_name;
+         char *fqdn = (char *) hp->h_name;
          char *p;
 
          if (!index (fqdn, '.'))
@@ -2184,6 +2289,43 @@ init_system_name ()
        }
     }
 #endif /* HAVE_SOCKETS */
+  /* We used to try using getdomainname as an alternative
+     to sysinfo, here, but NIIBE Yutaka <gniibe@etl.go.jp> says that
+     getdomainname gets the NIS/YP domain which often is not the same
+     as in Internet domain name.  */
+#if (HAVE_SYSINFO && defined (SI_SRPC_DOMAIN))
+  if (! index (hostname, '.'))
+    {
+      /* The hostname is not fully qualified.  Append the domain name.  */
+
+      int hostlen = strlen (hostname);
+      int domain_size = 256;
+
+      for (;;)
+       {
+         char *domain = (char *) alloca (domain_size + 1);
+         char *fqdn = (char *) alloca (hostlen + 1 + domain_size + 1);
+         int sys_domain_size = sysinfo (SI_SRPC_DOMAIN, domain, domain_size);
+         if (sys_domain_size <= 0)
+           break;
+         if (domain_size < sys_domain_size)
+           {
+             domain_size = sys_domain_size;
+             continue;
+           }
+         strcpy (fqdn, hostname);
+         if (domain[0] == '.')
+           strcpy (fqdn + hostlen, domain);
+         else if (domain[0] != 0)
+           {
+             fqdn[hostlen] = '.';
+             strcpy (fqdn + hostlen + 1, domain);
+           }
+         hostname = fqdn;
+         break;
+       }
+    }
+#endif /* HAVE_SYSINFO && defined (SI_SRPC_DOMAIN) */
   Vsystem_name = build_string (hostname);
 #endif /* HAVE_GETHOSTNAME */
 #endif /* VMS */
@@ -2196,6 +2338,7 @@ init_system_name ()
   }
 }
 \f
+#ifndef MSDOS
 #ifndef VMS
 #if !defined (HAVE_SELECT) || defined (BROKEN_SELECT_NON_X)
 
@@ -2316,9 +2459,6 @@ sys_select (nfds, rfds, wfds, efds, timeout)
 #ifdef FIONREAD
                      status = ioctl (fd, FIONREAD, &avail);
 #else /* no FIONREAD */
-#ifdef MSDOS
-                     abort (); /* I don't think we need it.  */
-#else /* not MSDOS */
                      /* Hoping it will return -1 if nothing available
                         or 0 if all 0 chars requested are read.  */
                      if (proc_buffered_char[fd] >= 0)
@@ -2329,7 +2469,6 @@ sys_select (nfds, rfds, wfds, efds, timeout)
                          if (avail > 0)
                            proc_buffered_char[fd] = buf;
                        }
-#endif /* not MSDOS */
 #endif /* no FIONREAD */
                    }
                  if (status >= 0 && avail > 0)
@@ -2350,10 +2489,6 @@ sys_select (nfds, rfds, wfds, efds, timeout)
       while (select_alarmed == 0 && *local_timeout != 0
             && process_tick == update_tick)
        {
-#ifdef MSDOS
-         sleep_or_kbd_hit (SELECT_PAUSE, FD_ISSET (0, &orfds) != 0);
-         select_alarm ();
-#else /* not MSDOS */
          /* If we are interested in terminal input,
             wait by reading the terminal.
             That makes instant wakeup for terminal input at least.  */
@@ -2365,7 +2500,6 @@ sys_select (nfds, rfds, wfds, efds, timeout)
            }
          else
            pause ();
-#endif /* not MSDOS */
        }
       (*local_timeout) -= SELECT_PAUSE;
       /* Reset the old alarm if there was one */
@@ -2390,8 +2524,8 @@ sys_select (nfds, rfds, wfds, efds, timeout)
 /* Read keyboard input into the standard buffer,
    waiting for at least one character.  */
 
-/* Make all keyboard buffers much bigger when using X windows.  */
-#ifdef HAVE_X_WINDOWS
+/* Make all keyboard buffers much bigger when using a window system.  */
+#ifdef HAVE_WINDOW_SYSTEM
 #define BUFFER_SIZE_FACTOR 16
 #else
 #define BUFFER_SIZE_FACTOR 1
@@ -2458,6 +2592,7 @@ read_input_waiting ()
 
 #endif /* not HAVE_SELECT */
 #endif /* not VMS */
+#endif /* not MSDOS */
 \f
 #ifdef BSD4_1
 /*
@@ -2568,11 +2703,6 @@ init_signals ()
 signal_handler_t
 sys_signal (int signal_number, signal_handler_t action)
 {
-#ifdef DGUX
-  /* This gets us restartable system calls for efficiency.
-     The "else" code will works as well. */
-  return (berk_signal (signal_number, action));
-#else
   sigemptyset (&new_action.sa_mask);
   new_action.sa_handler = action;
 #ifdef SA_RESTART
@@ -2585,7 +2715,6 @@ sys_signal (int signal_number, signal_handler_t action)
 #endif
   sigaction (signal_number, &new_action, &old_action);
   return (old_action.sa_handler);
-#endif /* DGUX */
 }
 
 #ifndef __GNUC__
@@ -2670,7 +2799,7 @@ sys_sigsetmask (sigset_t new_mask)
 #      define random rand
 #     else
 #      define random() (rand () >> 16)
-#     endif /* !BSD */
+#     endif /* !USG */
 #    endif /* RAND_MAX != 2147483647 */
 #   endif /* RAND_MAX != 32767 */
 #  endif /* !HAVE_LRAND48 */
@@ -2781,7 +2910,7 @@ sys_abort ()
 \f
 #ifdef VMS
 #ifdef LINK_CRTL_SHARE
-#ifdef SHAREABLE_LIB_BUG
+#ifdef SHARABLE_LIB_BUG
 /* Variables declared noshare and initialized in sharable libraries
    cannot be shared.  The VMS linker incorrectly forces you to use a private
    version which is uninitialized... If not for this "feature", we
@@ -2827,7 +2956,7 @@ char *sys_errlist[] =
     "I/O stream empty",
     "vax/vms specific error code nontranslatable error"
   };
-#endif /* SHAREABLE_LIB_BUG */
+#endif /* SHARABLE_LIB_BUG */
 #endif /* LINK_CRTL_SHARE */
 #endif /* VMS */
 
@@ -2869,10 +2998,19 @@ sys_open (path, oflag, mode)
 sys_close (fd)
      int fd;
 {
+  int did_retry = 0;
   register int rtnval;
 
   while ((rtnval = close (fd)) == -1
-        && (errno == EINTR));
+        && (errno == EINTR))
+    did_retry = 1;
+
+  /* If close is interrupted SunOS 4.1 may or may not have closed the
+     file descriptor.  If it did the second close will fail with
+     errno = EBADF.  That means we have succeeded.  */
+  if (rtnval == -1 && did_retry && errno == EBADF)
+    return 0;
+
   return rtnval;
 }
 
@@ -2930,6 +3068,7 @@ sys_write (fildes, buf, nbyte)
  *      Substitute fork for vfork on USG flavors.
  */
 
+VFORK_RETURN_TYPE
 vfork ()
 {
   return (fork ());
@@ -3016,7 +3155,7 @@ char *sys_siglist[NSIG + 1] =
 #ifdef sun
   "window size change",                            /* 20 SIGWINCH */
   "urgent socket condition",               /* 21 SIGURG */
-  "pollable event occured",                /* 22 SIGPOLL */
+  "pollable event occurred",               /* 22 SIGPOLL */
   "stop (cannot be caught or ignored)", /*  23 SIGSTOP */
   "user stop requested from tty",          /* 24 SIGTSTP */
   "stopped process has been continued",        /* 25 SIGCONT */
@@ -3568,17 +3707,17 @@ rmdir (dpath)
          dup2 (fd, 1);
          dup2 (fd, 2);
         }
-      wait_for_termination (cpid);
-  if (synch_process_death != 0 || synch_process_retcode != 0)
-      return -1;               /* /bin/rmdir failed */
+      execl ("/bin/rmdir", "rmdir", dpath, (char *) 0);
+      _exit (-1);              /* Can't exec /bin/rmdir */
+
     default:                   /* Parent process */
-      while (cpid != wait (&status));  /* Wait for kid to finish */
+      wait_for_termination (cpid);
     }
 
-  if (WIFSIGNALED (status) || WEXITSTATUS (status) != 0)
+  if (synch_process_death != 0 || synch_process_retcode != 0)
     {
       errno = EIO;             /* We don't know why, but */
-      return -1;               /* /bin/mkdir failed */
+      return -1;               /* /bin/rmdir failed */
     }
 
   return 0;
@@ -3736,7 +3875,7 @@ sys_access (filename, type)
   /* Check write protection. */
     
 #define CHECKPRIV(bit)    (prvmask.bit)
-#define WRITEABLE(field)  (! ((xab.xab$w_pro >> field) & XAB$M_NOWRITE))
+#define WRITABLE(field)  (! ((xab.xab$w_pro >> field) & XAB$M_NOWRITE))
 
   /* Find privilege bits */
   status = SYS$SETPRV (0, 0, 0, prvmask);
@@ -3757,7 +3896,7 @@ sys_access (filename, type)
     return -1;
   SYS$CLOSE (&fab, 0, 0);
   /* Check system access */
-  if (CHECKPRIV (PRV$V_SYSPRV) && WRITEABLE (XAB$V_SYS))
+  if (CHECKPRIV (PRV$V_SYSPRV) && WRITABLE (XAB$V_SYS))
     return 0;
   /* Check ACL entries, if any */
   acl_controlled = 0;
@@ -3783,16 +3922,16 @@ sys_access (filename, type)
        return -1;
     }
   /* No ACL entries specified, check normal protection */
-  if (WRITEABLE (XAB$V_WLD))   /* World writeable */
+  if (WRITABLE (XAB$V_WLD))    /* World writable */
     return 0;
-  if (WRITEABLE (XAB$V_GRP) &&
+  if (WRITABLE (XAB$V_GRP) &&
       (unsigned short) (xab.xab$l_uic >> 16) == grpid)
-    return 0;                  /* Group writeable */
-  if (WRITEABLE (XAB$V_OWN) &&
+    return 0;                  /* Group writable */
+  if (WRITABLE (XAB$V_OWN) &&
       (xab.xab$l_uic & 0xFFFF) == memid)
-    return 0;                  /* Owner writeable */
+    return 0;                  /* Owner writable */
 
-  return -1;   /* Not writeable */
+  return -1;   /* Not writable */
 }
 #endif /* not VMS4_4 */
 #endif /* access */
@@ -4475,7 +4614,7 @@ cnv_uaf_pw (up)
   retpw.pw_uid = up->uaf$w_mem;
   retpw.pw_gid = up->uaf$w_grp;
 
-  /* I suppose this is not the best sytle, to possibly overwrite one
+  /* I suppose this is not the best style, to possibly overwrite one
      byte beyond the end of the field, but what the heck... */
   ptr = &up->uaf$t_username[UAF$S_USERNAME];
   while (ptr[-1] == ' ')
@@ -4990,7 +5129,7 @@ bzero (b, length)
 #endif /* no bzero */
 #endif /* BSTRING */
 
-#if (defined (BSTRING) && !defined (bcopy)) || defined (NEED_BCOPY)
+#if (!defined (BSTRING) && !defined (bcopy)) || defined (NEED_BCOPY)
 #undef bcopy
 
 /* Saying `void' requires a declaration, above, where bcopy is used
@@ -5018,7 +5157,7 @@ bcopy (b1, b2, length)
 }
 #endif /* (defined (BSTRING) && !defined (bcopy)) || defined (NEED_BCOPY) */
 
-#ifdef BSTRING
+#ifndef BSTRING
 #ifndef bcmp
 int
 bcmp (b1, b2, length)  /* This could be a macro! */