branch: externals/compat
commit c81ff6a92f74a4ca47da05db46f6b3f69882271e
Author: Daniel Mendler <m...@daniel-mendler.de>
Commit: Daniel Mendler <m...@daniel-mendler.de>

    compat-29: with-narrowing -> with-restriction, without-restriction
---
 NEWS.org        |  2 ++
 compat-29.el    | 31 ++++++++++++++++++-------
 compat-tests.el | 22 ++++++++++++++----
 compat.texi     | 72 +++++++++++++++++++++++++++++++++++++++++++++++++--------
 4 files changed, 105 insertions(+), 22 deletions(-)

diff --git a/NEWS.org b/NEWS.org
index 530759cd63..7532f7cb71 100644
--- a/NEWS.org
+++ b/NEWS.org
@@ -3,6 +3,8 @@
 * Development
 
 - compat-27: Drop obsolete ~compat-call dired-get-marked-files~.
+- compat-29: Add ~with-restriction~ and ~without-restriction~.
+- compat-29: Drop ~with-narrowing~.
 
 * Release of "Compat" Version 29.1.3.4
 
diff --git a/compat-29.el b/compat-29.el
index 9cf4a76981..d394f0934c 100644
--- a/compat-29.el
+++ b/compat-29.el
@@ -294,22 +294,37 @@ in order to restore the state of the local variables set 
via this macro.
   "Delete the current line."
   (delete-region (pos-bol) (pos-bol 2)))
 
-(compat-defmacro with-narrowing (start end &rest rest) ;; 
<compat-tests:with-narrowing>
+(compat-defmacro with-restriction (start end &rest rest) ;; 
<compat-tests:with-restriction>
   "Execute BODY with restrictions set to START and END.
 
 The current restrictions, if any, are restored upon return.
 
-With the optional :locked TAG argument, inside BODY,
-`narrow-to-region' and `widen' can be used only within the START
-and END limits, unless the restrictions are unlocked by calling
-`narrowing-unlock' with TAG.  See `narrowing-lock' for a more
-detailed description.
+When the optional :label LABEL argument is present, in which
+LABEL is a symbol, inside BODY, `narrow-to-region' and `widen'
+can be used only within the START and END limits.  To gain access
+to other portions of the buffer, use `without-restriction' with the
+same LABEL argument.
 
-\(fn START END [:locked TAG] BODY)"
+\(fn START END [:label LABEL] BODY)"
   `(save-restriction
      (narrow-to-region ,start ,end)
      ;; Locking is ignored
-     ,@(if (eq (car rest) :locked) (cddr rest) rest)))
+     ,@(if (eq (car rest) :label) (cddr rest) rest)))
+
+(compat-defmacro without-restriction (&rest rest) ;; 
<compat-tests:without-restriction>
+  "Execute BODY without restrictions.
+
+The current restrictions, if any, are restored upon return.
+
+When the optional :label LABEL argument is present, the
+restrictions set by `with-restriction' with the same LABEL argument
+are lifted.
+
+\(fn [:label LABEL] BODY)"
+  `(save-restriction
+     (widen)
+     ;; Locking is ignored
+     ,@(if (eq (car rest) :label) (cddr rest) rest)))
 
 (compat-defmacro with-memoization (place &rest code) ;; 
<compat-tests:with-memoization>
   "Return the value of CODE and stash it in PLACE.
diff --git a/compat-tests.el b/compat-tests.el
index 8ea2ce89b7..ba6cec4263 100644
--- a/compat-tests.el
+++ b/compat-tests.el
@@ -237,16 +237,30 @@
     (should-equal 'h (get-text-property 2 'help-echo))
     (should-equal 'h (get-text-property 6 'help-echo))))
 
-(ert-deftest with-narrowing ()
+  ;; TODO reenable if Emacs 29 nightly builds are updated
+(compat-tests--if (< emacs-major-version 29) (progn
+(ert-deftest with-restriction ()
   (with-temp-buffer
     (insert "abc")
-    (with-narrowing 2 3 :locked 'foo
+    (with-restriction 2 3 :label 'foo
       (should-equal "b" (buffer-string)))
     (should-equal "abc" (buffer-string))
-    (with-narrowing 2 3
-                    (should-equal "b" (buffer-string)))
+    (with-restriction 2 3
+      (should-equal "b" (buffer-string)))
     (should-equal "abc" (buffer-string))))
 
+(ert-deftest without-restriction ()
+  (with-temp-buffer
+    (insert "abc")
+    (narrow-to-region 2 3)
+    (without-restriction :label 'foo
+      (should-equal "abc" (buffer-string)))
+    (should-equal "b" (buffer-string))
+    (without-restriction
+      (should-equal "abc" (buffer-string)))
+    (should-equal "b" (buffer-string))))
+))
+
 (ert-deftest with-memoization ()
   (let ((x (cons nil nil)) y computed)
     (with-memoization (car x)
diff --git a/compat.texi b/compat.texi
index a15b3bd5fb..521ca1102b 100644
--- a/compat.texi
+++ b/compat.texi
@@ -2338,16 +2338,68 @@ evaluated and then stashed in @var{place}.  If 
@var{place}'s value is
 non-@code{nil}, return that value instead of evaluating @var{code}.
 @end defmac
 
-@c based on lisp/subr.el
-@defmac with-narrowing start end [:locked tag] &rest body
-Execute @var{body} with restrictions set to @var{start} and @var{end}.
-The current restrictions, if any, are restored upon return.  With the
-optional :locked @var{tag} argument, inside @var{tag},
-@code{narrow-to-region} and @code{widen} can be used only within the
-@var{start} and @var{end} limits, unless the restrictions are unlocked
-by calling @code{narrowing-unlock} with @var{tag}.  See
-@code{narrowing-lock} for a more detailed description.
-@end defmac
+@c copied from lispref/positions.texi
+@defspec with-restriction start end [:label label] body
+This special form saves the current bounds of the accessible portion
+of the buffer, sets the accessible portion to start at @var{start} and
+end at @var{end}, evaluates the @var{body} forms, and restores the
+saved bounds.  In that case it is equivalent to
+
+@example
+(save-restriction
+  (narrow-to-region start end)
+  body)
+@end example
+
+@cindex labeled narrowing
+When the optional argument @var{label}, a symbol, is present, the
+narrowing is @dfn{labeled}.  A labeled narrowing differs from a
+non-labeled one in several ways:
+
+@itemize @bullet
+@item
+During the evaluation of the @var{body} form, @code{narrow-to-region}
+and @code{widen} can be used only within the @var{start} and @var{end}
+limits.
+
+@item
+To lift the restriction introduced by @code{with-restriction} and gain
+access to other portions of the buffer, use @code{without-restriction}
+with the same @var{label} argument.  (Another way to gain access to
+other portions of the buffer is to use an indirect buffer
+(@pxref{Indirect Buffers,,,elisp}).)
+
+@item
+Labeled narrowings can be nested.
+
+@item
+Labeled narrowings can only be used in Lisp programs: they are never
+visible on display, and never interfere with narrowings set by the
+user.
+@end itemize
+
+If you use @code{with-restriction} with the optional @var{label}
+argument, we recommend documenting the @var{label} in the doc strings
+of the functions which use it, so that other Lisp programs your code
+calls could lift the labeled narrowing if and when it needs.
+@end defspec
+
+@c copied from lispref/positions.texi
+@defspec without-restriction [:label label] body
+This special form saves the current bounds of the accessible portion
+of the buffer, widens the buffer, evaluates the @var{body} forms, and
+restores the saved bounds.  In that case it is equivalent to
+
+@example
+(save-restriction
+  (widen)
+  body)
+@end example
+
+When the optional argument @var{label} is present, the narrowing set
+by @code{with-restriction} with the same @var{label} argument is
+lifted.
+@end defspec
 
 @c copied from lispref/positions.texi
 @defun pos-bol &optional count

Reply via email to