* bug#56340: 29.0.50; [PATCH] Don't ask people to order requires. @ 2022-07-01 15:23 dick.r.chiang 2022-07-02 12:32 ` Lars Ingebrigtsen 0 siblings, 1 reply; 12+ messages in thread From: dick.r.chiang @ 2022-07-01 15:23 UTC (permalink / raw) To: 56340 [-- Warning: decoded text below may be mangled, UTF-8 assumed --] [-- Attachment #1: 0001-Don-t-do-this.patch --] [-- Type: text/x-diff, Size: 35646 bytes --] From 2a5b0e418d8182378929e902fb35cf53f25de94d Mon Sep 17 00:00:00 2001 From: dickmao <dick.r.chiang@gmail.com> Date: Fri, 1 Jul 2022 11:06:51 -0400 Subject: [PATCH] Don't do this. Asking people to order require's is about as effective as asking kids to keep off the grass. * lisp/erc/erc-backend.el (erc-networks--id, erc-reuse-buffers, erc-kill-server-buffer-on-quit, erc-insert-marker, erc-input-marker, erc-hide-prompt, erc-default-recipients, erc-prompt-hidden, erc-channel-users, erc-invitation, erc-nick-change-attempt-count, erc--target, erc-nick, erc-default-nicks, erc-kill-buffer-on-part, erc-verbose-server-ping, erc-minibuffer-ignored, erc-auto-query, erc-join-buffer, erc-format-nick-function, erc-format-query-as-channel-p, erc-channel-list, erc-whowas-on-nosuchnick, erc-prompt-for-channel-key, erc-active-buffer, erc-session-password, erc-format-message, erc-networks--id-given, erc-open, erc-set-active-buffer, erc-update-mode-line, erc-server-buffer, erc-log-irc-protocol, define-erc-module, erc-with-all-buffers-of-server, erc-default-target, erc-buffer-filter, erc-login, erc-with-server-buffer, erc-emacs-time-to-erc-time, erc-display-message, erc-get-buffer, erc-with-buffer, erc-current-nick, erc-channel-begin-receiving-names, erc-add-default-channel, erc--open-target, erc-current-nick-p, erc-parse-user, erc-delete-default-channel, erc-remove-channel-users, erc-remove-channel-member, erc-trim-string, erc-channel-p, erc-log, erc-handle-user-status-change, erc-networks--id-reload, erc-network, erc-set-current-nick, erc-update-user-nick, erc-get-buffer-create, erc--target-from-string, erc-buffer-list-with-nick, erc-banlist-update, erc-update-modes, erc-time-diff, erc-current-time, erc-query-buffer-p, erc-format-privmessage, erc-process-ctcp-reply, erc-is-message-ctcp-and-not-action-p, erc-ignored-reply-p, erc-ignored-user-p, erc-process-ctcp-query, erc-is-message-ctcp-p, erc-get-channel-user, erc-update-channel-member, erc-make-notice, erc-wash-quit-reason, erc-remove-user, erc-handle-login, erc-connection-established, erc-update-mode-line-buffer, erc-set-modes, erc-display-server-message, erc-process-away, erc-sec-to-time, erc-update-channel-topic, erc-channel-receive-names, erc-channel-end-receiving-names, erc-nickname-in-use, erc-cmd-JOIN, erc-display-error-notice): Forward declares and macro repositioning. (erc--with-memoization): Defalias was a kung-fu I've never seen before. * lisp/erc/erc-goodies.el (erc, erc-backend, erc--target, erc-reuse-buffers, erc-rename-buffers, erc-input-marker, erc-insert-marker, erc-kill-server-hook, erc-kill-buffer-hook, erc-modules, erc-controls-highlight-regexp, erc-controls-remove-regexp, erc-beg-of-input-line, erc-extract-command-from-line, erc-input-string, erc-send-distinguish-noncommands, erc-log, erc-error, erc-buffer-list): Forward declares and macro repositioning. * lisp/erc/erc-networks.el (erc, erc-backend, erc--target, erc-reuse-buffers, erc-rename-buffers, erc-insert-marker, erc-kill-server-hook, erc-kill-buffer-hook, erc-modules, erc-obsolete-var, erc--target-channel-local-p, erc--target-symbol, erc--target-string, erc--default-target, erc-buffer-filter, erc-downcase, erc-current-nick, erc-server-buffer, erc-error, erc-display-error-notice, erc-get-buffer, erc-set-active-buffer): Forward declares and macro repositioning. * lisp/erc/erc.el (erc-networks, erc-goodies, erc-session-password, erc-with-server-buffer, define-erc-module): * test/lisp/erc/erc-networks-tests.el (erc-networks, erc): Defalias was a kung-fu I've never seen before. --- lisp/erc/erc-backend.el | 246 ++++++++++++++++++++++++++-- lisp/erc/erc-goodies.el | 23 ++- lisp/erc/erc-networks.el | 23 ++- lisp/erc/erc.el | 139 +--------------- test/lisp/erc/erc-networks-tests.el | 2 +- 5 files changed, 277 insertions(+), 156 deletions(-) diff --git a/lisp/erc/erc-backend.el b/lisp/erc/erc-backend.el index bee2551d76e..a550ddaaad2 100644 --- a/lisp/erc/erc-backend.el +++ b/lisp/erc/erc-backend.el @@ -99,13 +99,40 @@ ;;; Code: (eval-when-compile (require 'cl-lib)) -;; There's a fairly strong mutual dependency between erc.el and erc-backend.el. -;; Luckily, erc.el does not need erc-backend.el for macroexpansion whereas the -;; reverse is true: -(require 'erc) +(require 'subr-x) ;;;; Variables and options +(defvar erc-networks--id) +(defvar erc-reuse-buffers) +(defvar erc-kill-server-buffer-on-quit) +(defvar erc-insert-marker) +(defvar erc-input-marker) +(defvar erc-hide-prompt) +(defvar erc-default-recipients) +(defvar erc-prompt-hidden) +(defvar erc-channel-users) +(defvar erc-invitation) +(defvar erc-default-recipients) +(defvar erc-nick-change-attempt-count) +(defvar erc--target) +(defvar erc-nick) +(defvar erc-default-nicks) +(defvar erc-kill-buffer-on-part) +(defvar erc-verbose-server-ping) +(defvar erc-minibuffer-ignored) +(defvar erc-auto-query) +(defvar erc-join-buffer) +(defvar erc-format-nick-function) +(defvar erc-format-query-as-channel-p) +(defvar erc-channel-list) +(defvar erc-whowas-on-nosuchnick) +(defvar erc-prompt-for-channel-key) +(defvar erc-active-buffer) + +(defvar-local erc-session-password nil + "The password used for the current session.") + (defvar erc-server-responses (make-hash-table :test #'equal) "Hash table mapping server responses to their handler hooks.") @@ -532,6 +559,7 @@ erc-open-network-stream (let ((p (plist-put parameters :nowait t))) (apply #'open-network-stream name buffer host service p))) +(declare-function erc-format-message "erc") (defun erc-server-connect (server port buffer &optional client-certificate) "Perform the connection and login using the specified SERVER and PORT. We will store server variables in the buffer given by BUFFER. @@ -582,6 +610,11 @@ erc-server-connect (message "%s...done" msg) (erc-login)) )) +(declare-function erc-networks--id-given "erc") +(declare-function erc-open "erc") +(declare-function erc-set-active-buffer "erc") +(declare-function erc-update-mode-line "erc") +(declare-function erc-server-buffer "erc") (defun erc-server-reconnect () "Reestablish the current IRC connection. Make sure you are in an ERC buffer when running this." @@ -611,6 +644,7 @@ erc-server-delayed-reconnect (with-current-buffer buffer (erc-server-reconnect)))) +(declare-function erc-log-irc-protocol "erc") (defun erc-server-filter-function (process string) "The process filter for the ERC server." (with-current-buffer (process-buffer process) @@ -728,6 +762,89 @@ erc--unhide-prompt-on-self-insert (or (eobp) (= (point) erc-input-marker))) (erc--unhide-prompt))) +(defmacro define-erc-module (name alias doc enable-body disable-body + &optional local-p) + "Define a new minor mode using ERC conventions. +Symbol NAME is the name of the module. +Symbol ALIAS is the alias to use, or nil. +DOC is the documentation string to use for the minor mode. +ENABLE-BODY is a list of expressions used to enable the mode. +DISABLE-BODY is a list of expressions used to disable the mode. +If LOCAL-P is non-nil, the mode will be created as a buffer-local +mode, rather than a global one. + +This will define a minor mode called erc-NAME-mode, possibly +an alias erc-ALIAS-mode, as well as the helper functions +erc-NAME-enable, and erc-NAME-disable. + +Example: + + ;;;###autoload(autoload \\='erc-replace-mode \"erc-replace\") + (define-erc-module replace nil + \"This mode replaces incoming text according to `erc-replace-alist'.\" + ((add-hook \\='erc-insert-modify-hook + #\\='erc-replace-insert)) + ((remove-hook \\='erc-insert-modify-hook + #\\='erc-replace-insert)))" + (declare (doc-string 3) (indent defun)) + (let* ((sn (symbol-name name)) + (mode (intern (format "erc-%s-mode" (downcase sn)))) + (group (intern (format "erc-%s" (downcase sn)))) + (enable (intern (format "erc-%s-enable" (downcase sn)))) + (disable (intern (format "erc-%s-disable" (downcase sn))))) + `(progn + (define-minor-mode + ,mode + ,(format "Toggle ERC %S mode. +With a prefix argument ARG, enable %s if ARG is positive, +and disable it otherwise. If called from Lisp, enable the mode +if ARG is omitted or nil. +%s" name name doc) + ;; FIXME: We don't know if this group exists, so this `:group' may + ;; actually just silence a valid warning about the fact that the var + ;; is not associated with any group. + :global ,(not local-p) :group (quote ,group) + (if ,mode + (,enable) + (,disable))) + (defun ,enable () + ,(format "Enable ERC %S mode." + name) + (interactive) + (add-to-list 'erc-modules (quote ,name)) + (setq ,mode t) + ,@enable-body) + (defun ,disable () + ,(format "Disable ERC %S mode." + name) + (interactive) + (setq erc-modules (delq (quote ,name) erc-modules)) + (setq ,mode nil) + ,@disable-body) + ,(when (and alias (not (eq name alias))) + `(defalias + ',(intern + (format "erc-%s-mode" + (downcase (symbol-name alias)))) + #',mode)) + ;; For find-function and find-variable. + (put ',mode 'definition-name ',name) + (put ',enable 'definition-name ',name) + (put ',disable 'definition-name ',name)))) + +(defmacro erc-with-all-buffers-of-server (process pred &rest forms) + "Execute FORMS in all buffers which have same process as this server. +FORMS will be evaluated in all buffers having the process PROCESS and +where PRED matches or in all buffers of the server process if PRED is +nil." + (declare (indent 1) (debug (form form body))) + (macroexp-let2 nil pred pred + `(erc-buffer-filter (lambda () + (when (or (not ,pred) (funcall ,pred)) + ,@forms)) + ,process))) + +(declare-function erc-default-target "erc") (defun erc--hide-prompt (proc) (erc-with-all-buffers-of-server proc nil ; sorta wish this was indent 2 @@ -748,6 +865,8 @@ erc--hide-prompt `(display ,erc-prompt-hidden))) (add-hook 'pre-command-hook #'erc--unhide-prompt-on-self-insert 0 t)))) +(declare-function erc-buffer-filter "erc") +(declare-function erc-login "erc") (defun erc-process-sentinel (cproc event) "Sentinel function for ERC process." (let ((buf (process-buffer cproc))) @@ -821,6 +940,17 @@ erc-send-line (funcall display-fn)) (erc-split-line text))) +(declare-function erc-server-buffer "erc") +(defmacro erc-with-server-buffer (&rest body) + "Execute BODY in the current ERC server buffer. +If no server buffer exists, return nil." + (declare (indent 0) (debug (body))) + (let ((buffer (make-symbol "buffer"))) + `(let ((,buffer (erc-server-buffer))) + (when (buffer-live-p ,buffer) + (with-current-buffer ,buffer + ,@body))))) + ;; From Circe, with modifications (defun erc-server-send (string &optional force target) "Send STRING to the current server. @@ -890,6 +1020,7 @@ erc-server-send-ping (setcdr timer nil))))) ;; From Circe +(declare-function erc-emacs-time-to-erc-time "erc") (defun erc-server-send-queue (buffer) "Send messages in `erc-server-flood-queue'. See `erc-server-flood-margin' for an explanation of the flood @@ -931,6 +1062,7 @@ erc-server-send-queue (run-at-time (+ 0.2 erc-server-flood-penalty) nil #'erc-server-send-queue buffer))))))) +(declare-function erc-display-message "erc") (defun erc-message (message-command line &optional force) "Send LINE to the server as a privmsg or a notice. MESSAGE-COMMAND should be either \"PRIVMSG\" or \"NOTICE\". @@ -1147,6 +1279,40 @@ erc-handle-unknown-server-response " ")))) (erc-display-message parsed 'notice proc line))) +(declare-function erc-get-buffer "erc") +(defmacro erc-with-buffer (spec &rest body) + "Execute BODY in the buffer associated with SPEC. + +SPEC should have the form + + (TARGET [PROCESS]) + +If TARGET is a buffer, use it. Otherwise, use the buffer +matching TARGET in the process specified by PROCESS. + +If PROCESS is nil, use the current `erc-server-process'. +See `erc-get-buffer' for details. + +See also `with-current-buffer'. + +\(fn (TARGET [PROCESS]) BODY...)" + (declare (indent 1) (debug ((form &optional form) body))) + (let ((buf (make-symbol "buf")) + (proc (make-symbol "proc")) + (target (make-symbol "target")) + (process (make-symbol "process"))) + `(let* ((,target ,(car spec)) + (,process ,(cadr spec)) + (,buf (if (bufferp ,target) + ,target + (let ((,proc (or ,process + (and (processp erc-server-process) + erc-server-process)))) + (if (and ,target ,proc) + (erc-get-buffer ,target ,proc)))))) + (when (buffer-live-p ,buf) + (with-current-buffer ,buf + ,@body))))) (cl-defmacro define-erc-response-handler ((name &rest aliases) &optional extra-fn-doc extra-var-doc @@ -1307,6 +1473,7 @@ define-erc-response-handler parsed 'error nil 'ERROR ?s (erc-response.sender parsed) ?c (erc-response.contents parsed))) +(declare-function erc-current-nick "erc") (define-erc-response-handler (INVITE) "Handle invitation messages." nil @@ -1320,6 +1487,11 @@ define-erc-response-handler parsed 'notice 'active 'INVITE ?n nick ?u login ?h host ?c chnl))))) +(declare-function erc-channel-begin-receiving-names "erc") +(declare-function erc-add-default-channel "erc") +(declare-function erc--open-target "erc") +(declare-function erc-current-nick-p "erc") +(declare-function erc-parse-user "erc") (define-erc-response-handler (JOIN) "Handle join messages." nil @@ -1357,6 +1529,10 @@ define-erc-response-handler ;;(set-buffer ob) (erc-display-message parsed nil buffer str)))))) +(declare-function erc-delete-default-channel "erc") +(declare-function erc-remove-channel-users "erc") +(declare-function erc-remove-channel-member "erc") +(declare-function erc-trim-string "erc") (define-erc-response-handler (KICK) "Handle kick messages received from the server." nil (let* ((ch (nth 0 (erc-response.command-args parsed))) @@ -1386,6 +1562,9 @@ define-erc-response-handler parsed 'notice buffer 'KICK ?k tgt ?n nick ?u login ?h host ?c ch ?r reason)))))) +(declare-function erc-active-buffer "erc") +(declare-function erc-channel-p "erc") +(declare-function erc-log "erc") (define-erc-response-handler (MODE) "Handle server mode changes." nil (let ((tgt (car (erc-response.command-args parsed))) @@ -1412,6 +1591,16 @@ define-erc-response-handler ?h host ?t tgt ?m mode))) (erc-banlist-update proc parsed)))) +(declare-function erc-handle-user-status-change "erc") +(declare-function erc-networks--id-reload "erc-networks") +(declare-function erc-network "erc-networks") +(declare-function erc-set-current-nick "erc") +(declare-function erc-update-user-nick "erc") +(declare-function erc-get-buffer-create "erc") +(declare-function erc--target-from-string "erc") +(declare-function erc-buffer-list-with-nick "erc") +(declare-function erc-banlist-update "erc") +(declare-function erc-update-modes "erc") (define-erc-response-handler (NICK) "Handle nick change messages." nil (let ((nn (erc-response.contents parsed)) @@ -1479,6 +1668,8 @@ define-erc-response-handler (when erc-kill-buffer-on-part (kill-buffer buffer)))))) +(declare-function erc-time-diff "erc") +(declare-function erc-current-time "erc") (define-erc-response-handler (PING) "Handle ping messages." nil (let ((pinger (car (erc-response.command-args parsed)))) @@ -1503,6 +1694,17 @@ define-erc-response-handler ?s (if (/= erc-server-lag 1) "s" ""))) (erc-update-mode-line)))) +(declare-function erc-query-buffer-p "erc") +(declare-function erc-format-privmessage "erc") +(declare-function erc-process-ctcp-reply "erc") +(declare-function erc-is-message-ctcp-and-not-action-p "erc") +(declare-function erc-ignored-reply-p "erc") +(declare-function erc-ignored-user-p "erc") +(declare-function erc-process-ctcp-query "erc") +(declare-function erc-is-message-ctcp-p "erc") +(declare-function erc-get-channel-user "erc") +(declare-function erc-update-channel-member "erc") +(declare-function erc-make-notice "erc") (define-erc-response-handler (PRIVMSG NOTICE) "Handle private messages, including messages in channels." nil (let ((sender-spec (erc-response.sender parsed)) @@ -1569,6 +1771,8 @@ define-erc-response-handler 'erc-echo-notice-hook s parsed buffer nick)) (erc-display-message parsed nil buffer s))))))) +(declare-function erc-wash-quit-reason "erc") +(declare-function erc-remove-user "erc") (define-erc-response-handler (QUIT) "Another user has quit IRC." nil (let ((reason (erc-response.contents parsed)) @@ -1615,6 +1819,7 @@ define-erc-response-handler (erc-display-message parsed 'notice 'active (erc-response.contents parsed))) +(declare-function erc-handle-login "erc") (define-erc-response-handler (MOTD 002 003 371 372 374 375) "Display the server's message of the day." nil (erc-handle-login) @@ -1622,11 +1827,13 @@ define-erc-response-handler parsed 'notice (if erc-server-connected 'active proc) (erc-response.contents parsed))) +(declare-function erc-connection-established "erc") (define-erc-response-handler (376 422) "End of MOTD/MOTD is missing." nil (erc-server-MOTD proc parsed) (erc-connection-established proc parsed)) +(declare-function erc-update-mode-line-buffer "erc") (define-erc-response-handler (004) "Display the server's identification." nil (pcase-let ((`(,server-name ,server-version) @@ -1673,12 +1880,15 @@ erc--parse-isupport-value (split-string value ",") (list value))))) -;; FIXME move to erc-compat (once we decide how to load it) -(defalias 'erc--with-memoization - (cond - ((fboundp 'with-memoization) #'with-memoization) ; 29.1 - ((fboundp 'cl--generic-with-memoization) #'cl--generic-with-memoization) - (t (lambda (_ v) v)))) +(defmacro erc--with-memoization (table &rest forms) + "Adapter to be migrated to erc-compat." + (declare (indent defun)) + `(cond + ((fboundp 'with-memoization) + (with-memoization ,table ,@forms)) ; 29.1 + ((fboundp 'cl--generic-with-memoization) + (cl--generic-with-memoization ,table ,@forms)) + (t ,@forms))) (defun erc--get-isupport-entry (key &optional single) "Return an item for \"ISUPPORT\" token KEY, a symbol. @@ -1732,6 +1942,7 @@ erc--get-isupport-entry (erc-display-message parsed 'notice proc line) nil)) +(declare-function erc-set-modes "erc") (define-erc-response-handler (221) "Display the current user modes." nil (let* ((nick (car (erc-response.command-args parsed))) @@ -1755,6 +1966,7 @@ erc--get-isupport-entry (erc-display-message parsed 'notice 'active 's254 ?i (cadr (erc-response.command-args parsed)))) +(declare-function erc-display-server-message "erc") (define-erc-response-handler (250 251 255 256 257 258 259 265 266 377 378) "Generic display of server messages as notices. @@ -1785,6 +1997,7 @@ erc--get-isupport-entry (erc-display-message parsed 'notice 'active 's303 ?n (cadr (erc-response.command-args parsed)))) +(declare-function erc-process-away "erc") (define-erc-response-handler (305) "Return from AWAYness." nil (erc-process-away proc nil) @@ -1840,6 +2053,7 @@ erc--get-isupport-entry "End of WHO/WHOIS/LIST/WHOWAS notices." nil (ignore proc parsed)) +(declare-function erc-sec-to-time "erc") (define-erc-response-handler (317) "IDLE notice." nil (pcase-let ((`(,nick ,seconds-idle ,on-since ,time) @@ -1880,6 +2094,7 @@ erc-server-321-message nil) (add-hook 'erc-server-321-functions #'erc-server-321-message t) +(declare-function erc-update-channel-topic "erc") (define-erc-response-handler (322) "LIST notice." nil (let ((topic (erc-response.contents parsed))) @@ -1987,6 +2202,7 @@ erc-server-322-message ?c channel ?n nick ?a away-flag ?u user ?h host ?f full-name)))) +(declare-function erc-channel-receive-names "erc") (define-erc-response-handler (353) "NAMES notice." nil (let ((channel (nth 2 (erc-response.command-args parsed))) @@ -1997,6 +2213,7 @@ erc-server-322-message (erc-with-buffer (channel proc) (erc-channel-receive-names users)))) +(declare-function erc-channel-end-receiving-names "erc") (define-erc-response-handler (366) "End of NAMES." nil (erc-with-buffer ((cadr (erc-response.command-args parsed)) proc) @@ -2084,10 +2301,11 @@ erc-server-322-message (erc-display-message parsed '(notice error) 'active 's432 ?n (cadr (erc-response.command-args parsed)))) +(declare-function erc-nickname-in-use "erc") (define-erc-response-handler (433) - "Login-time \"nick in use\"." nil - (erc-nickname-in-use (cadr (erc-response.command-args parsed)) - "already in use")) + "Login-time \"nick in use\"." nil + (erc-nickname-in-use (cadr (erc-response.command-args parsed)) + "already in use")) (define-erc-response-handler (437) "Nick temporarily unavailable (on IRCnet)." nil @@ -2121,6 +2339,7 @@ erc-server-322-message (erc-response.command parsed))) ?c (cadr (erc-response.command-args parsed)))) +(declare-function erc-cmd-JOIN "erc") (define-erc-response-handler (475) "Channel key needed." nil (erc-display-message parsed '(notice error) nil 's475 @@ -2154,6 +2373,7 @@ erc-server-322-message (erc-display-message parsed 'notice 'active 's671 ?n nick ?a securemsg))) +(declare-function erc-display-error-notice "erc") (define-erc-response-handler (431 445 446 451 462 463 464 481 483 484 485 491 501 502) ;; 431 - No nickname given diff --git a/lisp/erc/erc-goodies.el b/lisp/erc/erc-goodies.el index 8fef23945d4..73746bcbaeb 100644 --- a/lisp/erc/erc-goodies.el +++ b/lisp/erc/erc-goodies.el @@ -29,10 +29,20 @@ ;;; Code: -(require 'erc) - ;;; Imenu support +(require 'erc-backend) +(defvar erc--target) +(defvar erc-reuse-buffers) +(defvar erc-rename-buffers) +(defvar erc-input-marker) +(defvar erc-insert-marker) +(defvar erc-kill-server-hook) +(defvar erc-kill-buffer-hook) +(defvar erc-modules) +(defvar erc-controls-highlight-regexp) +(defvar erc-controls-remove-regexp) + (defun erc-imenu-setup () "Setup Imenu support in an ERC buffer." (setq-local imenu-create-index-function #'erc-create-imenu-index)) @@ -146,6 +156,7 @@ keep-place ((add-hook 'erc-insert-pre-hook #'erc-keep-place)) ((remove-hook 'erc-insert-pre-hook #'erc-keep-place))) +(declare-function erc-beg-of-input-line "erc") (defun erc-keep-place (_ignored) "Move point away from the last line in a non-selected ERC buffer." (when (and (not (eq (window-buffer (selected-window)) @@ -186,6 +197,8 @@ noncommands ((add-hook 'erc-pre-send-functions #'erc-send-distinguish-noncommands)) ((remove-hook 'erc-pre-send-functions #'erc-send-distinguish-noncommands))) +(declare-function erc-extract-command-from-line "erc") +(declare-function erc-input-string "erc") (defun erc-send-distinguish-noncommands (state) "If STR is an ERC non-command, set `insertp' in STATE to nil." (let* ((string (erc-input-string state)) @@ -196,7 +209,8 @@ erc-send-distinguish-noncommands (not (string-match "\n.+$" string)) (memq cmd-fun erc-noncommands-list)) ;; Inhibit sending this string. - (setf (erc-input-insertp state) nil)))) + (with-no-warnings ;how to declare-function a cl-defmethod? + (setf (erc-input-insertp state) nil))))) ;;; IRC control character processing. (defgroup erc-control-characters nil @@ -339,6 +353,8 @@ bg:erc-color-face15 "ERC face." :group 'erc-faces) +(declare-function erc-log "erc") +(declare-function erc-error "erc") (defun erc-get-bg-color-face (n) "Fetches the right face for background color N (0-15)." (if (stringp n) (setq n (string-to-number n))) @@ -582,6 +598,7 @@ erc-unmorse (unmorse-region (point-min) (point-max))))) ;;; erc-occur +(declare-function erc-buffer-list "erc") (defun erc-occur (string &optional proc) "Search for STRING in all buffers related to current server. If called interactively and prefix argument is given, search on all connected diff --git a/lisp/erc/erc-networks.el b/lisp/erc/erc-networks.el index 091b8aa92d7..f1192ea2f16 100644 --- a/lisp/erc/erc-networks.el +++ b/lisp/erc/erc-networks.el @@ -39,8 +39,15 @@ ;;; Code: -(require 'erc) (eval-when-compile (require 'cl-lib)) +(require 'erc-backend) +(defvar erc--target) +(defvar erc-reuse-buffers) +(defvar erc-rename-buffers) +(defvar erc-insert-marker) +(defvar erc-kill-server-hook) +(defvar erc-kill-buffer-hook) +(defvar erc-modules) ;; Variables @@ -813,7 +820,7 @@ erc-networks--id-given (erc-networks--id-symbol nid)) (cl-generic-define-context-rewriter erc-obsolete-var (var spec) - `((with-suppressed-warnings ((obsolete ,var)) ,var) ,spec)) + `((with-suppressed-warnings ((obsolete ,var) (free-vars ,var)) ,var) ,spec)) ;; As a catch-all, derive the symbol from the unquoted printed repr. (cl-defgeneric erc-networks--id-create (id) @@ -1089,6 +1096,13 @@ erc-networks-shrink-ids-and-buffer-names connection is active." (erc-networks--shrink-ids-and-buffer-names)) +(declare-function erc--target-channel-local-p "erc") +(declare-function erc--target-symbol "erc") +(declare-function erc--target-string "erc") +(declare-function erc--default-target "erc") +(declare-function erc-buffer-filter "erc") +(declare-function erc-downcase "erc") +(declare-function erc-current-nick "erc") (defun erc-networks--examine-targets (identity target on-dupe on-collision) "Visit all ERC target buffers with the same TARGET. Call ON-DUPE when a buffer's identity belongs to a network @@ -1212,6 +1226,7 @@ erc-determine-network do (cl-return name))) 'Unknown)))) +(declare-function erc-server-buffer "erc") (defun erc-network () "Return the value of `erc-network' for the current server." (or erc-network (erc-with-server-buffer erc-network))) @@ -1245,6 +1260,8 @@ erc-networks--determine ((intern vanity)))) erc-networks--name-missing-sentinel)) +(declare-function erc-error "erc") +(declare-function erc-display-error-notice "erc") (defun erc-networks--set-name (_proc parsed) "Set `erc-network' to the value returned by `erc-networks--determine'. Signal an error when the network cannot be determined." @@ -1298,6 +1315,7 @@ erc-networks--insert-transplanted-content ;; This should run whenever a network identity is updated. +(declare-function erc-get-buffer "erc") (defun erc-networks--reclaim-orphaned-target-buffers (new-proc nid announced) "Visit disowned buffers for same NID and associate with NEW-PROC. ANNOUNCED is the server's reported host name." @@ -1384,6 +1402,7 @@ erc-networks--init-identity ;; nil) +(declare-function erc-set-active-buffer "erc") (defun erc-networks--rename-server-buffer (new-proc &optional _parsed) "Rename a server buffer based on its network identity. Assume that the current buffer is a server buffer, either one diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el index 239d8ebdcb6..18d0710d56f 100644 --- a/lisp/erc/erc.el +++ b/lisp/erc/erc.el @@ -60,6 +60,8 @@ (load "erc-loaddefs" 'noerror 'nomessage) +(require 'erc-networks) +(require 'erc-goodies) (require 'cl-lib) (require 'format-spec) (require 'pp) @@ -347,9 +349,6 @@ erc-channel-hide-list :group 'erc-ignore :type 'erc-message-type) -(defvar-local erc-session-password nil - "The password used for the current session.") - (defcustom erc-disconnected-hook nil "Run this hook with arguments (NICK IP REASON) when disconnected. This happens before automatic reconnection. Note, that @@ -449,16 +448,6 @@ erc-downcase erc--casemapping-rfc1459)) (buffer-string))))) -(defmacro erc-with-server-buffer (&rest body) - "Execute BODY in the current ERC server buffer. -If no server buffer exists, return nil." - (declare (indent 0) (debug (body))) - (let ((buffer (make-symbol "buffer"))) - `(let ((,buffer (erc-server-buffer))) - (when (buffer-live-p ,buffer) - (with-current-buffer ,buffer - ,@body))))) - (cl-defstruct (erc-server-user (:type vector) :named) ;; User data nickname host login full-name info @@ -1375,76 +1364,6 @@ erc-debug-log-file (defvar-local erc-dbuf nil) -(defmacro define-erc-module (name alias doc enable-body disable-body - &optional local-p) - "Define a new minor mode using ERC conventions. -Symbol NAME is the name of the module. -Symbol ALIAS is the alias to use, or nil. -DOC is the documentation string to use for the minor mode. -ENABLE-BODY is a list of expressions used to enable the mode. -DISABLE-BODY is a list of expressions used to disable the mode. -If LOCAL-P is non-nil, the mode will be created as a buffer-local -mode, rather than a global one. - -This will define a minor mode called erc-NAME-mode, possibly -an alias erc-ALIAS-mode, as well as the helper functions -erc-NAME-enable, and erc-NAME-disable. - -Example: - - ;;;###autoload(autoload \\='erc-replace-mode \"erc-replace\") - (define-erc-module replace nil - \"This mode replaces incoming text according to `erc-replace-alist'.\" - ((add-hook \\='erc-insert-modify-hook - #\\='erc-replace-insert)) - ((remove-hook \\='erc-insert-modify-hook - #\\='erc-replace-insert)))" - (declare (doc-string 3) (indent defun)) - (let* ((sn (symbol-name name)) - (mode (intern (format "erc-%s-mode" (downcase sn)))) - (group (intern (format "erc-%s" (downcase sn)))) - (enable (intern (format "erc-%s-enable" (downcase sn)))) - (disable (intern (format "erc-%s-disable" (downcase sn))))) - `(progn - (define-minor-mode - ,mode - ,(format "Toggle ERC %S mode. -With a prefix argument ARG, enable %s if ARG is positive, -and disable it otherwise. If called from Lisp, enable the mode -if ARG is omitted or nil. -%s" name name doc) - ;; FIXME: We don't know if this group exists, so this `:group' may - ;; actually just silence a valid warning about the fact that the var - ;; is not associated with any group. - :global ,(not local-p) :group (quote ,group) - (if ,mode - (,enable) - (,disable))) - (defun ,enable () - ,(format "Enable ERC %S mode." - name) - (interactive) - (add-to-list 'erc-modules (quote ,name)) - (setq ,mode t) - ,@enable-body) - (defun ,disable () - ,(format "Disable ERC %S mode." - name) - (interactive) - (setq erc-modules (delq (quote ,name) erc-modules)) - (setq ,mode nil) - ,@disable-body) - ,(when (and alias (not (eq name alias))) - `(defalias - ',(intern - (format "erc-%s-mode" - (downcase (symbol-name alias)))) - #',mode)) - ;; For find-function and find-variable. - (put ',mode 'definition-name ',name) - (put ',enable 'definition-name ',name) - (put ',disable 'definition-name ',name)))) - ;; The rationale for favoring inheritance here (nicer dispatch) is ;; kinda flimsy since there aren't yet any actual methods. @@ -1838,40 +1757,6 @@ erc-member-ignore-case (throw 'result list) (setq list (cdr list)))))) -(defmacro erc-with-buffer (spec &rest body) - "Execute BODY in the buffer associated with SPEC. - -SPEC should have the form - - (TARGET [PROCESS]) - -If TARGET is a buffer, use it. Otherwise, use the buffer -matching TARGET in the process specified by PROCESS. - -If PROCESS is nil, use the current `erc-server-process'. -See `erc-get-buffer' for details. - -See also `with-current-buffer'. - -\(fn (TARGET [PROCESS]) BODY...)" - (declare (indent 1) (debug ((form &optional form) body))) - (let ((buf (make-symbol "buf")) - (proc (make-symbol "proc")) - (target (make-symbol "target")) - (process (make-symbol "process"))) - `(let* ((,target ,(car spec)) - (,process ,(cadr spec)) - (,buf (if (bufferp ,target) - ,target - (let ((,proc (or ,process - (and (processp erc-server-process) - erc-server-process)))) - (if (and ,target ,proc) - (erc-get-buffer ,target ,proc)))))) - (when (buffer-live-p ,buf) - (with-current-buffer ,buf - ,@body))))) - (defun erc-get-buffer (target &optional proc) "Return the buffer matching TARGET in the process PROC. If PROC is not supplied, all processes are searched." @@ -1918,18 +1803,6 @@ erc-buffer-list (setq predicate (lambda () t))) (erc-buffer-filter predicate proc)) -(defmacro erc-with-all-buffers-of-server (process pred &rest forms) - "Execute FORMS in all buffers which have same process as this server. -FORMS will be evaluated in all buffers having the process PROCESS and -where PRED matches or in all buffers of the server process if PRED is -nil." - (declare (indent 1) (debug (form form body))) - (macroexp-let2 nil pred pred - `(erc-buffer-filter (lambda () - (when (or (not ,pred) (funcall ,pred)) - ,@forms)) - ,process))) - (define-obsolete-function-alias 'erc-iswitchb #'erc-switch-to-buffer "25.1") (defun erc--switch-to-buffer (&optional arg) (read-buffer "Switch to ERC buffer: " @@ -7459,12 +7332,4 @@ erc-handle-irc-url (provide 'erc) -(require 'erc-backend) - -;; Deprecated. We might eventually stop requiring the goodies automatically. -;; IMPORTANT: This require must appear _after_ the above (provide 'erc) to -;; avoid a recursive require error when byte-compiling the entire package. -(require 'erc-goodies) -(require 'erc-networks) - ;;; erc.el ends here diff --git a/test/lisp/erc/erc-networks-tests.el b/test/lisp/erc/erc-networks-tests.el index 66a334b7091..32bdfa11ff7 100644 --- a/test/lisp/erc/erc-networks-tests.el +++ b/test/lisp/erc/erc-networks-tests.el @@ -20,7 +20,7 @@ ;;; Code: (require 'ert-x) ; cl-lib -(require 'erc-networks) +(require 'erc) (defun erc-networks-tests--create-dead-proc (&optional buf) (let ((p (start-process "true" (or buf (current-buffer)) "true"))) -- 2.36.1 [-- Attachment #2: Type: text/plain, Size: 14194 bytes --] In Commercial Emacs 0.3.1snapshot 5de4c3d in dev (upstream 29.0.50, x86_64-pc-linux-gnu) built on dick Repository revision: 5de4c3deabbd44bd3b9e1aaa52e23237af9c7f3e Repository branch: dev Windowing system distributor 'The X.Org Foundation', version 11.0.12013000 System Description: Ubuntu 20.04.4 LTS Configured using: 'configure --prefix=/home/dick/.local --with-tree-sitter' Configured features: CAIRO DBUS FREETYPE GIF GLIB GMP GNUTLS GSETTINGS HARFBUZZ JPEG JSON TREE_SITTER LCMS2 LIBSELINUX LIBXML2 MODULES NOTIFY INOTIFY PDUMPER PNG RSVG SECCOMP SOUND THREADS TIFF TOOLKIT_SCROLL_BARS WEBP X11 XDBE XIM XINPUT2 XPM GTK3 ZLIB Important settings: value of $LANG: en_US.UTF-8 locale-coding-system: utf-8-unix Major mode: Magit Log Minor modes in effect: global-git-commit-mode: t shell-dirtrack-mode: t projectile-mode: t flx-ido-mode: t override-global-mode: t global-hl-line-mode: t hl-line-mode: t winner-mode: t tooltip-mode: t show-paren-mode: t mouse-wheel-mode: t file-name-shadow-mode: t global-font-lock-mode: t font-lock-mode: t blink-cursor-mode: t buffer-read-only: t column-number-mode: t line-number-mode: t transient-mark-mode: t auto-composition-mode: t auto-encryption-mode: t auto-compression-mode: t Load-path shadows: /home/dick/gomacro-mode/gomacro-mode hides /home/dick/.emacs.d/elpa/gomacro-mode-20200326.1103/gomacro-mode /home/dick/.emacs.d/elpa/go-rename-20190805.2101/go-rename hides /home/dick/.emacs.d/elpa/go-mode-1.6.0/go-rename /home/dick/.emacs.d/elpa/go-guru-20181012.330/go-guru hides /home/dick/.emacs.d/elpa/go-mode-1.6.0/go-guru /home/dick/org-gcal.el/org-gcal hides /home/dick/.emacs.d/elpa/org-gcal-0.3/org-gcal /home/dick/.emacs.d/elpa/request-deferred-0.2.0/request-deferred hides /home/dick/.emacs.d/elpa/request-0.3.3/request-deferred /home/dick/.emacs.d/elpa/chess-2.0.5/_pkg hides /home/dick/.local/share/emacs/site-lisp/_pkg /home/dick/.emacs.d/elpa/chess-2.0.5/chess-pos hides /home/dick/.local/share/emacs/site-lisp/chess-pos /home/dick/.emacs.d/elpa/chess-2.0.5/chess-module hides /home/dick/.local/share/emacs/site-lisp/chess-module /home/dick/.emacs.d/elpa/chess-2.0.5/chess-ucb hides /home/dick/.local/share/emacs/site-lisp/chess-ucb /home/dick/.emacs.d/elpa/chess-2.0.5/chess-scid hides /home/dick/.local/share/emacs/site-lisp/chess-scid /home/dick/.emacs.d/elpa/chess-2.0.5/chess-puzzle hides /home/dick/.local/share/emacs/site-lisp/chess-puzzle /home/dick/.emacs.d/elpa/chess-2.0.5/chess-irc hides /home/dick/.local/share/emacs/site-lisp/chess-irc /home/dick/.emacs.d/elpa/chess-2.0.5/chess-network hides /home/dick/.local/share/emacs/site-lisp/chess-network /home/dick/.emacs.d/elpa/chess-2.0.5/chess-autosave hides /home/dick/.local/share/emacs/site-lisp/chess-autosave /home/dick/.emacs.d/elpa/chess-2.0.5/chess-engine hides /home/dick/.local/share/emacs/site-lisp/chess-engine /home/dick/.emacs.d/elpa/chess-2.0.5/chess-tutorial hides /home/dick/.local/share/emacs/site-lisp/chess-tutorial /home/dick/.emacs.d/elpa/chess-2.0.5/chess-german hides /home/dick/.local/share/emacs/site-lisp/chess-german /home/dick/.emacs.d/elpa/chess-2.0.5/chess-file hides /home/dick/.local/share/emacs/site-lisp/chess-file /home/dick/.emacs.d/elpa/chess-2.0.5/chess-random hides /home/dick/.local/share/emacs/site-lisp/chess-random /home/dick/.emacs.d/elpa/chess-2.0.5/chess-stockfish hides /home/dick/.local/share/emacs/site-lisp/chess-stockfish /home/dick/.emacs.d/elpa/chess-2.0.5/chess-pgn hides /home/dick/.local/share/emacs/site-lisp/chess-pgn /home/dick/.emacs.d/elpa/chess-2.0.5/chess-kibitz hides /home/dick/.local/share/emacs/site-lisp/chess-kibitz /home/dick/.emacs.d/elpa/chess-2.0.5/chess-eco hides /home/dick/.local/share/emacs/site-lisp/chess-eco /home/dick/.emacs.d/elpa/chess-2.0.5/chess-display hides /home/dick/.local/share/emacs/site-lisp/chess-display /home/dick/.emacs.d/elpa/chess-2.0.5/chess-var hides /home/dick/.local/share/emacs/site-lisp/chess-var /home/dick/.emacs.d/elpa/chess-2.0.5/chess-test hides /home/dick/.local/share/emacs/site-lisp/chess-test /home/dick/.emacs.d/elpa/chess-2.0.5/chess-ply hides /home/dick/.local/share/emacs/site-lisp/chess-ply /home/dick/.emacs.d/elpa/chess-2.0.5/chess-message hides /home/dick/.local/share/emacs/site-lisp/chess-message /home/dick/.emacs.d/elpa/chess-2.0.5/chess-ics1 hides /home/dick/.local/share/emacs/site-lisp/chess-ics1 /home/dick/.emacs.d/elpa/chess-2.0.5/chess-phalanx hides /home/dick/.local/share/emacs/site-lisp/chess-phalanx /home/dick/.emacs.d/elpa/chess-2.0.5/chess-game hides /home/dick/.local/share/emacs/site-lisp/chess-game /home/dick/.emacs.d/elpa/chess-2.0.5/chess-log hides /home/dick/.local/share/emacs/site-lisp/chess-log /home/dick/.emacs.d/elpa/chess-2.0.5/chess-plain hides /home/dick/.local/share/emacs/site-lisp/chess-plain /home/dick/.emacs.d/elpa/chess-2.0.5/chess-perft hides /home/dick/.local/share/emacs/site-lisp/chess-perft /home/dick/.emacs.d/elpa/chess-2.0.5/chess-glaurung hides /home/dick/.local/share/emacs/site-lisp/chess-glaurung /home/dick/.emacs.d/elpa/chess-2.0.5/chess-ai hides /home/dick/.local/share/emacs/site-lisp/chess-ai /home/dick/.emacs.d/elpa/chess-2.0.5/chess-fruit hides /home/dick/.local/share/emacs/site-lisp/chess-fruit /home/dick/.emacs.d/elpa/chess-2.0.5/chess-uci hides /home/dick/.local/share/emacs/site-lisp/chess-uci /home/dick/.emacs.d/elpa/chess-2.0.5/chess-epd hides /home/dick/.local/share/emacs/site-lisp/chess-epd /home/dick/.emacs.d/elpa/chess-2.0.5/chess-database hides /home/dick/.local/share/emacs/site-lisp/chess-database /home/dick/.emacs.d/elpa/chess-2.0.5/chess-link hides /home/dick/.local/share/emacs/site-lisp/chess-link /home/dick/.emacs.d/elpa/chess-2.0.5/chess-transport hides /home/dick/.local/share/emacs/site-lisp/chess-transport /home/dick/.emacs.d/elpa/chess-2.0.5/chess-none hides /home/dick/.local/share/emacs/site-lisp/chess-none /home/dick/.emacs.d/elpa/chess-2.0.5/chess-polyglot hides /home/dick/.local/share/emacs/site-lisp/chess-polyglot /home/dick/.emacs.d/elpa/chess-2.0.5/chess-crafty hides /home/dick/.local/share/emacs/site-lisp/chess-crafty /home/dick/.emacs.d/elpa/chess-2.0.5/chess-chat hides /home/dick/.local/share/emacs/site-lisp/chess-chat /home/dick/.emacs.d/elpa/chess-2.0.5/chess hides /home/dick/.local/share/emacs/site-lisp/chess /home/dick/.emacs.d/elpa/chess-2.0.5/chess-images hides /home/dick/.local/share/emacs/site-lisp/chess-images /home/dick/.emacs.d/elpa/chess-2.0.5/chess-gnuchess hides /home/dick/.local/share/emacs/site-lisp/chess-gnuchess /home/dick/.emacs.d/elpa/chess-2.0.5/chess-fen hides /home/dick/.local/share/emacs/site-lisp/chess-fen /home/dick/.emacs.d/elpa/chess-2.0.5/chess-ics hides /home/dick/.local/share/emacs/site-lisp/chess-ics /home/dick/.emacs.d/elpa/chess-2.0.5/chess-ics2 hides /home/dick/.local/share/emacs/site-lisp/chess-ics2 /home/dick/.emacs.d/elpa/chess-2.0.5/chess-common hides /home/dick/.local/share/emacs/site-lisp/chess-common /home/dick/.emacs.d/elpa/chess-2.0.5/chess-input hides /home/dick/.local/share/emacs/site-lisp/chess-input /home/dick/.emacs.d/elpa/chess-2.0.5/chess-announce hides /home/dick/.local/share/emacs/site-lisp/chess-announce /home/dick/.emacs.d/elpa/chess-2.0.5/chess-clock hides /home/dick/.local/share/emacs/site-lisp/chess-clock /home/dick/.emacs.d/elpa/chess-2.0.5/chess-sound hides /home/dick/.local/share/emacs/site-lisp/chess-sound /home/dick/.emacs.d/elpa/chess-2.0.5/chess-sjeng hides /home/dick/.local/share/emacs/site-lisp/chess-sjeng /home/dick/.emacs.d/elpa/chess-2.0.5/chess-algebraic hides /home/dick/.local/share/emacs/site-lisp/chess-algebraic /home/dick/.emacs.d/elpa/transient-0.3.7snapshot/transient hides /home/dick/.local/share/emacs/0.3.1/lisp/transient Features: (mode-local elpaso elpaso-admin elpaso-milky elpaso-defs shortdoc supercite regi shr-color rect pulse ivy delsel colir ivy-overlay ffap dumb-jump gravatar dns ag vc-svn find-dired markdown-mode edit-indirect flow-fill nndoc org-element avl-tree ol-eww eww xdg ol-rmail ol-mhe ol-irc ol-info ol-gnus nnselect ol-docview doc-view image-mode exif ol-bibtex ol-bbdb ol-w3m ol-doi org-link-doi org-tempo tempo org org-macro org-footnote org-pcomplete org-list org-faces org-entities org-version ob-R ob-emacs-lisp ob-ein ein-cell ein-shared-output ein-output-area ein-kernel ein-ipdb ein-query ein-events ein-websocket websocket bindat ein-node ewoc ein-log ein-classes ein-core ein ein-utils deferred ob ob-tangle org-src ob-ref ob-lob ob-table ob-exp ob-comint ob-core ob-eval org-table oc-basic bibtex ol org-keys oc org-compat org-macs org-loaddefs cal-menu calendar cal-loaddefs whitespace cl-print debug backtrace goto-addr magit-extras mule-util display-line-numbers debbugs-gnu debbugs-compat debbugs soap-client rng-xsd rng-dt rng-util xsd-regexp jka-compr gnus-html url-queue help-fns radix-tree vc cc-mode cc-fonts cc-guess cc-menus cc-cmds cc-styles cc-align cc-engine cc-vars cc-defs eudc-capf eudc eudc-vars shadow bbdb-message footnote emacsbug texinfo texinfo-loaddefs face-remap magit-patch-changelog magit-patch magit-submodule magit-obsolete magit-blame magit-stash magit-reflog magit-bisect magit-push magit-pull magit-fetch magit-clone magit-remote magit-commit magit-sequence magit-notes magit-worktree magit-tag magit-merge magit-branch magit-reset magit-files magit-refs magit-status magit magit-repos magit-apply magit-wip magit-log which-func imenu magit-diff smerge-mode diff git-commit log-edit pcvs-util add-log magit-core magit-margin magit-transient magit-process with-editor server magit-mode transient misearch multi-isearch vc-git diff-mode vc-dispatcher bug-reference tramp-archive tramp-gvfs tramp-cache zeroconf textsec uni-scripts idna-mapping ucs-normalize uni-confusable textsec-check sort smiley mm-archive mail-extr qp gnus-async gnus-ml gnus-notifications gnus-fun notifications gnus-kill gnus-dup disp-table utf-7 blamer a tramp tramp-loaddefs trampver tramp-integration cus-start files-x tramp-compat shell pcomplete ls-lisp url-cache benchmark nnrss nnfolder nndiscourse rbenv nnhackernews nntwitter nntwitter-api bbdb-gnus gnus-demon nntp nnmairix nnml nnreddit gnus-topic url-http url-auth url-gw network-stream nsm request virtualenvwrapper gud s json-rpc python gnus-score score-mode gnus-bcklg gnus-srvr gnus-cite anaphora bbdb-mua bbdb-com bbdb bbdb-site timezone gnus-delay gnus-draft gnus-cache gnus-agent gnus-msg gnus-art mm-uu mml2015 mm-view mml-smime smime gnutls dig gnus-sum shr pixel-fill kinsoku url-file url-dired svg dom nndraft nnmh gnus-group mm-url gnus-undo use-package use-package-delight use-package-diminish gnus-start gnus-dbus dbus xml gnus-cloud nnimap nnmail mail-source utf7 netrc nnoo parse-time iso8601 gnus-spec gnus-int gnus-range message sendmail yank-media puny dired-x dired dired-loaddefs rfc822 mml mml-sec epa epg rfc6068 epg-config mm-decode mm-bodies mm-encode mail-parse rfc2231 rfc2047 rfc2045 ietf-drums mailabbrev gmm-utils mailheader gnus-win paredit-ext paredit inf-ruby ruby-mode smie company pcase haskell-interactive-mode haskell-presentation-mode haskell-process haskell-session haskell-compile haskell-mode haskell-cabal haskell-utils haskell-font-lock haskell-indentation haskell-string haskell-sort-imports haskell-lexeme haskell-align-imports haskell-complete-module haskell-ghc-support noutline outline flymake-proc flymake warnings etags fileloop generator dabbrev haskell-customize hydra lv use-package-ensure solarized-theme solarized-definitions projectile lisp-mnt ibuf-ext ibuffer ibuffer-loaddefs thingatpt magit-autorevert autorevert filenotify magit-git magit-base magit-section format-spec crm dash rx compat-27 compat-26 compat grep compile comint ansi-color gnus nnheader range mail-utils mm-util mail-prsvr gnus-util text-property-search time-date flx-ido flx google-translate-default-ui google-translate-core-ui facemenu color ido google-translate-core google-translate-tk google-translate-backend use-package-bind-key bind-key auto-complete easy-mmode advice edmacro kmacro popup cus-edit pp cus-load wid-edit emms-player-mplayer emms-player-simple emms emms-compat cl-extra help-mode xref project use-package-core derived hl-line winner ring debbugs-autoloads eglot-autoloads elpaso-disc-autoloads elpaso-autoloads find-func finder-inf go-mode-autoloads json-reformat-autoloads json-snatcher-autoloads projectile-autoloads sml-mode-autoloads epl-autoloads tornado-template-mode-autoloads typescript-mode-autoloads request-autoloads info package browse-url url url-proxy url-privacy url-expand url-methods url-history url-cookie generate-lisp-file url-domsuf url-util mailcap url-handlers url-parse auth-source cl-seq eieio eieio-core cl-macs eieio-loaddefs password-cache json subr-x map byte-opt gv bytecomp byte-compile cconv cldefs url-vars cl-loaddefs cl-lib rmc iso-transl tooltip eldoc paren electric uniquify ediff-hook vc-hooks lisp-float-type elisp-mode mwheel term/x-win x-win term/common-win x-dnd tool-bar dnd fontset image regexp-opt fringe tree-sitter tabulated-list replace newcomment text-mode lisp-mode prog-mode register page tab-bar menu-bar rfn-eshadow isearch easymenu timer select scroll-bar mouse jit-lock font-lock syntax font-core term/tty-colors frame minibuffer nadvice seq simple cl-generic indonesian philippine cham georgian utf-8-lang misc-lang vietnamese tibetan thai tai-viet lao korean japanese eucjp-ms cp51932 hebrew greek romanian slovak czech european ethiopic indian cyrillic chinese composite emoji-zwj charscript charprop case-table epa-hook jka-cmpr-hook help abbrev obarray oclosure cl-preloaded button loaddefs faces cus-face macroexp files window text-properties overlay sha1 md5 base64 format env code-pages mule custom widget keymap hashtable-print-readable backquote threads dbusbind inotify lcms2 dynamic-setting system-font-setting font-render-setting cairo move-toolbar gtk x-toolkit xinput2 x multi-tty make-network-process emacs) Memory information: ((conses 16 2291654 278813) (symbols 48 57591 99) (strings 32 325470 81126) (string-bytes 1 10675600) (vectors 16 166031) (vector-slots 8 4028354 252813) (floats 8 3841 3992) (intervals 56 226408 5693) (buffers 1000 92)) ^ permalink raw reply related [flat|nested] 12+ messages in thread
* bug#56340: 29.0.50; [PATCH] Don't ask people to order requires. 2022-07-01 15:23 bug#56340: 29.0.50; [PATCH] Don't ask people to order requires dick.r.chiang @ 2022-07-02 12:32 ` Lars Ingebrigtsen 2022-07-04 23:36 ` J.P. [not found] ` <87czekcuxj.fsf@neverwas.me> 0 siblings, 2 replies; 12+ messages in thread From: Lars Ingebrigtsen @ 2022-07-02 12:32 UTC (permalink / raw) To: dick.r.chiang; +Cc: 56340, Amin Bandali, F. Jason Park dick.r.chiang@gmail.com writes: > Asking people to order require's is about as effective > as asking kids to keep off the grass. It looks like this patch is rearranging some dependencies to make erc load in a more logical way? I haven't tried the patch, but skimming it, it seems to make some sense. I've added the erc maintainers to the CCs. -- (domestic pets only, the antidote for overdose, milk.) bloggy blog: http://lars.ingebrigtsen.no ^ permalink raw reply [flat|nested] 12+ messages in thread
* bug#56340: 29.0.50; [PATCH] Don't ask people to order requires. 2022-07-02 12:32 ` Lars Ingebrigtsen @ 2022-07-04 23:36 ` J.P. [not found] ` <87czekcuxj.fsf@neverwas.me> 1 sibling, 0 replies; 12+ messages in thread From: J.P. @ 2022-07-04 23:36 UTC (permalink / raw) To: dick.r.chiang; +Cc: Lars Ingebrigtsen, 56340, Amin Bandali, emacs-erc Hi Dick, Lars, people, Lars Ingebrigtsen <larsi@gnus.org> writes: > dick.r.chiang@gmail.com writes: > >> Asking people to order require's is about as effective >> as asking kids to keep off the grass. > > It looks like this patch is rearranging some dependencies to make erc > load in a more logical way? > > I haven't tried the patch, but skimming it, it seems to make some sense. > I've added the erc maintainers to the CCs. This bug seems to be in answer to #54825, which, Dick, I guess you found wanting enough to serve as your next meal (and its author simple enough to adopt as your next mark). Perhaps all is right with the world. Regardless of whatever ancillary motivations might have prompted that perceived half measure from me [1], given the direction I'd like to see ERC move in, a little turbulence in this arena is likely inevitable. So I suppose now's a good a time as any to rip this Band Aid clean off. And having myself on occasion gamed out similar changes to these, I can somewhat appreciate what appears to be an earnest attempt at leaving a relatively light footprint overall. > * lisp/erc/erc-backend.el (erc-networks--id, erc-reuse-buffers, > erc-kill-server-buffer-on-quit, erc-insert-marker, erc-input-marker, > erc-hide-prompt, erc-default-recipients, erc-prompt-hidden, Is the convention here really to list all of these? Or is this like all part of the show (or maybe both)? (Sorry, I, Philistine.) If yes to the first, I guess I've been missing out but will fall in line ASAP. FWIW, grepping the change logs for "forward decl" only returns a handful of hits. > @@ -1673,12 +1880,15 @@ erc--parse-isupport-value > (split-string value ",") > (list value))))) > > -;; FIXME move to erc-compat (once we decide how to load it) > -(defalias 'erc--with-memoization > - (cond > - ((fboundp 'with-memoization) #'with-memoization) ; 29.1 > - ((fboundp 'cl--generic-with-memoization) #'cl--generic-with-memoization) > - (t (lambda (_ v) v)))) Hmm, yeah, thanks. Caught that one on the chin on the way out the door and was hoping no one would notice until I could sweep it under the rug all furtive like. (It's definitely one for the ages, though, I'll give you that: hall of shame material for sure.) I'm kinda surprised the compiled version runs at all instead of signaling an "invalid function" or something. Either way, short of our keeping it as a pet and renaming it `with-bath-salts' (or `with-kung-flu' or whatever), I doubt it'll be long for this world in any form once we get our compat ducks in a row. > +(declare-function erc-nickname-in-use "erc") > (define-erc-response-handler (433) > - "Login-time \"nick in use\"." nil > - (erc-nickname-in-use (cadr (erc-response.command-args parsed)) > - "already in use")) > + "Login-time \"nick in use\"." nil > + (erc-nickname-in-use (cadr (erc-response.command-args parsed)) > + "already in use")) Indentation thing aside, I wasn't aware we were allowed to forgo including signatures in these `declare-function' forms. But if that's the deal, I guess it makes for a cleaner, less cluttered look overall. From "Rework mutual dependency yada yada" (bug#54825) [2]: > ;;;; Variables and options > modified lisp/erc/erc.el > @@ -130,7 +130,26 @@ erc-scripts > "Running scripts at startup and with /LOAD." > :group 'erc) > > -(require 'erc-backend) > +;; Defined in erc-backend > +(defvar erc--server-reconnecting) > +(defvar erc-channel-members-changed-hook) > +(defvar erc-server-367-functions) > +(defvar erc-server-announced-name) > [...] > > @@ -48,6 +48,27 @@ erc--read-time-period > (cl-letf (((symbol-function 'read-string) (lambda (&rest _) "1d"))) > (should (equal (erc--read-time-period "foo: ") 86400)))) > > +(ert-deftest erc--meta--backend-dependencies () > + (with-temp-buffer > + (insert-file-contents-literally Your changes obsolete most of these `defvars' and the associated test. Not saying it should fall on you to tidy up, but "someone" should remove them. Which gets me wondering (not for the first time): all these `defvar's and `declare-function's seem a bit litter-prone, no? Not sure if any diagnostic tooling already catches extraneous ones orphaned by refactoring, but I for one could use such a feature. > Don't do this. > > Asking people to order require's is about as effective > as asking kids to keep off the grass. How about a more pedestrian commit subject, like maybe one mentioning ERC or something it defines? (But just rolling the dice on whatever malaprop-laden ESL lesson I cook up also works.) > @@ -196,7 +209,8 @@ erc-send-distinguish-noncommands > (not (string-match "\n.+$" string)) > (memq cmd-fun erc-noncommands-list)) > ;; Inhibit sending this string. > - (setf (erc-input-insertp state) nil)))) > + (with-no-warnings ;how to declare-function a cl-defmethod? > + (setf (erc-input-insertp state) nil))))) > > ;;; IRC control character processing. > (defgroup erc-control-characters nil When I byte compile erc-goodies.el and then, with emacs -Q, do (require 'erc) (let ((input (make-erc-input :string "/me nods" :sendp t :insertp t))) (erc-send-distinguish-noncommands input) input) I get Symbol’s function definition is void: \(setf\ erc-input-insertp\) Adding this somewhere atop goodies (eval-when-compile (provide 'erc-goodies) (require 'erc)) seems to give the expected output: => #s(erc-input "/me nods" nil t) Although it also introduces a couple new compiler warnings as well, so what do I know? (Don't answer that.) This or similar (in emacs -Q) may offer some insights: (trace-function-foreground 'gv-get) (byte-compile-file "lisp/erc/erc-goodies.el") Basically, I don't really care what happens with `erc-goodies' in the extreme short term (barring some immediate ELPA release) as long as we preserve as much behavior and blame as is reasonable. Hopefully, requiring goodies will become a thing of the past after this [3] or something superior lands, meaning expect new bugs from me shortly. (That's your cue to flee, people.) Thanks, J.P. [1] Not that anyone should care, but there was, for example, the matter of damage control for some unfortunate advice that found its way to a couple "exemplar" configs, which ended up hooking all their setup on `erc-backend' as a sad workaround for these ancient dependency problems. So, some of my aim might have been diverted toward not breaking those until we had a worthy feature to trade for the churn. Add to that a general reticence to disturb large swaths of ancient blame and we get closer to my (perhaps failed) attempt at reining in only the most unwieldy parts of the dependency cycle rather than doing the bold thing (as is being proposed here). [2] https://git.savannah.gnu.org/cgit/emacs.git/commit/?id=0f52e7ac [3] https://ttm.sh/es3 ^ permalink raw reply [flat|nested] 12+ messages in thread
[parent not found: <87czekcuxj.fsf@neverwas.me>]
* bug#56340: 29.0.50; [PATCH] Don't ask people to order requires. [not found] ` <87czekcuxj.fsf@neverwas.me> @ 2022-07-05 1:59 ` dick 2022-07-05 6:39 ` bug#56340: Change erc dependencies J.P. [not found] ` <87sfng83n8.fsf_-_@neverwas.me> 2 siblings, 0 replies; 12+ messages in thread From: dick @ 2022-07-05 1:59 UTC (permalink / raw) Cc: 56340 > Symbol’s function definition is void: \(setf\ erc-input-insertp\) That is a good test. In my fork, I had to refactor up the defstruct of erc-input from erc.el to erc-backend.el. ^ permalink raw reply [flat|nested] 12+ messages in thread
* bug#56340: Change erc dependencies [not found] ` <87czekcuxj.fsf@neverwas.me> 2022-07-05 1:59 ` dick @ 2022-07-05 6:39 ` J.P. [not found] ` <87sfng83n8.fsf_-_@neverwas.me> 2 siblings, 0 replies; 12+ messages in thread From: J.P. @ 2022-07-05 6:39 UTC (permalink / raw) To: dick.r.chiang; +Cc: Lars Ingebrigtsen, 56340, Amin Bandali, emacs-erc "J.P." <jp@neverwas.me> writes: >> +(declare-function erc-nickname-in-use "erc") >> (define-erc-response-handler (433) >> - "Login-time \"nick in use\"." nil >> - (erc-nickname-in-use (cadr (erc-response.command-args parsed)) >> - "already in use")) >> + "Login-time \"nick in use\"." nil >> + (erc-nickname-in-use (cadr (erc-response.command-args parsed)) >> + "already in use")) > > Indentation thing aside, I wasn't aware we were allowed to forgo > including signatures in these `declare-function' forms. But if that's > the deal, I guess it makes for a cleaner, less cluttered look overall. > > [...] > > Which gets me wondering (not for the first time): all these > `defvar's and `declare-function's seem a bit litter-prone, no? Not sure > if any diagnostic tooling already catches extraneous ones orphaned by > refactoring, but I for one could use such a feature. Hmm, now I'm thinking there's likely some benefit to always including a lambda list in these `declare-function's because it seems 1. byte compiling only warns of a mismatch between the call site and the declaration but doesn't actually validate the latter 2. check-declare makes up for that by emitting an "arglist mismatch" when necessary, which diagnostic tools, like flymake, can pick up on Not saying you need to comply, but someone should probably at least append a (t t) to the following declarations because, at present, with your patch applied, running `check-declare-directory' on lisp/erc gives: lisp/erc/erc-networks.el:1099:Warning (check-declare): said ‘erc--target-channel-local-p’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-networks.el:1100:Warning (check-declare): said ‘erc--target-symbol’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-networks.el:1101:Warning (check-declare): said ‘erc--target-string’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-goodies.el:201:Warning (check-declare): said ‘erc-input-string’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-goodies.el:356:Warning (check-declare): said ‘erc-log’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-backend.el:613:Warning (check-declare): said ‘erc-networks--id-given’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-backend.el:647:Warning (check-declare): said ‘erc-log’ was defined in lisp/erc/erc.el: function not found lisp/erc/erc-backend.el:1705:Warning (check-declare): said ‘erc-get-channel-user’ was defined in lisp/erc/erc.el: function not found Perhaps the definitions of these irregulars should all eventually be moved to erc-backend.el, as you did with `erc-input'. In the meantime, I'm going to extract the non-forward-declaration hunks from your patch into a standalone commit (attributed to you, unless you object relatively soonish) and install that along with some other, unrelated fixes. That way, we can let the rest steep until others weigh in or at least until there's some clear indication of your willingness to iterate further on this bug thread (apart from related activity on your fork). Thanks. ^ permalink raw reply [flat|nested] 12+ messages in thread
[parent not found: <87sfng83n8.fsf_-_@neverwas.me>]
* bug#56340: Change erc dependencies [not found] ` <87sfng83n8.fsf_-_@neverwas.me> @ 2022-07-16 14:17 ` J.P. [not found] ` <877d4d9m6c.fsf@neverwas.me> 1 sibling, 0 replies; 12+ messages in thread From: J.P. @ 2022-07-16 14:17 UTC (permalink / raw) To: dick.r.chiang; +Cc: Lars Ingebrigtsen, 56340, Amin Bandali, emacs-erc [-- Attachment #1: Type: text/plain, Size: 3234 bytes --] As an experiment, I've tried rearranging things into a more traditional layout, with most of the compile-time dependencies moved to a dedicated file [1]. This is mainly for show and does nothing for the close coupling and hard dependencies that have long plagued ERC from a design standpoint [2]. (There's definitely still something to be said for just having it all live in erc-backend.) Still, part of the impetus for collecting all the heavy stuff in one place was to avoid having to constantly check for hidden snags down the line. For example, AFAIK, the byte compiler doesn't catch stuff like the following, which are present in the original, "Don't do this" patch: Running $ emacs -Q -batch -f batch-byte-compile ./lisp/erc/erc-goodies.el and inspecting the output reveals missing inline expansions for calls to `erc-log', which are numerous, and which normally resemble something like (require 'erc) (byte-compile (macroexpand `(lambda (msg) ,(funcall (get 'erc-log 'compiler-macro) nil 'msg)))) The same goes for other files as well. For example, after doing $ emacs -Q -batch -f batch-byte-compile ./lisp/erc/erc-networks.el notice the missing expansions for `erc--target' accessors in lisp/erc/erc-networks.elc. Again, where we'd normally expect to see (require 'erc) (byte-compile (macroexpand `(lambda (targ) ,(funcall (get 'erc--target-string 'compiler-macro) 'erc--target 'targ)))) we're instead left with normal function calls. FWIW, the layout in the attached patch doesn't suffer from these complications. Of course, that's only one way to confront this stuff, perhaps even the dumbest. People at home with a clue, please chime in with your insights and shade (or be haunted 'til your dying day). Thanks! Overflow ~~~~~~~~ [1] If we did stick with a new file, what's the best name for such a thing? I just went with `erc-common', for now, but perhaps something ending in -macs or -core would be more faithful to the platform? [2] However, I was really hoping to start inching toward eventually making headway on a goal that's been with ERC since the old CVS days, and that's decoupling protocol handling from the display machinery, likely by abstracting away the particulars of network processes and I/O. This would open the door for "pluggable backends" supporting IRC-adjacent client protocols, such as those in use by WeeChat and Quassel (or even commercial entities, like IrcCloud). Or, at the very least, it'd allow us to start exploring proxy protocols, like IRC over WebSockets and bouncer multiplexing schemes. But erc-backend.el in its current form is the opposite of modular. It's hardwired to speak IRC over stream sockets. And while I'd really wanted to hold off on shuffling things around until we had a solid plan in place, I've come to accept the futility of that delusion. As such, I'm hoping we can use whatever shake up emerges from this bug report as a somewhat stable stepping stone to nudge things in a more modular direction over the next few minor releases. [-- Warning: decoded text below may be mangled, UTF-8 assumed --] [-- Attachment #2: 0001-Move-ERC-s-core-dependencies-to-separate-file.patch --] [-- Type: text/x-patch, Size: 44184 bytes --] From 103c6f646d6aef18468dd3dae719dd11afa0f8a8 Mon Sep 17 00:00:00 2001 From: dickmao <dick.r.chiang@gmail.com> Date: Fri, 1 Jul 2022 11:06:51 -0400 Subject: [PATCH] Move ERC's core dependencies to separate file Asking people to order require's is about as effective as asking kids to keep off the grass. * lisp/erc/erc-backend.el (erc--target, erc-auto-query, erc-channel-list, erc-channel-users, erc-default-nicks, erc-default-recipients, erc-format-nick-function, erc-format-query-as-channel-p, erc-hide-prompt, erc-input-marker, erc-insert-marker, erc-invitation, erc-join-buffer, erc-kill-buffer-on-part, erc-kill-server-buffer-on-quit, erc-log-p, erc-minibuffer-ignored, erc-networks--id, erc-nick, erc-nick-change-attempt-count, erc-prompt-for-channel-key, erc-prompt-hidden, erc-reuse-buffers, erc-verbose-server-ping, erc-whowas-on-nosuchnick): Forward-declare variables. (erc--open-target, erc--target-from-string, erc-active-buffer, erc-add-default-channel, erc-banlist-update, erc-buffer-filter, erc-buffer-list-with-nick, erc-channel-begin-receiving-names, erc-channel-end-receiving-names, erc-channel-p, erc-channel-receive-names, erc-cmd-JOIN, erc-connection-established, erc-current-nick, erc-current-nick-p, erc-current-time, erc-default-target, erc-delete-default-channel, erc-display-error-notice, erc-display-server-message, erc-emacs-time-to-erc-time, erc-format-message, erc-format-privmessage, erc-get-buffer, erc-handle-login, erc-handle-user-status-change, erc-ignored-reply-p, erc-ignored-user-p, erc-is-message-ctcp-and-not-action-p, erc-is-message-ctcp-p, erc-log-irc-protocol, erc-login, erc-make-notice, erc-network, erc-networks--id-given, erc-networks--id-reload, erc-nickname-in-use, erc-parse-user, erc-process-away, erc-process-ctcp-query, erc-query-buffer-p, erc-remove-channel-member, erc-remove-channel-users, erc-remove-user, erc-sec-to-time, erc-server-buffer, erc-set-active-buffer, erc-set-current-nick, erc-set-modes, erc-time-diff, erc-trim-string, erc-update-mode-line, erc-update-mode-line-buffer, erc-wash-quit-reason, erc-display-message, erc-get-buffer-create, erc-process-ctcp-reply, erc-update-channel-topic, erc-update-modes, erc-update-user-nick, erc-open, erc-update-channel-member): Forward-declare functions. (erc-response, erc--with-memoization): Move to lisp/erc/erc-common.el. * lisp/erc/erc-common.el: New file. Change indentation for `erc-with-all-buffers-of-server' from 1 to 2. * lisp/erc/erc-goodies.el: Require `erc-common' instead of `erc'. (erc-controls-highlight-regexp, erc-controls-remove-regexp, erc-input-marker, erc-insert-marker, erc-server-process, erc-modules, erc-log-p): Forward declare variables. (erc-buffer-list, erc-error, erc-extract-command-from-line): Forward-declare functions. * lisp/erc/erc-networks.el (erc--target, erc-insert-marker, erc-kill-buffer-hook, erc-kill-server-hook, erc-modules, erc-rename-buffers, erc-reuse-buffers, erc-server-announced-name, erc-server-connected, erc-server-parameters, erc-server-process, erc-session-server): Forward declare variables. (erc--default-target, erc--get-isupport-entry, erc-buffer-filter, erc-current-nick, erc-display-error-notice, erc-downcase, erc-error, erc-get-buffer, erc-server-buffer, erc-server-process-alive): Forward-declare functions. (erc-obsolete-var): Also suppress free-variable warnings. * lisp/erc/erc.el: Require `erc-networks', `erc-goodies', and `erc-backend' at top of file. (erc--server-last-reconnect-count, erc--server-reconnecting, erc-channel-members-changed-hook, erc-network, erc-networks--id, erc-server-367-functions, erc-server-announced-name, erc-server-connect-function, erc-server-connected, erc-server-current-nick, erc-server-lag, erc-server-last-sent-time, erc-server-process, erc-server-quitting, erc-server-reconnect-count, erc-server-reconnecting, erc-session-client-certificate, erc-session-connector, erc-session-port, erc-session-server, erc-session-user-full-name) Remove superfluous forward declarations. (erc-message-parsed, tabbar--local-hlf, motif-version-string): Relocate forward declares to central location. (erc-session-password): Move to `erc-backend'. (erc-with-server-buffer, erc-server-user, erc-channel-user, erc-get-channel-user, erc-get-server-user): Move to lisp/erc/erc-common.el. (erc-add-server-user, erc-remove-server-user, erc-channel-user-owner-p, erc-channel-user-admin-p, erc-channel-user-op-p, erc-channel-user-halfop-p, erc-channel-user-voice-p): Convert from inline functions to normal functions. (define-erc-module, erc--target, erc--target-channel, erc--target-channel-local, erc-log, erc-log-aux, erc-with-buffer, erc-with-all-buffers-of-server): Move to lisp/erc/erc-common.el. (erc-channel-members-changed-hook): Relocate option to avoid compiler warning. (erc-input, erc--input-split): Move to lisp/erc/erc-common.el. (erc-controls-strip): Remove forward declaration temporarily until this file stops requiring `erc-goodies'. * test/lisp/erc/erc-networks-tests.el: Require `erc' instead of `erc-networks'. * test/lisp/erc/erc.el (erc--meta--backend-dependencies): Remove unused test. --- lisp/erc/erc-backend.el | 127 ++++++++-- lisp/erc/erc-common.el | 264 +++++++++++++++++++++ lisp/erc/erc-goodies.el | 17 +- lisp/erc/erc-networks.el | 29 ++- lisp/erc/erc.el | 346 ++++------------------------ test/lisp/erc/erc-networks-tests.el | 2 +- test/lisp/erc/erc-tests.el | 21 -- 7 files changed, 457 insertions(+), 349 deletions(-) create mode 100644 lisp/erc/erc-common.el diff --git a/lisp/erc/erc-backend.el b/lisp/erc/erc-backend.el index 8be4894ecb..b4c9d538b7 100644 --- a/lisp/erc/erc-backend.el +++ b/lisp/erc/erc-backend.el @@ -99,24 +99,117 @@ ;;; Code: (eval-when-compile (require 'cl-lib)) -;; There's a fairly strong mutual dependency between erc.el and erc-backend.el. -;; Luckily, erc.el does not need erc-backend.el for macroexpansion whereas the -;; reverse is true: -(require 'erc) +(require 'erc-common) + +(defvar erc--target) +(defvar erc-auto-query) +(defvar erc-channel-list) +(defvar erc-channel-users) +(defvar erc-default-nicks) +(defvar erc-default-recipients) +(defvar erc-format-nick-function) +(defvar erc-format-query-as-channel-p) +(defvar erc-hide-prompt) +(defvar erc-input-marker) +(defvar erc-insert-marker) +(defvar erc-invitation) +(defvar erc-join-buffer) +(defvar erc-kill-buffer-on-part) +(defvar erc-kill-server-buffer-on-quit) +(defvar erc-log-p) +(defvar erc-minibuffer-ignored) +(defvar erc-networks--id) +(defvar erc-nick) +(defvar erc-nick-change-attempt-count) +(defvar erc-prompt-for-channel-key) +(defvar erc-prompt-hidden) +(defvar erc-reuse-buffers) +(defvar erc-verbose-server-ping) +(defvar erc-whowas-on-nosuchnick) + +(declare-function erc--open-target "erc" (target)) +(declare-function erc--target-from-string "erc" (string)) +(declare-function erc-active-buffer "erc" nil) +(declare-function erc-add-default-channel "erc" (channel)) +(declare-function erc-banlist-update "erc" (proc parsed)) +(declare-function erc-buffer-filter "erc" (predicate &optional proc)) +(declare-function erc-buffer-list-with-nick "erc" (nick proc)) +(declare-function erc-channel-begin-receiving-names "erc" nil) +(declare-function erc-channel-end-receiving-names "erc" nil) +(declare-function erc-channel-p "erc" (channel)) +(declare-function erc-channel-receive-names "erc" (names-string)) +(declare-function erc-cmd-JOIN "erc" (channel &optional key)) +(declare-function erc-connection-established "erc" (proc parsed)) +(declare-function erc-current-nick "erc" nil) +(declare-function erc-current-nick-p "erc" (nick)) +(declare-function erc-current-time "erc" (&optional specified-time)) +(declare-function erc-default-target "erc" nil) +(declare-function erc-delete-default-channel "erc" (channel &optional buffer)) +(declare-function erc-display-error-notice "erc" (parsed string)) +(declare-function erc-display-server-message "erc" (_proc parsed)) +(declare-function erc-emacs-time-to-erc-time "erc" (&optional specified-time)) +(declare-function erc-format-message "erc" (msg &rest args)) +(declare-function erc-format-privmessage "erc" (nick msg privp msgp)) +(declare-function erc-get-buffer "erc" (target &optional proc)) +(declare-function erc-handle-login "erc" nil) +(declare-function erc-handle-user-status-change "erc" (type nlh &optional l)) +(declare-function erc-ignored-reply-p "erc" (msg tgt proc)) +(declare-function erc-ignored-user-p "erc" (spec)) +(declare-function erc-is-message-ctcp-and-not-action-p "erc" (message)) +(declare-function erc-is-message-ctcp-p "erc" (message)) +(declare-function erc-log-irc-protocol "erc" (string &optional outbound)) +(declare-function erc-login "erc" nil) +(declare-function erc-make-notice "erc" (message)) +(declare-function erc-network "erc-networks" nil) +(declare-function erc-networks--id-given "erc-networks" (arg &rest args)) +(declare-function erc-networks--id-reload "erc-networks" (arg &rest args)) +(declare-function erc-nickname-in-use "erc" (nick reason)) +(declare-function erc-parse-user "erc" (string)) +(declare-function erc-process-away "erc" (proc away-p)) +(declare-function erc-process-ctcp-query "erc" (proc parsed nick login host)) +(declare-function erc-query-buffer-p "erc" (&optional buffer)) +(declare-function erc-remove-channel-member "erc" (channel nick)) +(declare-function erc-remove-channel-users "erc" nil) +(declare-function erc-remove-user "erc" (nick)) +(declare-function erc-sec-to-time "erc" (ns)) +(declare-function erc-server-buffer "erc" nil) +(declare-function erc-set-active-buffer "erc" (buffer)) +(declare-function erc-set-current-nick "erc" (nick)) +(declare-function erc-set-modes "erc" (tgt mode-string)) +(declare-function erc-time-diff "erc" (t1 t2)) +(declare-function erc-trim-string "erc" (s)) +(declare-function erc-update-mode-line "erc" (&optional buffer)) +(declare-function erc-update-mode-line-buffer "erc" (buffer)) +(declare-function erc-wash-quit-reason "erc" (reason nick login host)) + +(declare-function erc-display-message "erc" + (parsed type buffer msg &rest args)) +(declare-function erc-get-buffer-create "erc" + (server port target &optional tgt-info id)) +(declare-function erc-process-ctcp-reply "erc" + (proc parsed nick login host msg)) +(declare-function erc-update-channel-topic "erc" + (channel topic &optional modify)) +(declare-function erc-update-modes "erc" + (tgt mode-string &optional _nick _host _login)) +(declare-function erc-update-user-nick "erc" + (nick &optional new-nick host login full-name info)) +(declare-function erc-open "erc" + (&optional server port nick full-name connect passwd tgt-list + channel process client-certificate user id)) +(declare-function erc-update-channel-member "erc" + (channel nick new-nick + &optional add voice halfop op admin owner host + login full-name info update-message-time)) ;;;; Variables and options +(defvar-local erc-session-password nil + "The password used for the current session.") + (defvar erc-server-responses (make-hash-table :test #'equal) "Hash table mapping server responses to their handler hooks.") -(cl-defstruct (erc-response (:conc-name erc-response.)) - (unparsed "" :type string) - (sender "" :type string) - (command "" :type string) - (command-args '() :type list) - (contents "" :type string) - (tags '() :type list)) - ;;; User data (defvar-local erc-server-current-nick nil @@ -1673,16 +1766,6 @@ erc--parse-isupport-value (split-string value ",") (list value))))) -(defmacro erc--with-memoization (table &rest forms) - "Adapter to be migrated to erc-compat." - (declare (indent defun)) - `(cond - ((fboundp 'with-memoization) - (with-memoization ,table ,@forms)) ; 29.1 - ((fboundp 'cl--generic-with-memoization) - (cl--generic-with-memoization ,table ,@forms)) - (t ,@forms))) - (defun erc--get-isupport-entry (key &optional single) "Return an item for \"ISUPPORT\" token KEY, a symbol. When a lookup fails return nil. Otherwise return a list whose diff --git a/lisp/erc/erc-common.el b/lisp/erc/erc-common.el new file mode 100644 index 0000000000..0e63615b17 --- /dev/null +++ b/lisp/erc/erc-common.el @@ -0,0 +1,264 @@ +;;; erc-common.el --- Macros and types for ERC -*- lexical-binding:t -*- + +;; Copyright (C) 2022 Free Software Foundation, Inc. +;; +;; Maintainer: Amin Bandali <bandali@gnu.org>, F. Jason Park <jp@neverwas.me> +;; Keywords: comm, IRC, chat, client, internet +;; +;; This file is part of GNU Emacs. +;; +;; GNU Emacs is free software: you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published +;; by the Free Software Foundation, either version 3 of the License, +;; or (at your option) any later version. +;; +;; GNU Emacs is distributed in the hope that it will be useful, but +;; WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +;; General Public License for more details. +;; +;; You should have received a copy of the GNU General Public License +;; along with GNU Emacs. If not, see <https://www.gnu.org/licenses/>. + +;;; Commentary: +;;; Code: + +(eval-when-compile (require 'cl-lib) (require 'subr-x)) + +(defvar erc-channel-users) +(defvar erc-dbuf) +(defvar erc-log-p) +(defvar erc-server-users) +(defvar erc-session-server) + +(declare-function erc-downcase "erc" (string)) +(declare-function erc-get-buffer "erc" (target &optional proc)) +(declare-function erc-server-buffer "erc" nil) + +(cl-defstruct erc-input + string insertp sendp) + +(cl-defstruct (erc--input-split (:include erc-input)) + lines cmdp) + +(cl-defstruct (erc-server-user (:type vector) :named) + ;; User data + nickname host login full-name info + ;; Buffers + ;; + ;; This is an alist of the form (BUFFER . CHANNEL-DATA), where + ;; CHANNEL-DATA is either nil or an erc-channel-user struct. + (buffers nil)) + +(cl-defstruct (erc-channel-user (:type vector) :named) + voice halfop op admin owner + ;; Last message time (in the form of the return value of + ;; (current-time) + ;; + ;; This is useful for ordered name completion. + (last-message-time nil)) + +(cl-defstruct erc--target + (string "" :type string :documentation "Received name of target.") + (symbol nil :type symbol :documentation "Case-mapped name as symbol.")) + +;; At some point, it may make sense to add a query type with an +;; account field, which may help support reassociation across +;; reconnects and nick changes (likely requires v3 extensions). +;; +;; These channel variants should probably take on a `joined' field to +;; track "joinedness", which `erc-server-JOIN', `erc-server-PART', +;; etc. should toggle. Functions like `erc--current-buffer-joined-p' +;; may find it useful. + +(cl-defstruct (erc--target-channel (:include erc--target))) +(cl-defstruct (erc--target-channel-local (:include erc--target-channel))) + +(cl-defstruct (erc-response (:conc-name erc-response.)) + (unparsed "" :type string) + (sender "" :type string) + (command "" :type string) + (command-args '() :type list) + (contents "" :type string) + (tags '() :type list)) + +(defmacro define-erc-module (name alias doc enable-body disable-body + &optional local-p) + "Define a new minor mode using ERC conventions. +Symbol NAME is the name of the module. +Symbol ALIAS is the alias to use, or nil. +DOC is the documentation string to use for the minor mode. +ENABLE-BODY is a list of expressions used to enable the mode. +DISABLE-BODY is a list of expressions used to disable the mode. +If LOCAL-P is non-nil, the mode will be created as a buffer-local +mode, rather than a global one. + +This will define a minor mode called erc-NAME-mode, possibly +an alias erc-ALIAS-mode, as well as the helper functions +erc-NAME-enable, and erc-NAME-disable. + +Example: + + ;;;###autoload(autoload \\='erc-replace-mode \"erc-replace\") + (define-erc-module replace nil + \"This mode replaces incoming text according to `erc-replace-alist'.\" + ((add-hook \\='erc-insert-modify-hook + #\\='erc-replace-insert)) + ((remove-hook \\='erc-insert-modify-hook + #\\='erc-replace-insert)))" + (declare (doc-string 3) (indent defun)) + (let* ((sn (symbol-name name)) + (mode (intern (format "erc-%s-mode" (downcase sn)))) + (group (intern (format "erc-%s" (downcase sn)))) + (enable (intern (format "erc-%s-enable" (downcase sn)))) + (disable (intern (format "erc-%s-disable" (downcase sn))))) + `(progn + (define-minor-mode + ,mode + ,(format "Toggle ERC %S mode. +With a prefix argument ARG, enable %s if ARG is positive, +and disable it otherwise. If called from Lisp, enable the mode +if ARG is omitted or nil. +%s" name name doc) + ;; FIXME: We don't know if this group exists, so this `:group' may + ;; actually just silence a valid warning about the fact that the var + ;; is not associated with any group. + :global ,(not local-p) :group (quote ,group) + (if ,mode + (,enable) + (,disable))) + (defun ,enable () + ,(format "Enable ERC %S mode." + name) + (interactive) + (add-to-list 'erc-modules (quote ,name)) + (setq ,mode t) + ,@enable-body) + (defun ,disable () + ,(format "Disable ERC %S mode." + name) + (interactive) + (setq erc-modules (delq (quote ,name) erc-modules)) + (setq ,mode nil) + ,@disable-body) + ,(when (and alias (not (eq name alias))) + `(defalias + ',(intern + (format "erc-%s-mode" + (downcase (symbol-name alias)))) + #',mode)) + ;; For find-function and find-variable. + (put ',mode 'definition-name ',name) + (put ',enable 'definition-name ',name) + (put ',disable 'definition-name ',name)))) + +(defmacro erc-with-buffer (spec &rest body) + "Execute BODY in the buffer associated with SPEC. + +SPEC should have the form + + (TARGET [PROCESS]) + +If TARGET is a buffer, use it. Otherwise, use the buffer +matching TARGET in the process specified by PROCESS. + +If PROCESS is nil, use the current `erc-server-process'. +See `erc-get-buffer' for details. + +See also `with-current-buffer'. + +\(fn (TARGET [PROCESS]) BODY...)" + (declare (indent 1) (debug ((form &optional form) body))) + (let ((buf (make-symbol "buf")) + (proc (make-symbol "proc")) + (target (make-symbol "target")) + (process (make-symbol "process"))) + `(let* ((,target ,(car spec)) + (,process ,(cadr spec)) + (,buf (if (bufferp ,target) + ,target + (let ((,proc (or ,process + (and (processp erc-server-process) + erc-server-process)))) + (if (and ,target ,proc) + (erc-get-buffer ,target ,proc)))))) + (when (buffer-live-p ,buf) + (with-current-buffer ,buf + ,@body))))) + +(defmacro erc-with-server-buffer (&rest body) + "Execute BODY in the current ERC server buffer. +If no server buffer exists, return nil." + (declare (indent 0) (debug (body))) + (let ((buffer (make-symbol "buffer"))) + `(let ((,buffer (erc-server-buffer))) + (when (buffer-live-p ,buffer) + (with-current-buffer ,buffer + ,@body))))) + +(defmacro erc-with-all-buffers-of-server (process pred &rest forms) + "Execute FORMS in all buffers which have same process as this server. +FORMS will be evaluated in all buffers having the process PROCESS and +where PRED matches or in all buffers of the server process if PRED is +nil." + (declare (indent 2) (debug (form form body))) + (macroexp-let2 nil pred pred + `(erc-buffer-filter (lambda () + (when (or (not ,pred) (funcall ,pred)) + ,@forms)) + ,process))) + +(defun erc-log-aux (string) + "Do the debug logging of STRING." + (let ((cb (current-buffer)) + (point 1) + (was-eob nil) + (session-buffer (erc-server-buffer))) + (if session-buffer + (progn + (set-buffer session-buffer) + (if (not (and erc-dbuf (bufferp erc-dbuf) (buffer-live-p erc-dbuf))) + (progn + (setq erc-dbuf (get-buffer-create + (concat "*ERC-DEBUG: " + erc-session-server "*"))))) + (set-buffer erc-dbuf) + (setq point (point)) + (setq was-eob (eobp)) + (goto-char (point-max)) + (insert (concat "** " string "\n")) + (if was-eob (goto-char (point-max)) + (goto-char point)) + (set-buffer cb)) + (message "ERC: ** %s" string)))) + +(define-inline erc-log (string) + "Logs STRING if logging is on (see `erc-log-p')." + (inline-quote + (when erc-log-p + (erc-log-aux ,string)))) + +(define-inline erc-get-channel-user (nick) + "Find NICK in the current buffer's `erc-channel-users' hash table." + (inline-quote (gethash (erc-downcase ,nick) erc-channel-users))) + +(define-inline erc-get-server-user (nick) + "Find NICK in the current server's `erc-server-users' hash table." + (inline-letevals (nick) + (inline-quote (erc-with-server-buffer + (gethash (erc-downcase ,nick) erc-server-users))))) + +;; FIXME move this to erc-compat +(defmacro erc--with-memoization (table &rest forms) + "Adapter to be migrated to erc-compat." + (declare (indent defun)) + `(cond + ((fboundp 'with-memoization) + (with-memoization ,table ,@forms)) ; 29.1 + ((fboundp 'cl--generic-with-memoization) + (cl--generic-with-memoization ,table ,@forms)) + (t ,@forms))) + +(provide 'erc-common) + +;;; erc-common.el ends here diff --git a/lisp/erc/erc-goodies.el b/lisp/erc/erc-goodies.el index 8fef23945d..59b5f01f23 100644 --- a/lisp/erc/erc-goodies.el +++ b/lisp/erc/erc-goodies.el @@ -29,10 +29,23 @@ ;;; Code: -(require 'erc) - ;;; Imenu support +(require 'erc-common) + +(defvar erc-controls-highlight-regexp) +(defvar erc-controls-remove-regexp) +(defvar erc-input-marker) +(defvar erc-insert-marker) +(defvar erc-server-process) +(defvar erc-modules) +(defvar erc-log-p) + +(declare-function erc-buffer-list "erc" (&optional predicate proc)) +(declare-function erc-error "erc" (&rest args)) +(declare-function erc-extract-command-from-line "erc" (line)) +(declare-function erc-beg-of-input-line "erc" nil) + (defun erc-imenu-setup () "Setup Imenu support in an ERC buffer." (setq-local imenu-create-index-function #'erc-create-imenu-index)) diff --git a/lisp/erc/erc-networks.el b/lisp/erc/erc-networks.el index 091b8aa92d..186fbca18f 100644 --- a/lisp/erc/erc-networks.el +++ b/lisp/erc/erc-networks.el @@ -39,8 +39,33 @@ ;;; Code: -(require 'erc) (eval-when-compile (require 'cl-lib)) +(require 'erc-common) + +(defvar erc--target) +(defvar erc-insert-marker) +(defvar erc-kill-buffer-hook) +(defvar erc-kill-server-hook) +(defvar erc-modules) +(defvar erc-rename-buffers) +(defvar erc-reuse-buffers) +(defvar erc-server-announced-name) +(defvar erc-server-connected) +(defvar erc-server-parameters) +(defvar erc-server-process) +(defvar erc-session-server) + +(declare-function erc--default-target "erc" nil) +(declare-function erc--get-isupport-entry "erc-backend" (key &optional single)) +(declare-function erc-buffer-filter "erc" (predicate &optional proc)) +(declare-function erc-current-nick "erc" nil) +(declare-function erc-display-error-notice "erc" (parsed string)) +(declare-function erc-downcase "erc" (string)) +(declare-function erc-error "erc" (&rest args)) +(declare-function erc-get-buffer "erc" (target &optional proc)) +(declare-function erc-server-buffer "erc" nil) +(declare-function erc-server-process-alive "erc-backend" (&optional buffer)) +(declare-function erc-set-active-buffer "erc" (buffer)) ;; Variables @@ -813,7 +838,7 @@ erc-networks--id-given (erc-networks--id-symbol nid)) (cl-generic-define-context-rewriter erc-obsolete-var (var spec) - `((with-suppressed-warnings ((obsolete ,var)) ,var) ,spec)) + `((with-suppressed-warnings ((obsolete ,var) (free-vars ,var)) ,var) ,spec)) ;; As a catch-all, derive the symbol from the unquoted printed repr. (cl-defgeneric erc-networks--id-create (id) diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el index 0a16831fba..d97e8a65f5 100644 --- a/lisp/erc/erc.el +++ b/lisp/erc/erc.el @@ -60,6 +60,9 @@ (load "erc-loaddefs" 'noerror 'nomessage) +(require 'erc-networks) +(require 'erc-goodies) +(require 'erc-backend) (require 'cl-lib) (require 'format-spec) (require 'pp) @@ -130,29 +133,12 @@ erc-scripts "Running scripts at startup and with /LOAD." :group 'erc) -;; Defined in erc-backend -(defvar erc--server-last-reconnect-count) -(defvar erc--server-reconnecting) -(defvar erc-channel-members-changed-hook) -(defvar erc-network) -(defvar erc-networks--id) -(defvar erc-server-367-functions) -(defvar erc-server-announced-name) -(defvar erc-server-connect-function) -(defvar erc-server-connected) -(defvar erc-server-current-nick) -(defvar erc-server-lag) -(defvar erc-server-last-sent-time) -(defvar erc-server-process) -(defvar erc-server-quitting) -(defvar erc-server-reconnect-count) -(defvar erc-server-reconnecting) -(defvar erc-session-client-certificate) -(defvar erc-session-connector) -(defvar erc-session-port) -(defvar erc-session-server) -(defvar erc-session-user-full-name) -(defvar erc-session-username) +;; Forward declarations +(defvar erc-message-parsed) + +(defvar tabbar--local-hlf) +(defvar motif-version-string) +(defvar gtk-version-string) ;; tunable connection and authentication parameters @@ -347,9 +333,6 @@ erc-channel-hide-list :group 'erc-ignore :type 'erc-message-type) -(defvar-local erc-session-password nil - "The password used for the current session.") - (defcustom erc-disconnected-hook nil "Run this hook with arguments (NICK IP REASON) when disconnected. This happens before automatic reconnection. Note, that @@ -449,54 +432,14 @@ erc-downcase erc--casemapping-rfc1459)) (buffer-string))))) -(defmacro erc-with-server-buffer (&rest body) - "Execute BODY in the current ERC server buffer. -If no server buffer exists, return nil." - (declare (indent 0) (debug (body))) - (let ((buffer (make-symbol "buffer"))) - `(let ((,buffer (erc-server-buffer))) - (when (buffer-live-p ,buffer) - (with-current-buffer ,buffer - ,@body))))) - -(cl-defstruct (erc-server-user (:type vector) :named) - ;; User data - nickname host login full-name info - ;; Buffers - ;; - ;; This is an alist of the form (BUFFER . CHANNEL-DATA), where - ;; CHANNEL-DATA is either nil or an erc-channel-user struct. - (buffers nil) - ) - -(cl-defstruct (erc-channel-user (:type vector) :named) - voice halfop op admin owner - ;; Last message time (in the form of the return value of - ;; (current-time) - ;; - ;; This is useful for ordered name completion. - (last-message-time nil)) - -(define-inline erc-get-channel-user (nick) - "Find NICK in the current buffer's `erc-channel-users' hash table." - (inline-quote (gethash (erc-downcase ,nick) erc-channel-users))) - -(define-inline erc-get-server-user (nick) - "Find NICK in the current server's `erc-server-users' hash table." - (inline-letevals (nick) - (inline-quote (erc-with-server-buffer - (gethash (erc-downcase ,nick) erc-server-users))))) - -(define-inline erc-add-server-user (nick user) +(defun erc-add-server-user (nick user) "This function is for internal use only. Adds USER with nickname NICK to the `erc-server-users' hash table." - (inline-letevals (nick user) - (inline-quote - (erc-with-server-buffer - (puthash (erc-downcase ,nick) ,user erc-server-users))))) + (erc-with-server-buffer + (puthash (erc-downcase nick) user erc-server-users))) -(define-inline erc-remove-server-user (nick) +(defun erc-remove-server-user (nick) "This function is for internal use only. Removes the user with nickname NICK from the `erc-server-users' @@ -504,10 +447,8 @@ erc-remove-server-user `erc-channel-users' lists of other buffers. See also: `erc-remove-user'." - (inline-letevals (nick) - (inline-quote - (erc-with-server-buffer - (remhash (erc-downcase ,nick) erc-server-users))))) + (erc-with-server-buffer + (remhash (erc-downcase nick) erc-server-users))) (defun erc-change-user-nickname (user new-nick) "This function is for internal use only. @@ -578,55 +519,45 @@ erc-remove-channel-users erc-channel-users) (clrhash erc-channel-users))) -(define-inline erc-channel-user-owner-p (nick) +(defun erc-channel-user-owner-p (nick) "Return non-nil if NICK is an owner of the current channel." - (inline-letevals (nick) - (inline-quote - (and ,nick - (hash-table-p erc-channel-users) - (let ((cdata (erc-get-channel-user ,nick))) - (and cdata (cdr cdata) - (erc-channel-user-owner (cdr cdata)))))))) - -(define-inline erc-channel-user-admin-p (nick) + (and nick + (hash-table-p erc-channel-users) + (let ((cdata (erc-get-channel-user nick))) + (and cdata (cdr cdata) + (erc-channel-user-owner (cdr cdata)))))) + +(defun erc-channel-user-admin-p (nick) "Return non-nil if NICK is an admin in the current channel." - (inline-letevals (nick) - (inline-quote - (and ,nick + (and nick (hash-table-p erc-channel-users) - (let ((cdata (erc-get-channel-user ,nick))) + (let ((cdata (erc-get-channel-user nick))) (and cdata (cdr cdata) - (erc-channel-user-admin (cdr cdata)))))))) + (erc-channel-user-admin (cdr cdata)))))) -(define-inline erc-channel-user-op-p (nick) +(defun erc-channel-user-op-p (nick) "Return non-nil if NICK is an operator in the current channel." - (inline-letevals (nick) - (inline-quote - (and ,nick + (and nick (hash-table-p erc-channel-users) - (let ((cdata (erc-get-channel-user ,nick))) + (let ((cdata (erc-get-channel-user nick))) (and cdata (cdr cdata) - (erc-channel-user-op (cdr cdata)))))))) + (erc-channel-user-op (cdr cdata)))))) -(define-inline erc-channel-user-halfop-p (nick) +(defun erc-channel-user-halfop-p (nick) "Return non-nil if NICK is a half-operator in the current channel." - (inline-letevals (nick) - (inline-quote - (and ,nick + (and nick (hash-table-p erc-channel-users) - (let ((cdata (erc-get-channel-user ,nick))) + (let ((cdata (erc-get-channel-user nick))) (and cdata (cdr cdata) - (erc-channel-user-halfop (cdr cdata)))))))) + (erc-channel-user-halfop (cdr cdata)))))) -(define-inline erc-channel-user-voice-p (nick) +(defun erc-channel-user-voice-p (nick) "Return non-nil if NICK has voice in the current channel." - (inline-letevals (nick) - (inline-quote - (and ,nick + (and nick (hash-table-p erc-channel-users) - (let ((cdata (erc-get-channel-user ,nick))) + (let ((cdata (erc-get-channel-user nick))) (and cdata (cdr cdata) - (erc-channel-user-voice (cdr cdata)))))))) + (erc-channel-user-voice (cdr cdata)))))) (defun erc-get-channel-user-list () "Return a list of users in the current channel. @@ -1375,96 +1306,6 @@ erc-debug-log-file (defvar-local erc-dbuf nil) -(defmacro define-erc-module (name alias doc enable-body disable-body - &optional local-p) - "Define a new minor mode using ERC conventions. -Symbol NAME is the name of the module. -Symbol ALIAS is the alias to use, or nil. -DOC is the documentation string to use for the minor mode. -ENABLE-BODY is a list of expressions used to enable the mode. -DISABLE-BODY is a list of expressions used to disable the mode. -If LOCAL-P is non-nil, the mode will be created as a buffer-local -mode, rather than a global one. - -This will define a minor mode called erc-NAME-mode, possibly -an alias erc-ALIAS-mode, as well as the helper functions -erc-NAME-enable, and erc-NAME-disable. - -Example: - - ;;;###autoload(autoload \\='erc-replace-mode \"erc-replace\") - (define-erc-module replace nil - \"This mode replaces incoming text according to `erc-replace-alist'.\" - ((add-hook \\='erc-insert-modify-hook - #\\='erc-replace-insert)) - ((remove-hook \\='erc-insert-modify-hook - #\\='erc-replace-insert)))" - (declare (doc-string 3) (indent defun)) - (let* ((sn (symbol-name name)) - (mode (intern (format "erc-%s-mode" (downcase sn)))) - (group (intern (format "erc-%s" (downcase sn)))) - (enable (intern (format "erc-%s-enable" (downcase sn)))) - (disable (intern (format "erc-%s-disable" (downcase sn))))) - `(progn - (define-minor-mode - ,mode - ,(format "Toggle ERC %S mode. -With a prefix argument ARG, enable %s if ARG is positive, -and disable it otherwise. If called from Lisp, enable the mode -if ARG is omitted or nil. -%s" name name doc) - ;; FIXME: We don't know if this group exists, so this `:group' may - ;; actually just silence a valid warning about the fact that the var - ;; is not associated with any group. - :global ,(not local-p) :group (quote ,group) - (if ,mode - (,enable) - (,disable))) - (defun ,enable () - ,(format "Enable ERC %S mode." - name) - (interactive) - (add-to-list 'erc-modules (quote ,name)) - (setq ,mode t) - ,@enable-body) - (defun ,disable () - ,(format "Disable ERC %S mode." - name) - (interactive) - (setq erc-modules (delq (quote ,name) erc-modules)) - (setq ,mode nil) - ,@disable-body) - ,(when (and alias (not (eq name alias))) - `(defalias - ',(intern - (format "erc-%s-mode" - (downcase (symbol-name alias)))) - #',mode)) - ;; For find-function and find-variable. - (put ',mode 'definition-name ',name) - (put ',enable 'definition-name ',name) - (put ',disable 'definition-name ',name)))) - -;; The rationale for favoring inheritance here (nicer dispatch) is -;; kinda flimsy since there aren't yet any actual methods. - -(cl-defstruct erc--target - (string "" :type string :documentation "Received name of target.") - (symbol nil :type symbol :documentation "Case-mapped name as symbol.")) - -;; These should probably take on a `joined' field to track joinedness, -;; which should be toggled by `erc-server-JOIN', `erc-server-PART', -;; etc. Functions like `erc--current-buffer-joined-p' (bug#48598) may -;; find it useful. - -(cl-defstruct (erc--target-channel (:include erc--target))) - -(cl-defstruct (erc--target-channel-local (:include erc--target-channel))) - -;; At some point, it may make sense to add a query type with an -;; account field, which may help support reassociation across -;; reconnects and nick changes (likely requires v3 extensions). - (defun erc--target-from-string (string) "Construct an `erc--target' variant from STRING." (funcall (if (erc-channel-p string) @@ -1514,12 +1355,6 @@ erc-once-with-server-event (add-hook hook fun nil t) fun)) -(define-inline erc-log (string) - "Logs STRING if logging is on (see `erc-log-p')." - (inline-quote - (when erc-log-p - (erc-log-aux ,string)))) - (defun erc-server-buffer () "Return the server buffer for the current buffer's process. The buffer-local variable `erc-server-process' is used to find @@ -1575,29 +1410,7 @@ erc-ison-p (if erc-online-p "" "not ")) erc-online-p)))) -(defun erc-log-aux (string) - "Do the debug logging of STRING." - (let ((cb (current-buffer)) - (point 1) - (was-eob nil) - (session-buffer (erc-server-buffer))) - (if session-buffer - (progn - (set-buffer session-buffer) - (if (not (and erc-dbuf (bufferp erc-dbuf) (buffer-live-p erc-dbuf))) - (progn - (setq erc-dbuf (get-buffer-create - (concat "*ERC-DEBUG: " - erc-session-server "*"))))) - (set-buffer erc-dbuf) - (setq point (point)) - (setq was-eob (eobp)) - (goto-char (point-max)) - (insert (concat "** " string "\n")) - (if was-eob (goto-char (point-max)) - (goto-char point)) - (set-buffer cb)) - (message "ERC: ** %s" string)))) + ;; Last active buffer, to print server messages in the right place @@ -1838,40 +1651,6 @@ erc-member-ignore-case (throw 'result list) (setq list (cdr list)))))) -(defmacro erc-with-buffer (spec &rest body) - "Execute BODY in the buffer associated with SPEC. - -SPEC should have the form - - (TARGET [PROCESS]) - -If TARGET is a buffer, use it. Otherwise, use the buffer -matching TARGET in the process specified by PROCESS. - -If PROCESS is nil, use the current `erc-server-process'. -See `erc-get-buffer' for details. - -See also `with-current-buffer'. - -\(fn (TARGET [PROCESS]) BODY...)" - (declare (indent 1) (debug ((form &optional form) body))) - (let ((buf (make-symbol "buf")) - (proc (make-symbol "proc")) - (target (make-symbol "target")) - (process (make-symbol "process"))) - `(let* ((,target ,(car spec)) - (,process ,(cadr spec)) - (,buf (if (bufferp ,target) - ,target - (let ((,proc (or ,process - (and (processp erc-server-process) - erc-server-process)))) - (if (and ,target ,proc) - (erc-get-buffer ,target ,proc)))))) - (when (buffer-live-p ,buf) - (with-current-buffer ,buf - ,@body))))) - (defun erc-get-buffer (target &optional proc) "Return the buffer matching TARGET in the process PROC. If PROC is not supplied, all processes are searched." @@ -1918,18 +1697,6 @@ erc-buffer-list (setq predicate (lambda () t))) (erc-buffer-filter predicate proc)) -(defmacro erc-with-all-buffers-of-server (process pred &rest forms) - "Execute FORMS in all buffers which have same process as this server. -FORMS will be evaluated in all buffers having the process PROCESS and -where PRED matches or in all buffers of the server process if PRED is -nil." - (declare (indent 1) (debug (form form body))) - (macroexp-let2 nil pred pred - `(erc-buffer-filter (lambda () - (when (or (not ,pred) (funcall ,pred)) - ,@forms)) - ,process))) - (define-obsolete-function-alias 'erc-iswitchb #'erc-switch-to-buffer "25.1") (defun erc--switch-to-buffer (&optional arg) (read-buffer "Switch to ERC buffer: " @@ -2874,8 +2641,6 @@ erc-lurker-cleanup-interval consumption of lurker state during long Emacs sessions and/or ERC sessions with large numbers of incoming PRIVMSGs.") -(defvar erc-message-parsed) - (defun erc-lurker-update-status (_message) "Update `erc-lurker-state' if necessary. @@ -4089,9 +3854,6 @@ erc-cmd-SERVER t) (put 'erc-cmd-SERVER 'process-not-needed t) -(defvar motif-version-string) -(defvar gtk-version-string) - (defun erc-cmd-SV () "Say the current ERC and Emacs version into channel." (erc-send-message (format "I'm using ERC %s with GNU Emacs %s (%s%s)%s." @@ -5347,6 +5109,12 @@ erc-parse-prefix (setq i (1+ i))) alist)))) +(defcustom erc-channel-members-changed-hook nil + "This hook is called every time the variable `channel-members' changes. +The buffer where the change happened is current while this hook is called." + :group 'erc-hooks + :type 'hook) + (defun erc-channel-receive-names (names-string) "This function is for internal use only. @@ -5390,13 +5158,6 @@ erc-channel-receive-names name name t voice halfop op admin owner))))) (run-hooks 'erc-channel-members-changed-hook))) - -(defcustom erc-channel-members-changed-hook nil - "This hook is called every time the variable `channel-members' changes. -The buffer where the change happened is current while this hook is called." - :group 'erc-hooks - :type 'hook) - (defun erc-update-user-nick (nick &optional new-nick host login full-name info) "Update the stored user information for the user with nickname NICK. @@ -6006,12 +5767,6 @@ erc-user-input (defvar erc-command-regexp "^/\\([A-Za-z']+\\)\\(\\s-+.*\\|\\s-*\\)$" "Regular expression used for matching commands in ERC.") -(cl-defstruct erc-input - string insertp sendp) - -(cl-defstruct (erc--input-split (:include erc-input)) - lines cmdp) - (defun erc--discard-trailing-multiline-nulls (state) "Ensure last line of STATE's string is non-null. But only when `erc-send-whitespace-lines' is non-nil. STATE is @@ -6957,9 +6712,6 @@ erc-format-lag-time (t "")))) ;; erc-goodies is required at end of this file. -(declare-function erc-controls-strip "erc-goodies" (str)) - -(defvar tabbar--local-hlf) (defun erc-update-mode-line-buffer (buffer) "Update the mode line in a single ERC buffer BUFFER." @@ -7457,12 +7209,4 @@ erc-handle-irc-url (provide 'erc) -(require 'erc-backend) - -;; Deprecated. We might eventually stop requiring the goodies automatically. -;; IMPORTANT: This require must appear _after_ the above (provide 'erc) to -;; avoid a recursive require error when byte-compiling the entire package. -(require 'erc-goodies) -(require 'erc-networks) - ;;; erc.el ends here diff --git a/test/lisp/erc/erc-networks-tests.el b/test/lisp/erc/erc-networks-tests.el index 66a334b709..32bdfa11ff 100644 --- a/test/lisp/erc/erc-networks-tests.el +++ b/test/lisp/erc/erc-networks-tests.el @@ -20,7 +20,7 @@ ;;; Code: (require 'ert-x) ; cl-lib -(require 'erc-networks) +(require 'erc) (defun erc-networks-tests--create-dead-proc (&optional buf) (let ((p (start-process "true" (or buf (current-buffer)) "true"))) diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el index 4971d0e194..39b65fd5e1 100644 --- a/test/lisp/erc/erc-tests.el +++ b/test/lisp/erc/erc-tests.el @@ -48,27 +48,6 @@ erc--read-time-period (cl-letf (((symbol-function 'read-string) (lambda (&rest _) "1d"))) (should (equal (erc--read-time-period "foo: ") 86400)))) -(ert-deftest erc--meta--backend-dependencies () - (with-temp-buffer - (insert-file-contents-literally - (concat (file-name-sans-extension (symbol-file 'erc)) ".el")) - (let ((beg (search-forward ";; Defined in erc-backend")) - (end (search-forward "\n\n")) - vars) - (save-excursion - (save-restriction - (narrow-to-region beg end) - (goto-char (point-min)) - (with-syntax-table lisp-data-mode-syntax-table - (condition-case _ - (while (push (cadr (read (current-buffer))) vars)) - (end-of-file))))) - (should (= (point) end)) - (dolist (var vars) - (setq var (concat "\\_<" (symbol-name var) "\\_>")) - (ert-info (var) - (should (save-excursion (search-forward-regexp var nil t)))))))) - (ert-deftest erc-with-all-buffers-of-server () (let (proc-exnet proc-onet -- 2.36.1 ^ permalink raw reply related [flat|nested] 12+ messages in thread
[parent not found: <877d4d9m6c.fsf@neverwas.me>]
* bug#56340: Change erc dependencies [not found] ` <877d4d9m6c.fsf@neverwas.me> @ 2022-09-05 19:33 ` Lars Ingebrigtsen [not found] ` <875yi1zkdu.fsf@gnus.org> 1 sibling, 0 replies; 12+ messages in thread From: Lars Ingebrigtsen @ 2022-09-05 19:33 UTC (permalink / raw) To: J.P.; +Cc: 56340, Amin Bandali, dick.r.chiang, emacs-erc "J.P." <jp@neverwas.me> writes: > [1] If we did stick with a new file, what's the best name for such a > thing? I just went with `erc-common', for now, but perhaps something > ending in -macs or -core would be more faithful to the platform? erc-common is fine. ^ permalink raw reply [flat|nested] 12+ messages in thread
[parent not found: <875yi1zkdu.fsf@gnus.org>]
* bug#56340: Change erc dependencies [not found] ` <875yi1zkdu.fsf@gnus.org> @ 2022-09-06 13:54 ` J.P. 2022-09-06 14:03 ` Lars Ingebrigtsen [not found] ` <87tu5kr45x.fsf@gnus.org> 0 siblings, 2 replies; 12+ messages in thread From: J.P. @ 2022-09-06 13:54 UTC (permalink / raw) To: Lars Ingebrigtsen; +Cc: 56340, Amin Bandali, dick.r.chiang, emacs-erc Lars Ingebrigtsen <larsi@gnus.org> writes: > "J.P." <jp@neverwas.me> writes: > >> [1] If we did stick with a new file, what's the best name for such a >> thing? I just went with `erc-common', for now, but perhaps something >> ending in -macs or -core would be more faithful to the platform? > > erc-common is fine. Cool, thanks. BTW (for anyone who cares), I'm pretty sure going this route would mean having to update ERC's ELPA recipe. Actually, since we'll likely be adding more files later this year (SASL, for one), it might be prudent to just take care of that now, regardless. Bandali added the original entry, so he's probably better equipped to handle this, but rather than list the entire manifest, what about doing something like this? :core ("lisp/erc/" "doc/emacs/doclicense.texi" "doc/emacs/docstyle.texi" "doc/misc/erc.texi" "etc/ERC-NEWS" "COPYING") :excludes ("lisp/erc/erc-loaddefs.el" "lisp/erc/ChangeLog.*") I tried the above with a local checkout of ELPA, and it seemed to build all right. But, as usual, I don't know what I'm doing. ^ permalink raw reply [flat|nested] 12+ messages in thread
* bug#56340: Change erc dependencies 2022-09-06 13:54 ` J.P. @ 2022-09-06 14:03 ` Lars Ingebrigtsen [not found] ` <87tu5kr45x.fsf@gnus.org> 1 sibling, 0 replies; 12+ messages in thread From: Lars Ingebrigtsen @ 2022-09-06 14:03 UTC (permalink / raw) To: J.P.; +Cc: 56340, Amin Bandali, dick.r.chiang, emacs-erc "J.P." <jp@neverwas.me> writes: > I tried the above with a local checkout of ELPA, and it seemed to build > all right. But, as usual, I don't know what I'm doing. I don't know about ELPA manifests either; perhaps somebody else can chime in... ^ permalink raw reply [flat|nested] 12+ messages in thread
[parent not found: <87tu5kr45x.fsf@gnus.org>]
* bug#56340: Change erc dependencies (ELPA question) [not found] ` <87tu5kr45x.fsf@gnus.org> @ 2022-10-12 2:52 ` J.P. [not found] ` <875ygp3g9j.fsf_-_@neverwas.me> 1 sibling, 0 replies; 12+ messages in thread From: J.P. @ 2022-10-12 2:52 UTC (permalink / raw) To: Stefan Monnier Cc: Lars Ingebrigtsen, 56340, Amin Bandali, dick.r.chiang, emacs-erc [-- Attachment #1: Type: text/plain, Size: 486 bytes --] Hi Stefan, Lars Ingebrigtsen <larsi@gnus.org> writes: > I don't know about ELPA manifests either; perhaps somebody else can > chime in... ERC will be introducing some new files soon, but not all in one go. I was therefore wondering if it'd be possible to modify our ELPA-packages entry to be more resilient to piecemeal changes. The attached patch appears to produce an identical tarball, but it's quite possible I'm just fooling myself. Can you take a peek sometime? Thanks, J.P. [-- Warning: decoded text below may be mangled, UTF-8 assumed --] [-- Attachment #2: 0001-elpa-packages-erc-Use-lisp-erc-and-excludes.patch --] [-- Type: text/x-patch, Size: 2229 bytes --] From e53b67887c194092bbf7e1f077e5592d7e8df71c Mon Sep 17 00:00:00 2001 From: "F. Jason Park" <jp@neverwas.me> Date: Tue, 11 Oct 2022 18:51:30 -0700 Subject: [PATCH] * elpa-packages (erc): Use lisp/erc/ and `:excludes' --- elpa-packages | 38 ++------------------------------------ 1 file changed, 2 insertions(+), 36 deletions(-) diff --git a/elpa-packages b/elpa-packages index 8471f70032..015e21caf4 100644 --- a/elpa-packages +++ b/elpa-packages @@ -296,47 +296,13 @@ ("enwc" :url "hg::https://hg.savannah.nongnu.org/hgweb/enwc/") ("epoch-view" :url nil) ("erc" - :core ("lisp/erc/erc-autoaway.el" - "lisp/erc/erc-backend.el" - "lisp/erc/erc-button.el" - "lisp/erc/erc-capab.el" - "lisp/erc/erc-compat.el" - "lisp/erc/erc-dcc.el" - "lisp/erc/erc-desktop-notifications.el" - "lisp/erc/erc-ezbounce.el" - "lisp/erc/erc-fill.el" - "lisp/erc/erc-goodies.el" - "lisp/erc/erc-ibuffer.el" - "lisp/erc/erc-identd.el" - "lisp/erc/erc-imenu.el" - "lisp/erc/erc-join.el" - "lisp/erc/erc-lang.el" - "lisp/erc/erc-list.el" - "lisp/erc/erc-log.el" - "lisp/erc/erc-match.el" - "lisp/erc/erc-menu.el" - "lisp/erc/erc-netsplit.el" - "lisp/erc/erc-networks.el" - "lisp/erc/erc-notify.el" - "lisp/erc/erc-page.el" - "lisp/erc/erc-pcomplete.el" - "lisp/erc/erc-replace.el" - "lisp/erc/erc-ring.el" - "lisp/erc/erc-services.el" - "lisp/erc/erc-sound.el" - "lisp/erc/erc-speedbar.el" - "lisp/erc/erc-spelling.el" - "lisp/erc/erc-stamp.el" - "lisp/erc/erc-status-sidebar.el" - "lisp/erc/erc-track.el" - "lisp/erc/erc-truncate.el" - "lisp/erc/erc-xdcc.el" - "lisp/erc/erc.el" + :core ("lisp/erc/" "doc/emacs/doclicense.texi" "doc/emacs/docstyle.texi" "doc/misc/erc.texi" "etc/ERC-NEWS" "COPYING") + :excludes ("lisp/erc/erc-loaddefs.el" "lisp/erc/ChangeLog.*") :shell-command "(echo '@set ERCDIST from GNU ELPA'; echo '@set EMACSVER') >emacsver.texi" :doc "erc.texi" :news "ERC-NEWS") -- 2.37.3 ^ permalink raw reply related [flat|nested] 12+ messages in thread
[parent not found: <875ygp3g9j.fsf_-_@neverwas.me>]
* bug#56340: Change erc dependencies (ELPA question) [not found] ` <875ygp3g9j.fsf_-_@neverwas.me> @ 2022-10-12 17:45 ` Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors [not found] ` <jwv4jw9lz5z.fsf-monnier+emacs@gnu.org> 1 sibling, 0 replies; 12+ messages in thread From: Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors @ 2022-10-12 17:45 UTC (permalink / raw) To: J.P.; +Cc: Lars Ingebrigtsen, 56340, Amin Bandali, dick.r.chiang, emacs-erc > ERC will be introducing some new files soon, but not all in one go. I > was therefore wondering if it'd be possible to modify our ELPA-packages > entry to be more resilient to piecemeal changes. > > The attached patch appears to produce an identical tarball, but it's > quite possible I'm just fooling myself. Can you take a peek sometime? That sounds sane. I recommend you install it and then next time we make a change to `erc.el` (without changing the `Version:` yet) we can check the generated package on https://elpa.gnu.org/devel/erc.html Note that GNU-devel :core packages are only produced when the "main" file (e.g. `erc.el`) is modified (contrary to non-:core packages, where any new commit causes a new tarball to be produced). Stefan ^ permalink raw reply [flat|nested] 12+ messages in thread
[parent not found: <jwv4jw9lz5z.fsf-monnier+emacs@gnu.org>]
* bug#56340: Change erc dependencies (ELPA question) [not found] ` <jwv4jw9lz5z.fsf-monnier+emacs@gnu.org> @ 2022-10-13 2:49 ` J.P. 0 siblings, 0 replies; 12+ messages in thread From: J.P. @ 2022-10-13 2:49 UTC (permalink / raw) To: Stefan Monnier Cc: Lars Ingebrigtsen, 56340, Amin Bandali, dick.r.chiang, emacs-erc Stefan Monnier <monnier@iro.umontreal.ca> writes: > I recommend you install it and then next time we make > a change to `erc.el` (without changing the `Version:` yet) we can check > the generated package on https://elpa.gnu.org/devel/erc.html Sounds good. Installed. > Note that GNU-devel :core packages are only produced when the "main" > file (e.g. `erc.el`) is modified (contrary to non-:core packages, where > any new commit causes a new tarball to be produced). TIL. Thanks. ^ permalink raw reply [flat|nested] 12+ messages in thread
end of thread, other threads:[~2022-10-13 2:49 UTC | newest] Thread overview: 12+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2022-07-01 15:23 bug#56340: 29.0.50; [PATCH] Don't ask people to order requires dick.r.chiang 2022-07-02 12:32 ` Lars Ingebrigtsen 2022-07-04 23:36 ` J.P. [not found] ` <87czekcuxj.fsf@neverwas.me> 2022-07-05 1:59 ` dick 2022-07-05 6:39 ` bug#56340: Change erc dependencies J.P. [not found] ` <87sfng83n8.fsf_-_@neverwas.me> 2022-07-16 14:17 ` J.P. [not found] ` <877d4d9m6c.fsf@neverwas.me> 2022-09-05 19:33 ` Lars Ingebrigtsen [not found] ` <875yi1zkdu.fsf@gnus.org> 2022-09-06 13:54 ` J.P. 2022-09-06 14:03 ` Lars Ingebrigtsen [not found] ` <87tu5kr45x.fsf@gnus.org> 2022-10-12 2:52 ` bug#56340: Change erc dependencies (ELPA question) J.P. [not found] ` <875ygp3g9j.fsf_-_@neverwas.me> 2022-10-12 17:45 ` Stefan Monnier via Bug reports for GNU Emacs, the Swiss army knife of text editors [not found] ` <jwv4jw9lz5z.fsf-monnier+emacs@gnu.org> 2022-10-13 2:49 ` J.P.
Code repositories for project(s) associated with this external index https://git.savannah.gnu.org/cgit/emacs.git https://git.savannah.gnu.org/cgit/emacs/org-mode.git This is an external index of several public inboxes, see mirroring instructions on how to clone and mirror all data and code used by this external index.