Main Content

AUTOSAR C++14 Rule A15-4-5

Checked exceptions that could be thrown from a function shall be specified together with the function declaration and they shall be identical in all function declarations and for all its overriders

Since R2021a

Description

Rule Definition

Checked exceptions that could be thrown from a function shall be specified together with the function declaration and they shall be identical in all function declarations and for all its overriders.

Rationale

In C++, there are no checked exceptions because the compiler does not force functions to specify or handle the exceptions that the functions might raise. Dynamic exception specification of the form throw(<>) is obsolete and error-prone. The exception specification prescribed in the C++ standard specifies only whether a function raises an exception or not by using the specifier noexcept. Because there is no official way to declare which exceptions might arise from a function, the AUTOSAR standard requires that each function declaration be accompanied by comments that document the exception handling of the function. This method of documenting the exceptions is similar to the JAVA exception handling mechanism.

Use comments to specify a list of exceptions that a static analysis tool must check. Before function declarations, use comments to document which of the checked exceptions are expected in the function.

For a class template, the possible exceptions depend on the template argument. Because you cannot predicts the possible exceptions arising from a class template, this rule does not apply for templates.

Polyspace Implementation

Polyspace® reports a violation of this rule when any of these conditions are true:

  • A function raises a checked exception but does not document it before its declaration.

  • A function does not raise all the checked exceptions that are documented in comments before its declaration.

  • A function documents an unchecked exception.

  • A function documents an exception but does not define it.

This checker ignores the class member functions that are not called in your code. Because this rule does not apply for templates, Polyspace does not report violations of this rule on templates.

When documenting the checked exception classes, separate different checked exception classes by using line breaks, except between the class declaration and the documenting comments. For example, in this code, a line break separates the checked exceptions class A and B. The documenting comment and declaration of each class are kept together:

/// @checkedException
class A{};

/// @checkedException
class B{};

Troubleshooting

If you expect a rule violation but Polyspace does not report it, see Diagnose Why Coding Standard Violations Do Not Appear as Expected.

Examples

expand all

#include <cstdint>
#include <stdexcept>

class ObjectType1{};
class ObjectType2{};

/// @checkedException
class TypeError : public std::exception
{
	// Implementation
};

/// @checkedException
class DimMismatch : public std::exception
{
	// Implementation
};

/// @checkedException
class SizeError : public std::exception
{
	// Implementation
};

/// @throw TypeError Unexpetced Object Type as Input
/// @throw DimMismatch Container Dimension Mismatched
/// @throw SizeError    Object Size Too large
void Transform1(ObjectType1& substrate,
               ObjectType2& coating) noexcept(false) //Compliant
{
	// ...
	throw TypeError();
	// ...
	throw DimMismatch();
	// ...
	throw SizeError();
	// ...
}

/// @throw TypeError Unexpetced Object Type as Input
void Transform2(ObjectType1& substrate,//Noncompliant
             ObjectType2& coating) noexcept(false) 
//The function raises SizeError
//but does not document it before its declaration.
{
	// ...
	throw TypeError();
	// ...
	throw SizeError();
	// ...
}

class ValidationError : std::exception

{
	// Implementation
};

/// @throw TypeError Unexpetced Object Type as Input
/// @throw DimMismatch Container Dimension Mismatched
/// @throw SizeError   Object Size Too large
/// @throw ValidationError Checksum is Negative
void Transform3(ObjectType1& substrate,//Noncompliant
               ObjectType2& coating) noexcept(false) 
// The function does not raise all the @throw exceptions
// The function documents an unchecked exception ValidationError.
{
	// ...
	throw TypeError();
	// ...
	throw SizeError();
	// ...
}

/// @throw TypeError Unexpetced Object Type as Input
/// @throw LengthMismatch Array Length Mismatched
void Transform4(void){//Noncompliant
// The function does not define the documented exception LengthMismatch
	// ...
	throw TypeError();
	// ...
	
}

In this example, the functions list their checked exceptions at the beginning of the file by using the tag @checkedException in comments. These functions then specify which of these checked exceptions are raised in their bodies by using the comment tag @throw before their declarations.

  • The function Transform1 is compliant with this rule because it specifies three checked exceptions before its declaration and then raises the same checked exceptions in its body.

  • The function Transform2 is not compliant with this rule because it raises the checked exceptionSizeError but does not document the exception in the comments before the function declaration.

  • The function Transform2 violates the rule in two different ways:

    • The function documents the checked exception DimMismatch in the comments before the function declaration but does not raise it in the function body.

    • The function documents the exception ValidationError before its declaration, but the exception is not listed as a checked exception.

  • The function Transform4 is noncompliant because it documents an exception LengthMismatch but the code does not have the definition of this type.

Check Information

Group: Exception handling
Category: Required, Automated

Version History

Introduced in R2021a

expand all