diff options
| author | Phillip Lord | 2016-07-18 23:28:05 +0100 |
|---|---|---|
| committer | Phillip Lord | 2017-01-14 12:07:27 +0000 |
| commit | 86a2c93b3b62a1decad326fd66ed5cc1a9e64d5f (patch) | |
| tree | 2bba44a75181d40df367217f4d9f2d5ec5b05925 | |
| parent | 9569916d94c6c448862d02919e52fc3bfb9b9c8d (diff) | |
| download | emacs-feature/stdout-stderr-stream.tar.gz emacs-feature/stdout-stderr-stream.zip | |
Support standard input, output and error streamsfeature/stdout-stderr-stream
* doc/lispref/streams.texi: Update doc
* lisp/simple.el (external-standard-input): New function
* src/fns.c (external-standard-input-read-char,
external-standard-input-read-line): New functions
* src/print.c: (external-standard-output,
external-standard-input): New functions
| -rw-r--r-- | doc/lispref/streams.texi | 38 | ||||
| -rw-r--r-- | lisp/simple.el | 15 | ||||
| -rw-r--r-- | src/fns.c | 62 | ||||
| -rw-r--r-- | src/print.c | 19 |
4 files changed, 133 insertions, 1 deletions
diff --git a/doc/lispref/streams.texi b/doc/lispref/streams.texi index 41bc71e6aea..63a64947618 100644 --- a/doc/lispref/streams.texi +++ b/doc/lispref/streams.texi | |||
| @@ -142,7 +142,7 @@ A symbol as input stream is equivalent to the symbol's function | |||
| 142 | definition (if any). | 142 | definition (if any). |
| 143 | @end table | 143 | @end table |
| 144 | 144 | ||
| 145 | Here is an example of reading from a stream that is a buffer, showing | 145 | Here is an example of reading from a stream that is a buffer, showing |
| 146 | where point is located before and after: | 146 | where point is located before and after: |
| 147 | 147 | ||
| 148 | @example | 148 | @example |
| @@ -265,6 +265,20 @@ reader encountered the open parenthesis, decided that it ended the | |||
| 265 | input, and unread it. Another attempt to read from the stream at this | 265 | input, and unread it. Another attempt to read from the stream at this |
| 266 | point would read @samp{()} and return @code{nil}. | 266 | point would read @samp{()} and return @code{nil}. |
| 267 | 267 | ||
| 268 | One function that is specifically designed for use as an input stream | ||
| 269 | is: | ||
| 270 | |||
| 271 | @cindex @code{external-standard-input} | ||
| 272 | @defun external-standard-input &optional char | ||
| 273 | This function reads a single character from the system standard input | ||
| 274 | (as opposed to @var{standard-input}) and functions as a stream. Note, | ||
| 275 | however, that if Emacs is running in a terminal its use can be | ||
| 276 | unpredictable. | ||
| 277 | @end defun | ||
| 278 | |||
| 279 | As with @code{external-standard-output}, this function is | ||
| 280 | predominately useful for debugging. | ||
| 281 | |||
| 268 | @node Input Functions | 282 | @node Input Functions |
| 269 | @section Input Functions | 283 | @section Input Functions |
| 270 | 284 | ||
| @@ -530,6 +544,28 @@ Now we can put the output in the proper order by reversing the list: | |||
| 530 | Calling @code{concat} converts the list to a string so you can see its | 544 | Calling @code{concat} converts the list to a string so you can see its |
| 531 | contents more clearly. | 545 | contents more clearly. |
| 532 | 546 | ||
| 547 | Two functions which are specifically designed for use as output | ||
| 548 | streams: | ||
| 549 | |||
| 550 | @defun external-standard-output | ||
| 551 | @cindex @code{external-standard-output} output stream | ||
| 552 | Prints to the system standard output (as opposed to the | ||
| 553 | @var{standard-output}), regardless of whether Emacs is running | ||
| 554 | interactively or not. | ||
| 555 | @end defun | ||
| 556 | |||
| 557 | @defun external-standard-error | ||
| 558 | @cindex @code{external-standard-error} output stream | ||
| 559 | Prints to the system standard error, regardless of whether Emacs is | ||
| 560 | running interactively or not. | ||
| 561 | @end defun | ||
| 562 | |||
| 563 | These functions are predominately useful for debugging, as they are a | ||
| 564 | mechanism for producing output that does not change any buffer. Note, | ||
| 565 | however, that if Emacs is running in a terminal their use can affect | ||
| 566 | the display unpredictably. | ||
| 567 | |||
| 568 | |||
| 533 | @node Output Functions | 569 | @node Output Functions |
| 534 | @section Output Functions | 570 | @section Output Functions |
| 535 | 571 | ||
diff --git a/lisp/simple.el b/lisp/simple.el index a757876328b..17697f9be2b 100644 --- a/lisp/simple.el +++ b/lisp/simple.el | |||
| @@ -8718,6 +8718,21 @@ to capitalize ARG words." | |||
| 8718 | (capitalize-region (region-beginning) (region-end)) | 8718 | (capitalize-region (region-beginning) (region-end)) |
| 8719 | (capitalize-word arg))) | 8719 | (capitalize-word arg))) |
| 8720 | 8720 | ||
| 8721 | (defvar external-standard-input-pushback nil | ||
| 8722 | "Pushback character for `external-standard-input'.") | ||
| 8723 | |||
| 8724 | (defun external-standard-input (&optional char) | ||
| 8725 | "Read a character from the system standard input. | ||
| 8726 | |||
| 8727 | If CHAR is non-nil, then do not read but return CHAR | ||
| 8728 | on the next invocation." | ||
| 8729 | (if char | ||
| 8730 | (setq external-standard-input-pushback char) | ||
| 8731 | (if (eq nil external-standard-input-pushback) | ||
| 8732 | (external-standard-input-read-char) | ||
| 8733 | (let ((rtn external-standard-input-pushback)) | ||
| 8734 | (setq external-standard-input-pushback nil) | ||
| 8735 | rtn)))) | ||
| 8721 | 8736 | ||
| 8722 | 8737 | ||
| 8723 | (provide 'simple) | 8738 | (provide 'simple) |
| @@ -5082,6 +5082,65 @@ If nil, use the current buffer." */ ) | |||
| 5082 | return make_digest_string (digest, SHA1_DIGEST_SIZE); | 5082 | return make_digest_string (digest, SHA1_DIGEST_SIZE); |
| 5083 | } | 5083 | } |
| 5084 | 5084 | ||
| 5085 | DEFUN ("external-standard-input-read-char",Fexternal_standard_input_read_char, Sexternal_standard_input_read_char, 0, 0, 0, | ||
| 5086 | doc: /* Read a single character from the system standard input. | ||
| 5087 | |||
| 5088 | Returns -1 if standard input is at the end.*/) | ||
| 5089 | (void) | ||
| 5090 | { | ||
| 5091 | int c; | ||
| 5092 | Lisp_Object val; | ||
| 5093 | |||
| 5094 | c = getchar(); | ||
| 5095 | XSETINT(val,c); | ||
| 5096 | |||
| 5097 | return val; | ||
| 5098 | } | ||
| 5099 | |||
| 5100 | DEFUN ("external-standard-input-read-line", Fexternal_standard_input_read_line, Sexternal_standard_input_read_line, 0, 0, 0, | ||
| 5101 | doc: /* Read a line from the system standard input.*/) | ||
| 5102 | (void) | ||
| 5103 | { | ||
| 5104 | ptrdiff_t size, len; | ||
| 5105 | char *line; | ||
| 5106 | Lisp_Object val; | ||
| 5107 | int c; | ||
| 5108 | |||
| 5109 | val = Qnil; | ||
| 5110 | size = 100; | ||
| 5111 | len = 0; | ||
| 5112 | line = xmalloc (size); | ||
| 5113 | |||
| 5114 | while ((c = getchar ()) != '\n' && c != '\r') | ||
| 5115 | { | ||
| 5116 | if (c == EOF) | ||
| 5117 | { | ||
| 5118 | if (errno != 0) | ||
| 5119 | break; | ||
| 5120 | } | ||
| 5121 | else | ||
| 5122 | { | ||
| 5123 | if (len == size) | ||
| 5124 | line = xpalloc (line, &size, 1, -1, sizeof *line); | ||
| 5125 | line[len++] = c; | ||
| 5126 | } | ||
| 5127 | } | ||
| 5128 | |||
| 5129 | if (len || c == '\n' || c == '\r') | ||
| 5130 | { | ||
| 5131 | val = make_string (line, len); | ||
| 5132 | xfree (line); | ||
| 5133 | } | ||
| 5134 | else | ||
| 5135 | { | ||
| 5136 | xfree (line); | ||
| 5137 | error ("Error reading from stdin"); | ||
| 5138 | } | ||
| 5139 | |||
| 5140 | return val; | ||
| 5141 | } | ||
| 5142 | |||
| 5143 | |||
| 5085 | 5144 | ||
| 5086 | void | 5145 | void |
| 5087 | syms_of_fns (void) | 5146 | syms_of_fns (void) |
| @@ -5249,4 +5308,7 @@ this variable. */); | |||
| 5249 | defsubr (&Ssecure_hash); | 5308 | defsubr (&Ssecure_hash); |
| 5250 | defsubr (&Sbuffer_hash); | 5309 | defsubr (&Sbuffer_hash); |
| 5251 | defsubr (&Slocale_info); | 5310 | defsubr (&Slocale_info); |
| 5311 | defsubr (&Sexternal_standard_input_read_char); | ||
| 5312 | defsubr (&Sexternal_standard_input_read_line); | ||
| 5313 | |||
| 5252 | } | 5314 | } |
diff --git a/src/print.c b/src/print.c index 5531210e1b8..25f0afbf972 100644 --- a/src/print.c +++ b/src/print.c | |||
| @@ -769,6 +769,22 @@ to make it write to the debugging output. */) | |||
| 769 | return character; | 769 | return character; |
| 770 | } | 770 | } |
| 771 | 771 | ||
| 772 | DEFUN ("external-standard-output", Fexternal_standard_output, Sexternal_standard_output, 1, 1, 0, | ||
| 773 | doc: /* Output character CHARACTER to system standard output. */) | ||
| 774 | (Lisp_Object character) | ||
| 775 | { | ||
| 776 | CHECK_NUMBER (character); | ||
| 777 | printchar_to_stream (XINT(character), stdout); | ||
| 778 | return character; | ||
| 779 | } | ||
| 780 | |||
| 781 | DEFUN ("external-standard-error", Fexternal_standard_error, Sexternal_standard_error, 1, 1, 0, | ||
| 782 | doc: /* Output character CHARACTER to system standard error. */) | ||
| 783 | (Lisp_Object character) | ||
| 784 | { | ||
| 785 | return Fexternal_debugging_output (character); | ||
| 786 | } | ||
| 787 | |||
| 772 | /* This function is never called. Its purpose is to prevent | 788 | /* This function is never called. Its purpose is to prevent |
| 773 | print_output_debug_flag from being optimized away. */ | 789 | print_output_debug_flag from being optimized away. */ |
| 774 | 790 | ||
| @@ -2307,7 +2323,10 @@ priorities. */); | |||
| 2307 | defsubr (&Sprinc); | 2323 | defsubr (&Sprinc); |
| 2308 | defsubr (&Sprint); | 2324 | defsubr (&Sprint); |
| 2309 | defsubr (&Sterpri); | 2325 | defsubr (&Sterpri); |
| 2326 | defsubr (&Sexternal_standard_output); | ||
| 2327 | defsubr (&Sexternal_standard_error); | ||
| 2310 | defsubr (&Swrite_char); | 2328 | defsubr (&Swrite_char); |
| 2329 | |||
| 2311 | defsubr (&Sredirect_debugging_output); | 2330 | defsubr (&Sredirect_debugging_output); |
| 2312 | 2331 | ||
| 2313 | DEFSYM (Qprint_escape_newlines, "print-escape-newlines"); | 2332 | DEFSYM (Qprint_escape_newlines, "print-escape-newlines"); |