Как ключ DES генерируется из ключевой фразы в C?

(Не путать с генерацией подраздела алгоритма DES)
(редактировать: больше примеров)

Объяснение проблемы:

Я делаю это как часть школьного задания, где мне нужно перекодировать части OpenSSL в C, особенно те, которые относятся к криптосистемам PKI. До сих пор я с нуля перекодировал основной алгоритм DES ecb, cbc, 3des-ecb, а также 3des-cbc режимы работы. Другие части проекта включают MD5 и SHA256. Эта часть проекта фокусируется на генерации, манипулировании и использовании ключей RSA.

Часть манипуляции ключом RSA включает в себя шифрование заданного ключа парольной фразой.
(не с чистым key + initial vector один, как я делал раньше с DES)

Это требует преобразования пользовательской парольной фразы в ключ DES (и необязательный дополнительный IV при необходимости), а затем использовать его для шифрования ключа RSA. Я знаю, что общим термином для функции, которую я ищу, является PBKDF, или Функция получения ключа на основе пароля. Однако я не смог (через поиск man страницы OpenSSL или Google), чтобы узнать, какие именно функции (или функции) используются в OpenSSL для получения ключей.

Демонстрация генерации ключей DES с шифрованием ключей RSA:

Выполнение следующей команды без ключевой фразы создает незашифрованный ключ RSA example_plain_key,

ssh-keygen -t rsa -f example_plain_key

Затем выполнение следующих команд зашифрует example_plain_key с des шифровать ecb Режим. Каждая команда выводит зашифрованную версию в новый файл, поэтому она не меняет оригинал. Используйте одну и ту же фразу-пароль для обеих команд (например,пароль).

openssl rsa -DES-ECB -in id_rsa -out id_rsa_1
openssl rsa -DES-ECB -in id_rsa -out id_rsa_2

Ты можешь использовать head id_rsa а также head id_rsa_1 чтобы увидеть, как шифрование ключа меняет заголовок. Если сравнить два новых ключа с

diff id_rsa_1 id_rsa_2

они будут идентичны в заголовке и форматировании, но сам ключ будет зашифрован по-разному, даже если используется одна и та же ключевая фраза. Разница в том, что генерация ключа (я считаю) генерирует новую случайную соль каждый раз, когда она запускается. Я бы предположил, что алгоритм хеширования и количество итераций будут одинаковыми. Кроме того, в отличие от /etc/shadow на Unix-машинах соль не хранится рядом с ключом (или, по крайней мере, я не знаю, как ее прочитать).

Демонстрация генерации ключа DES из пароля:

Более конкретный пример DES:

openssl des -P

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

Мои выводы и вычтенные предположения:

  • Поиск "как шифруются ключи rsa?" Дает много результатов об использовании ключей RSA для шифрования. (иногда я ожидаю слишком многого от Google NLP)
  • Поиск "как ключи DES генерируются из ключевой фразы?" Дает много результатов о том, как сгенерировать 16 раундов подразделов des.
  • Я просмотрел исходники OpenSSL без удачи. Я сделаю исчерпывающий поиск, если это абсолютно необходимо, но код не самый читаемый или доступный для поиска.

  • прототип php

  • страница man perl
  • Ссылка, я думаю, будет более полезной, чем была
    (Примечание: у меня нет учетной записи в OpenSSL, но я не думаю, что это потребуется для просмотра)

Самые полезные результаты привели меня к мысли, что пример прототипа того, что я ищу, будет выглядеть примерно так:

#include <unistd.h>
#include <stdio.h>
#include <pwd.h>
// #include <something_else_maybe.h>

int     main(void)
{
    int     num_iterations = 1000;
    char    *salt;
    char    *passphrase;
    char    *key;

    passphrase = getpass("Password: ");
    salt = get_some_random_bytes(8); // assumed arbitrary length

    // the function in question
    key = example_pbkdf(md5_function, num_iterations, salt, 8, passphrase, strlen(passphrase));

    printf("Key (in hexadecimal or otherwise) is: %s\n", key);

    free(key);
    free(passphrase);
    free(salt);
    return (0);
}

Вещи, которые я специально ищу:

(Знание, где искать эти ответы, будет более ценным, чем сами ответы, но вся помощь приветствуется. Хотя мне нужен заголовок / source / prototype / etc в C).

  • Функция (если она существует), которая работает так, как показано выше. Это не должно быть идеальное совпадение, я больше беспокоюсь о том, что он делает, а не о точном прототипировании или использовании.
  • В качестве альтернативы (если он не существует) "рецепт" или последовательность операций, которые можно было бы обобщить как "алгоритм", который я ищу.
  • Генерация ключей DES. (хотя включение нескольких шифров, скажем, AES, тоже круто)
  • Как соль хранится в зашифрованном ключе RSA, если он есть (и если нет, то как его восстановить). Я знаю, что IV хранится в заголовке ключа, зашифрованного с помощью шифра в CBC.

1 ответ

Решение

Я нашел ответ на этот вопрос на бирже стека безопасности.

Спасибо, Grant Sanders, ваша ссылка на источник функции помогла мне указать источник функции (которую я планировал разобрать и идентифицировать), но оказалось, что фактический процесс намного проще. Даже если PBKDF по определению имеет ряд итераций и переменных хеш-функций, реализация OpenSSL просто использует одну итерацию MD5 с паролем и необработанной солью (возможно, жестко закодированную).

Я написал быстрый скрипт, который доказывает ответ выше (по крайней мере для DES) здесь.

Другие вопросы по тегам