fix-windows-reproducibility.patch 35 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035
  1. From c6df45304e92aa2d7e9f2d8311ae5a0b1543daa8 Mon Sep 17 00:00:00 2001
  2. From: Nicolas Vigier <boklm@torproject.org>
  3. Date: Wed, 16 May 2018 11:07:52 +0200
  4. Subject: [PATCH] Revert "Fix LTO vs. COFF archives"
  5. This reverts commit 13e570f80cbfb299a8858ce6830e91a6cb40ab7b.
  6. ---
  7. bfd/aoutx.h | 2 -
  8. bfd/cofflink.c | 116 +++++++++++++++---
  9. bfd/ecoff.c | 164 +++++++++++++++++++++++--
  10. bfd/elflink.c | 53 ++++++--
  11. bfd/libbfd-in.h | 4 +-
  12. bfd/libbfd.h | 4 +-
  13. bfd/linker.c | 366 ++++++++++++++++++++++++++++++++++++++++----------------
  14. bfd/pdp11.c | 4 +-
  15. bfd/xcofflink.c | 4 +-
  16. 9 files changed, 560 insertions(+), 157 deletions(-)
  17. diff --git a/bfd/aoutx.h b/bfd/aoutx.h
  18. index 9385a98..6ca9c58 100644
  19. --- a/bfd/aoutx.h
  20. +++ b/bfd/aoutx.h
  21. @@ -3405,8 +3405,6 @@ aout_link_check_ar_symbols (bfd *abfd,
  22. static bfd_boolean
  23. aout_link_check_archive_element (bfd *abfd,
  24. struct bfd_link_info *info,
  25. - struct bfd_link_hash_entry *h ATTRIBUTE_UNUSED,
  26. - const char *name ATTRIBUTE_UNUSED,
  27. bfd_boolean *pneeded)
  28. {
  29. bfd *oldbfd;
  30. diff --git a/bfd/cofflink.c b/bfd/cofflink.c
  31. index 2782795..3a82640 100644
  32. --- a/bfd/cofflink.c
  33. +++ b/bfd/cofflink.c
  34. @@ -29,11 +29,9 @@
  35. #include "libcoff.h"
  36. #include "safe-ctype.h"
  37. -static bfd_boolean coff_link_add_object_symbols (bfd *, struct bfd_link_info *);
  38. -static bfd_boolean coff_link_check_archive_element
  39. - (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *, const char *,
  40. - bfd_boolean *);
  41. -static bfd_boolean coff_link_add_symbols (bfd *, struct bfd_link_info *);
  42. +static bfd_boolean coff_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info);
  43. +static bfd_boolean coff_link_check_archive_element (bfd *abfd, struct bfd_link_info *info, bfd_boolean *pneeded);
  44. +static bfd_boolean coff_link_add_symbols (bfd *abfd, struct bfd_link_info *info);
  45. /* Return TRUE if SYM is a weak, external symbol. */
  46. #define IS_WEAK_EXTERNAL(abfd, sym) \
  47. @@ -192,6 +190,74 @@ coff_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
  48. return TRUE;
  49. }
  50. +/* Look through the symbols to see if this object file should be
  51. + included in the link. */
  52. +
  53. +static bfd_boolean
  54. +coff_link_check_ar_symbols (bfd *abfd,
  55. + struct bfd_link_info *info,
  56. + bfd_boolean *pneeded,
  57. + bfd **subsbfd)
  58. +{
  59. + bfd_size_type symesz;
  60. + bfd_byte *esym;
  61. + bfd_byte *esym_end;
  62. +
  63. + *pneeded = FALSE;
  64. +
  65. + symesz = bfd_coff_symesz (abfd);
  66. + esym = (bfd_byte *) obj_coff_external_syms (abfd);
  67. + esym_end = esym + obj_raw_syment_count (abfd) * symesz;
  68. + while (esym < esym_end)
  69. + {
  70. + struct internal_syment sym;
  71. + enum coff_symbol_classification classification;
  72. +
  73. + bfd_coff_swap_sym_in (abfd, esym, &sym);
  74. +
  75. + classification = bfd_coff_classify_symbol (abfd, &sym);
  76. + if (classification == COFF_SYMBOL_GLOBAL
  77. + || classification == COFF_SYMBOL_COMMON)
  78. + {
  79. + const char *name;
  80. + char buf[SYMNMLEN + 1];
  81. + struct bfd_link_hash_entry *h;
  82. +
  83. + /* This symbol is externally visible, and is defined by this
  84. + object file. */
  85. + name = _bfd_coff_internal_syment_name (abfd, &sym, buf);
  86. + if (name == NULL)
  87. + return FALSE;
  88. + h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
  89. +
  90. + /* Auto import. */
  91. + if (!h
  92. + && info->pei386_auto_import
  93. + && CONST_STRNEQ (name, "__imp_"))
  94. + h = bfd_link_hash_lookup (info->hash, name + 6, FALSE, FALSE, TRUE);
  95. +
  96. + /* We are only interested in symbols that are currently
  97. + undefined. If a symbol is currently known to be common,
  98. + COFF linkers do not bring in an object file which defines
  99. + it. */
  100. + if (h != (struct bfd_link_hash_entry *) NULL
  101. + && h->type == bfd_link_hash_undefined)
  102. + {
  103. + if (!(*info->callbacks
  104. + ->add_archive_element) (info, abfd, name, subsbfd))
  105. + return FALSE;
  106. + *pneeded = TRUE;
  107. + return TRUE;
  108. + }
  109. + }
  110. +
  111. + esym += (sym.n_numaux + 1) * symesz;
  112. + }
  113. +
  114. + /* We do not need this object file. */
  115. + return TRUE;
  116. +}
  117. +
  118. /* Check a single archive element to see if we need to include it in
  119. the link. *PNEEDED is set according to whether this element is
  120. needed in the link or not. This is called via
  121. @@ -200,23 +266,41 @@ coff_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
  122. static bfd_boolean
  123. coff_link_check_archive_element (bfd *abfd,
  124. struct bfd_link_info *info,
  125. - struct bfd_link_hash_entry *h,
  126. - const char *name,
  127. bfd_boolean *pneeded)
  128. {
  129. - *pneeded = FALSE;
  130. + bfd *oldbfd;
  131. + bfd_boolean needed;
  132. - /* We are only interested in symbols that are currently undefined.
  133. - If a symbol is currently known to be common, COFF linkers do not
  134. - bring in an object file which defines it. */
  135. - if (h->type != bfd_link_hash_undefined)
  136. - return TRUE;
  137. + if (!_bfd_coff_get_external_symbols (abfd))
  138. + return FALSE;
  139. - if (!(*info->callbacks->add_archive_element) (info, abfd, name, &abfd))
  140. + oldbfd = abfd;
  141. + if (!coff_link_check_ar_symbols (abfd, info, pneeded, &abfd))
  142. return FALSE;
  143. - *pneeded = TRUE;
  144. - return coff_link_add_object_symbols (abfd, info);
  145. + needed = *pneeded;
  146. + if (needed)
  147. + {
  148. + /* Potentially, the add_archive_element hook may have set a
  149. + substitute BFD for us. */
  150. + if (abfd != oldbfd)
  151. + {
  152. + if (!info->keep_memory
  153. + && !_bfd_coff_free_symbols (oldbfd))
  154. + return FALSE;
  155. + if (!_bfd_coff_get_external_symbols (abfd))
  156. + return FALSE;
  157. + }
  158. + if (!coff_link_add_symbols (abfd, info))
  159. + return FALSE;
  160. + }
  161. +
  162. + if (!info->keep_memory || !needed)
  163. + {
  164. + if (!_bfd_coff_free_symbols (abfd))
  165. + return FALSE;
  166. + }
  167. + return TRUE;
  168. }
  169. /* Add all the symbols from an object file to the hash table. */
  170. diff --git a/bfd/ecoff.c b/bfd/ecoff.c
  171. index 01f51e6..2c915f0 100644
  172. --- a/bfd/ecoff.c
  173. +++ b/bfd/ecoff.c
  174. @@ -3500,29 +3500,171 @@ ecoff_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
  175. return FALSE;
  176. }
  177. +/* Factored out from ecoff_link_check_archive_element. */
  178. +
  179. +static bfd_boolean
  180. +read_ext_syms_and_strs (HDRR **symhdr, bfd_size_type *external_ext_size,
  181. + bfd_size_type *esize, void **external_ext, char **ssext, bfd *abfd,
  182. + const struct ecoff_backend_data * const backend)
  183. +{
  184. + if (! ecoff_slurp_symbolic_header (abfd))
  185. + return FALSE;
  186. +
  187. + /* If there are no symbols, we don't want it. */
  188. + if (bfd_get_symcount (abfd) == 0)
  189. + return TRUE;
  190. +
  191. + *symhdr = &ecoff_data (abfd)->debug_info.symbolic_header;
  192. +
  193. + *external_ext_size = backend->debug_swap.external_ext_size;
  194. + *esize = (*symhdr)->iextMax * *external_ext_size;
  195. + *external_ext = bfd_malloc (*esize);
  196. + if (*external_ext == NULL && *esize != 0)
  197. + return FALSE;
  198. +
  199. + if (bfd_seek (abfd, (file_ptr) (*symhdr)->cbExtOffset, SEEK_SET) != 0
  200. + || bfd_bread (*external_ext, *esize, abfd) != *esize)
  201. + return FALSE;
  202. +
  203. + *ssext = (char *) bfd_malloc ((bfd_size_type) (*symhdr)->issExtMax);
  204. + if (*ssext == NULL && (*symhdr)->issExtMax != 0)
  205. + return FALSE;
  206. +
  207. + if (bfd_seek (abfd, (file_ptr) (*symhdr)->cbSsExtOffset, SEEK_SET) != 0
  208. + || (bfd_bread (*ssext, (bfd_size_type) (*symhdr)->issExtMax, abfd)
  209. + != (bfd_size_type) (*symhdr)->issExtMax))
  210. + return FALSE;
  211. + return TRUE;
  212. +}
  213. +
  214. +static bfd_boolean
  215. +reread_ext_syms_and_strs (HDRR **symhdr, bfd_size_type *external_ext_size,
  216. + bfd_size_type *esize, void **external_ext, char **ssext, bfd *abfd,
  217. + const struct ecoff_backend_data * const backend)
  218. +{
  219. + if (*external_ext != NULL)
  220. + free (*external_ext);
  221. + *external_ext = NULL;
  222. + if (*ssext != NULL)
  223. + free (*ssext);
  224. + *ssext = NULL;
  225. + return read_ext_syms_and_strs (symhdr, external_ext_size, esize,
  226. + external_ext, ssext, abfd, backend);
  227. +}
  228. +
  229. /* This is called if we used _bfd_generic_link_add_archive_symbols
  230. because we were not dealing with an ECOFF archive. */
  231. static bfd_boolean
  232. ecoff_link_check_archive_element (bfd *abfd,
  233. struct bfd_link_info *info,
  234. - struct bfd_link_hash_entry *h,
  235. - const char *name,
  236. bfd_boolean *pneeded)
  237. {
  238. + const struct ecoff_backend_data * const backend = ecoff_backend (abfd);
  239. + void (* const swap_ext_in) (bfd *, void *, EXTR *)
  240. + = backend->debug_swap.swap_ext_in;
  241. + HDRR *symhdr;
  242. + bfd_size_type external_ext_size = 0;
  243. + void * external_ext = NULL;
  244. + bfd_size_type esize = 0;
  245. + char *ssext = NULL;
  246. + char *ext_ptr;
  247. + char *ext_end;
  248. +
  249. *pneeded = FALSE;
  250. - /* Unlike the generic linker, we do not pull in elements because
  251. - of common symbols. */
  252. - if (h->type != bfd_link_hash_undefined)
  253. - return TRUE;
  254. + /* Read in the external symbols and external strings. */
  255. + if (!read_ext_syms_and_strs (&symhdr, &external_ext_size, &esize,
  256. + &external_ext, &ssext, abfd, backend))
  257. + goto error_return;
  258. - /* Include this element. */
  259. - if (!(*info->callbacks->add_archive_element) (info, abfd, name, &abfd))
  260. - return FALSE;
  261. - *pneeded = TRUE;
  262. + /* If there are no symbols, we don't want it. */
  263. + if (bfd_get_symcount (abfd) == 0)
  264. + goto successful_return;
  265. - return ecoff_link_add_object_symbols (abfd, info);
  266. + /* Look through the external symbols to see if they define some
  267. + symbol that is currently undefined. */
  268. + ext_ptr = (char *) external_ext;
  269. + ext_end = ext_ptr + esize;
  270. + for (; ext_ptr < ext_end; ext_ptr += external_ext_size)
  271. + {
  272. + EXTR esym;
  273. + bfd_boolean def;
  274. + const char *name;
  275. + bfd *oldbfd;
  276. + struct bfd_link_hash_entry *h;
  277. +
  278. + (*swap_ext_in) (abfd, (void *) ext_ptr, &esym);
  279. +
  280. + /* See if this symbol defines something. */
  281. + if (esym.asym.st != stGlobal
  282. + && esym.asym.st != stLabel
  283. + && esym.asym.st != stProc)
  284. + continue;
  285. +
  286. + switch (esym.asym.sc)
  287. + {
  288. + case scText:
  289. + case scData:
  290. + case scBss:
  291. + case scAbs:
  292. + case scSData:
  293. + case scSBss:
  294. + case scRData:
  295. + case scCommon:
  296. + case scSCommon:
  297. + case scInit:
  298. + case scFini:
  299. + case scRConst:
  300. + def = TRUE;
  301. + break;
  302. + default:
  303. + def = FALSE;
  304. + break;
  305. + }
  306. +
  307. + if (! def)
  308. + continue;
  309. +
  310. + name = ssext + esym.asym.iss;
  311. + h = bfd_link_hash_lookup (info->hash, name, FALSE, FALSE, TRUE);
  312. +
  313. + /* Unlike the generic linker, we do not pull in elements because
  314. + of common symbols. */
  315. + if (h == NULL
  316. + || h->type != bfd_link_hash_undefined)
  317. + continue;
  318. +
  319. + /* Include this element. */
  320. + oldbfd = abfd;
  321. + if (!(*info->callbacks
  322. + ->add_archive_element) (info, abfd, name, &abfd))
  323. + goto error_return;
  324. + /* Potentially, the add_archive_element hook may have set a
  325. + substitute BFD for us. */
  326. + if (abfd != oldbfd
  327. + && !reread_ext_syms_and_strs (&symhdr, &external_ext_size, &esize,
  328. + &external_ext, &ssext, abfd, backend))
  329. + goto error_return;
  330. + if (! ecoff_link_add_externals (abfd, info, external_ext, ssext))
  331. + goto error_return;
  332. +
  333. + *pneeded = TRUE;
  334. + goto successful_return;
  335. + }
  336. +
  337. + successful_return:
  338. + if (external_ext != NULL)
  339. + free (external_ext);
  340. + if (ssext != NULL)
  341. + free (ssext);
  342. + return TRUE;
  343. + error_return:
  344. + if (external_ext != NULL)
  345. + free (external_ext);
  346. + if (ssext != NULL)
  347. + free (ssext);
  348. + return FALSE;
  349. }
  350. /* Add the symbols from an archive file to the global hash table.
  351. diff --git a/bfd/elflink.c b/bfd/elflink.c
  352. index 94ab762..164df6b 100644
  353. --- a/bfd/elflink.c
  354. +++ b/bfd/elflink.c
  355. @@ -2933,6 +2933,13 @@ elf_link_is_defined_archive_symbol (bfd * abfd, carsym * symdef)
  356. if (! bfd_check_format (abfd, bfd_object))
  357. return FALSE;
  358. + /* If we have already included the element containing this symbol in the
  359. + link then we do not need to include it again. Just claim that any symbol
  360. + it contains is not a definition, so that our caller will not decide to
  361. + (re)include this element. */
  362. + if (abfd->archive_pass)
  363. + return FALSE;
  364. +
  365. /* Select the appropriate symbol table. */
  366. if ((abfd->flags & DYNAMIC) == 0 || elf_dynsymtab (abfd) == 0)
  367. hdr = &elf_tdata (abfd)->symtab_hdr;
  368. @@ -4929,8 +4936,20 @@ _bfd_elf_archive_symbol_lookup (bfd *abfd,
  369. }
  370. /* Add symbols from an ELF archive file to the linker hash table. We
  371. - don't use _bfd_generic_link_add_archive_symbols because we need to
  372. - handle versioned symbols.
  373. + don't use _bfd_generic_link_add_archive_symbols because of a
  374. + problem which arises on UnixWare. The UnixWare libc.so is an
  375. + archive which includes an entry libc.so.1 which defines a bunch of
  376. + symbols. The libc.so archive also includes a number of other
  377. + object files, which also define symbols, some of which are the same
  378. + as those defined in libc.so.1. Correct linking requires that we
  379. + consider each object file in turn, and include it if it defines any
  380. + symbols we need. _bfd_generic_link_add_archive_symbols does not do
  381. + this; it looks through the list of undefined symbols, and includes
  382. + any object file which defines them. When this algorithm is used on
  383. + UnixWare, it winds up pulling in libc.so.1 early and defining a
  384. + bunch of symbols. This means that some of the other objects in the
  385. + archive are not included in the link, which is incorrect since they
  386. + precede libc.so.1 in the archive.
  387. Fortunately, ELF archive handling is simpler than that done by
  388. _bfd_generic_link_add_archive_symbols, which has to allow for a.out
  389. @@ -4945,7 +4964,8 @@ static bfd_boolean
  390. elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
  391. {
  392. symindex c;
  393. - unsigned char *included = NULL;
  394. + bfd_boolean *defined = NULL;
  395. + bfd_boolean *included = NULL;
  396. carsym *symdefs;
  397. bfd_boolean loop;
  398. bfd_size_type amt;
  399. @@ -4969,10 +4989,11 @@ elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
  400. if (c == 0)
  401. return TRUE;
  402. amt = c;
  403. - amt *= sizeof (*included);
  404. - included = (unsigned char *) bfd_zmalloc (amt);
  405. - if (included == NULL)
  406. - return FALSE;
  407. + amt *= sizeof (bfd_boolean);
  408. + defined = (bfd_boolean *) bfd_zmalloc (amt);
  409. + included = (bfd_boolean *) bfd_zmalloc (amt);
  410. + if (defined == NULL || included == NULL)
  411. + goto error_return;
  412. symdefs = bfd_ardata (abfd)->symdefs;
  413. bed = get_elf_backend_data (abfd);
  414. @@ -4997,7 +5018,7 @@ elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
  415. struct bfd_link_hash_entry *undefs_tail;
  416. symindex mark;
  417. - if (included[i])
  418. + if (defined[i] || included[i])
  419. continue;
  420. if (symdef->file_offset == last)
  421. {
  422. @@ -5032,8 +5053,7 @@ elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
  423. else if (h->root.type != bfd_link_hash_undefined)
  424. {
  425. if (h->root.type != bfd_link_hash_undefweak)
  426. - /* Symbol must be defined. Don't check it again. */
  427. - included[i] = TRUE;
  428. + defined[i] = TRUE;
  429. continue;
  430. }
  431. @@ -5045,6 +5065,16 @@ elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
  432. if (! bfd_check_format (element, bfd_object))
  433. goto error_return;
  434. + /* Doublecheck that we have not included this object
  435. + already--it should be impossible, but there may be
  436. + something wrong with the archive. */
  437. + if (element->archive_pass != 0)
  438. + {
  439. + bfd_set_error (bfd_error_bad_value);
  440. + goto error_return;
  441. + }
  442. + element->archive_pass = 1;
  443. +
  444. undefs_tail = info->hash->undefs_tail;
  445. if (!(*info->callbacks
  446. @@ -5082,11 +5112,14 @@ elf_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
  447. }
  448. while (loop);
  449. + free (defined);
  450. free (included);
  451. return TRUE;
  452. error_return:
  453. + if (defined != NULL)
  454. + free (defined);
  455. if (included != NULL)
  456. free (included);
  457. return FALSE;
  458. diff --git a/bfd/libbfd-in.h b/bfd/libbfd-in.h
  459. index 50a46ac..90c6018 100644
  460. --- a/bfd/libbfd-in.h
  461. +++ b/bfd/libbfd-in.h
  462. @@ -596,9 +596,7 @@ extern bfd_boolean _bfd_generic_link_add_symbols_collect
  463. /* Generic archive add symbol routine. */
  464. extern bfd_boolean _bfd_generic_link_add_archive_symbols
  465. (bfd *, struct bfd_link_info *,
  466. - bfd_boolean (*) (bfd *, struct bfd_link_info *,
  467. - struct bfd_link_hash_entry *, const char *,
  468. - bfd_boolean *));
  469. + bfd_boolean (*) (bfd *, struct bfd_link_info *, bfd_boolean *));
  470. /* Forward declaration to avoid prototype errors. */
  471. typedef struct bfd_link_hash_entry _bfd_link_hash_entry;
  472. diff --git a/bfd/libbfd.h b/bfd/libbfd.h
  473. index 6c48f82..ffb6ea4 100644
  474. --- a/bfd/libbfd.h
  475. +++ b/bfd/libbfd.h
  476. @@ -601,9 +601,7 @@ extern bfd_boolean _bfd_generic_link_add_symbols_collect
  477. /* Generic archive add symbol routine. */
  478. extern bfd_boolean _bfd_generic_link_add_archive_symbols
  479. (bfd *, struct bfd_link_info *,
  480. - bfd_boolean (*) (bfd *, struct bfd_link_info *,
  481. - struct bfd_link_hash_entry *, const char *,
  482. - bfd_boolean *));
  483. + bfd_boolean (*) (bfd *, struct bfd_link_info *, bfd_boolean *));
  484. /* Forward declaration to avoid prototype errors. */
  485. typedef struct bfd_link_hash_entry _bfd_link_hash_entry;
  486. diff --git a/bfd/linker.c b/bfd/linker.c
  487. index abdf5b0..4cff1e7 100644
  488. --- a/bfd/linker.c
  489. +++ b/bfd/linker.c
  490. @@ -229,16 +229,28 @@ SUBSUBSECTION
  491. @findex _bfd_generic_link_add_archive_symbols
  492. In most cases the work of looking through the symbols in the
  493. archive should be done by the
  494. - <<_bfd_generic_link_add_archive_symbols>> function.
  495. + <<_bfd_generic_link_add_archive_symbols>> function. This
  496. + function builds a hash table from the archive symbol table and
  497. + looks through the list of undefined symbols to see which
  498. + elements should be included.
  499. <<_bfd_generic_link_add_archive_symbols>> is passed a function
  500. to call to make the final decision about adding an archive
  501. element to the link and to do the actual work of adding the
  502. - symbols to the linker hash table. If the element is to
  503. + symbols to the linker hash table.
  504. +
  505. + The function passed to
  506. + <<_bfd_generic_link_add_archive_symbols>> must read the
  507. + symbols of the archive element and decide whether the archive
  508. + element should be included in the link. If the element is to
  509. be included, the <<add_archive_element>> linker callback
  510. routine must be called with the element as an argument, and
  511. the element's symbols must be added to the linker hash table
  512. just as though the element had itself been passed to the
  513. - <<_bfd_link_add_symbols>> function.
  514. + <<_bfd_link_add_symbols>> function. The <<add_archive_element>>
  515. + callback has the option to indicate that it would like to
  516. + replace the element archive with a substitute BFD, in which
  517. + case it is the symbols of that substitute BFD that must be
  518. + added to the linker hash table instead.
  519. When the a.out <<_bfd_link_add_symbols>> function receives an
  520. archive, it calls <<_bfd_generic_link_add_archive_symbols>>
  521. @@ -407,14 +419,11 @@ static bfd_boolean generic_link_add_object_symbols
  522. static bfd_boolean generic_link_add_symbols
  523. (bfd *, struct bfd_link_info *, bfd_boolean);
  524. static bfd_boolean generic_link_check_archive_element_no_collect
  525. - (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *, const char *,
  526. - bfd_boolean *);
  527. + (bfd *, struct bfd_link_info *, bfd_boolean *);
  528. static bfd_boolean generic_link_check_archive_element_collect
  529. - (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *, const char *,
  530. - bfd_boolean *);
  531. + (bfd *, struct bfd_link_info *, bfd_boolean *);
  532. static bfd_boolean generic_link_check_archive_element
  533. - (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *, const char *,
  534. - bfd_boolean *, bfd_boolean);
  535. + (bfd *, struct bfd_link_info *, bfd_boolean *, bfd_boolean);
  536. static bfd_boolean generic_link_add_symbol_list
  537. (bfd *, struct bfd_link_info *, bfd_size_type count, asymbol **,
  538. bfd_boolean);
  539. @@ -908,32 +917,138 @@ generic_link_add_object_symbols (bfd *abfd,
  540. return generic_link_add_symbol_list (abfd, info, symcount, outsyms, collect);
  541. }
  542. +/* We build a hash table of all symbols defined in an archive. */
  543. +
  544. +/* An archive symbol may be defined by multiple archive elements.
  545. + This linked list is used to hold the elements. */
  546. +
  547. +struct archive_list
  548. +{
  549. + struct archive_list *next;
  550. + unsigned int indx;
  551. +};
  552. +
  553. +/* An entry in an archive hash table. */
  554. +
  555. +struct archive_hash_entry
  556. +{
  557. + struct bfd_hash_entry root;
  558. + /* Where the symbol is defined. */
  559. + struct archive_list *defs;
  560. +};
  561. +
  562. +/* An archive hash table itself. */
  563. +
  564. +struct archive_hash_table
  565. +{
  566. + struct bfd_hash_table table;
  567. +};
  568. +
  569. +/* Create a new entry for an archive hash table. */
  570. +
  571. +static struct bfd_hash_entry *
  572. +archive_hash_newfunc (struct bfd_hash_entry *entry,
  573. + struct bfd_hash_table *table,
  574. + const char *string)
  575. +{
  576. + struct archive_hash_entry *ret = (struct archive_hash_entry *) entry;
  577. +
  578. + /* Allocate the structure if it has not already been allocated by a
  579. + subclass. */
  580. + if (ret == NULL)
  581. + ret = (struct archive_hash_entry *)
  582. + bfd_hash_allocate (table, sizeof (struct archive_hash_entry));
  583. + if (ret == NULL)
  584. + return NULL;
  585. +
  586. + /* Call the allocation method of the superclass. */
  587. + ret = ((struct archive_hash_entry *)
  588. + bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
  589. +
  590. + if (ret)
  591. + {
  592. + /* Initialize the local fields. */
  593. + ret->defs = NULL;
  594. + }
  595. +
  596. + return &ret->root;
  597. +}
  598. +
  599. +/* Initialize an archive hash table. */
  600. +
  601. +static bfd_boolean
  602. +archive_hash_table_init
  603. + (struct archive_hash_table *table,
  604. + struct bfd_hash_entry *(*newfunc) (struct bfd_hash_entry *,
  605. + struct bfd_hash_table *,
  606. + const char *),
  607. + unsigned int entsize)
  608. +{
  609. + return bfd_hash_table_init (&table->table, newfunc, entsize);
  610. +}
  611. +
  612. +/* Look up an entry in an archive hash table. */
  613. +
  614. +#define archive_hash_lookup(t, string, create, copy) \
  615. + ((struct archive_hash_entry *) \
  616. + bfd_hash_lookup (&(t)->table, (string), (create), (copy)))
  617. +
  618. +/* Allocate space in an archive hash table. */
  619. +
  620. +#define archive_hash_allocate(t, size) bfd_hash_allocate (&(t)->table, (size))
  621. +
  622. +/* Free an archive hash table. */
  623. +
  624. +#define archive_hash_table_free(t) bfd_hash_table_free (&(t)->table)
  625. +
  626. /* Generic function to add symbols from an archive file to the global
  627. hash file. This function presumes that the archive symbol table
  628. has already been read in (this is normally done by the
  629. - bfd_check_format entry point). It looks through the archive symbol
  630. - table for symbols that are undefined or common in the linker global
  631. - symbol hash table. When one is found, the CHECKFN argument is used
  632. - to see if an object file should be included. This allows targets
  633. - to customize common symbol behaviour. CHECKFN should set *PNEEDED
  634. - to TRUE if the object file should be included, and must also call
  635. - the bfd_link_info add_archive_element callback function and handle
  636. - adding the symbols to the global hash table. CHECKFN must notice
  637. - if the callback indicates a substitute BFD, and arrange to add
  638. - those symbols instead if it does so. CHECKFN should only return
  639. - FALSE if some sort of error occurs. */
  640. + bfd_check_format entry point). It looks through the undefined and
  641. + common symbols and searches the archive symbol table for them. If
  642. + it finds an entry, it includes the associated object file in the
  643. + link.
  644. +
  645. + The old linker looked through the archive symbol table for
  646. + undefined symbols. We do it the other way around, looking through
  647. + undefined symbols for symbols defined in the archive. The
  648. + advantage of the newer scheme is that we only have to look through
  649. + the list of undefined symbols once, whereas the old method had to
  650. + re-search the symbol table each time a new object file was added.
  651. +
  652. + The CHECKFN argument is used to see if an object file should be
  653. + included. CHECKFN should set *PNEEDED to TRUE if the object file
  654. + should be included, and must also call the bfd_link_info
  655. + add_archive_element callback function and handle adding the symbols
  656. + to the global hash table. CHECKFN must notice if the callback
  657. + indicates a substitute BFD, and arrange to add those symbols instead
  658. + if it does so. CHECKFN should only return FALSE if some sort of
  659. + error occurs.
  660. +
  661. + For some formats, such as a.out, it is possible to look through an
  662. + object file but not actually include it in the link. The
  663. + archive_pass field in a BFD is used to avoid checking the symbols
  664. + of an object files too many times. When an object is included in
  665. + the link, archive_pass is set to -1. If an object is scanned but
  666. + not included, archive_pass is set to the pass number. The pass
  667. + number is incremented each time a new object file is included. The
  668. + pass number is used because when a new object file is included it
  669. + may create new undefined symbols which cause a previously examined
  670. + object file to be included. */
  671. bfd_boolean
  672. _bfd_generic_link_add_archive_symbols
  673. (bfd *abfd,
  674. struct bfd_link_info *info,
  675. - bfd_boolean (*checkfn) (bfd *, struct bfd_link_info *,
  676. - struct bfd_link_hash_entry *, const char *,
  677. - bfd_boolean *))
  678. + bfd_boolean (*checkfn) (bfd *, struct bfd_link_info *, bfd_boolean *))
  679. {
  680. - bfd_boolean loop;
  681. - bfd_size_type amt;
  682. - unsigned char *included;
  683. + carsym *arsyms;
  684. + carsym *arsym_end;
  685. + register carsym *arsym;
  686. + int pass;
  687. + struct archive_hash_table arsym_hash;
  688. + unsigned int indx;
  689. + struct bfd_link_hash_entry **pundef;
  690. if (! bfd_has_map (abfd))
  691. {
  692. @@ -944,103 +1059,148 @@ _bfd_generic_link_add_archive_symbols
  693. return FALSE;
  694. }
  695. - amt = bfd_ardata (abfd)->symdef_count;
  696. - if (amt == 0)
  697. - return TRUE;
  698. - amt *= sizeof (*included);
  699. - included = (unsigned char *) bfd_zmalloc (amt);
  700. - if (included == NULL)
  701. + arsyms = bfd_ardata (abfd)->symdefs;
  702. + arsym_end = arsyms + bfd_ardata (abfd)->symdef_count;
  703. +
  704. + /* In order to quickly determine whether an symbol is defined in
  705. + this archive, we build a hash table of the symbols. */
  706. + if (! archive_hash_table_init (&arsym_hash, archive_hash_newfunc,
  707. + sizeof (struct archive_hash_entry)))
  708. return FALSE;
  709. + for (arsym = arsyms, indx = 0; arsym < arsym_end; arsym++, indx++)
  710. + {
  711. + struct archive_hash_entry *arh;
  712. + struct archive_list *l, **pp;
  713. - do
  714. + arh = archive_hash_lookup (&arsym_hash, arsym->name, TRUE, FALSE);
  715. + if (arh == NULL)
  716. + goto error_return;
  717. + l = ((struct archive_list *)
  718. + archive_hash_allocate (&arsym_hash, sizeof (struct archive_list)));
  719. + if (l == NULL)
  720. + goto error_return;
  721. + l->indx = indx;
  722. + for (pp = &arh->defs; *pp != NULL; pp = &(*pp)->next)
  723. + ;
  724. + *pp = l;
  725. + l->next = NULL;
  726. + }
  727. +
  728. + /* The archive_pass field in the archive itself is used to
  729. + initialize PASS, sine we may search the same archive multiple
  730. + times. */
  731. + pass = abfd->archive_pass + 1;
  732. +
  733. + /* New undefined symbols are added to the end of the list, so we
  734. + only need to look through it once. */
  735. + pundef = &info->hash->undefs;
  736. + while (*pundef != NULL)
  737. {
  738. - carsym *arsyms;
  739. - carsym *arsym_end;
  740. - carsym *arsym;
  741. - unsigned int indx;
  742. - file_ptr last_ar_offset = -1;
  743. - bfd_boolean needed = FALSE;
  744. - bfd *element = NULL;
  745. -
  746. - loop = FALSE;
  747. - arsyms = bfd_ardata (abfd)->symdefs;
  748. - arsym_end = arsyms + bfd_ardata (abfd)->symdef_count;
  749. - for (arsym = arsyms, indx = 0; arsym < arsym_end; arsym++, indx++)
  750. + struct bfd_link_hash_entry *h;
  751. + struct archive_hash_entry *arh;
  752. + struct archive_list *l;
  753. +
  754. + h = *pundef;
  755. +
  756. + /* When a symbol is defined, it is not necessarily removed from
  757. + the list. */
  758. + if (h->type != bfd_link_hash_undefined
  759. + && h->type != bfd_link_hash_common)
  760. {
  761. - struct bfd_link_hash_entry *h;
  762. - struct bfd_link_hash_entry *undefs_tail;
  763. + /* Remove this entry from the list, for general cleanliness
  764. + and because we are going to look through the list again
  765. + if we search any more libraries. We can't remove the
  766. + entry if it is the tail, because that would lose any
  767. + entries we add to the list later on (it would also cause
  768. + us to lose track of whether the symbol has been
  769. + referenced). */
  770. + if (*pundef != info->hash->undefs_tail)
  771. + *pundef = (*pundef)->u.undef.next;
  772. + else
  773. + pundef = &(*pundef)->u.undef.next;
  774. + continue;
  775. + }
  776. - if (included[indx])
  777. - continue;
  778. - if (needed && arsym->file_offset == last_ar_offset)
  779. + /* Look for this symbol in the archive symbol map. */
  780. + arh = archive_hash_lookup (&arsym_hash, h->root.string, FALSE, FALSE);
  781. + if (arh == NULL)
  782. + {
  783. + /* If we haven't found the exact symbol we're looking for,
  784. + let's look for its import thunk */
  785. + if (info->pei386_auto_import)
  786. + {
  787. + bfd_size_type amt = strlen (h->root.string) + 10;
  788. + char *buf = (char *) bfd_malloc (amt);
  789. + if (buf == NULL)
  790. + return FALSE;
  791. +
  792. + sprintf (buf, "__imp_%s", h->root.string);
  793. + arh = archive_hash_lookup (&arsym_hash, buf, FALSE, FALSE);
  794. + free(buf);
  795. + }
  796. + if (arh == NULL)
  797. {
  798. - included[indx] = 1;
  799. + pundef = &(*pundef)->u.undef.next;
  800. continue;
  801. }
  802. + }
  803. + /* Look at all the objects which define this symbol. */
  804. + for (l = arh->defs; l != NULL; l = l->next)
  805. + {
  806. + bfd *element;
  807. + bfd_boolean needed;
  808. +
  809. + /* If the symbol has gotten defined along the way, quit. */
  810. + if (h->type != bfd_link_hash_undefined
  811. + && h->type != bfd_link_hash_common)
  812. + break;
  813. - h = bfd_link_hash_lookup (info->hash, arsym->name,
  814. - FALSE, FALSE, TRUE);
  815. + element = bfd_get_elt_at_index (abfd, l->indx);
  816. + if (element == NULL)
  817. + goto error_return;
  818. - if (h == NULL
  819. - && info->pei386_auto_import
  820. - && CONST_STRNEQ (arsym->name, "__imp_"))
  821. - h = bfd_link_hash_lookup (info->hash, arsym->name + 6,
  822. - FALSE, FALSE, TRUE);
  823. - if (h == NULL)
  824. + /* If we've already included this element, or if we've
  825. + already checked it on this pass, continue. */
  826. + if (element->archive_pass == -1
  827. + || element->archive_pass == pass)
  828. continue;
  829. - if (h->type != bfd_link_hash_undefined
  830. - && h->type != bfd_link_hash_common)
  831. + /* If we can't figure this element out, just ignore it. */
  832. + if (! bfd_check_format (element, bfd_object))
  833. {
  834. - if (h->type != bfd_link_hash_undefweak)
  835. - /* Symbol must be defined. Don't check it again. */
  836. - included[indx] = 1;
  837. + element->archive_pass = -1;
  838. continue;
  839. }
  840. - if (last_ar_offset != arsym->file_offset)
  841. - {
  842. - last_ar_offset = arsym->file_offset;
  843. - element = _bfd_get_elt_at_filepos (abfd, last_ar_offset);
  844. - if (element == NULL
  845. - || !bfd_check_format (element, bfd_object))
  846. - goto error_return;
  847. - }
  848. -
  849. - undefs_tail = info->hash->undefs_tail;
  850. -
  851. /* CHECKFN will see if this element should be included, and
  852. go ahead and include it if appropriate. */
  853. - if (! (*checkfn) (element, info, h, arsym->name, &needed))
  854. + if (! (*checkfn) (element, info, &needed))
  855. goto error_return;
  856. - if (needed)
  857. + if (! needed)
  858. + element->archive_pass = pass;
  859. + else
  860. {
  861. - unsigned int mark;
  862. + element->archive_pass = -1;
  863. - /* Look backward to mark all symbols from this object file
  864. - which we have already seen in this pass. */
  865. - mark = indx;
  866. - do
  867. - {
  868. - included[mark] = 1;
  869. - if (mark == 0)
  870. - break;
  871. - --mark;
  872. - }
  873. - while (arsyms[mark].file_offset == last_ar_offset);
  874. -
  875. - if (undefs_tail != info->hash->undefs_tail)
  876. - loop = TRUE;
  877. + /* Increment the pass count to show that we may need to
  878. + recheck object files which were already checked. */
  879. + ++pass;
  880. }
  881. }
  882. - } while (loop);
  883. - free (included);
  884. + pundef = &(*pundef)->u.undef.next;
  885. + }
  886. +
  887. + archive_hash_table_free (&arsym_hash);
  888. +
  889. + /* Save PASS in case we are called again. */
  890. + abfd->archive_pass = pass;
  891. +
  892. return TRUE;
  893. error_return:
  894. - free (included);
  895. + archive_hash_table_free (&arsym_hash);
  896. return FALSE;
  897. }
  898. @@ -1050,14 +1210,12 @@ _bfd_generic_link_add_archive_symbols
  899. for finding them. */
  900. static bfd_boolean
  901. -generic_link_check_archive_element_no_collect (bfd *abfd,
  902. +generic_link_check_archive_element_no_collect (
  903. + bfd *abfd,
  904. struct bfd_link_info *info,
  905. - struct bfd_link_hash_entry *h,
  906. - const char *name,
  907. bfd_boolean *pneeded)
  908. {
  909. - return generic_link_check_archive_element (abfd, info, h, name, pneeded,
  910. - FALSE);
  911. + return generic_link_check_archive_element (abfd, info, pneeded, FALSE);
  912. }
  913. /* See if we should include an archive element. This version is used
  914. @@ -1067,12 +1225,9 @@ generic_link_check_archive_element_no_collect (bfd *abfd,
  915. static bfd_boolean
  916. generic_link_check_archive_element_collect (bfd *abfd,
  917. struct bfd_link_info *info,
  918. - struct bfd_link_hash_entry *h,
  919. - const char *name,
  920. bfd_boolean *pneeded)
  921. {
  922. - return generic_link_check_archive_element (abfd, info, h, name, pneeded,
  923. - TRUE);
  924. + return generic_link_check_archive_element (abfd, info, pneeded, TRUE);
  925. }
  926. /* See if we should include an archive element. Optionally collect
  927. @@ -1081,8 +1236,6 @@ generic_link_check_archive_element_collect (bfd *abfd,
  928. static bfd_boolean
  929. generic_link_check_archive_element (bfd *abfd,
  930. struct bfd_link_info *info,
  931. - struct bfd_link_hash_entry *h,
  932. - const char *name ATTRIBUTE_UNUSED,
  933. bfd_boolean *pneeded,
  934. bfd_boolean collect)
  935. {
  936. @@ -1098,6 +1251,7 @@ generic_link_check_archive_element (bfd *abfd,
  937. for (; pp < ppend; pp++)
  938. {
  939. asymbol *p;
  940. + struct bfd_link_hash_entry *h;
  941. p = *pp;
  942. diff --git a/bfd/pdp11.c b/bfd/pdp11.c
  943. index 593c5ca..5111a51 100644
  944. --- a/bfd/pdp11.c
  945. +++ b/bfd/pdp11.c
  946. @@ -251,7 +251,7 @@ HOWTO( 1, 0, 1, 16, TRUE, 0, complain_overflow_signed,0,"DISP16", TRU
  947. #define TABLE_SIZE(TABLE) (sizeof(TABLE)/sizeof(TABLE[0]))
  948. -static bfd_boolean aout_link_check_archive_element (bfd *, struct bfd_link_info *, struct bfd_link_hash_entry *, const char *, bfd_boolean *);
  949. +static bfd_boolean aout_link_check_archive_element (bfd *, struct bfd_link_info *, bfd_boolean *);
  950. static bfd_boolean aout_link_add_object_symbols (bfd *, struct bfd_link_info *);
  951. static bfd_boolean aout_link_add_symbols (bfd *, struct bfd_link_info *);
  952. static bfd_boolean aout_link_write_symbols (struct aout_final_link_info *, bfd *);
  953. @@ -2682,8 +2682,6 @@ aout_link_check_ar_symbols (bfd *abfd,
  954. static bfd_boolean
  955. aout_link_check_archive_element (bfd *abfd,
  956. struct bfd_link_info *info,
  957. - struct bfd_link_hash_entry *h ATTRIBUTE_UNUSED,
  958. - const char *name ATTRIBUTE_UNUSED,
  959. bfd_boolean *pneeded)
  960. {
  961. bfd *oldbfd;
  962. diff --git a/bfd/xcofflink.c b/bfd/xcofflink.c
  963. index 9522974..dcfd58f 100644
  964. --- a/bfd/xcofflink.c
  965. +++ b/bfd/xcofflink.c
  966. @@ -2384,8 +2384,6 @@ xcoff_link_check_ar_symbols (bfd *abfd,
  967. static bfd_boolean
  968. xcoff_link_check_archive_element (bfd *abfd,
  969. struct bfd_link_info *info,
  970. - struct bfd_link_hash_entry *h ATTRIBUTE_UNUSED,
  971. - const char *name ATTRIBUTE_UNUSED,
  972. bfd_boolean *pneeded)
  973. {
  974. bfd_boolean keep_syms_p;
  975. @@ -2465,7 +2463,7 @@ _bfd_xcoff_bfd_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
  976. bfd_boolean needed;
  977. if (! xcoff_link_check_archive_element (member, info,
  978. - NULL, NULL, &needed))
  979. + &needed))
  980. return FALSE;
  981. if (needed)
  982. member->archive_pass = -1;