CERT C++: INT35-C

Используйте правильные целочисленные точности

Описание

Определение правила

Используйте правильные целочисленные точности.[1]

Реализация Polyspace

Эта проверка проверяет превышение целочисленной точности.

Примеры

расширить все

Проблема

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

Риск

Использование размера целого числа в операции с целочисленной точностью может привести к целочисленному переполнению, переносу или неожиданным результатам. Для образца беззнаковое целое число может храниться в памяти в 64 битах, но использует только 48 битов, чтобы представлять его значение. Операция с 56 битами левого сдвига для этого целого числа является неопределенным поведением.

Предположение, что размер целого числа равен его точности, также может привести к проблемам переносимости программы между различными архитектурами.

Зафиксировать

Не используйте размер целого числа вместо его точности. Чтобы определить целочисленную точность, реализуйте стандартную программу точных расчетов или используйте функцию builtin, такую как __builtin_popcount().

Пример - Использование размера unsigned int для операции сдвига влево
#include <limits.h>

unsigned int func(unsigned int exp)
{
    if (exp >= sizeof(unsigned int) * CHAR_BIT) {
        /* Handle error */
    }
    return 1U << exp;
}

В этом примере функция использует операцию сдвига влево, чтобы вернуть значение 2, поднятое в степень exp. Операция сдвигает биты 1U по exp положения налево. The if оператор гарантирует, что операция не сдвигает биты на несколько позиций exp больше, чем размер unsigned int. Однако, если unsigned int содержит биты заполнения, значение, возвращаемое sizeof() больше, чем точность unsigned int. В результате некоторые значения exp может быть слишком большим, и операция сдвига может быть неопределенным поведением.

Коррекция - Реализуйте функцию для вычисления точности unsigned int

Одной из возможных коррекций является реализация функции popcount() который вычисляет точность unsigned int путем подсчета количества установленных бит.

#include <stddef.h>
#include <stdint.h>
#include <limits.h>

size_t popcount(uintmax_t);
#define PRECISION(umax_value) popcount(umax_value)


unsigned int func(unsigned int exp)
{
    if (exp >= PRECISION(UINT_MAX)) {
        /* Handle error */
    }
    return 1 << exp;
}




size_t popcount(uintmax_t num)
{
    size_t precision = 0;
    while (num != 0) {
        if (num % 2 == 1) {
            precision++;
        }
        num >>= 1;
    }
    return precision;
} 

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

Группа: 03. Целые числа (INT)
Введенный в R2019a

[1] Это программное обеспечение было создано MathWorks, включающее фрагменты: «Сайт SEI CERT-C», © 2017 Университет Карнеги Меллон, Веб-сайт SEI CERT-C + + © 2017 Университет Карнеги Меллон, "Стандарт кодирования SEI CERT C - Правила разработки безопасных, Надежные и безопасные системы - 2016 Edition ", © 2016 Университет Карнеги Меллон, и "Стандарт кодирования SEI CERT C++ - Правила разработки безопасных, Надежные и безопасные системы в C++ - 2016 Edition "© 2016 Университет Карнеги Меллон, с специального разрешения от его Института программной инженерии.

ЛЮБОЙ МАТЕРИАЛ УНИВЕРСИТЕТА КАРНЕГИ МЕЛЛОН И/ИЛИ ЕГО ИНЖЕНЕРНОГО ИНСТИТУТА ПРОГРАММНОГО ОБЕСПЕЧЕНИЯ, СОДЕРЖАЩИЙСЯ В НАСТОЯЩЕМ ДОКУМЕНТЕ, ПОСТАВЛЯЕТСЯ НА БАЗИСЕ «КАК ЕСТЬ». УНИВЕРСИТЕТ КАРНЕГИ МЕЛЛОН НЕ ДАЕТ НИКАКИХ ГАРАНТИЙ, ВЫРАЖЕННЫХ ИЛИ ПОДРАЗУМЕВАЕМЫХ, В ОТНОШЕНИИ ЛЮБОГО ВОПРОСА, ВКЛЮЧАЯ, НО НЕ ОГРАНИЧИВАЯСЬ, ГАРАНТИЮ ПРИГОДНОСТИ ДЛЯ ЦЕЛЕЙ ИЛИ КОММЕРЧЕСКОЙ ВЫГОДЫ, ИСКЛЮЧИТЕЛЬНОСТИ, ИЛИ УНИВЕРСИТЕТ КАРНЕГИ МЕЛЛОН НЕ ДАЕТ НИКАКИХ ГАРАНТИЙ В ОТНОШЕНИИ СВОБОДЫ ОТ ПАТЕНТА, ТОВАРНОГО ЗНАКА ИЛИ НАРУШЕНИЯ АВТОРСКИХ ПРАВ.

Это программное обеспечение и связанная с ним документация не были рассмотрены и не одобрены Университетом Карнеги-Меллон или его Институтом программной инженерии.