Использование GMP для криптографии: как получить случайные числа? - PullRequest
3 голосов
/ 20 марта 2012

Документация для GMP содержит только следующие алгоритмы генерации случайных чисел:

  • gmp_randinit_mt, Twister Мерсенна;
  • gmp_randinit_lc_2exp и gmp_randinit_lc_2exp_size, линейные конгруэнтные.

Существует также gmp_randinit_default, но он указывает на gmp_randinit_mt.

Ни криптография Мерсенна, ни линейные конгруэнтные генераторы не должны использоваться. Что обычно делают люди, когда они хотят использовать GMP для создания некоторого криптографического кода?

(Использование криптографического API для шифрования / дешифрования / и т. Д. Не помогает, потому что я бы на самом деле реализовал новый алгоритм, которого нет в крипто-библиотеках).

1 Ответ

0 голосов
/ 24 марта 2012

Отказ от ответственности: я только "возился" с ГСЧ, и это было больше года назад.

Если вы работаете в Linux, решение является относительно простым и недетерминированным.Просто откройте и прочитайте нужное количество бит из /dev/urandom.Однако, если вам нужно большое количество случайных битов для вашей программы, вы можете использовать меньшее количество бит из /dev/urandom в качестве начальных чисел для PRNG.

boost предлагает несколько PRNG и недетерминированный RNG random_device.random_device использует ту же самую /dev/urandom для Linux и аналогичную (IIRC) функцию для Windows, поэтому, если вам нужны Windows или X-платформа.

Конечно, вы можете захотеть написать / написать функцию на основена выбранном вами СПГ с использованием типов и функций GMP.


Редактировать:

#include<stdio.h>
#include<gmp.h>
#include<boost/random/random_device.hpp>

int main( int argc, char *argv[]){

    unsigned min_digits = 30;
    unsigned max_digits = 50;
    unsigned quantity = 1000;   // How many numbers do you want?
    unsigned sequence = 10;     // How many numbers before reseeding?

    mpz_t rmin;
    mpz_init(rmin);
    mpz_ui_pow_ui(rmin, 10, min_digits-1);

    mpz_t rmax;
    mpz_init(rmax);
    mpz_ui_pow_ui(rmax, 10, max_digits);

    gmp_randstate_t rstate;
    gmp_randinit_mt(rstate);

    mpz_t rnum;
    mpz_init(rnum);

    boost::random::random_device rdev;

    for( unsigned i = 0; i < quantity; i++){

        if(!(i % sequence)) 
            gmp_randseed_ui(rstate, rdev.operator ()());

        do{
            mpz_urandomm(rnum, rstate, rmax);
        }while(mpz_cmp(rnum, rmin) < 0);

        gmp_printf("%Zd\n", rnum);
    }

    return 0;
}
...