From xemacs-m  Tue Jun 10 19:50:07 1997
Received: from jagor.srce.hr (hniksic@jagor.srce.hr [161.53.2.130])
	by xemacs.org (8.8.5/8.8.5) with ESMTP id TAA05835
	for <xemacs-beta@xemacs.org>; Tue, 10 Jun 1997 19:50:05 -0500 (CDT)
Received: (from hniksic@localhost)
          by jagor.srce.hr (8.8.5/8.8.4)
	  id CAA05184; Wed, 11 Jun 1997 02:50:06 +0200 (MET DST)
To: XEmacs Developers <xemacs-beta@xemacs.org>
Subject: `save-current-buffer' and a load of other stuff synched with FSF
X-Attribution: Hrv
X-Face: Mie8:rOV<\c/~z{s.X4A{!?vY7{drJ([U]0O=W/<W*SMo/Mv:58:*_y~ki>xDi&N7XG
        KV^$k0m3Oe/)'e%3=$PCR&3ITUXH,cK>]bci&<qQ>Ff%x_>1`T(+M2Gg/fgndU%k*ft
        [(7._6e0n-V%|%'[c|q:;}td$#INd+;?!-V=c8Pqf}3J
From: Hrvoje Niksic <hniksic@srce.hr>
Date: 11 Jun 1997 02:50:06 +0200
Message-ID: <kig206am08x.fsf@jagor.srce.hr>
Lines: 234
X-Mailer: Gnus v5.4.52/XEmacs 20.3(beta4)

This required an addition to the byte-compiler.  Unfortunately, the
bytecode RMS chose as `save-current-buffer' is our eq.  I picked an
unused one.

ChangeLog entries (Lisp):

1997-06-11  Hrvoje Niksic  <hniksic@srce.hr>

	* prim/subr.el (with-current-buffer): New macro.
	(with-temp-file): Ditto.

	* bytecomp/byte-optimize.el (byte-optimize-form-code-walker): Test 
	for `save-current-buffer'.

	* bytecomp/bytecomp.el: Recognize `save-current-buffer'.

	* edebug/edebug.el: Register with-current-buffer and others.

	* modes/lisp-mode.el: Added specs for save-current-buffer,
 	with-output-to-string, with-current-buffer, with-temp-file and
 	with-output-to-temp-buffer.

C:

1997-06-11  Hrvoje Niksic  <hniksic@srce.hr>

	* bytecode.c (Bsave_current_buffer): Register.
	(Fbyte_code): Do action.

	* editfns.c (Fsave_current_buffer): New SUBR.


Patches follow.  Knowledgable people, this is a call to you to
proofread this material.  Although I have been *very* careful in
composing these patches, I may have made mistakes.  Steve, Kyle,
Martin, everyone -- please take a look at these.


--- etc/NEWS.orig	Wed Jun 11 02:38:44 1997
+++ etc/NEWS	Wed Jun 11 02:40:17 1997
@@ -202,6 +202,23 @@
 ** The PATTERN argument to `split-string' is now optional and defaults
 to whitespace ("[ \f\t\n\r\v]+").
 
+** The new macro `with-current-buffer' lets you evaluate an expression
+conveniently with a different current buffer.  It looks like this:
+
+  (with-current-buffer BUFFER BODY-FORMS...)
+
+BUFFER is the expression that says which buffer to use.
+BODY-FORMS say what to do in that buffer.
+
+** The new primitive `save-current-buffer' saves and restores the
+choice of current buffer, like `save-excursion', but without saving or
+restoring the value of point or the mark.  `with-current-buffer'
+works using `save-current-buffer'.
+
+** The new macro `with-temp-file' lets you do some work in a new buffer and
+write the output to a specified file.  Like `progn', it returns the value
+of the last form.
+
 
 
 * Changes in XEmacs 20.2
--- src/editfns.c.orig	Wed Jun 11 01:35:49 1997
+++ src/editfns.c	Wed Jun 11 01:39:14 1997
@@ -489,6 +489,20 @@
 			 
   return unbind_to (speccount, Fprogn (args));
 }
+
+DEFUN ("save-current-buffer", Fsave_current_buffer, 0, UNEVALLED, 0, /*
+Save the current buffer; execute BODY; restore the current buffer.
+Executes BODY just like `progn'.
+*/
+  (args))
+{
+  /* This function can GC */
+  int speccount = specpdl_depth ();
+
+  record_unwind_protect (Fset_buffer, Fcurrent_buffer ());
+
+  return unbind_to (speccount, Fprogn (args));
+}
 
 DEFUN ("buffer-size", Fbufsize, 0, 1, 0, /*
 Return the number of characters in BUFFER.
@@ -2100,6 +2114,7 @@
   DEFSUBR (Fregion_beginning);
   DEFSUBR (Fregion_end);
   DEFSUBR (Fsave_excursion);
+  DEFSUBR (Fsave_current_buffer);
 
   DEFSUBR (Fbufsize);
   DEFSUBR (Fpoint_max);
--- src/bytecode.c.orig	Wed Jun 11 01:49:24 1997
+++ src/bytecode.c	Wed Jun 11 01:53:33 1997
@@ -155,7 +155,8 @@
 #define Bbobp 0157
 #define Bcurrent_buffer 0160
 #define Bset_buffer 0161
-#define Bread_char 0162 /* No longer generated as of v19 */
+#define Bsave_current_buffer 0162 /* was Bread_char, but no longer
+				     generated as of v19 */
 #define Bmemq 0163 /* was Bset_mark, but no longer generated as of v18 */
 #define Binteractive_p 0164 /* Needed since interactive-p takes unevalled args */
 
@@ -941,8 +942,8 @@
 	  TOP = Fset_buffer (TOP);
 	  break;
 
-	case Bread_char:
-	  error ("read-char is an obsolete byte code");
+	case Bsave_current_buffer:
+	  record_unwind_protect (Fset_buffer, Fcurrent_buffer ());
 	  break;
 
 	case Binteractive_p:
--- lisp/prim/subr.el.orig	Tue Jun 10 22:38:11 1997
+++ lisp/prim/subr.el	Wed Jun 11 02:27:22 1997
@@ -333,6 +333,33 @@
 	   (buffer-string)
 	 (erase-buffer)))))
 
+(defmacro with-current-buffer (buffer &rest body)
+  "Execute the forms in BODY with BUFFER as the current buffer.
+The value returned is the value of the last form in BODY.
+See also `with-temp-buffer'."
+  `(save-current-buffer
+    (set-buffer ,buffer)
+    ,@body))
+
+(defmacro with-temp-file (file &rest forms)
+  "Create a new buffer, evaluate FORMS there, and write the buffer to FILE.
+The value of the last form in FORMS is returned, like `progn'.
+See also `with-temp-buffer'."
+  (let ((temp-file (make-symbol "temp-file"))
+	(temp-buffer (make-symbol "temp-buffer")))
+    `(let ((,temp-file ,file)
+	   (,temp-buffer
+	    (get-buffer-create (generate-new-buffer-name " *temp file*"))))
+       (unwind-protect
+	   (prog1
+	       (with-current-buffer ,temp-buffer
+                  ,@forms)
+	     (with-current-buffer ,temp-buffer
+               (widen)
+	       (write-region (point-min) (point-max) ,temp-file nil 0)))
+	 (and (buffer-name ,temp-buffer)
+	      (kill-buffer ,temp-buffer))))))
+
 (defmacro with-temp-buffer (&rest forms)
   "Create a temporary buffer, and evaluate FORMS there like `progn'."
   (let ((temp-buffer (make-symbol "temp-buffer")))
--- lisp/bytecomp/bytecomp.el.orig	Wed Jun 11 01:56:45 1997
+++ lisp/bytecomp/bytecomp.el	Wed Jun 11 02:00:45 1997
@@ -577,7 +577,9 @@
 (byte-defop 111  1 byte-bobp)
 (byte-defop 112  1 byte-current-buffer)
 (byte-defop 113  0 byte-set-buffer)
-(byte-defop 114  1 byte-read-char-OBSOLETE) ;obsolete as of v19
+(byte-defop 114  0 byte-save-current-buffer
+  "To make a binding to record the current buffer.")
+;;(byte-defop 114  1 byte-read-char-OBSOLETE) ;obsolete as of v19
 (byte-defop 115 -1 byte-memq) ; new as of v20
 (byte-defop 116  1 byte-interactive-p)
 
@@ -3527,6 +3529,7 @@
 (byte-defop-compiler-1 unwind-protect)
 (byte-defop-compiler-1 condition-case)
 (byte-defop-compiler-1 save-excursion)
+(byte-defop-compiler-1 save-current-buffer)
 (byte-defop-compiler-1 save-restriction)
 (byte-defop-compiler-1 save-window-excursion)
 (byte-defop-compiler-1 with-output-to-temp-buffer)
@@ -3611,6 +3614,11 @@
 
 (defun byte-compile-save-restriction (form)
   (byte-compile-out 'byte-save-restriction 0)
+  (byte-compile-body-do-effect (cdr form))
+  (byte-compile-out 'byte-unbind 1))
+
+(defun byte-compile-save-current-buffer (form)
+  (byte-compile-out 'byte-save-current-buffer 0)
   (byte-compile-body-do-effect (cdr form))
   (byte-compile-out 'byte-unbind 1))
 
--- lisp/bytecomp/byte-optimize.el.orig	Wed Jun 11 02:02:47 1997
+++ lisp/bytecomp/byte-optimize.el	Wed Jun 11 02:02:59 1997
@@ -433,7 +433,7 @@
 	       (cons (byte-optimize-form (nth 2 form) for-effect)
 		     (byte-optimize-body (cdr (cdr (cdr form))) t)))))
 	  
-	  ((memq fn '(save-excursion save-restriction))
+	  ((memq fn '(save-excursion save-restriction save-current-buffer))
 	   ;; those subrs which have an implicit progn; it's not quite good
 	   ;; enough to treat these like normal function calls.
 	   ;; This can turn (save-excursion ...) into (save-excursion) which
--- lisp/edebug/edebug.el.orig	Wed Jun 11 02:07:16 1997
+++ lisp/edebug/edebug.el	Wed Jun 11 02:10:38 1997
@@ -2164,6 +2164,14 @@
 (def-edebug-spec eval-when-compile t)
 (def-edebug-spec eval-and-compile t)
 
+(def-edebug-spec save-selected-window t)
+(def-edebug-spec save-current-buffer t)
+(def-edebug-spec save-match-data t)
+(def-edebug-spec with-output-to-string t)
+(def-edebug-spec with-current-buffer t)
+(def-edebug-spec with-temp-file t)
+(def-edebug-spec with-temp-buffer t)
+
 ;; Anything else?
 
 
--- lisp/modes/lisp-mode.el.orig	Wed Jun 11 02:23:19 1997
+++ lisp/modes/lisp-mode.el	Wed Jun 11 02:34:39 1997
@@ -713,6 +713,10 @@
 (put 'catch 'lisp-indent-function 1)
 (put 'condition-case 'lisp-indent-function 2)
 (put 'unwind-protect 'lisp-indent-function 1)
+(put 'save-current-buffer 'lisp-indent-function 0)
+(put 'with-current-buffer 'lisp-indent-function 1)
+(put 'with-temp-file 'lisp-indent-function 1)
+(put 'with-output-to-string 'lisp-indent-function 0)
 (put 'with-output-to-temp-buffer 'lisp-indent-function 1)
 
 (defun indent-sexp (&optional endpos)


-- 
Hrvoje Niksic <hniksic@srce.hr> | Student at FER Zagreb, Croatia
--------------------------------+--------------------------------
Speak softly and carry a +6 two-handed sword.

