/// <summary> /// accessor_mbr = "." identifier [ type_args ] /// </summary> private GetMemberNode parseAccessorMbr() { if (!check(LexemType.Dot)) return null; var node = new GetMemberNode(); node.MemberName = ensure(LexemType.Identifier, ParserMessages.MemberNameExpected).Value; var args = attempt(parseTypeArgs); if (args != null) node.TypeHints = args; return node; }
/// <summary> /// lvalue_stmbr_expr = type "::" identifier /// </summary> private GetMemberNode parseLvalueStmbrExpr() { var type = attempt(parseType); if (type == null || !check(LexemType.DoubleСolon)) return null; var node = new GetMemberNode(); node.StaticType = type; node.MemberName = ensure(LexemType.Identifier, ParserMessages.MemberNameExpected).Value; return node; }
/// <summary> /// invoke_pass = "******" identifier ( invoke_block_args | invoke_line_args ) /// </summary> private InvocationNode parseInvokePass() { if (!check(LexemType.PassRight)) return null; var getter = new GetMemberNode(); var invoker = new InvocationNode { Expression = getter }; getter.MemberName = ensure(LexemType.Identifier, ParserMessages.MemberNameExpected).Value; invoker.Arguments = parseInvokeBlockArgs().ToList(); if (invoker.Arguments.Count == 0) invoker.Arguments = parseInvokeLineArgs().ToList(); if (invoker.Arguments.Count == 0) error(ParserMessages.ArgumentsExpected); return invoker; }
private void resolveGetMember(Context ctx, GetMemberNode node) { m_InvocationSource = node.Expression; var type = m_InvocationSource != null ? m_InvocationSource.GetExpressionType(ctx) : ctx.ResolveType(node.StaticType); SafeModeCheckType(ctx, type); if (node.TypeHints.Any()) m_TypeHints = node.TypeHints.Select(x => x.FullSignature == "_" ? null : ctx.ResolveType(x)).ToArray(); try { // resolve a normal method try { m_Method = ctx.ResolveMethod(type, node.MemberName, m_ArgTypes, m_TypeHints); if (m_Method.IsStatic) m_InvocationSource = null; return; } catch (KeyNotFoundException) { if (m_InvocationSource == null) throw; } // resolve a callable field try { ctx.ResolveField(type, node.MemberName); resolveExpression(ctx, node); return; } catch (KeyNotFoundException) { } // resolve a callable field try { ctx.ResolveProperty(type, node.MemberName); resolveExpression(ctx, node); return; } catch (KeyNotFoundException) { } // resolve a local function that is implicitly used as an extension method // move invocation source to arguments if (Arguments[0] is UnitNode) Arguments[0] = m_InvocationSource; else Arguments.Insert(0, m_InvocationSource); var oldArgTypes = m_ArgTypes; m_ArgTypes = Arguments.Select(a => a.GetExpressionType(ctx)).ToArray(); m_InvocationSource = null; try { m_Method = ctx.ResolveMethod(ctx.MainType.TypeInfo, node.MemberName, m_ArgTypes); } catch (KeyNotFoundException) { // resolve a declared extension method // most time-consuming operation, therefore is last checked if(ctx.Options.AllowExtensionMethods) m_Method = ctx.ResolveExtensionMethod(type, node.MemberName, oldArgTypes, m_TypeHints); } } catch (AmbiguousMatchException) { Error(CompilerMessages.TypeMethodInvocationAmbiguous, type, node.MemberName); } catch (KeyNotFoundException) { var msg = node.StaticType != null ? CompilerMessages.TypeStaticMethodNotFound : CompilerMessages.TypeMethodNotFound; Error(msg, type, node.MemberName); } }
public void FieldWithTypeParameters() { var src = "Enumerable::Empty<int>"; var result = new GetMemberNode { StaticType = new TypeSignature("Enumerable"), MemberName = "Empty", TypeHints = { new TypeSignature("int") } }; TestParser(src, result); }
protected bool Equals(GetMemberNode other) { return base.Equals(other) && PointerRequired.Equals(other.PointerRequired) && RefArgumentRequired.Equals(other.RefArgumentRequired) && TypeHints.SequenceEqual(other.TypeHints); }