[prev in list] [next in list] [prev in thread] [next in thread]
List: binutils
Subject: [PATCH] add section caches to coff_data_type
From: Oleg Tolmatcev via Binutils <binutils () sourceware ! org>
Date: 2023-04-29 11:19:26
Message-ID: CACcXsZjWfeQR3_pC3nVtq+sAkq-QGfEnA3DE2K8rsDnK9edWrQ () mail ! gmail ! com
[Download RAW message or body]
Hello all,
final patch to ld. All the patches together improve linking
performance from 9 minutes to 1 minute when linking rpcs3 in debug
mode with BUILD_LLVM=ON.
---
bfd/coff-x86_64.c | 35 +++++++++++++++++++++++------------
bfd/coffgen.c | 27 +++++++++++++++++++++++++--
bfd/libcoff-in.h | 6 ++++++
bfd/libcoff.h | 6 ++++++
bfd/peicode.h | 35 +++++++++++++++++++++++++++++++++++
5 files changed, 95 insertions(+), 14 deletions(-)
diff --git a/bfd/coff-x86_64.c b/bfd/coff-x86_64.c
index 822504a339..09291e2455 100644
--- a/bfd/coff-x86_64.c
+++ b/bfd/coff-x86_64.c
@@ -745,23 +745,34 @@ coff_amd64_rtype_to_howto (bfd *abfd ATTRIBUTE_UNUSED,
if (rel->r_type == R_AMD64_SECREL)
{
- bfd_vma osect_vma;
+ bfd_vma osect_vma = 0;
if (h && (h->root.type == bfd_link_hash_defined
|| h->root.type == bfd_link_hash_defweak))
osect_vma = h->root.u.def.section->output_section->vma;
else
- {
- asection *s;
- int i;
-
- /* Sigh, the only way to get the section to offset against
- is to find it the hard way. */
- for (s = abfd->sections, i = 1; i < sym->n_scnum; i++)
- s = s->next;
-
- osect_vma = s->output_section->vma;
- }
+ {
+ asection *s;
+
+ /* Sigh, the only way to get the section to offset against
+ is to find it the hard way. */
+
+ if (htab_elements (coff_data (abfd)->section_by_index) == 0)
+ {
+ for (s = abfd->sections; s != NULL; s = s->next)
+ {
+ void **slot
+ = htab_find_slot (coff_data
(abfd)->section_by_index, s, INSERT);
+ if (slot != NULL)
+ *slot = s;
+ }
+ }
+ struct bfd_section needle;
+ needle.index = sym->n_scnum - 1;
+ s = htab_find (coff_data (abfd)->section_by_index, &needle);
+ if (s != NULL)
+ osect_vma = s->output_section->vma;
+ }
*addendp -= osect_vma;
}
diff --git a/bfd/coffgen.c b/bfd/coffgen.c
index 05f2640abe..326a7dbd88 100644
--- a/bfd/coffgen.c
+++ b/bfd/coffgen.c
@@ -42,6 +42,7 @@
#include "libbfd.h"
#include "coff/internal.h"
#include "libcoff.h"
+#include "hashtab.h"
/* Take a section header read from a coff file (in HOST byte order),
and make a BFD "section" out of it. This is used by ECOFF. */
@@ -360,8 +361,6 @@ coff_object_p (bfd *abfd)
asection *
coff_section_from_bfd_index (bfd *abfd, int section_index)
{
- struct bfd_section *answer = abfd->sections;
-
if (section_index == N_ABS)
return bfd_abs_section_ptr;
if (section_index == N_UNDEF)
@@ -369,6 +368,30 @@ coff_section_from_bfd_index (bfd *abfd, int section_index)
if (section_index == N_DEBUG)
return bfd_abs_section_ptr;
+ struct bfd_section *answer;
+
+ if (htab_elements (coff_data (abfd)->section_by_target_index) == 0)
+ {
+ answer = abfd->sections;
+ while (answer)
+ {
+ void **slot
+ = htab_find_slot (coff_data
(abfd)->section_by_target_index, answer, INSERT);
+ if (slot == NULL)
+ return bfd_und_section_ptr;
+ *slot = answer;
+ answer = answer->next;
+ }
+ }
+
+ struct bfd_section needle;
+ needle.target_index = section_index;
+
+ answer = htab_find (coff_data (abfd)->section_by_target_index, &needle);
+ if (answer != NULL)
+ return answer;
+
+ answer = abfd->sections;
while (answer)
{
if (answer->target_index == section_index)
diff --git a/bfd/libcoff-in.h b/bfd/libcoff-in.h
index cdd504605b..6f4109931c 100644
--- a/bfd/libcoff-in.h
+++ b/bfd/libcoff-in.h
@@ -130,6 +130,12 @@ typedef struct coff_tdata
COFF object into memory. */
char * stub;
bfd_size_type stub_size;
+
+ /* hash table containing sections by target index */
+ htab_t section_by_target_index;
+
+ /* hash table containing sections by index */
+ htab_t section_by_index;
} coff_data_type;
/* Tdata for pe image files. */
diff --git a/bfd/libcoff.h b/bfd/libcoff.h
index b58ee8aded..0cb335ee8d 100644
--- a/bfd/libcoff.h
+++ b/bfd/libcoff.h
@@ -133,6 +133,12 @@ typedef struct coff_tdata
COFF object into memory. */
char * stub;
bfd_size_type stub_size;
+
+ /* hash table containing sections by target index */
+ htab_t section_by_target_index;
+
+ /* hash table containing sections by index */
+ htab_t section_by_index;
} coff_data_type;
/* Tdata for pe image files. */
diff --git a/bfd/peicode.h b/bfd/peicode.h
index df1e678b5a..c60961be9f 100644
--- a/bfd/peicode.h
+++ b/bfd/peicode.h
@@ -274,6 +274,36 @@ htab_eq_flags (const void *e1, const void *e2)
&& fe1->target_index == fe2->target_index;
}
+static hashval_t
+htab_hash_section_index (const void *entry)
+{
+ const struct bfd_section *sec = entry;
+ return sec->index;
+}
+
+static int
+htab_eq_section_index (const void *e1, const void *e2)
+{
+ const struct bfd_section *sec1 = e1;
+ const struct bfd_section *sec2 = e2;
+ return sec1->index == sec2->index;
+}
+
+static hashval_t
+htab_hash_section_target_index (const void *entry)
+{
+ const struct bfd_section *sec = entry;
+ return sec->target_index;
+}
+
+static int
+htab_eq_section_target_index (const void *e1, const void *e2)
+{
+ const struct bfd_section *sec1 = e1;
+ const struct bfd_section *sec2 = e2;
+ return sec1->target_index == sec2->target_index;
+}
+
static bool
pe_mkobject (bfd * abfd)
{
@@ -373,6 +403,11 @@ pe_mkobject_hook (bfd * abfd,
memcpy (pe->dos_message, internal_f->pe.dos_message,
sizeof (pe->dos_message));
+ pe->coff.section_by_index
+ = htab_create (10, htab_hash_section_index, htab_eq_section_index, NULL);
+ pe->coff.section_by_target_index = htab_create (
+ 10, htab_hash_section_target_index, htab_eq_section_target_index, NULL);
+
return (void *) pe;
}
--
2.40.0.windows.1
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic