module Package.C.Build.Tree ( buildByName
) where
import Control.Recursion
import CPkgPrelude
import Data.Containers.ListUtils (nubOrd)
import Data.List (isInfixOf)
import Package.C.Build
import Package.C.Monad
import Package.C.PackageSet
import Package.C.Type
import Package.C.Type.Tree
import System.Directory (doesDirectoryExist)
import System.FilePath ((</>))
data BuildDirs = BuildDirs { libraries :: [FilePath]
, share :: [FilePath]
, include :: [FilePath]
, binaries :: [FilePath]
}
getAll :: [BuildDirs] -> BuildDirs
getAll bds =
let go f = fold (f <$> bds)
in BuildDirs (go libraries) (go share) (go include) (go binaries)
immoralFilter :: Maybe TargetTriple -> [FilePath] -> [FilePath]
immoralFilter Nothing fps = fps
immoralFilter (Just tgt') fps =
let infixDir = show tgt'
in filter (\fp -> infixDir `isInfixOf` fp || "meson" `isInfixOf` fp || "XML-Parser" `isInfixOf` fp || "python3" `isInfixOf` fp) fps
filterCross :: Maybe TargetTriple -> [FilePath] -> [FilePath]
filterCross Nothing = id
filterCross (Just tgt') =
let infixDir = show tgt'
in filter (\fp -> not (infixDir `isInfixOf` fp) || "ncurses" `isInfixOf` fp)
buildWithContext :: DepTree CPkg
-> Maybe TargetTriple
-> Bool
-> Bool
-> PkgM ()
buildWithContext cTree host sta glob = zygoM' dirAlg buildAlg cTree
where buildAlg :: DepTreeF CPkg (BuildDirs, ()) -> PkgM ()
buildAlg (DepNodeF c preBds) =
buildCPkg c host sta glob ds (immoralFilter host ls) is (filterCross host bs)
where (BuildDirs ls ds is bs) = getAll (fst <$> preBds)
buildAlg (BldDepNodeF c preBds) =
buildCPkg c Nothing False False ds ls is bs
where (BuildDirs ls ds is bs) = getAll (fst <$> preBds)
mkBuildDirs :: MonadIO m => FilePath -> BuildDirs -> m BuildDirs
mkBuildDirs pkgDir (BuildDirs ls ds is bs) = do
let linkDir = pkgDir </> "lib"
linkDir64 = pkgDir </> "lib64"
includeDir = pkgDir </> "include"
dataDir = pkgDir </> "share"
binDir = pkgDir </> "bin"
links = linkDir64 : linkDir : ls
bins = binDir : bs
shares = dataDir : ds
includeExists <- liftIO (doesDirectoryExist includeDir)
let includes = if includeExists
then includeDir : is
else is
pure (BuildDirs (nubOrd links) (nubOrd shares) (nubOrd includes) (nubOrd bins))
dirAlg :: DepTreeF CPkg BuildDirs -> PkgM BuildDirs
dirAlg (DepNodeF c bds) = do
let bldDirs@(BuildDirs ls ds is bs) = getAll bds
buildVars <- getVars host sta ds (immoralFilter host ls) is (filterCross host bs)
pkgDir <- cPkgToDir c host glob buildVars
mkBuildDirs pkgDir bldDirs
dirAlg (BldDepNodeF c bds) = do
let bldDirs@(BuildDirs ls ds is bs) = getAll bds
buildVars <- getVars Nothing False ds ls is bs
pkgDir <- cPkgToDir c Nothing False buildVars
mkBuildDirs pkgDir bldDirs
buildByName :: PackId -> Maybe TargetTriple -> Maybe String -> Bool -> Bool -> PkgM ()
buildByName pkId host pkSet sta glob = do
allPkgs <- liftIO (pkgsM pkId pkSet)
buildWithContext allPkgs host sta glob