private void WriteMethod(MethodTarget target, ReferenceLinkDisplayOptions options, XmlWriter writer,
                                 IDictionary <IndexedTemplateTypeReference, TypeReference> dictionary)
        {
            WriteProcedureName(target, options, writer);

            if ((options & ReferenceLinkDisplayOptions.ShowTemplates) > 0)
            {
                // if this is a generic method, write any template params or args
                if (target.TemplateArgs != null && target.TemplateArgs.Count > 0)
                {
                    WriteTemplateArguments(target.TemplateArgs, writer);
                }
            }

            if ((options & ReferenceLinkDisplayOptions.ShowParameters) > 0)
            {
                IList <Parameter> parameters = target.Parameters;

                if (target.ConversionOperator)
                {
                    TypeReference returns = target.returnType;
                    WriteConversionOperatorParameters(parameters, returns, writer, dictionary);
                }
                else
                {
                    WriteMethodParameters(parameters, writer, dictionary);
                }
            }
        }
Пример #2
0
        public static ProcedureTarget ReadProcedureTarget(XmlReader reader)
        {
            if (reader == null || reader.NodeType != XmlNodeType.Element)
            {
                return(null);
            }

            switch (reader.Name)
            {
            case "ProcedureTarget":
                ProcedureTarget procedTarget = new ProcedureTarget();
                procedTarget.ReadXml(reader);
                return(procedTarget);

            case "EventTarget":
                EventTarget eventTarget = new EventTarget();
                eventTarget.ReadXml(reader);
                return(eventTarget);

            case "PropertyTarget":
                PropertyTarget propertyTarget = new PropertyTarget();
                propertyTarget.ReadXml(reader);
                return(propertyTarget);

            case "MethodTarget":
                MethodTarget methodTarget = new MethodTarget();
                methodTarget.ReadXml(reader);
                return(methodTarget);
            }

            return(null);
        }
Пример #3
0
        private void WriteMemberTarget(MemberTarget target, ReferenceLinkDisplayOptions options, XmlWriter writer,
                                       IDictionary <IndexedTemplateTypeReference, TypeReference> dictionary)
        {
            if (target == null)
            {
                throw new ArgumentNullException("target");
            }
            if (writer == null)
            {
                throw new ArgumentNullException("writer");
            }

            if ((options & ReferenceLinkDisplayOptions.ShowContainer) > 0)
            {
                TypeReference type = target.Type;
                WriteType(type, options & ~ReferenceLinkDisplayOptions.ShowContainer, writer);
                if (target.TargetType == TargetType.Method)
                {
                    MethodTarget methodTarget = (MethodTarget)target;
                    if (methodTarget.conversionOperator)
                    {
                        writer.WriteString(" ");
                    }
                    else
                    {
                        WriteSeperator(writer);
                    }
                }
                else
                {
                    WriteSeperator(writer);
                }
            }

            switch (target.TargetType)
            {
            case TargetType.Method:
                // special logic for writing methods
                WriteMethod((MethodTarget)target, options, writer, dictionary);
                return;

            case TargetType.Property:
                // special logic for writing properties
                WriteProperty((PropertyTarget)target, options, writer);
                return;

            case TargetType.Constructor:
                // special logic for writing constructors
                WriteConstructor((ConstructorTarget)target, options, writer);
                return;

            case TargetType.Event:
                // special logic for writing events
                WriteEvent((EventTarget)target, options, writer);
                return;
            }

            // by default, just write name
            writer.WriteString(target.Name);
        }
Пример #4
0
 public void TargetMethodSwitch(MethodTarget methodTarget)
 {
     switch (methodTarget)
     {
     default:
         break;
     }
 }
Пример #5
0
        internal MethodCandidate(MethodTarget target, List <ParameterWrapper> parameters)
        {
            Debug.Assert(target != null);

            _target         = target;
            _parameters     = parameters;
            _narrowingLevel = NarrowingLevel.None;
            parameters.TrimExcess();
        }
Пример #6
0
        public void Method_Converter_Test()
        {
            TargetIdConverter conv   = new TargetIdConverter("M:java.lang.Boolean.booleanValue");
            Target            target = conv.ToTarget();

            Assert.AreEqual(LinkType2.External, target.DefaultLinkType);
            Assert.IsInstanceOf <MethodTarget>(target);

            MethodTarget mt = (MethodTarget)target;

            Assert.AreEqual("booleanValue", mt.Name);
            //Assert.AreEqual("java.lang", tt.Container);
            //Assert.IsNotNull(mt.Type);
            CollectionAssert.IsEmpty(mt.Templates);
            CollectionAssert.IsEmpty(mt.Parameters);
            CollectionAssert.IsEmpty(mt.TemplateArgs);
        }
Пример #7
0
        public void Remove(TDelegate target)
        {
            if (null == target)
            {
                return;
            }

            foreach (Delegate d in (target as Delegate).GetInvocationList())
            {
                MethodTarget mt = _targets.Find(w => Equals(d.Target, w.Reference?.Target) && Equals(d.Method.MethodHandle, w.Method.MethodHandle));

                if (mt != null)
                {
                    _targets.Remove(mt);
                }
            }
        }
        private string GetTemplateName(string templateId, int position)
        {
            Target target = _targets[templateId];

            if (target == null)
            {
                return("UTT");
            }
            else
            {
                TargetType targetType = target.TargetType;
                if (targetType == TargetType.Type || targetType == TargetType.Enumeration)
                {
                    TypeTarget     type      = (TypeTarget)target;
                    IList <string> templates = type.Templates;
                    if (templates.Count > position)
                    {
                        return(templates[position]);
                    }
                    else
                    {
                        return("UTT");
                    }
                }

                if (targetType == TargetType.Method)
                {
                    MethodTarget   method    = (MethodTarget)target;
                    IList <string> templates = method.Templates;
                    if (templates.Count > position)
                    {
                        return(templates[position]);
                    }
                    else
                    {
                        return("UTT");
                    }
                }

                return("UTT");
            }
        }
Пример #9
0
        private MethodTarget ToMethod()
        {
            MethodTarget mt = new MethodTarget();

            mt.Templates    = new string[0];
            mt.Parameters   = new Parameter[0];
            mt.TemplateArgs = new TypeReference[0];

            Match match = MethodPattern.Match(this.targetId);

            if (!match.Success)
            {
                throw new InvalidOperationException(
                          String.Format("TargetId with value '{0}' cannot be parsed as method name.", targetId));
            }

            mt.Name = match.Groups[4].Value;

            // optional namespace
            mt.SetTypeReference(null);            // match.Groups[2];
            return(mt);
        }
        private static MethodTarget CreateMethodTarget(XPathNavigator api)
        {
            MethodTarget target = new MethodTarget();

            target.parameters = CreateParameterList(api);
            target.returnType = CreateReturnType(api);

            target.conversionOperator = (bool)api.Evaluate(apiIsConversionOperatorExpression);

            if ((bool)api.Evaluate(apiIsExplicitImplementationExpression))
            {
                target.explicitlyImplements = CreateMemberReference(
                    api.SelectSingleNode(apiImplementedMembersExpression));
            }

            // this selects templates/template or templates/type, because extension methods can have a mix of generic and specialization
            XPathNodeIterator    templateArgNodes           = api.Select(methodTemplateArgsExpression);
            List <TypeReference> templateArgumentReferences = null;

            if (templateArgNodes != null && templateArgNodes.Count > 0)
            {
                templateArgumentReferences = new List <TypeReference>(templateArgNodes.Count);
                int i = 0;
                foreach (XPathNavigator templateArgNode in templateArgNodes)
                {
                    templateArgumentReferences.Add(CreateTypeReference(templateArgNode));
                    i++;
                }
            }
            target.templateArgs = templateArgumentReferences;

            // get the short name of each template param
            target.templates = GetTemplateNames(api);

            return(target);
        }
Пример #11
0
 public void Setup()
 {
     instance     = new TypeTarget(typeof(TypeTargetTesterClass));
     methodTarget = instance.Methods.Where(x => x.Name == "SomeGenericMethod").FirstOrDefault();
 }
Пример #12
0
            public int CompareTo(MethodTarget other, CallType callType)
            {
                ParameterComparison cmpParams = CompareParameters(this.parameters, other.parameters);
                if (cmpParams == ParameterComparison.First) return 1;
                if (cmpParams == ParameterComparison.Second) return -1;

                int ret = CompareEqualParameters(other);
                if (ret != 0) return ret;

                if (method.IsStatic && !other.method.IsStatic) {
                    return callType == CallType.ImplicitInstance ? -1 : +1;
                } else if (!method.IsStatic && other.method.IsStatic) {
                    return callType == CallType.ImplicitInstance ? +1 : -1;
                }

                return 0;
            }
Пример #13
0
            public int CompareEqualParameters(MethodTarget other)
            {
                // Prefer normal methods over explicit interface implementations
                if (other.method.Method.IsPrivate && !this.method.Method.IsPrivate) return +1;
                if (this.method.Method.IsPrivate && !other.method.Method.IsPrivate) return -1;

                // Prefer non-generic methods over generic methods
                if (method.Method.IsGenericMethod) {
                    if (!other.method.Method.IsGenericMethod) {
                        return -1;
                    } else {
                        //!!! Need to support selecting least generic method here
                        return 0;
                    }
                } else if (other.method.Method.IsGenericMethod) {
                    return +1;
                }

                //prefer methods without out params over those with them
                switch (Compare(returnBuilder.CountOutParams, other.returnBuilder.CountOutParams)) {
                    case 1: return -1;
                    case -1: return 1;
                }

                //prefer methods using earlier conversions rules to later ones
                int maxPriorityThis = FindMaxPriority(this.argBuilders);
                int maxPriorityOther = FindMaxPriority(other.argBuilders);

                if (maxPriorityThis < maxPriorityOther) return +1;
                if (maxPriorityOther < maxPriorityThis) return -1;

                return 0;
            }
Пример #14
0
 private void AddTarget(MethodTarget target)
 {
     int count = target.ParameterCount;
     TargetSet set;
     if (!targetSets.TryGetValue(count, out set)) {
         set = new TargetSet(this, count);
         targetSets[count] = set;
     }
     set.Add(target);
 }
Пример #15
0
 private void AddSimpleTarget(MethodTarget target)
 {
     AddTarget(target);
     if (target.method.IsParamsMethod) {
         ParamsMethodMaker maker = new ParamsMethodMaker(target);
         paramsMakers.Add(maker);
         //MethodTarget paramsTarget = maker.MakeTarget(target.ParameterCount - 1);
         //if (paramsTarget != null) AddTarget(paramsTarget);
     }
 }
Пример #16
0
 private static bool IsBest(MethodTarget candidate, List<MethodTarget> applicableTargets, CallType callType)
 {
     foreach (MethodTarget target in applicableTargets) {
         if (candidate == target) continue;
         if (candidate.CompareTo(target, callType) != +1) return false;
     }
     return true;
 }
Пример #17
0
        /// <summary>
        /// Constrói a novo instancia do ConfigurationMap para o tipo submetido.
        /// Isso irá carrega as informações dos metados contidos no tipo para carregar
        /// o mapeamento do arquivo de configuração <see cref="ConfigurationAttribute"/>.
        /// </summary>
        /// <exception cref="GDA.GDAException"></exception>
        public ConfigurationMap(Type type)
        {
            List <MemberAttributeInfo> memberInfos = LoadMembersConfigurationAttributes(Helper.ReflectionFlags.InstanceCriteria, type);

            foreach (MemberAttributeInfo mai in memberInfos)
            {
                ConfigurationAttribute ca = mai.Attributes[0] as ConfigurationAttribute;
                switch (mai.MemberInfo.MemberType)
                {
                case MemberTypes.Method:
                    MethodTarget target = null;
                    if (instanceOverloads.ContainsKey(ca.XmlNodePath))
                    {
                        target = instanceOverloads[ca.XmlNodePath] as MethodTarget;
                    }
                    if (target != null)
                    {
                        target.AddCallbackMethod(mai.MemberInfo as MethodInfo, ca.RequiredParameters);
                    }
                    else
                    {
                        target = new MethodTarget(ca, mai.MemberInfo as MethodInfo);
                        instanceTargets.Add(target);
                        instanceOverloads[ca.XmlNodePath] = target;
                    }
                    break;

                case MemberTypes.Field:
                    instanceTargets.Add(new FieldTarget(ca, mai.MemberInfo as FieldInfo));
                    break;

                case MemberTypes.Property:
                    instanceTargets.Add(new PropertyTarget(ca, mai.MemberInfo as PropertyInfo));
                    break;

                default:
                    throw new GDAException("Unknown configuration target type for member {0} on class {1}.", mai.MemberInfo.Name, type);
                }
            }
            memberInfos = LoadMembersConfigurationAttributes(Helper.ReflectionFlags.StaticCriteria, type);
            foreach (MemberAttributeInfo mai in memberInfos)
            {
                ConfigurationAttribute ca = mai.Attributes[0] as ConfigurationAttribute;
                switch (mai.MemberInfo.MemberType)
                {
                case MemberTypes.Method:
                    MethodTarget target = null;
                    if (staticOverloads.ContainsKey(ca.XmlNodePath))
                    {
                        target = staticOverloads[ca.XmlNodePath] as MethodTarget;
                    }
                    if (target != null)
                    {
                        target.AddCallbackMethod(mai.MemberInfo as MethodInfo, ca.RequiredParameters);
                    }
                    else
                    {
                        target = new MethodTarget(ca, mai.MemberInfo as MethodInfo);
                        staticTargets.Add(target);
                        staticOverloads[ca.XmlNodePath] = target;
                    }
                    break;

                case MemberTypes.Field:
                    staticTargets.Add(new FieldTarget(ca, mai.MemberInfo as FieldInfo));
                    break;

                case MemberTypes.Property:
                    staticTargets.Add(new PropertyTarget(ca, mai.MemberInfo as PropertyInfo));
                    break;

                default:
                    throw new GDAException("Unknown configuration target type for member {0} on class {1}.", mai.MemberInfo.Name, type);
                }
            }
        }
Пример #18
0
 public ParamsMethodMaker(MethodTarget baseTarget)
 {
     this.baseTarget = baseTarget;
 }
Пример #19
0
        // component logic

        public override void Apply(XmlDocument document, string key)
        {
            // XmlNodeList link_nodes = document.SelectNodes("//referenceLink");
            XPathNodeIterator linkIterator = document.CreateNavigator().Select(referenceLinkExpression);

            XPathNavigator[] linkNodes = BuildComponentUtilities.ConvertNodeIteratorToArray(linkIterator);

            foreach (XPathNavigator linkNode in linkNodes)
            {
                // extract link information
                ReferenceLinkInfo2 link = ReferenceLinkInfo2.Create(linkNode);

                if (link == null)
                {
                    WriteMessage(MessageLevel.Warn, "Invalid referenceLink element.");
                }
                else
                {
                    // determine target, link type, and display options
                    string         targetId = link.Target;
                    DisplayOptions options  = link.DisplayOptions;
                    LinkType2      type     = LinkType2.None;

                    Target target = GetTarget(targetId);
                    if (target == null)
                    {
                        // no such target known; set link type to none and warn
                        type = LinkType2.None;
                        WriteMessage(MessageLevel.Warn, String.Format("Unknown reference link target '{0}'.", targetId));
                    }
                    else
                    {
                        // if overload is prefered and found, change targetId and make link options hide parameters
                        if (link.PreferOverload)
                        {
                            bool isConversionOperator = false;

                            MethodTarget method = target as MethodTarget;
                            if (method != null)
                            {
                                isConversionOperator = method.conversionOperator;
                            }

                            MemberTarget member = target as MemberTarget;

                            // if conversion operator is found, always link to individual topic.
                            if ((member != null) && (!String.IsNullOrEmpty(member.OverloadId)) && !isConversionOperator)
                            {
                                Target overloadTarget = targets[member.OverloadId];
                                if (overloadTarget != null)
                                {
                                    target   = overloadTarget;
                                    targetId = overloadTarget.Id;
                                }
                            }

                            // if individual conversion operator is found, always display parameters.
                            if (isConversionOperator && member != null && (!string.IsNullOrEmpty(member.OverloadId)))
                            {
                                options = options | DisplayOptions.ShowParameters;
                            }
                            else
                            {
                                options = options & ~DisplayOptions.ShowParameters;
                            }
                        }

                        // get stored link type
                        type = target.DefaultLinkType;

                        // if link type is local or index, determine which
                        if (type == LinkType2.LocalOrIndex)
                        {
                            if ((key != null) && targets.Contains(key) && (target.Container == targets[key].Container))
                            {
                                type = LinkType2.Local;
                            }
                            else
                            {
                                type = LinkType2.Index;
                            }
                        }
                    }

                    // links to this page are not live
                    if (targetId == key)
                    {
                        type = LinkType2.Self;
                    }
                    else if ((target != null) && (key != null) && targets.Contains(key) && (target.File == targets[key].File))
                    {
                        type = LinkType2.Self;
                    }

                    // get msdn or external endpoint, if needed
                    string externalUrl = null;
                    if (type == LinkType2.Msdn || type == LinkType2.External)
                    {
                        externalUrl = ResolveExternalUrl(targetId, type);
                        if (String.IsNullOrEmpty(externalUrl))
                        {
                            type = LinkType2.None;
                        }
                    }

                    // write opening link tag and target info
                    XmlWriter writer = linkNode.InsertAfter();
                    switch (type)
                    {
                    case LinkType2.None:
                        writer.WriteStartElement("span");
                        writer.WriteAttributeString("class", "nolink");
                        break;

                    case LinkType2.Self:
                        writer.WriteStartElement("span");
                        writer.WriteAttributeString("class", "selflink");
                        break;

                    case LinkType2.Local:
                        // format link with prefix and/or postfix
                        string href = String.Format(hrefFormat, target.File);

                        // make link relative, if we have a baseUrl
                        if (baseUrl != null)
                        {
                            href = BuildComponentUtilities.GetRelativePath(href, BuildComponentUtilities.EvalXPathExpr(document, baseUrl, "key", key));
                        }

                        writer.WriteStartElement("a");
                        writer.WriteAttributeString("href", href);
                        break;

                    case LinkType2.Index:
                        writer.WriteStartElement("mshelp", "link", "http://msdn.microsoft.com/mshelp");
                        writer.WriteAttributeString("keywords", targetId);
                        writer.WriteAttributeString("tabindex", "0");
                        break;

                    case LinkType2.Msdn:
                    case LinkType2.External:
                        writer.WriteStartElement("a");
                        writer.WriteAttributeString("href", externalUrl);
                        writer.WriteAttributeString("target", linkTarget);
                        break;
                    }

                    // write the link text
                    if (String.IsNullOrEmpty(link.DisplayTarget))
                    {
                        if (link.Contents == null)
                        {
                            if (target != null)
                            {
                                resolver.WriteTarget(target, options, writer);
                            }
                            else
                            {
                                //Console.WriteLine("Attemting to create reference");
                                Reference reference = TextReferenceUtilities.CreateReference(targetId);
                                //Console.WriteLine("Returned");
                                if (reference is InvalidReference)
                                {
                                    WriteMessage(MessageLevel.Warn, String.Format("Invalid reference link target '{0}'.", targetId));
                                }
                                resolver.WriteReference(reference, options, writer);
                            }
                        }
                        else
                        {
                            // write contents to writer
                            link.Contents.WriteSubtree(writer);
                        }
                    }
                    else
                    {
                        //Console.WriteLine("Display target = {0}", link.DisplayTarget);
                        if ((String.Compare(link.DisplayTarget, "content", true) == 0) && (link.Contents != null))
                        {
                            // Use the contents as an XML representation of the display target

                            //Console.WriteLine(link.Contents.NodeType);
                            Reference reference = XmlTargetCollectionUtilities.CreateReference(link.Contents);
                            //Console.WriteLine(reference.GetType().FullName);
                            resolver.WriteReference(reference, options, writer);
                        }
                        if ((String.Compare(link.DisplayTarget, "format", true) == 0) && (link.Contents != null))
                        {
                            // Use the contents as a format string for the display target

                            string format = link.Contents.OuterXml;
                            //Console.WriteLine("format = {0}", format);

                            string       input     = null;
                            StringWriter textStore = new StringWriter();
                            try {
                                XmlWriterSettings settings = new XmlWriterSettings();
                                settings.ConformanceLevel = ConformanceLevel.Fragment;

                                XmlWriter xmlStore = XmlWriter.Create(textStore, settings);
                                try {
                                    if (target != null)
                                    {
                                        resolver.WriteTarget(target, options, xmlStore);
                                    }
                                    else
                                    {
                                        Reference reference = TextReferenceUtilities.CreateReference(targetId);
                                        resolver.WriteReference(reference, options, xmlStore);
                                    }
                                } finally {
                                    xmlStore.Close();
                                }
                                input = textStore.ToString();
                            } finally {
                                textStore.Close();
                            }
                            //Console.WriteLine("input = {0}", input);

                            string output = String.Format(format, input);
                            //Console.WriteLine("output = {0}", output);

                            XmlDocumentFragment fragment = document.CreateDocumentFragment();
                            fragment.InnerXml = output;
                            fragment.WriteTo(writer);

                            //writer.WriteRaw(output);
                        }
                        else if ((String.Compare(link.DisplayTarget, "extension", true) == 0) && (link.Contents != null))
                        {
                            Reference extMethodReference = XmlTargetCollectionUtilities.CreateExtensionMethodReference(link.Contents);
                            resolver.WriteReference(extMethodReference, options, writer);
                        }
                        else
                        {
                            // Use the display target value as a CER for the display target

                            TextReferenceUtilities.SetGenericContext(key);
                            Reference reference = TextReferenceUtilities.CreateReference(link.DisplayTarget);
                            //Console.WriteLine("Reference is {0}", reference.GetType().FullName);
                            resolver.WriteReference(reference, options, writer);
                        }
                    }

                    // write the closing link tag
                    writer.WriteEndElement();
                    writer.Close();
                }

                // delete the original tag
                linkNode.DeleteSelf();
            }
        }
Пример #20
0
        private void ProcessReferenceLink(XmlDocument document, string key)
        {
            XPathNodeIterator linkIterator = document.CreateNavigator().Select(
                referenceLinkExpression);

            if (linkIterator == null || linkIterator.Count == 0)
            {
                return;
            }

            XPathNavigator[] linkNodes = BuildComponentUtilities.ConvertNodeIteratorToArray(linkIterator);

            foreach (XPathNavigator linkNode in linkNodes)
            {
                // extract link information
                ReferenceLinkInfo link = ReferenceLinkInfo.Create(linkNode);

                if (link == null)
                {
                    this.WriteMessage(MessageLevel.Warn,
                                      "Invalid referenceLink element.");
#if DEBUG
                    this.WriteMessage(MessageLevel.Warn, linkNode.OuterXml);
#endif
                }
                else
                {
                    // determine target, link type, and display options
                    string targetId = link.Target;
                    ReferenceLinkDisplayOptions options = link.DisplayOptions;
                    ReferenceLinkType           type    = ReferenceLinkType.None;

                    Target target = _targets[targetId];
                    if (target == null)
                    {
                        if (_hasTopicLinks && _targetController[targetId] != null)
                        {
                            this.ProcessConceptualLink(linkNode, key);

                            // delete the original tag
                            linkNode.DeleteSelf();

                            continue;
                        }
                        else
                        {
                            // no such target known; set link type to none and warn
                            type = ReferenceLinkType.None;
                            this.WriteMessage(MessageLevel.Warn, String.Format(
                                                  "Unknown reference link target '{0}'.", targetId));
                        }
                    }
                    else
                    {
                        // if overload is preferred and found, change targetId and make link options hide parameters
                        if (link.PreferOverload)
                        {
                            bool isConversionOperator = false;

                            TargetType targetType = target.TargetType;

                            MemberTarget member = null;
                            if (targetType == TargetType.Method)
                            {
                                MethodTarget method = (MethodTarget)target;
                                isConversionOperator = method.ConversionOperator;
                                member = method;  // a method is a member...
                            }
                            else if (targetType == TargetType.Member || targetType == TargetType.Constructor ||
                                     targetType == TargetType.Procedure || targetType == TargetType.Event ||
                                     targetType == TargetType.Property)
                            {
                                member = (MemberTarget)target;
                            }

                            // if conversion operator is found, always link to individual topic.
                            if ((member != null) && (!String.IsNullOrEmpty(member.OverloadId)) && !isConversionOperator)
                            {
                                Target overloadTarget = _targets[member.OverloadId];
                                if (overloadTarget != null)
                                {
                                    target   = overloadTarget;
                                    targetId = overloadTarget.Id;
                                }
                            }

                            // if individual conversion operator is found, always display parameters.
                            if (isConversionOperator && member != null &&
                                (!string.IsNullOrEmpty(member.OverloadId)))
                            {
                                options = options | ReferenceLinkDisplayOptions.ShowParameters;
                            }
                            else
                            {
                                options = options & ~ReferenceLinkDisplayOptions.ShowParameters;
                            }
                        }

                        // get stored link type
                        type = _targets.RecentLinkTypeIsMsdn ?
                               _targets.RecentLinkType : target.LinkType;

                        // if link type is local or index, determine which
                        if (type == ReferenceLinkType.LocalOrIndex)
                        {
                            if ((key != null) && _targets.Contains(key) &&
                                (target.Container == _targets[key].Container))
                            {
                                type = ReferenceLinkType.Local;
                            }
                            else
                            {
                                type = ReferenceLinkType.Index;
                            }
                        }
                    }

                    // links to this page are not live
                    if (targetId == key)
                    {
                        type = ReferenceLinkType.Self;
                    }
                    else if ((target != null) && (key != null) && _targets.Contains(key) &&
                             (target.File == _targets[key].File))
                    {
                        type = ReferenceLinkType.Self;
                    }

                    // get msdn endpoint, if needed
                    string msdnUrl = null;
                    if (type == ReferenceLinkType.Msdn)
                    {
                        if ((_msdnResolver == null) || (_msdnResolver.IsDisabled))
                        {
                            // no msdn resolver
                        }
                        else
                        {
                            msdnUrl = _msdnResolver[targetId];
                            if (String.IsNullOrEmpty(msdnUrl))
                            {
                                WriteMessage(MessageLevel.Warn, String.Format(
                                                 "MSDN URL not found for target '{0}'.", targetId));
                            }
                        }

                        if (String.IsNullOrEmpty(msdnUrl))
                        {
                            type = ReferenceLinkType.None;
                        }
                    }

                    // write opening link tag and target info
                    XmlWriter writer = linkNode.InsertAfter();
                    switch (type)
                    {
                    case ReferenceLinkType.None:
                        writer.WriteStartElement("span");
                        writer.WriteAttributeString("class", "nolink");
                        break;

                    case ReferenceLinkType.Self:
                        writer.WriteStartElement("span");
                        writer.WriteAttributeString("class", "selflink");
                        break;

                    case ReferenceLinkType.Local:
                        // format link with prefix and/or postfix
                        string href = String.Format(_hrefFormat, target.File);

                        // make link relative, if we have a baseUrl
                        if (_baseUrl != null)
                        {
                            href = BuildComponentUtilities.GetRelativePath(href,
                                                                           BuildComponentUtilities.EvalXPathExpr(document, _baseUrl, "key", key));
                        }

                        writer.WriteStartElement("a");
                        writer.WriteAttributeString("href", href);
                        break;

                    case ReferenceLinkType.Index:
                        writer.WriteStartElement("mshelp", "link", "http://msdn.microsoft.com/mshelp");
                        writer.WriteAttributeString("keywords", targetId);
                        writer.WriteAttributeString("tabindex", "0");
                        break;

                    case ReferenceLinkType.Msdn:
                        writer.WriteStartElement("a");
                        writer.WriteAttributeString("href", msdnUrl);
                        writer.WriteAttributeString("target", _linkTarget);
                        break;

                    case ReferenceLinkType.Id:
                        string xhelp = String.Format("ms-xhelp://?Id={0}", targetId);
                        xhelp = xhelp.Replace("#", "%23");
                        writer.WriteStartElement("a");
                        writer.WriteAttributeString("href", xhelp);
                        break;
                    }

                    // write the link text
                    if (String.IsNullOrEmpty(link.DisplayTarget))
                    {
                        if (link.Contents == null)
                        {
                            if (target != null)
                            {
                                _linkResolver.WriteTarget(target, options, writer);
                            }
                            else
                            {
                                Reference reference = ReferenceTextUtilities.CreateReference(targetId);

                                if (reference.ReferenceType == ReferenceType.Invalid)
                                {
                                    WriteMessage(MessageLevel.Warn, String.Format(
                                                     "Invalid reference link target '{0}'.", targetId));
                                }

                                _linkResolver.WriteReference(reference, options, writer);
                            }
                        }
                        else
                        {
                            // write contents to writer
                            link.Contents.WriteSubtree(writer);
                        }
                    }
                    else
                    {
                        if ((String.Compare(link.DisplayTarget, "content", true) == 0) && (link.Contents != null))
                        {
                            // Use the contents as an XML representation of the display target
                            Reference reference = TargetCollectionXmlUtilities.CreateReference(link.Contents);

                            _linkResolver.WriteReference(reference, options, writer);
                        }
                        if ((String.Compare(link.DisplayTarget, "format", true) == 0) && (link.Contents != null))
                        {
                            // Use the contents as a format string for the display target
                            string format = link.Contents.OuterXml;

                            string       input     = null;
                            StringWriter textStore = new StringWriter();
                            try
                            {
                                XmlWriter xmlStore = XmlWriter.Create(textStore, _writerSettings);
                                try
                                {
                                    if (target != null)
                                    {
                                        _linkResolver.WriteTarget(target, options, xmlStore);
                                    }
                                    else
                                    {
                                        Reference reference = ReferenceTextUtilities.CreateReference(targetId);
                                        _linkResolver.WriteReference(reference, options, xmlStore);
                                    }
                                }
                                finally
                                {
                                    xmlStore.Close();
                                }
                                input = textStore.ToString();
                            }
                            finally
                            {
                                textStore.Close();
                            }

                            string output = String.Format(format, input);

                            XmlDocumentFragment fragment = document.CreateDocumentFragment();
                            fragment.InnerXml = output;
                            fragment.WriteTo(writer);

                            //writer.WriteRaw(output);
                        }
                        else if ((String.Compare(link.DisplayTarget, "extension", true) == 0) && (link.Contents != null))
                        {
                            Reference extMethodReference = TargetCollectionXmlUtilities.CreateExtensionMethodReference(link.Contents);
                            _linkResolver.WriteReference(extMethodReference, options, writer);
                        }
                        else
                        {
                            // Use the display target value as a CER for the display target

                            ReferenceTextUtilities.SetGenericContext(key);
                            Reference reference = ReferenceTextUtilities.CreateReference(link.DisplayTarget);

                            _linkResolver.WriteReference(reference, options, writer);
                        }
                    }

                    // write the closing link tag
                    writer.WriteEndElement();
                    writer.Close();
                }

                // delete the original tag
                linkNode.DeleteSelf();
            }
        }
Пример #21
0
 public MethodCandidate(MethodCandidate previous, NarrowingLevel narrowingLevel)
 {
     this._target     = previous.Target;
     this._parameters = previous._parameters;
     _narrowingLevel  = narrowingLevel;
 }
Пример #22
0
 public TargetHolder(MethodTarget target)
 {
     _target = target;
 }
Пример #23
0
        public static Target ReadTarget(XmlReader reader)
        {
            if (reader == null || reader.NodeType != XmlNodeType.Element)
            {
                return(null);
            }

            switch (reader.Name)
            {
            case "Target":
                Target target = new Target();
                target.ReadXml(reader);
                return(target);

            case "NamespaceTarget":
                NamespaceTarget namespaceTarget = new NamespaceTarget();
                namespaceTarget.ReadXml(reader);
                return(namespaceTarget);

            case "TypeTarget":
                TypeTarget typeTarget = new TypeTarget();
                typeTarget.ReadXml(reader);
                return(typeTarget);

            case "EnumerationTarget":
                EnumerationTarget enumTarget = new EnumerationTarget();
                enumTarget.ReadXml(reader);
                return(enumTarget);

            case "MemberTarget":
                MemberTarget memberTarget = new MemberTarget();
                memberTarget.ReadXml(reader);
                return(memberTarget);

            case "ConstructorTarget":
                ConstructorTarget constructorTarget = new ConstructorTarget();
                constructorTarget.ReadXml(reader);
                return(constructorTarget);

            case "ProcedureTarget":
                ProcedureTarget procedTarget = new ProcedureTarget();
                procedTarget.ReadXml(reader);
                return(procedTarget);

            case "EventTarget":
                EventTarget eventTarget = new EventTarget();
                eventTarget.ReadXml(reader);
                return(eventTarget);

            case "PropertyTarget":
                PropertyTarget propertyTarget = new PropertyTarget();
                propertyTarget.ReadXml(reader);
                return(propertyTarget);

            case "MethodTarget":
                MethodTarget methodTarget = new MethodTarget();
                methodTarget.ReadXml(reader);
                return(methodTarget);
            }

            return(null);
        }
Пример #24
0
 public void Add(MethodTarget target)
 {
     for (int i = 0; i < targets.Count; i++) {
         if (CompareParameters(targets[i].parameters, target.parameters) == ParameterComparison.Same) {
             switch (targets[i].CompareEqualParameters(target)) {
                 case -1:
                     // the new method is strictly better than the existing one so remove the existing one
                     targets.RemoveAt(i);
                     i -= 1; // modify the index since we removed a target from the list
                     break;
                 case +1:
                     // the new method is strictly worse than the existing one so skip it
                     return;
                 case 0:
                     // the two methods are identical ignoring CallType so list a conflict
                     hasConflict = true;
                     break;
             }
         }
     }
     targets.Add(target);
 }
Пример #25
0
        /// <inheritdoc />
        public override void Apply(XmlDocument document, string key)
        {
            Target target = null, keyTarget;
            string msdnUrl = null;

            foreach (XPathNavigator linkNode in document.CreateNavigator().Select(referenceLinkExpression).ToArray())
            {
                // Extract link information
                ReferenceLinkInfo link = new ReferenceLinkInfo(linkNode);

                // Determine target, link type, and display options
                string            targetId = link.Target;
                DisplayOptions    options  = link.DisplayOptions;
                ReferenceLinkType type     = ReferenceLinkType.None;

                if (String.IsNullOrWhiteSpace(targetId))
                {
                    this.WriteMessage(key, MessageLevel.Warn, "The target attribute is missing or has no " +
                                      "value.  You have most likely omitted a cref attribute or left it blank on an XML " +
                                      "comments element such as see, seealso, or exception.");
                    continue;
                }

                bool targetFound = targets.TryGetValue(targetId, out target, out type);

                // If it's an overload ID that wasn't found, it's possible that the overloads got excluded.
                // As such, see if we can find a match for a method using the same ID regardless of any
                // parameters.
                if (!targetFound && targetId.StartsWith("Overload:", StringComparison.Ordinal) ||
                    targetId.StartsWith("O:", StringComparison.Ordinal))
                {
                    string methodTargetId = "M:" + targetId.Substring(targetId.IndexOf(':') + 1);
                    methodTargetId = targets.Keys.FirstOrDefault(k => k.StartsWith(methodTargetId));

                    if (methodTargetId != null)
                    {
                        targetId    = methodTargetId;
                        targetFound = targets.TryGetValue(targetId, out target, out type);
                        options    |= DisplayOptions.ShowParameters;

                        // Don't use the content as it may not be appropriate for the method.  The default is
                        // "{0} Overload" which no longer applies.  Instead we'll show the method name and
                        // its parameters.
                        if (link.DisplayTarget.Equals("format", StringComparison.OrdinalIgnoreCase))
                        {
                            link.DisplayTarget = null;
                            link.Contents      = null;
                        }
                    }
                }

                // If not found and it starts with "System." or "Microsoft." we'll go with the assumption that
                // it's part of a Microsoft class library that is not part of the core framework but does have
                // documentation available on MSDN.  Worst case it doesn't and we get an unresolved link warning
                // instead of an unknown reference target warning.
                if (!targetFound && ((targetId.Length > 9 && targetId.Substring(2).StartsWith("System.",
                                                                                              StringComparison.Ordinal)) || (targetId.Length > 12 && targetId.Substring(2).StartsWith(
                                                                                                                                 "Microsoft.", StringComparison.Ordinal))))
                {
                    // Use the same link type as a core framework class
                    targetFound = targets.TryGetValue("T:System.Object", out target, out type);

                    // We don't have a target in this case so links to overloads pages won't work.  Also note
                    // that the link text will be generated from the ID which shouldn't make much of a difference
                    // in most cases.  If either case is an issue, the Additional Reference Links SHFB plug-in
                    // can be used to generate valid link target data.
                    target = null;
                }

                if (!targetFound)
                {
                    // If not being rendered as a link, don't report a warning
                    if (link.RenderAsLink && targetId != key)
                    {
                        this.WriteMessage(key, MessageLevel.Warn, "Unknown reference link target '{0}'.", targetId);
                    }

                    // !EFW - Turn off the Show Parameters option for unresolved elements except methods.  If
                    // not, it outputs an empty "()" after the member name which looks odd.
                    if (targetId[0] != 'M')
                    {
                        options &= ~DisplayOptions.ShowParameters;
                    }
                }
                else
                {
                    // If overload is preferred and found, change targetId and make link options hide parameters
                    if (link.PreferOverload && target != null)
                    {
                        bool isConversionOperator = false;

                        MethodTarget method = target as MethodTarget;

                        if (method != null)
                        {
                            isConversionOperator = method.IsConversionOperator;
                        }

                        MemberTarget member = target as MemberTarget;

                        // If conversion operator is found, always link to individual topic
                        if (member != null && !String.IsNullOrEmpty(member.OverloadId) && !isConversionOperator)
                        {
                            Target overloadTarget = targets[member.OverloadId];

                            if (overloadTarget != null)
                            {
                                target   = overloadTarget;
                                targetId = overloadTarget.Id;
                            }
                        }

                        // If individual conversion operator is found, always display parameters
                        if (isConversionOperator && member != null && !String.IsNullOrEmpty(member.OverloadId))
                        {
                            options = options | DisplayOptions.ShowParameters;
                        }
                        else
                        {
                            options = options & ~DisplayOptions.ShowParameters;
                        }
                    }
                }

                // Suppress the link if so requested.  Links to this page are not live.
                if (!link.RenderAsLink)
                {
                    type = ReferenceLinkType.None;
                }
                else
                if (targetId == key)
                {
                    type = ReferenceLinkType.Self;
                }
                else
                if (target != null && targets.TryGetValue(key, out keyTarget) && target.File == keyTarget.File)
                {
                    type = ReferenceLinkType.Self;
                }

                // !EFW - Redirect enumeration fields to the containing enumerated type so that we
                // get a valid link target.  Enum fields don't have a topic to themselves.
                if (type != ReferenceLinkType.None && type != ReferenceLinkType.Self && type != ReferenceLinkType.Local &&
                    targetId.StartsWith("F:", StringComparison.OrdinalIgnoreCase))
                {
                    MemberTarget member = target as MemberTarget;

                    if (member != null)
                    {
                        SimpleTypeReference typeRef = member.ContainingType as SimpleTypeReference;

                        if (typeRef != null && targets[typeRef.Id] is EnumerationTarget)
                        {
                            targetId = typeRef.Id;
                        }
                    }
                }

                // Get MSDN endpoint if needed
                if (type == ReferenceLinkType.Msdn)
                {
                    if (msdnResolver != null && !msdnResolver.IsDisabled)
                    {
                        msdnUrl = msdnResolver.GetMsdnUrl(targetId);

                        if (String.IsNullOrEmpty(msdnUrl))
                        {
                            // If the web service failed, report the reason
                            if (msdnResolver.IsDisabled)
                            {
                                this.WriteMessage(key, MessageLevel.Warn, "MSDN web service failed.  No " +
                                                  "further look ups will be performed for this build.\r\nReason: {0}",
                                                  msdnResolver.DisabledReason);
                            }
                            else
                            {
                                this.WriteMessage(key, MessageLevel.Warn, "MSDN URL not found for target '{0}'.",
                                                  targetId);
                            }

                            type = ReferenceLinkType.None;
                        }
                    }
                    else
                    {
                        type = ReferenceLinkType.None;
                    }
                }

                // Write opening link tag and target info
                XmlWriter writer = linkNode.InsertAfter();

                switch (type)
                {
                case ReferenceLinkType.None:
                    writer.WriteStartElement("span");

                    // If the link was intentionally suppressed, write it out as an identifier (i.e. links
                    // in the syntax section).
                    if (link.RenderAsLink)
                    {
                        writer.WriteAttributeString("class", "nolink");
                    }
                    else
                    {
                        writer.WriteAttributeString("class", "identifier");
                    }
                    break;

                case ReferenceLinkType.Self:
                    writer.WriteStartElement("span");
                    writer.WriteAttributeString("class", "selflink");
                    break;

                case ReferenceLinkType.Local:
                    // Format link with prefix and/or postfix
                    string href = String.Format(CultureInfo.InvariantCulture, hrefFormat, target.File);

                    // Make link relative, if we have a baseUrl
                    if (baseUrl != null)
                    {
                        href = href.GetRelativePath(document.EvalXPathExpr(baseUrl, "key", key));
                    }

                    writer.WriteStartElement("a");
                    writer.WriteAttributeString("href", href);
                    break;

                case ReferenceLinkType.Msdn:
                    writer.WriteStartElement("a");
                    writer.WriteAttributeString("href", msdnUrl);
                    writer.WriteAttributeString("target", linkTarget);
                    break;

                case ReferenceLinkType.Id:
                    writer.WriteStartElement("a");
                    writer.WriteAttributeString("href", ("ms-xhelp:///?Id=" + targetId).Replace("#", "%23"));
                    break;
                }

                // Write the link text
                if (String.IsNullOrEmpty(link.DisplayTarget))
                {
                    if (link.Contents == null)
                    {
                        if (target != null)
                        {
                            resolver.WriteTarget(target, options, writer);
                        }
                        else
                        {
                            Reference reference = TextReferenceUtilities.CreateReference(targetId);

                            if (reference is InvalidReference)
                            {
                                this.WriteMessage(key, MessageLevel.Warn,
                                                  "Invalid reference link target '{0}'.", targetId);
                            }

                            resolver.WriteReference(reference, options, writer);
                        }
                    }
                    else
                    {
                        do
                        {
                            link.Contents.WriteSubtree(writer);
                        } while(link.Contents.MoveToNext());
                    }
                }
                else
                {
                    if (link.DisplayTarget.Equals("content", StringComparison.OrdinalIgnoreCase) &&
                        link.Contents != null)
                    {
                        // Use the contents as an XML representation of the display target
                        Reference reference = XmlTargetDictionaryUtilities.CreateReference(link.Contents);
                        resolver.WriteReference(reference, options, writer);
                    }

                    if (link.DisplayTarget.Equals("format", StringComparison.OrdinalIgnoreCase) &&
                        link.Contents != null)
                    {
                        // Use the contents as a format string for the display target
                        string format = link.Contents.OuterXml;
                        string input  = null;

                        using (StringWriter textStore = new StringWriter(CultureInfo.InvariantCulture))
                        {
                            XmlWriterSettings settings = new XmlWriterSettings();
                            settings.ConformanceLevel = ConformanceLevel.Fragment;

                            using (XmlWriter xmlStore = XmlWriter.Create(textStore, settings))
                            {
                                if (target != null)
                                {
                                    resolver.WriteTarget(target, options, xmlStore);
                                }
                                else
                                {
                                    Reference reference = TextReferenceUtilities.CreateReference(targetId);
                                    resolver.WriteReference(reference, options, xmlStore);
                                }
                            }

                            input = textStore.ToString();
                        }

                        string output = String.Format(CultureInfo.InvariantCulture, format, input);

                        XmlDocumentFragment fragment = document.CreateDocumentFragment();
                        fragment.InnerXml = output;
                        fragment.WriteTo(writer);
                    }
                    else if (link.DisplayTarget.Equals("extension", StringComparison.OrdinalIgnoreCase) &&
                             link.Contents != null)
                    {
                        Reference extMethodReference = XmlTargetDictionaryUtilities.CreateExtensionMethodReference(link.Contents);
                        resolver.WriteReference(extMethodReference, options, writer);
                    }
                    else
                    {
                        // Use the display target value as a CER for the display target
                        TextReferenceUtilities.SetGenericContext(key);
                        Reference reference = TextReferenceUtilities.CreateReference(link.DisplayTarget);
                        resolver.WriteReference(reference, options, writer);
                    }
                }

                // Write the closing link tag
                writer.WriteEndElement();
                writer.Close();

                // Delete the original tag
                linkNode.DeleteSelf();
            }
        }
Пример #26
0
        internal static Candidate CompareEquivalentParameters(MethodTarget one, MethodTarget two) {
            // Prefer normal methods over explicit interface implementations
            if (two.Method.IsPrivate && !one.Method.IsPrivate) return Candidate.One;
            if (one.Method.IsPrivate && !two.Method.IsPrivate) return Candidate.Two;

            // Prefer non-generic methods over generic methods
            if (one.Method.IsGenericMethod) {
                if (!two.Method.IsGenericMethod) {
                    return Candidate.Two;
                } else {
                    //!!! Need to support selecting least generic method here
                    return Candidate.Equivalent;
                }
            } else if (two.Method.IsGenericMethod) {
                return Candidate.One;
            }

            //prefer methods without out params over those with them
            switch (Compare(one._returnBuilder.CountOutParams, two._returnBuilder.CountOutParams)) {
                case 1: return Candidate.Two;
                case -1: return Candidate.One;
            }

            //prefer methods using earlier conversions rules to later ones            
            for (int i = Int32.MaxValue; i >= 0; ) {
                int maxPriorityThis = FindMaxPriority(one._argBuilders, i);
                int maxPriorityOther = FindMaxPriority(two._argBuilders, i);

                if (maxPriorityThis < maxPriorityOther) return Candidate.One;
                if (maxPriorityOther < maxPriorityThis) return Candidate.Two;

                i = maxPriorityThis - 1;
            }

            return Candidate.Equivalent;
        }