Мы используем куки, чтобы пользоваться сайтом было удобно.
Хорошо
to the top
>
>
>
V2649. MISRA. All arguments of any...
menu mobile close menu
Проверка проектов
Дополнительная информация
toggle menu Оглавление

V2649. MISRA. All arguments of any type-generic macros from <tgmath.h> should have an appropriate essential type.

01 Авг 2025

Диагностическое правило основано на руководстве MISRA (Motor Industry Software Reliability Association) по разработке программного обеспечения.

Правило актуально только для языка C.

Все аргументы, передаваемые в макросы из заголовочного файла <tgmath.h>, должны иметь один из следующих типов: essentially signed, essentially unsigned, essentially real floating, essentially complex floating. Эти типы предназначены для арифметических операций, в дальнейшем будем называть их арифметическими.

Стандарт MISRA определяет собственную модель типов (Essential type model).

Использование аргументов essentially complex floating типа для следующих макросов может привести к неопределённому поведению:

atan2, cbrt, ceil, copysign, erf, erfc, exp2, expm1, fdim, floor, fma, fmax, fmin, fmod, frexp, hypot, ilogb, ldexp, lgamma, llrint, llround, log10, log1p, log2, logb, lrint, lround, nearbyint, nextafter, nexttoward, remainder, remquo, rint, round, scalbn, scalbln, tgamma, trunc

Примечание. Последний аргумент макросов frexp и remquo используется для записи результата, тип этого аргумента может отличаться от остальных.

Использование неарифметических типов в качестве аргументов может привести к неопределённому поведению, поскольку они не могут быть преобразованы к вещественным типам, которые используются в макросах из заголовочного файла <tgmath.h>.

Рассмотрим пример:

#include <tgmath.h>

char sampleSqrt(char ch)
{
  return sqrt(ch);
}

Здесь в качестве аргумента макроса sqrt используется переменная типа char. В результате раскрытия макроса будет вызвана функция, принимающая аргумент типа double, а сам аргумент преобразован к типу double. Однако, согласно стандарту MISRA, char не является арифметическим типом и не предназначен для использования в вычислениях.

Преобразование между вещественными и символьными типами лишено смысла, поскольку нет точного соответствия между этими двумя представлениями. В итоге подобное преобразование может привести к неопределённому поведению. Стандарт MISRA определяет следующую таблицу преобразований типов и случаев, когда таких преобразований следует избегать:

Исключения:

  • Переменная типа enum может быть приведена к синониму этого же типа.
  • Переменные, имеющие константные значения 0 и 1, могут быть приведены из целочисленного типа к Boolean.

В данном случае стоит использовать один из вещественных типов, например, double.

Исправленный пример:

#include <tgmath.h>

double sampleSqrt(double ch)
{
  return sqrt(ch);
}

Данная диагностика классифицируется как:

  • MISRA-C-2023-21.22