exponenta event banner

CERT C: STR34-C правил

Приведение символов к символу без знака перед преобразованием в более крупные целочисленные размеры

Описание

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

Приведение символов к символу без знака перед преобразованием в большее целое число. [1 ]

Внедрение Polyspace

Эта проверка проверяет, не используется ли значение символа со знаком.

Примеры

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

Проблема

Неправильное использование расширенного символьного значения происходит при преобразовании подписанного или простого символа char к более широкому целочисленному типу данных со знаком расширения. Затем результирующее расширенное по знаку значение используется в качестве индекса массива для сравнения с EOF или в качестве аргумента функции обработки символов.

Риск

Сравнение с EOF: Предположим, ваш компилятор реализует простой char введите как подписанный. В этой реализации символ с десятичной формой 255 (-1 в форме дополнения) сохраняется как подписанное значение. При преобразовании char переменная для более широкого типа данных int например, бит знака сохраняется (расширение знака). Это расширение знака приводит к преобразованию десятичной формы 255 в целое число -1, которое нельзя отличить от EOF.

Использовать в качестве индекса массива: С помощью аналогичных рассуждений нельзя использовать простую форму со знаком extended char переменные как индекс массива. Если бит знака сохранен, преобразование из char кому int может привести к отрицательным целым числам. Для индекса массива необходимо использовать положительные целочисленные значения.

Аргумент функции обработки символов: С помощью аналогичных рассуждений нельзя использовать расширенную простоту знака char переменные в качестве аргументов для функций обработки символов, объявленных в ctype.h, например, isalpha() или isdigit(). В соответствии со стандартом C11 (раздел 7.4), если указан целый аргумент, который не может быть представлен как unsigned char или EOF, результирующее поведение не определено.

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

Перед преобразованием в более широкий целочисленный тип данных приведите знак или простой char значение явно для unsigned char.

Пример - Расширенное знаковое значение по сравнению с EOF
#include <stdio.h>
#include <stdlib.h>
#define fatal_error() abort()

extern char parsed_token_buffer[20];

static int parser(char *buf)
{
    int c = EOF;
    if (buf && *buf) {
        c = *buf++;    
    }
    return c;
}

void func()
{
    if (parser(parsed_token_buffer) == EOF) { 
        /* Handle error */
        fatal_error();
    }
}

В этом примере функция parser может проходить строковый ввод buf. Если символ в строке имеет десятичную форму 255, при преобразовании в int переменная c, его значение становится -1, что неотличимо от EOF. Более позднее сравнение с EOF может привести к ложному положительному.

Коррекция - Приведение к unsigned char Перед преобразованием

Одной из возможных корректировок является отливка простой char значение для unsigned char перед преобразованием в более широкий int тип.

#include <stdio.h>
#include <stdlib.h>
#define fatal_error() abort()

extern char parsed_token_buffer[20];

static int parser(char *buf)
{
    int c = EOF;
    if (buf && *buf) {
        c = (unsigned char)*buf++;    
    }
    return c;
}

void func()
{
    if (parser(parsed_token_buffer) == EOF) { 
        /* Handle error */
        fatal_error();
    }
}

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

Группа: Правило 07. Символы и строки (STR)
Представлен в R2019a

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

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

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