public inbox for binutils@sourceware.org
 help / color / mirror / Atom feed
* [PATCH] ld: pe-dll: Fix MS link.exe linking against two ld generated import libraries
@ 2022-01-04 20:14 Martin Storsjö
  2022-01-11 15:45 ` Nick Clifton
  0 siblings, 1 reply; 3+ messages in thread
From: Martin Storsjö @ 2022-01-04 20:14 UTC (permalink / raw)
  To: binutils

MS link.exe can successfully link against import libraries generated
by ld (via the --out-implib option). However, if linking against more
than one such import library at a time, then MS link.exe produces
intermixed import tables for those DLL files.

MS link.exe seems to sort the individual object files in the import
library based on their member names, without taking library
boundaries into consideration. E.g. when both libfoo.a and libbar.a
contain object files named d000.o, d001.o, d002.o, MS link.exe orders
them as libfoo.a(d000.o) libbar.a(d000.o) libfoo.a(d001.o) libbar.a(d001.o)
etc. This breaks the implicit assumption that these object files need
to be grouped tightly together within one import library.

This has not been an issue when MS link.exe links against import
libraries produced by dlltool, as the object files there use a
pseudorandom prefix (based on the dlltool process ID).

Thus this avoids needing to regenerate import libraries with dlltool, if
linking a DLL which is going to be linked against by MS link.exe.

Signed-off-by: Martin Storsjö <martin@martin.st>
---
 ld/pe-dll.c | 31 +++++++++++++++++--------------
 1 file changed, 17 insertions(+), 14 deletions(-)

diff --git a/ld/pe-dll.c b/ld/pe-dll.c
index 907fafc6208..4e47abd9b24 100644
--- a/ld/pe-dll.c
+++ b/ld/pe-dll.c
@@ -1972,6 +1972,7 @@ static int symptr;
 static int tmp_seq;
 static const char *dll_filename;
 static char *dll_symname;
+static int dll_symname_len;
 
 #define UNDSEC bfd_und_section_ptr
 
@@ -2082,8 +2083,8 @@ make_head (bfd *parent)
   char *oname;
   bfd *abfd;
 
-  oname = xmalloc (20);
-  sprintf (oname, "d%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_d%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2171,8 +2172,8 @@ make_tail (bfd *parent)
   char *oname;
   bfd *abfd;
 
-  oname = xmalloc (20);
-  sprintf (oname, "d%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_d%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2322,8 +2323,8 @@ make_one (def_file_export *exp, bfd *parent, bool include_jmp_stub)
 	}
     }
 
-  oname = xmalloc (20);
-  sprintf (oname, "d%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_d%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2508,8 +2509,8 @@ make_singleton_name_thunk (const char *import, bfd *parent)
   char *oname;
   bfd *abfd;
 
-  oname = xmalloc (20);
-  sprintf (oname, "nmth%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_nmth%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2584,8 +2585,8 @@ make_import_fixup_entry (const char *name,
   char *oname;
   bfd *abfd;
 
-  oname = xmalloc (20);
-  sprintf (oname, "fu%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_fu%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2638,8 +2639,8 @@ make_runtime_pseudo_reloc (const char *name ATTRIBUTE_UNUSED,
   bfd *abfd;
   bfd_size_type size;
 
-  oname = xmalloc (20);
-  sprintf (oname, "rtr%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_rtr%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2725,8 +2726,8 @@ pe_create_runtime_relocator_reference (bfd *parent)
   char *oname;
   bfd *abfd;
 
-  oname = xmalloc (20);
-  sprintf (oname, "ertr%06d.o", tmp_seq);
+  oname = xmalloc (20 + dll_symname_len);
+  sprintf (oname, "%s_ertr%06d.o", dll_symname, tmp_seq);
   tmp_seq++;
 
   abfd = bfd_create (oname, parent);
@@ -2833,6 +2834,7 @@ pe_dll_generate_implib (def_file *def, const char *impfilename, struct bfd_link_
 
   dll_filename = (def->name) ? def->name : dll_name;
   dll_symname = xstrdup (dll_filename);
+  dll_symname_len = strlen (dll_symname);
   for (i = 0; dll_symname[i]; i++)
     if (!ISALNUM (dll_symname[i]))
       dll_symname[i] = '_';
@@ -3201,6 +3203,7 @@ pe_process_import_defs (bfd *output_bfd, struct bfd_link_info *linfo)
 
       dll_filename = module->name;
       dll_symname = xstrdup (module->name);
+      dll_symname_len = strlen (dll_symname);
       for (j = 0; dll_symname[j]; j++)
 	if (!ISALNUM (dll_symname[j]))
 	  dll_symname[j] = '_';
-- 
2.25.1


^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: [PATCH] ld: pe-dll: Fix MS link.exe linking against two ld generated import libraries
  2022-01-04 20:14 [PATCH] ld: pe-dll: Fix MS link.exe linking against two ld generated import libraries Martin Storsjö
@ 2022-01-11 15:45 ` Nick Clifton
  2022-01-11 19:49   ` Martin Storsjö
  0 siblings, 1 reply; 3+ messages in thread
From: Nick Clifton @ 2022-01-11 15:45 UTC (permalink / raw)
  To: Martin Storsjö, binutils

Hi Martin,

> MS link.exe can successfully link against import libraries generated
> by ld (via the --out-implib option). However, if linking against more
> than one such import library at a time, then MS link.exe produces
> intermixed import tables for those DLL files.
> 
> MS link.exe seems to sort the individual object files in the import
> library based on their member names, without taking library
> boundaries into consideration. E.g. when both libfoo.a and libbar.a
> contain object files named d000.o, d001.o, d002.o, MS link.exe orders
> them as libfoo.a(d000.o) libbar.a(d000.o) libfoo.a(d001.o) libbar.a(d001.o)
> etc. This breaks the implicit assumption that these object files need
> to be grouped tightly together within one import library.
> 
> This has not been an issue when MS link.exe links against import
> libraries produced by dlltool, as the object files there use a
> pseudorandom prefix (based on the dlltool process ID).
> 
> Thus this avoids needing to regenerate import libraries with dlltool, if
> linking a DLL which is going to be linked against by MS link.exe.
> 

Patch approved and applied.  Thanks for fixing this problem.

Cheers
   Nick


^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: [PATCH] ld: pe-dll: Fix MS link.exe linking against two ld generated import libraries
  2022-01-11 15:45 ` Nick Clifton
@ 2022-01-11 19:49   ` Martin Storsjö
  0 siblings, 0 replies; 3+ messages in thread
From: Martin Storsjö @ 2022-01-11 19:49 UTC (permalink / raw)
  To: Nick Clifton; +Cc: binutils

Hi Nick,

On Tue, 11 Jan 2022, Nick Clifton wrote:

> Patch approved and applied.  Thanks for fixing this problem.

Thanks for the review!

// Martin


^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2022-01-11 19:49 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-01-04 20:14 [PATCH] ld: pe-dll: Fix MS link.exe linking against two ld generated import libraries Martin Storsjö
2022-01-11 15:45 ` Nick Clifton
2022-01-11 19:49   ` Martin Storsjö

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).