Skip to content

Commit

Permalink
net-sim: asynchronous exception handling of accept call
Browse files Browse the repository at this point in the history
When we accept a connection we were using `bracketOnError`.  However we
should not unmask exceptions when executing the in-between callback.
The non-error case is non-blocking, interruptibly masked exceptions
ensures that the simulation state is updated.  In the error case, we
need to uninterruptible mask exceptions to close the channel (since it
is a blocking operation), and then update sim-state which is
a non-blocking operation: for that interruptibly masked exceptions is
enough.
  • Loading branch information
coot committed Mar 16, 2022
1 parent bd62a51 commit 8c6ed3d
Showing 1 changed file with 13 additions and 1 deletion.
14 changes: 13 additions & 1 deletion ouroboros-network-framework/src/Simulation/Network/Snocket.hs
Original file line number Diff line number Diff line change
Expand Up @@ -1037,7 +1037,7 @@ mkSnocket state tr = Snocket { getLocalAddr
(TestAddress addr)
accept_ time deltaAndIOErrType = Accept $ do
ctime <- getMonotonicTime
bracketOnError
bracketOnErrorMasked
(atomically $ do
fd <- readTVar fdVar
case fd of
Expand Down Expand Up @@ -1316,6 +1316,18 @@ mkSnocket state tr = Snocket { getLocalAddr
-- Utils
--

-- | Unlike 'bracketOnError' it does not unmask exceptions for the in between
-- action.
bracketOnErrorMasked :: MonadMask m
=> m a
-> (a -> m b)
-> (a -> m c)
-> m c
bracketOnErrorMasked before after thing = mask_ $ do
a <- before
thing a `onException` after a


hush :: Either a b -> Maybe b
hush Left {} = Nothing
hush (Right a) = Just a
Expand Down

0 comments on commit 8c6ed3d

Please sign in to comment.