1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46
|
{-# LANGUAGE OverloadedStrings #-}
module ThreadSpec where
import Control.Concurrent
import Control.Concurrent.Async
import Data.ByteString (ByteString)
import qualified Data.ByteString.Lazy as L
import Data.Foldable (traverse_)
import Network.TLS
import Test.Hspec
import Test.Hspec.QuickCheck
import API
import Arbitrary ()
import Run
spec :: Spec
spec = do
describe "thread safety" $ do
prop "can read/write concurrently" $ \params ->
runTLS params tlsClient tlsServer
tlsClient :: Chan ByteString -> Context -> IO ()
tlsClient queue ctx = do
handshake ctx
runReaderWriters ctx "server-value" "client-value"
d <- readChan queue
sendData ctx (L.fromChunks [d])
checkCtxFinished ctx
bye ctx
tlsServer :: Context -> Chan [ByteString] -> IO ()
tlsServer ctx queue = do
handshake ctx
runReaderWriters ctx "client-value" "server-value"
d <- recvData ctx
writeChan queue [d]
checkCtxFinished ctx
bye ctx
runReaderWriters :: Context -> ByteString -> L.ByteString -> IO ()
runReaderWriters ctx r w =
-- run concurrently 10 readers and 10 writers on the same context
let workers = concat $ replicate 10 [recvDataAssert ctx r, sendData ctx w]
in runConcurrently $ traverse_ Concurrently workers
|