Race condition in setNumCapabilities
|Reported by:||akio||Owned by:||simonmar|
|Operating System:||Unknown/Multiple||Architecture:||x86_64 (amd64)|
|Type of failure:||Runtime crash||Difficulty:||Unknown|
|Test Case:||Blocked By:|
In HEAD, the following program sometimes deadlocks (about 1/10 of the time).
import Control.Concurrent import Control.Monad import GHC.Conc main = do mainTid <- myThreadId labelThread mainTid "main" forM_ [0..0] $ \i -> forkIO $ do subTid <- myThreadId labelThread subTid $ "sub " ++ show i forM_ [0..100000000] $ \j -> putStrLn $ "sub " ++ show i ++ ": " ++ show j yield setNumCapabilities 2
The problem seems to be that there is a race condition between setNumCapabilites and a Task returning from a foreign call. Specifically, a sequence of events like the following can happen:
- Task 0 makes a foreign call.
- Task 1 calls setNumCapabilities()
- The call on task 0 returns; it reads task->cap from the memory.
- Task 1 moves the Capabilities, invalidating all pointers to them.
- Task 0 takes over the invalidated Capability.
The attached patch adds an ASSERT to the RTS to demonstrate the problem (it does not fix the problem).
Change History (14)
Changed 8 months ago by akio
comment:1 Changed 8 months ago by parcs
comment:4 Changed 8 months ago by simonmar
- Owner set to simonmar
- Priority changed from normal to highest