Skip to main content
A newer version of this page is available. .

Null Reference Analysis

  • 5 minutes to read

CodeRush provides the CRR0027 - Possible System.NullReferenceException analyzer which detects unprotected code that can potentially raise a System.NullReferenceException exception.

Null Reference Analysis Modes

CodeRush can analyze values in Trusting, Skeptical, and Thorough diagnostic modes. You can specify the Possible System.NullReferenceException diagnostic mode for methods, properties, parameters, fields, and local variables.

Options

The following sections describe each diagnostic mode:

Trusting

If an element is not checked for null in the current scope and does not have the [CanBeNull] attribute, the analyzer trusts this element and does not show the diagnostic.

In the example below, the SortElements method does not provide information whether Elements are null or not null. The analyzer considers Elements as not null in Trusting mode and does not show the diagnostic in the Code Issues window.

class TrustingMode {
    public List<string> Elements { get; set; }

    public void SortElements() {
        Elements.Sort();
    }
}

The analyzer shows the diagnostic in Trusting mode, for example, if the following code has a null check error:

class TrustingMode {
    public List<string> Elements { get; set; }

    public void SortElements() {
        if (Elements == null)
            Elements.Sort();
    }
}

You can mark the Elements property with the [CanBeNull] code annotation attribute to indicate this property can be null. In this case, the analyzer shows the diagnostic even if the code does not have a null check expression.

class TrustingMode {
    [CanBeNull]
    public List<string> Elements { get; set; }

    public void SortElements() {
        Elements.Sort();
    }
}

Skeptical

If an element is not checked for null in the current scope, the analyzer does not show the diagnostic for elements that have the [NotNull] attribute.

In the example below, the analyzer shows the diagnostic for the Elements property because this property is not checked for null.

class SkepticalMode {
    public List<string> Elements { get; set; }

    public int GetEmptyElementCount() {
        var count = 0;

        foreach (var element in Elements) {

            if (string.IsNullOrEmpty(element))
                count++;
        }
        return count;
    }
}

If you do not want the analyzer to show this diagnostic, add the null check.

class SkepticalMode {
    public List<string> Elements { get; set; }

    public int GetEmptyElementCount() {
        var count = 0;

        if (Elements == null)
            return 0;

        foreach (var element in Elements) {

            if (string.IsNullOrEmpty(element))
                count++;
        }
        return count;
    }
}

You can also use the [NotNull] code attribute to indicate the Elements property is not null.

class SkepticalMode {

    [NotNull]
    public List<string> Elements { get; set; }

    public int GetEmptyElementCount() {
        var count = 0;        

        foreach (var element in Elements) {

            if (string.IsNullOrEmpty(element))
                count++;
        }
        return count;
    }
}

Thorough

If an element is not checked for null in the current scope and the element does not have the [CanBeNull] or [NotNull] attribute, the analyzer checks if the element can never be null (lazy initialized, returns new created object, etc). The mode works more slowly than others.

In the following code, the analyzer shows the diagnostic in Skeptical mode but does not show it in Thorough mode because the Elements property always returns a non-null value.

class ThoroughMode {

    List<string> elements;

    public List<string> Elements {

        get

        {   
            if (elements == null)
                elements = new List<string>();
            return elements;
            }
        }

    public int GetEmptyElementCount() {

        var count = 0;

        foreach (var element in Elements) {

            if (string.IsNullOrEmpty(element))

                count++;
        }
        return count;
    }
}

Annotation Attributes

CodeRush checks annotation attributes by a partial name. This means you do not need to reference annotations, just declare them in code.