@@ -124,14 +124,18 @@ cabalFromDirectory dir = do
124124 _ -> liftIO $ hPutStrLn stderr "*** found zero or more than one cabal file. Exiting." >> exitFailure
125125
126126cabalFromFile :: Bool -> FilePath -> MaybeT IO Cabal.GenericPackageDescription
127−cabalFromFile failHard file = do
128− content <- MaybeT $ either (const Nothing) Just <$> Compat.tryIO (readFile file)
129− case Cabal.parsePackageDescription content of
130− Cabal.ParseFailed e -> do
131− guard failHard
132− liftIO $ do
127+cabalFromFile failHard file =
128+ -- readFile throws an error if it's used on binary files which contain sequences
129+ -- that do not represent valid characters. To catch that exception, we need to
130+ -- wrap the whole block in `catchIO`, because of lazy IO. The `case` will force
131+ -- the reading of the file, so we will always catch the expression here.
132+ MaybeT $ flip Compat.catchIO (const $ return Nothing) $ do
133+ content <- readFile file
134+ case Cabal.parsePackageDescription content of
135+ Cabal.ParseFailed e | failHard -> do
133136 let (line, err) = ParseUtils.locatedErrorMsg e
134137 msg = maybe "" ((++ ": ") . show) line ++ err
135138 putStrLn $ "*** error parsing cabal file: " ++ msg
136139 exitFailure
137− Cabal.ParseOk _ a -> return a
140+ Cabal.ParseFailed _ -> return Nothing
141+ Cabal.ParseOk _ a -> return (Just a)