@@ -77,14 +77,16 @@ import Control.Monad.IO.Class (MonadIO, liftIO)
77import Control.Applicative ((<$>))
77import Control.Applicative ((<$>))
78import Control.Exception (Exception, throwIO, SomeException)
78import Control.Exception (Exception, throwIO, SomeException)
79import qualified Control.Exception as Ex (catch, mask)
79import qualified Control.Exception as Ex (catch, mask)
80−import Control.Distributed.Process.Internal.StrictMVar (modifyMVar)
80+import Control.Distributed.Process.Internal.StrictMVar
81import Control.Concurrent.Chan (writeChan)
85import Control.Concurrent.Chan (writeChan)
82import Control.Concurrent.STM
86import Control.Concurrent.STM
84 , atomically
88 , atomically
89 , readTVar
91 , readTVar
90 , writeTVar
92 , writeTVar
@@ -123,12 +125,19 @@ import Control.Distributed.Process.Internal.Types
123 , createMessage
125 , createMessage
124 , runLocalProcess
126 , runLocalProcess
125 , ImplicitReconnect(WithImplicitReconnect, NoImplicitReconnect)
127 , ImplicitReconnect(WithImplicitReconnect, NoImplicitReconnect)
127import Control.Distributed.Process.Internal.Messaging
131import Control.Distributed.Process.Internal.Messaging
128 ( sendMessage
132 ( sendMessage
129 , sendBinary
133 , sendBinary
130 , disconnect
134 , disconnect
136+import Control.Distributed.Process.Internal.WeakTQueue
133--------------------------------------------------------------------------------
142--------------------------------------------------------------------------------
134-- Basic messaging --
143-- Basic messaging --
@@ -157,21 +166,26 @@ expect = receiveWait [match return]
157-- | Create a new typed channel
166-- | Create a new typed channel
158newChan :: Serializable a => Process (SendPort a, ReceivePort a)
167newChan :: Serializable a => Process (SendPort a, ReceivePort a)
159newChan = do
168newChan = do
160− proc <- ask
169+ proc <- ask
161− liftIO . modifyMVar (processState proc) $ \st -> do
170+ liftIO . modifyMVar (processState proc) $ \st -> do
162− chan <- liftIO . atomically $ newTChan
163− let lcid = st ^. channelCounter
171+ let lcid = st ^. channelCounter
164− cid = SendPortId { sendPortProcessId = processId proc
172+ let cid = SendPortId { sendPortProcessId = processId proc
165− , sendPortLocalId = lcid
173+ , sendPortLocalId = lcid
167− sport = SendPort cid
175+ let sport = SendPort cid
176+ chan <- liftIO newTQueueIO
177+ chan' <- mkWeakTQueue chan $ finalizer (processState proc) lcid
168− rport = ReceivePortSingle chan
178+ let rport = ReceivePortSingle chan
169− tch = TypedChannel chan
179+ let tch = TypedChannel chan'
170− return ( (channelCounter ^: (+ 1))
180+ return ( (channelCounter ^: (+ 1))
171− . (typedChannelWithId lcid ^= Just tch)
181+ . (typedChannelWithId lcid ^= Just tch)
173− , (sport, rport)
183+ , (sport, rport)
186+ finalizer :: StrictMVar LocalProcessState -> LocalSendPortId -> IO ()
187+ finalizer processState lcid = modifyMVar_ processState $
188+ return . (typedChannelWithId lcid ^= Nothing)
176-- | Send a message on a typed channel
190-- | Send a message on a typed channel
177sendChan :: Serializable a => SendPort a -> a -> Process ()
191sendChan :: Serializable a => SendPort a -> a -> Process ()
@@ -189,7 +203,7 @@ receiveChan = liftIO . atomically . receiveSTM
190 receiveSTM :: ReceivePort a -> STM a
204 receiveSTM :: ReceivePort a -> STM a
191 receiveSTM (ReceivePortSingle c) =
205 receiveSTM (ReceivePortSingle c) =
192− readTChan c
206+ readTQueue c
193 receiveSTM (ReceivePortBiased ps) =
207 receiveSTM (ReceivePortBiased ps) =
194 foldr1 orElse (map receiveSTM ps)
208 foldr1 orElse (map receiveSTM ps)
195 receiveSTM (ReceivePortRR psVar) = do
209 receiveSTM (ReceivePortRR psVar) = do