Skip to content
This repository has been archived by the owner on Jul 15, 2023. It is now read-only.

Commit

Permalink
Update docs to correct small issues, clean up table formatting and
Browse files Browse the repository at this point in the history
update the Quirk definition.

Fixing a couple issues from code review.

on 'db3b509'.
  • Loading branch information
JJVertical committed Oct 22, 2015
1 parent db3b509 commit 2118dfa
Show file tree
Hide file tree
Showing 5 changed files with 62 additions and 56 deletions.
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,13 @@ Today, the repository contains the following components:
### Tools

| Project | Description |
| ------- | ----------- |
| :------- | :----------- |
| ApiPort | Console tool to access portability webservice |

### Libraries

| Project | Description |
| ------- | ----------- |
| :------- | :----------- |
| Microsoft.Fx.Portability [![version](https://img.shields.io/myget/dotnet-apiport/v/Microsoft.Fx.Portability.svg)](https://www.myget.org/gallery/dotnet-apiport) | Provides common types for API Port |
| Microsoft.Fx.Portability.MetadataReader [![version](https://img.shields.io/myget/dotnet-apiport/v/Microsoft.Fx.Portability.MetadataReader.svg)](https://www.myget.org/gallery/dotnet-apiport) | Implements a dependency finder based off of [System.Reflection.Metadata](https://github.com/dotnet/corefx/tree/master/src/System.Reflection.Metadata). The library will generate DocIds that conform to [these specifications](https://msdn.microsoft.com/en-us/library/fsbx0t7x.aspx). |
| Microsoft.Fx.Portability.Offline [![version](https://img.shields.io/myget/dotnet-apiport/v/Microsoft.Fx.Portability.Offline.svg)](https://www.myget.org/gallery/dotnet-apiport) | Provides access to data in an offline setting so network calls are not needed |
Expand Down
86 changes: 46 additions & 40 deletions docs/HowTo/BreakingChanges.md
Original file line number Diff line number Diff line change
@@ -1,50 +1,48 @@
# Breaking Changes

Compatibility is a very important goal of each .NET release. This is accomplished by ensuring each version is additive, so previous
versions will still work. However, when a change must be made to previous functionality (for performance, security, or a bug) this
Compatibility is a very important goal of each .NET release. This is accomplished by ensuring each version is additive so previous
versions will still work; however, when a change must be made to previous functionality (for performance, security, or a bug) this
can cause compatibility problems in already written code. A distinction to understand with .NET compatibility is runtime vs retargeting
issues.

When developing an app, the .NET Framework version that the app is targeting is [specified either by specifying a target Framework
in Visual Studio](https://msdn.microsoft.com/en-us/library/bb398202%28v=vs.140%29.aspx), directly
[specifying the target Framework](https://msdn.microsoft.com/en-us/library/hh264221.aspx) in a project file, or applying a
[TargetFrameworkAttribute](https://msdn.microsoft.com/en-us/library/system.runtime.versioning.targetframeworkattribute%28v=vs.110%29.aspx)
to the source code.
When developing an app the .NET Framework version that the app is targeting is specified either by [specifying a target Framework
in Visual Studio](https://msdn.microsoft.com/en-us/library/bb398202%28v=vs.140%29.aspx), [specifying the target Framework in a project
file](https://msdn.microsoft.com/en-us/library/hh264221.aspx), or [applying a TargetFrameworkAttribute
to the source code](https://msdn.microsoft.com/en-us/library/system.runtime.versioning.targetframeworkattribute%28v=vs.110%29.aspx).

When running on a newer version than what was targeted, the .NET Framework will
use quirked behavior to mimic the older targeted version. The app will run on the newer version of the Framework, but act as if it's
use quirked behavior to mimic the older targeted version. In other words, the app will run on the newer version of the Framework, but act as if it's
running on the older version. Many of the breaking changes between versions of the .NET Framework are mitigated through this
quirking model.

Runtime issues are those that arise when a new runtime is placed on a machine and the same binaries are run, but different behavior is
seen. If a binary was compiled for .NET 4.0, it will then run in .NET 4.0 compatibility mode on 4.5+. Many of the changes that affect
seen. If a binary was compiled for .NET 4.0 it will run in .NET 4.0 compatibility mode on 4.5+. Many of the changes that affect
4.5 will not affect a binary compiled for 4.0. This is specific to the AppDomain and depends on the settings of the entry assembly.

Retargeting issues are those that arise when an assembly that was targeting 4.0 is now set to target 4.5. Now, it opts into many of
the new features, with some breaking changes to old features. Again, this is dictated by the entry assembly, so the console app that
Retargeting issues are those that arise when an assembly that was targeting 4.0 is now set to target 4.5. Now the assembly opts into the new features
as well as potential breaking changes to old features. Again, this is dictated by the entry assembly, so the console app that
uses the assembly, or the website that references the assembly.

Sometimes, there are new behaviors that can be toggled on or off. This is often done by registry keys or configuration values, but
Sometimes there are new behaviors that can be toggled on or off. This is often done by registry keys or configuration values, but
depends on the specific change if those are available.

**Note** This analysis is only applicable to assemblies that are designed to run on the .NET Framework 4.0+.

## Quirks
Quirks are an important concept to understand .NET compatibility. Quirks are special branches within the .NET Framework the outcome of which
depends on certain factors. These quirks are generally consistent within a single AppDomain and depends on the settings of the entry assembly.
Quirks can come in a few different forms:
Quirks are an important concept to understand .NET compatibility. Quirks are special branches within the .NET Framework that preserve
the legacy behavior and applies it where appropriate. For some features and APIs, rather than introducing a breaking change, the .NET
Framework provides a quirks mode that preserves the legacy behavior and applies it where appropriate, depending on the target version
the app was originally built and tested for. If the target version is .NET Framework 4.0, quirks mode either emulates the same
behavior, or it uses the same code when running on .NET Framework 4.5+. In other words, the app runs in .NET Framework 4.5+ as it
did when it was tested against .NET Framework 4.0.

- Framework version the assembly was compiled for
- Certain configuration values
- Certain registry settings
The most common quirks are dependent on the framework an assembly is compiled for. This can help ensure that it will only run on later
versions; i.e., if you compile against 4.5, you cannot add this to a 4.0 project; however, you may add it to any version greater than
or equal to 4.5. This is one of the simplest ways to opt into a quirk and if compiling with msbuild this is done automatically. If
msbuild is not being used to compile the assembly then a one line global assembly attribute will add it manually.

The most common quirks are dependent on the framework an assembly is compiled for. This can help ensure that it will only run on later versions; i.e., if you compile
against 4.5, you cannot add this to a 4.0 project. However, you may add it to any version greater than or equal to 4.5. This is one of the simplest
ways to opt into a quirk, and, if compiling with msbuild, this is done automatically. If msbuild is not being used to compile the assembly, then a one line
global assembly attribute will add it manually.

A TFM is automatically added by msbuild projects during the compilation step. If you create a project that targets .NET Framework 4.6 and compile, you
will find a new file located at `%temp%\.NETFramework,Version=v4.6.AssemblyAttributes.cs` in which the TFM is described:
A TFM is automatically added by msbuild projects during the compilation step. If you create a project that targets .NET Framework 4.6
and compile, you will find a new file located at `%temp%\.NETFramework,Version=v4.6.AssemblyAttributes.cs` in which the TFM is described:

```csharp
// <autogenerated />
Expand All @@ -54,16 +52,18 @@ using System.Reflection;
```

## Known Issues
This tool does not catch all known issues of breaking changes. ApiPort is restricted to catching only breaks introduced for a specific API, not breaks due to patterns that may be used. To see
the full list of issues, please review those listed [here](/docs/BreakingChanges).
This tool does not catch all known issues of breaking changes. ApiPort is restricted to catching only breaks introduced for a specific API,
not breaks due to patterns that may be used. To see the full list of issues, please review those listed [here](/docs/BreakingChanges).

In addition to this tool, there is work being done on a set of Roslyn-based analyzers that will better determine
possible breaking changes that also include specific programming patterns. These are much more targeted and will provide better information as to what should be done. ApiPort lets you know which issues
have source analyzers available, but they are currently not released. Please watch for updates regarding this in the near future.
possible breaking changes that also include specific programming patterns. These are much more targeted and will provide better information
as to what should be done. ApiPort lets you know which issues have source analyzers available, but they are currently not released. Please
watch for updates regarding this in the near future.

# Find Breaking Changes with ApiPort

To obtain ApiPort, download it [here](https://github.com/Microsoft/dotnet-apiport/releases). Finding breaking changes with ApiPort is done by running the following command:
To obtain ApiPort, download it [here](https://github.com/Microsoft/dotnet-apiport/releases). Finding breaking changes with ApiPort is done
by running the following command:

```cmd
ApiPort.exe analyze -b -f [assembly]
Expand Down Expand Up @@ -110,11 +110,12 @@ As discussed earlier, the most important issue to address are the runtime issues

### Step 1: Runtime issues

Only one runtime issue was found, so we first take a look at that. It is categorized as a minor issue; however, there are ways to customize the reporting as the impact of a specific issue may be more serious for certain scenarios.
The report shows the following information for this issue:
Only one runtime issue was found, so we first take a look at that. It is categorized as a minor issue; however, there are ways to customize the
reporting as the impact of a specific issue may be more serious for certain scenarios. The report shows the following information for this issue:


| Field | Value |
|----|----|
|:----|:----|
| ID | 26 |
| API | System.Threading.Tasks.Task.WaitAll(System.Threading.Tasks.Task[],System.Int32) |
| Details | Task.WaitAll behavior was made more consistent in .NET 4.5.<br/> In the .NET Framework 4, these methods behaved inconsistently. When the time-out expired, if one or more tasks were completed or canceled before the method call, the method threw an AggregateException exception. When the time-out expired, if no tasks were completed or canceled before the method call, but one or more tasks entered these states after the method call, the method returned false.<br/> In the .NET Framework 4.5, these method overloads now return false if any tasks are still running when the time-out interval expired, and they throw an AggregateException exception only if an input task was cancelled (regardless of whether it was before or after the method call) and no other tasks are still running. |
Expand All @@ -126,20 +127,24 @@ The report shows the following information for this issue:
| Link | More info |


With this information, the next step is to look at the times in which Task.WaitAll is used and verify that the old inconsistent behavior was not being used. Identifying those locations will also help know where targeted testing should
be focused to ensure that the updated behavior works with the modifications.
With this information, the next step is to look at the times in which Task.WaitAll is used and verify that the old inconsistent behavior was
not being used. Identifying those locations will also help know where targeted testing should be focused to ensure that the updated behavior
works with the modifications.

After the issue has been addressed and tested, the runtime issues for this assembly has been addressed. Keep in mind that the number of call sites is not reflected in the report, just the presence of a call.
After the issue has been addressed and tested, the runtime issues for this assembly has been addressed. Keep in mind that the number of call
sites is not reflected in the report, just the presence of a call.

### Step 2: Retargeting Issue

*Note: This section is only needed when retargeting. If no retargeting will occur (i.e. running the same binary on .NET 4.0
and 4.6 without changing the target framework), these issues can be ignored*

The retargeting issue for this one should be addressed after the runtime issue has been addressed and when the assembly is being retargeted to a newer version, most likely to take advantage of new functionality. The report for this retargeting issue is a major issue, although, again, the severity of these changes are customizable as it is not a one-size-fit-all.
The retargeting issue for this one should be addressed after the runtime issue has been addressed and when the assembly is being
retargeted to a newer version, most likely to take advantage of new functionality. The report for this retargeting issue is a major
issue, although, again, the severity of these changes are customizable as it is not a one-size-fit-all.

| Field | Value |
|---|---|
|:---|:---|
| ID | 6 |
| API | System.Uri.#ctor(System.String) |
| Details | URI parsing has changed in several ways in .NET 4.5. Note, however, that these changes only affect code targeting .NET 4.5. If a binary targets .NET 4.0, the old behavior will be observed. Changes to URI parsing in .NET 4.5 include:<br /> - URI parsing will perform normalization and character checking according to the latest IRI rules in RFC 3987<br /> - Unicode normalization form C will only be performed on the host portion of the URI<br /> - Invalid mailto: URIs will now cause an exception<br /> - Trailing dots at the end of a path segment are now preserved<br /> - file:// URIs do not escape the '?' character<br /> - Unicode control characters U+0080 through U+009F are not supported<br /> - Comma characters (',' %2c) are not automatically unescaped |
Expand All @@ -151,5 +156,6 @@ The retargeting issue for this one should be addressed after the runtime issue h
| Link | More info |


This issue gives a list of cases wherein the changes may be manifest in an application. Since this change is most likely highly data-driven, a possible way to mitigate breaks with the new changes would be to find instances of
`System.Uri` use in the codebase and track the data that may be coming into it. This data could be analyzed to see if they may break with the new changes to `System.Uri`.
This issue gives a list of cases wherein the changes may be manifest in an application. Since this change is most likely highly
data-driven, a possible way to mitigate breaks with the new changes would be to find instances of `System.Uri` used in the codebase
and track the data that may be coming into it. This data could be analyzed to see if it may break with the new changes to `System.Uri`.
14 changes: 7 additions & 7 deletions docs/HowTo/Introduction.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,17 +12,17 @@ tools is to help identify possible problem areas in an assembly and help direct
The first goal of these tools are to help identify APIs that are not portable among the various .NET Platforms. These
include Microsoft supported platforms (Windows, Windows apps, DNX) as well as other implementations, such as Mono and
Xamarin. Some APIs may be removed on certain platforms (such as AppDomains, File I/O, etc), or refactored into other
types (such as some Reflection APIs). Sometimes, the fix is relatively simple, sometimes not as simple. This tool provides
information to help guide a developer to rework or rewrite certain parts of an assembly to be more portable and resilient
to version changes. For details, please see [here](PlatformPortability.md).
types (such as some Reflection APIs). Sometimes the fix will be relatively simple while other times it may be more involved.
This tool provides information to help guide a developer to rework or rewrite certain parts of an assembly to be more portable
and resilient to version changes. For details please see [here](PlatformPortability.md).

## Breaking Changes between .NET 4.x versions

Another goal of the tool is to provide guidance and insight into possible breaking changes on the .NET Framework that may
Another goal of the tools is to provide guidance and insight into possible breaking changes on the .NET Framework that may
apply to a given assembly. This functionality is currently restricted to .NET Framework 4.x given that it is updated in-place
with no side-by-side support for alternative versions. Most of these are considered benign changes that shouldn't affect
most applications. However, we understand that what may be low impact for one scenario may be very impactful breaking change
for another. For details, please see [here](BreakingChanges.md).
most applications; however, we understand that what may be low impact for one scenario may be a very impactful breaking change
for another. For details please see [here](BreakingChanges.md).

# Usage

Expand Down Expand Up @@ -71,7 +71,7 @@ The current options are:
-h, -?, --help Show help
```

For more details on analysis for portability, look [here](PlatformPortability.md) and for breaking change analysis, please
For more details on analysis for portability look [here](PlatformPortability.md). For breaking change analysis please
look [here](BreakingChanges.md).

For example, to analyze `foo.dll` against `.NET Core` to get an HTML report, the following command would be run:
Expand Down
2 changes: 1 addition & 1 deletion docs/HowTo/OfflineMode.md
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
# Offline Mode

There are times when using the web service is not ideal (extremely large data sets, limited network connectivity, privacy concerns)and
There are times when using the web service is not ideal (extremely large data sets, limited network connectivity, privacy concerns) and
there is a mode that can enable offline analysis of projects. This is not listed on the release downloads, but can be built manually.
The steps to do this:

Expand Down
Loading

0 comments on commit 2118dfa

Please sign in to comment.