@@ -15,7 +15,9 @@ import qualified Data.ByteString.Lazy as BSL (toChunks)
15import qualified Data.ByteString as BSS (ByteString)
15import qualified Data.ByteString as BSS (ByteString)
16import Control.Distributed.Process.Serializable ()
16import Control.Distributed.Process.Serializable ()
18+import Control.Concurrent (forkIO)
18import Control.Concurrent.Chan (writeChan)
19import Control.Concurrent.Chan (writeChan)
20+import Control.Exception (mask_)
19import Control.Monad (unless)
21import Control.Monad (unless)
20import Control.Monad.IO.Class (liftIO)
22import Control.Monad.IO.Class (liftIO)
21import Control.Monad.Reader (ask)
23import Control.Monad.Reader (ask)
@@ -30,6 +32,7 @@ import qualified Network.Transport as NT
30import Control.Distributed.Process.Internal.Types
32import Control.Distributed.Process.Internal.Types
31 ( LocalNode(localState, localEndPoint, localCtrlChan)
33 ( LocalNode(localState, localEndPoint, localCtrlChan)
32 , withValidLocalState
34 , withValidLocalState
35+ , modifyValidLocalState
33 , modifyValidLocalState_
36 , modifyValidLocalState_
34 , Identifier
37 , Identifier
35 , localConnections
38 , localConnections
@@ -51,6 +54,7 @@ import Control.Distributed.Process.Internal.Types
51 , Identifier(NodeIdentifier, ProcessIdentifier, SendPortIdentifier)
54 , Identifier(NodeIdentifier, ProcessIdentifier, SendPortIdentifier)
53import Control.Distributed.Process.Serializable (Serializable)
56import Control.Distributed.Process.Serializable (Serializable)
57+import Data.Foldable (forM_)
55--------------------------------------------------------------------------------
59--------------------------------------------------------------------------------
56-- Message sending --
60-- Message sending --
@@ -135,24 +139,28 @@ connBetween node from to implicitReconnect = do
135 setupConnBetween node from to implicitReconnect
139 setupConnBetween node from to implicitReconnect
137disconnect :: LocalNode -> Identifier -> Identifier -> IO ()
141disconnect :: LocalNode -> Identifier -> Identifier -> IO ()
138−disconnect node from to =
142+disconnect node from to = mask_ $ do
139− modifyValidLocalState_ node $ \vst ->
143+ mio <- modifyValidLocalState node $ \vst ->
140 case vst ^. localConnectionBetween from to of
144 case vst ^. localConnectionBetween from to of
141 Nothing ->
145 Nothing ->
142− return vst
146+ return (vst, return ())
143 Just (conn, _) -> do
147 Just (conn, _) -> do
145− return $ localConnectionBetween from to ^= Nothing $ vst
148+ return ( localConnectionBetween from to ^= Nothing $ vst
147closeImplicitReconnections :: LocalNode -> Identifier -> IO ()
153closeImplicitReconnections :: LocalNode -> Identifier -> IO ()
148−closeImplicitReconnections node to =
154+closeImplicitReconnections node to = mask_ $ do
149− modifyValidLocalState_ node $ \vst -> do
155+ mconns <- modifyValidLocalState node $ \vst -> do
150 let shouldClose (_, to') (_, WithImplicitReconnect) = to `impliesDeathOf` to'
156 let shouldClose (_, to') (_, WithImplicitReconnect) = to `impliesDeathOf` to'
151 shouldClose _ _ = False
157 shouldClose _ _ = False
152 let (affected, unaffected) =
158 let (affected, unaffected) =
153 Map.partitionWithKey shouldClose (vst ^. localConnections)
159 Map.partitionWithKey shouldClose (vst ^. localConnections)
154− mapM_ (NT.close . fst) (Map.elems affected)
155− return $ localConnections ^= unaffected $ vst
160+ return ( localConnections ^= unaffected $ vst
161+ , map fst $ Map.elems affected
163+ forM_ mconns $ forkIO . mapM_ NT.close
157-- | @a `impliesDeathOf` b@ is true if the death of @a@ (for instance, a node)
165-- | @a `impliesDeathOf` b@ is true if the death of @a@ (for instance, a node)
158-- implies the death of @b@ (for instance, a process on that node)
166-- implies the death of @b@ (for instance, a process on that node)