    -- | This module allows to use SmallCheck properties in tasty.
    {-# LANGUAGE MultiParamTypeClasses, FlexibleInstances, FlexibleContexts,
                 TypeOperators, DeriveDataTypeable, TypeFamilies,
                 GeneralizedNewtypeDeriving #-}
    module Test.Tasty.SmallCheck
      ( testProperty
      , SmallCheckDepth(..)
      , module Test.SmallCheck
      ) where

    import Test.Tasty.Providers
    import Test.Tasty.Options
    import qualified Test.SmallCheck as SC
    import Test.SmallCheck hiding (smallCheck) -- for re-export
    import Test.SmallCheck.Drivers as SC
    import Control.Exception
    import Control.Monad (when)
    import Data.Typeable
    import Data.IORef
    import Options.Applicative (metavar)
    import Text.Printf

    -- | Create a 'Test' for a SmallCheck 'SC.Testable' property
    testProperty :: SC.Testable IO a => TestName -> a -> TestTree
    testProperty :: forall a. Testable IO a => TestName -> a -> TestTree
    testProperty TestName
    name a
    prop = TestName -> Property IO -> TestTree
    forall t. IsTest t => TestName -> t -> TestTree
    singleTest TestName
    name (Property IO -> TestTree) -> Property IO -> TestTree
    forall a b. (a -> b) -> a -> b
    $ (a -> Property IO
    forall (m :: * -> *) a. Testable m a => a -> Property m
    SC.test a
    prop :: SC.Property IO)

    -- | The \"depth\" parameter for SmallCheck
    newtype SmallCheckDepth = SmallCheckDepth Int
      deriving (Integer -> SmallCheckDepth
    SmallCheckDepth -> SmallCheckDepth
    SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth)
    -> (Integer -> SmallCheckDepth)
    -> Num SmallCheckDepth
    forall a.
    (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a)
    -> (a -> a)
    -> (a -> a)
    -> (Integer -> a)
    -> Num a
    $c+ :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    + :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $c- :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    - :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $c* :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    * :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $cnegate :: SmallCheckDepth -> SmallCheckDepth
    negate :: SmallCheckDepth -> SmallCheckDepth
    $cabs :: SmallCheckDepth -> SmallCheckDepth
    abs :: SmallCheckDepth -> SmallCheckDepth
    $csignum :: SmallCheckDepth -> SmallCheckDepth
    signum :: SmallCheckDepth -> SmallCheckDepth
    $cfromInteger :: Integer -> SmallCheckDepth
    fromInteger :: Integer -> SmallCheckDepth
    Num, Eq SmallCheckDepth
    Eq SmallCheckDepth =>
    (SmallCheckDepth -> SmallCheckDepth -> Ordering)
    -> (SmallCheckDepth -> SmallCheckDepth -> Bool)
    -> (SmallCheckDepth -> SmallCheckDepth -> Bool)
    -> (SmallCheckDepth -> SmallCheckDepth -> Bool)
    -> (SmallCheckDepth -> SmallCheckDepth -> Bool)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> Ord SmallCheckDepth
    SmallCheckDepth -> SmallCheckDepth -> Bool
    SmallCheckDepth -> SmallCheckDepth -> Ordering
    SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: SmallCheckDepth -> SmallCheckDepth -> Ordering
    compare :: SmallCheckDepth -> SmallCheckDepth -> Ordering
    $c< :: SmallCheckDepth -> SmallCheckDepth -> Bool
    < :: SmallCheckDepth -> SmallCheckDepth -> Bool
    $c<= :: SmallCheckDepth -> SmallCheckDepth -> Bool
    <= :: SmallCheckDepth -> SmallCheckDepth -> Bool
    $c> :: SmallCheckDepth -> SmallCheckDepth -> Bool
    > :: SmallCheckDepth -> SmallCheckDepth -> Bool
    $c>= :: SmallCheckDepth -> SmallCheckDepth -> Bool
    >= :: SmallCheckDepth -> SmallCheckDepth -> Bool
    $cmax :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    max :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $cmin :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    min :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    Ord, SmallCheckDepth -> SmallCheckDepth -> Bool
    (SmallCheckDepth -> SmallCheckDepth -> Bool)
    -> (SmallCheckDepth -> SmallCheckDepth -> Bool)
    -> Eq SmallCheckDepth
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: SmallCheckDepth -> SmallCheckDepth -> Bool
    == :: SmallCheckDepth -> SmallCheckDepth -> Bool
    $c/= :: SmallCheckDepth -> SmallCheckDepth -> Bool
    /= :: SmallCheckDepth -> SmallCheckDepth -> Bool
    Eq, Num SmallCheckDepth
    Ord SmallCheckDepth
    (Num SmallCheckDepth, Ord SmallCheckDepth) =>
    (SmallCheckDepth -> Rational) -> Real SmallCheckDepth
    SmallCheckDepth -> Rational
    forall a. (Num a, Ord a) => (a -> Rational) -> Real a
    $ctoRational :: SmallCheckDepth -> Rational
    toRational :: SmallCheckDepth -> Rational
    Real, Int -> SmallCheckDepth
    SmallCheckDepth -> Int
    SmallCheckDepth -> [SmallCheckDepth]
    SmallCheckDepth -> SmallCheckDepth
    SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    SmallCheckDepth
    -> SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    (SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth)
    -> (Int -> SmallCheckDepth)
    -> (SmallCheckDepth -> Int)
    -> (SmallCheckDepth -> [SmallCheckDepth])
    -> (SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth])
    -> (SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth])
    -> (SmallCheckDepth
        -> SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth])
    -> Enum SmallCheckDepth
    forall a.
    (a -> a)
    -> (a -> a)
    -> (Int -> a)
    -> (a -> Int)
    -> (a -> [a])
    -> (a -> a -> [a])
    -> (a -> a -> [a])
    -> (a -> a -> a -> [a])
    -> Enum a
    $csucc :: SmallCheckDepth -> SmallCheckDepth
    succ :: SmallCheckDepth -> SmallCheckDepth
    $cpred :: SmallCheckDepth -> SmallCheckDepth
    pred :: SmallCheckDepth -> SmallCheckDepth
    $ctoEnum :: Int -> SmallCheckDepth
    toEnum :: Int -> SmallCheckDepth
    $cfromEnum :: SmallCheckDepth -> Int
    fromEnum :: SmallCheckDepth -> Int
    $cenumFrom :: SmallCheckDepth -> [SmallCheckDepth]
    enumFrom :: SmallCheckDepth -> [SmallCheckDepth]
    $cenumFromThen :: SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    enumFromThen :: SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    $cenumFromTo :: SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    enumFromTo :: SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    $cenumFromThenTo :: SmallCheckDepth
    -> SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    enumFromThenTo :: SmallCheckDepth
    -> SmallCheckDepth -> SmallCheckDepth -> [SmallCheckDepth]
    Enum, Enum SmallCheckDepth
    Real SmallCheckDepth
    (Real SmallCheckDepth, Enum SmallCheckDepth) =>
    (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth)
    -> (SmallCheckDepth
        -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth))
    -> (SmallCheckDepth
        -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth))
    -> (SmallCheckDepth -> Integer)
    -> Integral SmallCheckDepth
    SmallCheckDepth -> Integer
    SmallCheckDepth
    -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth)
    SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    forall a.
    (Real a, Enum a) =>
    (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> (a, a))
    -> (a -> a -> (a, a))
    -> (a -> Integer)
    -> Integral a
    $cquot :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    quot :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $crem :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    rem :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $cdiv :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    div :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $cmod :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    mod :: SmallCheckDepth -> SmallCheckDepth -> SmallCheckDepth
    $cquotRem :: SmallCheckDepth
    -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth)
    quotRem :: SmallCheckDepth
    -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth)
    $cdivMod :: SmallCheckDepth
    -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth)
    divMod :: SmallCheckDepth
    -> SmallCheckDepth -> (SmallCheckDepth, SmallCheckDepth)
    $ctoInteger :: SmallCheckDepth -> Integer
    toInteger :: SmallCheckDepth -> Integer
    Integral, Typeable)

    instance IsOption SmallCheckDepth where
      defaultValue :: SmallCheckDepth
    defaultValue = SmallCheckDepth
    5
      parseValue :: TestName -> Maybe SmallCheckDepth
    parseValue = (Int -> SmallCheckDepth) -> Maybe Int -> Maybe SmallCheckDepth
    forall a b. (a -> b) -> Maybe a -> Maybe b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    fmap Int -> SmallCheckDepth
    SmallCheckDepth (Maybe Int -> Maybe SmallCheckDepth)
    -> (TestName -> Maybe Int) -> TestName -> Maybe SmallCheckDepth
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . TestName -> Maybe Int
    forall a. Read a => TestName -> Maybe a
    safeRead
      optionName :: Tagged SmallCheckDepth TestName
    optionName = TestName -> Tagged SmallCheckDepth TestName
    forall a. a -> Tagged SmallCheckDepth a
    forall (m :: * -> *) a. Monad m => a -> m a
    return TestName
    "smallcheck-depth"
      optionHelp :: Tagged SmallCheckDepth TestName
    optionHelp = TestName -> Tagged SmallCheckDepth TestName
    forall a. a -> Tagged SmallCheckDepth a
    forall (m :: * -> *) a. Monad m => a -> m a
    return TestName
    "Depth to use for smallcheck tests"
      optionCLParser :: Parser SmallCheckDepth
    optionCLParser = Mod OptionFields SmallCheckDepth -> Parser SmallCheckDepth
    forall v. IsOption v => Mod OptionFields v -> Parser v
    mkOptionCLParser (Mod OptionFields SmallCheckDepth -> Parser SmallCheckDepth)
    -> Mod OptionFields SmallCheckDepth -> Parser SmallCheckDepth
    forall a b. (a -> b) -> a -> b
    $ TestName -> Mod OptionFields SmallCheckDepth
    forall (f :: * -> *) a. HasMetavar f => TestName -> Mod f a
    metavar TestName
    "NUMBER"

    -- | The maximum number of test cases to generate. Can be used as an
    -- alternative to setting 'SmallCheckDepth'.
    newtype SmallCheckMaxCount = SmallCheckMaxCount Int
      deriving (Integer -> SmallCheckMaxCount
    SmallCheckMaxCount -> SmallCheckMaxCount
    SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (Integer -> SmallCheckMaxCount)
    -> Num SmallCheckMaxCount
    forall a.
    (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a)
    -> (a -> a)
    -> (a -> a)
    -> (Integer -> a)
    -> Num a
    $c+ :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    + :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $c- :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    - :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $c* :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    * :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $cnegate :: SmallCheckMaxCount -> SmallCheckMaxCount
    negate :: SmallCheckMaxCount -> SmallCheckMaxCount
    $cabs :: SmallCheckMaxCount -> SmallCheckMaxCount
    abs :: SmallCheckMaxCount -> SmallCheckMaxCount
    $csignum :: SmallCheckMaxCount -> SmallCheckMaxCount
    signum :: SmallCheckMaxCount -> SmallCheckMaxCount
    $cfromInteger :: Integer -> SmallCheckMaxCount
    fromInteger :: Integer -> SmallCheckMaxCount
    Num, Eq SmallCheckMaxCount
    Eq SmallCheckMaxCount =>
    (SmallCheckMaxCount -> SmallCheckMaxCount -> Ordering)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> Bool)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> Bool)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> Bool)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> Bool)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> Ord SmallCheckMaxCount
    SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    SmallCheckMaxCount -> SmallCheckMaxCount -> Ordering
    SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: SmallCheckMaxCount -> SmallCheckMaxCount -> Ordering
    compare :: SmallCheckMaxCount -> SmallCheckMaxCount -> Ordering
    $c< :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    < :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    $c<= :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    <= :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    $c> :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    > :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    $c>= :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    >= :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    $cmax :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    max :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $cmin :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    min :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    Ord, SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    (SmallCheckMaxCount -> SmallCheckMaxCount -> Bool)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> Bool)
    -> Eq SmallCheckMaxCount
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    == :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    $c/= :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    /= :: SmallCheckMaxCount -> SmallCheckMaxCount -> Bool
    Eq, Num SmallCheckMaxCount
    Ord SmallCheckMaxCount
    (Num SmallCheckMaxCount, Ord SmallCheckMaxCount) =>
    (SmallCheckMaxCount -> Rational) -> Real SmallCheckMaxCount
    SmallCheckMaxCount -> Rational
    forall a. (Num a, Ord a) => (a -> Rational) -> Real a
    $ctoRational :: SmallCheckMaxCount -> Rational
    toRational :: SmallCheckMaxCount -> Rational
    Real, Int -> SmallCheckMaxCount
    SmallCheckMaxCount -> Int
    SmallCheckMaxCount -> [SmallCheckMaxCount]
    SmallCheckMaxCount -> SmallCheckMaxCount
    SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    SmallCheckMaxCount
    -> SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    (SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (Int -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> Int)
    -> (SmallCheckMaxCount -> [SmallCheckMaxCount])
    -> (SmallCheckMaxCount
        -> SmallCheckMaxCount -> [SmallCheckMaxCount])
    -> (SmallCheckMaxCount
        -> SmallCheckMaxCount -> [SmallCheckMaxCount])
    -> (SmallCheckMaxCount
        -> SmallCheckMaxCount
        -> SmallCheckMaxCount
        -> [SmallCheckMaxCount])
    -> Enum SmallCheckMaxCount
    forall a.
    (a -> a)
    -> (a -> a)
    -> (Int -> a)
    -> (a -> Int)
    -> (a -> [a])
    -> (a -> a -> [a])
    -> (a -> a -> [a])
    -> (a -> a -> a -> [a])
    -> Enum a
    $csucc :: SmallCheckMaxCount -> SmallCheckMaxCount
    succ :: SmallCheckMaxCount -> SmallCheckMaxCount
    $cpred :: SmallCheckMaxCount -> SmallCheckMaxCount
    pred :: SmallCheckMaxCount -> SmallCheckMaxCount
    $ctoEnum :: Int -> SmallCheckMaxCount
    toEnum :: Int -> SmallCheckMaxCount
    $cfromEnum :: SmallCheckMaxCount -> Int
    fromEnum :: SmallCheckMaxCount -> Int
    $cenumFrom :: SmallCheckMaxCount -> [SmallCheckMaxCount]
    enumFrom :: SmallCheckMaxCount -> [SmallCheckMaxCount]
    $cenumFromThen :: SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    enumFromThen :: SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    $cenumFromTo :: SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    enumFromTo :: SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    $cenumFromThenTo :: SmallCheckMaxCount
    -> SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    enumFromThenTo :: SmallCheckMaxCount
    -> SmallCheckMaxCount -> SmallCheckMaxCount -> [SmallCheckMaxCount]
    Enum, Enum SmallCheckMaxCount
    Real SmallCheckMaxCount
    (Real SmallCheckMaxCount, Enum SmallCheckMaxCount) =>
    (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount)
    -> (SmallCheckMaxCount
        -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount))
    -> (SmallCheckMaxCount
        -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount))
    -> (SmallCheckMaxCount -> Integer)
    -> Integral SmallCheckMaxCount
    SmallCheckMaxCount -> Integer
    SmallCheckMaxCount
    -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount)
    SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    forall a.
    (Real a, Enum a) =>
    (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> (a -> a -> (a, a))
    -> (a -> a -> (a, a))
    -> (a -> Integer)
    -> Integral a
    $cquot :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    quot :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $crem :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    rem :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $cdiv :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    div :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $cmod :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    mod :: SmallCheckMaxCount -> SmallCheckMaxCount -> SmallCheckMaxCount
    $cquotRem :: SmallCheckMaxCount
    -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount)
    quotRem :: SmallCheckMaxCount
    -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount)
    $cdivMod :: SmallCheckMaxCount
    -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount)
    divMod :: SmallCheckMaxCount
    -> SmallCheckMaxCount -> (SmallCheckMaxCount, SmallCheckMaxCount)
    $ctoInteger :: SmallCheckMaxCount -> Integer
    toInteger :: SmallCheckMaxCount -> Integer
    Integral, Typeable)

    instance IsOption SmallCheckMaxCount where
      defaultValue :: SmallCheckMaxCount
    defaultValue = Int -> SmallCheckMaxCount
    SmallCheckMaxCount Int
    forall a. Bounded a => a
    maxBound -- disable by default
      parseValue :: TestName -> Maybe SmallCheckMaxCount
    parseValue = (Int -> SmallCheckMaxCount)
    -> Maybe Int -> Maybe SmallCheckMaxCount
    forall a b. (a -> b) -> Maybe a -> Maybe b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    fmap Int -> SmallCheckMaxCount
    SmallCheckMaxCount (Maybe Int -> Maybe SmallCheckMaxCount)
    -> (TestName -> Maybe Int) -> TestName -> Maybe SmallCheckMaxCount
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . TestName -> Maybe Int
    forall a. Read a => TestName -> Maybe a
    safeRead
      optionName :: Tagged SmallCheckMaxCount TestName
    optionName = TestName -> Tagged SmallCheckMaxCount TestName
    forall a. a -> Tagged SmallCheckMaxCount a
    forall (m :: * -> *) a. Monad m => a -> m a
    return TestName
    "smallcheck-max-count"
      optionHelp :: Tagged SmallCheckMaxCount TestName
    optionHelp = TestName -> Tagged SmallCheckMaxCount TestName
    forall a. a -> Tagged SmallCheckMaxCount a
    forall (m :: * -> *) a. Monad m => a -> m a
    return TestName
    "Maximum smallcheck test count"
      optionCLParser :: Parser SmallCheckMaxCount
    optionCLParser = Mod OptionFields SmallCheckMaxCount -> Parser SmallCheckMaxCount
    forall v. IsOption v => Mod OptionFields v -> Parser v
    mkOptionCLParser (Mod OptionFields SmallCheckMaxCount -> Parser SmallCheckMaxCount)
    -> Mod OptionFields SmallCheckMaxCount -> Parser SmallCheckMaxCount
    forall a b. (a -> b) -> a -> b
    $ TestName -> Mod OptionFields SmallCheckMaxCount
    forall (f :: * -> *) a. HasMetavar f => TestName -> Mod f a
    metavar TestName
    "NUMBER"

    instance IsTest (SC.Property IO) where
      testOptions :: Tagged (Property IO) [OptionDescription]
    testOptions = [OptionDescription] -> Tagged (Property IO) [OptionDescription]
    forall a. a -> Tagged (Property IO) a
    forall (m :: * -> *) a. Monad m => a -> m a
    return
        [ Proxy SmallCheckDepth -> OptionDescription
    forall v. IsOption v => Proxy v -> OptionDescription
    Option (Proxy SmallCheckDepth
    forall {k} (t :: k). Proxy t
    Proxy :: Proxy SmallCheckDepth)
        , Proxy SmallCheckMaxCount -> OptionDescription
    forall v. IsOption v => Proxy v -> OptionDescription
    Option (Proxy SmallCheckMaxCount
    forall {k} (t :: k). Proxy t
    Proxy :: Proxy SmallCheckMaxCount)
        ]

      run :: OptionSet -> Property IO -> (Progress -> IO ()) -> IO Result
    run OptionSet
    opts Property IO
    prop Progress -> IO ()
    yieldProgress = do
        let
          SmallCheckDepth Int
    depth = OptionSet -> SmallCheckDepth
    forall v. IsOption v => OptionSet -> v
    lookupOption OptionSet
    opts
          SmallCheckMaxCount Int
    maxCount = OptionSet -> SmallCheckMaxCount
    forall v. IsOption v => OptionSet -> v
    lookupOption OptionSet
    opts

        counter <- (Int, Int) -> IO (IORef (Int, Int))
    forall a. a -> IO (IORef a)
    newIORef (Int
    0 :: Int, Int
    0 :: Int)

        let
          hook TestQuality
    quality = do
            let
              inc :: (Int, Int) -> (Int, Int)
    inc (Int
    total, Int
    bad) =
                case TestQuality
    quality of
                  TestQuality
    GoodTest -> ((,) (Int -> Int -> (Int, Int)) -> Int -> Int -> (Int, Int)
    forall a b. (a -> b) -> a -> b
    $! Int
    total Int -> Int -> Int
    forall a. Num a => a -> a -> a
    + Int
    1) Int
    bad
                  TestQuality
    BadTest -> ((,) (Int -> Int -> (Int, Int)) -> Int -> Int -> (Int, Int)
    forall a b. (a -> b) -> a -> b
    $! Int
    total Int -> Int -> Int
    forall a. Num a => a -> a -> a
    + Int
    1) (Int -> (Int, Int)) -> Int -> (Int, Int)
    forall a b. (a -> b) -> a -> b
    $! Int
    bad Int -> Int -> Int
    forall a. Num a => a -> a -> a
    + Int
    1

            count <- IORef (Int, Int) -> ((Int, Int) -> ((Int, Int), Int)) -> IO Int
    forall a b. IORef a -> (a -> (a, b)) -> IO b
    myAtomicModifyIORef' IORef (Int, Int)
    counter (\(Int, Int)
    c -> let c' :: (Int, Int)
    c' = (Int, Int) -> (Int, Int)
    inc (Int, Int)
    c in ((Int, Int)
    c', (Int, Int) -> Int
    forall a b. (a, b) -> a
    fst (Int, Int)
    c'))

            when (count >= maxCount) $ throwIO Finish

            -- submit progress data to tasty
            yieldProgress $ Progress
              { progressText = show count
              , progressPercent = 0 -- we don't know the total number of tests
              }

        -- small check does not catch exceptions on its own, so lets do it
        scResult <- try $ smallCheckWithHook depth hook prop

        (total, bad) <- readIORef counter
        let
          desc
            | Int
    bad Int -> Int -> Bool
    forall a. Eq a => a -> a -> Bool
    == Int
    0
              = TestName -> Int -> TestName
    forall r. PrintfType r => TestName -> r
    printf TestName
    "%d tests completed" Int
    total
            | Bool
    otherwise
              = TestName -> Int -> Int -> TestName
    forall r. PrintfType r => TestName -> r
    printf TestName
    "%d tests completed (but %d did not meet the condition)" Int
    total Int
    bad

        return $
          case scResult of
            Left SomeException
    e
              | Just Finish
    Finish <- SomeException -> Maybe Finish
    forall e. Exception e => SomeException -> Maybe e
    fromException SomeException
    e
                           -> TestName -> Result
    testPassed TestName
    desc
              | Bool
    otherwise  -> TestName -> Result
    testFailed (TestName -> Result) -> TestName -> Result
    forall a b. (a -> b) -> a -> b
    $ SomeException -> TestName
    forall a. Show a => a -> TestName
    show SomeException
    e
            Right Maybe PropertyFailure
    Nothing  -> TestName -> Result
    testPassed TestName
    desc
            Right (Just PropertyFailure
    f) -> TestName -> Result
    testFailed (TestName -> Result) -> TestName -> Result
    forall a b. (a -> b) -> a -> b
    $ PropertyFailure -> TestName
    ppFailure PropertyFailure
    f

    data Finish = Finish
      deriving (Finish -> Finish -> Bool
    (Finish -> Finish -> Bool)
    -> (Finish -> Finish -> Bool) -> Eq Finish
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: Finish -> Finish -> Bool
    == :: Finish -> Finish -> Bool
    $c/= :: Finish -> Finish -> Bool
    /= :: Finish -> Finish -> Bool
    Eq, Int -> Finish -> ShowS
    [Finish] -> ShowS
    Finish -> TestName
    (Int -> Finish -> ShowS)
    -> (Finish -> TestName) -> ([Finish] -> ShowS) -> Show Finish
    forall a.
    (Int -> a -> ShowS) -> (a -> TestName) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> Finish -> ShowS
    showsPrec :: Int -> Finish -> ShowS
    $cshow :: Finish -> TestName
    show :: Finish -> TestName
    $cshowList :: [Finish] -> ShowS
    showList :: [Finish] -> ShowS
    Show)

    instance Exception Finish

    -- Copied from base to stay compatible with GHC 7.4.
    myAtomicModifyIORef' :: IORef a -> (a -> (a,b)) -> IO b
    myAtomicModifyIORef' :: forall a b. IORef a -> (a -> (a, b)) -> IO b
    myAtomicModifyIORef' IORef a
    ref a -> (a, b)
    f = do
        b <- IORef a -> (a -> (a, b)) -> IO b
    forall a b. IORef a -> (a -> (a, b)) -> IO b
    atomicModifyIORef IORef a
    ref
                (\a
    x -> let (a
    a, b
    b) = a -> (a, b)
    f a
    x
                        in (a
    a, a
    a a -> b -> b
    forall a b. a -> b -> b
    `seq` b
    b))
        b `seq` return b