exponenta event banner

CERT C++: MEM54-CPP

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

Описание

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

Обеспечить размещение новых с правильно выровненными указателями для достаточной емкости хранилища [1 ]

Внедрение Polyspace

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

Примеры

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

Проблема

Новое размещение, используемое при недостаточном хранении или несогласованных указателях, происходит при переходе указателя к размещению new у оператора недостаточно памяти для выделения памяти или он неправильно выровнен.

Предположим, что указатель ptr предварительно распределено m байт памяти в стеке и имеет выравнивание n. Например, если ptr является массивом:

uint8_t ptr[5];
выделенное хранилище sizeof(uint8_t) * 5 и выравнивание alignof(uint8_t). Если вы распределяете более m байты для этого указателя в месте размещения new выражение или если выравнивание, необходимое для выделения, больше, чем n, шашка поднимает нарушение. При определении выравнивания указателя средство проверки учитывает явные выравнивания, такие как std::align.

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

Риск

new оператор выделяет необходимый объем памяти для хранения объекта в куче и конструирует новый объект в выделенной памяти за одну операцию. Если требуется разделить выделение и конструкцию и поместить объект в предварительно выделенную память в стек или кучу, используется размещение new. Размещение new имеет преимущества перед new в определенных ситуациях, например, когда необходимо поместить объект в известную ячейку памяти.

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

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

Убедитесь, что указатель, используемый при размещении new операция имеет достаточный объем памяти для распределения и соответствия трасс.

Пример - Размещение new Используется с недостаточной емкостью хранилища и неправильно выровненными указателями
#include <new>
#include<memory>
#include <cstdint>

void Foo()
{
  uint8_t c;                
  uint64_t* ptr =
      new    // Non-compliant (insufficient storage, misaligned)
      (&c) uint64_t;
}

void Bar()
{
  uint8_t buf[sizeof(uint64_t)];    
  uint64_t* ptr =
      new            // Non-compliant (sufficient storage, misaligned)
      (buf) uint64_t;
}

void Baz()
{
  void* buf;
  std::size_t sp = 64;
  std::align(alignof(uint64_t), sizeof(uint64_t), buf, sp);
  uint64_t* ptr =
      new            // Compliant (sufficient storage, aligned)
      (buf) uint64_t;
}

В функции Foo, &c указывает на uint8_t и имеет однобайтовую память в стеке с однобайтовым выравниванием. Указатель передается на размещение new, который создает экземпляр uint64_t для этого требуется 8 байт памяти и 4-байтовое выравнивание. Это использование нарушает правило.

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

Функция Baz вызывает std::align создание указателя с правильной емкостью памяти (8 байт) и выравнивание (4 байта) для uint64_t. Это использование соответствует правилу.

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

Группа: 06. Управление памятью (MEM)
Представлен в R2020b

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

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

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