From 01a2aa830b73028aecf1f7dae7dadba7467a3144 Mon Sep 17 00:00:00 2001 From: "F. Jason Park" Date: Wed, 8 Mar 2023 06:14:36 -0800 Subject: [PATCH 1/1] Add conditional erc-server-reconnect-function * lisp/erc/erc-backend.el (erc--server-reconnect-timer, erc-server-delayed-check-reconnect): Add possible alternate value for option `erc-server-reconnect-function' that only attempts to reconnect after hearing back from the server. Also add helper variable. --- lisp/erc/erc-backend.el | 56 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 56 insertions(+) diff --git a/lisp/erc/erc-backend.el b/lisp/erc/erc-backend.el index 567443f5329..d289df98bab 100644 --- a/lisp/erc/erc-backend.el +++ b/lisp/erc/erc-backend.el @@ -744,6 +744,62 @@ erc-server-delayed-reconnect (with-current-buffer buffer (erc-server-reconnect)))) +(defvar-local erc--server-reconnect-timeout nil) + +(defun erc-server-delayed-check-reconnect (buffer) + "Wait for internet connectivity before trying to reconnect. +BUFFER is the server buffer for the current connection." + ;; This may appear to hang for a good while at various places + ;; because it calls wait_reading_process_output a bunch. It does at + ;; least sometimes print "Waiting for socket from ..." or similar. + (with-current-buffer buffer + (setq erc--server-reconnect-timeout + (min 300 (* (or erc--server-reconnect-timeout + erc-server-reconnect-timeout) + 2))) + (let ((reschedule + (lambda (proc) + (let ((erc-server-reconnect-timeout + erc--server-reconnect-timeout)) + (with-current-buffer buffer + (delete-process proc) + (erc-display-message nil 'error buffer "Nobody home...") + (erc-schedule-reconnect buffer 0)))))) + (condition-case _ + (let ((proc (funcall erc-session-connector + "*erc-connectivity-check" nil + erc-session-server erc-session-port + :nowait t)) + tls-check) + (when (and (not (eq erc-session-connector + #'erc-open-network-stream)) + (process-contact proc :tls-parameters)) + (setq tls-check + (run-at-time + 1 1 (lambda (proc) + (unless (eq 'connect (process-status proc)) + (cancel-timer tls-check)) + (when (eq 'failed (process-status proc)) + (funcall reschedule proc))) + proc))) + (set-process-filter + proc (lambda (proc _) + (delete-process proc) + (with-current-buffer buffer + (setq erc--server-reconnect-timeout nil)) + (run-at-time nil nil #'erc-server-delayed-reconnect + buffer))) + (set-process-sentinel + proc (lambda (cproc event) + (with-current-buffer buffer + (pcase event + ("open\n" + (run-at-time nil nil #'send-string + cproc "PING *connect-check*\r\n")) + ("connection broken by remote peer\n" + (funcall reschedule cproc))))))) + (file-error (funcall reschedule nil)))))) + (defun erc-server-filter-function (process string) "The process filter for the ERC server." (with-current-buffer (process-buffer process) -- 2.39.2