Improve Template Haskell error recovery
Marc Weber wants better error recovery in TH's Q monad: http://www.haskell.org/pipermail/template-haskell/2008-May/000666.html
The Quasi monad is defined thus:
```
class (Monad m, Functor m) => Quasi m where
-- Fresh names
qNewName :: String -> m Name
-- Error reporting and recovery
qReport :: Bool -> String -> m () -- Report an error (True) or warning (False)
-- ...but carry on; use 'fail' to stop
qRecover :: m a -> m a -> m a -- Recover from the monadic 'fail'
-- The first arg is the error handler
-- Inspect the type-checker's environment
qReify :: Name -> m Info
qLocation :: m Loc
-- Input/output (dangerous)
qRunIO :: IO a -> m a
```
A sensible change (but it would be a change) would be to change `qRecover` thus:
```
qRecover :: m a -> ([(Bool,String)] -> m a) -> m a
-- (qRecover q f) runs the action `q`, collecting all the messages
-- emitted by `qReport`. If the action `q` calls the monad `fail`,
-- these messages are passed to `f`. If the action `q` does not call
-- `fail`, the messages are retained in the monad, just as if the
-- `qRecover` was not there.
```
Comments? This would be quite easy to implement in 6.10.
Simon
<details><summary>Trac metadata</summary>
| Trac field | Value |
| ---------------------- | ------------------- |
| Version | 6.8.2 |
| Type | FeatureRequest |
| TypeOfFailure | OtherFailure |
| Priority | normal |
| Resolution | Unresolved |
| Component | Compiler |
| Test case | |
| Differential revisions | |
| BlockedBy | |
| Related | |
| Blocking | |
| CC | marco-oweber@gmx.de |
| Operating system | Unknown |
| Architecture | Unknown |
</details>
<!-- {"blocked_by":[],"summary":"Improve Template Haskell error recovery","status":"New","operating_system":"Unknown","component":"Compiler","related":[],"milestone":"","resolution":"Unresolved","owner":{"tag":"Unowned"},"version":"6.8.2","keywords":[],"differentials":[],"test_case":"","architecture":"Unknown","cc":["marco-oweber@gmx.de"],"type":"FeatureRequest","description":"Marc Weber wants better error recovery in TH's Q monad: http://www.haskell.org/pipermail/template-haskell/2008-May/000666.html\r\n\r\nThe Quasi monad is defined thus:\r\n{{{\r\nclass (Monad m, Functor m) => Quasi m where\r\n\t-- Fresh names\r\n qNewName :: String -> m Name\r\n\r\n\t-- Error reporting and recovery\r\n qReport :: Bool -> String -> m ()\t-- Report an error (True) or warning (False)\r\n\t\t\t\t\t-- ...but carry on; use 'fail' to stop\r\n qRecover :: m a -> m a -> m a\t\t-- Recover from the monadic 'fail'\r\n\t\t\t\t\t-- The first arg is the error handler\r\n \r\n\t-- Inspect the type-checker's environment\r\n qReify :: Name -> m Info\r\n qLocation :: m Loc\r\n\r\n\t-- Input/output (dangerous)\r\n qRunIO :: IO a -> m a\r\n}}}\r\nA sensible change (but it would be a change) would be to change `qRecover` thus:\r\n{{{\r\n qRecover :: m a -> ([(Bool,String)] -> m a) -> m a\r\n -- (qRecover q f) runs the action `q`, collecting all the messages\r\n -- emitted by `qReport`. If the action `q` calls the monad `fail`,\r\n -- these messages are passed to `f`. If the action `q` does not call\r\n -- `fail`, the messages are retained in the monad, just as if the \r\n -- `qRecover` was not there.\r\n}}}\r\nComments? This would be quite easy to implement in 6.10. \r\n\r\nSimon","type_of_failure":"OtherFailure","blocking":[]} -->
issue