AUTOSAR C++14 Rule A27-0-1

Входные параметры от независимых компонентов должны быть подтверждены.

Описание

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

Входные параметры от независимых компонентов должны быть подтверждены.

Объяснение

Когда входные параметры от независимых компонентов непосредственно используются в исходном коде, атакующие могут получить полный или частичный контроль буфера приложений. Это управление позволяет атакующему отключить программу, просмотреть содержимое стека, получить доступ к содержимому памяти, изменить память в случайных местах и выполнить нежелательный код, замаскированный как исходный код программы.

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

  • Входные параметры получены от сетей

  • Входные параметры получили от других процессов и программного обеспечения посредством межпроцессного взаимодействия (IPC)

  • Входные параметры получены от API компонентов

Реализация Polyspace

Polyspace® повышает флаг, когда входные параметры от независимых компонентов используются без валидации. Отмеченное использование включает:

  • Стандартные программы, такие как sethostid (Linux®) или SetComputerName Windows®) использование внешне управляло аргументами, чтобы изменить идентификатор хоста. Смотрите Host change using externally controlled elements.

  • Функционирует, такие как putenv и setenv получите новые значения переменной окружения или из небезопасных источников. Смотрите Use of externally controlled environment variable.

  • Функционирует, такие как printf используйте спецификатор формата, который создается из небезопасных источников. Смотрите Tainted string format.

  • Массивы или указатели используют индекс, который получен из небезопасных источников. Смотрите Array access with tainted index.

  • Программа получает путь к команде из внешнего небезопасного источника. Смотрите Command executed from externally controlled path.

  • Программа выполняет команду, которая полностью или частично создается из внешне управляемого входа. Смотрите Execution of externally controlled command.

  • Библиотеки загрузок программы от фиксированных или внешне управляемых небезопасных путей, которыми могут частично или полностью управлять атакующие. Смотрите Library loaded from externally controlled path.

  • Цикл использует значения, полученные из небезопасных источников как его контур. Смотрите Loop bounded with tainted value.

  • Функции выделения памяти, такие как calloc или malloc, используйте аргумент размера из небезопасного источника. Смотрите Size argument to memory function is from an unsecure source.

  • Указатель разыменовывает, использует переменную смещения из неизвестного или небезопасного источника. Смотрите Pointer dereference with tainted offset.

  • Один или оба целочисленных операнда в операции деления прибывают из небезопасных источников. Смотрите Tainted division operand.

  • Один или оба целочисленных операнда в операции остатка (%) прибывает из небезопасных источников. Смотрите Tainted modulo operand.

  • Функции обработки строк, которые неявно разыменовывают буфер строки, такой как strcpy или sprintf используйте строки из небезопасных источников. Смотрите Tainted NULL or non-null-terminated string.

  • Значения из небезопасных источников неявно или явным образом преобразованы от со знаком до значений без знака. Смотрите Tainted sign change conversion.

  • Программа разыменовывает указатель из небезопасного источника, который может быть NULL или указать на неизвестную память. Смотрите Use of tainted pointer.

Polyspace рассматривает эти входные параметры как вход от независимого компонента или испорченный:

  • Энергозависимые объекты

  • Объект, которые взаимодействуют с пользователем

  • Объекты, которые взаимодействуют с оборудованием

  • Объекты, которые используют случайные числа или текущую дату и время

Чтобы рассмотреть весь вход снаружи текущего аналитического периметра как небезопасный, используйте -consider-analysis-perimeter-as-trust-boundary. Смотрите источники заражения в анализе Polyspace.

Когда вход от независимого компонента используется без валидации многократно в коде, Polyspace отмечает первое использование.

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

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

Примеры

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

#include <unistd.h>
#include <stdlib.h>

void bug_taintedhostid(void) {
    long userhid = strtol(getenv("HID"),NULL,10);
    sethostid(userhid);//Noncompliant
}

Этот пример устанавливает новый идентификатор хоста с помощью аргумента, переданного функции. Перед использованием идентификатора хоста проверяйте, что значение передало в.

Коррекция — предопределенный идентификатор хоста

Одна возможная коррекция должна изменить идентификатор хоста в предопределенный ID. Этот пример использует аргумент хоста в качестве переменной переключателя, чтобы выбрать между различными, предопределенными идентификаторами хоста.

#include <unistd.h>
#include <stdlib.h>

extern long called_taintedhostid_sanitize(long);
enum { HI0 = 1, HI1, HI2, HI3 };

void taintedhostid(void) {
    long host = strtol(getenv("HID"),NULL,10);
    long hid = 0;
    switch(host) {
        case HI0:
            hid = 0x7f0100;
            break;
        case HI1:
            hid = 0x7f0101;
            break;
        case HI2:
            hid = 0x7f0102;
            break;
        case HI3:
            hid = 0x7f0103;
            break;
        default:
            /* do nothing */
	    break;
    }
    if (hid > 0) {
        sethostid(hid);
    }
}
#define _XOPEN_SOURCE
#define _GNU_SOURCE
#include "stdlib.h"

void taintedenvvariable(void)
{
    char* path = getenv("APP_PATH");
    putenv(path); //Noncompliant
}

В этом примере, putenv изменяет переменную окружения. Путь path не проверялся, чтобы убедиться, что это - намеченный путь.

Коррекция — санирует путь

Одна возможная коррекция должна санировать путь, проверяя, что это совпадает с тем, что вы ожидаете.

#define _POSIX_C_SOURCE
#include <stdlib.h>
#include <string.h>

/* Function to sanitize a path */
const char * sanitize_path(const char* str) {
	/* secure white list of paths */
	static const char *const authorized_paths[] = {
		"/bin",
		"/usr/bin"
	};
	if (str != NULL) {
		for (int i = 0; i < sizeof(authorized_paths) / sizeof(authorized_paths[0]); i++)
		if (strcmp(authorized_paths[i], str) == 0) {
			return authorized_paths[i];
		}
	}
	return NULL;
}

void taintedenvvariable(void)
{
	const char* path = getenv("APP_PATH");
	path = sanitize_path(path);
	if (path != NULL) {
		if (setenv("PATH", path, /* overwrite = */1) != 0) {
			/* fatal error */
			exit(1);
		}
	}
} 
#include <stdio.h>
#include <unistd.h>
#define MAX 40
void taintedstringformat(void) {
	char userstr[MAX];
	read(0,userstr,MAX);
	printf(userstr);//Noncompliant   
}

Этот пример распечатывает входной параметр userstr. Строка неизвестна. Если это содержит элементы, такие как %, printf может интерпретировать userstr как формат строки вместо строки, заставляя вашу программу отказать.

Коррекция — печать как строка

Одна возможная коррекция должна распечатать userstr явным образом как строка так, чтобы не было никакой неоднозначности.

#include "stdio.h"
#include <unistd.h>
#define MAX 40

void taintedstringformat(void) {
	char userstr[MAX];
	read(0,userstr,MAX);
	printf("%.20s", userstr); 
}
#include <stdlib.h>
#include <stdio.h>
#define SIZE100 100
extern int tab[SIZE100];
static int tainted_int_source(void) {
  return strtol(getenv("INDEX"),NULL,10);
}
int taintedarrayindex(void) {
	int num = tainted_int_source();
    return tab[num];//Noncompliant  
}

В этом примере, индекс num получает доступ к массиву tab. Индекс num получен из небезопасного источника и функционального taintedarrayindex не проверяет, чтобы видеть если num в области значений tab.

Коррекция — область значений проверки перед использованием

Одна возможная коррекция должна проверять тот num находится в области значений перед использованием его.

#include <stdlib.h>
#include <stdio.h>
#define SIZE100 100
extern int tab[SIZE100];
static int tainted_int_source(void) {
	return strtol(getenv("INDEX"),NULL,10);
}
int taintedarrayindex(void) {
	int num = tainted_int_source();
	if (num >= 0 && num < SIZE100) {
		return tab[num]; 
	} else {
		return -1;
	}
}

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

void bug_taintedpathcmd() {
    char cmd[SIZE128] = "";
    char* userpath = getenv("MYAPP_PATH");

    strncpy(cmd, userpath, SIZE100);//Noncompliant
    strcat(cmd, "/ls *");
    /* Launching command */
    system(cmd);//Noncompliant 
}

Этот пример получает путь из переменной окружения MYAPP_PATH. Строка пути испорчена. Polyspace отмечает свое использование в strncopy функция. system запускает команду от испорченного пути, не проверяя значение пути. Если путь не является намеченным путем, ваша программа выполняется в неправильном месте.

Коррекция — использует доверяемый путь

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

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

/* Function to sanitize a string */
/* Any defect is localized here */
int sanitize_str(char* s, size_t n) {
    int res = 0;
    /* String is ok if */
    if (s && n>0 && n<SIZE128) {
        /* - string is not null                     */
        /* - string has a positive and limited size */
        s[n-1] = '\0';  /* Add a security \0 char at end of string *///Noncompliant
        /* Tainted pointer detected above, used as "firewall" */
        res = 1;
    }
    return res;
}

/* Authorized path ids */
enum { PATH0=1, PATH1, PATH2 };

void taintedpathcmd() {
    char cmd[SIZE128] = "";

    char* userpathid = getenv("MYAPP_PATH_ID");
    if (sanitize_str(userpathid, SIZE100)) {
        int pathid = atoi(userpathid);


        char path[SIZE128] = "";
        switch(pathid) {
            case PATH0:
                strcpy(path, "/usr/local/my_app0");
                break;
            case PATH1:
                strcpy(path, "/usr/local/my_app1");
                break;
            case PATH2:
                strcpy(path, "/usr/local/my_app2");
                break;
            default:
                /* do nothing */
		break;
        }
        if (strlen(path)>0) {
            strncpy(cmd, path, SIZE100);
            strcat(cmd, "/ls *");
            system(cmd);    
        }
    }
}
#include "stdlib.h"
#include "stdio.h"
#include "string.h"
#include "unistd.h"
#include "dlfcn.h"
#include "limits.h"
#define MAX 128


void taintedexternalcmd(void)
{
	char* usercmd;
	fgets(usercmd,MAX,stdin);
	char cmd[MAX] = "/usr/bin/cat ";
	strcat(cmd, usercmd);
	system(cmd);//Noncompliant 
}

Эта функция, взятая в качестве примера, вызывает команду от ввода данных пользователем, не проверяя переменную команды.

Коррекция — использует предопределенную команду

Одна возможная коррекция должна использовать switch оператор, чтобы запустить предопределенную команду, с помощью ввода данных пользователем в качестве переменной переключателя.

#define _XOPEN_SOURCE
#define _GNU_SOURCE

#include "stdlib.h"
#include "stdio.h"
#include "string.h"
#include "unistd.h"
#include "dlfcn.h"
#include "limits.h"

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};
enum { CMD0 = 1, CMD1, CMD2 };

void taintedexternalcmd(void)
{
    int usercmd = strtol(getenv("cmd"),NULL,10);
    char cmd[SIZE128] = "/usr/bin/cat ";

    switch(usercmd) {
        case CMD0:
            strcat(cmd, "*.c");
            break;
        case CMD1:
            strcat(cmd, "*.h");
            break;
        case CMD2:
            strcat(cmd, "*.cpp");
            break;
        default:
            strcat(cmd, "*.c");
    }
    system(cmd); 
}
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <dlfcn.h>
#include <limits.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

void* taintedpathlib() {
    void* libhandle = NULL;
    char lib[SIZE128] = "";
    char* userpath = getenv("LD_LIBRARY_PATH");
    strncpy(lib, userpath, SIZE128);//Noncompliant- userpath is tainted
    strcat(lib, "/libX.so");
    libhandle = dlopen(lib, 0x00001);//Noncompliant
    return libhandle;
}

Этот пример загружает библиотеку libX.so от переменной окружения LD_LIBRARY_PATH. Атакующий может изменить путь к библиотеке в этой переменной окружения. Фактическая библиотека, которую вы загружаете, могла быть различной библиотекой от той, которую вы предназначаете.

Коррекция — изменение и путь к проверке

Одна возможная коррекция должна измениться, как вы получаете путь к библиотеке и проверяете путь библиотеки прежде, чем открыть библиотеку. Этот пример получает путь как входной параметр, но затем выполняет следующие проверки на пути:

  • Функциональный sanitize_str защищает от возможного переполнения буфера.

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

#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include <dlfcn.h>
#include <limits.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

/* Use white list */
static const char *libX_safe_folder[] = {
  "/usr/",
  "/usr/lib",
  "/lib"
};

/* Return the index if the input is in the white list */
int identified_safe_libX_folder(const char* path)
{
  for (int i = 0; i < sizeof(libX_safe_folder) / sizeof(libX_safe_folder[0]); i ++)
    {
      if (strcmp(path, libX_safe_folder[i]) == 0)
      return i;
    }
  return -1;    
}

/* Function to sanitize a string */
char *sanitize_str(char* s, size_t n) {
  /* strlen is used here as a kind of firewall for tainted string errors */
  if (strlen(s) > 0 && strlen(s) < n)
    return s;
  else
    return NULL;
}

void* taintedpathlib(char* userpath) {
  void* libhandle = NULL;
  const char *const checked_userpath = sanitize_str(userpath, SIZE128);
  if (checked_userpath != NULL) {
    int index = identified_safe_libX_folder(checked_userpath);
    if (index > 0) {
      char lib[SIZE128] = "";
      strncpy(lib, libX_safe_folder[index], SIZE128);
      strcat(lib, "/libX.so");
      libhandle = dlopen(lib, RTLD_LAZY);    
    }
  }
  return libhandle;
}

#include<stdio.h>
enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

int taintedloopboundary(void) {
    int count;
    scanf("%d", &count);
    int res = 0;
    for (int i=0 ; i < count; ++i) {//Noncompliant
        res += i;
    }
    return res;
}

В этом примере функция использует ввод данных пользователем, чтобы циклично выполнить count \times. count мог быть любой номер, потому что значение не проверяется прежде, чем запустить for цикл.

Коррекция: зафиксируйте испорченное управление циклом

Одна возможная коррекция должна зафиксировать испорченное управление циклом. Подтверждать испорченную переменную цикла count, этот пример ограничивает count к минимальному значению и максимальному значению при помощи подставляемых функций min и max. Независимо от ввода данных пользователем, значения count остается в известной области значений.

#include<stdio.h>
#include<algorithm>
#define MIN 50
#define MAX 128
static  inline int max(int a, int b) { return a > b ? a : b;}
static inline int min(int a, int b) { return a < b ? a : b; }

int taintedloopboundary(void) {
	int count;
	scanf("%d", &count);
	int res = 0;
	count = max(MIN, min(count, MAX));
	for (int i=0 ; i<count ; ++i) { 
		res += i;
	} 
	return res;
}
Коррекция — проверка испорченное управление циклом

Другая возможная коррекция должна проверять нижнюю границу и верхнюю границу испорченной переменной контура цикла прежде, чем запустить for цикл. Этот пример проверяет нижние и верхние границы count и выполняет цикл только когда count между 0 и 127.

#include<stdio.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};


int taintedloopboundary(void) {
    int count;
    scanf("%d", &count);
    int res = 0;

    if (count>=0 && count<SIZE128) {
        for (int i=0 ; i<count ; ++i) { 
            res += i;
        }
    }
    return res;
}
#include<stdio.h>
#include <stdlib.h>

int* bug_taintedmemoryallocsize(void) {
    size_t size;
    scanf("%zu", &size);
    int* p = (int*)malloc(size);//Noncompliant
    return p;
}

В этом примере, malloc выделяет size байты памяти для указателя p. Переменная size прибывает от пользователя программы. Его значение не проверяется, и это могло быть больше, чем сумма доступной памяти. Если size больше, чем количество доступных байтов, ваша программа могла отказать.

Коррекция — Размер Проверки Памяти, которая будет Выделена

Одна возможная коррекция должна проверять размер памяти, которую вы хотите выделить прежде, чем выполнить malloc операция. Этот пример проверки, чтобы видеть, если size положительно и меньше, чем максимальный размер.

#include<stdio.h>
#include <stdlib.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

int* corrected_taintedmemoryallocsize(void) {
    size_t size;
    scanf("%zu", &size);
    int* p = NULL;
    if (size>0 && size<SIZE128) {          /* Fix: Check entry range before use */
        p = (int*)malloc((unsigned int)size);
    }
    return p;
}
#include <stdio.h>
#include <stdlib.h>
enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};
extern void read_pint(int*);

int taintedptroffset(void) {
    int offset;
    scanf("%d",&offset);
    int* pint = (int*)calloc(SIZE10, sizeof(int));
    int c = 0;
    if(pint) {
        /* Filling array */
        read_pint(pint);
        c = pint[offset];//Noncompliant
        free(pint);
    }
    return c;
}

В этом примере функция инициализирует целочисленный указатель pint. Указатель разыменовывается с помощью входного индекса offset. Значение offset мог найтись вне области значений указателя, вызвав ошибку из области значений.

Коррекция — индекс проверки прежде разыменовывает

Одна возможная коррекция должна подтвердить значение offset. Продолжите разыменование указателя только если offset в допустимой области значений.

#include <stdlib.h>
#include <stdio.h>
enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};
extern void read_pint(int*);

int taintedptroffset(void) {
    int offset;
    scanf("%d",&offset);
    int* pint = (int*)calloc(SIZE10, sizeof(int));
    int c = 0;
    if (pint) {
        /* Filling array */
        read_pint(pint);
        if (offset>0 && offset<SIZE10) {
            c = pint[offset];
        }
        free(pint);
    }
    return c;
}
#include <limits.h>
#include <stdio.h>

extern void print_int(int);

int taintedintdivision(void) {
    long num, denum;
    scanf("%lf %lf", &num, &denum);
    int r =  num/denum; //Noncompliant
    print_int(r);
    return r;
}

Эта функция, взятая в качестве примера, делит две переменные аргумента, затем распечатывает и возвращает результат. Значения аргументов неизвестны и могут вызвать деление на нуль или целочисленное переполнение.

Коррекция — контрольные числа

Одна возможная коррекция должна проверять значения числителя и знаменателя прежде, чем выполнить деление.

#include <limits.h>
#include <stdio.h>

extern void print_long(long);

int taintedintdivision(void) {
    long num, denum;
    scanf("%lf %lf", &num, &denum);
    long res= 0;
    if (denum!=0 && !(num==INT_MIN && denum==-1)) {
        res = num/denum;
    }
    print_long(res);
    return res;
}
#include <stdio.h>
extern void print_int(int);

int taintedintmod(void) {
    int userden;
    scanf("%d", &userden);
    int rem =  128%userden; //Noncompliant
    print_int(rem);
    return rem;
}

В этом примере функция выполняет операцию с модулем при помощи ввода данных пользователем. Вход не проверяется прежде, чем вычислить остаток для значений, которые могут разрушить программу, такой как 0 и-1.

Коррекция — значения операнда проверки

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

#include<stdio.h>
extern void print_int(int);

int taintedintmod(void) {
    int userden;
    scanf("%d", &userden);
    int rem = 0;
    if (userden > 0 ) { 
        rem = 128 % userden; 
    }
    print_int(rem);
    return rem;
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#define SIZE128 128
#define MAX 40
extern void print_str(const char*);
void warningMsg(void)
{
	char userstr[MAX];
	read(0,userstr,MAX);
	char str[SIZE128] = "Warning: ";
	strncat(str, userstr, SIZE128-(strlen(str)+1));//Noncompliant
	print_str(str);
}


В этом примере, строка str конкатенирован с аргументом userstr. Значение userstr неизвестно. Если размер userstr больше доступного пробела, переполнение конкатенации.

Коррекция — подтверждает данные

Одна возможная коррекция должна проверять размер userstr и убедитесь, что строка отключена пустым указателем перед использованием его в strncat. Этот пример использует функцию помощника, sansitize_str, подтверждать строку. Дефекты сконцентрированы в этой функции.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#define SIZE128 128
#define MAX 40
extern void print_str(const char*);
int sanitize_str(char* s) {
	int res = 0; 
	if (s && (strlen(s) > 0)) { // Noncompliant-TAINTED_STRING only flagged here
		// - string is not null
		// - string has a positive and limited size
		// - TAINTED_STRING on strlen used as a firewall
		res = 1;
	}
	return res; 
}
void warningMsg(void)
{
	char userstr[MAX];
	read(0,userstr,MAX);
	char str[SIZE128] = "Warning: ";
	if (sanitize_str(userstr))	
		strncat(str, userstr, SIZE128-(strlen(str)+1));
	print_str(str);
}
Коррекция — подтверждает данные

Другая возможная коррекция должна вызвать функциональный errorMsg и warningMsg с определенными строками.

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

#define SIZE128 128

extern void print_str(const char*);

void warningMsg(char* userstr)
{
    char str[SIZE128] = "Warning: ";
    strncat(str, userstr, SIZE128-(strlen(str)+1));
    print_str(str);
}

void errorMsg(char* userstr)
{
  char str[SIZE128] = "Error: ";
  strncat(str, userstr, SIZE128-(strlen(str)+1));
  print_str(str);
}

int manageSensorValue(int sensorValue) {
  int ret = sensorValue;
  if ( sensorValue < 0 ) {
    errorMsg("sensor value should be positive");
    exit(1);
  } else if ( sensorValue > 50 ) {
    warningMsg("sensor value greater than 50 (applying threshold)...");
    sensorValue = 50;
  }
  
  return sensorValue;
}
#include <stdlib.h>
#include <string.h>
#include <stdio.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

void bug_taintedsignchange(void) {
    int size;
    scanf("%d",&size);
    char str[SIZE128] = "";
    if (size<SIZE128) {
        memset(str, 'c', size); //Noncompliant
    }
}

В этом примере, char буфер создается и заполнил использование memset. Аргумент размера к memset входной параметр к функции.

Вызов memset неявно преобразует size к беззнаковому целому. Если size большое отрицательное число, абсолютное значение могло быть слишком большим, чтобы представлять как целое число, вызвав переполнение буфера.

Коррекция — контрольное число size

Одна возможная коррекция должна проверять если size в допустимой области значений. Эта коррекция проверяет если size больше нуля и меньше, чем buffer size прежде, чем вызвать memset.

#include <stdlib.h>
#include <string.h>
#include <stdio.h>

enum {
    SIZE10  =  10,
    SIZE100 = 100,
    SIZE128 = 128
};

void corrected_taintedsignchange(void) {
    int size;
    scanf("%d",&size);
    char str[SIZE128] = "";
    if (size>0 && size<SIZE128) {
        memset(str, 'c', size);  
    }
}
#include<stdlib.h>
void taintedptr(void) {
	char *p = getenv("ARG");
	char x = *(p+10);//Noncompliant  
}

В этом примере, указатель *p точки к строке неизвестного размера. Во время операции разыменования указатель может быть пустым или указать на неизвестную память, которая может привести к отказу сегментации.

Коррекция — указатель проверки

Одна возможная коррекция должна санировать указатель перед использованием его. Этот пример проверяет, является ли указателем nullptr прежде чем это будет разыменовано.

#include<stdlib.h>
#include <string.h> 
void taintedptr(void) {
	char *p = getenv("ARG");
	if(p!=nullptr && strlen(p)>10)
	{
	char x = *(p+10);
	}
}

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

Группа: библиотека ввода/вывода
Категория: необходимый, неавтоматизированный
Введенный в R2021b