GNU bug report logs - #63288
30.0.50; Emacs 30 packages fail to build with native comp on some machines

Previous Next

Package: emacs;

Reported by: Brian Leung <leungbk <at> posteo.net>

Date: Fri, 5 May 2023 04:00:02 UTC

Severity: normal

Found in version 30.0.50

Done: Pip Cet <pipcet <at> protonmail.com>

Bug is archived. No further changes may be made.

Full log


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

From: Pip Cet <pipcet <at> protonmail.com>
To: damien <at> merenne.me
Cc: Eli Zaretskii <eliz <at> gnu.org>, Andrea Corallo <acorallo <at> gnu.org>,
 63288 <at> debbugs.gnu.org
Subject: Re: bug#63288: 30.0.50;
 Emacs 30 packages fail to build with native comp on some machines
Date: Sat, 25 Jan 2025 20:07:06 +0000
Pip Cet <pipcet <at> protonmail.com> writes:

> <damien <at> merenne.me> writes:
>
>> To reproduce, I simply have to start `emacs -Q` and eval
>>
>> ```
>> (require 'package)
>> (package-read-from-string "((emacs \"25.1\"))")
>> ```
>> in the scratch buffer:
>>
>> ```
>> Debugger entered--Lisp error: (error "Can’t read whole string")
>>   error("Can't read whole string")
>>   package-read-from-string("((emacs \"25.1\"))")
>>   (progn (package-read-from-string "((emacs \"25.1\"))"))
>>   eval((progn (package-read-from-string "((emacs \"25.1\"))")) t)
>>   elisp--eval-last-sexp(nil)
>> ```
>> Again, after re-evaluating the defun, it's working ok.
>>
>> I found something while messing around with recompiling the file.
>> If I rebuild it manually it works ok, but then rebuilding the whole emacs source tree, and it fails again.
>> So I found this: building with `make -j48` (I have a 24 core CPU) triggers the problem while building
>> with `make -j 1` does not. I attach the build.sh I used to configure the source tree, the configure and
>>  build logs, the elc file with the problem and a good version.
>
> Ouch.  It's known that make -j produces different output sometimes
> (defsubst gets inlined sometimes, sometimes it doesn't), but that's the
> first time I heard about an actual build breaking in identical settings
> depending on it!
>
> No "pure space overflow" message in the logs you sent, so it's probably
> not that.
>
> Few people have 24 cores, so it might just be that that particular
> constellation results in a weird build order.
>
> -(defalias 'package-read-from-string #[257 "\300!\211\242\243\3011\300\"\210\302\303!0\207\210\207" [read-from-string (end-of-file) error "Can't read whole string"] 7 "Read a Lisp expression from STR.\nSignal an error if the entire string was not used.\n\n(fn STR)"])
> +(defalias 'package-read-from-string #[257 "\300!\211\242\243\3011\302\303!0\207\210\207" [read-from-string (end-of-file) error "Can't read whole string"] 6 "Read a Lisp expression from STR.\nSignal an error if the entire string was not used.\n\n(fn STR)"])

(These bytecode objects are incorrect; I was in a comint buffer and ^A,
one of the most common bytecodes, was lost).

The actual disassembly of the correct code is:

byte code for package-read-from-string:
  doc:  Read a Lisp expression from STR. ...
  args: (arg1)
0	constant  read-from-string
1	stack-ref 1
2	call	  1
3	dup
4	car-safe
5	stack-ref 1
6	cdr-safe
7	constant  (end-of-file)
8	pushconditioncase 1
11	constant  read-from-string
12	stack-ref 4
13	stack-ref 2
14	call	  2
15	discard
16	constant  error
17	constant  "Can't read whole string"
18	call	  1
19	pophandler
20	return
21:1	discard
22	stack-ref 1
23	return

That's good and proper and should do the right thing.  The incorrect
code:

0	constant  read-from-string
1	stack-ref 1
2	call	  1
3	dup
4	car-safe
5	stack-ref 1
6	cdr-safe
7	constant  (end-of-file)
8	pushconditioncase 1
11	constant  error
12	constant  "Can't read whole string"
13	call	  1
14	pophandler
15	return
16:1	discard
17	stack-ref 1
18	return

omits the second call to read-string.

Lisp code:

;;;; Inferring package from current buffer
(defun package-read-from-string (str)
  "Read a Lisp expression from STR.
Signal an error if the entire string was not used."
  (pcase-let ((`(,expr . ,offset) (read-from-string str)))
    (condition-case ()
        ;; The call to `ignore' suppresses a compiler warning.
        (progn (ignore (read-from-string str offset))
               (error "Can't read whole string"))
      (end-of-file expr))))

read-from-string is side-effect-free, but not
side-effect-and-error-free.  Both the warning and the compiled code look
like the byte compiler assumed it was the latter.

I tried

(put 'read-from-string 'side-effect-free 'error-free)

and recompiled the Lisp function, and the result was identical to the
bad code.

This could be caused by byte-compile-delete-errors: setting that to t
also produces the incorrect code.

We need to figure out what was compiled in which order.  Can you

ls -lR --full-time

in the "emacs" directory so we get precise timestamps?

Thanks!

Pip





This bug report was last modified 132 days ago.

Previous Next


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