Retargeting Changes for Migration from .NET Framework 4.6.2 to 4.7.1

Introduction

Retargeting changes affect apps that are recompiled to target a different .NET Framework. They include:

  • Changes in the design-time environment. For example, build tools may emit warnings when previously they did not.

  • Changes in the runtime environment. These affect only apps that specifically target the retargeted .NET Framework. Apps that target previous versions of the .NET Framework behave as they did when running under those versions.

In the topics that describe retargeting changes, we have classified individual items by their expected impact, as follows:

Major This is a significant change that affects a large number of apps or that requires substantial modification of code.

Minor This is a change that affects a small number of apps or that requires minor modification of code.

Edge case This is a change that affects apps under very specific scenarios that are not common.

Transparent This is a change that has no noticeable effect on the app's developer or user. The app should not require modification because of this change.

If you are migrating from the .NET Framework 4.6.2 to 4.7.1, review the following topics for application compatibility issues that may affect your app:

ASP.NET

ASP.NET Accessibility Improvements in .NET Framework 4.7.1

Details Starting with the .NET Framework 4.7.1, ASP.NET has improved how ASP.NET Web Controls work with accessibility technology in Visual Studio to better support ASP.NET customers. These include the following changes:
  • Changes to implement missing UI accessibility patterns in controls, like the Add Field dialog in the Details View wizard, or the Configure ListView dialog of the ListView wizard.
  • Changes to improve the display in High Contrast mode, like the Data Pager Fields Editor.
  • Changes to improve the keyboard navigation experiences for controls, like the Fields dialog in the Edit Pager Fields wizard of the DataPager control, the Configure ObjectContext dialog, or the Configure Data Selection dialog of the Configure Data Source wizard.
Suggestion How to opt in or out of these changes In order for the Visual Studio Designer to benefit from these changes, it must run on the .NET Framework 4.7.1 or later. The web application can benefit from these changes in either of the following ways:
  • Install Visual Studio 2017 15.3 or later, which supports the new accessibility features with the following AppContext Switch by default.
  • Opt out of the legacy accessibility behaviors by adding the Switch.UseLegacyAccessibilityFeatures AppContext switch to the <runtime> section in the devenv.exe.config file and setting it to false, as the following example shows.
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<runtime>
...
<!-- AppContextSwitchOverrides value attribute is in the form of 'key1=true/false;key2=true/false'  -->
<AppContextSwitchOverrides value="Switch.UseLegacyAccessibilityFeatures=false" />
...
</runtime>
</configuration>
Applications that target the .NET Framework 4.7.1 or later and want to preserve the legacy accessibility behavior can opt in to the use of legacy accessibility features by explicitly setting this AppContext switch to true.
Scope Minor
Version 4.7.1
Type Retargeting

HttpRuntime.AppDomainAppPath Throws a NullReferenceException

Details In the .NET Framework 4.6.2, the runtime throws a T:System.NullReferenceException when retrieving a P:System.Web.HttpRuntime.AppDomainAppPath value that includes null characters.In the .NET Framework 4.6.1 and earlier versions, the runtime throws an T:System.ArgumentNullException.
Suggestion You can do either of the follow to respond to this change:
  • Handle the T:System.NullReferenceException if you application is running on the .NET Framework 4.6.2.
  • Upgrade to the .NET Framework 4.7, which restores the previous behavior and throws an T:System.ArgumentNullException.
Scope Edge
Version 4.6.2
Type Retargeting
Affected APIs

Throttle concurrent requests per session

Details In the .NET Framework 4.6.2 and earlier, ASP.NET executes requests with the same Sessionid sequentially, and ASP.NET always issues the Sessionid through cookies by default. If a page takes a long time to respond, it will significantly degrade server performance just by pressing F5 on the browser. In the fix, we added a counter to track the queued requests and terminate the requests when they exceed a specified limit. The default value is 50. If the limit is reached, a warning will be logged in the event log, and an HTTP 500 response may be recorded in the IIS log.
Suggestion To restore the old behavior, you can add the following setting to your web.config file to opt out of the new behavior.
<appSettings>
<add key="aspnet:RequestQueueLimitPerSession" value="2147483647"/>
</appSettings>
Scope Edge
Version 4.7
Type Retargeting

Core

SerialPort background thread exceptions

Details Background threads created with SerialPort streams no longer terminate the process when OS exceptions are thrown.
In applications that target the .NET Framework 4.7 and earlier versions, a process is terminated when an operating system exception is thrown on a background thread created with a SerialPort stream.
In applications that target the .NET Framework 4.7.1 or a later version, background threads wait for OS events related to the active serial port and could crash in some cases, such as sudden removal of the serial port.
Suggestion For apps that target the .NET Framework 4.7.1, you can opt out of the exception handling if it is not desirable by adding the following to the <runtime> section of your app.config file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.IO.Ports.DoNotCatchSerialStreamThreadExceptions=true" />
</runtime>
For apps that target earlier versions of the .NET Framework but run on the .NET Framework 4.7.1 or later, you can opt in to the exception handling by adding the following to the <runtime> section of your app.config file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.IO.Ports.DoNotCatchSerialStreamThreadExceptions=false" />
</runtime>
Scope Minor
Version 4.7.1
Type Retargeting
Affected APIs

ServiceBase doesn't propagate OnStart exceptions

Details In the .NET Framework 4.7 and earlier versions, exceptions thrown on service startup are not propagated to the caller of ServiceBase.Run.
Starting with applications that target the .NET Framework 4.7.1, the runtime propagates exceptions to ServiceBase.Run for services that fail to start.
Suggestion On service start, if there is an exception, that exception will be propagated. This should help diagnose cases where services fail to start.
If this behavior is undesirable, you can opt out of it by adding the following <AppContextSwitchOverrides> element to the <runtime> section of your application configuration file:
<AppContextSwitchOverrides value="Switch.System.ServiceProcess.DontThrowExceptionsOnStart=true" />
If your application targets an earlier version than 4.7.1 but you want to have this behavior, add the following <AppContextSwitchOverrides> element to the <runtime> section of your application configuration file:
<AppContextSwitchOverrides value="Switch.System.ServiceProcess.DontThrowExceptionsOnStart=false" />
Scope Minor
Version 4.7.1
Type Retargeting
Affected APIs

Networking

Default value of ServicePointManager.SecurityProtocol is SecurityProtocolType.System.Default

Details Starting with apps that target the .NET Framework 4.7, the default value of the ServicePointManager.SecurityProtocol property is SecurityProtocolType.SystemDefault. This change allows .NET Framework networking APIs based on SslStream (such as FTP, HTTPS, and SMTP) to inherit the default security protocols from the operating system instead of using hard-coded values defined by the .NET Framework. The default varies by operating system and any custom configuration performed by the system administrator. For information on the default SChannel protocol in each version of the Windows operating system, see Protocols in TLS/SSL (Schannel SSP).

For applications that target an earlier version of the .NET Framework, the default value of the ServicePointManager.SecurityProtocol property depends on the version of the .NET Framework targeted. See the Networking section of Retargeting Changes for Migration from .NET Framework 4.5.2 to 4.6 for more information.

Suggestion This change affects applications that target the .NET Framework 4.7 or later versions.
If you prefer to use a defined protocol rather than relying on the system default, you can explicitly set the value of the ServicePointManager.SecurityProtocol property.
If this change is undesirable, you can opt out of it by adding a configuration setting to the <runtime> section of your application configuration file. The following example shows both the <runtime> section and the Switch.System.Net.DontEnableSystemDefaultTlsVersions opt-out switch:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Net.DontEnableSystemDefaultTlsVersions=true" />
</runtime>
Scope Minor
Version 4.7
Type Retargeting
Affected APIs

SslStream supports TLS Alerts

Details After a failed TLS handshake, an IOException with an inner Win32Exception exception will be thrown by the first I/O Read/Write operation. The NativeErrorCode code for the Win32Exception can be mapped to the TLS Alert from the remote party using the Schannel error codes for TLS and SSL alerts. For more information, see RFC 2246: Section 7.2.2 Error alerts.
The behavior in .NET Framework 4.6.2 and earlier is that the transport channel (usually TCP connection) will timeout during either Write or Read if the other party failed the handshake and immediately afterwards rejected the connection.
Suggestion Applications calling network I/O APIs such as Read(Byte[], Int32, Int32)/Write(Byte[], Int32, Int32) should handle IOException or TimeoutException.
The TLS Alerts feature is enabled by default starting with .NET Framework 4.7. Applications targeting versions of the .NET Framework from 4.0 through 4.6.2 running on a .NET Framework 4.7 or higher system will have the feature disabled to preserve compatibility.
The following configuration API is available to enable or disable the feature for .NET Framework 4.6 and later applications running on .NET Framework 4.7 or later.
  • Programmatically:
Must be the very first thing the application does since ServicePointManager will initialize only once:
AppContext.SetSwitch("TestSwitch.LocalAppContext.DisableCaching", true);
AppContext.SetSwitch("Switch.System.Net.DontEnableTlsAlerts", true); // Set to 'false' to enable the feature in .NET Framework 4.6 - 4.6.2.
  • AppConfig:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Net.DontEnableTlsAlerts=true"/>
<!-- Set to 'false' to enable the feature in .NET Framework 4.6 - 4.6.2. -->
</runtime>
  • Registry key (machine global):

    Set the Value to false to enable the feature in .NET Framework 4.6 - 4.6.2.

    • >Key: HKLM\SOFTWARE\Wow6432Node\Microsoft\.NETFramework\AppContext\Switch.System.Net.DontEnableTlsAlerts
    • Type: String
    • Value: "true&quot
Scope Edge
Version 4.7
Type Retargeting
Affected APIs

Security

CspParameters.ParentWindowHandle now expects HWND value

Details The ParentWindowHandle value, introduced in .NET Framework 2.0, allows an application to register a parent window handle value such that any UI required to access the key (such as a PIN prompt or consent dialog) opens as a modal child to the specified window.Starting with apps that target the .NET Framework 4.7, a Windows Forms application can set the ParentWindowHandle property with code like the following:
cspParameters.ParentWindowHandle = form.Handle;
In previous versions of the .NET Framework, the value was expected to be an IntPtr representing a location in memory where the HWND value resided. Setting the property to form.Handle on Windows 7 and earlier versions had no effect, but on Windows 8 and later versions, it results in a "CryptographicException: The parameter is incorrect."
Suggestion Applications targeting .NET Framework 4.7 or higher wishing to register a parent window relationship are encouraged to use the simplified form:
cspParameters.ParentWindowHandle = form.Handle;
Users who had identified that the correct value to pass was the address of a memory location which held the value form.Handle can opt out of the behavior change by setting the AppContext switch Switch.System.Security.Cryptography.DoNotAddrOfCspParentWindowHandle to true.
  1. By programmatically setting compat switches on the AppContext, as explained here
  2. By adding the following line to the <runtime> section of the app.config file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Security.Cryptography.DoNotAddrOfCspParentWindowHandle=true"/>
</runtime>
Conversely, users who wish to opt in to the new behavior on the .NET Framework 4.7 runtime when the application loads under older .NET Framework versions can set the AppContext switch to false.
Scope Minor
Version 4.7
Type Retargeting
Affected APIs

Default SignedXML and SignedXMS algorithms changed to SHA256

Details In the .NET Framework 4.7 and earlier, SignedXML and SignedCMS default to SHA1 for some operations.Starting with the .NET Framework 4.7.1, SHA256 is enabled by default for these operations. This change is necessary because SHA1 is no longer considered to be secure.
Suggestion There are two new context switch values to control whether SHA1 (insecure) or SHA256 is used by default:
  • Switch.System.Security.Cryptography.Xml.UseInsecureHashAlgorithms
  • Switch.System.Security.Cryptography.Pkcs.UseInsecureHashAlgorithms
For applications that target the .NET Framework 4.7.1 and later versions, if the use of SHA256 is undesirable, you can restore the default to SHA1 by adding the following configuration switch to the runtime section of your app config file:
<AppContextSwitchOverrides value="Switch.System.Security.Cryptography.Xml.UseInsecureHashAlgorithms=true;Switch.System.Security.Cryptography.Pkcs.UseInsecureHashAlgorithms=true" />
For applications that target the .NET Framework 4.7 and earlier versions, you can opt into this change by adding the following configuration switch to the runtime section of your app config file:
<AppContextSwitchOverrides value="Switch.System.Security.Cryptography.Xml.UseInsecureHashAlgorithms=false;Switch.System.Security.Cryptography.Pkcs.UseInsecureHashAlgorithms=false" />
Scope Minor
Version 4.7.1
Type Retargeting
Affected APIs

SignedXml.GetPublicKey returns RSACng on net462 (or lightup) without retargeting change

Details Starting with the .NET Framework 4.6.2, the concrete type of the object returned by the SignedXml.GetPublicKey method changed (without a quirk) from a CryptoServiceProvider implementation to a Cng implementation. This is because the implementation changed from using certificate.PublicKey.Key to using the internal certificate.GetAnyPublicKey which forwards to RSACertificateExtensions.GetRSAPublicKey.
Suggestion Starting with apps running on the .NET Framework 4.7.1, you can use the CryptoServiceProvider implementation used by default in the .NET Framework 4.6.1 and earlier versions by adding the following configuration switch to the runtime section of your app config file:
<AppContextSwitchOverrides value="Switch.System.Security.Cryptography.Xml.SignedXmlUseLegacyCertificatePrivateKey=true" />
Scope Edge
Version 4.6.2
Type Retargeting
Affected APIs

SslStream supports TLS Alerts

Details After a failed TLS handshake, an IOException with an inner Win32Exception exception will be thrown by the first I/O Read/Write operation. The NativeErrorCode code for the Win32Exception can be mapped to the TLS Alert from the remote party using the Schannel error codes for TLS and SSL alerts. For more information, see RFC 2246: Section 7.2.2 Error alerts.
The behavior in .NET Framework 4.6.2 and earlier is that the transport channel (usually TCP connection) will timeout during either Write or Read if the other party failed the handshake and immediately afterwards rejected the connection.
Suggestion Applications calling network I/O APIs such as Read(Byte[], Int32, Int32)/Write(Byte[], Int32, Int32) should handle IOException or TimeoutException.
The TLS Alerts feature is enabled by default starting with .NET Framework 4.7. Applications targeting versions of the .NET Framework from 4.0 through 4.6.2 running on a .NET Framework 4.7 or higher system will have the feature disabled to preserve compatibility.
The following configuration API is available to enable or disable the feature for .NET Framework 4.6 and later applications running on .NET Framework 4.7 or later.
  • Programmatically:
Must be the very first thing the application does since ServicePointManager will initialize only once:
AppContext.SetSwitch("TestSwitch.LocalAppContext.DisableCaching", true);
AppContext.SetSwitch("Switch.System.Net.DontEnableTlsAlerts", true); // Set to 'false' to enable the feature in .NET Framework 4.6 - 4.6.2.
  • AppConfig:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Net.DontEnableTlsAlerts=true"/>
<!-- Set to 'false' to enable the feature in .NET Framework 4.6 - 4.6.2. -->
</runtime>
  • Registry key (machine global):

    Set the Value to false to enable the feature in .NET Framework 4.6 - 4.6.2.

    • >Key: HKLM\SOFTWARE\Wow6432Node\Microsoft\.NETFramework\AppContext\Switch.System.Net.DontEnableTlsAlerts
    • Type: String
    • Value: "true&quot
Scope Edge
Version 4.7
Type Retargeting
Affected APIs

Windows Communication Foundation (WCF)

Improved accessibility for some .NET SDK tools

Details In the .NET Framework SDK 4.7.1, the SvcConfigEditor.exe and SvcTraceViewer.exe tools have been improved by fixing varied accessibility issues. Most of these were small issues like a name not being defined or certain UI automation patterns not being implemented correctly. While many users wouldn’t be aware of these incorrect values, customers who use assistive technologies like screen readers will find these SDK tools more accessible. Certainly, these fixes change some previous behaviors, like keyboard focus order.In order to get all the accessibility fixes in these tools, you can the following to your app.config file:
<runtime>
<AppContextSwitchOverrides value="Switch.UseLegacyAccessibilityFeatures=false"/>
</runtime>
Scope Edge
Version 4.7.1
Type Retargeting

Serialization of control characters with DataContractJsonSerializer is now compatible with ECMAScript V6 and V8

Details In the .NET framework 4.6.2 and earlier versions, the DataContractJsonSerializer did not serialize some special control characters, such as \b, \f, and \t, in a way that was compatible with the ECMAScript V6 and V8 standards. Starting with the .NET Framework 4.7, serialization of these control characters is compatible with ECMAScript V6 and V8.
Suggestion For apps that target the .NET Framework 4.7, this feature is enabled by default. If this behavior is not desirable, you can opt out of this feature by adding the following line to the <runtime> section of the app.config or web.config file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Runtime.Serialization.DoNotUseECMAScriptV6EscapeControlCharacter=false" />
</runtime>
Scope Edge
Version 4.7
Type Retargeting
Affected APIs

WCF message security now is able to use TLS1.1 and TLS1.2

Details Starting in the .NET Framework 4.7, customers can configure either TLS1.1 or TLS1.2 in WCF message security in addition to SSL3.0 and TLS1.0 through application configuration settings.
Suggestion In the .NET Framework 4.7, support for TLS1.1 and TLS1.2 in WCF message security is disabled by default. You can enable it by adding the following line to the <runtime> section of the app.config or web.config file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.ServiceModel.DisableUsingServicePointManagerSecurityProtocols=false;Switch.System.Net.DontEnableSchUseStrongCrypto=false" />
</runtime>
Scope Edge
Version 4.7
Type Retargeting

Windows Forms

Accessibility improvements in Windows Forms controls

Details Windows Forms is improving how it works with accessibility technologies to better support Windows Forms customers. These include the following changes starting with the .NET Framework 4.7.1:
  • Changes to improve display during High Contrast mode.
  • Changes to improve the property browser experience. Property browser improvements include:
  • Better keyboard navigation through the various drop-down selection windows.
  • Reduced unnecessary tab stops.
  • Better reporting of control types.
  • Improved narrator behavior.
  • Changes to implement missing UI accessibility patterns in controls.
Suggestion How to opt in or out of these changes
In order for the application to benefit from these changes, it must run on the .NET Framework 4.7.1 or later. The application can benefit from these changes in either of the following ways:
  • It is recompiled to target the .NET Framework 4.7.1. These accessibility changes are enabled by default on Windows Forms applications that target the .NET Framework 4.7.1 or later.
  • It opts out of the legacy accessibility behaviors by adding the following AppContext switch to the <runtime> section of the app.config file and setting it to false, as the following example shows.
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7"/>
</startup>
<runtime>
<!-- AppContextSwitchOverrides value attribute is in the form of 'key1=true/false;key2=true/false  -->
<AppContextSwitchOverrides value="Switch.UseLegacyAccessibilityFeatures=false" />
</runtime>
</configuration>

Applications that target the .NET Framework 4.7.1 or later and want to preserve the legacy accessibility behavior can opt in to the use of legacy accessibility features by explicitly setting this AppContext switch to true.

For an overview of UI automation, see the UI Automation Overview.</p/>

Added support for UI Automation patterns and properties
Accessibility clients can take advantage of new WinForms accessibility functionality by using common, publicly described invocation patterns. These patterns are not WinForms-specific. For instance, accessibility clients can call the QueryInterface method on the IAccessible interface (MAAS) to obtain an IServiceProvider interface. If this interface is available, clients can use its QueryService method to request an IAccessibleEx interface. For more information, see Using IAccessibleEx from a Client. Starting with the .NET Framework 4.7.1, IServiceProvider and IAccessibleEx (where applicable) are available for WinForms accessibility objects.

The .NET Framework 4.7.1 adds support for the following UI automation patterns and properties:

Improvements to the PropertyGrid control
The .NET Framework 4.7.1 adds the following improvements to the PropertyBrowser control:
  • The Details button in the error dialog that is displayed when the user enters an incorrect value in the PropertyGrid control supports the Expand/Collapse pattern, state and name change notifications, and a [ControlType]~/docs/framework/ui-automation/ui-automation-support-for-the-menubar-control-type.md) property with a value of ControlType.MenuItem.
  • The message pane displayed when the Details button of the error dialog is expanded is now keyboard accessible and allows Narrator to announce the content of the error message.
  • The AccessibleRole of rows in the PropertyGrid control have changed from "Row" to "Cell". The cell maps to UIA ControlType "DataItem", which allows it to support appropriate keyboard shortcuts and Narrator announcements.
  • The PropertyGrid control rows that represent header items when the PropertyGrid control has a PropertySort property set to PropertySort.Categorized have a ControlType property value of ControlType.Button.
  • The PropertyGrid control rows that represent header items when the PropertyGrid control has a PropertySort property set to PropertySort.Categorized support the Expand/Collapse pattern.
  • Improved keyboard navigation between the grid and the ToolBar above it. Pressing "Shift-Tab" now selects the first ToolBar button, instead of the whole ToolBar.
  • PropertyGrid controls displayed in High Contrast mode will now draw a focus rectangle around the ToolBar button which corresponds to the current PropertySort property value.
  • PropertyGrid controls displayed in High Contrast mode and with a PropertySort property set to PropertySort.Categorized will now display the background of category headers in a highly contrasting color.
  • PropertyGrid controls better differentiates between ToolBar items with focus and the ToolBar items which indicate the current value of the PropertySort property. This fix consists of a High Contrast change and a change for non-High Contrast scenarios.
  • PropertyGrid control ToolBar items which indicates the current value of the PropertySort property support the TogglePattern.
  • Improved Narrator support for distinguishing the selected alignment in the Alignment Picker.
  • When an empty PropertyGrid control is displayed on a form, it will now receive focus where previously it would not.

Use of OS-defined colors in High Contrast themes
  • The Button and CheckBox controls with their FlatStyle property set to FlatStyle.System, which is the default style, now use OS-defined colors in High Contrast theme when selected. Previously, text and background colors were not contrasting and were hard to read.
  • The Button, CheckBox, RadioButton, Label, LinkLabel and GroupBox controls with their Enabled property set to false used a shaded color to render text in High Contrast themes, resulting in low contrast against the background. Now these controls use the "Disabled Text" color defined by the OS. This fix applies to controls with their FlatStyle property set to a value other than FlatStyle.System. The latter controls are rendered by the OS.
  • DataGridView now renders a visible rectangle around the content of the cell which has the current focus. Previously, this was not visible in certain High Contrast themes.
  • ToolStripMenuItem controls with their Enabled property set to false now use the "Disabled Text" color defined by the OS.
  • ToolStripMenuItem controls with their Checked property set to true now render the associated check mark in a contrasting system color. Previously the check mark color was not contrasting enough and not visible in High Contrast themes.
NOTE: Windows 10 has changed values for some high contrast system colors. Windows Forms Framework is based on the Win32 framework. For the best experience, run on the latest version of Windows and opt in to the latest OS changes by adding an app.manifest file in a test application and uncommenting the following code:
<!-- Windows 10 -->
<supportedOS Id="{8e0f7a12-bfb3-4fe8-b9a5-48fd50a15a9a}" />

Improved keyboard navigation
  • When a ComboBox control has its DropDownStyle property set to ComboBoxStyle.DropDownList and is the first control in the tab order on the form, it now displays a focus rectangle when the parent form is opened using the keyboard. Before this change, keyboard focus was on this control, but a focus indicator was not rendered.
Improved Narrator support
  • The MonthCalendar control has added support for assistive technologies to access the control, including the ability for Narrator to read the value of the control when previously it could not.
  • The CheckedListBox control now notifies Narrator when a CheckBox.CheckState property has been changed. Previously, Narrator did not receive notification and as a result users would not be informed that the CheckState property had been updated.
  • The LinkLabel control has changed the way it notifies Narrator of the text of in the control. Previously, Narrator announced this text twice and read "&" symbols as real text even though they are not visible to a user. The duplicated text was removed from the Narrator announcements, as well as unnecessary "&" symbols.
  • The DataGridViewCell control types now correctly report the read-only status to Narrator and other assistive technologies.
  • Narrator is now able to read the System Menu of child windows in [Multiple-Document Interface]~/docs/framework/winforms/advanced/multiple-document-interface-mdi-applications.md) applications.
  • Narrator is now able to read ToolStripMenuItem controls with a ToolStripItem.Enabled property set to false. Previously, Narrator was unable to focus on disabled menu items to read the content.
Scope Major
Version 4.7.1
Type Retargeting
Affected APIs

Windows Presentation Foundation (WPF)

Accessibility improvements in WPF

Details High Contrast improvements
  • The focus for the Expander control is now visible. In previous versions of the .NET Framework, it was not.
  • The text in CheckBox and RadioButton controls when they are selected is now easier to see than in previous .NET Framework versions.
  • The border of a disabled ComboBox is now the same color as the disabled text. In previous versions of the .NET Framework, it was not.
  • Disabled and focused buttons now use the correct theme color. In previous versions of the .NET Framework, they did not.
  • The dropdown button is now visible when a ComboBox control's style is set to ToolBar.ComboBoxStyleKey, In previous versions of the .NET Framework, it was not.
  • The sort indicator arrow in a DataGrid control now uses theme colors. In previous versions of the .NET Framework, it did not.
  • The default hyperlink style now changes to the correct theme color on mouse over. In previous versions of the .NET Framework, it did not.
  • The Keyboard focus on radio buttons is now visible. In previous versions of the .NET Framework, it was not.
  • The DataGrid control's checkbox column now uses the expected colors for keyboard focus feedback. In previous versions of the .NET Framework, it did not.
  • the Keyboard focus visuals are now visible on ComboBox and ListBox controls. In previous versions of the .NET Framework, it was not.

Screen reader interaction improvements
  • Expander controls are now correctly announced as groups (expand/collapse) by screen readers.
  • DataGridCell controls are now correctly announced as data grid cell (localized) by screen readers.
  • Screen readers will now announce the name of an editable ComboBox.
  • PasswordBox controls are no longer announced as "no item in view" by screen readers.

LiveRegion support
Screen readers such as Narrator help people know the UI contents of an application, usually by describing something about the UI that's currently focused, because that is probably the element of most interest to the user. However, if a UI element changes somewhere in the screen and it does not have the focus, the user may not be informed and miss important information. LiveRegions are meant to solve this problem. A developer can use them to inform the screen reader or any other UI Automation client that an important change has been made to a UI element. The screen reader can then decide how and when to inform the user of this change.The LiveSetting property also lets the screen reader know how important it is to inform the user of the change made to the UI.
Suggestion How to opt in or out of these changes
In order for the application to benefit from these changes, it must run on the .NET Framework 4.7.1 or later. The application can benefit from these changes in either of the following ways:
  • Target the .NET Framework 4.7.1. This is the recommended approach. These accessibility changes are enabled by default on WPF applications that target the .NET Framework 4.7.1 or later.
  • It opts out of the legacy accessibility behaviors by adding the following AppContext Switch in the <runtime> section of the app config file and setting it to false, as the following example shows.
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7"/>
</startup>
<runtime>
<!-- AppContextSwitchOverrides value attribute is in the form of 'key1=true/false;key2=true/false  -->
<AppContextSwitchOverrides value="Switch.UseLegacyAccessibilityFeatures=false" />
</runtime>
</configuration>
Applications that target the .NET Framework 4.7.1 or later and want to preserve the legacy accessibility behavior can opt in to the use of legacy accessibility features by explicitly setting this AppContext switch to true.
For an overview of UI automation, see the UI Automation Overview.
Scope Major
Version 4.7.1
Type Retargeting
Affected APIs

Calls to System.Windows.Input.PenContext.Disable on touch-enabled systems may throw an ArgumentException

Details Under some circumstances, calls to the internal System.Windows.Intput.PenContext.Disable method on touch-enabled systems may throw an unhandled T:System.ArgumentException because of reentrancy.
Suggestion This issue has been addressed in the .NET Framework 4.7. To prevent the exception, upgrade to a version of the .NET Framework starting with the .NET Framework 4.7.
Scope Edge
Version 4.6.1
Type Retargeting

NullReferenceException in exception handling code from ImageSourceConverter.ConvertFrom

Details An error in the exception handling code for ConvertFrom(ITypeDescriptorContext, CultureInfo, Object) caused an incorrect NullReferenceException to be thrown instead of the intended exception (e.g. DirectoryNotFoundException, FileNotFoundException). This change corrects that error so that the method now throws the right exception.

By default all applications targeting .NET Framework 4.6.2 and earlier continue to throw NullReferenceException for compatibility. Developers targeting .NET Framework 4.7 and above should see the right exceptions.

Suggestion Developers who wish to revert to getting NullReferenceException when targeting .NET Framework 4.7 can add/merge the following to their application's App.config file:
<configuration>
<runtime>
<AppContextSwitchOverrides value="Switch.System.Windows.Media.ImageSourceConverter.OverrideExceptionWithNullReferenceException=true"/>
</runtime>
</configuration>
Scope Edge
Version 4.7
Type Retargeting
Affected APIs

Selector SelectionChanged event and SelectedValue property

Details Starting with the .NET Framework 4.7.1, a Selector always updates the value of its SelectedValue property before raising the SelectionChanged event, when its selection changes. This makes the SelectedValue property consistent with the other selection properties (SelectedItem and SelectedIndex), which are updated before raising the event.

In the .NET Framework 4.7 and earlier versions, the update to SelectedValue happened before the event in most cases, but it happened after the event if the selection change was caused by changing the SelectedValue property.

Suggestion Apps that target the .NET Framework 4.7.1 or later can opt out of this change and use legacy behavior by adding the following to the <runtime> section of the application configuration file:
<runtime>
<AppContextSwitchOverrides
value="Switch.System.Windows.Controls.TabControl.SelectionPropertiesCanLagBehindSelectionChangedEvent=true" />
</runtime>
Apps that target the .NET Framework 4.7 or earlier but are running on the .NET Framework 4.7.1 or later can enable the new behavior by adding the following line to the <runtime> section of the application .configuration file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Windows.Controls.TabControl.SelectionPropertiesCanLagBehindSelectionChangedEvent=false" />
</runtime>
Scope Minor
Version 4.7.1
Type Retargeting
Affected APIs

TabControl SelectionChanged event and SelectedContent property

Details Starting with the .NET Framework 4.7.1, a TabControl updates the value of its SelectedContent property before raising the SelectionChanged event, when its selection changes.In the .NET Framework 4.7 and earlier versions, the update to SelectedContent happened after the event.
Suggestion Apps that target the .NET Framework 4.7.1 or later can opt out of this change and use legacy behavior by adding the following to the <runtime> section of the application configuration file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Windows.Controls.TabControl.SelectionPropertiesCanLagBehindSelectionChangedEvent=true" />
</runtime>
Apps that target the .NET Framework 4.7 or earlier but are running on the .NET Framework 4.7.1 or later can enable the new behavior by adding the following line to the <runtime> section of the application .configuration file:
<runtime>
<AppContextSwitchOverrides value="Switch.System.Windows.Controls.TabControl.SelectionPropertiesCanLagBehindSelectionChangedEvent=false" />
</runtime>
Scope Minor
Version 4.7.1
Type Retargeting
Affected APIs

The default hash algorithm for WPF PackageDigitalSignatureManager is now SHA256

Details The System.IO.Packaging.PackageDigitalSignatureManager provides functionality for digital signatures in relation to WPF packages. In the .NET Framework 4.7 and earlier versions, the default algorithm (PackageDigitalSignatureManager.DefaultHashAlgorithm) used for signing parts of a package was SHA1. Due to recent security concerns with SHA1, this default has been changed to SHA256 starting with the .NET Framework 4.7.1. This change affects all package signing, including XPS documents.
Suggestion A developer who wants to utilize this change while targeting a framework version below .NET Framework 4.7.1 or a developer who requires the previous functionality while targeting .NET Framework 4.7.1 or greater can set the following AppContext flag appropriately. A value of true will result in SHA1 being used as the default algorithm; false results in SHA256.
<configuration>
<runtime>
<AppContextSwitchOverrides value="Switch.MS.Internal.UseSha1AsDefaultHashAlgorithmForDigitalSignatures=true"/>
</runtime>
</configuration>
Scope Edge
Version 4.7.1
Type Retargeting
Affected APIs

WPF Grid allocation of space to star-columns

Details Starting with the .NET Framework 4.7, WPF replaces the algorithm that Grid uses to allocate space to *-columns. This will change the actual width assigned to *-columns in a number of cases:
  • When one or more *-columns also have a minimum or maximum width that overrides the proportional allocation for that column. (The minimum width can derive from an explicit MinWidth declaration, or from an implicit minimum obtained from the column's content. The maximum width can only be defined explicitly, from a MaxWidth declaration.)
  • When one or more *-columns declare an extremely large *-weight, greater than 10^298.
  • When the *-weights are sufficiently different to encounter floating-point instability (overflow, underflow, loss of precision).
  • When layout rounding is enabled, and the effective display DPI is sufficiently high.
In the first two cases, the widths produced by the new algorithm can be significantly different from those produced by the old algorithm; in the last case, the difference will be at most one or two pixels.

The new algorithm fixes several bugs present in the old algorithm:

  1. Total allocation to columns can exceed the Grid's width. This can occur when allocating space to a column whose proportional share is less than its minimum size. The algorithm allocates the minimum size, which decreases the space available to other columns. If there are no *-columns left to allocate, the total allocation will be too large.
  2. Total allocation can fall short of the Grid's width. This is the dual problem to #1, arising when allocating to a column whose proportional share is greater than its maximum size, with no *-columns left to take up the slack.
  3. Two *-columns can receive allocations not proportional to their *-weights. This is a milder version of #1/#2, arising when allocating to *-columns A, B, and C (in that order), where B's proportional share violates its min (or max) constraint. As above, this changes the space available to column C, who gets less (or more) proportional allocation than A did,
  4. Columns with extremely large weights (> 10^298) are all treated as if they had weight 10^298. Proportional differences between them (and between columns with slightly smaller weights) are not honored.
  5. Columns with infinite weights are not handled correctly. [Actually you can't set a weight to Infinity, but this is an artificial restriction. The allocation code was trying to handle it, but doing a bad job.]
  6. Several minor problems while avoiding overflow, underflow, loss of precision and similar floating-point issues.
  7. Adjustments for layout rounding are incorrect at sufficiently high DPI.
The new algorithm produces results that meet the following criteria:

A. The actual width assigned to a *-column is never less than its minimum width nor greater than its maximum width.
B. Each -column that is not assigned its minimum or maximum width is assigned a width proportional to its -weight. To be precise, if two columns are declared with width x and y respectively, and if neither column receives its minimum or maximum width, the actual widths v and w assigned to the columns are in the same proportion: v / w == x / y.
C. The total width allocated to "proportional" *-columns is equal to the space available after allocating to the constrained columns (fixed, auto, and *-columns that are allocated their min or max width). This might be zero, for instance if the sum of the minimum widths exceeds the Grid's available width.
D. All these statements are to be interpreted with respect to the "ideal" layout. When layout rounding is in effect, the actual widths can differ from the ideal widths by as much as one pixel.
The old algorithm honored (A) but failed to honor the other criteria in the cases outlined above.

Everything said about columns and widths in this article applies as well to rows and heights.

Suggestion By default, apps that target versions of the .NET Framework starting with the .NET Framework 4.7 will see the new algorithm, while apps that target the .NET Framework 4.6.2 or earlier versions will see the old algorithm.

To override the default, use the following configuration setting:

<runtime>
<AppContextSwitchOverrides value="Switch.System.Windows.Controls.Grid.StarDefinitionsCanExceedAvailableSpace=true" />
</runtime>
The value true selects the old algorithm, false selects the new algorithm.
Scope Minor
Version 4.7
Type Retargeting

WPF Pointer-Based Touch Stack

Details This change adds the ability to enable an optional WM_POINTER based WPF touch/stylus stack. Developers that do not explicitly enable this should see no change in WPF touch/stylus behavior.Current Known Issues With optional WM_POINTER based touch/stylus stack:
  • No support for real-time inking.
  • While inking and StylusPlugins will still work, they will be processed on the UI Thread which can lead to poor performance.
  • Behavioral changes due to changes in promotion from touch/stylus events to mouse events
  • Manipulation may behave differently
  • Drag/Drop will not show appropriate feedback for touch input
  • This does not affect stylus input
  • Drag/Drop can no longer be initiated on touch/stylus events
  • This can potentially hang the application until mouse input is detected.
  • Instead, developers should initiate drag and drop from mouse events.
Suggestion Developers who wish to enable this stack can add/merge the following to their application's App.config file:
<configuration>
<runtime>
<AppContextSwitchOverrides value="Switch.System.Windows.Input.Stylus.EnablePointerSupport=true"/>
</runtime>
</configuration>
Removing this or setting the value to false will turn this optional stack off.Note that this stack is available only on Windows 10 Creators Update and above.
Scope Edge
Version 4.7
Type Retargeting

Windows Workflow Foundation (WF)

Accessibility improvements in Windows Workflow Foundation (WF) workflow designer

Details The Windows Workflow Foundation (WF) workflow designer is improving how it works with accessibility technologies. These improvements include the following changes:
  • The tab order is changed to left to right and top to bottom in some controls:
  • The initialize correlation window for setting correlation data for the InitializeCorrelation activity
  • The content definition window for the Receive, Send, SendReply, and ReceiveReply activities
  • More functions are available via the keyboard:
  • When editing the properties of an activity, property groups can be collapsed by keyboard the first time they are focused.
  • Warning icons are now accessible by keyboard.
  • The More Properties button in the Properties window is now accessible by keyboard.
  • Keyboard users now can access the header items in the Arguments and Variables panes of the Workflow Designer.
  • Improved visibility of items with focus, such as when:
  • Adding rows to data grids used by the Workflow Designer and activity designers.
  • Tabbing through fields in the ReceiveReply and SendReply activities.
  • Setting default values for variables or arguments
  • Screen readers can now correctly recognize:
  • Breakpoints set in the workflow designer.
  • The FlowSwitch<T>, FlowDecision, and CorrelationScope activities.
  • The contents of the Receive activity.
  • The Target Type for the InvokeMethod activity.
  • The Exception combobox and the Finally section in the TryCatch activity.
  • The Message Type combobox, the splitter in the Add Correlation Initializers window, the Content Definition window, and the CorrelatesOn Defintion window in the messaging activities (Receive, Send, SendReply, and ReceiveReply).
  • State machine transitions and transitions destinations.
  • Annotations and connectors on FlowDecision activities.
  • The context (right-click) menus for activities.
  • The property value editors, the Clear Search button, the By Category and Alphabetical sort buttons, and the Expression Editor dialog in the properties grid.
  • The zoom percentage in the Workflow Designer.
  • The separator in Parallel and Pick activities.
  • The InvokeDelegate activity.
  • The Select Types window for dictionary activities (Microsoft.Activities.AddToDictionary<TKey,TValue>, Microsoft.Activities.RemoveFromDictionary<TKey,TValue>, etc.).
  • The Browse and Select .NET Type window.
  • Breadcrumbs in the Workflow Designer.
  • Users who choose High Contrast themes will see many improvements in the visibility of the Workflow Designer and its controls like better contrast ratios between elements and more noticeable selection boxes used for focus elements.
Suggestion If you have an application with a re-hosted workflow designer, your application can benefit from these changes by performing either of these actions:
  • Recompile your application to target the .NET Framework 4.7.1. These accessibility changes are enabled by default.
  • If your application targets the .NET Framework 4.7 or earlier but is running on the .NET Framework 4.7.1, you can opt out of these legacy accessibility behaviors by adding the following AppContext switch to the <runtime> section of the app.config file and set it to false, as the following example shows.
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7"/>
</startup>
<runtime>
<!-- AppContextSwitchOverrides value attribute is in the form of 'key1=true/false;key2=true/false  -->
<AppContextSwitchOverrides value="Switch.UseLegacyAccessibilityFeatures=false" />
</runtime>
</configuration>
Applications that target the .NET Framework 4.7.1 or later and want to preserve the legacy accessibility behavior can opt in to the use of legacy accessibility features by explicitly setting this AppContext switch to true.
Scope Minor
Version 4.7.1
Type Retargeting

Workflow checksums changed from MD5 to SHA1

Details To support debugging with Visual Studio, the Workflow runtime generates a checksum for a workflow instance using a hashing algorithm. In the .NET Framework 4.6.2 and earlier versions, workflow checksum hashing used the MD5 algorithm, which caused issues on FIPS-enabled systems. Starting with the .NET Framework 4.7, the algorithm is SHA1. If your code has persisted these checksums, they will be incompatible.
Suggestion If your code is unable to load workflow instances due to a checksum failure, try setting the AppContext switch "Switch.System.Activities.UseMD5ForWFDebugger" to true.In code:
System.AppContext.SetSwitch("Switch.System.Activities.UseMD5ForWFDebugger", true);
Or in configuration:
<configuration>
<runtime>
<AppContextSwitchOverrides value="Switch.System.Activities.UseMD5ForWFDebugger=true" />
</runtime>
</configuration>
Scope Minor
Version 4.7
Type Retargeting