exponenta event banner

В контекст не добавлены данные

Выполнение хэш-операции в пустом контексте может привести к ошибкам во время выполнения

Описание

Дефект возникает только при обновлении контекста дайджеста сообщений нулевыми данными или при выполнении последнего шага над контекстом дайджеста сообщений без выполнения какого-либо шага обновления.

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

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

void bar(unsigned char* src, int len, EVP_MD_CTX *ctx) {
    //ctx passed as argument of bar()
    EVP_DigestFinal(ctx, out_buf, &out_len); //no defect
}
EVP_MD_CTX glob_ctx;
void foo(unsigned char* src, int len) {
    //glob_ctx declared outside scope of foo()
    EVP_DigestFinal(&glob_ctx, out_buf, &out_len); //no defect
}

Риск

Выполнение шага обновления контекста с нулевыми данными может привести к ошибке во время выполнения.

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

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

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

Примеры

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

#include <openssl/evp.h>
#include <stdio.h>

unsigned char out_buf[EVP_MAX_MD_SIZE];
unsigned int out_len;

void func(unsigned char* src, int len)
{
    EVP_MD_CTX ctx;
    EVP_MD_CTX_init(&ctx);


    EVP_DigestInit(&ctx, EVP_sha256());
    EVP_DigestUpdate(&ctx, src, len);
    EVP_MD_CTX_init(&ctx);
    EVP_DigestFinal(&ctx, out_buf, &out_len);
}

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

Исправление - Выполнить заключительный шаг перед повторной инициализацией контекста

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

#include <openssl/evp.h>
#include <stdio.h>

unsigned char out_buf[EVP_MAX_MD_SIZE];
unsigned int out_len;

void func(unsigned char* src, int len)
{
    EVP_MD_CTX ctx;
    EVP_MD_CTX_init(&ctx);


    EVP_DigestInit(&ctx, EVP_sha256());
    EVP_DigestUpdate(&ctx, src, len);
    EVP_DigestFinal(&ctx, out_buf, &out_len);
    EVP_MD_CTX_init(&ctx);
} 
#include <openssl/evp.h>
#include <stdio.h>

unsigned char out_buf[EVP_MAX_MD_SIZE];
unsigned int out_len;

void func(unsigned char* src, int len)
{
    EVP_MD_CTX ctx;
    EVP_MD_CTX_init(&ctx);
    size_t cnt = 0;

    EVP_DigestInit(&ctx, EVP_sha256());
    EVP_DigestUpdate(&ctx, src, cnt);
    EVP_DigestFinal(&ctx, out_buf, &out_len);
}

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

Исправление - добавление ненулевых данных в контекст

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

#include <openssl/evp.h>
#include <stdio.h>

unsigned char out_buf[EVP_MAX_MD_SIZE];
unsigned int out_len;

void func(unsigned char* src, int len)
{
    EVP_MD_CTX ctx;
    EVP_MD_CTX_init(&ctx);

    EVP_DigestInit(&ctx, EVP_sha256());
    EVP_DigestUpdate(&ctx, src, len);
    EVP_DigestFinal(&ctx, out_buf, &out_len);
}

Информация о результатах

Группа: Криптография
Язык: C | C++
По умолчанию: Откл.
Синтаксис командной строки: CRYPTO_MD_NO_DATA
Воздействие: среднее
ИДЕНТИФИКАТОР CWE: 325
Представлен в R2020a