summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristopher Faylor <me+cygwin@cgf.cx>2004-07-03 16:07:51 +0000
committerChristopher Faylor <me+cygwin@cgf.cx>2004-07-03 16:07:51 +0000
commitc1c5dc0e88ea9196142e71bcd3f61cd3de4c97bd (patch)
treef4d61ba874786f045701ea315a1922667a177d5e
parent0cd36cc9585026047d5dbd9c92735e4a9c809746 (diff)
downloadbinutils-redhat-c1c5dc0e88ea9196142e71bcd3f61cd3de4c97bd.tar.gz
2004-07-04 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
* bfd/cofflink.c (_bfd_coff_generic_relocate_section): Resolve PE weak externals properly. * src/gas/config/obj-coff.c (obj_coff_weak): New .weak syntax for PE weak externals. * binutils/doc/binutils.texi (nm): Clarify weak symbol description. * gas/config/tc-i386.c (tc_gen_reloc): Use addend for weak symbols in TE_PE. * gas/doc/as.texinfo (Weak): Document PE weak symbols. * ld/ld.texinfo (WIN32): Document PE weak symbols.
-rw-r--r--bfd/ChangeLog5
-rw-r--r--bfd/cofflink.c29
-rw-r--r--binutils/ChangeLog4
-rw-r--r--binutils/doc/binutils.texi3
-rw-r--r--gas/ChangeLog6
-rw-r--r--gas/config/obj-coff.c121
-rw-r--r--gas/config/tc-i386.c6
-rw-r--r--gas/doc/as.texinfo27
-rw-r--r--ld/ChangeLog4
-rw-r--r--ld/ld.texinfo18
10 files changed, 174 insertions, 49 deletions
diff --git a/bfd/ChangeLog b/bfd/ChangeLog
index e8e452f976..198494653e 100644
--- a/bfd/ChangeLog
+++ b/bfd/ChangeLog
@@ -1,3 +1,8 @@
+2004-07-03 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
+
+ * cofflink.c (_bfd_coff_generic_relocate_section): Resolve PE weak
+ externals properly.
+
2004-07-02 Martin Schwidefsky <schwidefsky@de.ibm.com>
* config.bfd: Add want64 to configuration target s390-*-linux*.
diff --git a/bfd/cofflink.c b/bfd/cofflink.c
index 1af86abaec..af6dd3d699 100644
--- a/bfd/cofflink.c
+++ b/bfd/cofflink.c
@@ -2923,16 +2923,41 @@ _bfd_coff_generic_relocate_section (bfd *output_bfd,
if (h->root.type == bfd_link_hash_defined
|| h->root.type == bfd_link_hash_defweak)
{
+ /* Defined weak symbols are a GNU extension. */
asection *sec;
sec = h->root.u.def.section;
val = (h->root.u.def.value
+ sec->output_section->vma
+ sec->output_offset);
- }
+ }
else if (h->root.type == bfd_link_hash_undefweak)
- val = 0;
+ {
+ if (h->class == C_NT_WEAK && h->numaux == 1)
+ {
+ /* See _Microsoft Portable Executable and Common Object
+ * File Format Specification_, section 5.5.3.
+ * Note that weak symbols without aux records are a GNU
+ * extension.
+ * FIXME: All weak externals are treated as having
+ * characteristics IMAGE_WEAK_EXTERN_SEARCH_LIBRARY (2).
+ * There are no known uses of the other two types of
+ * weak externals.
+ */
+ asection *sec;
+ struct coff_link_hash_entry *h2 =
+ input_bfd->tdata.coff_obj_data->sym_hashes[
+ h->aux->x_sym.x_tagndx.l];
+
+ sec = h2->root.u.def.section;
+ val = h2->root.u.def.value + sec->output_section->vma
+ + sec->output_offset;
+ }
+ else
+ /* This is a GNU extension. */
+ val = 0;
+ }
else if (! info->relocatable)
{
diff --git a/binutils/ChangeLog b/binutils/ChangeLog
index 6cb1f691a4..8ea599b12c 100644
--- a/binutils/ChangeLog
+++ b/binutils/ChangeLog
@@ -1,3 +1,7 @@
+2004-07-03 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
+
+ * doc/binutils.texi (nm): Clarify weak symbol description.
+
2004-06-24 Ben Elliston <bje@au.ibm.com>
* readelf.c (get_segment_type): Display "GNU_STACK", not just
diff --git a/binutils/doc/binutils.texi b/binutils/doc/binutils.texi
index 2e78720298..c27c627094 100644
--- a/binutils/doc/binutils.texi
+++ b/binutils/doc/binutils.texi
@@ -748,7 +748,8 @@ The symbol is a weak symbol that has not been specifically tagged as a
weak object symbol. When a weak defined symbol is linked with a normal
defined symbol, the normal defined symbol is used with no error.
When a weak undefined symbol is linked and the symbol is not defined,
-the value of the weak symbol becomes zero with no error.
+the value of the symbol is determined in a system-specific manner without
+error. Uppercase indicates that a default value has been specified.
@item -
The symbol is a stabs symbol in an a.out object file. In this case, the
diff --git a/gas/ChangeLog b/gas/ChangeLog
index 50a3ac42de..f02d2a816d 100644
--- a/gas/ChangeLog
+++ b/gas/ChangeLog
@@ -1,3 +1,9 @@
+2004-07-03 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
+
+ * config/obj-coff.c (obj_coff_weak): New .weak syntax for PE weak
+ externals.
+ * doc/as.texinfo (Weak): Document PE weak symbols.
+
2004-07-03 Richard Sandiford <rsandifo@redhat.com>
* config/tc-mips.c (HAVE_IN_PLACE_ADDENDS): New macro.
diff --git a/gas/config/obj-coff.c b/gas/config/obj-coff.c
index 8ead485253..0239b76f88 100644
--- a/gas/config/obj-coff.c
+++ b/gas/config/obj-coff.c
@@ -212,47 +212,6 @@ obj_coff_bss (ignore)
s_lcomm (0);
}
-/* Handle .weak. This is a GNU extension. */
-
-static void
-obj_coff_weak (ignore)
- int ignore ATTRIBUTE_UNUSED;
-{
- char *name;
- int c;
- symbolS *symbolP;
-
- do
- {
- name = input_line_pointer;
- c = get_symbol_end ();
- symbolP = symbol_find_or_make (name);
- *input_line_pointer = c;
- SKIP_WHITESPACE ();
-
-#if defined BFD_ASSEMBLER || defined S_SET_WEAK
- S_SET_WEAK (symbolP);
-#endif
-
-#ifdef TE_PE
- S_SET_STORAGE_CLASS (symbolP, C_NT_WEAK);
-#else
- S_SET_STORAGE_CLASS (symbolP, C_WEAKEXT);
-#endif
-
- if (c == ',')
- {
- input_line_pointer++;
- SKIP_WHITESPACE ();
- if (*input_line_pointer == '\n')
- c = '\n';
- }
- }
- while (c == ',');
-
- demand_empty_rest_of_line ();
-}
-
#ifdef BFD_ASSEMBLER
static segT fetch_coff_debug_section PARAMS ((void));
@@ -1135,6 +1094,86 @@ obj_coff_val (ignore)
demand_empty_rest_of_line ();
}
+/* Handle .weak. This is a GNU extension in formats other than PE. */
+static void
+obj_coff_weak (ignore)
+ int ignore ATTRIBUTE_UNUSED;
+{
+ char *name;
+ int c;
+ symbolS *symbolP;
+
+ do
+ {
+ name = input_line_pointer;
+ c = get_symbol_end ();
+ if (*name == 0)
+ {
+ as_warn (_("badly formed .weak directive ignored"));
+ ignore_rest_of_line ();
+ return;
+ }
+ symbolP = symbol_find_or_make (name);
+ *input_line_pointer = c;
+ SKIP_WHITESPACE ();
+
+#if defined BFD_ASSEMBLER || defined S_SET_WEAK
+ S_SET_WEAK (symbolP);
+#endif
+
+#ifdef TE_PE
+ /* See _Microsoft Portable Executable and Common Object
+ * File Format Specification_, section 5.5.3.
+ * Note that weak symbols without aux records are a GNU
+ * extension.
+ */
+ S_SET_STORAGE_CLASS (symbolP, C_NT_WEAK);
+
+ if (c == '=')
+ {
+ symbolS *alternateP;
+ long characteristics = 2;
+ ++input_line_pointer;
+ if (*input_line_pointer == '=')
+ {
+ characteristics = 1;
+ ++input_line_pointer;
+ }
+
+ SKIP_WHITESPACE();
+ name = input_line_pointer;
+ c = get_symbol_end();
+ if (*name == 0)
+ {
+ as_warn (_("alternate name missing in .weak directive"));
+ ignore_rest_of_line ();
+ return;
+ }
+ alternateP = symbol_find_or_make (name);
+ *input_line_pointer = c;
+
+ S_SET_NUMBER_AUXILIARY (symbolP, 1);
+ SA_SET_SYM_TAGNDX (symbolP, alternateP);
+ SA_SET_SYM_FSIZE (symbolP, characteristics);
+ }
+#else /* TE_PE */
+ S_SET_STORAGE_CLASS (symbolP, C_WEAKEXT);
+#endif /* TE_PE */
+
+ if (c == ',')
+ {
+ input_line_pointer++;
+ SKIP_WHITESPACE ();
+ if (*input_line_pointer == '\n')
+ c = '\n';
+ }
+
+ }
+ while (c == ',');
+
+ demand_empty_rest_of_line ();
+}
+
void
coff_obj_read_begin_hook ()
{
diff --git a/gas/config/tc-i386.c b/gas/config/tc-i386.c
index 823435f110..cc95843662 100644
--- a/gas/config/tc-i386.c
+++ b/gas/config/tc-i386.c
@@ -5280,6 +5280,12 @@ tc_gen_reloc (section, fixp)
*rel->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
rel->address = fixp->fx_frag->fr_address + fixp->fx_where;
+
+#ifdef TE_PE
+ if (S_IS_WEAK (fixp->fx_addsy))
+ rel->addend = rel->address - (*rel->sym_ptr_ptr)->value + 4;
+ else
+#endif
if (!use_rela_relocations)
{
/* HACK: Since i386 ELF uses Rel instead of Rela, encode the
diff --git a/gas/doc/as.texinfo b/gas/doc/as.texinfo
index 056fa6db35..29605b3f1e 100644
--- a/gas/doc/as.texinfo
+++ b/gas/doc/as.texinfo
@@ -3400,8 +3400,8 @@ respectively, with @code{.val} and @code{.type}.
@cindex auxiliary attributes, COFF symbols
The @command{@value{AS}} directives @code{.dim}, @code{.line}, @code{.scl},
-@code{.size}, and @code{.tag} can generate auxiliary symbol table
-information for COFF.
+@code{.size}, @code{.tag}, and @code{.weak} can generate auxiliary symbol
+table information for COFF.
@end ifset
@ifset SOM
@@ -3823,9 +3823,9 @@ Some machine configurations provide additional directives.
* Version:: @code{.version "@var{string}"}
* VTableEntry:: @code{.vtable_entry @var{table}, @var{offset}}
* VTableInherit:: @code{.vtable_inherit @var{child}, @var{parent}}
-* Weak:: @code{.weak @var{names}}
@end ifset
+* Weak:: @code{.weak @var{names}}
* Word:: @code{.word @var{expressions}}
* Deprecated:: Deprecated Directives
@end menu
@@ -5808,14 +5808,31 @@ parent whose addend is the value of the child symbol. As a special case the
parent name of @code{0} is treated as refering the @code{*ABS*} section.
@end ifset
-@ifset ELF
@node Weak
@section @code{.weak @var{names}}
@cindex @code{weak} directive
This directive sets the weak attribute on the comma separated list of symbol
@code{names}. If the symbols do not already exist, they will be created.
-@end ifset
+
+Weak symbols are supported in COFF as a GNU extension. This directive
+sets the weak attribute on the comma separated list of symbol
+@code{names}. If the symbols do not already exist, they will be created.
+
+@smallexample
+@code{.weak @var{name} [ < = | == > @var{alternate}] [, ...]}
+@end smallexample
+
+On the PE target, weak aliases are supported natively. Weak aliases
+(usually called "weak externals" in PE) are created when an alternate
+name is specified. When a weak symbol is linked and the symbol is not
+defined, the weak symbol becomes an alias for the alternate symbol. If
+one equal sign is used, the linker searches for defined symbols within
+other objects and libraries. This is the usual mode, historically
+called "lazy externals." Otherwise, when two equal signs are used,
+the linker searches for defined symbols only within other objects.
+
+Non-alias weak symbols are supported on PE as a GNU extension.
@node Word
@section @code{.word @var{expressions}}
diff --git a/ld/ChangeLog b/ld/ChangeLog
index 8aad6330be..c957555ab9 100644
--- a/ld/ChangeLog
+++ b/ld/ChangeLog
@@ -1,3 +1,7 @@
+2004-07-03 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
+
+ * ld.texinfo (WIN32): Document PE weak symbols.
+
2004-07-02 Kaz Kojima <kkojima@rr.iij4u.or.jp>
* emulparams/shlelf32_linux.sh (COMMONPAGESIZE): Set to 4KB.
diff --git a/ld/ld.texinfo b/ld/ld.texinfo
index c6002da1f9..2b77260b60 100644
--- a/ld/ld.texinfo
+++ b/ld/ld.texinfo
@@ -5292,6 +5292,24 @@ to handle the other symbols, then the both the new names @emph{and}
the original names for the renamed symbols will be exported.
In effect, you'd be aliasing those symbols, not renaming them,
which is probably not what you wanted.
+
+@cindex weak externals
+@item weak externals
+The Windows object format, PE, specifies a form of weak symbols called
+weak externals. When a weak symbol is linked and the symbol is not
+defined, the weak symbol becomes an alias for some other symbol. There
+are three variants of weak externals:
+@itemize
+@item Definition is searched for in objects and libraries, historically
+called lazy externals.
+@item Definition is searched for only in other objects, not in libraries.
+This form is not presently implemented.
+@item No search; the symbol is an alias. This form is not presently
+implemented.
+@end itemize
+As a GNU extension, weak symbols that do not specify an alternate symbol
+are supported. If the symbol is undefined when linking, the symbol
+uses a default value.
@end table
@ifclear GENERIC