diff --git a/compiler/ghci/Linker.hs b/compiler/ghci/Linker.hs index b5979e83bb3138d2a5597214db3eae513d76dcbd..4b33f4c239bf3ded61381a86182827b901adbd69 100644 --- a/compiler/ghci/Linker.hs +++ b/compiler/ghci/Linker.hs @@ -1201,7 +1201,7 @@ locateLib dflags is_hs dirs lib -- for a dynamic library (#5289) -- otherwise, assume loadDLL can find it -- - = findDll `orElse` findArchive `orElse` tryGcc `orElse` assumeDll + = findDll `orElse` findArchive `orElse` tryGcc `orElse` tryGccPrefixed `orElse` assumeDll | not dynamicGhc -- When the GHC package was not compiled as dynamic library @@ -1222,6 +1222,7 @@ locateLib dflags is_hs dirs lib mk_hs_dyn_lib_path dir = dir </> mkHsSOName platform hs_dyn_lib_name so_name = mkSOName platform lib + lib_so_name = "lib" ++ so_name mk_dyn_lib_path dir = case (arch, os) of (ArchX86_64, OSSolaris2) -> dir </> ("64/" ++ so_name) _ -> dir </> so_name @@ -1232,6 +1233,7 @@ locateLib dflags is_hs dirs lib findHSDll = liftM (fmap DLLPath) $ findFile mk_hs_dyn_lib_path dirs findDll = liftM (fmap DLLPath) $ findFile mk_dyn_lib_path dirs tryGcc = liftM (fmap DLLPath) $ searchForLibUsingGcc dflags so_name dirs + tryGccPrefixed = liftM (fmap DLLPath) $ searchForLibUsingGcc dflags lib_so_name dirs assumeDll = return (DLL lib) infixr `orElse` @@ -1246,7 +1248,9 @@ locateLib dflags is_hs dirs lib searchForLibUsingGcc :: DynFlags -> String -> [FilePath] -> IO (Maybe FilePath) searchForLibUsingGcc dflags so dirs = do - str <- askCc dflags (map (FileOption "-L") dirs + -- GCC does not seem to extend the library search path (using -L) when using + -- --print-file-name. So instead pass it a new base location. + str <- askCc dflags (map (FileOption "-B") dirs ++ [Option "--print-file-name", Option so]) let file = case lines str of [] -> "" diff --git a/testsuite/tests/ghci/linking/Makefile b/testsuite/tests/ghci/linking/Makefile index 5b8e23c66cca701ba4da25b64308d15c4e109153..c833454ea788d815821876e1404ec180332c7048 100644 --- a/testsuite/tests/ghci/linking/Makefile +++ b/testsuite/tests/ghci/linking/Makefile @@ -40,7 +40,11 @@ ghcilink002 : .PHONY: ghcilink003 ghcilink003 : +ifeq "$(WINDOWS)" "YES" + echo ":q" | "$(TEST_HC)" --interactive -ignore-dot-ghci -v0 -lstdc++-6 +else echo ":q" | "$(TEST_HC)" --interactive -ignore-dot-ghci -v0 -lstdc++ +endif # Test 4: # package P @@ -114,7 +118,11 @@ ghcilink006 : echo "version: 1.0" >>$(PKG006) echo "id: test-XXX" >>$(PKG006) echo "key: test-1.0" >>$(PKG006) +ifeq "$(WINDOWS)" "YES" + echo "extra-libraries: stdc++-6" >>$(PKG006) +else echo "extra-libraries: stdc++" >>$(PKG006) +endif '$(GHC_PKG)' init $(LOCAL_PKGCONF006) '$(GHC_PKG)' --no-user-package-db -f $(LOCAL_PKGCONF006) register $(PKG006) -v0 # diff --git a/testsuite/tests/ghci/linking/T1407.script b/testsuite/tests/ghci/linking/T1407.script deleted file mode 100644 index 97164359d04e60f1e5a5b6526404d4eca1076671..0000000000000000000000000000000000000000 --- a/testsuite/tests/ghci/linking/T1407.script +++ /dev/null @@ -1,4 +0,0 @@ -:set -ldl -import Foreign -import Foreign.C.String -foreign import ccall "dlerror" dle :: IO CString diff --git a/testsuite/tests/ghci/linking/all.T b/testsuite/tests/ghci/linking/all.T index 6675a539ec4918d1ca3b6ea7c9ace706c7068a52..a8aa5a3b94352bb7056002152b5a83c741c5b73c 100644 --- a/testsuite/tests/ghci/linking/all.T +++ b/testsuite/tests/ghci/linking/all.T @@ -12,8 +12,6 @@ test('ghcilink002', test('ghcilink003', [ - # still cannot load libstdc++ on Windows. See also #4468. - when(opsys('mingw32'), expect_broken(5289)), unless(doing_ghci, skip), extra_clean(['dir003/*','dir003']) ], @@ -33,8 +31,6 @@ test('ghcilink005', test('ghcilink006', [ - # still cannot load libstdc++ on Windows. See also #4468. - when(opsys('mingw32'), expect_broken(5289)), unless(doing_ghci, skip), extra_clean(['dir006/*','dir006']) ], @@ -44,8 +40,7 @@ test('ghcilink006', test('T3333', [extra_clean('T3333.o'), unless(doing_ghci, skip), - unless(opsys('linux') or ghci_dynamic(), expect_broken(3333))], + unless(ghci_dynamic(), expect_broken(3333))], run_command, ['$MAKE -s --no-print-directory T3333']) -test('T1407', normal, ghci_script, ['T1407.script']) diff --git a/testsuite/tests/ghci/linking/dyn/A.c b/testsuite/tests/ghci/linking/dyn/A.c new file mode 100644 index 0000000000000000000000000000000000000000..fec94f2829fe7158b7b9d0bc9873ba96cd074b33 --- /dev/null +++ b/testsuite/tests/ghci/linking/dyn/A.c @@ -0,0 +1,17 @@ +#if defined(_MSC_VER) + // Microsoft + #define EXPORT __declspec(dllexport) +#elif defined(_GCC) + // GCC + #define EXPORT __attribute__((visibility("default"))) +#else + // do nothing and hope for the best? + #define EXPORT +#endif + +extern EXPORT int foo(); + +EXPORT int foo() +{ + return 2; +} diff --git a/testsuite/tests/ghci/linking/dyn/Makefile b/testsuite/tests/ghci/linking/dyn/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..8a3b7363e458600b0c41b0eea86080441f3791c6 --- /dev/null +++ b/testsuite/tests/ghci/linking/dyn/Makefile @@ -0,0 +1,23 @@ +TOP=../../../.. +include $(TOP)/mk/boilerplate.mk +include $(TOP)/mk/test.mk + +ifeq "$(WINDOWS)" "YES" +DLL = lib$1.dll +else ifeq "$(DARWIN)" "YES" +DLL = lib$1.dylib +else +DLL = lib$1.so +endif + + +.PHONY: load_short_name +load_short_name: + rm -rf bin_short + mkdir bin_short + gcc -shared A.c -o "bin_short/$(call DLL,A)" + echo ":q" | "$(TEST_HC)" --interactive -L"$(PWD)/bin_short" -lA -v0 + +.PHONY: compile_libAS +compile_libAS: + gcc -shared A.c -o $(call DLL,AS) diff --git a/testsuite/tests/ghci/linking/dyn/T1407.script b/testsuite/tests/ghci/linking/dyn/T1407.script new file mode 100644 index 0000000000000000000000000000000000000000..0274f8245dd082782682984d5d5db9c0dfe76cda --- /dev/null +++ b/testsuite/tests/ghci/linking/dyn/T1407.script @@ -0,0 +1,4 @@ +:set -lAS +import Foreign +import Foreign.C.Types +foreign import ccall "foo" dle :: IO CInt diff --git a/testsuite/tests/ghci/linking/dyn/all.T b/testsuite/tests/ghci/linking/dyn/all.T new file mode 100644 index 0000000000000000000000000000000000000000..2810c7f29fc3cfa23370bcec79000e39f613b97f --- /dev/null +++ b/testsuite/tests/ghci/linking/dyn/all.T @@ -0,0 +1,12 @@ +test('load_short_name', + [unless(doing_ghci, skip), + extra_clean(['bin_short/*', 'bin_short'])], + run_command, + ['$MAKE -s --no-print-directory load_short_name']) + +test('T1407', + [unless(doing_ghci, skip), + extra_clean(['libAS.*']), + pre_cmd('$MAKE -s --no-print-directory compile_libAS'), + extra_hc_opts('-L.')], + ghci_script, ['T1407.script']) diff --git a/testsuite/tests/ghci/scripts/all.T b/testsuite/tests/ghci/scripts/all.T index 70a816b5e03d6ec8de31b39eab8530022bcaeb17..ec5559ef2ddbf5d4cebe273506261cc360f0d938 100755 --- a/testsuite/tests/ghci/scripts/all.T +++ b/testsuite/tests/ghci/scripts/all.T @@ -204,7 +204,7 @@ test('T9878', ghci_script, ['T9878.script']) test('T9878b', [ extra_run_opts('-fobject-code'), - extra_clean(['T9878.hi','T9878.o'])], + extra_clean(['T9878b.hi','T9878b.o'])], ghci_script, ['T9878b.script']) test('T10321', normal, ghci_script, ['T10321.script'])