Subject: bug#70914: 29.3; Crashes often on Windows

From: Eli Zaretskii <[email-masked]>
Date: Mon, 20 May 2024 16:47:39 +0300

> From: Simen Endsjø <[email-masked]>
> Date: Sun, 19 May 2024 20:38:24 +0200
> Cc: [email-masked], [email-masked]
> 
> *****************************| System Information |*****************************

Thanks.  I think, given that every other avenue of approach has
failed, we should try the direct one: try to determine which code
called the zero PC address.  I think the following should work for
you, after Emacs crashes due to zero address:

  (gdb) thread 1
  (gdb) p/x *(uintptr_t *)$sp
  $1 = 0x1234567887654321
  (gdb) list *$

The "0x1234567887654321" stands for some 64-bit address that GDB will
show in your case, which is the address pointed by the stack pointer
register.  AFAIU, that address should hold the return address of the
function which called the "zero address", and the "list" command
should show its source code (assuming it's some Emacs code).

Please try this with a healthy Emacs process before you do it after
the crash, to make sure this procedure works.  Here's my attempt to
validate this technique:

  gdb ./emacs.exe
  ...
  (gdb) break Frecursive_edit
  Breakpoint 2 at 0x115dc2f: file emacs.c, line 2621.
  (gdb) run -Q
  Thread 1 hit Breakpoint 2, main (argc=2, argv=0x7ab2570) at emacs.c:2621
  2621      Frecursive_edit ();
  (gdb) si
  Frecursive_edit () at keyboard.c:808
  808     {
  (gdb) p/x *(uintptr_t *)$sp
  $4 = 0x76dc34
  (gdb) list *$
  0x76dc34 is in main (emacs.c:2622).
  2617    #endif
  2618
  2619      /* Enter editor command loop.  This never returns.  */
  2620      set_initial_minibuffer_mode ();
  2621      Frecursive_edit ();
  2622      eassume (false);
  2623    }
  2624    ^L
  2625    /* Sort the args so we can find the most important ones
  2626       at the beginning of argv.  */
  (gdb)

The above is in a 32-bit build of Emacs, not 64-bit build as in your
case.  The above tells us that Frecursive_edit was called from a line
before 2622 (since the return address on the stack is the address of
the first function _after_ Frecursive_edit).

Note that I used the "si" command (stepi) to step 1 machine
instruction inside Frecursive_edit and stop immediately after the
call, before the function's preamble pushes local variables onto the
stack, so as to ensure that the stack pointer points to the return
address.

I hope using this technique we will be able to find the immediate
caller of the "zero address".  Fingers crossed.