Предупреждение C6101

Возвращает неинициализированную память "имя параметра".

Успешный путь через функцию не задает _Out_ аннотированный параметр.

Замечания

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

Если поведение инициализации выполняется по проектированию, неправильные или отсутствующие заметки SAL, скорее всего, являются причиной предупреждения. Как правило, эти случаи можно устранить одним из двух способов: изменение _Out_ более подходящей заметки или использование _Success_() заметки для определения состояний успешности или ошибки функции. Важно, чтобы статические средства анализа имели правильные заметки в функции при анализе сайтов вызовов функции.

Исправление изменений в заметках параметров

Если параметр уже должен находиться в инициализированном состоянии, а функция условно изменяет ее, _Inout_ то заметка может быть более подходящей. Если другие заметки высокого уровня не соответствуют предполагаемому поведению, можно использовать такие заметки низкого уровня, как _Pre_null_, _Pre_satisfies_()и _Post_satisfies_() обеспечить дополнительную гибкость и контроль над ожидаемым состоянием параметра. Дополнительные сведения о заметках параметров см. в разделе "Аннотирование параметров функции" и возвращаемых значений.

Исправление путем определения успешных путей возврата

Анализатор выдает это предупреждение только в том случае, если код не инициализирует _Out_ параметр в путях успешности функции. Если заметки нет _Success_ и нет заметки возвращаемого типа функции, то он считает все пути возврата успешными. Дополнительные сведения о _Success_ и аналогичных заметках см. в заметках об успешном выполнении и сбое.

Имя анализа кода: RETURN_UNINIT_VAR

Пример

Следующий код создает это предупреждение. Так как функция возвращается void, анализатор учитывает все пути успешно. В этом случае правильное исправление, вероятно, будет изменять логику if инструкции, но в реальном мире код обычно не так просто, и решение зависит от предполагаемого поведения функции.

#include <sal.h>
void AlwaysInit(_Out_ int* output, int input) // : warning C6101: Returning uninitialized memory '*p'.: Lines: 2, 4, 9, 14, 2
{
  if( input > 0 )
  {
    *output = input;
    return;
  }
  else if( input < 0 )
  {
    *output = 0;
    return;
  }
  return; // Oops, input was 0
}

Чтобы сделать решение более интересным, мы предполагаем, что он не является допустимым для инициализации output при input наличии 0. Одним из способов является изменение возвращаемого значения функции на другой тип, например bool. Затем добавьте заметку _Success_ , чтобы определить успешные пути возврата.

_Success_(return == true)
bool InitNotZero(_Out_ int* output, int input)
{
  if( input > 0 )
  {
    *output = input;
    return true;
  }
  else if( input < 0 )
  {
    *output = 0;
    return true;
  }
  return false;
}

Если этот шаблон распространен в базе кода, можно добавить заметку в тип возвращаемого значения. Коды ошибок, такие как HRESULT из пакета SDK для Windows, дают вам поведение заметки _Success_ без необходимости добавлять ее в каждую функцию. Если вы уже используете аннотированный тип в качестве возвращаемого типа и хотите переопределить поведение, добавьте заметку в функцию, как показано в предыдущем примере.

using SuccessWhenTrue = _Success_(return == true) bool;

SuccessWhenTrue InitNotZero(_Out_ int* output, int input)
{
  // ...
}

См. также

Наборы правил для кода C++
Использование аннотаций SAL для уменьшения количества дефектов в коде C/C++