dotnet/wpf · error · ArgumentException
SR.NonclientClassnameCannotBeUsedWithFlagsOrImagename
Error message
SR.NonclientClassnameCannotBeUsedWithFlagsOrImagename
What it means
AddToProxyDescriptionTable special-cases pseudo-proxy class names (non-client-area proxies like scroll bars); for these, providing an ImageName or non-zero Flags is rejected with ArgumentException(SR.NonclientClassnameCannotBeUsedWithFlagsOrImagename). Pseudo-proxy class names must be matched solely by class name.
Solutions
- Set ImageName to null and Flags to 0 (ClientSideProviderMatchFlags.None) for the provider description targeting the pseudo-proxy class name.
- If you need ImageName/Flags matching, use a different ClassName that is not one of the reserved pseudo-proxy class names.
- Review your ClientSideProviderDescription table and separate nonclient pseudo-proxy registrations from ordinary hwnd proxy registrations.
Example fix
// before new ClientSideProviderDescription(Factory, @"C:\my.dll", "#32768", ClientSideProviderMatchFlags.Substring) // after new ClientSideProviderDescription(Factory, null, "#32768", ClientSideProviderMatchFlags.None)
Defensive patterns
Strategy: validation
Validate before calling
bool isPseudoProxy = pseudoClassNames.Contains(desc.ClassName);
if (isPseudoProxy && (desc.ImageName != null || desc.Flags != 0)) throw new ArgumentException("Pseudo-proxy class names cannot use ImageName/Flags"); Type guard
static bool IsValidProxyDescription(ClientSideProviderDescription d) => !(reservedPseudoProxyClassNames.Contains(d.ClassName) && (d.ImageName != null || d.Flags != 0));
Try / catch
try { ClientSettings.RegisterClientSideProviders(table); }
catch (ArgumentException ex) { log.Error($"Invalid provider description: {ex.Message}"); } Prevention
- Register pseudo-proxy (nonclient) class names with ImageName = null and Flags = 0.
- Keep reserved class names in a constant list and validate descriptions before registration.
- Never reuse a generic provider entry (with image/flags filters) for nonclient class names.
When it happens
Trigger: Calling ClientSettings.RegisterClientSideProviders / SetProxyDescriptionTable with a ClientSideProviderDescription whose ClassName equals one of the known pseudo-proxy class names (e.g., nonclient class names) while ImageName is non-null or Flags != 0.
Common situations: Developers writing custom proxies for nonclient UI (scroll bars, title bars) who copy a normal proxy registration and also set an image/module filter or match flags; accidental reuse of a generic provider entry for a pseudo-proxy class name.
Understand the failure class
Background: Conflicting config options: "cannot be used together" — configuration validation errors across open-source libraries — this error's family across 162 libraries.
Related errors
- SR.Assembly0NotFound (formatted with assemblyName)
- SR.CouldNotFindRegisterMethodOnType0InAssembly1 (formatted…
- SR.CouldNotFindType0InAssembly1 (formatted with typeName…
- SR.GenericInvalidArgument (formatted with argName)
- SR.ParamsNotApplicableToWindowClosedEvent
AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14).
Data as JSON: /api/errors/857c936f33c7f8af.
Report an issue: GitHub.
Appendix: source
Thrown at src/Microsoft.DotNet.Wpf/src/UIAutomation/UIAutomationClient/MS/Internal/Automation/ProxyManager.cs:729
// the array that is passed in may have the same className occuring more than once in the table.
// The way this works it the first occurence in the array is giver the first chance to return a valid
// proxy. In order to make that work we go through the array backwards so the the entries first
// in the table get inserted in front of the ones that came later. This also works if
// RegisterWindowHandlers is called more than once.
for( int i = proxyInfo.Length - 1; i >= 0; i-- )
{
pi = proxyInfo[i];
// Check for pseudo-proxy names...
if( pi.ClassName != null && pi.ClassName.Length > 0 && pi.ClassName[ 0 ] == '#' )
{
for( int j = 0 ; j < _pseudoProxyClassNames.Length ; j++ )
{
if( pi.ClassName.Equals( _pseudoProxyClassNames[ j ] ) )
{
if( pi.ImageName != null || pi.Flags != 0 )
{
throw new ArgumentException(SR.NonclientClassnameCannotBeUsedWithFlagsOrImagename);
}
_pseudoProxies[j] = pi.ClientSideProviderFactoryCallback;
break;
}
}
// fall through to add to table as usual, that ensures that it appears in a 'get' operation.
}
if( pi.ClassName == null && pi.ImageName == null )
{
_fallbackHandlers.Insert(0, pi.ClientSideProviderFactoryCallback);
}
else if ( pi.ClassName == null )
{
AddToHashTable(_imageOnlyHandlers, pi.ImageName, pi.ClientSideProviderFactoryCallback);
}
else if ((pi.Flags & ClientSideProviderMatchIndicator.AllowSubstringMatch) != 0)View on GitHub (pinned to 81131a70a4)