runstmt within API

pepe mnislaih at gmail.com
Wed Apr 23 09:40:26 EDT 2008


Chris,

On 23/04/2008, at 12:41, C.M.Brown wrote:

> Hello,
>
> I want to use the ghc evaluator on the fly for some refactorings  
> within
> HaRe. However, I notice that runstmt ::Session -> String -> IO  
> RunResult.
>
> Is there anyway I can grab the result of the evaluated expression as a
> String (rather than it being outputted to the terminal)?
>


The result of an expression is not a String, but an arbitrary value of  
some type.
If there is a Show instance around for it, you can use that to get a  
String.

One way to do that (untested):

 > nameToString :: Session -> Name -> IO String
>  nameToString cms@(Session ref) name = do
>          dflags  <- GHC.getSessionDynFlags cms
>          do
>            let noop_log _ _ _ _ = return ()
>                expr = "show " ++ showSDoc (ppr name)
>            GHC.setSessionDynFlags cms dflags{log_action=noop_log}
>            mb_txt <- GHC.compileExpr cms expr
>            case mb_txt of
>              Just txt_ | txt <- unsafeCoerce# txt_, not (null txt)
>                        -> return $ Just txt
>              _  -> return Nothing
>          `finally`
>            GHC.setSessionDynFlags cms dflags

The expression "show <name>" is evaluated via compileExpr. CompileExpr  
will return a HValue that you need to cast to a String.
Or one can use dynCompileExpr instead.
The code takes care of temporarily replacing log_action to capture the  
type error arising in the case there is not a Show instance available.


A way to tell runStmt that you don't want the result outputted to  
stdout is to enable the flag -no-print-bind-result.

It would be nice to wrap this code in a more friendly API. Hopefully  
the SoC project will take care of that !

Cheers
pepe


More information about the Glasgow-haskell-users mailing list