C# compiler strict mode

The C# compilers has some hidden features. Today I've discovered a new compiler option. The author of a recent issue on GitHub indicates that the C# compiler allows to compare an IntPtr with null, which at runtime is always false. He suggests the compiler should raise an error in this case. The answer of Sam Harwell describes a compiler option, /features:strict, to detect this error and a few other potential errors in your code.

To enable it, you must add <Features>strict</Features> to your csproj file:

<Project Sdk="Microsoft.NET.Sdk">
  <PropertyGroup>
    <OutputType>Exe</OutputType>
    <TargetFramework>netcoreapp2.1</TargetFramework>
    <Features>strict</Features>
  </PropertyGroup>
</Project>

If your solution has many projects and you want to enable this compiler option for all projects, you can create a file named Directory.Build.props at the root of your solution with the content (MSBuild documentation):

<Project>
  <PropertyGroup>
    <Features>strict</Features>
  </PropertyGroup>
</Project>

Here are some errors that will be reported by using this feature strict:

IntPtr ptr = IntPtr.Zero;
if (ptr == null) // Warning CS8073 The result of the expression is always 'false' since a value of type 'IntPtr' is never equal to 'null' of type 'IntPtr?'
lock (null) // Error CS0185 '<null>' is not a reference type as required by the lock statement
{
}
var o = new object();
if (o is Math) // Error CS7023 The second operand of an 'is' or 'as' operator may not be static type 'Math'
{
}

I really hope this flag will be the default behavior in a next release of C#. Maybe they can enable it by default based on the language version of the project. But at the moment you must enable it manually…

Note that this flag is not documented and not well-known. After the comment on GitHub, the CoreCLR has started a new pull request to use this option in their codebase (Fix invalid IntPtr == null comparisons, set strict mode for Roslyn]).

Leave a reply