Bir linker problemi nedeniyle Yesod'u Darcs kütüphanesi ile birlikte kullanmak imkansız gibi görünüyor. Problemi takip ettim ve Darcs internals'ı tanıyan insanlar tarafından etrafta dolanmak için ipuçları lazım.Yesod ve Darcs kitaplığını kullanırken yinelenen sembol hatası nasıl çalışır?
bir Yesod uygulamada darcs library kullanarak, aşağıdaki hatayı alıyorum:
ilgili nesne dosyaları arasında arama yapma gibi, Darcs ve aynı sembolü açığa cryptohash kütüphaneler neden gibi görünmektedirGHCi runtime linker: fatal error: I found a duplicate definition for symbol
sha256_init
whilst processing object file
/home/sebfisch/.cabal/lib/darcs-2.9.5/ghc-7.4.2/libHSdarcs-2.9.5.a
This could be caused by:
* Loading two different object files which export the same symbol
* Specifying the same object file twice on the GHCi command line
* An incorrect `package.conf' entry, causing some object to be
loaded twice.
GHCi cannot safely continue in this situation. Exiting now. Sorry.
ortaya :
:# for file in `find ~/.cabal/lib/ -name "*.a"`; do (readelf -s $file | grep -i sha256_init) && (echo $file; echo); done
293: 0000000000000000 0 NOTYPE GLOBAL DEFAULT UND sha256_init
17: 0000000000000690 94 FUNC GLOBAL DEFAULT 1 sha256_init
~/.cabal/lib/cryptohash-0.7.5/ghc-7.4.2/libHScryptohash-0.7.5.a
10: 0000000000000290 45 FUNC GLOBAL DEFAULT 1 sha256_init
~/.cabal/lib/darcs-2.8.2/ghc-7.4.2/libHSdarcs-2.8.2.a
Ben Darcs ve cryptohash kütüphaneler çatışma içinde olan onaylamak için bir test programı yazdım
import Crypt.SHA256 (sha256sum)
import Crypto.Hash.SHA256 (hash)
import Data.ByteString (empty)
import qualified Data.ByteString.Char8 as BS
main :: IO()
main = do
BS.putStrLn $ hash empty -- cryptohash
putStrLn $ sha256sum empty -- darcs
Benzer bir hata ile derlenmeyecektir:
/home/sebfisch/.cabal/lib/cryptohash-0.7.5/ghc-7.4.2/libHScryptohash-0.7.5.a(sha256.o): In function `sha256_update': sha256.c:(.text+0x4b0): multiple definition of `sha256_update'
/home/sebfisch/.cabal/lib/darcs-2.8.2/ghc-7.4.2/libHSdarcs-2.8.2.a(sha2.o):sha2.c:(.text+0xf90): first defined here
/home/sebfisch/.cabal/lib/cryptohash-0.7.5/ghc-7.4.2/libHScryptohash-0.7.5.a(sha256.o): In function `sha224_update': sha256.c:(.text+0x640): multiple definition of `sha224_update'
/home/sebfisch/.cabal/lib/darcs-2.8.2/ghc-7.4.2/libHSdarcs-2.8.2.a(sha2.o):sha2.c:(.text+0xbb0): first defined here
/home/sebfisch/.cabal/lib/cryptohash-0.7.5/ghc-7.4.2/libHScryptohash-0.7.5.a(sha256.o): In function `sha256_init': sha256.c:(.text+0x690): multiple definition of `sha256_init'
/home/sebfisch/.cabal/lib/darcs-2.8.2/ghc-7.4.2/libHSdarcs-2.8.2.a(sha2.o):sha2.c (.text+0x290): first defined here
/home/sebfisch/.cabal/lib/cryptohash-0.7.5/ghc-7.4.2/libHScryptohash-0.7.5.a(sha256.o): In function `sha224_init': sha256.c:(.text+0x6f0): multiple definition of `sha224_init'
/home/sebfisch/.cabal/lib/darcs-2.8.2/ghc-7.4.2/libHSdarcs-2.8.2.a(sha2.o):sha2.c (.text+0x620): first defined here
collect2: ld returned 1 exit status
cryptohash kütüphane yesod-static gereklidir ve bir Yesod'dan uygulaması yazarken kolaylıkla önüne geçilememektedir. Aynı uygulamada Yesod ve Darcs'i (kitaplık olarak) nasıl kullanabilirim?
Yinelenen sembolleri bir kitaplıktan silmek yardımcı olur mu? Her iki paket de FFI aracılığıyla karma işlevlere erişir ancak farklı dosyalar kullanır.
darcs/Crypt.SHA256 itibaren:
foreign import ccall unsafe "sha2.h sha256" c_sha256
:: Ptr CChar -> CSize -> Ptr Word8 -> IO()
cryptohash/Crypto.Hash.SHA256 Gönderen:
foreign import ccall unsafe "sha256.h sha256_init"
c_sha256_init :: Ptr Ctx -> IO()
foreign import ccall "sha256.h sha256_update"
c_sha256_update :: Ptr Ctx -> CString -> Word32 -> IO()
foreign import ccall unsafe "sha256.h sha256_finalize"
c_sha256_finalize :: Ptr Ctx -> CString -> IO()
başka bir fikir kendi karma işlevi kullanmak değil Darcs yeniden etmektir. Darcs'in SHA256
modülünü kriptohash kullanmak için nasıl yeniden canlandırabilirim? Test programımın main
işlevindeki iki deyim, aynı çıktısını vermez (diğer ifadeyi yorumlayarak test edilmiştir), bu nedenle Darcs'deki kriptohash kullanımı tamamen basit görünmez.
Bu işlevin Darcs sürümünü "darcs_sha256_init" gibi bir şeye yeniden adlandıramıyor musunuz? –
Eğer doğru anlıyorsam, sorun FFI ile kullanılan iki farklı C dosyasında sembol tanımlanmasıdır, bu nedenle Haskell işlevinin yeniden adlandırılması yardımcı olmaz, değil mi? –
Ancak C işlevini yeniden adlandırma yardımcı olur. Benim revize edilmiş cevabımı görün. –