Subject: Re: bug#42790: [PATH] 27.1; Add version info into file name "emacs.pdmp" to avoid mismatch pdmp file

From: Lars Ingebrigtsen <[email-masked]>
Date: Wed, 21 Jul 2021 15:51:18 +0200

Eli Zaretskii <[email-masked]> writes:

> I hope this gets cleaned up, because I think it would be good to have
> this fixed for Emacs 27.2.

I've reworked Glenn's patch for Emacs 28...  but this is only for
installed Emacsen?  (And his comments about it needing more work is
still true.)

So that bit of the patch isn't directly relevant for the subject of this
bug report, but I guess the addition of the "--fingerprint" bit is?  (So
that we can write to emacs-FINGERPRINT.pdmp before moving to the
numbered version?)

-- 
(domestic pets only, the antidote for overdose, milk.)
   bloggy blog: http://lars.ingebrigtsen.no
diff --git a/Makefile.in b/Makefile.in
index 97d954b6ce..edca0e7cf3 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -307,6 +307,7 @@ TRANSFORM =
 EMACS_NAME = `echo emacs | sed '$(TRANSFORM)'`
 EMACS = ${EMACS_NAME}${EXEEXT}
 EMACSFULL = `echo emacs-${version} | sed '$(TRANSFORM)'`${EXEEXT}
+EMACS_PDMP = `./src/emacs${EXEEXT} --fingerprint 2>&1 | sed 's/.* //'`.pdmp
 
 # Subdirectories to make recursively.
 SUBDIR = $(NTDIR) lib lib-src src lisp
@@ -515,7 +516,7 @@ install-arch-dep:
 ifeq (${ns_self_contained},no)
 	${INSTALL_PROGRAM} $(INSTALL_STRIP) src/emacs${EXEEXT} "$(DESTDIR)${bindir}/$(EMACSFULL)"
 ifeq (${DUMPING},pdumper)
-	${INSTALL_DATA} src/emacs.pdmp "$(DESTDIR)${libexecdir}/emacs/${version}/${configuration}"/emacs.pdmp
+	${INSTALL_DATA} src/emacs.pdmp "$(DESTDIR)${libexecdir}/emacs/${version}/${configuration}"/${EMACS_PDMP}
 endif
 	-chmod 755 "$(DESTDIR)${bindir}/$(EMACSFULL)"
 ifndef NO_BIN_LINK
diff --git a/src/emacs.c b/src/emacs.c
index 866e43fda9..2f971880cc 100644
--- a/src/emacs.c
+++ b/src/emacs.c
@@ -133,6 +133,7 @@ #define MAIN_PROGRAM
 #endif
 
 #include "pdumper.h"
+#include "fingerprint.h"
 #include "epaths.h"
 
 static const char emacs_version[] = PACKAGE_VERSION;
@@ -255,6 +256,7 @@ #define MAIN_PROGRAM
 #ifdef HAVE_PDUMPER
     "\
 --dump-file FILE            read dumped state from FILE\n\
+--fingerprint               output fingerprint and exit\n\
 ",
 #endif
 #if SECCOMP_USABLE
@@ -830,6 +832,8 @@ load_pdump (int argc, char **argv)
   const char *const suffix = ".pdmp";
   int result;
   char *emacs_executable = argv[0];
+  ptrdiff_t hexbuf_size;
+  char *hexbuf;
   const char *strip_suffix =
 #if defined DOS_NT || defined CYGWIN
     ".exe"
@@ -927,9 +931,13 @@ load_pdump (int argc, char **argv)
   /* Look for "emacs.pdmp" in PATH_EXEC.  We hardcode "emacs" in
      "emacs.pdmp" so that the Emacs binary still works if the user
      copies and renames it.  */
+  hexbuf_size = 2 * sizeof fingerprint + 1;
+  hexbuf = xmalloc (hexbuf_size);
+  hexbuf_digest (hexbuf, (char *)fingerprint, sizeof fingerprint);
+  hexbuf[sizeof hexbuf] = '\0';
   needed = (strlen (path_exec)
 	    + 1
-	    + strlen (argv0_base)
+	    + strlen (hexbuf)
 	    + strlen (suffix)
 	    + 1);
   if (bufsize < needed)
@@ -938,7 +946,7 @@ load_pdump (int argc, char **argv)
       dump_file = xpalloc (NULL, &bufsize, needed - bufsize, -1, 1);
     }
   sprintf (dump_file, "%s%c%s%s",
-           path_exec, DIRECTORY_SEP, argv0_base, suffix);
+           path_exec, DIRECTORY_SEP, hexbuf, suffix);
 #if !defined (NS_SELF_CONTAINED)
   /* Assume the Emacs binary lives in a sibling directory as set up by
      the default installation configuration.  */
@@ -1387,6 +1395,23 @@ main (int argc, char **argv)
       exit (0);
     }
 
+#ifdef HAVE_PDUMPER
+  if (argmatch (argv, argc, "-fingerprint", "--fingerprint", 4,
+		NULL, &skip_args))
+    {
+      if (initialized)
+        {
+          dump_fingerprint ("fingerprint", (unsigned char *)fingerprint);
+          exit (0);
+        }
+      else
+        {
+          fputs ("Not initialized\n", stderr);
+          exit (1);
+        }
+    }
+#endif
+
   emacs_wd = emacs_get_current_dir_name ();
 #ifdef HAVE_PDUMPER
   if (dumped_with_pdumper_p ())
diff --git a/src/pdumper.c b/src/pdumper.c
index 7730ea3d06..0a97849047 100644
--- a/src/pdumper.c
+++ b/src/pdumper.c
@@ -312,7 +312,7 @@ dump_reloc_set_offset (struct dump_reloc *reloc, dump_off offset)
     error ("dump relocation out of range");
 }
 
-static void
+void
 dump_fingerprint (char const *label,
 		  unsigned char const xfingerprint[sizeof fingerprint])
 {
diff --git a/src/pdumper.h b/src/pdumper.h
index deec9af046..bc339c42da 100644
--- a/src/pdumper.h
+++ b/src/pdumper.h
@@ -50,6 +50,9 @@ #define PDUMPER_IGNORE(thing) ((void) &(thing))
 #define PDUMPER_REMEMBER_SCALAR(thing)                  \
   pdumper_remember_scalar (&(thing), sizeof (thing))
 
+extern void dump_fingerprint (const char *label,
+                              const unsigned char *xfingerprint);
+
 extern void pdumper_remember_scalar_impl (void *data, ptrdiff_t nbytes);
 
 INLINE void