@@ -1,4 +1,5 @@
1{-# LANGUAGE NoImplicitPrelude #-}
1{-# LANGUAGE NoImplicitPrelude #-}
2+{-# LANGUAGE DeriveDataTypeable #-}
2{-# LANGUAGE RecordWildCards #-}
3{-# LANGUAGE RecordWildCards #-}
3{-# LANGUAGE OverloadedStrings #-}
4{-# LANGUAGE OverloadedStrings #-}
4{-# LANGUAGE DeriveFunctor #-}
5{-# LANGUAGE DeriveFunctor #-}
@@ -11,6 +12,7 @@ module Stackage2.PackageDescription
11 ( FlatComponent (..)
12 ( FlatComponent (..)
12 , getFlattenedComponent
13 , getFlattenedComponent
13 , SimpleExtra (..)
14 , SimpleExtra (..)
16import Distribution.Package (Dependency (..))
18import Distribution.Package (Dependency (..))
@@ -25,6 +27,8 @@ import Control.Monad.State.Strict (execState, get, put)
25import qualified Data.Map as Map
27import qualified Data.Map as Map
26import qualified Data.Set as Set
28import qualified Data.Set as Set
27import Data.Aeson
29import Data.Aeson
30+import Distribution.System (OS, Arch)
31+import Distribution.Compiler (CompilerFlavor)
29data SimpleTree = SimpleTree
33data SimpleTree = SimpleTree
30 { stDeps :: Map PackageName VersionRange
34 { stDeps :: Map PackageName VersionRange
@@ -51,12 +55,16 @@ instance Monoid SimpleExtra where
53getFlattenedComponent
57getFlattenedComponent
54− :: Bool -- ^ include test suites?
60+ -> Bool -- ^ include test suites?
55 -> Bool -- ^ include benchmarks?
61 -> Bool -- ^ include benchmarks?
56 -> GenericPackageDescription
62 -> GenericPackageDescription
57− -> FlatComponent
63+ -> m FlatComponent
58−getFlattenedComponent includeTests includeBench gpd =
64+getFlattenedComponent checkCond' includeTests includeBench gpd =
66+ $ mapM (flattenComponent checkCond')
59− foldMap flattenComponent $ getSimpleTrees includeTests includeBench gpd
67+ $ getSimpleTrees includeTests includeBench gpd
61getSimpleTrees :: Bool -- ^ include test suites?
69getSimpleTrees :: Bool -- ^ include test suites?
62 -> Bool -- ^ include benchmarks?
70 -> Bool -- ^ include benchmarks?
@@ -103,14 +111,45 @@ instance Monoid FlatComponent where
103 (unionWith intersectVersionRanges a x)
111 (unionWith intersectVersionRanges a x)
106−flattenComponent :: SimpleTree -> FlatComponent
114+flattenComponent :: MonadThrow m => CheckCond -> SimpleTree -> m FlatComponent
107−flattenComponent (SimpleTree deps conds extra) =
115+flattenComponent checkCond' (SimpleTree deps conds extra) = do
116+ conds' <- mapM goCond conds
108− mconcat $ here : map goCond conds
117+ return $ mconcat $ here : conds'
110 here = FlatComponent { fcDeps = deps, fcExtra = extra }
119 here = FlatComponent { fcDeps = deps, fcExtra = extra }
111− goCond (cond, tree1, mtree2)
120+ goCond (cond, tree1, mtree2) = do
121+ b <- checkCond checkCond' cond
112− | checkCond cond = flattenComponent tree1
123+ then flattenComponent checkCond' tree1
113− | otherwise = maybe mempty flattenComponent mtree2
124+ else maybe (return mempty) (flattenComponent checkCond') mtree2
115−checkCond :: Condition ConfVar -> Bool
126+checkCond :: MonadThrow m => CheckCond -> Condition ConfVar -> m Bool
116−checkCond _ = False -- FIXME
127+checkCond CheckCond {..} cond0 =
130+ go (Var (OS os)) = return $ os == ccOS
131+ go (Var (Arch arch)) = return $ arch == ccArch
132+ go (Var (Flag flag)) =
133+ case lookup flag ccFlags of
134+ Nothing -> throwM $ FlagNotDefined ccPackageName flag cond0
136+ go (Var (Impl flavor range)) = return
137+ $ flavor == ccCompilerFlavor
138+ && ccCompilerVersion `withinRange` range
139+ go (Lit b) = return b
140+ go (CNot c) = not `liftM` go c
141+ go (CAnd x y) = (&&) `liftM` go x `ap` go y
142+ go (COr x y) = (||) `liftM` go x `ap` go y
144+data CheckCondException = FlagNotDefined PackageName FlagName (Condition ConfVar)
145+ deriving (Show, Typeable)
146+instance Exception CheckCondException
148+data CheckCond = CheckCond
149+ { ccPackageName :: PackageName -- for debugging only
152+ , ccFlags :: Map FlagName Bool
153+ , ccCompilerFlavor :: CompilerFlavor
154+ , ccCompilerVersion :: Version