]> code.delx.au - gnu-emacs/blobdiff - src/process.c
(x_clip_to_row): Add area arg. Callers changed.
[gnu-emacs] / src / process.c
index 237f202e2f2bd05d2f8819823aea6f8196dd3122..ec07e95c34acc29eded1bbb1aa549a6cec8d8a9b 100644 (file)
@@ -310,6 +310,7 @@ static SELECT_TYPE non_keyboard_wait_mask;
 
 static SELECT_TYPE non_process_wait_mask;
 
+#ifdef NON_BLOCKING_CONNECT
 /* Mask of bits indicating the descriptors that we wait for connect to
    complete on.  Once they complete, they are removed from this mask
    and added to the input_wait_mask and non_keyboard_wait_mask.  */
@@ -319,6 +320,11 @@ static SELECT_TYPE connect_wait_mask;
 /* Number of bits set in connect_wait_mask.  */
 static int num_pending_connects;
 
+#define IF_NON_BLOCKING_CONNECT(s) s
+#else
+#define IF_NON_BLOCKING_CONNECT(s)
+#endif
+
 /* The largest descriptor currently in use for a process object.  */
 static int max_process_desc;
 
@@ -445,10 +451,11 @@ decode_status (l, symbol, code, coredump)
 
 /* Return a string describing a process status list.  */
 
-Lisp_Object
-status_message (status)
-     Lisp_Object status;
+static Lisp_Object
+status_message (p)
+     struct Lisp_Process *p;
 {
+  Lisp_Object status = p->status;
   Lisp_Object symbol;
   int code, coredump;
   Lisp_Object string, string2;
@@ -469,6 +476,8 @@ status_message (status)
     }
   else if (EQ (symbol, Qexit))
     {
+      if (NETCONN1_P (p))
+       return build_string (code == 0 ? "deleted\n" : "connection broken by remote peer\n");
       if (code == 0)
        return build_string ("finished\n");
       string = Fnumber_to_string (make_number (code));
@@ -764,6 +773,7 @@ nil, indicating the current buffer's process.  */)
     {
       XPROCESS (process)->status = Fcons (Qexit, Fcons (make_number (0), Qnil));
       XSETINT (XPROCESS (process)->tick, ++process_tick);
+      status_notify ();
     }
   else if (XINT (XPROCESS (process)->infd) >= 0)
     {
@@ -1457,12 +1467,12 @@ static Lisp_Object start_process_unwind ();
 DEFUN ("start-process", Fstart_process, Sstart_process, 3, MANY, 0,
        doc: /* Start a program in a subprocess.  Return the process object for it.
 NAME is name for process.  It is modified if necessary to make it unique.
-BUFFER is the buffer or (buffer-name) to associate with the process.
+BUFFER is the buffer (or buffer name) to associate with the process.
  Process output goes at end of that buffer, unless you specify
  an output stream or filter function to handle the output.
  BUFFER may be also nil, meaning that this process is not associated
  with any buffer.
-Third arg is program file name.  It is searched for in PATH.
+PROGRAM is the program file name.  It is searched for in PATH.
 Remaining arguments are strings to give program as arguments.
 
 usage: (start-process NAME BUFFER PROGRAM &rest PROGRAM-ARGS)  */)
@@ -2712,7 +2722,6 @@ usage: (make-network-process &rest ARGS)  */)
   int xerrno = 0;
   int s = -1, outch, inch;
   struct gcpro gcpro1;
-  int retry = 0;
   int count = SPECPDL_INDEX ();
   int count1;
   Lisp_Object QCaddress;  /* one of QClocal or QCremote */
@@ -3013,6 +3022,8 @@ usage: (make-network-process &rest ARGS)  */)
     {
       int optn, optbits;
 
+    retry_connect:
+
       s = socket (lres->ai_family, lres->ai_socktype, lres->ai_protocol);
       if (s < 0)
        {
@@ -3091,8 +3102,6 @@ usage: (make-network-process &rest ARGS)  */)
          break;
        }
 
-    retry_connect:
-
       immediate_quit = 1;
       QUIT;
 
@@ -3134,22 +3143,13 @@ usage: (make-network-process &rest ARGS)  */)
 
       immediate_quit = 0;
 
-      if (xerrno == EINTR)
-       goto retry_connect;
-      if (xerrno == EADDRINUSE && retry < 20)
-       {
-         /* A delay here is needed on some FreeBSD systems,
-            and it is harmless, since this retrying takes time anyway
-            and should be infrequent.  */
-         Fsleep_for (make_number (1), Qnil);
-         retry++;
-         goto retry_connect;
-       }
-
       /* Discard the unwind protect closing S.  */
       specpdl_ptr = specpdl + count1;
       emacs_close (s);
       s = -1;
+
+      if (xerrno == EINTR)
+       goto retry_connect;
     }
 
   if (s >= 0)
@@ -3615,6 +3615,8 @@ FLAGS is the current flags of the interface.  */)
 #endif
 #endif /* HAVE_SOCKETS */
 
+/* Turn off input and output for process PROC.  */
+
 void
 deactivate_process (proc)
      Lisp_Object proc;
@@ -3666,12 +3668,14 @@ deactivate_process (proc)
       chan_process[inchannel] = Qnil;
       FD_CLR (inchannel, &input_wait_mask);
       FD_CLR (inchannel, &non_keyboard_wait_mask);
+#ifdef NON_BLOCKING_CONNECT
       if (FD_ISSET (inchannel, &connect_wait_mask))
        {
          FD_CLR (inchannel, &connect_wait_mask);
          if (--num_pending_connects < 0)
            abort ();
        }
+#endif
       if (inchannel == max_process_desc)
        {
          int i;
@@ -3712,7 +3716,7 @@ close_process_descs ()
 }
 \f
 DEFUN ("accept-process-output", Faccept_process_output, Saccept_process_output,
-       0, 3, 0,
+       0, 4, 0,
        doc: /* Allow any pending output from subprocesses to be read by Emacs.
 It is read into the process' buffers or given to their filter functions.
 Non-nil arg PROCESS means do not return until some output has been received
@@ -3720,15 +3724,20 @@ from PROCESS.
 Non-nil second arg TIMEOUT and third arg TIMEOUT-MSECS are number of
 seconds and microseconds to wait; return after that much time whether
 or not there is input.
+If optional fourth arg JUST-THIS-ONE is non-nil, only accept output
+from PROCESS, suspending reading output from other processes.
+If JUST-THIS-ONE is an integer, don't run any timers either.
 Return non-nil iff we received any output before the timeout expired.  */)
-     (process, timeout, timeout_msecs)
-     register Lisp_Object process, timeout, timeout_msecs;
+     (process, timeout, timeout_msecs, just_this_one)
+     register Lisp_Object process, timeout, timeout_msecs, just_this_one;
 {
   int seconds;
   int useconds;
 
   if (! NILP (process))
     CHECK_PROCESS (process);
+  else
+    just_this_one = Qnil;
 
   if (! NILP (timeout_msecs))
     {
@@ -3766,11 +3775,12 @@ Return non-nil iff we received any output before the timeout expired.  */)
   else
     seconds = NILP (process) ? -1 : 0;
 
-  if (NILP (process))
-    XSETFASTINT (process, 0);
-
   return
-    (wait_reading_process_input (seconds, useconds, process, 0)
+    (wait_reading_process_output (seconds, useconds, 0, 0,
+                                 Qnil,
+                                 !NILP (process) ? XPROCESS (process) : NULL,
+                                 NILP (just_this_one) ? 0 :
+                                 !INTEGERP (just_this_one) ? 1 : -1)
      ? Qt : Qnil);
 }
 
@@ -3970,12 +3980,12 @@ server_accept_connection (server, channel)
    lisp code is being evalled.
    This is also used in record_asynch_buffer_change.
    For that purpose, this must be 0
-   when not inside wait_reading_process_input.  */
+   when not inside wait_reading_process_output.  */
 static int waiting_for_user_input_p;
 
 /* This is here so breakpoints can be put on it.  */
 static void
-wait_reading_process_input_1 ()
+wait_reading_process_output_1 ()
 {
 }
 
@@ -3997,60 +4007,59 @@ wait_reading_process_input_1 ()
      1 to return when input is available, or
      -1 meaning caller will actually read the input, so don't throw to
        the quit handler, or
-     a cons cell, meaning wait until its car is non-nil
-       (and gobble terminal input into the buffer if any arrives), or
-     a process object, meaning wait until something arrives from that
-       process.  The return value is true iff we read some input from
-       that process.
 
    DO_DISPLAY != 0 means redisplay should be done to show subprocess
-   output that arrives.
+     output that arrives.
 
-   If READ_KBD is a pointer to a struct Lisp_Process, then the
-     function returns true iff we received input from that process
-     before the timeout elapsed.
+   If WAIT_FOR_CELL is a cons cell, wait until its car is non-nil
+     (and gobble terminal input into the buffer if any arrives).
+
+   If WAIT_PROC is specified, wait until something arrives from that
+     process.  The return value is true iff we read some input from
+     that process.
+
+   If JUST_WAIT_PROC is non-nil, handle only output from WAIT_PROC
+     (suspending output from other processes).  A negative value
+     means don't run any timers either.
+
+   If WAIT_PROC is specified, then the function returns true iff we
+     received input from that process before the timeout elapsed.
    Otherwise, return true iff we received input from any process.  */
 
 int
-wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
-     int time_limit, microsecs;
-     Lisp_Object read_kbd;
-     int do_display;
+wait_reading_process_output (time_limit, microsecs, read_kbd, do_display,
+                            wait_for_cell, wait_proc, just_wait_proc)
+     int time_limit, microsecs, read_kbd, do_display;
+     Lisp_Object wait_for_cell;
+     struct Lisp_Process *wait_proc;
+     int just_wait_proc;
 {
   register int channel, nfds;
-  static SELECT_TYPE Available;
-  static SELECT_TYPE Connecting;
-  int check_connect, check_delay, no_avail;
+  SELECT_TYPE Available;
+#ifdef NON_BLOCKING_CONNECT
+  SELECT_TYPE Connecting;
+  int check_connect;
+#endif
+  int check_delay, no_avail;
   int xerrno;
   Lisp_Object proc;
   EMACS_TIME timeout, end_time;
   int wait_channel = -1;
-  struct Lisp_Process *wait_proc = 0;
   int got_some_input = 0;
   /* Either nil or a cons cell, the car of which is of interest and
      may be changed outside of this routine.  */
-  Lisp_Object wait_for_cell = Qnil;
+  int saved_waiting_for_user_input_p = waiting_for_user_input_p;
 
   FD_ZERO (&Available);
+#ifdef NON_BLOCKING_CONNECT
   FD_ZERO (&Connecting);
+#endif
 
-  /* If read_kbd is a process to watch, set wait_proc and wait_channel
-     accordingly.  */
-  if (PROCESSP (read_kbd))
-    {
-      wait_proc = XPROCESS (read_kbd);
-      wait_channel = XINT (wait_proc->infd);
-      XSETFASTINT (read_kbd, 0);
-    }
-
-  /* If waiting for non-nil in a cell, record where.  */
-  if (CONSP (read_kbd))
-    {
-      wait_for_cell = read_kbd;
-      XSETFASTINT (read_kbd, 0);
-    }
+  /* If wait_proc is a process to watch, set wait_channel accordingly.  */
+  if (wait_proc != NULL)
+    wait_channel = XINT (wait_proc->infd);
 
-  waiting_for_user_input_p = XINT (read_kbd);
+  waiting_for_user_input_p = read_kbd;
 
   /* Since we may need to wait several times,
      compute the absolute time to return at.  */
@@ -4078,7 +4087,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
       /* If calling from keyboard input, do not quit
         since we want to return C-g as an input character.
         Otherwise, do pending quit if requested.  */
-      if (XINT (read_kbd) >= 0)
+      if (read_kbd >= 0)
        QUIT;
 #ifdef SYNC_INPUT
       else if (interrupt_input_pending)
@@ -4115,7 +4124,8 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
         But not if wait_for_cell; in those cases,
         the wait is supposed to be short,
         and those callers cannot handle running arbitrary Lisp code here.  */
-      if (NILP (wait_for_cell))
+      if (NILP (wait_for_cell)
+         && just_wait_proc >= 0)
        {
          EMACS_TIME timer_delay;
 
@@ -4143,7 +4153,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
          while (!detect_input_pending ());
 
          /* If there is unread keyboard input, also return.  */
-         if (XINT (read_kbd) != 0
+         if (read_kbd != 0
              && requeued_events_pending_p ())
            break;
 
@@ -4161,7 +4171,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
          else if (time_limit != -1)
            {
              /* This is so a breakpoint can be put here.  */
-             wait_reading_process_input_1 ();
+             wait_reading_process_output_1 ();
            }
        }
 
@@ -4171,7 +4181,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
         It is important that we do this before checking for process
         activity.  If we get a SIGCHLD after the explicit checks for
         process activity, timeout is the only way we will know.  */
-      if (XINT (read_kbd) < 0)
+      if (read_kbd < 0)
        set_waiting_for_input (&timeout);
 
       /* If status of something has changed, and no input is
@@ -4180,22 +4190,31 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
         timeout to get our attention.  */
       if (update_tick != process_tick && do_display)
        {
-         SELECT_TYPE Atemp, Ctemp;
+         SELECT_TYPE Atemp;
+#ifdef NON_BLOCKING_CONNECT
+         SELECT_TYPE Ctemp;
+#endif
 
          Atemp = input_wait_mask;
-#ifdef MAC_OSX
-          /* On Mac OS X, the SELECT system call always says input is
+#if 0
+          /* On Mac OS X 10.0, the SELECT system call always says input is
              present (for reading) at stdin, even when none is.  This
              causes the call to SELECT below to return 1 and
              status_notify not to be called.  As a result output of
-             subprocesses are incorrectly discarded.  */
+             subprocesses are incorrectly discarded.
+         */
           FD_CLR (0, &Atemp);
 #endif
-         Ctemp = connect_wait_mask;
+         IF_NON_BLOCKING_CONNECT (Ctemp = connect_wait_mask);
+
          EMACS_SET_SECS_USECS (timeout, 0, 0);
          if ((select (max (max_process_desc, max_keyboard_desc) + 1,
                       &Atemp,
+#ifdef NON_BLOCKING_CONNECT
                       (num_pending_connects > 0 ? &Ctemp : (SELECT_TYPE *)0),
+#else
+                      (SELECT_TYPE *)0,
+#endif
                       (SELECT_TYPE *)0, &timeout)
               <= 0))
            {
@@ -4250,18 +4269,27 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
 
       /* Wait till there is something to do */
 
-      if (!NILP (wait_for_cell))
+      if (wait_proc && just_wait_proc)
+       {
+         if (XINT (wait_proc->infd) < 0)  /* Terminated */
+           break;
+         FD_SET (XINT (wait_proc->infd), &Available);
+         check_delay = 0;
+         IF_NON_BLOCKING_CONNECT (check_connect = 0);
+       }
+      else if (!NILP (wait_for_cell))
        {
          Available = non_process_wait_mask;
-         check_connect = check_delay = 0;
+         check_delay = 0;
+         IF_NON_BLOCKING_CONNECT (check_connect = 0);
        }
       else
        {
-         if (! XINT (read_kbd))
+         if (! read_kbd)
            Available = non_keyboard_wait_mask;
          else
            Available = input_wait_mask;
-         check_connect = (num_pending_connects > 0);
+         IF_NON_BLOCKING_CONNECT (check_connect = (num_pending_connects > 0));
          check_delay = wait_channel >= 0 ? 0 : process_output_delay_count;
        }
 
@@ -4274,20 +4302,22 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
        {
          clear_waiting_for_input ();
          redisplay_preserve_echo_area (11);
-         if (XINT (read_kbd) < 0)
+         if (read_kbd < 0)
            set_waiting_for_input (&timeout);
        }
 
       no_avail = 0;
-      if (XINT (read_kbd) && detect_input_pending ())
+      if (read_kbd && detect_input_pending ())
        {
          nfds = 0;
          no_avail = 1;
        }
       else
        {
+#ifdef NON_BLOCKING_CONNECT
          if (check_connect)
            Connecting = connect_wait_mask;
+#endif
 
 #ifdef ADAPTIVE_READ_BUFFERING
          if (process_output_skip && check_delay > 0)
@@ -4318,7 +4348,11 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
 
          nfds = select (max (max_process_desc, max_keyboard_desc) + 1,
                         &Available,
+#ifdef NON_BLOCKING_CONNECT
                         (check_connect ? &Connecting : (SELECT_TYPE *)0),
+#else
+                        (SELECT_TYPE *)0,
+#endif
                         (SELECT_TYPE *)0, &timeout);
        }
 
@@ -4374,7 +4408,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
       if (no_avail)
        {
          FD_ZERO (&Available);
-         check_connect = 0;
+         IF_NON_BLOCKING_CONNECT (check_connect = 0);
        }
 
 #if defined(sun) && !defined(USG5_4)
@@ -4396,10 +4430,10 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
       /* If we are using polling for input,
         and we see input available, make it get read now.
         Otherwise it might not actually get read for a second.
-        And on hpux, since we turn off polling in wait_reading_process_input,
+        And on hpux, since we turn off polling in wait_reading_process_output,
         it might never get read at all if we don't spend much time
-        outside of wait_reading_process_input.  */
-      if (XINT (read_kbd) && interrupt_input
+        outside of wait_reading_process_output.  */
+      if (read_kbd && interrupt_input
          && keyboard_bit_set (&Available)
          && input_polling_used ())
        kill (getpid (), SIGALRM);
@@ -4409,7 +4443,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
       /* If there is any, return immediately
         to give it higher priority than subprocesses */
 
-      if (XINT (read_kbd) != 0)
+      if (read_kbd != 0)
        {
          int old_timers_run = timers_run;
          struct buffer *old_buffer = current_buffer;
@@ -4434,7 +4468,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
        }
 
       /* If there is unread keyboard input, also return.  */
-      if (XINT (read_kbd) != 0
+      if (read_kbd != 0
          && requeued_events_pending_p ())
        break;
 
@@ -4445,7 +4479,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
         That would causes delays in pasting selections, for example.
 
         (We used to do this only if wait_for_cell.)  */
-      if (XINT (read_kbd) == 0 && detect_input_pending ())
+      if (read_kbd == 0 && detect_input_pending ())
        {
          swallow_events (do_display);
 #if 0  /* Exiting when read_kbd doesn't request that seems wrong, though.  */
@@ -4464,7 +4498,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
         In that case, there really is no input and no SIGIO,
         but select says there is input.  */
 
-      if (XINT (read_kbd) && interrupt_input
+      if (read_kbd && interrupt_input
          && keyboard_bit_set (&Available) && ! noninteractive)
        kill (getpid (), SIGIO);
 #endif
@@ -4474,7 +4508,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
 
       /* If checking input just got us a size-change event from X,
         obey it now if we should.  */
-      if (XINT (read_kbd) || ! NILP (wait_for_cell))
+      if (read_kbd || ! NILP (wait_for_cell))
        do_pending_window_change (0);
 
       /* Check for data from a process.  */
@@ -4580,7 +4614,8 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
                }
            }
 #ifdef NON_BLOCKING_CONNECT
-         if (check_connect && FD_ISSET (channel, &Connecting))
+         if (check_connect && FD_ISSET (channel, &Connecting)
+             && FD_ISSET (channel, &connect_wait_mask))
            {
              struct Lisp_Process *p;
 
@@ -4643,12 +4678,12 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
        }                       /* end for each file descriptor */
     }                          /* end while exit conditions not met */
 
-  waiting_for_user_input_p = 0;
+  waiting_for_user_input_p = saved_waiting_for_user_input_p;
 
   /* If calling from keyboard input, do not quit
      since we want to return C-g as an input character.
      Otherwise, do pending quit if requested.  */
-  if (XINT (read_kbd) >= 0)
+  if (read_kbd >= 0)
     {
       /* Prevent input_pending from remaining set if we quit.  */
       clear_input_pending ();
@@ -4690,7 +4725,7 @@ read_process_output_error_handler (error)
    starting with our buffered-ahead character if we have one.
    Yield number of decoded characters read.
 
-   This function reads at most 1024 characters.
+   This function reads at most 4096 characters.
    If you want to read all available subprocess output,
    you must call it repeatedly until it returns zero.
 
@@ -4710,7 +4745,7 @@ read_process_output (proc, channel)
   register int opoint;
   struct coding_system *coding = proc_decode_coding_system[channel];
   int carryover = XINT (p->decoding_carryover);
-  int readmax = 1024;
+  int readmax = 4096;
 
 #ifdef VMS
   VMS_PROC_STUFF *vs, *get_vms_process_pointer();
@@ -4743,16 +4778,6 @@ read_process_output (proc, channel)
     }
 #else /* not VMS */
 
-#ifdef DATAGRAM_SOCKETS
-  /* A datagram is one packet; allow at least 1500+ bytes of data
-     corresponding to the typical Ethernet frame size.  */
-  if (DATAGRAM_CHAN_P (channel))
-    {
-      /* carryover = 0; */  /* Does carryover make sense for datagrams? */
-      readmax += 1024;
-    }
-#endif
-
   chars = (char *) alloca (carryover + readmax);
   if (carryover)
     /* See the comment above.  */
@@ -4763,16 +4788,16 @@ read_process_output (proc, channel)
   if (DATAGRAM_CHAN_P (channel))
     {
       int len = datagram_address[channel].len;
-      nbytes = recvfrom (channel, chars + carryover, readmax - carryover,
+      nbytes = recvfrom (channel, chars + carryover, readmax,
                         0, datagram_address[channel].sa, &len);
     }
   else
 #endif
   if (proc_buffered_char[channel] < 0)
     {
-      nbytes = emacs_read (channel, chars + carryover, readmax - carryover);
+      nbytes = emacs_read (channel, chars + carryover, readmax);
 #ifdef ADAPTIVE_READ_BUFFERING
-      if (!NILP (p->adaptive_read_buffering))
+      if (nbytes > 0 && !NILP (p->adaptive_read_buffering))
        {
          int delay = XINT (p->read_output_delay);
          if (nbytes < 256)
@@ -4784,7 +4809,7 @@ read_process_output (proc, channel)
                  delay += READ_OUTPUT_DELAY_INCREMENT * 2;
                }
            }
-         else if (delay > 0 && (nbytes == readmax - carryover))
+         else if (delay > 0 && (nbytes == readmax))
            {
              delay -= READ_OUTPUT_DELAY_INCREMENT;
              if (delay == 0)
@@ -4803,7 +4828,7 @@ read_process_output (proc, channel)
     {
       chars[carryover] = proc_buffered_char[channel];
       proc_buffered_char[channel] = -1;
-      nbytes = emacs_read (channel, chars + carryover + 1,  readmax - 1 - carryover);
+      nbytes = emacs_read (channel, chars + carryover + 1,  readmax - 1);
       if (nbytes < 0)
        nbytes = 1;
       else
@@ -4894,6 +4919,8 @@ read_process_output (proc, channel)
        }
 
       carryover = nbytes - coding->consumed;
+      if (SCHARS (p->decoding_buf) < carryover)
+       p->decoding_buf = make_uninit_string (carryover);
       bcopy (chars + coding->consumed, SDATA (p->decoding_buf),
             carryover);
       XSETINT (p->decoding_carryover, carryover);
@@ -4998,6 +5025,8 @@ read_process_output (proc, channel)
            }
        }
       carryover = nbytes - coding->consumed;
+      if (SCHARS (p->decoding_buf) < carryover)
+       p->decoding_buf = make_uninit_string (carryover);
       bcopy (chars + coding->consumed, SDATA (p->decoding_buf),
             carryover);
       XSETINT (p->decoding_carryover, carryover);
@@ -5193,6 +5222,7 @@ send_process (proc, buf, len, object)
       object = p->encoding_buf;
       encode_coding (coding, (char *) buf, SDATA (object),
                     len, SBYTES (object));
+      coding_free_composition_data (coding);
       len = coding->produced;
       buf = SDATA (object);
     }
@@ -5301,7 +5331,6 @@ send_process (proc, buf, len, object)
                       that may allow the program
                       to finish doing output and read more.  */
                    {
-                     Lisp_Object zero;
                      int offset = 0;
 
 #ifdef BROKEN_PTY_READ_AFTER_EAGAIN
@@ -5336,11 +5365,10 @@ send_process (proc, buf, len, object)
                      else if (STRINGP (object))
                        offset = buf - SDATA (object);
 
-                     XSETFASTINT (zero, 0);
 #ifdef EMACS_HAS_USECS
-                     wait_reading_process_input (0, 20000, zero, 0);
+                     wait_reading_process_output (0, 20000, 0, 0, Qnil, NULL, 0);
 #else
-                     wait_reading_process_input (1, 0, zero, 0);
+                     wait_reading_process_output (1, 0, 0, 0, Qnil, NULL, 0);
 #endif
 
                      if (BUFFERP (object))
@@ -5546,29 +5574,36 @@ process_send_signal (process, signo, current_group, nomsg)
          work.  If the system has it, use it.  */
 #ifdef HAVE_TERMIOS
       struct termios t;
+      cc_t *sig_char = NULL;
+
+      tcgetattr (XINT (p->infd), &t);
 
       switch (signo)
        {
        case SIGINT:
-         tcgetattr (XINT (p->infd), &t);
-         send_process (proc, &t.c_cc[VINTR], 1, Qnil);
-         return;
+         sig_char = &t.c_cc[VINTR];
+         break;
 
        case SIGQUIT:
-         tcgetattr (XINT (p->infd), &t);
-         send_process (proc, &t.c_cc[VQUIT], 1, Qnil);
-         return;
+         sig_char = &t.c_cc[VQUIT];
+         break;
 
        case SIGTSTP:
-         tcgetattr (XINT (p->infd), &t);
 #if defined (VSWTCH) && !defined (PREFER_VSUSP)
-         send_process (proc, &t.c_cc[VSWTCH], 1, Qnil);
+         sig_char = &t.c_cc[VSWTCH];
 #else
-         send_process (proc, &t.c_cc[VSUSP], 1, Qnil);
+         sig_char = &t.c_cc[VSUSP];
 #endif
-         return;
+         break;
        }
 
+      if (sig_char && *sig_char != CDISABLE)
+       {
+         send_process (proc, sig_char, 1, Qnil);
+         return;
+       }
+      /* If we can't send the signal with a character,
+        fall through and send it another way.  */
 #else /* ! HAVE_TERMIOS */
 
       /* On Berkeley descendants, the following IOCTL's retrieve the
@@ -5625,9 +5660,12 @@ process_send_signal (process, signo, current_group, nomsg)
         you'd better be using one of the alternatives above!  */
 #endif /* ! defined (TCGETA) */
 #endif /* ! defined (TIOCGLTC) && defined (TIOCGETC) */
-#endif /* ! defined HAVE_TERMIOS */
+       /* In this case, the code above should alway returns.  */
        abort ();
-      /* The code above always returns from the function.  */
+#endif /* ! defined HAVE_TERMIOS */
+
+      /* The code above may fall through if it can't
+        handle the signal.  */
 #endif /* defined (SIGNALS_VIA_CHARACTERS) */
 
 #ifdef TIOCGPGRP
@@ -6199,7 +6237,7 @@ sigchld_handler (signo)
              FD_CLR (XINT (p->infd), &non_keyboard_wait_mask);
            }
 
-         /* Tell wait_reading_process_input that it needs to wake up and
+         /* Tell wait_reading_process_output that it needs to wake up and
             look around.  */
          if (input_available_clear_time)
            EMACS_SET_SECS_USECS (*input_available_clear_time, 0, 0);
@@ -6217,7 +6255,7 @@ sigchld_handler (signo)
          else if (WIFSIGNALED (w))
             synch_process_termsig = WTERMSIG (w);
 
-         /* Tell wait_reading_process_input that it needs to wake up and
+         /* Tell wait_reading_process_output that it needs to wake up and
             look around.  */
          if (input_available_clear_time)
            EMACS_SET_SECS_USECS (*input_available_clear_time, 0, 0);
@@ -6382,7 +6420,7 @@ status_notify ()
          /* Get the text to use for the message.  */
          if (!NILP (p->raw_status_low))
            update_status (p);
-         msg = status_message (p->status);
+         msg = status_message (p);
 
          /* If process is terminated, deactivate it or delete it.  */
          symbol = p->status;
@@ -6609,6 +6647,11 @@ init_process ()
   FD_ZERO (&non_process_wait_mask);
   max_process_desc = 0;
 
+#ifdef NON_BLOCKING_CONNECT
+  FD_ZERO (&connect_wait_mask);
+  num_pending_connects = 0;
+#endif
+
 #ifdef ADAPTIVE_READ_BUFFERING
   process_output_delay_count = 0;
   process_output_skip = 0;
@@ -6859,10 +6902,9 @@ Lisp_Object QCtype;
      1 to return when input is available, or
      -1 means caller will actually read the input, so don't throw to
        the quit handler.
-     a cons cell, meaning wait until its car is non-nil
-       (and gobble terminal input into the buffer if any arrives), or
-     We know that read_kbd will never be a Lisp_Process, since
-     `subprocesses' isn't defined.
+
+   see full version for other parameters. We know that wait_proc will
+     always be NULL, since `subprocesses' isn't defined.
 
    do_display != 0 means redisplay should be done to show subprocess
    output that arrives.
@@ -6870,27 +6912,17 @@ Lisp_Object QCtype;
    Return true iff we received input from any process.  */
 
 int
-wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
-     int time_limit, microsecs;
-     Lisp_Object read_kbd;
-     int do_display;
+wait_reading_process_output (time_limit, microsecs, read_kbd, do_display,
+                            wait_for_cell, wait_proc, just_wait_proc)
+     int time_limit, microsecs, read_kbd, do_display;
+     Lisp_Object wait_for_cell;
+     struct Lisp_Process *wait_proc;
+     int just_wait_proc;
 {
   register int nfds;
   EMACS_TIME end_time, timeout;
   SELECT_TYPE waitchannels;
   int xerrno;
-  /* Either nil or a cons cell, the car of which is of interest and
-     may be changed outside of this routine.  */
-  Lisp_Object wait_for_cell;
-
-  wait_for_cell = Qnil;
-
-  /* If waiting for non-nil in a cell, record where.  */
-  if (CONSP (read_kbd))
-    {
-      wait_for_cell = read_kbd;
-      XSETFASTINT (read_kbd, 0);
-    }
 
   /* What does time_limit really mean?  */
   if (time_limit || microsecs)
@@ -6913,7 +6945,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
       /* If calling from keyboard input, do not quit
         since we want to return C-g as an input character.
         Otherwise, do pending quit if requested.  */
-      if (XINT (read_kbd) >= 0)
+      if (read_kbd >= 0)
        QUIT;
 
       /* Exit now if the cell we're waiting for became non-nil.  */
@@ -6964,7 +6996,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
          while (!detect_input_pending ());
 
          /* If there is unread keyboard input, also return.  */
-         if (XINT (read_kbd) != 0
+         if (read_kbd != 0
              && requeued_events_pending_p ())
            break;
 
@@ -6982,12 +7014,12 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
 
       /* Cause C-g and alarm signals to take immediate action,
         and cause input available signals to zero out timeout.  */
-      if (XINT (read_kbd) < 0)
+      if (read_kbd < 0)
        set_waiting_for_input (&timeout);
 
       /* Wait till there is something to do.  */
 
-      if (! XINT (read_kbd) && NILP (wait_for_cell))
+      if (! read_kbd && NILP (wait_for_cell))
        FD_ZERO (&waitchannels);
       else
        FD_SET (0, &waitchannels);
@@ -6998,11 +7030,11 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
        {
          clear_waiting_for_input ();
          redisplay_preserve_echo_area (15);
-         if (XINT (read_kbd) < 0)
+         if (read_kbd < 0)
            set_waiting_for_input (&timeout);
        }
 
-      if (XINT (read_kbd) && detect_input_pending ())
+      if (read_kbd && detect_input_pending ())
        {
          nfds = 0;
          FD_ZERO (&waitchannels);
@@ -7038,13 +7070,13 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
        kill (getpid (), SIGIO);
 #endif
 #ifdef SIGIO
-      if (XINT (read_kbd) && interrupt_input && (waitchannels & 1))
+      if (read_kbd && interrupt_input && (waitchannels & 1))
        kill (getpid (), SIGIO);
 #endif
 
       /* Check for keyboard input */
 
-      if ((XINT (read_kbd) != 0)
+      if (read_kbd
          && detect_input_pending_run_timers (do_display))
        {
          swallow_events (do_display);
@@ -7053,7 +7085,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
        }
 
       /* If there is unread keyboard input, also return.  */
-      if (XINT (read_kbd) != 0
+      if (read_kbd
          && requeued_events_pending_p ())
        break;