diff --git a/driver/Main.hs b/driver/Main.hs
--- a/driver/Main.hs
+++ b/driver/Main.hs
@@ -1,59 +1,6 @@
 module Main (main) where
 
-import           Prelude ()
-import           Prelude.Compat
-
-import           Control.DeepSeq
-import           Control.Exception
-import           Control.Monad.Compat
-import           Data.List.Compat
-import           Data.Version (showVersion)
-import           System.Environment
-import           System.Exit
-import           System.IO
-import           System.IO.Error
-
-import           Paths_hpack (version)
-import           Hpack.Config
-import           Hpack.Run
-
-programVersion :: String
-programVersion = "hpack version " ++ showVersion version
-
-header :: String
-header = unlines [
-    "-- This file has been generated from " ++ packageConfig ++ " by " ++ programVersion ++ "."
-  , "--"
-  , "-- see: https://github.com/sol/hpack"
-  , ""
-  ]
+import qualified Hpack
 
 main :: IO ()
-main = do
-  args <- getArgs
-  case args of
-    ["--version"] -> putStrLn programVersion
-    ["--silent"] -> hpack False
-    [] -> hpack True
-    _ -> do
-      hPutStrLn stderr "Usage: hpack [ --version | --silent ]"
-      exitFailure
-
-hpack :: Bool -> IO ()
-hpack verbose = do
-  (warnings, name, new) <- run
-  forM_ warnings $ \warning -> hPutStrLn stderr ("WARNING: " ++ warning)
-  old <- force . either (const Nothing) (Just . stripHeader) <$> tryJust (guard . isDoesNotExistError) (readFile name)
-  if (old == Just (lines new)) then do
-    output (name ++ " is up-to-date")
-  else do
-    (writeFile name $ header ++ new)
-    output ("generated " ++ name)
-  where
-    stripHeader :: String -> [String]
-    stripHeader = dropWhile null . dropWhile ("--" `isPrefixOf`) . lines
-
-    output :: String -> IO ()
-    output message
-      | verbose = putStrLn message
-      | otherwise = return ()
+main = Hpack.main
diff --git a/hpack.cabal b/hpack.cabal
--- a/hpack.cabal
+++ b/hpack.cabal
@@ -1,9 +1,9 @@
--- This file has been generated from package.yaml by hpack version 0.5.4.
+-- This file has been generated from package.yaml by hpack version 0.8.0.
 --
 -- see: https://github.com/sol/hpack
 
 name:           hpack
-version:        0.8.0
+version:        0.9.0
 synopsis:       An alternative format for Haskell packages
 category:       Development
 homepage:       https://github.com/sol/hpack#readme
@@ -23,8 +23,7 @@
       src
   ghc-options: -Wall
   build-depends:
-      aeson >= 0.8
-    , base >= 4.7 && < 5
+      base >= 4.7 && < 5
     , base-compat >= 0.8
     , deepseq
     , directory
@@ -33,7 +32,9 @@
     , text
     , unordered-containers
     , yaml
+    , aeson >= 0.8
   exposed-modules:
+      Hpack
       Hpack.Config
       Hpack.Run
       Hpack.Yaml
@@ -42,6 +43,7 @@
       Hpack.Haskell
       Hpack.Render
       Hpack.Util
+      Paths_hpack
   default-language: Haskell2010
 
 executable hpack
@@ -50,8 +52,7 @@
       driver
   ghc-options: -Wall
   build-depends:
-      aeson >= 0.8
-    , base >= 4.7 && < 5
+      base >= 4.7 && < 5
     , base-compat >= 0.8
     , deepseq
     , directory
@@ -61,6 +62,7 @@
     , unordered-containers
     , yaml
     , hpack
+    , aeson >= 0.8
   default-language: Haskell2010
 
 test-suite spec
@@ -72,8 +74,7 @@
   ghc-options: -Wall
   cpp-options: -DTEST
   build-depends:
-      aeson >= 0.8
-    , base >= 4.7 && < 5
+      base >= 4.7 && < 5
     , base-compat >= 0.8
     , deepseq
     , directory
@@ -83,9 +84,11 @@
     , unordered-containers
     , yaml
     , hspec == 2.*
+    , temporary
     , mockery >= 0.3
     , interpolate
     , aeson-qq
+    , aeson >= 0.10
   other-modules:
       Helper
       Hpack.ConfigSpec
@@ -94,6 +97,8 @@
       Hpack.RenderSpec
       Hpack.RunSpec
       Hpack.UtilSpec
+      HpackSpec
+      Hpack
       Hpack.Config
       Hpack.GenericsUtil
       Hpack.Haskell
diff --git a/src/Hpack.hs b/src/Hpack.hs
new file mode 100644
--- /dev/null
+++ b/src/Hpack.hs
@@ -0,0 +1,78 @@
+{-# LANGUAGE CPP #-}
+module Hpack (
+  hpack
+, version
+, main
+#ifdef TEST
+, parseVerbosity
+#endif
+) where
+
+import           Prelude ()
+import           Prelude.Compat
+
+import           Control.DeepSeq
+import           Control.Exception
+import           Control.Monad.Compat
+import           Data.List.Compat
+import           Data.Version (showVersion)
+import           System.Environment
+import           System.Exit
+import           System.IO
+import           System.IO.Error
+
+import           Paths_hpack (version)
+import           Hpack.Config
+import           Hpack.Run
+
+programVersion :: String
+programVersion = "hpack version " ++ showVersion version
+
+header :: String
+header = unlines [
+    "-- This file has been generated from " ++ packageConfig ++ " by " ++ programVersion ++ "."
+  , "--"
+  , "-- see: https://github.com/sol/hpack"
+  , ""
+  ]
+
+main :: IO ()
+main = do
+  args <- getArgs
+  case args of
+    ["--version"] -> putStrLn programVersion
+    _ -> case parseVerbosity args of
+      (verbose, [dir]) -> hpack dir verbose
+      (verbose, []) -> hpack "." verbose
+      _ -> do
+        hPutStrLn stderr $ unlines [
+            "Usage: hpack [ --silent ] [ dir ]"
+          , "       hpack --version"
+          ]
+        exitFailure
+
+parseVerbosity :: [String] -> (Bool, [String])
+parseVerbosity xs = (verbose, ys)
+  where
+    silentFlag = "--silent"
+    verbose = not (silentFlag `elem` xs)
+    ys = filter (/= silentFlag) xs
+
+hpack :: FilePath -> Bool -> IO ()
+hpack dir verbose = do
+  (warnings, name, new) <- run dir
+  forM_ warnings $ \warning -> hPutStrLn stderr ("WARNING: " ++ warning)
+  old <- force . either (const Nothing) (Just . stripHeader) <$> tryJust (guard . isDoesNotExistError) (readFile name)
+  if (old == Just (lines new)) then do
+    output (name ++ " is up-to-date")
+  else do
+    (writeFile name $ header ++ new)
+    output ("generated " ++ name)
+  where
+    stripHeader :: String -> [String]
+    stripHeader = dropWhile null . dropWhile ("--" `isPrefixOf`) . lines
+
+    output :: String -> IO ()
+    output message
+      | verbose = putStrLn message
+      | otherwise = return ()
diff --git a/src/Hpack/Config.hs b/src/Hpack/Config.hs
--- a/src/Hpack/Config.hs
+++ b/src/Hpack/Config.hs
@@ -26,6 +26,7 @@
 , SourceRepository(..)
 #ifdef TEST
 , getModules
+, determineModules
 #endif
 ) where
 
@@ -55,7 +56,7 @@
 package name version = Package name version Nothing Nothing Nothing Nothing Nothing Nothing [] [] [] Nothing Nothing Nothing [] [] Nothing Nothing [] [] []
 
 section :: a -> Section a
-section a = Section a [] [] [] [] [] []
+section a = Section a [] [] [] [] [] [] []
 
 packageConfig :: FilePath
 packageConfig = "package.yaml"
@@ -124,6 +125,7 @@
   commonOptionsSourceDirs :: Maybe (List FilePath)
 , commonOptionsDependencies :: Maybe (List Dependency)
 , commonOptionsDefaultExtensions :: Maybe (List String)
+, commonOptionsOtherExtensions :: Maybe (List String)
 , commonOptionsGhcOptions :: Maybe (List GhcOption)
 , commonOptionsGhcProfOptions :: Maybe (List GhcProfOption)
 , commonOptionsCppOptions :: Maybe (List CppOption)
@@ -188,8 +190,12 @@
 
 readPackageConfig :: FilePath -> IO (Either String ([String], Package))
 readPackageConfig file = do
-  config <- decodeYaml file
-  either (return . Left) (fmap Right . mkPackage) config
+  r <- decodeYaml file
+  case r of
+    Left err -> return (Left err)
+    Right config -> do
+      dir <- takeDirectory <$> canonicalizePath file
+      Right <$> mkPackage dir config
 
 data Dependency = Dependency {
   dependencyName :: String
@@ -271,6 +277,7 @@
 , sectionSourceDirs :: [FilePath]
 , sectionDependencies :: [Dependency]
 , sectionDefaultExtensions :: [String]
+, sectionOtherExtensions :: [String]
 , sectionGhcOptions :: [GhcOption]
 , sectionGhcProfOptions :: [GhcProfOption]
 , sectionCppOptions :: [CppOption]
@@ -287,18 +294,18 @@
 , sourceRepositorySubdir :: Maybe String
 } deriving (Eq, Show)
 
-mkPackage :: (CaptureUnknownFields (Section PackageConfig)) -> IO ([String], Package)
-mkPackage (CaptureUnknownFields unknownFields globalOptions@Section{sectionData = PackageConfig{..}}) = do
-  mLibrary <- mapM (toLibrary globalOptions) mLibrarySection
-  executables <- toExecutables globalOptions (map (fmap captureUnknownFieldsValue) executableSections)
-  tests <- toExecutables globalOptions (map (fmap captureUnknownFieldsValue) testsSections)
-  benchmarks <- toExecutables globalOptions  (map (fmap captureUnknownFieldsValue) benchmarkSections)
+mkPackage :: FilePath -> (CaptureUnknownFields (Section PackageConfig)) -> IO ([String], Package)
+mkPackage dir (CaptureUnknownFields unknownFields globalOptions@Section{sectionData = PackageConfig{..}}) = do
+  let name = fromMaybe (takeBaseName dir) packageConfigName
 
-  name <- maybe (takeBaseName <$> getCurrentDirectory) return packageConfigName
+  mLibrary <- mapM (toLibrary dir name globalOptions) mLibrarySection
+  executables <- toExecutables dir globalOptions (map (fmap captureUnknownFieldsValue) executableSections)
+  tests <- toExecutables dir globalOptions (map (fmap captureUnknownFieldsValue) testsSections)
+  benchmarks <- toExecutables dir globalOptions  (map (fmap captureUnknownFieldsValue) benchmarkSections)
 
-  licenseFileExists <- doesFileExist "LICENSE"
+  licenseFileExists <- doesFileExist (dir </> "LICENSE")
 
-  missingSourceDirs <- nub . sort <$> filterM (fmap not <$> doesDirectoryExist) (
+  missingSourceDirs <- nub . sort <$> filterM (fmap not <$> doesDirectoryExist . (dir </>)) (
        maybe [] sectionSourceDirs mLibrary
     ++ concatMap sectionSourceDirs executables
     ++ concatMap sectionSourceDirs tests
@@ -306,10 +313,10 @@
     )
 
   (extraSourceFilesWarnings, extraSourceFiles) <-
-    expandGlobs (fromMaybeList packageConfigExtraSourceFiles)
+    expandGlobs dir (fromMaybeList packageConfigExtraSourceFiles)
 
   (dataFilesWarnings, dataFiles) <-
-    expandGlobs (fromMaybeList packageConfigDataFiles)
+    expandGlobs dir (fromMaybeList packageConfigDataFiles)
 
   let pkg = Package {
         packageName = name
@@ -399,8 +406,8 @@
       where
         fromGithub = (++ "/issues") . sourceRepositoryUrl <$> sourceRepository
 
-toLibrary :: Section global -> Section LibrarySection -> IO (Section Library)
-toLibrary globalOptions library = traverse fromLibrarySection sect
+toLibrary :: FilePath -> String -> Section global -> Section LibrarySection -> IO (Section Library)
+toLibrary dir name globalOptions library = traverse fromLibrarySection sect
   where
     sect :: Section LibrarySection
     sect = mergeSections globalOptions library
@@ -410,12 +417,12 @@
 
     fromLibrarySection :: LibrarySection -> IO Library
     fromLibrarySection LibrarySection{..} = do
-      modules <- concat <$> mapM getModules sourceDirs
-      let (exposedModules, otherModules) = determineModules modules librarySectionExposedModules librarySectionOtherModules
+      modules <- concat <$> mapM (getModules dir) sourceDirs
+      let (exposedModules, otherModules) = determineModules name modules librarySectionExposedModules librarySectionOtherModules
       return (Library exposedModules otherModules)
 
-toExecutables :: Section global -> [(String, Section ExecutableSection)] -> IO [Section Executable]
-toExecutables globalOptions executables = mapM toExecutable sections
+toExecutables :: FilePath -> Section global -> [(String, Section ExecutableSection)] -> IO [Section Executable]
+toExecutables dir globalOptions executables = mapM toExecutable sections
   where
     sections :: [(String, Section ExecutableSection)]
     sections = map (fmap $ mergeSections globalOptions) executables
@@ -427,7 +434,7 @@
       where
         fromExecutableSection :: ExecutableSection -> IO (Executable, [GhcOption])
         fromExecutableSection ExecutableSection{..} = do
-          modules <- maybe (filterMain . concat <$> mapM getModules sectionSourceDirs) (return . fromList) executableSectionOtherModules
+          modules <- maybe (filterMain . concat <$> mapM (getModules dir) sectionSourceDirs) (return . fromList) executableSectionOtherModules
           return (Executable name mainSrcFile modules, ghcOptions)
           where
             filterMain :: [String] -> [String]
@@ -437,11 +444,12 @@
 
 mergeSections :: Section global -> Section a -> Section a
 mergeSections globalOptions options
-  = Section a sourceDirs dependencies defaultExtensions ghcOptions ghcProfOptions cppOptions
+  = Section a sourceDirs dependencies defaultExtensions otherExtensions ghcOptions ghcProfOptions cppOptions
   where
     a = sectionData options
     sourceDirs = sectionSourceDirs globalOptions ++ sectionSourceDirs options
     defaultExtensions = sectionDefaultExtensions globalOptions ++ sectionDefaultExtensions options
+    otherExtensions = sectionOtherExtensions globalOptions ++ sectionOtherExtensions options
     ghcOptions = sectionGhcOptions globalOptions ++ sectionGhcOptions options
     ghcProfOptions = sectionGhcProfOptions globalOptions ++ sectionGhcProfOptions options
     cppOptions = sectionCppOptions globalOptions ++ sectionCppOptions options
@@ -449,39 +457,40 @@
 
 toSection :: a -> CommonOptions -> Section a
 toSection a CommonOptions{..}
-  = Section a sourceDirs dependencies defaultExtensions ghcOptions ghcProfOptions cppOptions
+  = Section a sourceDirs dependencies defaultExtensions otherExtensions ghcOptions ghcProfOptions cppOptions
   where
     sourceDirs = fromMaybeList commonOptionsSourceDirs
     defaultExtensions = fromMaybeList commonOptionsDefaultExtensions
+    otherExtensions = fromMaybeList commonOptionsOtherExtensions
     ghcOptions = fromMaybeList commonOptionsGhcOptions
     ghcProfOptions = fromMaybeList commonOptionsGhcProfOptions
     cppOptions = fromMaybeList commonOptionsCppOptions
     dependencies = fromMaybeList commonOptionsDependencies
 
-determineModules :: [String] -> Maybe (List String) -> Maybe (List String) -> ([String], [String])
-determineModules modules mExposedModules mOtherModules = case (mExposedModules, mOtherModules) of
+determineModules :: String -> [String] -> Maybe (List String) -> Maybe (List String) -> ([String], [String])
+determineModules name modules mExposedModules mOtherModules = case (mExposedModules, mOtherModules) of
   (Nothing, Nothing) -> (modules, [])
   _ -> (exposedModules, otherModules)
   where
-    otherModules   = maybe (modules \\ exposedModules) fromList mOtherModules
+    otherModules   = maybe ((modules \\ exposedModules) ++ pathsModule) fromList mOtherModules
     exposedModules = maybe (modules \\ otherModules)   fromList mExposedModules
+    pathsModule = ["Paths_" ++ name] \\ exposedModules
 
-getModules :: FilePath -> IO [String]
-getModules src_ = sort <$> do
-  exists <- doesDirectoryExist src_
+getModules :: FilePath -> FilePath -> IO [String]
+getModules dir src_ = sort <$> do
+  exists <- doesDirectoryExist (dir </> src_)
   if exists
     then do
-      src <- canonicalizePath src_
-      cwd <- getCurrentDirectory
-      removeSetup cwd src . toModules <$> getFilesRecursive src
+      src <- canonicalizePath (dir </> src_)
+      removeSetup src . toModules <$> getFilesRecursive src
     else return []
   where
     toModules :: [[FilePath]] -> [String]
     toModules = catMaybes . map toModule
 
-    removeSetup :: FilePath -> FilePath -> [String] -> [String]
-    removeSetup cwd src
-      | src == cwd = filter (/= "Setup")
+    removeSetup :: FilePath -> [String] -> [String]
+    removeSetup src
+      | src == dir = filter (/= "Setup")
       | otherwise = id
 
 fromMaybeList :: Maybe (List a) -> [a]
diff --git a/src/Hpack/Run.hs b/src/Hpack/Run.hs
--- a/src/Hpack/Run.hs
+++ b/src/Hpack/Run.hs
@@ -23,17 +23,18 @@
 import           Data.Maybe
 import           Data.List.Compat
 import           System.Exit.Compat
+import           System.FilePath
 
 import           Hpack.Util
 import           Hpack.Config
 import           Hpack.Render
 
-run :: IO ([String], FilePath, String)
-run = do
-  mPackage <- readPackageConfig packageConfig
+run :: FilePath -> IO ([String], FilePath, String)
+run dir = do
+  mPackage <- readPackageConfig (dir </> packageConfig)
   case mPackage of
     Right (warnings, pkg) -> do
-      let cabalFile = packageName pkg ++ ".cabal"
+      let cabalFile = dir </> (packageName pkg ++ ".cabal")
 
       old <- tryReadFile cabalFile
 
@@ -185,6 +186,7 @@
 renderSection Section{..} = [
     renderSourceDirs sectionSourceDirs
   , renderDefaultExtensions sectionDefaultExtensions
+  , renderOtherExtensions sectionOtherExtensions
   , renderGhcOptions sectionGhcOptions
   , renderGhcProfOptions sectionGhcProfOptions
   , renderCppOptions sectionCppOptions
@@ -217,3 +219,6 @@
 
 renderDefaultExtensions :: [String] -> Element
 renderDefaultExtensions = Field "default-extensions" . WordList
+
+renderOtherExtensions :: [String] -> Element
+renderOtherExtensions = Field "other-extensions" . WordList
diff --git a/src/Hpack/Util.hs b/src/Hpack/Util.hs
--- a/src/Hpack/Util.hs
+++ b/src/Hpack/Util.hs
@@ -119,13 +119,13 @@
     isNameChar = (`elem` nameChars)
     nameChars = ['a'..'z'] ++ ['A'..'Z'] ++ "-"
 
-expandGlobs :: [String] -> IO ([String], [FilePath])
-expandGlobs patterns = do
-  files <- (fst <$> globDir compiledPatterns ".") >>= mapM removeDirectories
+expandGlobs :: FilePath -> [String] -> IO ([String], [FilePath])
+expandGlobs dir patterns = do
+  files <- (fst <$> globDir compiledPatterns dir) >>= mapM removeDirectories
   let warnings = [warn pattern | ([], pattern) <- zip files patterns]
   return (warnings, combineResults files)
   where
-    combineResults = nub . map (makeRelative ".") . sort . concat
+    combineResults = nub . map (makeRelative dir) . sort . concat
     warn pattern = "Specified pattern " ++ show pattern ++ " for extra-source-files does not match any files"
     compiledPatterns = map (compileWith options) patterns
     removeDirectories = filterM doesFileExist
diff --git a/test/Helper.hs b/test/Helper.hs
--- a/test/Helper.hs
+++ b/test/Helper.hs
@@ -2,8 +2,21 @@
   module Test.Hspec
 , module Test.Mockery.Directory
 , module Control.Applicative
+, module System.IO.Temp
+, module System.FilePath
+, withCurrentDirectory
 ) where
 
 import           Test.Hspec
 import           Test.Mockery.Directory
 import           Control.Applicative
+import           System.Directory
+import           Control.Exception
+import           System.IO.Temp
+import           System.FilePath
+
+withCurrentDirectory :: FilePath -> IO a -> IO a
+withCurrentDirectory dir action = do
+  bracket (getCurrentDirectory) (setCurrentDirectory) $ \ _ -> do
+    setCurrentDirectory dir
+    action
diff --git a/test/Hpack/ConfigSpec.hs b/test/Hpack/ConfigSpec.hs
--- a/test/Hpack/ConfigSpec.hs
+++ b/test/Hpack/ConfigSpec.hs
@@ -14,7 +14,10 @@
 import           Data.Aeson.QQ
 import           Data.Aeson.Types
 import           Data.String.Interpolate
+import           Control.Arrow
+import           System.Directory (createDirectory)
 
+import           Hpack.Util
 import           Hpack.Config hiding (package)
 import qualified Hpack.Config as Config
 
@@ -27,6 +30,27 @@
 library :: Library
 library = Library [] []
 
+withPackage :: String -> IO () -> (([String], Package) -> Expectation) -> Expectation
+withPackage content beforeAction expectation = withSystemTempDirectory "hspec" $ \dir_ -> do
+  let dir = dir_ </> "foo"
+  createDirectory dir
+  writeFile (dir </> "package.yaml") content
+  withCurrentDirectory dir beforeAction
+  r <- readPackageConfig (dir </> "package.yaml")
+  either expectationFailure expectation r
+
+withPackageConfig :: String -> IO () -> (Package -> Expectation) -> Expectation
+withPackageConfig content beforeAction expectation = withPackage content beforeAction (expectation . snd)
+
+withPackageConfig_ :: String -> (Package -> Expectation) -> Expectation
+withPackageConfig_ content = withPackageConfig content (return ())
+
+withPackageWarnings :: String -> IO () -> ([String] -> Expectation) -> Expectation
+withPackageWarnings content beforeAction expectation = withPackage content beforeAction (expectation . fst)
+
+withPackageWarnings_ :: String -> ([String] -> Expectation) -> Expectation
+withPackageWarnings_ content = withPackageWarnings content (return ())
+
 spec :: Spec
 spec = do
   describe "parseJSON" $ do
@@ -83,199 +107,191 @@
                 }|]
             parseEither parseJSON value `shouldBe` (Left "Error in $: neither key \"git\" nor key \"github\" present" :: Either String Dependency)
 
-  describe "getModules" $ around_ inTempDirectory $ do
-    it "returns Haskell modules in specified source directory" $ do
-      touch "src/Foo.hs"
-      touch "src/Bar/Baz.hs"
-      touch "src/Setup.hs"
-      getModules "src" >>= (`shouldMatchList` ["Foo", "Bar.Baz", "Setup"])
+  describe "getModules" $ around (withSystemTempDirectory "hspec") $ do
+    it "returns Haskell modules in specified source directory" $ \dir -> do
+      touch (dir </> "src/Foo.hs")
+      touch (dir </> "src/Bar/Baz.hs")
+      touch (dir </> "src/Setup.hs")
+      getModules dir "src" >>= (`shouldMatchList` ["Foo", "Bar.Baz", "Setup"])
 
     context "when source directory is '.'" $ do
-      it "ignores Setup" $ do
-        touch "Foo.hs"
-        touch "Setup.hs"
-        getModules "." `shouldReturn` ["Foo"]
+      it "ignores Setup" $ \dir -> do
+        touch (dir </> "Foo.hs")
+        touch (dir </> "Setup.hs")
+        getModules dir  "." `shouldReturn` ["Foo"]
 
     context "when source directory is './.'" $ do
-      it "ignores Setup" $ do
-        touch "Foo.hs"
-        touch "Setup.hs"
-        getModules "./." `shouldReturn` ["Foo"]
+      it "ignores Setup" $ \dir -> do
+        touch (dir </> "Foo.hs")
+        touch (dir </> "Setup.hs")
+        getModules dir  "./." `shouldReturn` ["Foo"]
 
-  describe "readPackageConfig" $ around_ (inTempDirectoryNamed "foo") $ do
+  describe "determineModules" $ do
+    it "adds the Paths_* module to the other-modules" $ do
+      determineModules "foo" [] (Just $ List ["Foo"]) Nothing `shouldBe` (["Foo"], ["Paths_foo"])
+
+    context "when the Paths_* module is part of the exposed-modules" $ do
+      it "it does not add the Paths_* module to the other-modules" $ do
+        determineModules "foo" [] (Just $ List ["Foo", "Paths_foo"]) Nothing `shouldBe` (["Foo", "Paths_foo"], [])
+
+  describe "readPackageConfig" $ do
     it "warns on unknown fields" $ do
-      writeFile "package.yaml" [i|
+      withPackageWarnings_ [i|
         bar: 23
         baz: 42
         |]
-      fmap fst <$> readPackageConfig "package.yaml" `shouldReturn` Right [
+        (`shouldBe` [
           "Ignoring unknown field \"bar\" in package description"
         , "Ignoring unknown field \"baz\" in package description"
         ]
+        )
 
     it "accepts name" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         name: bar
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageName = "bar"}
+        (packageName >>> (`shouldBe` "bar"))
 
     it "accepts version" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         version: 0.1.0
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageVersion = "0.1.0"}
+        (packageVersion >>> (`shouldBe` "0.1.0"))
 
     it "accepts synopsis" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         synopsis: some synopsis
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageSynopsis = Just "some synopsis"}
+        (packageSynopsis >>> (`shouldBe` Just "some synopsis"))
 
     it "accepts description" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         description: some description
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageDescription = Just "some description"}
+        (packageDescription >>> (`shouldBe` Just "some description"))
 
     it "accepts category" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         category: Data
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageCategory = Just "Data"}
+        (`shouldBe` package {packageCategory = Just "Data"})
 
     it "accepts author" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         author: John Doe
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageAuthor = ["John Doe"]}
+        (`shouldBe` package {packageAuthor = ["John Doe"]})
 
     it "accepts maintainer" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         maintainer: John Doe <john.doe@example.com>
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageMaintainer = ["John Doe <john.doe@example.com>"]}
+        (`shouldBe` package {packageMaintainer = ["John Doe <john.doe@example.com>"]})
 
     it "accepts copyright" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         copyright: (c) 2015 John Doe
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageCopyright = ["(c) 2015 John Doe"]}
+        (`shouldBe` package {packageCopyright = ["(c) 2015 John Doe"]})
 
     it "accepts stability" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         stability: experimental
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageStability c `shouldBe` Just "experimental"
+        (packageStability >>> (`shouldBe` Just "experimental"))
 
     it "accepts homepage URL" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         homepage: https://example.com/
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageHomepage c `shouldBe` Just "https://example.com/"
+        (packageHomepage >>> (`shouldBe` Just "https://example.com/"))
 
     it "infers homepage URL from github" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageHomepage c `shouldBe` Just "https://github.com/hspec/hspec#readme"
+        (packageHomepage >>> (`shouldBe` Just "https://github.com/hspec/hspec#readme"))
 
     it "omits homepage URL if it is null" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         homepage: null
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageHomepage c `shouldBe` Nothing
+        (packageHomepage >>> (`shouldBe` Nothing))
 
     it "accepts bug-reports URL" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         bug-reports: https://example.com/issues
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageBugReports c `shouldBe` Just "https://example.com/issues"
+        (packageBugReports >>> (`shouldBe` Just "https://example.com/issues"))
 
     it "infers bug-reports URL from github" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageBugReports c `shouldBe` Just "https://github.com/hspec/hspec/issues"
+        (packageBugReports >>> (`shouldBe` Just "https://github.com/hspec/hspec/issues"))
 
     it "omits bug-reports URL if it is null" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         bug-reports: null
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageBugReports c `shouldBe` Nothing
+        (packageBugReports >>> (`shouldBe` Nothing))
 
     it "accepts license" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         license: MIT
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageLicense = Just "MIT"}
+        (`shouldBe` package {packageLicense = Just "MIT"})
 
     it "infers license file" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig [i|
         name: foo
         |]
-      touch "LICENSE"
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {packageLicenseFile = Just "LICENSE"}
+        (do
+        touch "LICENSE"
+        )
+        (`shouldBe` package {packageLicenseFile = Just "LICENSE"})
 
     it "accepts extra-source-files" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig [i|
         extra-source-files:
           - CHANGES.markdown
           - README.markdown
         |]
-      touch "CHANGES.markdown"
-      touch "README.markdown"
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageExtraSourceFiles c `shouldBe` ["CHANGES.markdown", "README.markdown"]
+        (do
+        touch "CHANGES.markdown"
+        touch "README.markdown"
+        )
+        (packageExtraSourceFiles >>> (`shouldBe` ["CHANGES.markdown", "README.markdown"]))
 
     it "accepts data-files" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig [i|
         data-files:
           - data/**/*.html
         |]
-      touch "data/foo/index.html"
-      touch "data/bar/index.html"
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageDataFiles c `shouldMatchList` ["data/foo/index.html", "data/bar/index.html"]
+        (do
+        touch "data/foo/index.html"
+        touch "data/bar/index.html"
+        )
+        (packageDataFiles >>> (`shouldMatchList` ["data/foo/index.html", "data/bar/index.html"]))
 
     it "accepts github" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageSourceRepository c `shouldBe`
-        Just (SourceRepository "https://github.com/hspec/hspec" Nothing)
+        (packageSourceRepository >>> (`shouldBe` Just (SourceRepository "https://github.com/hspec/hspec" Nothing)))
 
     it "accepts third part of github URL as subdir" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         github: hspec/hspec/hspec-core
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      packageSourceRepository c `shouldBe`
-        Just (SourceRepository "https://github.com/hspec/hspec" (Just "hspec-core"))
+        (packageSourceRepository >>> (`shouldBe` Just (SourceRepository "https://github.com/hspec/hspec" (Just "hspec-core"))))
 
     it "accepts CPP options" $ do
-      writeFile "package.yaml" [i|
+      withPackageConfig_ [i|
         cpp-options: -DFOO
         library:
           cpp-options: -DLIB
@@ -291,147 +307,146 @@
             main: Spec.hs
             cpp-options: -DTEST
         |]
-      Right (_, c) <- readPackageConfig "package.yaml"
-      c `shouldBe` package {
+        (`shouldBe` package {
           packageLibrary = Just (section library) {sectionCppOptions = ["-DFOO", "-DLIB"]}
         , packageExecutables = [(section $ executable "foo" "Main.hs") {sectionCppOptions = ["-DFOO", "-DFOO"]}]
         , packageTests = [(section $ executable "spec" "Spec.hs") {sectionCppOptions = ["-DFOO", "-DTEST"]}]
         }
+        )
 
     context "when reading library section" $ do
       it "warns on unknown fields" $ do
-        writeFile "package.yaml" [i|
+        withPackageWarnings_ [i|
           library:
             bar: 23
             baz: 42
           |]
-
-        fmap fst <$> readPackageConfig "package.yaml" `shouldReturn` Right [
+          (`shouldBe` [
             "Ignoring unknown field \"bar\" in library section"
           , "Ignoring unknown field \"baz\" in library section"
           ]
+          )
 
       it "accepts source-dirs" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           library:
             source-dirs:
               - foo
               - bar
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library) {sectionSourceDirs = ["foo", "bar"]}
+          (packageLibrary >>> (`shouldBe` Just (section library) {sectionSourceDirs = ["foo", "bar"]}))
 
       it "accepts default-extensions" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           library:
             default-extensions:
               - Foo
               - Bar
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library) {sectionDefaultExtensions = ["Foo", "Bar"]}
+          (packageLibrary >>> (`shouldBe` Just (section library) {sectionDefaultExtensions = ["Foo", "Bar"]}))
 
       it "accepts global default-extensions" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           default-extensions:
             - Foo
             - Bar
           library: {}
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library) {sectionDefaultExtensions = ["Foo", "Bar"]}
+          (packageLibrary >>> (`shouldBe` Just (section library) {sectionDefaultExtensions = ["Foo", "Bar"]}))
 
       it "accepts global source-dirs" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           source-dirs:
             - foo
             - bar
           library: {}
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library) {sectionSourceDirs = ["foo", "bar"]}
+          (packageLibrary >>> (`shouldBe` Just (section library) {sectionSourceDirs = ["foo", "bar"]}))
 
       it "allows to specify exposed-modules" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig [i|
           library:
             source-dirs: src
             exposed-modules: Foo
           |]
-        touch "src/Foo.hs"
-        touch "src/Bar.hs"
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library{libraryExposedModules = ["Foo"], libraryOtherModules = ["Bar"]}) {sectionSourceDirs = ["src"]}
+          (do
+          touch "src/Foo.hs"
+          touch "src/Bar.hs"
+          )
+          (packageLibrary >>> (`shouldBe` Just (section library{libraryExposedModules = ["Foo"], libraryOtherModules = ["Bar", "Paths_foo"]}) {sectionSourceDirs = ["src"]}))
 
       it "allows to specify other-modules" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig [i|
           library:
             source-dirs: src
             other-modules: Bar
           |]
-        touch "src/Foo.hs"
-        touch "src/Bar.hs"
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library{libraryExposedModules = ["Foo"], libraryOtherModules = ["Bar"]}) {sectionSourceDirs = ["src"]}
+          (do
+          touch "src/Foo.hs"
+          touch "src/Bar.hs"
+          )
+          (packageLibrary >>> (`shouldBe` Just (section library{libraryExposedModules = ["Foo"], libraryOtherModules = ["Bar"]}) {sectionSourceDirs = ["src"]}))
 
       it "allows to specify both exposed-modules and other-modules" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig [i|
           library:
             source-dirs: src
             exposed-modules: Foo
             other-modules: Bar
           |]
-        touch "src/Baz.hs"
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageLibrary c `shouldBe` Just (section library{libraryExposedModules = ["Foo"], libraryOtherModules = ["Bar"]}) {sectionSourceDirs = ["src"]}
+          (do
+          touch "src/Baz.hs"
+          )
+          (packageLibrary >>> (`shouldBe` Just (section library{libraryExposedModules = ["Foo"], libraryOtherModules = ["Bar"]}) {sectionSourceDirs = ["src"]}))
 
-      context "when neither exposed-module nor other-module are specified" $ do
+      context "when neither exposed-modules nor other-modules are specified" $ do
         it "exposes all modules" $ do
-          writeFile "package.yaml" [i|
+          withPackageConfig [i|
             library:
               source-dirs: src
             |]
-          touch "src/Foo.hs"
-          touch "src/Bar.hs"
-          Right (_, c) <- readPackageConfig "package.yaml"
-          packageLibrary c `shouldBe` Just (section library{libraryExposedModules = ["Bar", "Foo"]}) {sectionSourceDirs = ["src"]}
+            (do
+            touch "src/Foo.hs"
+            touch "src/Bar.hs"
+            )
+            (packageLibrary >>> (`shouldBe` Just (section library{libraryExposedModules = ["Bar", "Foo"]}) {sectionSourceDirs = ["src"]}))
 
     context "when reading executable section" $ do
       it "warns on unknown fields" $ do
-        writeFile "package.yaml" [i|
+        withPackageWarnings_ [i|
           executables:
             foo:
               main: Main.hs
               bar: 42
               baz: 23
           |]
-
-        fmap fst <$> readPackageConfig "package.yaml" `shouldReturn` Right [
+          (`shouldBe` [
             "Ignoring unknown field \"bar\" in executable section \"foo\""
           , "Ignoring unknown field \"baz\" in executable section \"foo\""
           ]
+          )
 
       it "reads executable section" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           executables:
             foo:
               main: driver/Main.hs
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageExecutables c `shouldBe` [section $ executable "foo" "driver/Main.hs"]
+          (packageExecutables >>> (`shouldBe` [section $ executable "foo" "driver/Main.hs"]))
 
       it "accepts arbitrary entry points as main" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           executables:
             foo:
               main: Foo
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageExecutables c `shouldBe` [
+          (packageExecutables >>> (`shouldBe` [
             (section $ executable "foo" "Foo.hs") {sectionGhcOptions = ["-main-is Foo"]}
           ]
+          ))
 
       it "accepts source-dirs" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           executables:
             foo:
               main: Main.hs
@@ -439,11 +454,10 @@
                 - foo
                 - bar
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageExecutables c `shouldBe` [(section $ executable "foo" "Main.hs") {sectionSourceDirs = ["foo", "bar"]}]
+          (packageExecutables >>> (`shouldBe` [(section $ executable "foo" "Main.hs") {sectionSourceDirs = ["foo", "bar"]}]))
 
       it "accepts global source-dirs" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           source-dirs:
             - foo
             - bar
@@ -451,38 +465,39 @@
             foo:
               main: Main.hs
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageExecutables c `shouldBe` [(section $ executable "foo" "Main.hs") {sectionSourceDirs = ["foo", "bar"]}]
+          (packageExecutables >>> (`shouldBe` [(section $ executable "foo" "Main.hs") {sectionSourceDirs = ["foo", "bar"]}]))
 
       it "infers other-modules" $ do
-        touch "src/Main.hs"
-        touch "src/Foo.hs"
-        touch "src/Bar.hs"
-        touch "src/Baz.lhs"
-        writeFile "package.yaml" [i|
+        withPackageConfig [i|
           executables:
             foo:
               main: Main.hs
               source-dirs: src
           |]
-        Right (_, [r]) <- (fmap . fmap) packageExecutables <$> readPackageConfig "package.yaml"
-        executableOtherModules (sectionData r) `shouldBe` ["Bar", "Baz", "Foo"]
+          (do
+          touch "src/Main.hs"
+          touch "src/Foo.hs"
+          touch "src/Bar.hs"
+          touch "src/Baz.lhs"
+          )
+          (map (executableOtherModules . sectionData) . packageExecutables >>> (`shouldBe` [["Bar", "Baz", "Foo"]]))
 
       it "allows to specify other-modules" $ do
-        touch "src/Foo.hs"
-        touch "src/Bar.hs"
-        writeFile "package.yaml" [i|
+        withPackageConfig [i|
           executables:
             foo:
               main: Main.hs
               source-dirs: src
               other-modules: Baz
           |]
-        Right (_, [r]) <- (fmap . fmap) packageExecutables <$> readPackageConfig "package.yaml"
-        executableOtherModules (sectionData r) `shouldBe` ["Baz"]
+          (do
+          touch "src/Foo.hs"
+          touch "src/Bar.hs"
+          )
+          (map (executableOtherModules . sectionData) . packageExecutables >>> (`shouldBe` [["Baz"]]))
 
       it "accepts default-extensions" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           executables:
             foo:
               main: driver/Main.hs
@@ -490,11 +505,10 @@
                 - Foo
                 - Bar
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageExecutables c `shouldBe` [(section $ executable "foo" "driver/Main.hs") {sectionDefaultExtensions = ["Foo", "Bar"]}]
+          (packageExecutables >>> (`shouldBe` [(section $ executable "foo" "driver/Main.hs") {sectionDefaultExtensions = ["Foo", "Bar"]}]))
 
       it "accepts global default-extensions" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           default-extensions:
             - Foo
             - Bar
@@ -502,86 +516,79 @@
             foo:
               main: driver/Main.hs
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        packageExecutables c `shouldBe` [(section $ executable "foo" "driver/Main.hs") {sectionDefaultExtensions = ["Foo", "Bar"]}]
+          (packageExecutables >>> (`shouldBe` [(section $ executable "foo" "driver/Main.hs") {sectionDefaultExtensions = ["Foo", "Bar"]}]))
 
       it "accepts GHC options" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           executables:
             foo:
               main: driver/Main.hs
               ghc-options: -Wall
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcOptions = ["-Wall"]}]}
+          (`shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcOptions = ["-Wall"]}]})
 
       it "accepts global GHC options" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           ghc-options: -Wall
           executables:
             foo:
               main: driver/Main.hs
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcOptions = ["-Wall"]}]}
+          (`shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcOptions = ["-Wall"]}]})
 
       it "accepts GHC profiling options" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           executables:
             foo:
               main: driver/Main.hs
               ghc-prof-options: -fprof-auto
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcProfOptions = ["-fprof-auto"]}]}
+          (`shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcProfOptions = ["-fprof-auto"]}]})
 
       it "accepts global GHC profiling options" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           ghc-prof-options: -fprof-auto
           executables:
             foo:
               main: driver/Main.hs
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcProfOptions = ["-fprof-auto"]}]}
+          (`shouldBe` package {packageExecutables = [(section $ executable "foo" "driver/Main.hs") {sectionGhcProfOptions = ["-fprof-auto"]}]})
 
 
     context "when reading test section" $ do
       it "warns on unknown fields" $ do
-        writeFile "package.yaml" [i|
+        withPackageWarnings_ [i|
           tests:
             foo:
               main: Main.hs
               bar: 42
               baz: 23
           |]
-
-        fmap fst <$> readPackageConfig "package.yaml" `shouldReturn` Right [
+          (`shouldBe` [
             "Ignoring unknown field \"bar\" in test section \"foo\""
           , "Ignoring unknown field \"baz\" in test section \"foo\""
           ]
+          )
 
       it "reads test section" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           tests:
             spec:
               main: test/Spec.hs
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageTests = [section $ executable "spec" "test/Spec.hs"]}
+          (`shouldBe` package {packageTests = [section $ executable "spec" "test/Spec.hs"]})
 
       it "accepts single dependency" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           tests:
             spec:
               main: test/Spec.hs
               dependencies: hspec
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageTests = [(section $ executable "spec" "test/Spec.hs") {sectionDependencies = ["hspec"]}]}
+          (`shouldBe` package {packageTests = [(section $ executable "spec" "test/Spec.hs") {sectionDependencies = ["hspec"]}]})
 
       it "accepts list of dependencies" $ do
-        writeFile "package.yaml" [i|
+        withPackageConfig_ [i|
           tests:
             spec:
               main: test/Spec.hs
@@ -589,12 +596,11 @@
                 - hspec
                 - QuickCheck
           |]
-        Right (_, c) <- readPackageConfig "package.yaml"
-        c `shouldBe` package {packageTests = [(section $ executable "spec" "test/Spec.hs") {sectionDependencies = ["hspec", "QuickCheck"]}]}
+          (`shouldBe` package {packageTests = [(section $ executable "spec" "test/Spec.hs") {sectionDependencies = ["hspec", "QuickCheck"]}]})
 
       context "when both global and section specific dependencies are specified" $ do
         it "combines dependencies" $ do
-          writeFile "package.yaml" [i|
+          withPackageConfig_ [i|
             dependencies:
               - base
 
@@ -603,12 +609,11 @@
                 main: test/Spec.hs
                 dependencies: hspec
             |]
-          Right (_, c) <- readPackageConfig "package.yaml"
-          c `shouldBe` package {packageTests = [(section $ executable "spec" "test/Spec.hs") {sectionDependencies = ["base", "hspec"]}]}
+            (`shouldBe` package {packageTests = [(section $ executable "spec" "test/Spec.hs") {sectionDependencies = ["base", "hspec"]}]})
 
     context "when a specified source directory does not exist" $ do
       it "warns" $ do
-        writeFile "package.yaml" [i|
+        withPackageWarnings [i|
           source-dirs:
             - some-dir
             - some-existing-dir
@@ -623,31 +628,38 @@
               main: Main.hs
               source-dirs: some-test-dir
           |]
-        touch "some-existing-dir/foo"
-        fmap fst <$> readPackageConfig "package.yaml" `shouldReturn` Right [
+          (do
+          touch "some-existing-dir/foo"
+          )
+          (`shouldBe` [
             "Specified source-dir \"some-dir\" does not exist"
           , "Specified source-dir \"some-exec-dir\" does not exist"
           , "Specified source-dir \"some-lib-dir\" does not exist"
           , "Specified source-dir \"some-test-dir\" does not exist"
           ]
+          )
 
-    context "when package.yaml can not be parsed" $ do
-      it "returns an error" $ do
-        writeFile "package.yaml" [i|
-          foo: bar
-          foo baz
-          |]
-        readPackageConfig "package.yaml" `shouldReturn` Left "package.yaml:3:10: could not find expected ':' while scanning a simple key"
+    around (withSystemTempDirectory "hspec") $ do
+      context "when package.yaml can not be parsed" $ do
+        it "returns an error" $ \dir -> do
+          let file = dir </> "package.yaml"
+          writeFile file [i|
+            foo: bar
+            foo baz
+            |]
+          readPackageConfig file `shouldReturn` Left (file ++ ":3:12: could not find expected ':' while scanning a simple key")
 
-    context "when package.yaml is invalid" $ do
-      it "returns an error" $ do
-        writeFile "package.yaml" [i|
-          executables:
-            foo:
-              ain: driver/Main.hs
-          |]
-        readPackageConfig "package.yaml" `shouldReturn` Left "package.yaml: Error in $.executables.foo: failed to parse field executables: The key \"main\" was not found"
+      context "when package.yaml is invalid" $ do
+        it "returns an error" $ \dir -> do
+          let file = dir </> "package.yaml"
+          writeFile file [i|
+            executables:
+              foo:
+                ain: driver/Main.hs
+            |]
+          readPackageConfig file `shouldReturn` Left (file ++ ": Error in $.executables.foo: failed to parse field executables: The key \"main\" was not found")
 
-    context "when package.yaml does not exist" $ do
-      it "returns an error" $
-        readPackageConfig "package.yaml" `shouldReturn` Left "package.yaml: Yaml file not found: package.yaml"
+      context "when package.yaml does not exist" $ do
+        it "returns an error" $ \dir -> do
+          let file = dir </> "package.yaml"
+          readPackageConfig file `shouldReturn` Left [i|#{file}: Yaml file not found: #{file}|]
diff --git a/test/Hpack/UtilSpec.hs b/test/Hpack/UtilSpec.hs
--- a/test/Hpack/UtilSpec.hs
+++ b/test/Hpack/UtilSpec.hs
@@ -142,64 +142,64 @@
     it "rejects invalid fields" $ do
       splitField "foo bar" `shouldBe` Nothing
 
-  describe "expandGlobs" $ around_ inTempDirectory $ do
-    it "accepts simple files" $ do
-      touch "foo.js"
-      expandGlobs ["foo.js"] `shouldReturn` ([], ["foo.js"])
+  describe "expandGlobs" $ around (withSystemTempDirectory "hspec") $ do
+    it "accepts simple files" $ \dir -> do
+        touch (dir </> "foo.js")
+        expandGlobs dir ["foo.js"] `shouldReturn` ([], ["foo.js"])
 
-    it "removes duplicates" $ do
-      touch "foo.js"
-      expandGlobs ["foo.js", "*.js"] `shouldReturn` ([], ["foo.js"])
+    it "removes duplicates" $ \dir -> do
+      touch (dir </> "foo.js")
+      expandGlobs dir ["foo.js", "*.js"] `shouldReturn` ([], ["foo.js"])
 
-    it "rejects directories" $ do
-      touch "foo"
-      createDirectory "bar"
-      expandGlobs ["*"] `shouldReturn` ([], ["foo"])
+    it "rejects directories" $ \dir -> do
+      touch (dir </> "foo")
+      createDirectory (dir </> "bar")
+      expandGlobs dir ["*"] `shouldReturn` ([], ["foo"])
 
-    it "rejects character ranges" $ do
-      touch "foo1"
-      touch "foo2"
-      touch "foo[1,2]"
-      expandGlobs ["foo[1,2]"] `shouldReturn` ([], ["foo[1,2]"])
+    it "rejects character ranges" $ \dir -> do
+      touch (dir </> "foo1")
+      touch (dir </> "foo2")
+      touch (dir </> "foo[1,2]")
+      expandGlobs dir ["foo[1,2]"] `shouldReturn` ([], ["foo[1,2]"])
 
     context "when expanding *" $ do
-      it "expands by extension" $ do
+      it "expands by extension" $ \dir -> do
         let files = [
                 "files/foo.js"
               , "files/bar.js"
               , "files/baz.js"]
-        mapM_ touch files
-        touch "files/foo.hs"
-        expandGlobs ["files/*.js"] `shouldReturn` ([], sort files)
+        mapM_ (touch . (dir </>)) files
+        touch (dir </> "files/foo.hs")
+        expandGlobs dir ["files/*.js"] `shouldReturn` ([], sort files)
 
-      it "rejects dot-files" $ do
-        touch "foo/bar"
-        touch "foo/.baz"
-        expandGlobs ["foo/*"] `shouldReturn` ([], ["foo/bar"])
+      it "rejects dot-files" $ \dir -> do
+        touch (dir </> "foo/bar")
+        touch (dir </> "foo/.baz")
+        expandGlobs dir ["foo/*"] `shouldReturn` ([], ["foo/bar"])
 
-      it "accepts dot-files when explicitly asked to" $ do
-        touch "foo/bar"
-        touch "foo/.baz"
-        expandGlobs ["foo/.*"] `shouldReturn` ([], ["foo/.baz"])
+      it "accepts dot-files when explicitly asked to" $ \dir -> do
+        touch (dir </> "foo/bar")
+        touch (dir </> "foo/.baz")
+        expandGlobs dir ["foo/.*"] `shouldReturn` ([], ["foo/.baz"])
 
-      it "matches at most one directory component" $ do
-        touch "foo/bar/baz.js"
-        touch "foo/bar.js"
-        expandGlobs ["*/*.js"] `shouldReturn` ([], ["foo/bar.js"])
+      it "matches at most one directory component" $ \dir -> do
+        touch (dir </> "foo/bar/baz.js")
+        touch (dir </> "foo/bar.js")
+        expandGlobs dir ["*/*.js"] `shouldReturn` ([], ["foo/bar.js"])
 
     context "when expanding **" $ do
-      it "matches arbitrary many directory components" $ do
+      it "matches arbitrary many directory components" $ \dir -> do
         let file = "foo/bar/baz.js"
-        touch file
-        expandGlobs ["**/*.js"] `shouldReturn` ([], [file])
+        touch (dir </> file)
+        expandGlobs dir ["**/*.js"] `shouldReturn` ([], [file])
 
     context "when a pattern does not match anything" $ do
-      it "warns" $ do
-        expandGlobs ["foo"] `shouldReturn`
+      it "warns" $ \dir -> do
+        expandGlobs dir ["foo"] `shouldReturn`
           (["Specified pattern \"foo\" for extra-source-files does not match any files"], [])
 
     context "when a pattern only matches a directory" $ do
-      it "warns" $ do
-        createDirectory "foo"
-        expandGlobs ["foo"] `shouldReturn`
+      it "warns" $ \dir -> do
+        createDirectory (dir </> "foo")
+        expandGlobs dir ["foo"] `shouldReturn`
           (["Specified pattern \"foo\" for extra-source-files does not match any files"], [])
diff --git a/test/HpackSpec.hs b/test/HpackSpec.hs
new file mode 100644
--- /dev/null
+++ b/test/HpackSpec.hs
@@ -0,0 +1,15 @@
+module HpackSpec (spec) where
+
+import           Test.Hspec
+
+import           Hpack
+
+spec :: Spec
+spec = do
+  describe "parseVerbosity" $ do
+    it "returns True by default" $ do
+      parseVerbosity ["foo"] `shouldBe` (True, ["foo"])
+
+    context "with --silent" $ do
+      it "returns False" $ do
+        parseVerbosity ["--silent"] `shouldBe` (False, [])
