emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

master 66cbe8b: CC Mode: Fix bug #40052, where a very large macro was to


From: Alan Mackenzie
Subject: master 66cbe8b: CC Mode: Fix bug #40052, where a very large macro was too slow in scrolling
Date: Fri, 15 May 2020 15:26:57 -0400 (EDT)

branch: master
commit 66cbe8b946bf83ab19c0d9a7b9fc03e951ffd5b6
Author: Alan Mackenzie <address@hidden>
Commit: Alan Mackenzie <address@hidden>

    CC Mode: Fix bug #40052, where a very large macro was too slow in scrolling
    
    * lisp/progmodes/cc-engine.el (c-end-of-macro): Fix faulty cache handling,
    where the upper bound of c-macro-cache was never being set.
    (c-forward-comment-minus-1): New macro which terminates unwanted indefinite
    backward searching with lots of escaped newlines in 
c-backward-single-comment.
    (c-backward-single-comment, c-backward-comments): Use the new macro above.
    
    * lisp/progmodes/cc-mode.el (c-before-change-check-unbalanced-strings)
    (c-after-change-mark-abnormal-strings, c-after-change-escape-NL-in-string):
    Optimize three regexps by using shy groups, thus preventing regexp stack
    overflow while handling the large C Macro.
---
 lisp/progmodes/cc-engine.el | 23 +++++++++++++++++++----
 lisp/progmodes/cc-mode.el   |  8 ++++----
 2 files changed, 23 insertions(+), 8 deletions(-)

diff --git a/lisp/progmodes/cc-engine.el b/lisp/progmodes/cc-engine.el
index aa3f7d3..8c8296f 100644
--- a/lisp/progmodes/cc-engine.el
+++ b/lisp/progmodes/cc-engine.el
@@ -405,7 +405,7 @@ comment at the start of cc-engine.el for more info."
          (when (and (car c-macro-cache)
                     (> (point) (car c-macro-cache)) ; in case we have a
                                        ; zero-sized region.
-                    (not (eq (char-before (1- (point))) ?\\)))
+                    (not lim))
            (setcdr c-macro-cache (point))
            (setq c-macro-cache-syntactic nil)))))))
 
@@ -1642,6 +1642,21 @@ comment at the start of cc-engine.el for more info."
            (forward-char 2)
            t))))
 
+(defmacro c-forward-comment-minus-1 ()
+  "Call (forward-comment -1), taking care of escaped newlines.
+Return the result of `forward-comment' if it gets called, nil otherwise."
+  `(if (not comment-end-can-be-escaped)
+       (forward-comment -1)
+     (when (and (< (skip-syntax-backward " >") 0)
+               (eq (char-after) ?\n))
+       (forward-char))
+     (cond
+      ((and (eq (char-before) ?\n)
+           (eq (char-before (1- (point))) ?\\))
+       (backward-char)
+       nil)
+      (t (forward-comment -1)))))
+
 (defun c-backward-single-comment ()
   "Move backward past whitespace and the closest preceding comment, if any.
 Return t if a comment was found, nil otherwise.  In either case, the
@@ -1675,12 +1690,12 @@ This function does not do any hidden buffer changes."
       ;; same line.
       (re-search-forward "\\=\\s *[\n\r]" start t)
 
-      (if (if (forward-comment -1)
+      (if (if (c-forward-comment-minus-1)
              (if (eolp)
                  ;; If forward-comment above succeeded and we're at eol
                  ;; then the newline we moved over above didn't end a
                  ;; line comment, so we give it another go.
-                 (forward-comment -1)
+                 (c-forward-comment-minus-1)
                t))
 
          ;; Emacs <= 20 and XEmacs move back over the closer of a
@@ -1709,7 +1724,7 @@ comment at the start of cc-engine.el for more info."
 
            (if (let (moved-comment)
                  (while
-                     (and (not (setq moved-comment (forward-comment -1)))
+                     (and (not (setq moved-comment 
(c-forward-comment-minus-1)))
                      ;; Cope specifically with ^M^J here -
                      ;; forward-comment sometimes gets stuck after ^Ms,
                      ;; sometimes after ^M^J.
diff --git a/lisp/progmodes/cc-mode.el b/lisp/progmodes/cc-mode.el
index e3a924e..d822788 100644
--- a/lisp/progmodes/cc-mode.el
+++ b/lisp/progmodes/cc-mode.el
@@ -1431,7 +1431,7 @@ Note that the style variables are always made local to 
the buffer."
 
       ;; Move to end of logical line (as it will be after the change, or as it
       ;; was before unescaping a NL.)
-      (re-search-forward "\\(\\\\\\(.\\|\n\\)\\|[^\\\n\r]\\)*" nil t)
+      (re-search-forward "\\(?:\\\\\\(?:.\\|\n\\)\\|[^\\\n\r]\\)*" nil t)
       ;; We're at an EOLL or point-max.
       (if (equal (c-get-char-property (point) 'syntax-table) '(15))
          (if (memq (char-after) '(?\n ?\r))
@@ -1539,7 +1539,7 @@ Note that the style variables are always made local to 
the buffer."
           (progn
             (goto-char (min (1+ end)   ; 1+, in case a NL has become escaped.
                             (point-max)))
-            (re-search-forward "\\(\\\\\\(.\\|\n\\)\\|[^\\\n\r]\\)*"
+            (re-search-forward "\\(?:\\\\\\(?:.\\|\n\\)\\|[^\\\n\r]\\)*"
                                nil t)
             (point))
           c-new-END))
@@ -1620,8 +1620,8 @@ Note that the style variables are always made local to 
the buffer."
                   (c-beginning-of-macro))))
       (goto-char (1+ end))             ; After the \
       ;; Search forward for EOLL
-      (setq lim (re-search-forward "\\(\\\\\\(.\\|\n\\)\\|[^\\\n\r]\\)*"
-                                  nil t))
+      (setq lim (re-search-forward "\\(?:\\\\\\(?:.\\|\n\\)\\|[^\\\n\r]\\)*"
+                                          nil t))
       (goto-char (1+ end))
       (when (c-search-forward-char-property-with-value-on-char
             'syntax-table '(15) ?\" lim)



reply via email to

[Prev in Thread] Current Thread [Next in Thread]