-----------------------------------------------------------------------------
--- $Id: InteractiveUI.hs,v 1.15 2000/11/24 17:09:52 simonmar Exp $
+-- $Id: InteractiveUI.hs,v 1.25 2001/01/10 17:19:01 sewardj Exp $
--
-- GHC Interactive User Interface
--
import Module
import Outputable
import Util
+import PprType {- instance Outputable Type; do not delete -}
+import Panic ( GhcException(..) )
import Exception
+#ifndef NO_READLINE
import Readline
+#endif
import IOExts
import Numeric
import IO
import Char
+
-----------------------------------------------------------------------------
ghciWelcomeMsg = "\
\|| || || || || (| Bug reports to: glasgow-haskell-bugs@haskell.org \n\
\(|___|| || || (|__|) \\\\______________________________________________________\n"
-commands :: [(String, String -> GHCi ())]
+commands :: [(String, String -> GHCi Bool)]
commands = [
- ("add", addModule),
- ("cd", changeDirectory),
- ("help", help),
- ("?", help),
- ("load", loadModule),
- ("module", setContext),
- ("reload", reloadModule),
- ("set", setOptions),
- ("type", typeOfExpr),
- ("unset", unsetOptions),
+ ("add", keepGoing addModule),
+ ("cd", keepGoing changeDirectory),
+ ("help", keepGoing help),
+ ("?", keepGoing help),
+ ("load", keepGoing loadModule),
+ ("module", keepGoing setContext),
+ ("reload", keepGoing reloadModule),
+ ("set", keepGoing setOptions),
+ ("type", keepGoing typeOfExpr),
+ ("unset", keepGoing unsetOptions),
("quit", quit)
]
+keepGoing :: (String -> GHCi ()) -> (String -> GHCi Bool)
+keepGoing a str = a str >> return False
+
shortHelpText = "use :? for help.\n"
helpText = "\
(unGHCi uiLoop) GHCiState{ modules = mods,
current_module = this_mod,
- target = Nothing,
+ target = mod,
cmstate = cmstate',
options = [ShowTiming]}
return ()
#ifndef NO_READLINE
l <- io (readline (moduleNameUserString (current_module st) ++ "> "))
#else
- l <- io (hGetLine stdin)
+ l_ok <- io (hGetLine stdin)
+ let l = Just l_ok
#endif
case l of
Nothing -> exitGHCi
#ifndef NO_READLINE
io (addHistory l)
#endif
- runCommand l
- uiLoop
+ quit <- runCommand l
+ if quit then exitGHCi else uiLoop
-exitGHCi = io $ do putStrLn "Leaving GHCi."; exitWith ExitSuccess
+exitGHCi = io $ do putStrLn "Leaving GHCi."
-- Top level exception handler, just prints out the exception
-- and carries on.
+runCommand :: String -> GHCi Bool
runCommand c =
- ghciHandle ( \other_exception ->io (putStrLn (show other_exception) )) $
+ ghciHandle (
+ \other_exception
+ -> io (putStrLn (show other_exception)) >> return False
+ ) $
ghciHandleDyn
(\dyn -> case dyn of
PhaseFailed phase code ->
io ( putStrLn ("Phase " ++ phase ++ " failed (code "
++ show code ++ ")"))
Interrupted -> io (putStrLn "Interrupted.")
- _ -> io (putStrLn (show (dyn :: BarfKind)))
+ _ -> io (putStrLn (show (dyn :: GhcException)))
+ >> return False
) $
doCommand c
doCommand (':' : command) = specialCommand command
-doCommand expr = timeIt (evalExpr expr)
+doCommand expr = do timeIt (evalExpr expr
+ >> evalExpr "Prelude.putStr \"\n\"")
+ return False
evalExpr expr
= do st <- getGHCiState
return ()
-}
-specialCommand ('!':str) = shellEscape (dropWhile isSpace str)
+specialCommand :: String -> GHCi Bool
+specialCommand ('!':str) = shellEscape (dropWhile isSpace str)
specialCommand str = do
let (cmd,rest) = break isSpace str
case [ (s,f) | (s,f) <- commands, prefixMatch cmd s ] of
- [] -> io $ hPutStr stdout ("unknown command `:" ++ cmd ++ "'\n"
- ++ shortHelpText)
+ [] -> io (hPutStr stdout ("unknown command `:" ++ cmd ++ "'\n"
+ ++ shortHelpText) >> return False)
[(_,f)] -> f (dropWhile isSpace rest)
- cs -> io $ hPutStrLn stdout ("prefix " ++ cmd ++
- " matches multiple commands (" ++
+ cs -> io (hPutStrLn stdout ("prefix " ++ cmd ++
+ " matches multiple commands (" ++
foldr1 (\a b -> a ++ ',':b) (map fst cs)
- ++ ")")
+ ++ ")") >> return False)
noArgs c = io (hPutStrLn stdout ("command `:" ++ c ++ "' takes no arguments"))
setGHCiState st{current_module = mkModuleName m}
changeDirectory :: String -> GHCi ()
-changeDirectory = io . setCurrentDirectory
+changeDirectory d = io (setCurrentDirectory d)
loadModule :: String -> GHCi ()
loadModule path = timeIt (loadModule' path)
modules = mods,
current_module = case mods of
[] -> defaultCurrentModule
- xs -> last xs,
+ xs -> head xs,
target = Just path
}
setGHCiState new_state
case target state of
Nothing -> io (putStr "no current target\n")
Just path
- -> do (new_cmstate, ok, mod) <- io (cmLoadModule (cmstate state) path)
- setGHCiState state{cmstate=new_cmstate}
+ -> do (new_cmstate, ok, mods) <- io (cmLoadModule (cmstate state) path)
+ setGHCiState
+ state{cmstate=new_cmstate,
+ modules = mods,
+ current_module = case mods of
+ [] -> defaultCurrentModule
+ xs -> head xs
+ }
+
+
reloadModule _ = noArgs ":reload"
typeOfExpr :: String -> GHCi ()
(current_module st) str)
case maybe_ty of
Nothing -> return ()
- Just (_, unqual, ty) -> io (printForUser stdout unqual (ppr ty))
+ Just (_, unqual, ty) -> io (printForUser stdout unqual (ppr ty))
-quit :: String -> GHCi ()
-quit _ = exitGHCi
+quit :: String -> GHCi Bool
+quit _ = return True
-shellEscape :: String -> GHCi ()
-shellEscape str = io (system str >> return ())
+shellEscape :: String -> GHCi Bool
+shellEscape str = io (system str >> return False)
----------------------------------------------------------------------------
-- Code for `:set'