sealed class ThisInitializer : Statement
{
readonly HoistedThis hoisted_this;
+ readonly AnonymousMethodStorey parent;
- public ThisInitializer (HoistedThis hoisted_this)
+ public ThisInitializer (HoistedThis hoisted_this, AnonymousMethodStorey parent)
{
this.hoisted_this = hoisted_this;
+ this.parent = parent;
+ }
+
+ public override bool Resolve (BlockContext bc)
+ {
+ return base.Resolve (bc);
}
protected override void DoEmit (EmitContext ec)
{
- hoisted_this.EmitAssign (ec, new CompilerGeneratedThis (ec.CurrentType, loc), false, false);
+ Expression source = EmptyExpression.Null;
+
+ if (parent == null)
+ source = new CompilerGeneratedThis (ec.CurrentType, loc);
+ else {
+ source = new FieldExpr (parent.HoistedThis.Field, Location.Null) {
+ InstanceExpression = new CompilerGeneratedThis (ec.CurrentType, Location.Null)
+ };
+ }
+
+ hoisted_this.EmitAssign (ec, source, false, false);
}
protected override void CloneTo (CloneContext clonectx, Statement target)
public Expression Instance;
bool initialize_hoisted_this;
+ AnonymousMethodStorey hoisted_this_parent;
public AnonymousMethodStorey (ExplicitBlock block, TypeDefinition parent, MemberBase host, TypeParameters tparams, string name, MemberKind kind)
: base (parent, MakeMemberName (host, name, parent.Module.CounterAnonymousContainers, tparams, block.StartLocation),
ID = parent.Module.CounterAnonymousContainers++;
}
- public void AddCapturedThisField (EmitContext ec)
+ public void AddCapturedThisField (EmitContext ec, AnonymousMethodStorey parent)
{
TypeExpr type_expr = new TypeExpression (ec.CurrentType, Location);
Field f = AddCompilerGeneratedField ("$this", type_expr);
hoisted_this = new HoistedThis (this, f);
initialize_hoisted_this = true;
+ hoisted_this_parent = parent;
}
public Field AddCapturedVariable (string name, TypeSpec type)
// referenced indirectly
//
if (initialize_hoisted_this) {
- rc.CurrentBlock.AddScopeStatement (new ThisInitializer (hoisted_this));
+ rc.CurrentBlock.AddScopeStatement (new ThisInitializer (hoisted_this, hoisted_this_parent));
}
//
//
parent = sm_parent.Parent.PartialContainer;
}
+ } else {
+ //
+ // For iterators we can host everything in one class
+ //
+ if (sm is IteratorStorey)
+ parent = storey = sm;
}
-
- //
- // For iterators we can host everything in one class
- //
- if (sm is IteratorStorey)
- parent = storey = sm;
}
modifiers = storey != null ? Modifiers.INTERNAL : Modifiers.PRIVATE;