CA1062: Validate arguments of public methods

Switch View :
ScriptFree
CA1062: Validate arguments of public methods

TypeName

ValidateArgumentsOfPublicMethods

CheckId

CA1062

Category

Microsoft.Design

Breaking Change

Non Breaking

Cause

An externally visible method dereferences one of its reference arguments without verifying whether that argument is null (Nothing in Visual Basic).

Rule Description

All reference arguments that are passed to externally visible methods should be checked against null. If appropriate, throw a ArgumentNullException when the argument is null.

If a method can be called from an unknown assembly because it is declared public or protected, you should validate all parameters of the method. If the method is designed to be called only by known assemblies, you should make the method internal and apply the InternalsVisibleToAttribute attribute to the assembly that contains the method.

How to Fix Violations

To fix a violation of this rule, validate each reference argument against null.

When to Suppress Warnings

You can suppress a warning from this rule if you are sure that the dereferenced parameter has been validated by another method call in the function.

Example

The following example shows a method that violates the rule and a method that satisfies the rule.

Visual Basic

Imports System

Namespace DesignLibrary

    Public Class Test

        ' This method violates the rule.
        Sub DoNotValidate(ByVal input As String)

            If input.Length <> 0 Then
                Console.WriteLine(input)
            End If

        End Sub

        ' This method satisfies the rule.
        Sub Validate(ByVal input As String)

            If input Is Nothing Then
                Throw New ArgumentNullException("input")
            End If

            If input.Length <> 0 Then
                Console.WriteLine(input)
            End If

        End Sub

    End Class

End Namespace


C#

public class Person
{
    public string Name { get; private set; }
    public int Age { get; private set; }

    public Person(string name, int age)
    {
        Name = name;
        Age = age;
    }

    // Copy constructor CA1062 fires because other is dereferenced
    // without being checked for null
    public Person(Person other)
        : this(other.Name, other.Age)
    {
    }
}



C#

using System;

namespace DesignLibrary
{
    public class Test
    {
        // This method violates the rule.
        public void DoNotValidate(string input)
        {
            if (input.Length != 0)
            {
                Console.WriteLine(input);
            }
        }

        // This method satisfies the rule.
        public void Validate(string input)
        {
            if (input == null)
            {
                throw new ArgumentNullException("input");
            }
            if (input.Length != 0)
            {
                Console.WriteLine(input);
            }
        }
    }
}


In Visual Studio 2005, this rule does not detect that parameters are being passed to another method that does the validation.

Visual Basic

Public Function Method(ByVal value As String) As String
    EnsureNotNull(value)

    ' Fires incorrectly    
    Return value.ToString()
End Function

Private Sub EnsureNotNull(ByVal value As String)
    If value Is Nothing Then
        Throw (New ArgumentNullException("value"))
    End If
End Sub


C#

public class Person
{
    public string Name { get; private set; }
    public int Age { get; private set; }

    public Person(string name, int age)
    {
        Name = name;
        Age = age;
    }

    // Copy constructor
    public Person(Person other)
        : this(PassThroughNonNull(other).Name,
          PassThroughNonNull(other).Age)
    {
    }

    // Null check method
    private static Person PassThroughNonNull(Person person)
    {
        if (person == null)
            throw new ArgumentNullException("person");
        return person;
    }
}


C#


public string Method(string value)
{
    EnsureNotNull(value);

    // Fires incorrectly    
    return value.ToString();
}

private void EnsureNotNull(string value)
{
    if (value == null)
        throw new ArgumentNullException("value");
}


Copy constructors that populate field or properties that are reference objects can also violate the CA1062 rule. The violation occurs because the copied object that is passed to the copy constructor might be null (Nothing in Visual Basic). To resolve the violation, use a static (Shared in Visual Basic) method to check that the copied object is not null.

In the following Person class example, the other object that is passed to the Person copy constructor might be null.


public class Person
{
    public string Name { get; private set; }
    public int Age { get; private set; }

    public Person(string name, int age)
    {
        Name = name;
        Age = age;
    }

    // Copy constructor CA1062 fires because other is dereferenced
    // without being checked for null
    public Person(Person other)
        : this(other.Name, other.Age)
    {
    }
}

In the following revised Person example, the other object that is passed to the copy constructor is first checked for null in the PassThroughNonNull method.

public class Person
{
    public string Name { get; private set; }
    public int Age { get; private set; }

    public Person(string name, int age)
    {
        Name = name;
        Age = age;
    }

    // Copy constructor
    public Person(Person other)
        : this(PassThroughNonNull(other).Name, 
          PassThroughNonNull(other).Age)
    { 
    }

    // Null check method
    private static Person PassThroughNonNull(Person person)
    {
        if (person == null)
            throw new ArgumentNullException("person");
        return person;
    }
}

Community Content

DanielRose
Check done in another method

If the check is done in another method (ex. in a Guard/Validate static class), then that method should have an attribute called "ValidatedNotNull" so code analysis knows that the argument is validated there.

See http://social.msdn.microsoft.com/Forums/en-US/vstscode/thread/52d40a8e-0dad-41e9-826a-a6fac21b266c for an example.


Patrick Sheahan
Incorrect firing when parameters are being passed to another method that does the validation.
&gt;&gt; In Visual Studio 2005, this rule does not detect that parameters are being passed to another method that does the validation.

Incredibly, this has regressed in VS2010, even with the new Phoenix engine! In fact, I have to turn this rule off because I have so many incorrect firings of this rule. This is not good.

[Patrick-MSFT]
Hi. The MSDN Library community content is designed primarily to enable MSDN users to provide feedback, extensions and explanations of the documentation. It is not a good way to have issues with the code analysis rules themselves addressed. To discuss the implementation of code analysis rules, post your questions or opinions on the Visual Studio Code Analysis and Code Metrics forum (http://social.msdn.microsoft.com/Forums/en-US/vstscode/). To provide feedback directly to the development team, you can file a bug on the Connect site for Visual Studio 2010 and .NET Framework 4 (https://connect.microsoft.com/VisualStudio). The dev team encourages your feedback through these channels.