summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--compiler/main/SysTools.hs19
1 files changed, 14 insertions, 5 deletions
diff --git a/compiler/main/SysTools.hs b/compiler/main/SysTools.hs
index aba4a1b06b..e6e7fa6ca5 100644
--- a/compiler/main/SysTools.hs
+++ b/compiler/main/SysTools.hs
@@ -690,7 +690,7 @@ in terror).
{- Note [Run-time linker info]
-See also: Trac #5240, Trac #6063
+See also: Trac #5240, Trac #6063, Trac #10110
Before 'runLink', we need to be sure to get the relevant information
about the linker we're using at runtime to see if we need any extra
@@ -717,6 +717,13 @@ We cache the LinkerInfo inside DynFlags, since clients may link
multiple times. The definition of LinkerInfo is there to avoid a
circular dependency.
+Some distributions change the link editor's default handling of
+ELF DT_NEEDED tags to include only those shared objects that are
+needed to resolve undefined symbols. For Template Haskell we need
+the last temporary shared library also if it is not needed for the
+currently linked temporary shared library. We specify --no-as-needed
+to override the default. This flag exists in GNU ld and GNU gold.
+
-}
@@ -753,12 +760,14 @@ getLinkerInfo' dflags = do
| any ("GNU ld" `isPrefixOf`) stdo =
-- GNU ld specifically needs to use less memory. This especially
-- hurts on small object files. Trac #5240.
+ -- Set DT_NEEDED for all shared libraries. Trac #10110.
return (GnuLD $ map Option ["-Wl,--hash-size=31",
- "-Wl,--reduce-memory-overheads"])
+ "-Wl,--reduce-memory-overheads",
+ "-Wl,--no-as-needed"])
| any ("GNU gold" `isPrefixOf`) stdo =
- -- GNU gold does not require any special arguments.
- return (GnuGold [])
+ -- GNU gold only needs --no-as-needed. Trac #10110.
+ return (GnuGold [Option "-Wl,--no-as-needed"])
-- Unknown linker.
| otherwise = fail "invalid --version output, or linker is unsupported"
@@ -875,7 +884,7 @@ runLink dflags args = do
linkargs <- neededLinkArgs `fmap` getLinkerInfo dflags
let (p,args0) = pgm_l dflags
args1 = map Option (getOpts dflags opt_l)
- args2 = args0 ++ args1 ++ args ++ linkargs
+ args2 = args0 ++ linkargs ++ args1 ++ args
mb_env <- getGccEnv args2
runSomethingFiltered dflags ld_filter "Linker" p args2 mb_env
where