dotnet/wpf · error · AmbiguousMatchException

throw new AmbiguousMatchException();

Error message

throw new AmbiguousMatchException();

What it means

AttachedPropertyMethodSelector.SelectMethod (a Binder override used by WPF's attached-property method resolution) throws AmbiguousMatchException when no types array is supplied and more than one candidate MethodInfo matches. Without type information it cannot disambiguate between overloads.

Solutions

  1. Provide a types array so overload resolution can disambiguate the candidates
  2. Rename or remove the duplicate overloads so only one method matches the attached-property naming convention
  3. Ensure attached property accessor signatures follow the exact expected pattern (single DependencyObject parameter for getters)
  4. Catch AmbiguousMatchException at the resolution site and apply a tie-breaking rule

Example fix

// before
binder.SelectMethod(bindingAttr, match, null, modifiers);
// after
binder.SelectMethod(bindingAttr, match, new Type[] { typeof(DependencyObject) }, modifiers);
Defensive patterns

Strategy: validation

Validate before calling

if (match == null) throw new ArgumentNullException(nameof(match));
if (types == null && match.Length > 1)
    throw new AmbiguousMatchException("Multiple overloads; provide types array");

Type guard

bool UnambiguousWithoutTypes(MethodBase[] m) => m != null && (m.Length == 1 || m.Select(x => x.GetParameters().Length).Distinct().Count() == 1);

Try / catch

try { var mi = binder.SelectMethod(bindingAttr, match, types, modifiers); }
catch (AmbiguousMatchException) { mi = match.FirstOrDefault(x => x.GetParameters().Length == 1); }

Prevention

When it happens

Trigger: Resolving an attached property getter/setter method where multiple overloads match the method name and the caller passed types == null to SelectMethod.

Common situations: XAML/attached-property processing selecting methods like GetFoo/SetFoo that have overloads; reflection-based property engine lookups without explicit parameter types.

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14). Data as JSON: /api/errors/b14acb8f8da43e65. Report an issue: GitHub.

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/WindowsBase/MS/Internal/ComponentModel/AttachedPropertyMethodSelector.cs:33

    ///     matching to find a match for any parameters that are
    ///     compatible.
    /// </summary>
    internal class AttachedPropertyMethodSelector : Binder 
    {
        /// <summary>
        ///     The only method we implement.  Our goal here is to find a method that best matches the arguments passed.
        ///     We are doing this only with the intent of pulling attached property metadata off of the method.
        ///     If there are ambiguous methods, we simply take the first one as all "Get" methods for an attached
        ///     property should have identical metadata.
        /// </summary>
        public override MethodBase SelectMethod(BindingFlags bindingAttr, MethodBase[] match, Type[] types, ParameterModifier[] modifiers)
        {
            // Short circuit for cases where someone didn't pass in a types array.
            if (types == null) 
            {
                if (match.Length > 1) 
                {
                    throw new AmbiguousMatchException();
                }
                else
                {
                    return match[0];
                }
            }

            for(int idx = 0; idx < match.Length; idx++)
            {
                MethodBase candidate = match[idx];
                ParameterInfo[] parameters = candidate.GetParameters();
                if (ParametersMatch(parameters, types)) 
                {
                    return candidate;
                }
            }

            return null;

View on GitHub (pinned to 81131a70a4)