简体   繁体   English

如何在emacs中修复“regexp matcher中的堆栈溢出”

[英]How to fix “stack overflow in regexp matcher” in emacs

I'm a big fan of Emacs, and use it a lot, especially while programming and debugging (using gud) (C/C++). 我是Emacs的忠实粉丝,并且经常使用它,特别是在编程和调试时(使用gud)(C / C ++)。

Recently I had to debug a program (rather simple but that compute on a lot of data (Graph Theory)), but I had a rather annoying problem. 最近我不得不调试一个程序(相当简单,但计算大量的数据(图论)),但我有一个相当烦人的问题。 During the execution step by step of the program, I get the following error: 在程序执行过程中,我收到以下错误:

error in process filter: Stack overflow in regexp matcher

I made some research to find out what it was, and I found out this post: Debugging in emacs (with gud) often results in stack overflow error . 我做了一些研究以找出它是什么,我发现了这篇文章: 在emacs中调试(使用gud)经常导致堆栈溢出错误

So as I understand it, there is a problem with the regexp matcher and the fact that some things in my program are simply too long? 据我了解,正则表达式匹配器存在问题,而且程序中的某些内容太长了? (I do have unusually long function name with a lot of parameters and I also use unusually big container.) (我确实有很多参数的异常长的函数名称,我也使用异常大的容器。)

I'd really like to fix this, but I don't know anything about debugging Emacs Lisp, is there anyone to help me ? 我真的想解决这个问题,但我对调试Emacs Lisp一无所知,有没有人帮我?

Here is the output I get from Emacs internal debbuger : http://pastebin.com/5CKe74e6 这是我从Emacs内部debbuger获得的输出: http ://pastebin.com/5CKe74e6

I should also point out, that I use a personalized version of Emacs Prelude. 我还应该指出,我使用的是个性化版本的Emacs Prelude。

The underlying problem is that a regular expression (regexp) contains too many alternatives, and when applied to a (typically long) text it fails to match whatever it tried to match. 潜在的问题是正则表达式(regexp)包含太多的替代方案,并且当应用于(通常很长的)文本时,它无法匹配它试图匹配的任何内容。

In your case it's the regexp: 在你的情况下,它是正则表达式:

"\\([[:alnum:]-_]+\\)=\\({\\|\\[\\|\"\"\\|\"\\(?:[^\\\"]\\|\\\\.\\)*\"\\)"

Which is used by the function gdb-jsonify-buffer . gdb-jsonify-buffer函数使用。

It looks like this regexp tries to match assignments. 看起来这个正则表达式尝试匹配分配。 Basically, it matches a variable to the left of an = and (part of) an expression to the right. 基本上,它匹配一个变量到左边的=和(部分)一个表达式到右边。 One of the things the regexp seems to match is a string, with containing escaped quotes -- this is always a warning sign as Emacs provides far better methods for parsing strings. regexp似乎匹配的一个东西是一个包含转义引号的字符串 - 这总是一个警告标志,因为Emacs提供了更好的解析字符串的方法。

The problem can originate from the fact that this regexp is wrong (so that it matches a lot more than your string), that you have a malformed string, or that your program simply contains a really large string. 问题可能源于这个正则表达式错误(因此它比你的字符串更多匹配),你有一个格式错误的字符串,或者你的程序只包含一个非常大的字符串。

I would suggest that you file a bug report to the maintainer of that package. 我建议您向该软件包的维护者提交错误报告。 Make sure you include the text that caused the error to be triggered. 确保包含导致错误被触发的文本。

Alternatively, you could make an attempt at fixing this yourself. 或者,您可以尝试自己修复此问题。 I would suggest that you replace the complex regexp with a simpler regexp that find the beginning of a string. 我建议您使用更简单的正则表达式替换复杂的正则表达式,以找到字符串的开头。 You could then use, for example, (forward-sexp) to find the end of the string. 然后,您可以使用(forward-sexp)来查找字符串的结尾。

I was also having this problem, so I used Lindydancer's suggestion of converting the regexp on the string literal to use (forward-sexp), and it's been working fine for me. 我也遇到了这个问题,所以我使用了Lindydancer建议将字符串文字上的正则表达式转换为使用(forward-sexp),并且它对我来说一直很好。

I've posted the patch: 我发布了补丁:

http://lists.gnu.org/archive/html/bug-gnu-emacs/2017-12/msg00968.html http://lists.gnu.org/archive/html/bug-gnu-emacs/2017-12/msg00968.html

so hopefully it will get merged at some point. 所以希望它会在某个时候合并。 In the meantime, you can use this for gdb-jsonify-buffer: 在此期间,您可以将此用于gdb-jsonify-buffer:


(defun gdb-jsonify-buffer (&optional fix-key fix-list)
  "Prepare GDB/MI output in current buffer for parsing with `json-read'.

Field names are wrapped in double quotes and equal signs are
replaced with semicolons.

If FIX-KEY is non-nil, strip all \"FIX-KEY=\" occurrences from
partial output.  This is used to get rid of useless keys in lists
in MI messages, e.g.: [key=.., key=..].  -stack-list-frames and
-break-info are examples of MI commands which issue such
responses.

If FIX-LIST is non-nil, \"FIX-LIST={..}\" is replaced with
\"FIX-LIST=[..]\" prior to parsing. This is used to fix broken
-break-info output when it contains breakpoint script field
incompatible with GDB/MI output syntax.

If `default-directory' is remote, full file names are adapted accordingly."
  (save-excursion
    (let ((remote (file-remote-p default-directory)))
      (when remote
        (goto-char (point-min))
        (while (re-search-forward "[\\[,]fullname=\"\\(.+\\)\"" nil t)
          (replace-match (concat remote "\\1") nil nil nil 1))))
    (goto-char (point-min))
    (when fix-key
      (save-excursion
        (while (re-search-forward (concat "[\\[,]\\(" fix-key "=\\)") nil t)
          (replace-match "" nil nil nil 1))))
    (when fix-list
      (save-excursion
        ;; Find positions of braces which enclose broken list
        (while (re-search-forward (concat fix-list "={\"") nil t)
          (let ((p1 (goto-char (- (point) 2)))
                (p2 (progn (forward-sexp)
                           (1- (point)))))
            ;; Replace braces with brackets
            (save-excursion
              (goto-char p1)
              (delete-char 1)
              (insert "[")
              (goto-char p2)
              (delete-char 1)
              (insert "]"))))))
    (goto-char (point-min))
    (insert "{")
    (let ((re (concat "\\([[:alnum:]-_]+\\)=")))
      (while (re-search-forward re nil t)
        (replace-match "\"\\1\":" nil nil)
        (if (eq (char-after) ?\") (forward-sexp) (forward-char))))
    (goto-char (point-max))
    (insert "}")))

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM