+Basically does the translation given in the Haskell~1.3 report:
+\begin{code}
+dsDo :: Id -- id for: (>>=) m
+ -> Id -- id for: zero m
+ -> [TypecheckedStmt]
+ -> DsM CoreExpr
+
+dsDo then_id zero_id (stmt:stmts)
+ = case stmt of
+ ExprStmt expr locn -> ASSERT( null stmts ) do_expr expr locn
+
+ ExprStmtOut expr locn a b ->
+ do_expr expr locn `thenDs` \ expr2 ->
+ ds_rest `thenDs` \ rest ->
+ newSysLocalDs a `thenDs` \ ignored_result_id ->
+ dsApp (HsVar then_id) [TyArg a, TyArg b, VarArg expr2,
+ VarArg (mkValLam [ignored_result_id] rest)]
+
+ LetStmt binds ->
+ dsBinds False binds `thenDs` \ binds2 ->
+ ds_rest `thenDs` \ rest ->
+ returnDs (mkCoLetsAny binds2 rest)
+
+ BindStmtOut pat expr locn a b ->
+ do_expr expr locn `thenDs` \ expr2 ->
+ let
+ zero_expr = TyApp (HsVar zero_id) [b]
+ main_match
+ = PatMatch pat (SimpleMatch (HsDoOut stmts then_id zero_id locn))
+ the_matches
+ = if failureFreePat pat
+ then [main_match]
+ else [main_match, PatMatch (WildPat a) (SimpleMatch zero_expr)]
+ in
+ matchWrapper DoBindMatch the_matches "`do' statement"
+ `thenDs` \ (binders, matching_code) ->
+ dsApp (HsVar then_id) [TyArg a, TyArg b,
+ VarArg expr2, VarArg (mkValLam binders matching_code)]
+ where
+ ds_rest = dsDo then_id zero_id stmts
+ do_expr expr locn = putSrcLocDs locn (dsExpr expr)