emacs-diffs
[Top][All Lists]
Advanced

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

emacs-29 671abd0cc40 4/7: Merge branch 'emacs-29' of git.sv.gnu.org:/srv


From: Eli Zaretskii
Subject: emacs-29 671abd0cc40 4/7: Merge branch 'emacs-29' of git.sv.gnu.org:/srv/git/emacs into emacs-29
Date: Mon, 10 Apr 2023 02:23:54 -0400 (EDT)

branch: emacs-29
commit 671abd0cc406ec45898fdc2d27d09ce449023540
Merge: 4bc678ec9f4 db8f207e52f
Author: Eli Zaretskii <eliz@gnu.org>
Commit: Eli Zaretskii <eliz@gnu.org>

    Merge branch 'emacs-29' of git.sv.gnu.org:/srv/git/emacs into emacs-29
    
    Pull in latest changes.
---
 doc/lispref/windows.texi                           |   2 +-
 lisp/progmodes/c-ts-mode.el                        |  17 ++
 lisp/progmodes/project.el                          |   5 +-
 .../lisp/progmodes/c-ts-mode-resources/indent.erts |  14 ++
 test/lisp/progmodes/eglot-tests.el                 | 197 +++++++++------------
 5 files changed, 121 insertions(+), 114 deletions(-)

diff --git a/doc/lispref/windows.texi b/doc/lispref/windows.texi
index 01ac6fb901a..0196ed0e813 100644
--- a/doc/lispref/windows.texi
+++ b/doc/lispref/windows.texi
@@ -3216,7 +3216,7 @@ any window it creates as dedicated to its buffer 
(@pxref{Dedicated
 Windows}).  It does that by calling @code{set-window-dedicated-p} with
 the chosen window as first argument and the entry's value as second.
 Side windows are by default dedicated with the value @code{side}
-((@pxref{Side Window Options and Functions}).
+(@pxref{Side Window Options and Functions}).
 
 @vindex preserve-size@r{, a buffer display action alist entry}
 @item preserve-size
diff --git a/lisp/progmodes/c-ts-mode.el b/lisp/progmodes/c-ts-mode.el
index 981c7766375..83e89c3a335 100644
--- a/lisp/progmodes/c-ts-mode.el
+++ b/lisp/progmodes/c-ts-mode.el
@@ -859,6 +859,18 @@ the semicolon.  This function skips the semicolon."
     (goto-char (match-end 0)))
   (treesit-default-defun-skipper))
 
+(defun c-ts-base--before-indent (args)
+  (pcase-let ((`(,node ,parent ,bol) args))
+    (when (null node)
+      (let ((smallest-node (treesit-node-at (point))))
+        ;; "Virtual" closer curly added by the
+        ;; parser's error recovery.
+        (when (and (equal (treesit-node-type smallest-node) "}")
+                   (equal (treesit-node-end smallest-node)
+                          (treesit-node-start smallest-node)))
+          (setq parent (treesit-node-parent smallest-node)))))
+    (list node parent bol)))
+
 (defun c-ts-mode-indent-defun ()
   "Indent the current top-level declaration syntactically.
 
@@ -904,6 +916,11 @@ the semicolon.  This function skips the semicolon."
   ;; function_definitions, so we need to find the top-level node.
   (setq-local treesit-defun-prefer-top-level t)
 
+  ;; When the code is in incomplete state, try to make a better guess
+  ;; about which node to indent against.
+  (add-function :filter-args (local 'treesit-indent-function)
+                #'c-ts-base--before-indent)
+
   ;; Indent.
   (when (eq c-ts-mode-indent-style 'linux)
     (setq-local indent-tabs-mode t))
diff --git a/lisp/progmodes/project.el b/lisp/progmodes/project.el
index 11228226592..a18b918db62 100644
--- a/lisp/progmodes/project.el
+++ b/lisp/progmodes/project.el
@@ -1216,7 +1216,10 @@ To continue searching for the next match, use the
 command \\[fileloop-continue]."
   (interactive "sSearch (regexp): ")
   (fileloop-initialize-search
-   regexp (project-files (project-current t)) 'default)
+   regexp
+   ;; XXX: See the comment in project-query-replace-regexp.
+   (cl-delete-if-not #'file-regular-p (project-files (project-current t)))
+   'default)
   (fileloop-continue))
 
 ;;;###autoload
diff --git a/test/lisp/progmodes/c-ts-mode-resources/indent.erts 
b/test/lisp/progmodes/c-ts-mode-resources/indent.erts
index 5cdefe2122c..221b3d809af 100644
--- a/test/lisp/progmodes/c-ts-mode-resources/indent.erts
+++ b/test/lisp/progmodes/c-ts-mode-resources/indent.erts
@@ -464,3 +464,17 @@ main (void)
   |
 }
 =-=-=
+
+Name: Empty Line (Block Start)
+
+=-=
+int
+main (void)
+{
+|
+=-=
+int
+main (void)
+{
+  |
+=-=-=
diff --git a/test/lisp/progmodes/eglot-tests.el 
b/test/lisp/progmodes/eglot-tests.el
index 2388cf9ef51..984c1bf9916 100644
--- a/test/lisp/progmodes/eglot-tests.el
+++ b/test/lisp/progmodes/eglot-tests.el
@@ -50,7 +50,6 @@
 (require 'tramp) ; must be prior ert-x
 (require 'ert-x) ; ert-simulate-command
 (require 'edebug)
-(require 'python) ; some tests use pylsp
 (require 'cc-mode) ; c-mode-hook
 (require 'company nil t)
 (require 'yasnippet nil t)
@@ -119,8 +118,6 @@ then restored."
                    ,(format "HOME=%s"
                             (expand-file-name (format "~%s" 
(user-login-name)))))
                  process-environment))
-               ;; Prevent "Can't guess python-indent-offset ..." messages.
-               (python-indent-guess-indent-offset-verbose . nil)
                (eglot-server-initialized-hook
                 (lambda (server) (push server new-servers))))
           (setq created-files (mapcan #'eglot--make-file-or-dir file-specs))
@@ -533,90 +530,101 @@ Pass TIMEOUT to `eglot--with-timeout'."
       (should (equal (buffer-string)
                      "int bar() {return 42;} int main() {return bar();}")))))
 
+(defun eglot--wait-for-clangd ()
+  (eglot--sniffing (:server-notifications s-notifs)
+    (should (eglot--tests-connect))
+    (eglot--wait-for (s-notifs 20) (&key method &allow-other-keys)
+      (string= method "textDocument/publishDiagnostics"))))
+
 (ert-deftest eglot-test-basic-completions ()
-  "Test basic autocompletion in a python LSP."
-  (skip-unless (executable-find "pylsp"))
+  "Test basic autocompletion in a clangd LSP."
+  (skip-unless (executable-find "clangd"))
   (eglot--with-fixture
-      `(("project" . (("something.py" . "import sys\nsys.exi"))))
+      `(("project" . (("coiso.c" . "#include <stdio.h>\nint main () {fprin"))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
-      (should (eglot--tests-connect))
+        (eglot--find-file-noselect "project/coiso.c")
+      (eglot--sniffing (:server-notifications s-notifs)
+        (eglot--wait-for-clangd)
+        (eglot--wait-for (s-notifs 20) (&key method &allow-other-keys)
+          (string= method "textDocument/publishDiagnostics")))
       (goto-char (point-max))
       (completion-at-point)
-      (should (looking-back "sys.exit")))))
+      (message (buffer-string))
+      (should (looking-back "fprintf.?")))))
 
 (ert-deftest eglot-test-non-unique-completions ()
   "Test completion resulting in 'Complete, but not unique'."
-  (skip-unless (executable-find "pylsp"))
+  (skip-unless (executable-find "clangd"))
   (eglot--with-fixture
-      '(("project" . (("something.py" . "foo=1\nfoobar=2\nfoo"))))
+      `(("project" . (("coiso.c" .
+                       ,(concat "int foo; int fooey;"
+                                "int main() {foo")))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
-      (should (eglot--tests-connect))
+        (eglot--find-file-noselect "project/coiso.c")
+      (eglot--wait-for-clangd)
       (goto-char (point-max))
-      (completion-at-point))
-    ;; FIXME: `current-message' doesn't work here :-(
+      (completion-at-point)
+      ;; FIXME: `current-message' doesn't work here :-(
     (with-current-buffer (messages-buffer)
       (save-excursion
         (goto-char (point-max))
         (forward-line -1)
-        (should (looking-at "Complete, but not unique"))))))
+        (should (looking-at "Complete, but not unique")))))))
 
 (ert-deftest eglot-test-basic-xref ()
-  "Test basic xref functionality in a python LSP."
-  (skip-unless (executable-find "pylsp"))
+  "Test basic xref functionality in a clangd LSP."
+  (skip-unless (executable-find "clangd"))
   (eglot--with-fixture
-      `(("project" . (("something.py" . "def foo(): pass\ndef bar(): foo()"))))
+      `(("project" . (("coiso.c" .
+                       ,(concat "int foo=42; int fooey;"
+                                "int main() {foo=82;}")))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
+        (eglot--find-file-noselect "project/coiso.c")
       (should (eglot--tests-connect))
-      (search-forward "bar(): f")
+      (search-forward "{foo")
       (call-interactively 'xref-find-definitions)
-      (should (looking-at "foo(): pass")))))
+      (should (looking-at "foo=42")))))
 
-(defvar eglot--test-python-buffer
+(defvar eglot--test-c-buffer
   "\
-def foobarquux(a, b, c=True): pass
-def foobazquuz(d, e, f): pass
+void foobarquux(int a, int b, int c){};
+void foobazquuz(int a, int b, int f){};
+int main() {
 ")
 
 (declare-function yas-minor-mode nil)
 
 (ert-deftest eglot-test-snippet-completions ()
-  "Test simple snippet completion in a python LSP."
-  (skip-unless (and (executable-find "pylsp")
+  "Test simple snippet completion in a clangd LSP."
+  (skip-unless (and (executable-find "clangd")
                     (functionp 'yas-minor-mode)))
   (eglot--with-fixture
-      `(("project" . (("something.py" . ,eglot--test-python-buffer))))
+      `(("project" . (("coiso.c" . ,eglot--test-c-buffer))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
+        (eglot--find-file-noselect "project/coiso.c")
       (yas-minor-mode 1)
-      (let ((eglot-workspace-configuration
-             `((:pylsp . (:plugins (:jedi_completion (:include_params t)))))))
-        (should (eglot--tests-connect)))
+      (eglot--wait-for-clangd)
       (goto-char (point-max))
       (insert "foobar")
       (completion-at-point)
       (should (looking-back "foobarquux("))
-      (should (looking-at "a, b)")))))
+      (should (looking-at "int a, int b, int c)")))))
 
 (defvar company-candidates)
 (declare-function company-mode nil)
 (declare-function company-complete nil)
 
 (ert-deftest eglot-test-snippet-completions-with-company ()
-  "Test simple snippet completion in a python LSP."
-  (skip-unless (and (executable-find "pylsp")
+  "Test simple snippet completion in a clangd LSP."
+  (skip-unless (and (executable-find "clangd")
                     (functionp 'yas-minor-mode)
                     (functionp 'company-complete)))
   (eglot--with-fixture
-      `(("project" . (("something.py" . ,eglot--test-python-buffer))))
+      `(("project" . (("coiso.c" . ,eglot--test-c-buffer))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
+        (eglot--find-file-noselect "project/coiso.c")
       (yas-minor-mode 1)
-      (let ((eglot-workspace-configuration
-             `((:pylsp . (:plugins (:jedi_completion (:include_params t)))))))
-        (should (eglot--tests-connect)))
+      (eglot--wait-for-clangd)
       (goto-char (point-max))
       (insert "foo")
       (company-mode)
@@ -624,98 +632,63 @@ def foobazquuz(d, e, f): pass
       (should (looking-back "fooba"))
       (should (= 2 (length company-candidates)))
       ;; this last one is brittle, since there it is possible that
-      ;; pylsp will change the representation of this candidate
-      (should (member "foobazquuz(d, e, f)" company-candidates)))))
+      ;; clangd will change the representation of this candidate
+      (should (member "foobazquuz(int a, int b, int f)" company-candidates)))))
 
 (ert-deftest eglot-test-eldoc-after-completions ()
-  "Test documentation echo in a python LSP."
-  (skip-unless (executable-find "pylsp"))
+  "Test documentation echo in a clangd LSP."
+  (skip-unless (executable-find "clangd"))
   (eglot--with-fixture
-      `(("project" . (("something.py" . "import sys\nsys.exi"))))
+      `(("project" . (("coiso.c" . "#include <stdio.h>\nint main () {fprin"))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
-      (should (eglot--tests-connect))
+        (eglot--find-file-noselect "project/coiso.c")
+      (eglot--wait-for-clangd)
       (goto-char (point-max))
       (completion-at-point)
-      (should (looking-back "sys.exit"))
-      (should (string-match "^exit" (eglot--tests-force-full-eldoc))))))
+      (message (buffer-string))
+      (should (looking-back "fprintf(?"))
+      (unless (= (char-before) ?\() (insert "()") (backward-char))
+      (eglot--signal-textDocument/didChange)
+      (should (string-match "^fprintf" (eglot--tests-force-full-eldoc))))))
 
 (ert-deftest eglot-test-multiline-eldoc ()
-  "Test if suitable amount of lines of hover info are shown."
-  (skip-unless (executable-find "pylsp"))
+  "Test Eldoc documentation from multiple osurces."
+  (skip-unless (executable-find "clangd"))
   (eglot--with-fixture
-      `(("project" . (("hover-first.py" . "from datetime import datetime"))))
+      `(("project" . (("coiso.c" .
+                       "#include <stdio.h>\nint main () {fprintf(blergh);}"))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/hover-first.py")
-      (should (eglot--tests-connect))
-      (goto-char (point-max))
-      ;; one-line
-      (let* ((eldoc-echo-area-use-multiline-p t)
-             (captured-message (eglot--tests-force-full-eldoc)))
-        (should (string-match "datetim" captured-message))
+        (eglot--find-file-noselect "project/coiso.c")
+      (search-forward "fprintf(ble")
+      (eglot--wait-for-clangd)
+      (flymake-start nil t) ;; thing brings in the "unknown identifier blergh"
+      (let* ((captured-message (eglot--tests-force-full-eldoc)))
+        ;; check for signature and error message in the result
+        (should (string-match "fprintf" captured-message))
+        (should (string-match "blergh" captured-message))
         (should (cl-find ?\n captured-message))))))
 
-(ert-deftest eglot-test-single-line-eldoc ()
-  "Test if suitable amount of lines of hover info are shown."
-  (skip-unless (executable-find "pylsp"))
-  (eglot--with-fixture
-      `(("project" . (("hover-first.py" . "from datetime import datetime"))))
-    (with-current-buffer
-        (eglot--find-file-noselect "project/hover-first.py")
-      (should (eglot--tests-connect))
-      (goto-char (point-max))
-      ;; one-line
-      (let* ((eldoc-echo-area-use-multiline-p nil)
-             (captured-message (eglot--tests-force-full-eldoc)))
-        (should (string-match "datetim" captured-message))
-        (should (not (cl-find ?\n eldoc-last-message)))))))
-
-(ert-deftest eglot-test-python-autopep-formatting ()
-  "Test formatting in the pylsp python LSP.
-pylsp prefers autopep over yafp, despite its README stating the contrary."
+(ert-deftest eglot-test-formatting ()
+  "Test formatting in the clangd server."
   ;; Beware, default autopep rules can change over time, which may
   ;; affect this test.
-  (skip-unless (and (executable-find "pylsp")
-                    (executable-find "autopep8")))
-  (eglot--with-fixture
-      `(("project" . (("something.py" . "def a():pass\n\ndef b():pass"))))
-    (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
-      (should (eglot--tests-connect))
-      ;; Try to format just the second line
-      (search-forward "b():pa")
-      (eglot-format (line-beginning-position) (line-end-position))
-      (should (looking-at "ss"))
-      (should
-       (or (string= (buffer-string) "def a():pass\n\n\ndef b(): pass\n")
-           ;; autopep8 2.0.0 (pycodestyle: 2.9.1)
-           (string= (buffer-string) "def a():pass\n\ndef b(): pass")))
-      ;; now format the whole buffer
-      (eglot-format-buffer)
-      (should
-       (string= (buffer-string) "def a(): pass\n\n\ndef b(): pass\n")))))
-
-(ert-deftest eglot-test-python-yapf-formatting ()
-  "Test formatting in the pylsp python LSP."
-  (skip-unless (and (executable-find "pylsp")
-                    (not (executable-find "autopep8"))
-                    (or (executable-find "yapf")
-                        (executable-find "yapf3"))))
+  (skip-unless (executable-find "clangd"))
   (eglot--with-fixture
-      `(("project" . (("something.py" . "def a():pass\ndef b():pass"))))
+      `(("project" . (("coiso.c" . ,(concat "#include <stdio.h>\n"
+                                            "int main(){fprintf(blergh);}"
+                                            "int ble{\n\nreturn 0;}")))))
     (with-current-buffer
-        (eglot--find-file-noselect "project/something.py")
-      (should (eglot--tests-connect))
+        (eglot--find-file-noselect "project/coiso.c")
+      (eglot--wait-for-clangd)
+      (forward-line)
       ;; Try to format just the second line
-      (search-forward "b():pa")
       (eglot-format (line-beginning-position) (line-end-position))
-      (should (looking-at "ss"))
-      (should
-       (string= (buffer-string) "def a():pass\n\n\ndef b():\n    pass\n"))
-      ;; now format the whole buffer
+      (should (looking-at "int main() { fprintf(blergh); }"))
+      ;; ;; now format the whole buffer
       (eglot-format-buffer)
       (should
-       (string= (buffer-string) "def a():\n    pass\n\n\ndef b():\n    
pass\n")))))
+       (string= (buffer-string)
+                "#include <stdio.h>\nint main() { fprintf(blergh); }\nint ble 
{ return 0; }")))))
 
 (ert-deftest eglot-test-rust-on-type-formatting ()
   "Test textDocument/onTypeFormatting against rust-analyzer."



reply via email to

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