commit 49e021e5be943477329b065fbff76862ea832acc (HEAD, refs/remotes/origin/master) Merge: 682fb19dc32 bd5115e1347 Author: Stefan Kangas Date: Sat Mar 4 06:30:12 2023 +0100 Merge from origin/emacs-29 bd5115e1347 Remove Eglot activation check from find-file-hook adc04ad5247 * src/intervals.c (set_intervals_multibyte_1): Fix bug#61887 b3e930d328e Revert inadvertent change to lisp/icomplete.el in previou... da8e4b6fe43 Revert previous change in go-ts-mode.el 7548446194a Release ERC 5.5 585faf4c173 ; More doc improvements for OClosures 2840895c1ae Don't create GUI frames in batch sessions 452b5ed1030 ; Fix wrong error name in erc-server-908 doc string. 1e9484f2fd1 ; * etc/ERC-NEWS: Mention more deprecations. 119b3a4dba1 Minor copyedits of documentation of OClosures 3a651773d29 Eglot: pay better attention to hints' paddingLeft/Right (... # Conflicts: # etc/NEWS commit 682fb19dc3215dde4b3b0330e5b513e7102c531f Author: Sean Whitton Date: Fri Mar 3 19:17:40 2023 -0700 * lisp/icomplete.el (icomplete-in-buffer): Make into a defcustom. diff --git a/lisp/icomplete.el b/lisp/icomplete.el index 47fdf3e7913..e0b591739ef 100644 --- a/lisp/icomplete.el +++ b/lisp/icomplete.el @@ -137,10 +137,11 @@ icomplete-max-delay-chars "Maximum number of initial chars to apply `icomplete-compute-delay'." :type 'integer) -(defvar icomplete-in-buffer nil +(defcustom icomplete-in-buffer nil "If non-nil, also use Icomplete when completing in non-mini buffers. This affects commands like `completion-in-region', but not commands -that use their own completions setup.") +that use their own completions setup." + :type 'boolean) (defcustom icomplete-minibuffer-setup-hook nil "Icomplete-specific customization of minibuffer setup. commit dff9657c6c039ad35734f1d98e0ccc71b85a1a24 Author: Dmitry Gutov Date: Sat Mar 4 02:37:14 2023 +0200 Redirect eldoc messages to the mode-line when in edebug-mode * lisp/emacs-lisp/eldoc.el (eldoc-minibuffer-message): Redirect eldoc messages to the mode-line when in edebug-mode (bug#56459). (eldoc-minibuffer--cleanup): New function, used in above. diff --git a/lisp/emacs-lisp/eldoc.el b/lisp/emacs-lisp/eldoc.el index 83948ad00d4..74bef264bf1 100644 --- a/lisp/emacs-lisp/eldoc.el +++ b/lisp/emacs-lisp/eldoc.el @@ -296,13 +296,9 @@ eldoc-minibuffer-message This function displays the message produced by formatting ARGS with FORMAT-STRING on the mode line when the current buffer is a minibuffer. Otherwise, it displays the message like `message' would." - (if (minibufferp) + (if (or (bound-and-true-p edebug-mode) (minibufferp)) (progn - (add-hook 'minibuffer-exit-hook - (lambda () (setq eldoc-mode-line-string nil - ;; https://debbugs.gnu.org/16920 - eldoc-last-message nil)) - nil t) + (add-hook 'post-command-hook #'eldoc-minibuffer--cleanup) (with-current-buffer (window-buffer (or (window-in-direction 'above (minibuffer-window)) @@ -321,6 +317,13 @@ eldoc-minibuffer-message (force-mode-line-update))) (apply #'message format-string args))) +(defun eldoc-minibuffer--cleanup () + (unless (or (bound-and-true-p edebug-mode) (minibufferp)) + (setq eldoc-mode-line-string nil + ;; https://debbugs.gnu.org/16920 + eldoc-last-message nil) + (remove-hook 'post-command-hook #'eldoc-minibuffer--cleanup))) + (make-obsolete 'eldoc-message "use `eldoc-documentation-functions' instead." "eldoc-1.1.0") (defun eldoc-message (&optional string) (eldoc--message string)) commit a33d3ae98aa9dbea6c8c2b5baed416acb776488e Author: Dmitry Gutov Date: Sat Mar 4 02:27:35 2023 +0200 Revert "Revert "Don't disable eldoc when doing edebug"" This reverts commit 99df815c153265706edc839b7467fb3ae3b6e1b1. diff --git a/lisp/emacs-lisp/eldoc.el b/lisp/emacs-lisp/eldoc.el index a175edcc671..83948ad00d4 100644 --- a/lisp/emacs-lisp/eldoc.el +++ b/lisp/emacs-lisp/eldoc.el @@ -388,7 +388,6 @@ eldoc-display-message-p (defun eldoc-display-message-no-interference-p () "Return nil if displaying a message would cause interference." (not (or executing-kbd-macro - (bound-and-true-p edebug-active) ;; The following configuration shows "Matches..." in the ;; echo area when point is after a closing bracket, which ;; conflicts with eldoc. commit bd5115e13479b1d81d6aa09efe362ad14d53c3c6 (refs/remotes/origin/emacs-29) Author: João Távora Date: Sat Mar 4 00:09:32 2023 +0000 Remove Eglot activation check from find-file-hook Adding eglot--maybe-activate-editing-mode to find-file-hook isn't really necessary, since it is already in 'after-change-major-mode-hook', and that also runs every time we find a file. This reduces the number of project.el logic that runs every time the user visits a file. * lisp/progmodes/eglot.el (find-file-hook): No need to add eglot--maybe-activate-editing-mode here. diff --git a/lisp/progmodes/eglot.el b/lisp/progmodes/eglot.el index a11ec0e4bbd..c74b13d3380 100644 --- a/lisp/progmodes/eglot.el +++ b/lisp/progmodes/eglot.el @@ -1924,7 +1924,6 @@ eglot--maybe-activate-editing-mode ;; about the buffer. (run-hooks 'eglot-managed-mode-hook)))) -(add-hook 'find-file-hook 'eglot--maybe-activate-editing-mode) (add-hook 'after-change-major-mode-hook 'eglot--maybe-activate-editing-mode) (defun eglot-clear-status (server) commit adc04ad52474113e5a540b33fbefd389b861a89f Author: Stefan Monnier Date: Fri Mar 3 19:13:03 2023 -0500 * src/intervals.c (set_intervals_multibyte_1): Fix bug#61887 When `total_length` is 0 there should be no subtree at all, but `delete_interval` only deletes one interval, so make sure we don't end up with some stale child of `i`. diff --git a/src/intervals.c b/src/intervals.c index 75e37a8c90c..ee976fb1035 100644 --- a/src/intervals.c +++ b/src/intervals.c @@ -2333,6 +2333,9 @@ set_intervals_multibyte_1 (INTERVAL i, bool multi_flag, if (TOTAL_LENGTH (i) == 0) { + /* Delete the whole subtree. */ + i->left = NULL; + i->right = NULL; delete_interval (i); return; } commit b3e930d328e2e9a3da4bf5b6c109928532326c06 Author: João Távora Date: Fri Mar 3 23:36:26 2023 +0000 Revert inadvertent change to lisp/icomplete.el in previous commit The change commit 3a651773d29afb48ac4229cd19e532bd57a4ee2d Author: João Távora Date: Fri Mar 3 13:13:35 2023 +0000 Eglot: pay better attention to hints' paddingLeft/Right (bug#61924) Inadvertently added a line to this file, which shouldn't (yet) bet added. * lisp/icomplete.el (icomplete--vertical-minibuffer-setup): Remove truncate-lines. diff --git a/lisp/icomplete.el b/lisp/icomplete.el index 4f39afb69f4..0adb0e5afeb 100644 --- a/lisp/icomplete.el +++ b/lisp/icomplete.el @@ -661,7 +661,6 @@ icomplete--vertical-minibuffer-setup (setq-local icomplete-hide-common-prefix nil ;; Ask `icomplete-completions' to return enough completions candidates. icomplete-prospects-height 25 - truncate-lines t redisplay-adhoc-scroll-in-resize-mini-windows nil)) ;;;###autoload commit da8e4b6fe43c0cb3c1ca08ac53f2957fe48291f1 Author: Yuan Fu Date: Fri Mar 3 13:59:54 2023 -0800 Revert previous change in go-ts-mode.el Reverts 59365f928565f1be551b1697b9246b00cb87a9b7 and 56cd810b9d1a4d537bee5a2fd954d6e0d346631a. Reverting because the use of treesit-ready-p is very much intentional. * lisp/progmodes/go-ts-mode.el (treesit-ready-p): Revert change. diff --git a/lisp/progmodes/go-ts-mode.el b/lisp/progmodes/go-ts-mode.el index fbe085a2c6c..e8f93d14744 100644 --- a/lisp/progmodes/go-ts-mode.el +++ b/lisp/progmodes/go-ts-mode.el @@ -393,7 +393,7 @@ go-mod-ts-mode (treesit-major-mode-setup))) -(if (treesit-language-available-p 'gomod) +(if (treesit-ready-p 'gomod) (add-to-list 'auto-mode-alist '("/go\\.mod\\'" . go-mod-ts-mode))) (provide 'go-ts-mode) commit 7548446194afdd3cd26851001565294da2732e29 Author: F. Jason Park Date: Mon Feb 13 23:27:50 2023 -0800 Release ERC 5.5 * doc/misc/erc.texi: Update ERCVER to 5.5. * lisp/erc/erc.el: Increment main version header to 5.5. Update Compat version in package-requires header to 29.1.3.4. Update `customize-package-emacs-version-alist' entry by mapping ERC 5.5 to Emacs 29.1. (erc-version): Update value to 5.5. diff --git a/doc/misc/erc.texi b/doc/misc/erc.texi index d5ec0f48e1c..b80affbc954 100644 --- a/doc/misc/erc.texi +++ b/doc/misc/erc.texi @@ -2,7 +2,7 @@ @c %**start of header @setfilename ../../info/erc.info @settitle ERC Manual -@set ERCVER 5.4.1 +@set ERCVER 5.5 @set ERCDIST as distributed with Emacs @value{EMACSVER} @include docstyle.texi @syncodeindex fn cp diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el index d35907a1677..69bdb5d71b1 100644 --- a/lisp/erc/erc.el +++ b/lisp/erc/erc.el @@ -12,8 +12,8 @@ ;; David Edmondson (dme@dme.org) ;; Michael Olson (mwolson@gnu.org) ;; Kelvin White (kwhite@gnu.org) -;; Version: 5.4.1 -;; Package-Requires: ((emacs "27.1") (compat "28.1.2.0")) +;; Version: 5.5 +;; Package-Requires: ((emacs "27.1") (compat "29.1.3.4")) ;; Keywords: IRC, chat, client, Internet ;; URL: https://www.gnu.org/software/emacs/erc.html @@ -71,7 +71,7 @@ (require 'iso8601) (eval-when-compile (require 'subr-x) (require 'url-parse)) -(defconst erc-version "5.4.1" +(defconst erc-version "5.5" "This version of ERC.") (defvar erc-official-location @@ -86,7 +86,8 @@ erc-official-location '(ERC ("5.2" . "22.1") ("5.3" . "23.1") ("5.4" . "28.1") - ("5.4.1" . "29.1"))) + ("5.4.1" . "29.1") + ("5.5" . "29.1"))) (defgroup erc nil "Emacs Internet Relay Chat client." commit 585faf4c173bb9d0a0315dfcfe598d27f82d2bbf Author: Eli Zaretskii Date: Fri Mar 3 21:44:54 2023 +0200 ; More doc improvements for OClosures * doc/lispref/functions.texi (OClosures): * doc/lispref/commands.texi (Using Interactive): * etc/NEWS: Some more docs improvements for OClosures. diff --git a/doc/lispref/commands.texi b/doc/lispref/commands.texi index 6fd9377e1de..20be706bebd 100644 --- a/doc/lispref/commands.texi +++ b/doc/lispref/commands.texi @@ -325,10 +325,10 @@ Using Interactive @defun oclosure-interactive-form function Just like @code{interactive-form}, this function takes a command and returns its interactive form. The difference is that it is a generic -function and it is only called when @var{function} is an OClosure. -The purpose is to make it possible for some OClosure types to compute -their interactive forms dynamically instead of carrying it in one of -their slots. +function and it is only called when @var{function} is an OClosure +(@pxref{OClosures}). The purpose is to make it possible for some +OClosure types to compute their interactive forms dynamically instead +of carrying it in one of their slots. This is used for example for @code{kmacro} functions in order to reduce their memory size, since they all share the same interactive diff --git a/doc/lispref/functions.texi b/doc/lispref/functions.texi index d1459404375..d38f6ef38bc 100644 --- a/doc/lispref/functions.texi +++ b/doc/lispref/functions.texi @@ -1731,6 +1731,11 @@ OClosures it is an OClosure, and @code{nil} otherwise. @end defun +One other function related to OClosures is +@code{oclosure-interactive-form}, which allows some types of OClosures +to compute their interactive forms dynamically. @xref{Using +Interactive, oclosure-interactive-form}. + @node Advising Functions @section Advising Emacs Lisp Functions diff --git a/etc/NEWS b/etc/NEWS index b5e67d47037..189ca590e3f 100644 --- a/etc/NEWS +++ b/etc/NEWS @@ -3231,8 +3231,11 @@ manually if needed, using the new user options 'wallpaper-command' and +++ ** New package 'oclosure'. -This allows the creation of "functions with slots" or "function -objects" via the macros 'oclosure-define' and 'oclosure-lambda'. +This allows the creation of OClosures, which are "functions with +slots" or "function objects" that expose additional information about +themselves. Use the new macros 'oclosure-define' and +'oclosure-lambda' to create OClosures. See the "(elisp) OClosures" +node for more information. +++ *** New generic function 'oclosure-interactive-form'. commit 2840895c1ae4f60c3b225dc1d75854fb09bca259 Author: Jim Porter Date: Tue Feb 28 11:35:21 2023 -0800 Don't create GUI frames in batch sessions This resolves an issue with running test/lisp/server-tests.el when 'DISPLAY' is set: the tests would start the Emacs server in a batch session, and then request a new GUI frame. However, that caused the tests to terminate with SIGIO, since a batch Emacs doesn't set a SIGIO handler. Ref: * lisp/frame.el (make-frame): Always create a terminal frame in batch sessions. diff --git a/lisp/frame.el b/lisp/frame.el index 81383349354..bf984da0d62 100644 --- a/lisp/frame.el +++ b/lisp/frame.el @@ -873,6 +873,11 @@ make-frame (interactive) (let* ((display (cdr (assq 'display parameters))) (w (cond + ;; When running in a batch session, don't create a GUI + ;; frame. (Batch sessions don't set a SIGIO handler on + ;; relevant platforms, so attempting this would terminate + ;; Emacs.) + (noninteractive nil) ((assq 'terminal parameters) (let ((type (terminal-live-p (cdr (assq 'terminal parameters))))) commit 452b5ed1030f9ddb10744db76f23e83d434965e8 Author: F. Jason Park Date: Thu Mar 2 23:37:06 2023 -0800 ; Fix wrong error name in erc-server-908 doc string. * lisp/erc/erc-sasl.el (erc-server-908): Correct well-known name for 908 numeric in doc string. (erc--register-connection): Fold overlong line. diff --git a/lisp/erc/erc-sasl.el b/lisp/erc/erc-sasl.el index ed91f412255..9265691c2d7 100644 --- a/lisp/erc/erc-sasl.el +++ b/lisp/erc/erc-sasl.el @@ -405,7 +405,7 @@ erc-sasl--destroy (erc-sasl--destroy proc)) (define-erc-response-handler (908) - "Handle a RPL_SASLALREADY response." nil + "Handle a RPL_SASLMECHS response." nil (erc-display-message parsed '(notice error) 'active 's908 ?m (alist-get 'mechanism erc-sasl--options) ?s (string-join (cdr (erc-response.command-args parsed)) @@ -426,7 +426,8 @@ erc--register-connection (erc-server-send (if erc-sasl--send-cap-ls "CAP LS" "CAP REQ :sasl")) (let ((erc-session-password (and erc-session-password - (not (eq :password (alist-get 'password erc-sasl--options))) + (not (eq :password + (alist-get 'password erc-sasl--options))) erc-session-password)) (erc-session-username ;; The username may contain a colon or a space commit 1e9484f2fd1d50e28d688d6e151c30b16ab7b6fe Author: F. Jason Park Date: Thu Mar 2 23:33:28 2023 -0800 ; * etc/ERC-NEWS: Mention more deprecations. diff --git a/etc/ERC-NEWS b/etc/ERC-NEWS index d5e256d9d33..434bfab94e9 100644 --- a/etc/ERC-NEWS +++ b/etc/ERC-NEWS @@ -44,8 +44,13 @@ The 'networks' module is now all but required for everyday interactive use. A default member of 'erc-modules' since ERC 5.3, 'networks' has grown increasingly integral to core client operations over the years. From now on, only the most essential operations will be officially -supported in its absence, and users will see a warning upon -entry-point invocation when it's not present. +supported in its absence, and users will see a warning upon invoking +an entry point, like 'erc-tls', when that's the case. + +On a related note, the function 'erc-network' now always returns +non-nil in buffers created by a successfully established IRC +connection, even after that connection has been closed. This was done +to aid the overall effort to improve buffer association. ** Tighter auth-source integration. The days of hit-and-miss auth-source queries are hopefully behind us. @@ -77,12 +82,14 @@ now avoids any hijacking of the active window as well. Beyond this, additional flexibility is now available for controlling the behavior of newly created target buffers during reconnection. +See the option 'erc-reconnect-display' for more. ** Improved handling of multiline prompt input. This means better detection and handling of intervening and trailing blanks when 'erc-send-whitespace-lines' is active. New options have also been added for warning when input spans multiple lines. Although -off by default, new users are encouraged to enable them. +off by default, new users are encouraged to enable them. See options +'erc-inhibit-multiline-input' and 'erc-ask-about-multiline-input'. ** URL handling has improved. Clicking on 'irc://' and 'ircs://' links elsewhere in Emacs now does @@ -91,6 +98,21 @@ users are now prompted to confirm connection parameters prior to lift off. See the new '(erc) Integrations' section in the Info manual for details. +** ERC's major-mode hook now runs slightly later. +The function 'erc-open' now delays running 'erc-mode-hook' until ERC's +prompt and its bounding markers and many essential local variables +have been initialized. Those essentials include the familiar +'erc-default-recipients', 'erc-server-users', and 'erc-network', as +well as the various "session" variables, like 'erc-session-connector'. +ERC activates "local modules" immediately afterward, just before +running 'erc-connect-pre-hook', which is still useful for gaining a +full accounting of what's been set. + +In similar news, 'erc-open' no longer calls 'erc-update-modules'. +However, it still activates modules in a similar fashion, meaning, +among other things, global-module setup still occurs before major-mode +activation (something that's here to stay for compatibility reasons). + ** Miscellaneous behavioral changes impacting the user experience. A bug has been fixed that saw prompts being mangled, doubled, or erased in server buffers upon disconnection. Instead, input prompts @@ -99,58 +121,61 @@ now collapse into an alternate form designated by the option but can be fine-tuned via the repurposed, formerly abandoned option 'erc-hide-prompt'. -Certain commands provided by the 'erc-match' module, such as -'erc-add-keyword', 'erc-add-pal', and others, now optionally ask -whether to 'regexp-quote' the current input. A new option, -'erc-match-quote-when-adding', has been added to allow for retaining -the old behavior, if desired. - -A bug has been fixed affecting users of the Soju bouncer: outgoing -messages during periods of heavy traffic no longer disappear. +Another fix-turned-feature involves certain commands provided by the +'erc-match' module, such as 'erc-add-keyword', 'erc-add-pal', and +others, which now optionally offer to 'regexp-quote' the current +input. The old behavior, if desired, can still be had via the new +option 'erc-match-quote-when-adding'. -Although rare, server passwords containing white space are now handled -correctly. - -** Miscellaneous behavioral changes in the library API. -A number of core macros and other definitions have been moved to a new -file called erc-common.el. This was done to further lessen the -various complications arising from the mutual dependency between 'erc' -and 'erc-backend'. - -ERC now relies on the Compat library from GNU ELPA to supply forward -compatibility shims for users running older versions of Emacs. The -required Compat version resides atop ERC's main library file, in the -'Package-Requires' header. Third-party ERC modules will benefit -automatically from this adoption. - -The function 'erc-network' always returns non-nil in server and target -buffers belonging to a successfully established IRC connection, even -after that connection has been closed. (Also see the note in the -section above about the 'networks' module basically being mandatory.) - -In 5.4, support for network symbols as keys was added for +In 5.4, support for using network symbols as keys was added for 'erc-autojoin-channels-alist'. This has been extended to include explicit symbols passed to 'erc-tls' and 'erc' as so-called network-context identifiers via a new ':id' keyword. The latter carries wider significance beyond autojoin and can be used for unequivocally identifying a connection in a human-readable way. -The function 'erc-auto-query' was deemed too difficult to reason -through and has thus been deprecated with no public replacement; it -has also been removed from the client code path. - -The function 'erc-open' now delays running 'erc-mode-hook' members -until most local session variables have been initialized (minus those -connection-related ones in erc-backend). 'erc-open' also no longer -calls 'erc-update-modules', although modules are still activated -in an identical fashion. - -Some groundwork has been laid for what may become a new breed of ERC -module, namely, "connection-local" (or simply "local") modules. +A number of UX-centric bug fixes accompany this release. For example, +spaces are now possible in server passwords, and users of the Soju +bouncer should no longer see outgoing messages pile up during periods +of heavy traffic. See the Emacs change log for the full complement. -A few internal variables have been introduced that could just as well -have been made public, possibly as user options. Likewise for some -internal functions. As always, users needing such functionality +** Miscellaneous behavioral changes in the library API. +A number of core macros and other definitions have been moved to a new +file called erc-common.el. This was done to help mitigate various +complications arising from the mutual dependency between 'erc' and +'erc-backend'. + +Also on the maintainability front, ERC now relies on the Compat +library from GNU ELPA to supply forward compatibility shims for users +running older versions of Emacs. The required Compat version resides +atop ERC's main library file, in the 'Package-Requires' header. +Third-party modules should benefit automatically from its adoption. + +In an effort to help further tame ERC's complexity, the variable +'erc-default-recipients' is now expected to hold but a single target. +As a consequence, functions like 'erc-add-default-channel' that +imagine an alternate, aspirational model of buffer-target relations +have been deprecated. See Emacs change-log entries from around July +of 2022 for specifics. + +A number of less consequential deprecations also debut in this +release. For example, the function 'erc-auto-query' was deemed too +difficult to understand, behavior wise, and has thus been stricken +from the client code path with no public replacement. Although likely +uncontroversial, such changes may still spell disruption for some. If +you find yourself among them and in need of explanations, please see +related entries in the change log and discussions on the bug tracker. + +Although this release is light on API features, some groundwork has +been laid for what may become a new breed of ERC module, namely, +"connection-local" (or simply "local") modules. This marks a small +but crucial step forward toward a more flexible and granular revamping +of ERC's long touted extensibility. See the Info node "(erc) Local +Modules" for details. + +Lastly, a few internal variables have been introduced that could just +as well have been made public, possibly as user options. Likewise for +some internal functions. As always, users needing such functionality officially exposed are encouraged to write to emacs-erc@gnu.org. commit 119b3a4dba17f0ab068937567c9350301690c18d Author: Eli Zaretskii Date: Fri Mar 3 15:23:22 2023 +0200 Minor copyedits of documentation of OClosures * doc/lispref/functions.texi (OClosures): Improve wording, indexing, and markup; add details. diff --git a/doc/lispref/elisp.texi b/doc/lispref/elisp.texi index c7dc330441f..a1d7b51b609 100644 --- a/doc/lispref/elisp.texi +++ b/doc/lispref/elisp.texi @@ -569,6 +569,7 @@ Top * Function Cells:: Accessing or setting the function definition of a symbol. * Closures:: Functions that enclose a lexical environment. +* OClosures:: Function objects with meta-data. * Advising Functions:: Adding to the definition of a function. * Obsolete Functions:: Declaring functions obsolete. * Inline Functions:: Defining functions that the compiler diff --git a/doc/lispref/functions.texi b/doc/lispref/functions.texi index f5572e447d3..d1459404375 100644 --- a/doc/lispref/functions.texi +++ b/doc/lispref/functions.texi @@ -22,7 +22,7 @@ Functions * Function Cells:: Accessing or setting the function definition of a symbol. * Closures:: Functions that enclose a lexical environment. -* OClosures:: Function objects +* OClosures:: Function objects with meta-data. * Advising Functions:: Adding to the definition of a function. * Obsolete Functions:: Declaring functions obsolete. * Inline Functions:: Functions that the compiler will expand inline. @@ -1581,56 +1581,69 @@ Closures @node OClosures @section Open Closures +@cindex oclosures +@cindex open closures -Traditionally, functions are opaque objects which offer no other -functionality but to call them. Emacs Lisp functions aren't fully + Traditionally, functions are opaque objects which offer no other +functionality but to call them. (Emacs Lisp functions aren't fully opaque since you can extract some info out of them such as their docstring, their arglist, or their interactive spec, but they are -mostly opaque. This is usually what we want, but occasionally we need -functions to expose a bit more information about themselves. +still mostly opaque.) This is usually what we want, but occasionally +we need functions to expose a bit more information about themselves. -OClosures are functions which carry additional type information, -and expose some information in the form of slots which you can access + @dfn{Open closures}, or @dfn{OClosures} for short, are function +objects which carry additional type information and expose some +information about themselves in the form of slots which you can access via accessor functions. -They are defined in two steps: first @code{oclosure-define} is used to -define new OClosure types by specifying the slots carried by those -OClosures, and then @code{oclosure-lambda} is used to create an -OClosure object of a given type. + OClosures are defined in two steps: first you use +@code{oclosure-define} to define a new OClosure type by specifying the +slots carried by the OClosures of this type, and then you use +@code{oclosure-lambda} to create an OClosure object of a given type. + +Let's say we want to define keyboard macros, i.e.@: interactive +functions which re-execute a sequence of key events (@pxref{Keyboard +Macros}). You could do it with a plain function as follows: -Say we want to define keyboard macros, i.e. interactive functions -which re-execute a sequence of key events. You could do it with -a plain function as follows: @example (defun kbd-macro (key-sequence) (lambda (&optional arg) (interactive "P") (execute-kbd-macro key-sequence arg))) @end example + +@noindent But with such a definition there is no easy way to extract the @var{key-sequence} from that function, for example to print it. We can solve this problem using OClosures as follows. First we define the type of our keyboard macros (to which we decided to add a @code{counter} slot while at it): + @example (oclosure-define kbd-macro "Keyboard macro." keys (counter :mutable t)) @end example + +@noindent After which we can rewrite our @code{kbd-macro} function: + @example (defun kbd-macro (key-sequence) (oclosure-lambda (kbd-macro (keys key-sequence) (counter 0)) (&optional arg) - (interactive "p") + (interactive "P") (execute-kbd-macro keys arg) (setq counter (1+ counter)))) @end example + +@noindent As you can see, the @code{keys} and @code{counter} slots of the OClosure can be accessed as local variables from within the body of the OClosure. But we can now also access them from outside of the body of the OClosure, for example to describe a keyboard macro: + @example (defun describe-kbd-macro (km) (if (not (eq 'kbd-macro (oclosure-type km))) @@ -1639,53 +1652,83 @@ OClosures (counter (kbd-macro--counter km))) (message "Keys=%S, called %d times" keys counter)))) @end example + +@noindent Where @code{kbd-macro--keys} and @code{kbd-macro--counter} are -accessor functions generated by the @code{oclosure-define} macro. +accessor functions generated by the @code{oclosure-define} macro for +oclosures whose type is @code{kbd-macro}. -@defmac oclosure-define name &optional docstring &rest slots +@defmac oclosure-define oname &optional docstring &rest slots This macro defines a new OClosure type along with accessor functions -for its slots. @var{name} can be a symbol (the name of -the new type), or a list of the form @code{(@var{name} . @var{type-props})} in -which case @var{type-props} is a list of additional properties. -@var{slots} is a list of slot descriptions where each slot can be -either a symbol (the name of the slot) or it can be of the form -@code{(@var{slot-name} . @var{slot-props})} where @var{slot-props} is -a property list. - -For each slot, the macro creates an accessor function named -@code{@var{name}--@var{slot-name}}. By default slots are immutable. -If you need a slot to be mutable, you need to specify it with the -@code{:mutable} slot property, after which it can be mutated for -example with @code{setf}. - -Beside slot accessors, the macro can create a predicate and -functional update functions according to @var{type-props}: -a @code{(:predicate @var{pred-name})} in the @var{type-props} causes -the definition of a predicate function under the name @var{pred-name}, -and @code{(:copier @var{copier-name} @var{copier-arglist})} causes the -definition of a functional update function which takes an OClosure of -type @var{name} as first argument and returns a copy of it with the -slots named in @var{copier-arglist} modified to the value passed in the -corresponding argument. +for its @var{slots}. @var{oname} can be a symbol (the name of the new +type), or a list of the form +@w{@code{(@var{oname} . @var{type-props})}}, in which case +@var{type-props} is a list of additional properties of this oclosure +type. @var{slots} is a list of slot descriptions where each slot can +be either a symbol (the name of the slot) or it can be of the form +@w{@code{(@var{slot-name} . @var{slot-props})}}, where +@var{slot-props} is a property list of the corresponding slot +@var{slot-name}. +The OClosure type's properties specified by @var{type-props} can +include the following: + +@table @code +@item (:predicate @var{pred-name}) +This requests creation of a predicate function named @var{pred-name}. +This function will be used to recognize OClosures of the type +@var{oname}. If this type property is not specified, +@code{oclosure-define} will generate a default name for the +predicate. +@item (:parent @var{otype}) +This makes type @var{otype} of OClosures be the parent of the type +@var{oname}. The OClosures of type @var{oname} inherit the +@var{slots} defined by their parent type. +@c FIXME: Is the above description of :parent correct? +@item (:copier @var{copier-name} @var{copier-args}) +This causes the definition of a functional update function, knows as +the @dfn{copier}, which takes an OClosure of type @var{oname} as its +first argument and returns a copy of it with the slots named in +@var{copier-args} modified to contain the value passed in the +corresponding argument in the actual call to @var{copier-name}. +@end table + +For each slot in @var{slots}, the @code{oclosure-define} macro creates +an accessor function named @code{@var{oname}--@var{slot-name}}; these +can be used to access the values of the slots. The slot definitions +in @var{slots} can specify the following properties of the slots: + +@table @code +@item :mutable @var{val} +By default, slots are immutable, but if you specify the +@code{:mutable} property with a non-@code{nil} value, the slot can be +mutated, for example with @code{setf} (@pxref{Setting Generalized +Variables}). +@c FIXME: Some rationale and meaning of immutable slot is probably in +@c order here. +@item :type @var{val-type} +This specifies the type of the values expected to appear in the slot. +@c FIXME: What will happen if the value is of a different type? error? +@end table @end defmac @defmac oclosure-lambda (type . slots) arglist &rest body -This macro creates an anonymous OClosure of type @var{type}. -@var{slots} should be a list of elements of the form @code{(@var{slot-name} -@var{exp})}. -At run time, each @var{exp} is evaluated, in order, after which -the OClosure is created with its slots initialized with the -resulting values. - -When called as a function, the OClosure will accept arguments -according to @var{arglist} and will execute the code in @var{body}. -@var{body} can refer to the value of any of its slot directly as if it -were a local variable that had been captured by static scoping. +This macro creates an anonymous OClosure of type @var{type}, which +should have been defined with @code{oclosure-define}. @var{slots} +should be a list of elements of the form +@w{@code{(@var{slot-name} @var{expr})}}. At run time, each @var{expr} +is evaluated, in order, after which the OClosure is created with its +slots initialized with the resulting values. + +When called as a function (@pxref{Calling Functions}), the OClosure +created by this macro will accept arguments according to @var{arglist} +and will execute the code in @var{body}. @var{body} can refer to the +value of any of its slot directly as if it were a local variable that +had been captured by static scoping. @end defmac @defun oclosure-type object -This function returns the OClosure type (a symbol) of @var{object} if it is an -OClosure, and @code{nil} otherwise. +This function returns the OClosure type (a symbol) of @var{object} if +it is an OClosure, and @code{nil} otherwise. @end defun commit 3a651773d29afb48ac4229cd19e532bd57a4ee2d Author: João Távora Date: Fri Mar 3 13:13:35 2023 +0000 Eglot: pay better attention to hints' paddingLeft/Right (bug#61924) * lisp/progmodes/eglot.el (eglot--update-hints-1): Consider :json-false, which is a non-nil value. diff --git a/lisp/icomplete.el b/lisp/icomplete.el index 0adb0e5afeb..4f39afb69f4 100644 --- a/lisp/icomplete.el +++ b/lisp/icomplete.el @@ -661,6 +661,7 @@ icomplete--vertical-minibuffer-setup (setq-local icomplete-hide-common-prefix nil ;; Ask `icomplete-completions' to return enough completions candidates. icomplete-prospects-height 25 + truncate-lines t redisplay-adhoc-scroll-in-resize-mini-windows nil)) ;;;###autoload diff --git a/lisp/progmodes/eglot.el b/lisp/progmodes/eglot.el index b17370ebf8b..a11ec0e4bbd 100644 --- a/lisp/progmodes/eglot.el +++ b/lisp/progmodes/eglot.el @@ -3603,8 +3603,10 @@ eglot--update-hints-1 (goto-char (eglot--lsp-position-to-point position)) (when (or (> (point) to) (< (point) from)) (cl-return)) (let ((left-pad (and paddingLeft + (not (eq paddingLeft :json-false)) (not (memq (char-before) '(32 9))) " ")) (right-pad (and paddingRight + (not (eq paddingRight :json-false)) (not (memq (char-after) '(32 9))) " "))) (cl-flet ((do-it (text lpad rpad) commit 7f740b87d8d18a64f578837096f5faf7c9e26ad8 Author: Mattias Engdegård Date: Fri Mar 3 11:32:34 2023 +0100 Remove ineffective uses of condition-case * lisp/gnus/message.el (message-setup-1): * lisp/progmodes/cc-engine.el (c-forward-single-comment): * lisp/progmodes/ruby-mode.el (ruby-add-log-current-method): Eliminate uses of condition-case without handlers. These seem to have been there for quite a long time. This change does not affect the behaviour of the code and makes some warnings go away. diff --git a/lisp/gnus/message.el b/lisp/gnus/message.el index f4cfffa2e8a..8d3fe010af4 100644 --- a/lisp/gnus/message.el +++ b/lisp/gnus/message.el @@ -6862,10 +6862,9 @@ message-headers-to-generate (defun message-setup-1 (headers &optional yank-action actions return-action) (dolist (action actions) - (condition-case nil - ;; FIXME: Use functions rather than expressions! - (add-to-list 'message-send-actions - `(apply #',(car action) ',(cdr action))))) + ;; FIXME: Use functions rather than expressions! + (add-to-list 'message-send-actions + `(apply #',(car action) ',(cdr action)))) (setq message-return-action return-action) (setq message-reply-buffer (if (and (consp yank-action) diff --git a/lisp/progmodes/cc-engine.el b/lisp/progmodes/cc-engine.el index 037a53421a8..81446c3c00b 100644 --- a/lisp/progmodes/cc-engine.el +++ b/lisp/progmodes/cc-engine.el @@ -1651,7 +1651,7 @@ c-forward-single-comment ;; comment, but XEmacs doesn't. We depend on the Emacs ;; behavior (which also is symmetric). (if (and (eolp) (elt (parse-partial-sexp start (point)) 7)) - (condition-case nil (forward-char 1))) + (forward-char 1)) t)))) diff --git a/lisp/progmodes/ruby-mode.el b/lisp/progmodes/ruby-mode.el index beccb8182a7..d2c4da794ac 100644 --- a/lisp/progmodes/ruby-mode.el +++ b/lisp/progmodes/ruby-mode.el @@ -1850,93 +1850,92 @@ ruby-add-log-current-method File.open See `add-log-current-defun-function'." - (condition-case nil - (save-excursion - (let* ((indent (ruby--add-log-current-indent)) - mname mlist - (start (point)) - (make-definition-re - (lambda (re &optional method-name?) - (concat "^[ \t]*" re "[ \t]+" - "\\(" - ;; \\. and :: for class methods - "\\([A-Za-z_]" ruby-symbol-re "*[?!]?" - "\\|" - (if method-name? ruby-operator-re "\\.") - "\\|::" "\\)" - "+\\)"))) - (definition-re (funcall make-definition-re ruby-defun-beg-re t)) - (module-re (funcall make-definition-re "\\(class\\|module\\)"))) - ;; Get the current method definition (or class/module). - (when (catch 'found - (while (and (re-search-backward definition-re nil t) - (if (if (string-equal "def" (match-string 1)) - ;; We're inside a method. - (if (ruby-block-contains-point (1- start)) - t - ;; Try to match a method only once. - (setq definition-re module-re) - nil) - ;; Class/module. For performance, - ;; comparing indentation. - (or (not (numberp indent)) - (> indent (current-indentation)))) - (throw 'found t) - t)))) - (goto-char (match-beginning 1)) - (if (not (string-equal "def" (match-string 1))) - (setq mlist (list (match-string 2))) - (setq mname (match-string 2))) - (setq indent (current-column)) - (beginning-of-line)) - ;; Walk up the class/module nesting. - (while (and indent - (> indent 0) - (re-search-backward module-re nil t)) - (goto-char (match-beginning 1)) - (when (< (current-column) indent) - (setq mlist (cons (match-string 2) mlist)) - (setq indent (current-column)) - (beginning-of-line))) - ;; Process the method name. - (when mname - (let ((mn (split-string mname "\\.\\|::"))) - (if (cdr mn) - (progn - (unless (string-equal "self" (car mn)) ; def self.foo - ;; def C.foo - (let ((ml (nreverse mlist))) - ;; If the method name references one of the - ;; containing modules, drop the more nested ones. - (while ml - (if (string-equal (car ml) (car mn)) - (setq mlist (nreverse (cdr ml)) ml nil)) - (or (setq ml (cdr ml)) (nreverse mlist)))) - (if mlist - (setcdr (last mlist) (butlast mn)) - (setq mlist (butlast mn)))) - (setq mname (concat "." (car (last mn))))) - ;; See if the method is in singleton class context. - (let ((in-singleton-class - (when (re-search-forward ruby-singleton-class-re start t) - (goto-char (match-beginning 0)) - ;; FIXME: Optimize it out, too? - ;; This can be slow in a large file, but - ;; unlike class/module declaration - ;; indentations, method definitions can be - ;; intermixed with these, and may or may not - ;; be additionally indented after visibility - ;; keywords. - (ruby-block-contains-point start)))) - (setq mname (concat - (if in-singleton-class "." "#") - mname)))))) - ;; Generate the string. - (if (consp mlist) - (setq mlist (mapconcat (function identity) mlist "::"))) - (if mname - (if mlist (concat mlist mname) mname) - mlist))))) + (save-excursion + (let* ((indent (ruby--add-log-current-indent)) + mname mlist + (start (point)) + (make-definition-re + (lambda (re &optional method-name?) + (concat "^[ \t]*" re "[ \t]+" + "\\(" + ;; \\. and :: for class methods + "\\([A-Za-z_]" ruby-symbol-re "*[?!]?" + "\\|" + (if method-name? ruby-operator-re "\\.") + "\\|::" "\\)" + "+\\)"))) + (definition-re (funcall make-definition-re ruby-defun-beg-re t)) + (module-re (funcall make-definition-re "\\(class\\|module\\)"))) + ;; Get the current method definition (or class/module). + (when (catch 'found + (while (and (re-search-backward definition-re nil t) + (if (if (string-equal "def" (match-string 1)) + ;; We're inside a method. + (if (ruby-block-contains-point (1- start)) + t + ;; Try to match a method only once. + (setq definition-re module-re) + nil) + ;; Class/module. For performance, + ;; comparing indentation. + (or (not (numberp indent)) + (> indent (current-indentation)))) + (throw 'found t) + t)))) + (goto-char (match-beginning 1)) + (if (not (string-equal "def" (match-string 1))) + (setq mlist (list (match-string 2))) + (setq mname (match-string 2))) + (setq indent (current-column)) + (beginning-of-line)) + ;; Walk up the class/module nesting. + (while (and indent + (> indent 0) + (re-search-backward module-re nil t)) + (goto-char (match-beginning 1)) + (when (< (current-column) indent) + (setq mlist (cons (match-string 2) mlist)) + (setq indent (current-column)) + (beginning-of-line))) + ;; Process the method name. + (when mname + (let ((mn (split-string mname "\\.\\|::"))) + (if (cdr mn) + (progn + (unless (string-equal "self" (car mn)) ; def self.foo + ;; def C.foo + (let ((ml (nreverse mlist))) + ;; If the method name references one of the + ;; containing modules, drop the more nested ones. + (while ml + (if (string-equal (car ml) (car mn)) + (setq mlist (nreverse (cdr ml)) ml nil)) + (or (setq ml (cdr ml)) (nreverse mlist)))) + (if mlist + (setcdr (last mlist) (butlast mn)) + (setq mlist (butlast mn)))) + (setq mname (concat "." (car (last mn))))) + ;; See if the method is in singleton class context. + (let ((in-singleton-class + (when (re-search-forward ruby-singleton-class-re start t) + (goto-char (match-beginning 0)) + ;; FIXME: Optimize it out, too? + ;; This can be slow in a large file, but + ;; unlike class/module declaration + ;; indentations, method definitions can be + ;; intermixed with these, and may or may not + ;; be additionally indented after visibility + ;; keywords. + (ruby-block-contains-point start)))) + (setq mname (concat + (if in-singleton-class "." "#") + mname)))))) + ;; Generate the string. + (if (consp mlist) + (setq mlist (mapconcat (function identity) mlist "::"))) + (if mname + (if mlist (concat mlist mname) mname) + mlist)))) (defun ruby-block-contains-point (pt) (save-excursion