branch: externals/xr
commit f3b61ef7450afd7726e509509f5b3042af23a051
Author: Mattias Engdegård <matti...@acm.org>
Commit: Mattias Engdegård <matti...@acm.org>

    Fix false negative in empty string repetition check
    
    We forgot to check for non-greedy inner repetitions.
---
 xr-test.el | 14 ++++++++++----
 xr.el      |  4 ++--
 2 files changed, 12 insertions(+), 6 deletions(-)

diff --git a/xr-test.el b/xr-test.el
index 88e68f7..2724e0d 100644
--- a/xr-test.el
+++ b/xr-test.el
@@ -404,16 +404,22 @@
              (xr-lint "[-A-Z][A-Z-][A-Z-a][^-A-Z][]-a][A-Z---.]")
              '((16 .
                 "Literal `-' not first or last in character alternative"))))
-    (should (equal
-             (xr-lint "\\(?:a*b?\\)*\\(c\\|d\\|\\)+\\(^\\|e\\)*\\(?:\\)*")
-             '((10 . "Repetition of expression matching an empty string")
-               (21 . "Repetition of expression matching an empty string"))))
     (should (equal (xr-lint "\\'*\\<?\\(?:$\\)+")
                    '((2 . "Repetition of zero-width assertion")
                      (5 . "Repetition of zero-width assertion")
                      (13 . "Repetition of zero-width assertion"))))
     ))
 
+(ert-deftest xr-lint-repetition-of-empty ()
+  (let ((text-quoting-style 'grave))
+    (should (equal
+             (xr-lint "\\(?:a*b?\\)*\\(c\\|d\\|\\)+\\(^\\|e\\)*\\(?:\\)*")
+             '((10 . "Repetition of expression matching an empty string")
+               (21 . "Repetition of expression matching an empty string"))))
+    (should (equal
+             (xr-lint "\\(?:a*?b??\\)+?")
+             '((12 . "Repetition of expression matching an empty string"))))))
+
 (ert-deftest xr-lint-branch-subsumption ()
   (let ((text-quoting-style 'grave))
     (should (equal (xr-lint "a.cde*f?g\\|g\\|abcdefg")
diff --git a/xr.el b/xr.el
index 03b5f0a..eccbf3f 100644
--- a/xr.el
+++ b/xr.el
@@ -424,13 +424,13 @@ UPPER may be nil, meaning infinity."
 (defun xr--matches-empty-p (rx)
   "Whether RX can match the empty string regardless of context."
   (pcase rx
-    (`(,(or 'seq 'one-or-more 'group) . ,body)
+    (`(,(or 'seq 'one-or-more '+? 'group) . ,body)
      (cl-every #'xr--matches-empty-p body))
     (`(or . ,body)
      (cl-some #'xr--matches-empty-p body))
     (`(group-n ,_ . ,body)
      (cl-every #'xr--matches-empty-p body))
-    (`(,(or 'opt 'zero-or-more) . ,_)
+    (`(,(or 'opt 'zero-or-more ?? '*?) . ,_)
      t)
     (`(repeat ,from ,_ . ,body)
      (or (= from 0)

Reply via email to