4f657aa14e
Avoid using fileSize which maxes out at just 2 gb on Windows. Instead, use hFileSize, which doesn't have a bounded size. Fixes support for files > 2 gb on Windows. Note that the InodeCache code only needs to compare a file size, so it doesn't matter it the file size wraps. So it has been left as-is. This was necessary both to avoid invalidating existing inode caches, and because the code passed FileStatus around and would have become more expensive if it called getFileSize. This commit was sponsored by Christian Dietrich.
33 lines
834 B
Haskell
33 lines
834 B
Haskell
{- File size.
|
|
-
|
|
- License: BSD-2-clause
|
|
-}
|
|
|
|
{-# LANGUAGE CPP #-}
|
|
|
|
module Utility.FileSize where
|
|
|
|
import System.PosixCompat.Files
|
|
import Control.Exception (bracket)
|
|
import System.IO
|
|
|
|
{- Gets the size of a file.
|
|
-
|
|
- This is better than using fileSize, because on Windows that returns a
|
|
- FileOffset which maxes out at 2 gb.
|
|
- See https://github.com/jystic/unix-compat/issues/16
|
|
-}
|
|
getFileSize :: FilePath -> IO Integer
|
|
#ifndef mingw32_HOST_OS
|
|
getFileSize f = fromIntegral . fileSize <$> getFileStatus f
|
|
#else
|
|
getFileSize f = bracket (openFile f ReadMode) hClose hFileSize
|
|
#endif
|
|
|
|
{- Gets the size of the file, when its FileStatus is already known. -}
|
|
getFileSize' :: FilePath -> FileStatus -> IO Integer
|
|
#ifndef mingw32_HOST_OS
|
|
getFileSize' _ s = return $ fromIntegral $ fileSize s
|
|
#else
|
|
getFileSize' f _ = getFileSize f
|
|
#endif
|