MISRA C++:2008 Rule 5-0-10

Если побитовые операторы ~ и <<будут применены к операнду с базовым типом символьного или короткого целого без знака без знака, результат должен быть сразу брошен к базовому типу операнда

Описание

Управляйте определением

Если побитовые операторы ~ и <<будут применены к операнду с базовым типом символьного или короткого целого без знака без знака, результат должен быть сразу брошен к базовому типу операнда.

Объяснение

Когда побитовые операторы ~ и << применяются к маленьким целочисленным типам, таким как короткое целое без знака и char без знака, операциям предшествует интегральное продвижение. Таким образом, маленькие целочисленные типы сначала продвинуты на больший целочисленный тип, и затем операция происходит. Результат их битовая операция может содержать неожиданные биты высшего порядка. Например:

uint8_t var = 0x5aU;
uint8_t result = (~var)>>4;
Бинарное представление var 0101 1010 и тот из ~var 1010 0101. Вы можете ожидать тот result 0000 1010. Поскольку var продвинут на большее целое число перед ~var вычисляется, результат становится 1111 1010. Биты высшего порядка могут быть неожиданными. Результаты таких операций могут зависеть от размера int в вашей реализации.

Чтобы избежать беспорядка и неожиданных ошибок, бросьте результат поразрядного ~ и >> операторы назад к базовому типу операндов перед использованием результатов. Например:

uint8_t var = 0x5aU;
uint8_t result = (static_cat<unit8_t>(~var))>>4;
Бинарное представление result в этом случае 0000 1010, который является ожидаемым значением.

Как исключение, не требуется кастинг, если вы применяете эти побитовые операторы на типы короткого целого, и затем сразу присваиваете результат объекту того же базового типа. Например, значением результата в этом случае является 0000 1010 не требуя броска.

uint8_t var = 0x5aU;
unit8_t result = ~var; // No higher order bits 
                       // due to implicit conversion
uint8_t result = results>>4;

Реализация Polyspace

Polyspace® отмечает использование поразрядного ~ и >> операторы, если все эти условия верны:

  • Операторы используются на unsigned short или unsigned char операнд.

  • Результат операции сразу не присвоен объекту, который имеет тот же базовый тип как операнд.

  • Результат используется, не будучи брошенным к базовому типу операнда.

Поиск и устранение проблем

Если вы ожидаете нарушение правила, но не видите его, относитесь, чтобы Диагностировать, Почему Кодирующие Стандартные Нарушения Не Появляются как ожидалось.

Примеры

развернуть все

#include<cstdint>
void foo(){
	uint8_t var = 0x5aU;
	uint8_t result;
	result = ( ~var ) >> 4; // Non-compliant
	result = static_cast<uint8_t>(( ~var )) >> 4; // Compliant
	uint8_t cbe = ~var;//Compliant by Exception
}

В этом примере Polyspace отмечает использование ~ на маленьком целочисленном var. ~ оператор отмечается потому что:

  • Это управляет на целом числе короткого целого без знака var.

  • Результат оператора используется в выражении, не бросая ~var к uint8_t.

Когда результат ~ оператор брошен к unit8_t, использование совместимо с этим правилом. Когда результат ~ сразу присвоен unit8_t переменная, использование совместимо к этому правилу исключением.

Проверяйте информацию

Группа: Выражения
Категория: необходимый
Введенный в R2013b