2008-04-04 Raja R Harinath <harinath@hurrynot.org>
+ * statement.cs (ResumableStatement): New. Common base class for
+ YieldReturn and ExceptionStatement.
+ (ExitStatement): New. Common base class for Return and YieldBreak.
+ (Return): Update to changes.
+ * iterator.cs (YieldBreak): Likewise.
+ * lambda.cs (ContextualReturn): Likewise.
+
Fix #377028
* ecore.cs (Expression.ResolveAsTypeStep): If '!silent' attempt to
emit a meaningful error message.
namespace Mono.CSharp {
- public class Yield : Statement {
+ public class Yield : ResumableStatement {
Expression expr;
ArrayList finally_blocks;
bool unwind_protect;
}
}
- public class YieldBreak : Statement {
- bool unwind_protect;
+ public class YieldBreak : ExitStatement {
public YieldBreak (Location l)
{
loc = l;
}
- public override bool Resolve (EmitContext ec)
+ protected override bool DoResolve (EmitContext ec)
{
- if (!Yield.CheckContext (ec, loc, true))
- return false;
-
- // not exactly a 'return' but close enough
- unwind_protect = ec.CurrentBranching.AddReturnOrigin (ec.CurrentBranching.CurrentUsageVector, loc);
- ec.CurrentBranching.CurrentUsageVector.Goto ();
- return true;
+ return Yield.CheckContext (ec, loc, true);
}
protected override void DoEmit (EmitContext ec)
base.Emit (ec);
}
- public override bool Resolve (EmitContext ec)
+ protected override bool DoResolve (EmitContext ec)
{
//
// When delegate returns void, only expression statements can be used
return false;
}
- return base.Resolve (ec);
+ return base.DoResolve (ec);
}
}
}
}
}
+ // A 'return' or a 'yield break'
+ public abstract class ExitStatement : Statement
+ {
+ protected bool unwind_protect;
+ protected abstract bool DoResolve (EmitContext ec);
+
+ public sealed override bool Resolve (EmitContext ec)
+ {
+ if (!DoResolve (ec))
+ return false;
+
+ unwind_protect = ec.CurrentBranching.AddReturnOrigin (ec.CurrentBranching.CurrentUsageVector, loc);
+ if (unwind_protect)
+ ec.NeedReturnLabel ();
+ ec.CurrentBranching.CurrentUsageVector.Goto ();
+ return true;
+ }
+ }
+
/// <summary>
/// Implements the return statement
/// </summary>
- public class Return : Statement {
+ public class Return : ExitStatement {
protected Expression Expr;
- bool unwind_protect;
-
public Return (Expression expr, Location l)
{
Expr = expr;
loc = l;
}
- bool DoResolve (EmitContext ec)
+ protected override bool DoResolve (EmitContext ec)
{
if (Expr == null) {
if (ec.ReturnType == TypeManager.void_type)
return true;
}
-
- public override bool Resolve (EmitContext ec)
- {
- if (!DoResolve (ec))
- return false;
-
- unwind_protect = ec.CurrentBranching.AddReturnOrigin (ec.CurrentBranching.CurrentUsageVector, loc);
- if (unwind_protect)
- ec.NeedReturnLabel ();
- ec.CurrentBranching.CurrentUsageVector.Goto ();
- return true;
- }
protected override void DoEmit (EmitContext ec)
{
}
}
- public abstract class ExceptionStatement : Statement
+ // A place where execution can restart in an iterator
+ public abstract class ResumableStatement : Statement
+ {
+ public Label ResumePoint;
+ }
+
+ public abstract class ExceptionStatement : ResumableStatement
{
public abstract void EmitFinallyBody (EmitContext ec);