aboutsummaryrefslogtreecommitdiff
path: root/ld
diff options
context:
space:
mode:
Diffstat (limited to 'ld')
-rw-r--r--ld/ChangeLog18
-rw-r--r--ld/NEWS4
-rw-r--r--ld/deffile.h10
-rw-r--r--ld/deffilep.y25
-rw-r--r--ld/ld.texinfo11
-rw-r--r--ld/pe-dll.c28
-rw-r--r--ld/testsuite/ChangeLog17
-rwxr-xr-xld/testsuite/ld-pe/aligncomm-1.c19
-rwxr-xr-xld/testsuite/ld-pe/aligncomm-2.c20
-rwxr-xr-xld/testsuite/ld-pe/aligncomm-3.c21
-rwxr-xr-xld/testsuite/ld-pe/aligncomm-4.c22
-rwxr-xr-xld/testsuite/ld-pe/aligncomm.d3
-rwxr-xr-xld/testsuite/ld-pe/pe-compile.exp (renamed from ld/testsuite/ld-pe/vers-script.exp)21
-rwxr-xr-x[-rw-r--r--]ld/testsuite/ld-pe/pe-run.exp (renamed from ld/testsuite/ld-pe/direct.exp)5
-rw-r--r--ld/testsuite/ld-pe/pe.exp2
15 files changed, 216 insertions, 10 deletions
diff --git a/ld/ChangeLog b/ld/ChangeLog
index 52364ef..15a2475 100644
--- a/ld/ChangeLog
+++ b/ld/ChangeLog
@@ -1,3 +1,21 @@
+2009-05-19 Dave Korn <dave.korn.cygwin@gmail.com>
+
+ * NEWS: Mention new feature.
+ * deffile.h (def_file_aligncomm): Add new struct definition.
+ (def_file): Add new def_file_aligncomm member.
+ * deffilep.y (%token): Add new ALIGNCOMM token.
+ (command): Add production rule for ALIGNCOMM.
+ (def_file_free): Free any chained def_file_aligncomm structs.
+ (diropts[]): Add entry for '-aligncomm' .drectve command.
+ (def_aligncomm): New grammar function.
+ * ld.texinfo: Document new feature.
+ * pe-dll.c (process_def_file): Rename from this ...
+ (process_def_file_and_drectve): ... to this, updating all callers,
+ and process any aligncomms chained to the def file after scanning
+ all .drectve sections.
+ (generate_edata): Updated to match.
+ (pe_dll_build_sections): Likewise.
+
2009-05-17 Dave Korn <dave.korn.cygwin@gmail.com>
2008-08-07 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
diff --git a/ld/NEWS b/ld/NEWS
index dce9503..6f05361 100644
--- a/ld/NEWS
+++ b/ld/NEWS
@@ -1,5 +1,9 @@
-*- text -*-
+* PE targets now support a GNU extension to allow the alignment of common
+ common symbols to be specified. This support uses custom options in
+ the .drectve section, which will be disregarded by the native tools.
+
* PE targets now add primitive support for ELF version scripts; symbols
are not versioned, but the local and global symbol visibility directives
are respected when filtering symbols in auto-export mode.
diff --git a/ld/deffile.h b/ld/deffile.h
index 1e7a0cb..79953b3 100644
--- a/ld/deffile.h
+++ b/ld/deffile.h
@@ -53,6 +53,12 @@ typedef struct def_file_import {
int data; /* = 1 if data */
} def_file_import;
+typedef struct def_file_aligncomm {
+ struct def_file_aligncomm *next; /* Chain pointer. */
+ char *symbol_name; /* Name of common symbol. */
+ unsigned int alignment; /* log-2 alignment. */
+} def_file_aligncomm;
+
typedef struct def_file {
/* From the NAME or LIBRARY command. */
char *name;
@@ -83,6 +89,10 @@ typedef struct def_file {
/* From the VERSION command, -1 if not specified. */
int version_major, version_minor;
+
+ /* Only expected from .drectve sections, not .DEF files. */
+ def_file_aligncomm *aligncomms;
+
} def_file;
extern def_file *def_file_empty (void);
diff --git a/ld/deffilep.y b/ld/deffilep.y
index 11c075d..5f02727 100644
--- a/ld/deffilep.y
+++ b/ld/deffilep.y
@@ -89,6 +89,7 @@ static void def_section_alt (const char *, const char *);
static void def_stacksize (int, int);
static void def_version (int, int);
static void def_directive (char *);
+static void def_aligncomm (char *str, int align);
static int def_parse (void);
static int def_error (const char *);
static int def_lex (void);
@@ -106,7 +107,7 @@ static const char *lex_parse_string_end = 0;
%token NAME LIBRARY DESCRIPTION STACKSIZE_K HEAPSIZE CODE DATAU DATAL
%token SECTIONS EXPORTS IMPORTS VERSIONK BASE CONSTANTU CONSTANTL
-%token PRIVATEU PRIVATEL
+%token PRIVATEU PRIVATEL ALIGNCOMM
%token READ WRITE EXECUTE SHARED NONAMEU NONAMEL DIRECTIVE
%token <id> ID
%token <number> NUMBER
@@ -134,6 +135,7 @@ command:
| VERSIONK NUMBER { def_version ($2, 0);}
| VERSIONK NUMBER '.' NUMBER { def_version ($2, $4);}
| DIRECTIVE ID { def_directive ($2);}
+ | ALIGNCOMM ID ',' NUMBER { def_aligncomm ($2, $4);}
;
@@ -379,6 +381,14 @@ def_file_free (def_file *def)
free (m);
}
+ while (def->aligncomms)
+ {
+ def_file_aligncomm *c = def->aligncomms;
+ def->aligncomms = def->aligncomms->next;
+ free (c->symbol_name);
+ free (c);
+ }
+
free (def);
}
@@ -573,6 +583,7 @@ diropts[] =
{ "-stack", STACKSIZE_K },
{ "-attr", SECTIONS },
{ "-export", EXPORTS },
+ { "-aligncomm", ALIGNCOMM },
{ 0, 0 }
};
@@ -831,6 +842,18 @@ def_directive (char *str)
d->len = strlen (str);
}
+static void
+def_aligncomm (char *str, int align)
+{
+ def_file_aligncomm *c = xmalloc (sizeof (def_file_aligncomm));
+
+ c->symbol_name = xstrdup (str);
+ c->alignment = (unsigned int) align;
+
+ c->next = def->aligncomms;
+ def->aligncomms = c;
+}
+
static int
def_error (const char *err)
{
diff --git a/ld/ld.texinfo b/ld/ld.texinfo
index bdfa948..2121725 100644
--- a/ld/ld.texinfo
+++ b/ld/ld.texinfo
@@ -6994,6 +6994,17 @@ implemented.
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.
+
+@cindex aligned common symbols
+@item aligned common symbols
+As a GNU extension to the PE file format, it is possible to specify the
+desired alignment for a common symbol. This information is conveyed from
+the assembler or compiler to the linker by means of GNU-specific commands
+carried in the object file's @samp{.drectve} section, which are recognized
+by @command{ld} and respected when laying out the common symbols. Native
+tools will be able to process object files employing this GNU extension,
+but will fail to respect the alignment instructions, and may issue noisy
+warnings about unknown linker directives.
@end table
@ifclear GENERIC
diff --git a/ld/pe-dll.c b/ld/pe-dll.c
index 3f2815e..f615b2d 100644
--- a/ld/pe-dll.c
+++ b/ld/pe-dll.c
@@ -615,7 +615,7 @@ auto_export (bfd *abfd, def_file *d, const char *n)
}
static void
-process_def_file (bfd *abfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
+process_def_file_and_drectve (bfd *abfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
{
int i, j;
struct bfd_link_hash_entry *blhe;
@@ -642,6 +642,28 @@ process_def_file (bfd *abfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
}
}
+ /* Process aligned common symbol information from the
+ .drectve sections now; common symbol allocation is
+ done before final link, so it will be too late to
+ process them in process_embedded_commands() called
+ from _bfd_coff_link_input_bfd(). */
+ if (pe_def_file->aligncomms)
+ {
+ def_file_aligncomm *ac = pe_def_file->aligncomms;
+ while (ac)
+ {
+ struct coff_link_hash_entry *sym_hash;
+ sym_hash = coff_link_hash_lookup (coff_hash_table (info),
+ ac->symbol_name, FALSE, FALSE, FALSE);
+ if (sym_hash && sym_hash->root.type == bfd_link_hash_common
+ && sym_hash->root.u.c.p->alignment_power < (unsigned) ac->alignment)
+ {
+ sym_hash->root.u.c.p->alignment_power = (unsigned) ac->alignment;
+ }
+ ac = ac->next;
+ }
+ }
+
/* If we are not building a DLL, when there are no exports
we do not build an export table at all. */
if (!pe_dll_export_everything && pe_def_file->num_exports == 0
@@ -1057,7 +1079,7 @@ generate_edata (bfd *abfd, struct bfd_link_info *info ATTRIBUTE_UNUSED)
}
/* Fill the exported symbol offsets. The preliminary work has already
- been done in process_def_file(). */
+ been done in process_def_file_and_drectve(). */
static void
fill_exported_offsets (bfd *abfd ATTRIBUTE_UNUSED, struct bfd_link_info *info)
@@ -3066,7 +3088,7 @@ pe_dll_build_sections (bfd *abfd, struct bfd_link_info *info)
{
pe_dll_id_target (bfd_get_target (abfd));
pe_output_file_set_long_section_names (abfd);
- process_def_file (abfd, info);
+ process_def_file_and_drectve (abfd, info);
if (pe_def_file->num_exports == 0 && !info->shared)
return;
diff --git a/ld/testsuite/ChangeLog b/ld/testsuite/ChangeLog
index c906850..db9fe11 100644
--- a/ld/testsuite/ChangeLog
+++ b/ld/testsuite/ChangeLog
@@ -1,3 +1,20 @@
+2009-05-19 Dave Korn <dave.korn.cygwin@gmail.com>
+
+ * ld-pe/aligncomm-1.c: New test source file.
+ * ld-pe/aligncomm-2.c: Likewise.
+ * ld-pe/aligncomm-3.c: Likewise.
+ * ld-pe/aligncomm-4.c: Likewise.
+ * ld-pe/aligncomm.d: New test pattern file.
+
+ * ld-pe/direct.exp: Deleted, and content moved into ...
+ * ld-pe/pe-run.exp: ... New common file for all PE run tests.
+
+ * ld-pe/vers-script.exp: Deleted, and content merged into ...
+ * ld-pe/pe-compile.exp: ... New common file for PE tests needing
+ a compiler, adding aligned common tests.
+
+ * ld-pe/pe.exp: Update header comment.
+
2009-05-17 Aaron W. LaFramboise <aaron98wiridge9@aaronwl.com>
* ld-pe/exports.d: New file.
diff --git a/ld/testsuite/ld-pe/aligncomm-1.c b/ld/testsuite/ld-pe/aligncomm-1.c
new file mode 100755
index 0000000..44f576e
--- /dev/null
+++ b/ld/testsuite/ld-pe/aligncomm-1.c
@@ -0,0 +1,19 @@
+
+typedef float __m128 __attribute__ ((__vector_size__ (16), __may_alias__));
+
+long s1 = 0;
+__m128 r;
+__m128 * volatile raddr = &r;
+
+int main (int argc, const char **argv)
+{
+ return 15 & (int)raddr;
+}
+
+void __main (void)
+{
+ asm (".section .drectve\n"
+ " .ascii \" -aligncomm:_r,4\"\n"
+ " .ascii \" -aligncomm:r,4\"\n"
+ " .text");
+}
diff --git a/ld/testsuite/ld-pe/aligncomm-2.c b/ld/testsuite/ld-pe/aligncomm-2.c
new file mode 100755
index 0000000..3b33362
--- /dev/null
+++ b/ld/testsuite/ld-pe/aligncomm-2.c
@@ -0,0 +1,20 @@
+
+typedef float __m128 __attribute__ ((__vector_size__ (16), __may_alias__));
+
+long s1 = 0;
+long s2 = 0;
+__m128 r;
+__m128 * volatile raddr = &r;
+
+int main (int argc, const char **argv)
+{
+ return 15 & (int)raddr;
+}
+
+void __main (void)
+{
+ asm (".section .drectve\n"
+ " .ascii \" -aligncomm:_r,4\"\n"
+ " .ascii \" -aligncomm:r,4\"\n"
+ " .text");
+}
diff --git a/ld/testsuite/ld-pe/aligncomm-3.c b/ld/testsuite/ld-pe/aligncomm-3.c
new file mode 100755
index 0000000..04fdfd1
--- /dev/null
+++ b/ld/testsuite/ld-pe/aligncomm-3.c
@@ -0,0 +1,21 @@
+
+typedef float __m128 __attribute__ ((__vector_size__ (16), __may_alias__));
+
+long s1 = 0;
+long s2 = 0;
+long s3 = 0;
+__m128 r;
+__m128 * volatile raddr = &r;
+
+int main (int argc, const char **argv)
+{
+ return 15 & (int)raddr;
+}
+
+void __main (void)
+{
+ asm (".section .drectve\n"
+ " .ascii \" -aligncomm:_r,4\"\n"
+ " .ascii \" -aligncomm:r,4\"\n"
+ " .text");
+}
diff --git a/ld/testsuite/ld-pe/aligncomm-4.c b/ld/testsuite/ld-pe/aligncomm-4.c
new file mode 100755
index 0000000..854d9ba
--- /dev/null
+++ b/ld/testsuite/ld-pe/aligncomm-4.c
@@ -0,0 +1,22 @@
+
+typedef float __m128 __attribute__ ((__vector_size__ (16), __may_alias__));
+
+long s1 = 0;
+long s2 = 0;
+long s3 = 0;
+long s4 = 0;
+__m128 r;
+__m128 * volatile raddr = &r;
+
+int main (int argc, const char **argv)
+{
+ return 15 & (int)raddr;
+}
+
+void __main (void)
+{
+ asm (".section .drectve\n"
+ " .ascii \" -aligncomm:_r,4\"\n"
+ " .ascii \" -aligncomm:r,4\"\n"
+ " .text");
+}
diff --git a/ld/testsuite/ld-pe/aligncomm.d b/ld/testsuite/ld-pe/aligncomm.d
new file mode 100755
index 0000000..6f33644
--- /dev/null
+++ b/ld/testsuite/ld-pe/aligncomm.d
@@ -0,0 +1,3 @@
+#...
+[0-9a-fA-F]{7,15}0 . r
+#...
diff --git a/ld/testsuite/ld-pe/vers-script.exp b/ld/testsuite/ld-pe/pe-compile.exp
index e0638b1..b9bc4af 100755
--- a/ld/testsuite/ld-pe/vers-script.exp
+++ b/ld/testsuite/ld-pe/pe-compile.exp
@@ -1,4 +1,5 @@
-# Expect script for version-script driven export from dll tests
+# Expect script for complex PE tests that require a C compiler
+# in addition to the just-built binutils.
# Copyright 2009
# Free Software Foundation, Inc.
#
@@ -20,7 +21,7 @@
# MA 02110-1301, USA.
#
-# This test can only be run on PE/COFF platforms.
+# These tests can only be run on PE/COFF platforms.
if {![is_pecoff_format]} {
return
}
@@ -28,6 +29,8 @@ if {![is_pecoff_format]} {
# No compiler, no test.
if { [which $CC] == 0 } {
untested "PE version scripts"
+ untested "aligned common tests"
+ # Add more "untested" directives here when adding more tests below.
return
}
@@ -36,7 +39,7 @@ proc build_vers_script_dll_o {} {
global CFLAGS
global srcdir
global subdir
-
+
# Compile the object file.
if ![ld_compile "$CC $CFLAGS -shared" $srcdir/$subdir/vers-script-dll.c tmpdir/vers-script-dll.o] {
fail "compiling shared lib object"
@@ -74,3 +77,15 @@ run_ver_script_test "vers-script-2"
run_ver_script_test "vers-script-3"
run_ver_script_test "vers-script-4"
+set align_tests {
+ {"aligned common 1" "" "" {aligncomm-1.c}
+ {{nm -C aligncomm.d}} "aligncomm-1.x"}
+ {"aligned common 2" "" "" {aligncomm-2.c}
+ {{nm -C aligncomm.d}} "aligncomm-2.x"}
+ {"aligned common 3" "" "" {aligncomm-3.c}
+ {{nm -C aligncomm.d}} "aligncomm-3.x"}
+ {"aligned common 4" "" "" {aligncomm-4.c}
+ {{nm -C aligncomm.d}} "aligncomm-4.x"}
+}
+
+run_ld_link_tests $align_tests
diff --git a/ld/testsuite/ld-pe/direct.exp b/ld/testsuite/ld-pe/pe-run.exp
index b4bb629..3e7c356 100644..100755
--- a/ld/testsuite/ld-pe/direct.exp
+++ b/ld/testsuite/ld-pe/pe-run.exp
@@ -1,4 +1,5 @@
-# Expect script for direct linking from dll tests
+# Expect script for complex PE tests that require a C compiler and the ability
+# to run target executables natively, in addition to the just-built binutils.
# Copyright 2006, 2007
# Free Software Foundation, Inc.
#
@@ -67,7 +68,7 @@ proc test_direct_link_dll {} {
global srcdir
global subdir
global tmpdir
-
+
# Compile the dll.
if ![ld_compile "$CC $CFLAGS" $srcdir/$subdir/direct_dll.c $tmpdir/direct_dll.o ] {
fail "compiling shared lib"
diff --git a/ld/testsuite/ld-pe/pe.exp b/ld/testsuite/ld-pe/pe.exp
index ad91f06..3fcf8cb 100644
--- a/ld/testsuite/ld-pe/pe.exp
+++ b/ld/testsuite/ld-pe/pe.exp
@@ -1,4 +1,4 @@
-# Expect script for export table in executables tests
+# Expect script for simple PE tests that require the just-built binutils only.
# Copyright 2004, 2006, 2007
# Free Software Foundation, Inc.
#