X-Git-Url: http://git.megacz.com/?p=ghc-hetmet.git;a=blobdiff_plain;f=utils%2Frunghc%2Frunghc.hs;h=aadafd9a7125ef28785770e74294187b4badc429;hp=decbdcd2ba838df17b7dabaa28e307e96fab54c3;hb=34cc75e1a62638f2833815746ebce0a9114dc26b;hpb=54b748e03297e970bbef9d00a96139798009af0d diff --git a/utils/runghc/runghc.hs b/utils/runghc/runghc.hs index decbdcd..aadafd9 100644 --- a/utils/runghc/runghc.hs +++ b/utils/runghc/runghc.hs @@ -25,6 +25,8 @@ module Main (main) where import Control.Exception import Data.Char import Data.List +import Data.Monoid +import Data.Version import System.Cmd import System.Directory import System.Environment @@ -41,9 +43,11 @@ import Foreign.C.String main :: IO () main = do args <- getArgs - case getGhcLoc args of - (Just ghc, args') -> doIt ghc args' - (Nothing, args') -> do + case parseRunGhcFlags args of + (Help, _) -> printUsage + (ShowVersion, _) -> printVersion + (RunGhcFlags (Just ghc), args') -> doIt ghc args' + (RunGhcFlags Nothing, args') -> do mbPath <- getExecPath case mbPath of Nothing -> dieProg ("cannot find ghc") @@ -51,20 +55,44 @@ main = do let ghc = takeDirectory (normalise path) "ghc" in doIt ghc args' -getGhcLoc :: [String] -> (Maybe FilePath, [String]) -getGhcLoc args = case args of - "-f" : ghc : args' -> f ghc args' - ('-' : 'f' : ghc) : args' -> f ghc args' - -- If you need the first GHC flag to be a -f flag then - -- you can pass -- first - "--" : args' -> (Nothing, args') - _ -> (Nothing, args) - where f ghc args' = -- If there is another -f flag later on then - -- that overrules the one that we've already - -- found - case getGhcLoc args' of - (Nothing, _) -> (Just ghc, args') - success -> success +data RunGhcFlags = RunGhcFlags (Maybe FilePath) -- GHC location + | Help -- Print help text + | ShowVersion -- Print version info + +instance Monoid RunGhcFlags where + mempty = RunGhcFlags Nothing + Help `mappend` _ = Help + _ `mappend` Help = Help + ShowVersion `mappend` _ = ShowVersion + _ `mappend` ShowVersion = ShowVersion + RunGhcFlags _ `mappend` right@(RunGhcFlags (Just _)) = right + left@(RunGhcFlags _) `mappend` RunGhcFlags Nothing = left + +parseRunGhcFlags :: [String] -> (RunGhcFlags, [String]) +parseRunGhcFlags = f mempty + where f flags ("-f" : ghc : args) + = f (flags `mappend` RunGhcFlags (Just ghc)) args + f flags (('-' : 'f' : ghc) : args) + = f (flags `mappend` RunGhcFlags (Just ghc)) args + f flags ("--help" : args) = f (flags `mappend` Help) args + f flags ("--version" : args) = f (flags `mappend` ShowVersion) args + -- If you need the first GHC flag to be a -f flag then + -- you can pass -- first + f flags ("--" : args) = (flags, args) + f flags args = (flags, args) + +printVersion :: IO () +printVersion = do + putStrLn ("runghc " ++ VERSION) + +printUsage :: IO () +printUsage = do + putStrLn "Usage: runghc [runghc flags] [GHC flags] module [program args]" + putStrLn "" + putStrLn "The runghc flags are" + putStrLn " -f /path/to/ghc Tell runghc where GHC is" + putStrLn " --help Print this usage information" + putStrLn " --version Print version number" doIt :: String -> [String] -> IO () doIt ghc args = do @@ -76,15 +104,22 @@ doIt ghc args = do tmpdir <- getTemporaryDirectory bracket (openTempFile tmpdir "runghcXXXX.hs") - (\(filename,_) -> removeFile filename) + (\(filename,h) -> do hClose h; removeFile filename) $ \(filename,h) -> do getContents >>= hPutStr h hClose h doIt ghc (ghc_args ++ [filename]) filename : prog_args -> do - let xflag = if takeExtension filename == ".lhs" - then [] - else ["-x", "hs"] + -- If the file exists, and is not a .lhs file, then we + -- want to treat it as a .hs file. + -- + -- If the file doesn't exist then GHC is going to look for + -- filename.hs and filename.lhs, and use the appropriate + -- type. + exists <- doesFileExist filename + let xflag = if exists && (takeExtension filename /= ".lhs") + then ["-x", "hs"] + else [] c1 = ":set prog " ++ show filename c2 = ":main " ++ show prog_args res <- rawSystem ghc (["-ignore-dot-ghci"] ++