[compute dangling nodes in a call graph, annex nodes and combine ingoing and outgoing edges
martin.hofmann@uni-bamberg.de**20091014074100] hunk ./src/Data/CallDependencies.hs 5
-        noCalls, addCall, tryAddCall,
-        admissible, allowedMaxCall, cycles
+        noCalls, addCall, annexFun, tryAddCall,
+        admissible, allowedMaxCall, cycles, danglingFuns
hunk ./src/Data/CallDependencies.hs 10
-import Data.Maybe (maybeToList, fromJust)
+import Data.Maybe (maybeToList, fromJust, mapMaybe)
hunk ./src/Data/CallDependencies.hs 13
-import qualified Data.Bimap as B (toAscList, empty, insert, member, lookup, lookupR)
+import qualified Data.Bimap as B (toAscList, empty, insert, delete, member, lookup, lookupR)
hunk ./src/Data/CallDependencies.hs 18
-import Data.List(unfoldr)
+import Data.List(unfoldr, (\\), deleteBy)
hunk ./src/Data/CallDependencies.hs 26
-import qualified Data.Graph.Inductive as G (empty)
+import qualified Data.Graph.Inductive as G (empty, nodes)
hunk ./src/Data/CallDependencies.hs 110
+       
+annexFun :: Name -> CallDep -> CallDep
+annexFun nn cd = 
+    let g   = (unC . callings $ cd)
+        cd' = asNode nn (nodes cd) >>= \n ->
+                return (composeAll (inn g n)(out g n)) >>= 
+                return . (remFunUnsafe nn) . (flip addEdgesUnsafe cd)
+    in maybe cd id cd'
+    where
+    composeAll :: [LEdge Ordering] -> [LEdge Ordering] -> [LEdge Ordering]
+    composeAll as bs = foldl (\es e -> (map (flip compose e) as)++es) [] bs
+    compose (s,_,l1)(_,g,l2) = (s,g,max l1 l2)
hunk ./src/Data/CallDependencies.hs 153
+
+danglingFuns :: CallDep -> [Name]
+danglingFuns cd  = 
+    let g  = unC . callings $ cd
+        ns = G.nodes g
+        outdegs  = map ((outdeg g) &&& id) $ ns
+        indegs  = map ((indeg g) &&& id) $ ns
+        outdeg0  = filter ((==0). fst) $ outdegs
+        outdeg1  = filter ((==1). fst) $ outdegs
+        indeg0  = filter ((==0). fst) $ indegs
+        replcbls = foldr (deleteBy ((==) `on` snd)) (outdeg0 ++ outdeg1) indeg0 
+        -- we need to remove the target functions, which are the only ones with 
+        -- indegree 0
+    in mapMaybe ((flip fromNode (nodes cd)). snd) replcbls
+              
hunk ./src/Data/CallDependencies.hs 230
+remFunUnsafe :: Name -> CallDep -> CallDep
+remFunUnsafe n cd@(CD (Calls cs) ns) = 
+    if not $ B.member n ns
+      then cd
+      else let cs' = maybe cs id $ liftM (flip delNode cs) (asNode n ns)
+               ns' = B.delete n ns               
+           in CD (Calls cs') ns'
+
+addEdgesUnsafe :: [LEdge Ordering] -> CallDep -> CallDep           
+addEdgesUnsafe es (CD (Calls cs) ns) = CD (Calls (insEdges es cs)) ns
+