packages feed

warp 3.3.6 → 3.3.7

raw patch · 4 files changed

+24/−21 lines, 4 files

Files

ChangeLog.md view
@@ -1,3 +1,8 @@+## 3.3.7++* InvalidArgument (Bad file descriptor) is ignored in `receive`.+  [#787](https://github.com/yesodweb/wai/pull/787)+ ## 3.3.6  * Fixing a bug of thread killed in the case of event source with
Network/Wai/Handler/Warp/Recv.hs view
@@ -17,7 +17,9 @@ import Foreign.ForeignPtr (withForeignPtr) import Foreign.Ptr (Ptr, castPtr, plusPtr) import GHC.Conc (threadWaitRead)+import qualified GHC.IO.Exception as E import Network.Socket (Socket)+import qualified System.IO.Error as E #if MIN_VERSION_network(3,1,0) import Network.Socket (withFdSocket) #else@@ -94,8 +96,11 @@                 siz' = siz - len             loop bss' siz' +-- The timeout manager may close the socket.+-- In that case, an error of "Bad file descriptor" occurs.+-- We ignores it because we expect TimeoutThread. receive :: Socket -> BufferPool -> Recv-receive sock pool = withBufferPool pool $ \ (ptr, size) -> do+receive sock pool = E.handle handler $ withBufferPool pool $ \ (ptr, size) -> do #if MIN_VERSION_network(3,1,0)   withFdSocket sock $ \fd -> do #elif MIN_VERSION_network(3,0,0)@@ -105,6 +110,11 @@ #endif     let size' = fromIntegral size     fromIntegral <$> receiveloop fd ptr size'+  where+    handler :: E.IOException -> IO ByteString+    handler e+      | E.ioeGetErrorType e == E.InvalidArgument = return ""+      | otherwise                                = E.throwIO e  receiveBuf :: Socket -> RecvBuf receiveBuf sock buf0 siz0 = do
Network/Wai/Handler/Warp/Run.hs view
@@ -17,7 +17,7 @@ import Control.Exception as E import qualified Data.ByteString as S import Data.Char (chr)-import Data.IORef (IORef, newIORef, readIORef, writeIORef, atomicModifyIORef')+import Data.IORef (IORef, newIORef, readIORef, writeIORef) import Data.Streaming.Network (bindPortTCP) import Foreign.C.Error (Errno(..), eCONNABORTED) import GHC.IO.Exception (IOException(..))@@ -282,10 +282,7 @@ fork set mkConn addr app counter ii = settingsFork set $ \unmask ->     -- Call the user-supplied on exception code if any     -- exceptions are thrown.-    handle (settingsOnException set Nothing) .-    -- Allocate a new IORef indicating whether the connection has been-    -- closed, to avoid double-freeing a connection-    withClosedRef $ \ref ->+    handle (settingsOnException set Nothing) $         -- Run the connection maker to get a new connection, and ensure         -- that the connection is closed. If the mkConn call throws an         -- exception, we will leak the connection. If the mkConn call is@@ -296,21 +293,13 @@         -- We grab the connection before registering timeouts since the         -- timeouts will be useless during connection creation, due to the         -- fact that async exceptions are still masked.-        bracket mkConn (cleanUp ref) (serve unmask ref)+        bracket mkConn cleanUp (serve unmask)   where-    withClosedRef inner = newIORef False >>= inner--    closeConn ref conn = do-        isClosed <- atomicModifyIORef' ref $ \x -> (True, x)-        unless isClosed $ connClose conn--    cleanUp ref (conn, _) = closeConn ref conn `finally` connFree conn+    cleanUp (conn, _) = connClose conn `finally` connFree conn      -- We need to register a timeout handler for this thread, and-    -- cancel that handler as soon as we exit. We additionally close-    -- the connection immediately in case the child thread catches the-    -- async exception or performs some long-running cleanup action.-    serve unmask ref (conn, transport) = bracket register cancel $ \th -> do+    -- cancel that handler as soon as we exit.+    serve unmask (conn, transport) = bracket register cancel $ \th -> do         -- We now have fully registered a connection close handler in         -- the case of all exceptions, so it is safe to once again         -- allow async exceptions.@@ -322,8 +311,7 @@            -- above ensures the connection is closed.            when goingon $ serveConnection conn ii th addr transport set app       where-        register = T.registerKillThread (timeoutManager ii)-                                        (closeConn ref conn)+        register = T.registerKillThread (timeoutManager ii) (connClose conn)         cancel   = T.cancel      onOpen adr    = increase counter >> settingsOnOpen  set adr
warp.cabal view
@@ -1,5 +1,5 @@ Name:                warp-Version:             3.3.6+Version:             3.3.7 Synopsis:            A fast, light-weight web server for WAI applications. License:             MIT License-file:        LICENSE