TypeDecl.hs revision b87efd3db0d2dc41615ea28669faf80fc1b48d56
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantModule : $Header$
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantDescription : analyse type declarations
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantCopyright : (c) Christian Maeder and Uni Bremen 2002-2005
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantLicense : GPLv2 or higher
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantMaintainer : Christian.Maeder@dfki.de
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantStability : provisional
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantPortability : portable
3437829f938dbb44527d91fbbc5f430a1243c5a5JnRouvignacanalyse type declarations
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant ( anaFormula
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant , mapAnMaybe
3437829f938dbb44527d91fbbc5f430a1243c5a5JnRouvignac , anaTypeItems
3437829f938dbb44527d91fbbc5f430a1243c5a5JnRouvignac , dataPatToType
3437829f938dbb44527d91fbbc5f430a1243c5a5JnRouvignac , ana1Datatype
3437829f938dbb44527d91fbbc5f430a1243c5a5JnRouvignac , anaDatatype
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant , addDataSen
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantimport qualified Data.Map as Map
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantimport qualified Data.Set as Set
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantimport Data.List(group)
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant-- | resolve and type check a formula
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaFormula :: Annoted Term -> State Env (Maybe (Annoted Term, Annoted Term))
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaFormula at = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant rt <- resolve $ item at
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Nothing -> return Nothing
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Just t -> do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant mt <- typeCheck (mkLazyType unitType) t
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ case mt of
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Nothing -> Nothing
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Just e -> Just (at { item = t }, at { item = e })
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaVars :: Env -> Vars -> Type -> Result Term
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaVars te vv t = case vv of
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Var v -> return $ QualVar $ VarDecl v t Other $ posOfId v
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant VarTuple vs ps -> let
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant (topTy, ts) = getTypeAppl t
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant n = length ts in
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant if n > 1 && lesserType te topTy (toProdType n nullRange) then
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant if n == length vs then
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let lrs = zipWith (anaVars te) vs ts
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant lms = map maybeResult lrs in
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant if all isJust lms then
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ TupleTerm (map fromJust lms) ps
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant else Result (concatMap diags lrs) Nothing
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant else mkError "wrong arity" topTy
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant else mkError "product type expected" topTy
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant-- | lift a analysis function to annotated items
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantmapAnMaybe :: (Monad m) => (Annoted a -> m (Maybe b)) -> [Annoted a]
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant -> m [Annoted b]
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantmapAnMaybe f al = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant il <- mapM f al
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ map ( \ (i, a) -> replaceAnnoted (fromJust i) a) $
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant filter (isJust . fst) $ zip il al
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant-- | analyse annotated type items
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaTypeItems :: GenKind -> [Annoted TypeItem] -> State Env [Annoted TypeItem]
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaTypeItems gk l = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant ul <- mapAnMaybe ana1TypeItem l
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant tys <- mapM ( \ (Datatype d) -> dataPatToType d) $
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant filter ( \ t -> case t of
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Datatype _ -> True
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant _ -> False) $ map item ul
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant rl <- mapAnMaybe (anaTypeItem gk tys) ul
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant addDataSen tys
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant-- | add sentences for data type definitions
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantaddDataSen :: [DataPat] -> State Env ()
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantaddDataSen tys = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant tm <- gets typeMap
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let tis = map ( \ (DataPat _ i _ _ _) -> i) tys
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant ds = foldr ( \ i dl -> case Map.lookup i tm of
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Nothing -> dl
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Just ti -> case typeDefn ti of
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant DatatypeDefn dd -> dd : dl
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant _ -> dl) [] tis
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant sen = (makeNamed ("ga_" ++ showSepList (showString "_") showId tis "")
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant $ DatatypeSen ds) { isDef = True }
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant unless (null tys) $ appendSentences [sen]
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantana1TypeItem :: Annoted TypeItem -> State Env (Maybe TypeItem)
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantana1TypeItem t = case item t of
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Datatype d -> do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant md <- ana1Datatype $ replaceAnnoted d t
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ fmap Datatype md
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant i -> return $ Just i
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaTypeDecl :: [TypePattern] -> Kind -> Range -> State Env (Maybe TypeItem)
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaTypeDecl pats kind ps = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant cm <- gets classMap
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let Result cs _ = anaKindM kind cm
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant Result ds (Just is) = convertTypePatterns pats
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant addDiags $ cs ++ ds
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let ak = if null cs then kind else universe
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant mis <- mapM (addTypePattern NoTypeDefn ak) is
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let newPats = map toTypePattern $ catMaybes mis
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ if null newPats then Nothing else Just $ TypeDecl newPats ak ps
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaIsoDecl :: [TypePattern] -> Range -> State Env (Maybe TypeItem)
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantanaIsoDecl pats ps = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let Result ds (Just is) = convertTypePatterns pats
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant addDiags ds
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant mis <- mapM (addTypePattern NoTypeDefn universe) is
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant case catMaybes mis of
43cf232e238dd2e98c8b2badc91071b6ada52956gary.williams [] -> return Nothing
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let (i, _) : ris = reverse nis
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant mapM_ (\ (j, _) -> addAliasType False j
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant (TypeScheme [] (TypeName i rStar 0) $ posOfId j) universe) ris
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ Just $ IsoDecl (map toTypePattern nis) ps
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantsetTypePatternVars :: [(Id, [TypeArg])] -> State Env [(Id, [TypeArg])]
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovantsetTypePatternVars ol = do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant l <- mapM ( \ (i, tArgs) -> do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant newAs <- mapM anaddTypeVarDecl tArgs
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return (i, catMaybes newAs)) ol
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant let g = group $ map snd l
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant [_ : _] -> do
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant newAs <- mapM anaddTypeVarDecl $ snd $ head l
bc36152ff9a3ea2c2fa75ba2a64becfae0d96e5ecsovant return $ map ( \ (i, _) -> (i, catMaybes newAs)) l
putTypeMap $ Map.map ( \ ti -> case typeDefn ti of
return $ DataPat Map.empty i nAs rk $ patToType i nAs rk
iMap = Map.fromList $ map (\ (DataPat _ j _ _ _) -> (j, j)) tys
$ Set.fromList newAlts
addOpId c sc Set.empty (ConstructData i)
addOpId s (getSelScheme dp pa ts) Set.empty $ SelectData
(Set.singleton $ ConstrInfo c sc) i
Just ((_, sks), newTy) -> case Set.toList sks of