unofficial mirror of bug-gnu-emacs@gnu.org 
 help / color / mirror / code / Atom feed
From: Spencer Baugh <sbaugh@janestreet.com>
To: Juri Linkov <juri@linkov.net>
Cc: dmitry@gutov.dev, 68514@debbugs.gnu.org, monnier@iro.umontreal.ca
Subject: bug#68514: 30.0.50; minibuffer-choose-completion + elisp-c-a-p delete next sexp when completing after open paren
Date: Tue, 16 Jan 2024 14:43:35 -0500	[thread overview]
Message-ID: <ierwms9qd20.fsf@janestreet.com> (raw)
In-Reply-To: <86ply1npno.fsf@mail.linkov.net> (Juri Linkov's message of "Tue,  16 Jan 2024 19:39:39 +0200")

[-- Attachment #1: Type: text/plain, Size: 451 bytes --]

Juri Linkov <juri@linkov.net> writes:
>> This is because elisp-completion-at-point returns a completion region
>> covering the entire sexp after the start of the region.  That sexp is
>> "(progn (some) (big) (expression))" in the first case and "a" in the
>> second case.
>
> This is a known bug without a known fix:
> https://debbugs.gnu.org/64903#18

Alright, how about this patch?  Should fix most of the issue without
changing the code too much.


[-- Attachment #2: 0001-Make-elisp-cap-region-cover-a-symbol-not-lists-or-st.patch --]
[-- Type: text/x-patch, Size: 2821 bytes --]

From d76353122ec563eb2d3ca23f96ea67a6843974c5 Mon Sep 17 00:00:00 2001
From: Spencer Baugh <sbaugh@janestreet.com>
Date: Tue, 16 Jan 2024 14:32:21 -0500
Subject: [PATCH] Make elisp-cap region cover a symbol, not lists or strings

elisp-completion-at-point calculates the completion region by running
backward-sexp from (point) and storing that position as the beginning,
then running forward-sexp from the beginning and storing that position
as the end.

elisp-completion-at-point does symbol completion, so the completion
region should only cover a symbol.  Therefore,
elisp-completion-at-point checks whether the beginning of the
completion region (the result from backward-sexp) is a quotation mark
or open paren, which would indicate that the region covers a string or
list, and returns nil in that case.

If point is already at the start of a sexp (e.g. immediately after an
open paren) then backward-sexp will not move point and the beginning
of the completion region would (correctly) be the original point.

forward-sexp, in this case, will move over the next sexp after point
and include it in the completion region, even if it's a string or
list.

That has several bad effects:

- An unrelated next sexp can be deleted by doing completion at the
start of some earlier sexp (bug#64903, bug#68514)

- The completion region can be very large, breaking some completion
styles; if the next sexp is large enough, completion will fail with::
(invalid-regexp "Regular expression too big")

- External completion packages can be broken by this, including corfu:
https://github.com/minad/corfu/issues/350

We fix this by mirroring the check on the character at start of the
region.  We now also check if the character at the end of the
completion region is a quotation mark or close paren, and set the end
of the region equal to the beginning in that case.  This way, we avoid
including a string or list in the completion region, but still allow
completion to proceed.

* lisp/progmodes/elisp-mode.el (elisp-completion-at-point): Avoid
returning a completion region which includes a string or
list. (bug#64903)
---
 lisp/progmodes/elisp-mode.el | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/lisp/progmodes/elisp-mode.el b/lisp/progmodes/elisp-mode.el
index 0ce98ee471c..c9ae92b5680 100644
--- a/lisp/progmodes/elisp-mode.el
+++ b/lisp/progmodes/elisp-mode.el
@@ -668,6 +668,9 @@ elisp-completion-at-point
 		    (goto-char beg)
 		    (forward-sexp 1)
                     (skip-chars-backward "'’")
+                    (when (member (char-syntax (char-before (point)))
+                                  '(?\" ?\)))
+                      (goto-char beg))
 		    (when (>= (point) pos)
 		      (point)))
 		(scan-error pos))))
-- 
2.39.3


  reply	other threads:[~2024-01-16 19:43 UTC|newest]

Thread overview: 13+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2024-01-16 17:06 bug#68514: 30.0.50; minibuffer-choose-completion + elisp-c-a-p delete next sexp when completing after open paren Spencer Baugh
2024-01-16 17:28 ` Dmitry Gutov
2024-01-16 17:39 ` Juri Linkov
2024-01-16 19:43   ` Spencer Baugh [this message]
2024-01-17 16:37     ` Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors
2024-01-17 17:20       ` Spencer Baugh
2024-01-17 17:53         ` Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors
2024-01-17 18:10           ` Spencer Baugh
2024-01-17 19:03             ` Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors
2024-01-18 19:05           ` Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors
2024-01-17 16:42     ` Juri Linkov
2024-01-17 17:22       ` Spencer Baugh
2024-01-17 17:44         ` Juri Linkov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://www.gnu.org/software/emacs/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=ierwms9qd20.fsf@janestreet.com \
    --to=sbaugh@janestreet.com \
    --cc=68514@debbugs.gnu.org \
    --cc=dmitry@gutov.dev \
    --cc=juri@linkov.net \
    --cc=monnier@iro.umontreal.ca \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).