#5553: sendWakeup error in simple test program with MVars and killThread -----------------------+---------------------------------------------------- Reporter: bit | Owner: Type: bug | Status: new Priority: normal | Component: Runtime System Version: 7.2.1 | Keywords: Testcase: | Blockedby: Os: Linux | Blocking: Architecture: x86 | Failure: Incorrect result at runtime -----------------------+---------------------------------------------------- The following test program causes a '''sendWakeup''' error to be printed. It happens rarely, not on every run of the program.
I'm running GHC 7.2.1 on a fairly old Linux 2.6.27 system. Running it from the shell in a loop should cause it to eventually display the error message. I found that by causing CPU activity (such as running "yes" in another terminal) while the shell loop below is running triggers the error. {{{ $ ghc --make -Wall -O -threaded -rtsopts ghc_sendWakeup_bug.hs $ while [ 1 ]; do ./ghc_sendWakeup_bug 40; done ghc_sendWakeup_bug: sendWakeup: invalid argument (Bad file descriptor) }}} == ghc_sendWakeup_bug.hs == {{{ module Main ( startTest , main ) where import Control.Concurrent (ThreadId, forkIO, killThread, threadDelay) import Control.Concurrent.MVar import Control.Exception (finally, catch, SomeException, mask_) import Control.Monad (when, replicateM_, forever) import Prelude hiding (catch) import System.Environment (getArgs, getProgName) import System.Exit (exitFailure) import System.IO (hPutStrLn, stderr) startClient :: IO () startClient = threadDelay (1000 * 10) startTest :: Int -> IO () startTest numClients = do -- Code adapted from: -- http://hackage.haskell.org/packages/archive/base/4.4.0.0/doc/html /Control-Concurrent.html#g:12 children <- newMVar [] :: IO (MVar [MVar ()]) let forkChild :: IO () -> IO ThreadId forkChild io = do mvar <- newEmptyMVar mask_ $ do modifyMVar_ children (return . (mvar:)) forkIO (io `finally` putMVar mvar ()) waitForChildren :: IO () waitForChildren = do cs <- takeMVar children case cs of [] -> return () m:ms -> do putMVar children ms takeMVar m waitForChildren serverThread <- forkIO $ forever (threadDelay 1000000) replicateM_ numClients (forkChild startClient) catch waitForChildren (printException "waitForChildren") catch (killThread serverThread) (printException "killThread") printException :: String -> SomeException -> IO () printException place ex = hPutStrLn stderr $ "Error in " ++ place ++ ": " ++ show ex main :: IO () main = do args <- getArgs when (length args /= 1) $ do prog <- getProgName hPutStrLn stderr $ "Usage: " ++ prog ++ " <numClients>" exitFailure let numClients = read (args !! 0) startTest numClients }}} -- Ticket URL: <http://hackage.haskell.org/trac/ghc/ticket/5553> GHC <http://www.haskell.org/ghc/> The Glasgow Haskell Compiler _______________________________________________ Glasgow-haskell-bugs mailing list Glasgow-haskell-bugs@haskell.org http://www.haskell.org/mailman/listinfo/glasgow-haskell-bugs