--- /dev/null
+// CS1706: Anonymous methods and lambda expressions cannot be used in the current context
+// Line: 13
+
+using System;
+
+delegate int TestDelegate();
+
+class MyAttr : Attribute
+{
+ public MyAttr (TestDelegate d) { }
+}
+
+[MyAttr (() => 1)]
+class C
+{
+}
+
public TypeSpec InferReturnType (ResolveContext ec, TypeInferenceContext tic, TypeSpec delegate_type)
{
+ Expression expr;
AnonymousExpression am;
+
+ if (compatibles.TryGetValue (delegate_type, out expr)) {
+ am = expr as AnonymousExpression;
+ return am == null ? null : am.ReturnType;
+ }
+
using (ec.Set (ResolveContext.Options.ProbingMode | ResolveContext.Options.InferReturnType)) {
am = CompatibleMethodBody (ec, tic, InternalType.Arglist, delegate_type);
if (am != null)
am = am.Compatible (ec);
}
-
+
if (am == null)
return null;
+// compatibles.Add (delegate_type, am);
return am.ReturnType;
}
} catch (Exception e) {
throw new InternalErrorException (e, loc);
}
-
- if (!ec.IsInProbingMode)
- compatibles.Add (type, am == null ? EmptyExpression.Null : am);
+
+ if (!ec.IsInProbingMode) {
+ compatibles.Add (type, am ?? EmptyExpression.Null);
+ }
return am;
}
//
type = InternalType.AnonymousMethod;
- if ((Parameters != null) && !Parameters.Resolve (ec))
+ if (!DoResolveParameters (ec))
return null;
// FIXME: The emitted code isn't very careful about reachability
return this;
}
+ protected virtual bool DoResolveParameters (ResolveContext rc)
+ {
+ return Parameters.Resolve (rc);
+ }
+
public override void Emit (EmitContext ec)
{
// nothing, as we only exist to not do anything.
public AnonymousExpression Compatible (ResolveContext ec, AnonymousExpression ae)
{
+ if (block.Resolved)
+ return this;
+
// TODO: Implement clone
BlockContext aec = new BlockContext (ec.MemberContext, Block, ReturnType);
aec.CurrentAnonymousMethod = ae;
- IDisposable aec_dispose = null;
+ ResolveContext.FlagsHandle? aec_dispose = null;
ResolveContext.Options flags = 0;
if (ec.HasSet (ResolveContext.Options.InferReturnType)) {
flags |= ResolveContext.Options.InferReturnType;
}
if (aec_dispose != null) {
- aec_dispose.Dispose ();
+ aec_dispose.Value.Dispose ();
}
if (res && errors != ec.Report.Errors)
// do nothing
}
+ public sealed override Expression Clone (CloneContext clonectx)
+ {
+ // No cloning is not needed for constants
+ return this;
+ }
+
protected override void CloneTo (CloneContext clonectx, Expression target)
{
- // CloneTo: Nothing, we do not keep any state on this expression
+ throw new NotSupportedException ("should not be reached");
}
public override System.Linq.Expressions.Expression MakeExpression (BuilderContext ctx)
}
}
- public abstract class IntegralConstant : Constant {
+ public abstract class IntegralConstant : Constant
+ {
protected IntegralConstant (Location loc) :
base (loc)
{
public bool IsObsolete {
get {
// Disables obsolete checks when probing is on
- return IsInProbingMode || MemberContext.IsObsolete;
+ return MemberContext.IsObsolete;
}
}
public void AddBlockMap (Block from, Block to)
{
- if (block_map.ContainsKey (from))
- return;
- block_map[from] = to;
+ block_map.Add (from, to);
}
public Block LookupBlock (Block from)
Block result;
if (!block_map.TryGetValue (from, out result)) {
result = (Block) from.Clone (this);
- block_map [from] = result;
}
return result;
// compile the same code using different type values for the same
// arguments to find the correct overload
//
- public Expression Clone (CloneContext clonectx)
+ public virtual Expression Clone (CloneContext clonectx)
{
Expression cloned = (Expression) MemberwiseClone ();
CloneTo (clonectx, cloned);
var a = bounds [index];
if (a == null) {
- a = new List<BoundInfo> ();
+ a = new List<BoundInfo> (2);
+ a.Add (bound);
bounds [index] = a;
- } else {
- if (a.Contains (bound))
- return;
+ return;
}
- //
- // SPEC: does not cover type inference using constraints
- //
- //if (TypeManager.IsGenericParameter (t)) {
- // GenericConstraints constraints = TypeManager.GetTypeParameterConstraints (t);
- // if (constraints != null) {
- // //if (constraints.EffectiveBaseClass != null)
- // // t = constraints.EffectiveBaseClass;
- // }
- //}
+ if (a.Contains (bound))
+ return;
+
a.Add (bound);
}
AttributesBag bag = null;
List<string> conditionals = null;
- var attrs = CustomAttributeData.GetCustomAttributes (mi);
+ // It should not throw any loading exception
+ IList<CustomAttributeData> attrs = CustomAttributeData.GetCustomAttributes (mi);
+
foreach (var a in attrs) {
var type = a.Constructor.DeclaringType;
if (type == typeof (ObsoleteAttribute)) {
return Parameters;
}
- protected override Expression DoResolve (ResolveContext ec)
+ protected override AnonymousMethodBody CompatibleMethodFactory (TypeSpec returnType, TypeSpec delegateType, ParametersCompiled p, ToplevelBlock b)
+ {
+ return new LambdaMethod (p, b, returnType, delegateType, loc);
+ }
+
+ protected override bool DoResolveParameters (ResolveContext rc)
{
//
// Only explicit parameters can be resolved at this point
//
if (HasExplicitParameters) {
- if (!Parameters.Resolve (ec))
- return null;
+ return Parameters.Resolve (rc);
}
- eclass = ExprClass.Value;
- type = InternalType.AnonymousMethod;
- return this;
- }
-
- protected override AnonymousMethodBody CompatibleMethodFactory (TypeSpec returnType, TypeSpec delegateType, ParametersCompiled p, ToplevelBlock b)
- {
- return new LambdaMethod (p, b, returnType, delegateType, loc);
+ return true;
}
public override string GetSignatureForError ()
}
}
- public class LambdaMethod : AnonymousMethodBody
+ class LambdaMethod : AnonymousMethodBody
{
public LambdaMethod (ParametersCompiled parameters,
ToplevelBlock block, TypeSpec return_type, TypeSpec delegate_type,
public TypeParameterSpec[] TypeParameters {
get {
+ // TODO: Cache this
return CurrentTypeParameters.Select (l => l.Type).ToArray ();
}
}
clonectx.AddBlockMap (this, target);
- target.Toplevel = (ToplevelBlock) clonectx.LookupBlock (Toplevel);
- target.Explicit = (ExplicitBlock) clonectx.LookupBlock (Explicit);
+ target.Toplevel = (ToplevelBlock) (Toplevel == this ? target : clonectx.LookupBlock (Toplevel));
+ target.Explicit = (ExplicitBlock) (Explicit == this ? target : clonectx.LookupBlock (Explicit));
+
if (Parent != null)
target.Parent = clonectx.RemapBlockCopy (Parent);
protected override void CloneTo (CloneContext clonectx, Statement t)
{
- ToplevelBlock target = (ToplevelBlock) t;
base.CloneTo (clonectx, t);
if (parameters.Count != 0) {
+ ToplevelBlock target = (ToplevelBlock) t;
+
target.parameter_info = new ToplevelParameterInfo[parameters.Count];
for (int i = 0; i < parameters.Count; ++i)
target.parameter_info[i] = new ToplevelParameterInfo (target, i);