oneShot, compileFile,
-- Interfaces for the batch-mode driver
- staticLink,
+ linkBinary,
-- Interfaces for the compilation manager (interpreted/batch-mode)
preprocess,
compile, CompResult(..),
link,
- -- DLL building
- doMkDLL,
-
) where
#include "HsVersions.h"
import HeaderInfo
import DriverPhases
import SysTools
-import qualified SysTools
import HscMain
import Finder
import HscTypes
import Data.List ( isSuffixOf )
import Data.Maybe
import System.Exit
-import System.Cmd
import System.Environment
-- ---------------------------------------------------------------------------
-- ---------------------------------------------------------------------------
-- Link
-link :: GhcMode -- interactive or batch
+link :: GhcLink -- interactive or batch
-> DynFlags -- dynamic flags
-> Bool -- attempt linking in batch mode?
-> HomePackageTable -- what to link
-- will succeed.
#ifdef GHCI
-link Interactive dflags batch_attempt_linking hpt
+link LinkInMemory dflags batch_attempt_linking hpt
= do -- Not Linking...(demand linker will do the job)
return Succeeded
#endif
-link JustTypecheck dflags batch_attempt_linking hpt
+link NoLink dflags batch_attempt_linking hpt
= return Succeeded
-link BatchCompile dflags batch_attempt_linking hpt
+link LinkBinary dflags batch_attempt_linking hpt
| batch_attempt_linking
= do
let
-- Don't showPass in Batch mode; doLink will do that for us.
let link = case ghcLink dflags of
- MkDLL -> doMkDLL
- StaticLink -> staticLink
+ LinkBinary -> linkBinary
+ LinkDynLib -> linkDynLib
link dflags obj_files pkg_deps
debugTraceMsg dflags 3 (text "link: done")
- -- staticLink only returns if it succeeds
+ -- linkBinary only returns if it succeeds
return Succeeded
| otherwise
| otherwise
= case ghcLink dflags of
NoLink -> return ()
- StaticLink -> staticLink dflags o_files link_pkgs
- MkDLL -> doMkDLL dflags o_files link_pkgs
+ LinkBinary -> linkBinary dflags o_files link_pkgs
+ LinkDynLib -> linkDynLib dflags o_files []
where
-- Always link in the haskell98 package for static linking. Other
-- packages have to be specified via the -package flag.
-- wrapper script calling the binary. Currently, we need this only in
-- a parallel way (i.e. in GUM), because PVM expects the binary in a
-- central directory.
--- This is called from staticLink below, after linking. I haven't made it
+-- This is called from linkBinary below, after linking. I haven't made it
-- a separate phase to minimise interfering with other modules, and
-- we don't need the generality of a phase (MoveBinary is always
-- done after linking and makes only sense in a parallel setup) -- HWL
"",
"args: while ($a = shift(@ARGV)) {",
" if ( $a eq '+RTS' ) {",
- " $in_RTS_args = 1;",
+ " $in_RTS_args = 1;",
" } elsif ( $a eq '-RTS' ) {",
- " $in_RTS_args = 0;",
+ " $in_RTS_args = 0;",
" }",
" if ( $a eq '-d' && $in_RTS_args ) {",
- " $debug = '-';",
+ " $debug = '-';",
" } elsif ( $a =~ /^-qN(\\d+)/ && $in_RTS_args ) {",
- " $nprocessors = $1;",
+ " $nprocessors = $1;",
" } elsif ( $a =~ /^-qp(\\d+)/ && $in_RTS_args ) {",
- " $nprocessors = $1;",
+ " $nprocessors = $1;",
" } else {",
- " push(@nonPVM_args, $a);",
+ " push(@nonPVM_args, $a);",
" }",
"}",
"",
-- read any interface files), so the user must explicitly specify all
-- the packages.
-staticLink :: DynFlags -> [FilePath] -> [PackageId] -> IO ()
-staticLink dflags o_files dep_packages = do
+linkBinary :: DynFlags -> [FilePath] -> [PackageId] -> IO ()
+linkBinary dflags o_files dep_packages = do
let verb = getVerbFlag dflags
output_fn = exeFileName dflags
"a.out"
#endif
------------------------------------------------------------------------------
--- Making a DLL (only for Win32)
-
-doMkDLL :: DynFlags -> [String] -> [PackageId] -> IO ()
-doMkDLL dflags o_files dep_packages = do
+linkDynLib :: DynFlags -> [String] -> [PackageId] -> IO ()
+linkDynLib dflags o_files dep_packages = do
let verb = getVerbFlag dflags
let static = opt_Static
let no_hs_main = dopt Opt_NoHsMain dflags
let o_file = outputFile dflags
- let output_fn = case o_file of { Just s -> s; Nothing -> "HSdll.dll"; }
pkg_lib_paths <- getPackageLibraryPath dflags dep_packages
let pkg_lib_path_opts = map ("-L"++) pkg_lib_paths
-- probably _stub.o files
extra_ld_inputs <- readIORef v_Ld_inputs
- -- opts from -optdll-<blah>
+ let (md_c_flags, _) = machdepCCOpts dflags
+#if defined(mingw32_HOST_OS)
+ -----------------------------------------------------------------------------
+ -- Making a DLL
+ -----------------------------------------------------------------------------
+
+ let output_fn = case o_file of { Just s -> s; Nothing -> "HSdll.dll"; }
+
+ -- opts from -optdll-<blah>
let extra_ld_opts = getOpts dflags opt_dll
let pstate = pkgState dflags
then []
else [ head (libraryDirs rts_pkg) ++ "/Main.dll_o",
head (libraryDirs base_pkg) ++ "/PrelMain.dll_o" ]
-
- let (md_c_flags, _) = machdepCCOpts dflags
SysTools.runMkDLL dflags
([ SysTools.Option verb
, SysTools.Option "-o"
then [ "" ]
else [ "--export-all" ])
))
-
+#else
+ -----------------------------------------------------------------------------
+ -- Making a DSO
+ -----------------------------------------------------------------------------
+ -- opts from -optl-<blah>
+ let extra_ld_opts = getOpts dflags opt_l
+ let output_fn = case o_file of { Just s -> s; Nothing -> "a.out"; }
+
+ SysTools.runLink dflags
+ ([ SysTools.Option verb
+ , SysTools.Option "-o"
+ , SysTools.FileOption "" output_fn
+ ]
+ ++ map SysTools.Option (
+ md_c_flags
+ ++ o_files
+ ++ [ "-shared", "-Wl,-Bsymbolic" ] -- we need symbolic linking to resolve non-PIC intra-package-relocations
+ ++ extra_ld_inputs
+ ++ lib_path_opts
+ ++ extra_ld_opts
+ ++ pkg_lib_path_opts
+ ++ pkg_link_opts
+ ))
+#endif
-- -----------------------------------------------------------------------------
-- Running CPP