-- Hoogle documentation, generated by Haddock -- See Hoogle, http://www.haskell.org/hoogle/ -- | Automated Mutation Testing -- -- This package defines a mutation analysis library for haskell programs. -- It does this by parsing the haskell source, and replacing a few of the -- common haskell functions and operators with other, but similar -- operators and functions, and running the testsuite to check whether -- the difference has been detected. Currently, it supports QuickCheck, -- HUnit and Hspec tests. @package MuCheck @version 0.1.2.2 module MuCheck.Utils.Common -- | The choose function generates subsets of a given size choose :: [a] -> Int -> [[a]] -- | The coupling function produces all possible pairings, and -- applies the given function to each coupling :: Eq a => (a -> a -> t) -> [a] -> [t] -- | The genFileNames function lazily generates filenames of mutants genFileNames :: String -> [String] -- | The replace function replaces first element in a list given old -- and new values as a pair replace :: Eq a => (a, a) -> [a] -> [a] -- | The safeHead function safely extracts head of a list using -- Maybe safeHead :: [a] -> Maybe a -- | The sample function takes a random generator and chooses a -- random sample subset of given size. sample :: (RandomGen g, Num n, Eq n) => g -> n -> [t] -> [t] -- | The sampleF function takes a random generator, and a fraction -- and returns subset of size given by fraction sampleF :: (RandomGen g, Num n) => g -> Rational -> [t] -> [t] -- | The remElt function removes element at index specified from a -- list remElt :: Int -> [a] -> [a] module MuCheck.Run.Common type InterpreterOutput a = Either InterpreterError (String, a) data TSum TSum :: Int -> Int -> Int -> Int -> Int -> String -> TSum tsum_numMutants :: TSum -> Int tsum_loadError :: TSum -> Int tsum_notKilled :: TSum -> Int tsum_killed :: TSum -> Int tsum_others :: TSum -> Int tsum_log :: TSum -> String type MutantFilename = String class Typeable s => Summarizable s testSummary :: Summarizable s => [MutantFilename] -> [InterpreterOutput s] -> TSum isSuccess :: Summarizable s => s -> Bool module MuCheck.Utils.Print -- | simple wrapper for adding a % at the end. (./.) :: (Show a, Integral a) => a -> a -> [Char] -- | join lines together showAS :: [String] -> String -- | make lists into lines in text. showA :: Show a => [a] -> String module MuCheck.Run.QuickCheck instance Typeable Result instance Summarizable Result module MuCheck.Run.HUnit instance Typeable Counts instance Summarizable Counts module MuCheck.Run.Hspec instance Typeable Summary instance Summarizable Summary module MuCheck.Interpreter -- | run quickcheck test suite on mutants >>> numMutants -- <- genMutants "qsort" "Examples/QuickCheckTest.hs" >>> -- checkQuickCheckOnMutants (take numMutants $ genFileNames -- -- "ExamplesQuickCheckTest.hs") Examples.QuickCheckTest -- ["quickCheckResult idEmpProp", "quickCheckResult revProp", -- "quickCheckResult modelProp"] ".quickcheck.log" checkQuickCheckOnMutants :: [String] -> String -> [String] -> String -> IO [Result] -- | run hunit test suite on mutants >>> numMutants <- -- genMutants "qsort" "Examples/HUnitTest.hs" >>> -- checkHUnitOnMutants (take numMutants $ genFileNames -- "ExamplesHUnitTest.hs") Examples.HUnitTest ["runTestTT -- tests"] ".hunit.log" checkHUnitOnMutants :: [String] -> String -> [String] -> String -> IO [Counts] -- | run hspec test suite on mutants >>> numMutants <- -- genMutants "qsort" "Examples/HspecTest.hs" >>> -- checkHspecOnMutants (take numMutants $ genFileNames -- "ExamplesHspecTest.hs") Examples.HspecTest ["spec (with -- "qsort1")"] ".hspec.log" checkHspecOnMutants :: [String] -> String -> [String] -> String -> IO [Summary] -- | Given the list of tests suites to check, run one test suite at a time -- on all mutants. mutantCheckSummary :: (Summarizable a, Show a) => [String] -> String -> [String] -> FilePath -> IO [a] -- | Run one test suite on all mutants >>> t = runInterpreter -- (evalMethod "Examples/QuickCheckTest.hs" -- Examples.QuickCheckTest "quickCheckResult idEmp") runCodeOnMutants :: Typeable * t => [[Char]] -> [Char] -> [Char] -> IO [Either InterpreterError (String, t)] -- | Given the filename, modulename, test to evaluate, evaluate, and return -- result as a pair. evalMethod :: (MonadInterpreter m, Typeable t) => String -> String -> String -> m (String, t) -- | Datatype to hold results of the entire run data TSSum TSSum :: Int -> Int -> Int -> String -> TSSum tssum_numMutants :: TSSum -> Int tssum_alive :: TSSum -> Int tssum_errors :: TSSum -> Int tssum_log :: TSSum -> String -- | Summarize the entire run multipleCheckSummary :: (Show b1, Show b, Ord b1) => ((b1, b) -> Bool) -> [[Either a (b1, b)]] -> TSSum module MuCheck.MuOp data MuOp (==>*) :: Mutable a => a -> [a] -> [MuOp] (*==>*) :: Mutable a => [a] -> [a] -> [MuOp] (~~>) :: (MonadPlus m, Eq a) => a -> a -> (a -> m a) mkMp' :: (MonadPlus m, Typeable * a) => MuOp -> a -> m a class Mutable a (==>) :: Mutable a => a -> a -> MuOp instance Mutable GuardedRhs instance Mutable Literal instance Mutable Decl instance Mutable Exp instance Mutable QOp instance Mutable QName instance Mutable Name instance Show MuOp module MuCheck.Operators -- | comparison operators comparators :: [MuOp] -- | predicates predNums :: [MuOp] -- | binary arithmetic binAriths :: [MuOp] -- | arithmetic on lists arithLists :: [MuOp] -- | all available operators allOps :: [MuOp] module MuCheck.Config data GenerationMode FirstOrderOnly :: GenerationMode FirstAndHigherOrder :: GenerationMode data Config Config :: [MuOp] -> Rational -> Rational -> Rational -> Rational -> Int -> GenerationMode -> Config muOps :: Config -> [MuOp] doMutatePatternMatches :: Config -> Rational doMutateValues :: Config -> Rational doNegateIfElse :: Config -> Rational doNegateGuards :: Config -> Rational maxNumMutants :: Config -> Int genMode :: Config -> GenerationMode defaultConfig :: Config instance Eq GenerationMode instance Show GenerationMode instance Show Config -- | SYB functions module MuCheck.Utils.Syb -- | select all code components satisfying a certain predicate selectMany :: (Data a, Typeable b) => (b -> Bool) -> a -> [b] -- | special case of selectMany, which selects the first components -- satisfying a predicate selectOne :: (Typeable a, Data a1) => (a -> Bool) -> a1 -> Maybe a -- | selecting all relevant ops relevantOps :: (Data a, Eq a) => a -> [MuOp] -> [MuOp] -- | apply a mutating function on a piece of code one at a time once :: MonadPlus m => GenericM m -> GenericM m once' :: (forall a. Data a => a -> Maybe a) -> (forall a. Data a => a -> a) module MuCheck.Mutation -- | The genMutants function is a wrapper to genMutantsWith with -- standard configuraton genMutants :: String -> FilePath -> IO Int -- | The genMutantsWith function takes configuration function to -- mutate, filename the function is defined in, and produces mutants in -- the same directory as the filename, and returns the number of mutants -- produced. genMutantsWith :: Config -> String -> FilePath -> IO Int -- | Mutating a function's code using a bunch of mutation operators (In all -- the three mutate functions, we assume working with functions -- declaration.) mutates :: [MuOp] -> Decl -> [Decl] mutatesN :: [MuOp] -> Decl -> Int -> [Decl] -- | Given a function, generate all mutants after applying applying op once -- (op might be applied at different places).E.g.: op = "== ">" -- and there are two instances of "<" mutate :: MuOp -> Decl -> [Decl] isFunctionD :: String -> Decl -> Bool -- | Generate all operators for permutating pattern matches in a function. -- We don't deal with permutating guards and case for now. permMatches :: Decl -> [MuOp] removeOnePMatch :: Decl -> [MuOp] removeOneElem :: Eq t => [t] -> [[t]] -- | Parse a module. Input is the content of the file parseModuleFromFile :: String -> Module getDecls :: Module -> [Decl] putDecls :: Module -> [Decl] -> Module selectValOps :: (Data a, Eq a, Typeable b, Mutable b, Eq b) => (b -> Bool) -> [b -> b] -> a -> [MuOp] selectValOps' :: (Data a, Eq a, Typeable b, Mutable b) => (b -> Bool) -> (b -> [b]) -> a -> [MuOp] selectIntOps :: (Data a, Eq a) => a -> [MuOp] -- | negating boolean in if/else statements selectIfElseBoolNegOps :: (Data a, Eq a) => a -> [MuOp] -- | negating boolean in Guards selectGuardedBoolNegOps :: (Data a, Eq a) => a -> [MuOp]