GNU bug report logs - #79396
30.1; cl-copy-list can error but is declared as error-free

Previous Next

Package: emacs;

Reported by: mail <at> kisaragi-hiu.com

Date: Sat, 6 Sep 2025 17:42:02 UTC

Severity: normal

Found in version 30.1

Done: Mattias EngdegÄrd <mattias.engdegard <at> gmail.com>

Full log


Message #8 received at 79396 <at> debbugs.gnu.org (full text, mbox):

From: Eli Zaretskii <eliz <at> gnu.org>
To: mail <at> kisaragi-hiu.com, Mattias EngdegÄrd
 <mattias.engdegard <at> gmail.com>
Cc: 79396 <at> debbugs.gnu.org
Subject: Re: bug#79396: 30.1;
 cl-copy-list can error but is declared as error-free
Date: Sun, 07 Sep 2025 10:35:29 +0300
> Date: Sat, 06 Sep 2025 17:40:34 +0000
> TLS-Required: No
> From: mail--- via "Bug reports for GNU Emacs,
>  the Swiss army knife of text editors" <bug-gnu-emacs <at> gnu.org>
> 
> cl-copy-list can error if given a value that isn't nil or a cons cell,
> like (cl-copy-list 3), as expected. However, the function was declared
> (side-effect-free error-free), which contradicts this. This means it
> gets removed during bytecomp if the value is unused, even when it can
> error, resulting in a surprising discrepancy between compiled and not
> compiled code.
> 
> cl-copy-list probably should be (side-effect-free t), just like
> `reverse`.
> 
> For a showcase, run these forms in emacs -Q with eval-defun:
> 
>   (require 'cl-lib)
>   (defun my-compiled-p ()
>     "Abuse cl-copy-list to return whether this function is byte-compiled."
>     (catch 'ret
>       (condition-case _e
>           (cl-copy-list 3)
>         ;; this line should always happen but currently doesn't.
>         (wrong-type-argument (throw 'ret nil)))
>       ;; currently after byte comp the call above is removed
>       ;; so this line ends up being reached.
>       (throw 'ret t)))
>   (list (my-compiled-p)
>         (progn
>           (byte-compile #'my-compiled-p)
>           (my-compiled-p)))
>   ;; -> (nil t) if both the function wasn't byte-compiled before
> 
> This reproduction works in emacs -Q.
> 
> Additional information:
> 
> - The declaration was added in commit 48ff93ba
>   https://cgit.git.savannah.gnu.org/cgit/emacs.git/commit/?h=48ff93ba
>   which shipped in Emacs 30.1 and 30.2, and is still present on master.
> 
> - Side note: the error is implemented in a weird way by doing (car list)
>   after LIST has been checked to not be consp. The car is there just to
>   error if LIST is not nil; if LIST is nil, it can only return nil. The
>   code has been this way since cl.el was "entered into RCS" in 1993; see
>   commit fcd73769.
>   https://cgit.git.savannah.gnu.org/cgit/emacs.git/tree/lisp/emacs-lisp/cl.el?h=fcd73769#n561

Thanks.

Mattias, any comments?




This bug report was last modified 3 days ago.

Previous Next


GNU bug tracking system
Copyright (C) 1999 Darren O. Benham, 1997,2003 nCipher Corporation Ltd, 1994-97 Ian Jackson.