The compiler now does not produce executables. In order to achieve Xcode integration, it now produces a lib.a file as output, which is then linked into Xcode. Without these changes, GHC will link correctly, but since Xcode provides the code signing and installation onto the iPhone, it is much more convenient to do things this way. The purpose of this change | otherwise = (cGCC, map Option cGCCOptions) is to remove the GCC options from the general options and move them to GCC only, because libtool does not accept most of them. For the same reason you can see we are removing lots of options that normally get passed to the linker. libtool gives lots of warnings which can apparently be safely ignored. We filter libtool's output so the user doesn't see them. --- ghc-6.10.2.orig/compiler/main/SysTools.lhs 2009-03-31 06:13:16.000000000 +1300 +++ ghc-6.10.2/compiler/main/SysTools.lhs 2009-06-18 15:54:37.000000000 +1200 @@ -238,7 +238,7 @@ -- install on the target, which is exactly what we're -- trying to avoid. = (installed_bin "gcc", [gcc_b_arg, gcc_mingw_include_arg]) - | otherwise = (cGCC, []) + | otherwise = (cGCC, map Option cGCCOptions) perl_path | isWindowsHost && am_installed = installed_bin cGHC_PERL | otherwise = cGHC_PERL @@ -280,7 +280,7 @@ -- Other things being equal, as and ld are simply gcc ; let (as_prog,as_args) = (gcc_prog,gcc_args) - (ld_prog,ld_args) = (gcc_prog,gcc_args) + (ld_prog,ld_args) = ("libtool",[]) ; return dflags1{ ghcUsagePath = ghc_usage_msg_path, @@ -457,12 +457,12 @@ mb_env <- getGccEnv args1 runSomethingFiltered dflags id "Assembler" p args1 mb_env -runLink :: DynFlags -> [Option] -> IO () -runLink dflags args = do +runLink :: (String -> String) -> DynFlags -> [Option] -> IO () +runLink filter_fn dflags args = do let (p,args0) = pgm_l dflags args1 = args0 ++ args mb_env <- getGccEnv args1 - runSomethingFiltered dflags id "Linker" p args1 mb_env + runSomethingFiltered dflags filter_fn "Linker" p args1 mb_env runMkDLL :: DynFlags -> [Option] -> IO () runMkDLL dflags args = do --- ghc-6.10.2.orig/compiler/main/DriverPipeline.hs 2009-03-31 06:13:16.000000000 +1300 +++ ghc-6.10.2/compiler/main/DriverPipeline.hs 2009-06-18 15:54:37.000000000 +1200 @@ -993,7 +995,7 @@ -- instructions, which need things 16-byte aligned, -- but we don't 16-byte align things. Thus drop -- back to generic i686 compatibility. Trac #2983. - ++ ["-march=i686"] + -- ++ ["-march=i686"] -- Breaks with iPhone stuff - may need to revisit #endif ++ (if hcc && mangle then md_regd_c_flags @@ -1162,7 +1164,7 @@ mapM_ assemble_file [1..n] -- and join the split objects into a single object file: - let ld_r args = SysTools.runLink dflags ([ + let ld_r args = SysTools.runLink id dflags ([ SysTools.Option "-nostdlib", SysTools.Option "-nodefaultlibs", SysTools.Option "-Wl,-r", @@ -1409,13 +1411,13 @@ rc_objs <- maybeCreateManifest dflags output_fn let (md_c_flags, _) = machdepCCOpts dflags - SysTools.runLink dflags ( + SysTools.runLink filterLibtoolWarnings dflags ( [ SysTools.Option verb , SysTools.Option "-o" , SysTools.FileOption "" output_fn ] ++ map SysTools.Option ( - md_c_flags + cTARGET_LDFLAGS -- iPhone: gives the Platform's library directory as a -L option ++ o_files #ifdef mingw32_TARGET_OS ++ [dynMain] @@ -1424,18 +1426,8 @@ ++ lib_path_opts ++ extra_ld_opts ++ rc_objs -#ifdef darwin_TARGET_OS - ++ framework_path_opts - ++ framework_opts -#endif ++ pkg_lib_path_opts ++ pkg_link_opts -#ifdef darwin_TARGET_OS - ++ pkg_framework_path_opts - ++ pkg_framework_opts -#endif - ++ debug_opts - ++ thread_opts )) -- parallel only: move binary to another dir -- HWL @@ -1443,6 +1435,14 @@ if success then return () else ghcError (InstallationError ("cannot move binary")) +-- | Suppress some libtool warnings +filterLibtoolWarnings :: String -> String +filterLibtoolWarnings = unlines . filter f . lines + where + f l | " has no symbols" `isSuffixOf` l = False + | " due to use of basename, truncation and blank padding" `isSuffixOf` l = False + | " (due to use of basename, truncation, blank padding or duplicate input files)" `isSuffixOf` l = False + | otherwise = True exeFileName :: DynFlags -> FilePath exeFileName dflags @@ -1452,7 +1452,8 @@ then s <.> "exe" else s #else - s + (let (path, file) = splitFileName s + in combine path ("lib"++file++".a")) -- For iPhone we must link the executable into Xcode #endif | otherwise = #if defined(mingw32_HOST_OS) @@ -1605,7 +1606,7 @@ let output_fn = case o_file of { Just s -> s; Nothing -> "a.out"; } pwd <- getCurrentDirectory - SysTools.runLink dflags + SysTools.runLink id dflags ([ SysTools.Option verb , SysTools.Option "-dynamiclib" , SysTools.Option "-o" --- ghc-6.10.2.orig/compiler/main/Packages.lhs 2009-03-31 06:13:15.000000000 +1300 +++ ghc-6.10.2/compiler/main/Packages.lhs 2009-06-18 15:54:37.000000000 +1200 @@ -642,7 +642,11 @@ collectLinkOpts dflags ps = concat (map all_opts ps) where libs p = packageHsLibs dflags p ++ extraLibraries p - all_opts p = map ("-l" ++) (libs p) ++ ldOptions p + -- on iPhone we are using libtool, which doesn't do the final link, and + -- which doesn't understand most ld options. Therefore we are just + -- discarding any specified in packages, and requiring these to be added + -- by hand to Xcode where necessary. + all_opts p = map ("-l" ++) (libs p) -- ++ ldOptions p packageHsLibs :: DynFlags -> PackageConfig -> [String] packageHsLibs dflags p = map (mkDynName . addSuffix) (hsLibraries p) --- ghc-6.10.2.orig/rts/package.conf.in 2009-03-31 06:13:16.000000000 +1300 +++ ghc-6.10.2/rts/package.conf.in 2009-06-18 15:54:37.000000000 +1200 @@ -30,13 +30,13 @@ hs-libraries: "HSrts" -extra-libraries: "m" /* for ldexp() */ - , "ffi" -#ifndef HAVE_FRAMEWORK_GMP - , "gmp" +/* iPhone: remove m and dl, because these are dynamic libraries, and we + * can't pass these to libtool, or it will complain. */ +extra-libraries: /*"m"*/ + "ffi", + "gmp" #ifdef HAVE_LIBDL - , "dl" -#endif + /*, "dl"*/ #endif #ifdef HAVE_LIBRT , "rt"