Predictable random output from predictable seed

Стандартная программа посева использует предсказуемый seed, делая выход предсказуемым

Описание

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

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

  • Функции стандартной библиотеки C, такие как srand, srandom и initstate

  • Функции стандартной библиотеки C++, такие как std::linear_congruential_engine<>::seed() и std::mersenne_twister_engine<>::seed() (а также конструкторы этих шаблонов классов)

Риск

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

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

Можно использовать другую функцию, чтобы сгенерировать менее предсказуемые семена.

Можно также использовать другой генератор случайных чисел, который не требует seed. Для примера, Windows® Функциональные rand_s API сами семена по умолчанию. Он использует информацию из всей системы, например, системное время, идентификаторы потоков, системный счетчик и кластеры памяти. Эта информация является более случайной, и пользователь не может получить доступ к этой информации.

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

Примеры

расширить все

#include <stdlib.h>
#include <time.h>

void seed_rng(int seed)
{
    srand(seed);
}

int generate_num(void)
{
    seed_rng(time(NULL) + 3);
    /* ... */
}

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

Коррекция - Используйте другой генератор случайных чисел

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


#define _CRT_RAND_S

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

int generate_num(void)
{
    unsigned int number;
    errno_t err;
    err = rand_s(&number);

    if(err != 0)
    {
        return number;
    }
    else
    {
        return err;
    }
}

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

Группа: Безопасность
Язык: C | C++
По умолчанию: Off
Синтаксис командной строки: RAND_SEED_PREDICTABLE
Влияние: Средний
ИДЕНТИФИКАТОР CWE: 330, 337
Введенный в R2015b