aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorKaroly Lorentey2004-01-02 04:37:46 +0000
committerKaroly Lorentey2004-01-02 04:37:46 +0000
commiteb9332fa2e41dbe54f5427b9383cb4028a6f926f (patch)
tree4f05548846c10ed0642893c1495882d670e90e4c /src
parentfa971ac34de80905a91d2af15dd8712329dad273 (diff)
parent31e0fbdd4308bde64849bbfa0327a2a77797b3e9 (diff)
downloademacs-eb9332fa2e41dbe54f5427b9383cb4028a6f926f.tar.gz
emacs-eb9332fa2e41dbe54f5427b9383cb4028a6f926f.zip
Merged in changes from CVS HEAD
Patches applied: * miles@gnu.org--gnu-2004/emacs--cvs-trunk--0--patch-10 Update from CVS * miles@gnu.org--gnu-2004/emacs--cvs-trunk--0--patch-11 Update from CVS * miles@gnu.org--gnu-2004/emacs--cvs-trunk--0--patch-12 Add section on button package to lisp reference manual * miles@gnu.org--gnu-2004/emacs--cvs-trunk--0--patch-13 Minor tweaks to Buttons section in lispref/display.texi * miles@gnu.org--gnu-2004/emacs--cvs-trunk--0--patch-14 Update from CVS git-archimport-id: lorentey@elte.hu--2004/emacs--multi-tty--0--patch-33
Diffstat (limited to 'src')
-rw-r--r--src/ChangeLog37
-rw-r--r--src/eval.c2
-rw-r--r--src/print.c4
-rw-r--r--src/process.c199
-rw-r--r--src/process.h12
-rw-r--r--src/w32term.c6
6 files changed, 221 insertions, 39 deletions
diff --git a/src/ChangeLog b/src/ChangeLog
index 121142703c9..d5bf5ba7aa9 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,40 @@
12004-01-02 Kim F. Storm <storm@cua.dk>
2
3 * process.h (struct Lisp_Process): New members for adaptive read
4 buffering: adaptive_read_buffering, read_output_delay, and
5 read_output_skip.
6
7 * process.c (ADAPTIVE_READ_BUFFERING): New conditional.
8 (READ_OUTPUT_DELAY_INCREMENT, READ_OUTPUT_DELAY_MAX)
9 (READ_OUTPUT_DELAY_MAX_MAX): New constants.
10 (process_output_delay_count, process_output_skip): New vars.
11 (Vprocess_adaptive_read_buffering): New variable.
12 (make_process): Initialize adaptive read buffering members.
13 (Fstart_process): Set adaptive_read_buffering member.
14 (deactivate_process): Cleanup adaptive read buffering.
15 (wait_reading_process_input): Temporarily omit delayed
16 subprocesses from the set of file descriptors to read from;
17 adjust the select timeout if we skipped any subprocesses.
18 (read_process_output): Increase adaptive read buffering delay if
19 we read less than a full buffer; reduce delay when we read a
20 full buffer.
21 (send_process): Simplify using local Lisp_Process var.
22 Reset adaptive read buffering delay after write.
23 (init_process): Initialize process_output_delay_count and
24 process_output_skip.
25 (syms_of_process): DEFVAR_LISP Vprocess_adaptive_read_buffering.
26
272004-01-01 Jason Rumney <jasonr@gnu.org>
28
29 * w32term.c (w32_text_out): Use s->font, for consistency with
30 callers.
31
322003-12-30 Luc Teirlinck <teirllm@auburn.edu>
33
34 * print.c (Ferror_message_string): Add hyperlink in the docstring
35 to the definition of `signal' in the Elisp manual.
36 * eval.c (Fsignal): Ditto.
37
12003-12-29 James Clark <jjc@jclark.com> (tiny change) 382003-12-29 James Clark <jjc@jclark.com> (tiny change)
2 39
3 * fns.c (internal_equal): Return t for two NaN arguments. 40 * fns.c (internal_equal): Return t for two NaN arguments.
diff --git a/src/eval.c b/src/eval.c
index 8a6d0d3ff54..a5f66b295a6 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -1436,6 +1436,8 @@ A handler for any of those names will get to handle this signal.
1436The symbol `error' should normally be one of them. 1436The symbol `error' should normally be one of them.
1437 1437
1438DATA should be a list. Its elements are printed as part of the error message. 1438DATA should be a list. Its elements are printed as part of the error message.
1439See Info anchor `(elisp)Definition of signal' for some details on how this
1440error message is constructed.
1439If the signal is handled, DATA is made available to the handler. 1441If the signal is handled, DATA is made available to the handler.
1440See also the function `condition-case'. */) 1442See also the function `condition-case'. */)
1441 (error_symbol, data) 1443 (error_symbol, data)
diff --git a/src/print.c b/src/print.c
index af76616e42b..2560f5f3e26 100644
--- a/src/print.c
+++ b/src/print.c
@@ -967,7 +967,9 @@ debug_print (arg)
967 967
968DEFUN ("error-message-string", Ferror_message_string, Serror_message_string, 968DEFUN ("error-message-string", Ferror_message_string, Serror_message_string,
969 1, 1, 0, 969 1, 1, 0,
970 doc: /* Convert an error value (ERROR-SYMBOL . DATA) to an error message. */) 970 doc: /* Convert an error value (ERROR-SYMBOL . DATA) to an error message.
971See Info anchor `(elisp)Definition of signal' for some details on how this
972error message is constructed. */)
971 (obj) 973 (obj)
972 Lisp_Object obj; 974 Lisp_Object obj;
973{ 975{
diff --git a/src/process.c b/src/process.c
index 3334f3258ae..906497f14ed 100644
--- a/src/process.c
+++ b/src/process.c
@@ -260,6 +260,33 @@ int update_tick;
260#undef DATAGRAM_SOCKETS 260#undef DATAGRAM_SOCKETS
261#endif 261#endif
262 262
263#if !defined (ADAPTIVE_READ_BUFFERING) && !defined (NO_ADAPTIVE_READ_BUFFERING)
264#ifdef EMACS_HAS_USECS
265#define ADAPTIVE_READ_BUFFERING
266#endif
267#endif
268
269#ifdef ADAPTIVE_READ_BUFFERING
270#define READ_OUTPUT_DELAY_INCREMENT 10000
271#define READ_OUTPUT_DELAY_MAX (READ_OUTPUT_DELAY_INCREMENT * 5)
272#define READ_OUTPUT_DELAY_MAX_MAX (READ_OUTPUT_DELAY_INCREMENT * 7)
273
274/* Number of processes which might be delayed. */
275
276static int process_output_delay_count;
277
278/* Non-zero if any process has non-nil process_output_skip. */
279
280static int process_output_skip;
281
282/* Non-nil means to delay reading process output to improve buffering.
283 A value of t means that delay is reset after each send, any other
284 non-nil value does not reset the delay. */
285static Lisp_Object Vprocess_adaptive_read_buffering;
286#else
287#define process_output_delay_count 0
288#endif
289
263 290
264#include "sysselect.h" 291#include "sysselect.h"
265 292
@@ -573,6 +600,12 @@ make_process (name)
573 p->status = Qrun; 600 p->status = Qrun;
574 p->mark = Fmake_marker (); 601 p->mark = Fmake_marker ();
575 602
603#ifdef ADAPTIVE_READ_BUFFERING
604 p->adaptive_read_buffering = Qnil;
605 XSETFASTINT (p->read_output_delay, 0);
606 p->read_output_skip = Qnil;
607#endif
608
576 /* If name is already in use, modify it until it is unused. */ 609 /* If name is already in use, modify it until it is unused. */
577 610
578 name1 = name; 611 name1 = name;
@@ -1501,6 +1534,10 @@ usage: (start-process NAME BUFFER PROGRAM &rest PROGRAM-ARGS) */)
1501 = buffer_defaults.enable_multibyte_characters; 1534 = buffer_defaults.enable_multibyte_characters;
1502 XPROCESS (proc)->command = Flist (nargs - 2, args + 2); 1535 XPROCESS (proc)->command = Flist (nargs - 2, args + 2);
1503 1536
1537#ifdef ADAPTIVE_READ_BUFFERING
1538 XPROCESS (proc)->adaptive_read_buffering = Vprocess_adaptive_read_buffering;
1539#endif
1540
1504 /* Make the process marker point into the process buffer (if any). */ 1541 /* Make the process marker point into the process buffer (if any). */
1505 if (!NILP (buffer)) 1542 if (!NILP (buffer))
1506 set_marker_both (XPROCESS (proc)->mark, buffer, 1543 set_marker_both (XPROCESS (proc)->mark, buffer,
@@ -3588,6 +3625,16 @@ deactivate_process (proc)
3588 inchannel = XINT (p->infd); 3625 inchannel = XINT (p->infd);
3589 outchannel = XINT (p->outfd); 3626 outchannel = XINT (p->outfd);
3590 3627
3628#ifdef ADAPTIVE_READ_BUFFERING
3629 if (XINT (p->read_output_delay) > 0)
3630 {
3631 if (--process_output_delay_count < 0)
3632 process_output_delay_count = 0;
3633 XSETINT (p->read_output_delay, 0);
3634 p->read_output_skip = Qnil;
3635 }
3636#endif
3637
3591 if (inchannel >= 0) 3638 if (inchannel >= 0)
3592 { 3639 {
3593 /* Beware SIGCHLD hereabouts. */ 3640 /* Beware SIGCHLD hereabouts. */
@@ -3973,7 +4020,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
3973 register int channel, nfds; 4020 register int channel, nfds;
3974 static SELECT_TYPE Available; 4021 static SELECT_TYPE Available;
3975 static SELECT_TYPE Connecting; 4022 static SELECT_TYPE Connecting;
3976 int check_connect, no_avail; 4023 int check_connect, check_delay, no_avail;
3977 int xerrno; 4024 int xerrno;
3978 Lisp_Object proc; 4025 Lisp_Object proc;
3979 EMACS_TIME timeout, end_time; 4026 EMACS_TIME timeout, end_time;
@@ -4202,7 +4249,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
4202 if (!NILP (wait_for_cell)) 4249 if (!NILP (wait_for_cell))
4203 { 4250 {
4204 Available = non_process_wait_mask; 4251 Available = non_process_wait_mask;
4205 check_connect = 0; 4252 check_connect = check_delay = 0;
4206 } 4253 }
4207 else 4254 else
4208 { 4255 {
@@ -4211,6 +4258,7 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
4211 else 4258 else
4212 Available = input_wait_mask; 4259 Available = input_wait_mask;
4213 check_connect = (num_pending_connects > 0); 4260 check_connect = (num_pending_connects > 0);
4261 check_delay = process_output_delay_count;
4214 } 4262 }
4215 4263
4216 /* If frame size has changed or the window is newly mapped, 4264 /* If frame size has changed or the window is newly mapped,
@@ -4236,6 +4284,34 @@ wait_reading_process_input (time_limit, microsecs, read_kbd, do_display)
4236 { 4284 {
4237 if (check_connect) 4285 if (check_connect)
4238 Connecting = connect_wait_mask; 4286 Connecting = connect_wait_mask;
4287
4288#ifdef ADAPTIVE_READ_BUFFERING
4289 if (process_output_skip && check_delay > 0)
4290 {
4291 int usecs = EMACS_USECS (timeout);
4292 if (EMACS_SECS (timeout) > 0 || usecs > READ_OUTPUT_DELAY_MAX)
4293 usecs = READ_OUTPUT_DELAY_MAX;
4294 for (channel = 0; check_delay > 0 && channel <= max_process_desc; channel++)
4295 {
4296 proc = chan_process[channel];
4297 if (NILP (proc))
4298 continue;
4299 if (XPROCESS (proc)->read_output_delay > 0)
4300 {
4301 check_delay--;
4302 if (NILP (XPROCESS (proc)->read_output_skip))
4303 continue;
4304 FD_CLR (channel, &Available);
4305 XPROCESS (proc)->read_output_skip = Qnil;
4306 if (XINT (XPROCESS (proc)->read_output_delay) < usecs)
4307 usecs = XINT (XPROCESS (proc)->read_output_delay);
4308 }
4309 }
4310 EMACS_SET_SECS_USECS (timeout, 0, usecs);
4311 process_output_skip = 0;
4312 }
4313#endif
4314
4239 nfds = select (max (max_process_desc, max_keyboard_desc) + 1, 4315 nfds = select (max (max_process_desc, max_keyboard_desc) + 1,
4240 &Available, 4316 &Available,
4241 (check_connect ? &Connecting : (SELECT_TYPE *)0), 4317 (check_connect ? &Connecting : (SELECT_TYPE *)0),
@@ -4689,7 +4765,36 @@ read_process_output (proc, channel)
4689 else 4765 else
4690#endif 4766#endif
4691 if (proc_buffered_char[channel] < 0) 4767 if (proc_buffered_char[channel] < 0)
4692 nbytes = emacs_read (channel, chars + carryover, readmax - carryover); 4768 {
4769 nbytes = emacs_read (channel, chars + carryover, readmax - carryover);
4770#ifdef ADAPTIVE_READ_BUFFERING
4771 if (!NILP (p->adaptive_read_buffering))
4772 {
4773 int delay = XINT (p->read_output_delay);
4774 if (nbytes < readmax - carryover)
4775 {
4776 if (delay < READ_OUTPUT_DELAY_MAX_MAX)
4777 {
4778 if (delay == 0)
4779 process_output_delay_count++;
4780 delay += READ_OUTPUT_DELAY_INCREMENT * 2;
4781 }
4782 }
4783 else if (delay > 0)
4784 {
4785 delay -= READ_OUTPUT_DELAY_INCREMENT;
4786 if (delay == 0)
4787 process_output_delay_count--;
4788 }
4789 XSETINT (p->read_output_delay, delay);
4790 if (delay)
4791 {
4792 p->read_output_skip = Qt;
4793 process_output_skip = 1;
4794 }
4795 }
4796#endif
4797 }
4693 else 4798 else
4694 { 4799 {
4695 chars[carryover] = proc_buffered_char[channel]; 4800 chars[carryover] = proc_buffered_char[channel];
@@ -4991,6 +5096,7 @@ send_process (proc, buf, len, object)
4991 volatile Lisp_Object object; 5096 volatile Lisp_Object object;
4992{ 5097{
4993 /* Use volatile to protect variables from being clobbered by longjmp. */ 5098 /* Use volatile to protect variables from being clobbered by longjmp. */
5099 struct Lisp_Process *p = XPROCESS (proc);
4994 int rv; 5100 int rv;
4995 struct coding_system *coding; 5101 struct coding_system *coding;
4996 struct gcpro gcpro1; 5102 struct gcpro gcpro1;
@@ -4998,20 +5104,17 @@ send_process (proc, buf, len, object)
4998 GCPRO1 (object); 5104 GCPRO1 (object);
4999 5105
5000#ifdef VMS 5106#ifdef VMS
5001 struct Lisp_Process *p = XPROCESS (proc);
5002 VMS_PROC_STUFF *vs, *get_vms_process_pointer(); 5107 VMS_PROC_STUFF *vs, *get_vms_process_pointer();
5003#endif /* VMS */ 5108#endif /* VMS */
5004 5109
5005 if (! NILP (XPROCESS (proc)->raw_status_low)) 5110 if (! NILP (p->raw_status_low))
5006 update_status (XPROCESS (proc)); 5111 update_status (p);
5007 if (! EQ (XPROCESS (proc)->status, Qrun)) 5112 if (! EQ (p->status, Qrun))
5008 error ("Process %s not running", 5113 error ("Process %s not running", SDATA (p->name));
5009 SDATA (XPROCESS (proc)->name)); 5114 if (XINT (p->outfd) < 0)
5010 if (XINT (XPROCESS (proc)->outfd) < 0) 5115 error ("Output file descriptor of %s is closed", SDATA (p->name));
5011 error ("Output file descriptor of %s is closed",
5012 SDATA (XPROCESS (proc)->name));
5013 5116
5014 coding = proc_encode_coding_system[XINT (XPROCESS (proc)->outfd)]; 5117 coding = proc_encode_coding_system[XINT (p->outfd)];
5015 Vlast_coding_system_used = coding->symbol; 5118 Vlast_coding_system_used = coding->symbol;
5016 5119
5017 if ((STRINGP (object) && STRING_MULTIBYTE (object)) 5120 if ((STRINGP (object) && STRING_MULTIBYTE (object))
@@ -5019,13 +5122,12 @@ send_process (proc, buf, len, object)
5019 && !NILP (XBUFFER (object)->enable_multibyte_characters)) 5122 && !NILP (XBUFFER (object)->enable_multibyte_characters))
5020 || EQ (object, Qt)) 5123 || EQ (object, Qt))
5021 { 5124 {
5022 if (!EQ (coding->symbol, XPROCESS (proc)->encode_coding_system)) 5125 if (!EQ (coding->symbol, p->encode_coding_system))
5023 /* The coding system for encoding was changed to raw-text 5126 /* The coding system for encoding was changed to raw-text
5024 because we sent a unibyte text previously. Now we are 5127 because we sent a unibyte text previously. Now we are
5025 sending a multibyte text, thus we must encode it by the 5128 sending a multibyte text, thus we must encode it by the
5026 original coding system specified for the current 5129 original coding system specified for the current process. */
5027 process. */ 5130 setup_coding_system (p->encode_coding_system, coding);
5028 setup_coding_system (XPROCESS (proc)->encode_coding_system, coding);
5029 /* src_multibyte should be set to 1 _after_ a call to 5131 /* src_multibyte should be set to 1 _after_ a call to
5030 setup_coding_system, since it resets src_multibyte to 5132 setup_coding_system, since it resets src_multibyte to
5031 zero. */ 5133 zero. */
@@ -5076,15 +5178,15 @@ send_process (proc, buf, len, object)
5076 coding->composing = COMPOSITION_DISABLED; 5178 coding->composing = COMPOSITION_DISABLED;
5077 } 5179 }
5078 5180
5079 if (SBYTES (XPROCESS (proc)->encoding_buf) < require) 5181 if (SBYTES (p->encoding_buf) < require)
5080 XPROCESS (proc)->encoding_buf = make_uninit_string (require); 5182 p->encoding_buf = make_uninit_string (require);
5081 5183
5082 if (from_byte >= 0) 5184 if (from_byte >= 0)
5083 buf = (BUFFERP (object) 5185 buf = (BUFFERP (object)
5084 ? BUF_BYTE_ADDRESS (XBUFFER (object), from_byte) 5186 ? BUF_BYTE_ADDRESS (XBUFFER (object), from_byte)
5085 : SDATA (object) + from_byte); 5187 : SDATA (object) + from_byte);
5086 5188
5087 object = XPROCESS (proc)->encoding_buf; 5189 object = p->encoding_buf;
5088 encode_coding (coding, (char *) buf, SDATA (object), 5190 encode_coding (coding, (char *) buf, SDATA (object),
5089 len, SBYTES (object)); 5191 len, SBYTES (object));
5090 len = coding->produced; 5192 len = coding->produced;
@@ -5102,8 +5204,7 @@ send_process (proc, buf, len, object)
5102 if (pty_max_bytes == 0) 5204 if (pty_max_bytes == 0)
5103 { 5205 {
5104#if defined (HAVE_FPATHCONF) && defined (_PC_MAX_CANON) 5206#if defined (HAVE_FPATHCONF) && defined (_PC_MAX_CANON)
5105 pty_max_bytes = fpathconf (XFASTINT (XPROCESS (proc)->outfd), 5207 pty_max_bytes = fpathconf (XFASTINT (p->outfd), _PC_MAX_CANON);
5106 _PC_MAX_CANON);
5107 if (pty_max_bytes < 0) 5208 if (pty_max_bytes < 0)
5108 pty_max_bytes = 250; 5209 pty_max_bytes = 250;
5109#else 5210#else
@@ -5126,7 +5227,7 @@ send_process (proc, buf, len, object)
5126 5227
5127 /* Decide how much data we can send in one batch. 5228 /* Decide how much data we can send in one batch.
5128 Long lines need to be split into multiple batches. */ 5229 Long lines need to be split into multiple batches. */
5129 if (!NILP (XPROCESS (proc)->pty_flag)) 5230 if (!NILP (p->pty_flag))
5130 { 5231 {
5131 /* Starting this at zero is always correct when not the first 5232 /* Starting this at zero is always correct when not the first
5132 iteration because the previous iteration ended by sending C-d. 5233 iteration because the previous iteration ended by sending C-d.
@@ -5155,7 +5256,7 @@ send_process (proc, buf, len, object)
5155 /* Send this batch, using one or more write calls. */ 5256 /* Send this batch, using one or more write calls. */
5156 while (this > 0) 5257 while (this > 0)
5157 { 5258 {
5158 int outfd = XINT (XPROCESS (proc)->outfd); 5259 int outfd = XINT (p->outfd);
5159 old_sigpipe = (SIGTYPE (*) ()) signal (SIGPIPE, send_process_trap); 5260 old_sigpipe = (SIGTYPE (*) ()) signal (SIGPIPE, send_process_trap);
5160#ifdef DATAGRAM_SOCKETS 5261#ifdef DATAGRAM_SOCKETS
5161 if (DATAGRAM_CHAN_P (outfd)) 5262 if (DATAGRAM_CHAN_P (outfd))
@@ -5168,7 +5269,18 @@ send_process (proc, buf, len, object)
5168 } 5269 }
5169 else 5270 else
5170#endif 5271#endif
5171 rv = emacs_write (outfd, (char *) buf, this); 5272 {
5273 rv = emacs_write (outfd, (char *) buf, this);
5274#ifdef ADAPTIVE_READ_BUFFERING
5275 if (XINT (p->read_output_delay) > 0
5276 && EQ (p->adaptive_read_buffering, Qt))
5277 {
5278 XSETFASTINT (p->read_output_delay, 0);
5279 process_output_delay_count--;
5280 p->read_output_skip = Qnil;
5281 }
5282#endif
5283 }
5172 signal (SIGPIPE, old_sigpipe); 5284 signal (SIGPIPE, old_sigpipe);
5173 5285
5174 if (rv < 0) 5286 if (rv < 0)
@@ -5209,8 +5321,7 @@ send_process (proc, buf, len, object)
5209 if (errno == EAGAIN) 5321 if (errno == EAGAIN)
5210 { 5322 {
5211 int flags = FWRITE; 5323 int flags = FWRITE;
5212 ioctl (XINT (XPROCESS (proc)->outfd), TIOCFLUSH, 5324 ioctl (XINT (p->outfd), TIOCFLUSH, &flags);
5213 &flags);
5214 } 5325 }
5215#endif /* BROKEN_PTY_READ_AFTER_EAGAIN */ 5326#endif /* BROKEN_PTY_READ_AFTER_EAGAIN */
5216 5327
@@ -5255,18 +5366,17 @@ send_process (proc, buf, len, object)
5255 { 5366 {
5256#ifndef VMS 5367#ifndef VMS
5257 proc = process_sent_to; 5368 proc = process_sent_to;
5369 p = XPROCESS (proc);
5258#endif 5370#endif
5259 XPROCESS (proc)->raw_status_low = Qnil; 5371 p->raw_status_low = Qnil;
5260 XPROCESS (proc)->raw_status_high = Qnil; 5372 p->raw_status_high = Qnil;
5261 XPROCESS (proc)->status = Fcons (Qexit, Fcons (make_number (256), Qnil)); 5373 p->status = Fcons (Qexit, Fcons (make_number (256), Qnil));
5262 XSETINT (XPROCESS (proc)->tick, ++process_tick); 5374 XSETINT (p->tick, ++process_tick);
5263 deactivate_process (proc); 5375 deactivate_process (proc);
5264#ifdef VMS 5376#ifdef VMS
5265 error ("Error writing to process %s; closed it", 5377 error ("Error writing to process %s; closed it", SDATA (p->name));
5266 SDATA (XPROCESS (proc)->name));
5267#else 5378#else
5268 error ("SIGPIPE raised on process %s; closed it", 5379 error ("SIGPIPE raised on process %s; closed it", SDATA (p->name));
5269 SDATA (XPROCESS (proc)->name));
5270#endif 5380#endif
5271 } 5381 }
5272 5382
@@ -6493,6 +6603,11 @@ init_process ()
6493 FD_ZERO (&non_process_wait_mask); 6603 FD_ZERO (&non_process_wait_mask);
6494 max_process_desc = 0; 6604 max_process_desc = 0;
6495 6605
6606#ifdef ADAPTIVE_READ_BUFFERING
6607 process_output_delay_count = 0;
6608 process_output_skip = 0;
6609#endif
6610
6496 FD_SET (0, &input_wait_mask); 6611 FD_SET (0, &input_wait_mask);
6497 6612
6498 Vprocess_alist = Qnil; 6613 Vprocess_alist = Qnil;
@@ -6626,6 +6741,20 @@ then a pipe is used in any case.
6626The value takes effect when `start-process' is called. */); 6741The value takes effect when `start-process' is called. */);
6627 Vprocess_connection_type = Qt; 6742 Vprocess_connection_type = Qt;
6628 6743
6744#ifdef ADAPTIVE_READ_BUFFERING
6745 DEFVAR_LISP ("process-adaptive-read-buffering", &Vprocess_adaptive_read_buffering,
6746 doc: /* If non-nil, improve receive buffering by delaying after short reads.
6747On some systems, when emacs reads the output from a subprocess, the output data
6748is read in very small blocks, potentially resulting in very poor performance.
6749This behaviour can be remedied to some extent by setting this variable to a
6750non-nil value, as it will automatically delay reading from such processes, to
6751allowing them to produce more output before emacs tries to read it.
6752If the value is t, the delay is reset after each write to the process; any other
6753non-nil value means that the delay is not reset on write.
6754The variable takes effect when `start-process' is called. */);
6755 Vprocess_adaptive_read_buffering = Qt;
6756#endif
6757
6629 defsubr (&Sprocessp); 6758 defsubr (&Sprocessp);
6630 defsubr (&Sget_process); 6759 defsubr (&Sget_process);
6631 defsubr (&Sget_buffer_process); 6760 defsubr (&Sget_buffer_process);
diff --git a/src/process.h b/src/process.h
index 63680a0ed8e..2f46e74d4d0 100644
--- a/src/process.h
+++ b/src/process.h
@@ -101,6 +101,18 @@ struct Lisp_Process
101 generated, and can be changed by the function 101 generated, and can be changed by the function
102 `set-process-fileter-multibyte'. */ 102 `set-process-fileter-multibyte'. */
103 Lisp_Object filter_multibyte; 103 Lisp_Object filter_multibyte;
104 /* Should we delay reading output from this process.
105 Initialized from `Vprocess_adaptive_read_buffering'. */
106 Lisp_Object adaptive_read_buffering;
107 /* Hysteresis to try to read process output in larger blocks.
108 On some systems, e.g. the Linux kernel, emacs is seen as
109 an interactive app also when reading process output, meaning
110 that process output can be read in as little as 1 byte at a
111 time. Value is micro-seconds to delay reading output from
112 this process. Range is 0 .. 50000. */
113 Lisp_Object read_output_delay;
114 /* Skip reading this process on next read. */
115 Lisp_Object read_output_skip;
104}; 116};
105 117
106/* Every field in the preceding structure except for the first two 118/* Every field in the preceding structure except for the first two
diff --git a/src/w32term.c b/src/w32term.c
index 6da7f612ec9..bee1a1913ff 100644
--- a/src/w32term.c
+++ b/src/w32term.c
@@ -1121,9 +1121,9 @@ w32_text_out (s, x, y,chars,nchars)
1121 wchar_t * chars; 1121 wchar_t * chars;
1122 int nchars; 1122 int nchars;
1123{ 1123{
1124 int charset_dim = w32_font_is_double_byte (s->gc->font) ? 2 : 1; 1124 int charset_dim = w32_font_is_double_byte (s->font) ? 2 : 1;
1125 if (s->gc->font->bdf) 1125 if (s->font->bdf)
1126 w32_BDF_TextOut (s->gc->font->bdf, s->hdc, 1126 w32_BDF_TextOut (s->font->bdf, s->hdc,
1127 x, y, (char *) chars, charset_dim, 1127 x, y, (char *) chars, charset_dim,
1128 nchars * charset_dim, 0); 1128 nchars * charset_dim, 0);
1129 else if (s->first_glyph->font_type == UNICODE_FONT) 1129 else if (s->first_glyph->font_type == UNICODE_FONT)