Как сгенерировать открытый ключ Ed25519 из закрытого ключа с помощью libsodium?

Не все криптовалюты используют технологию secp256k1 для генерации пары ключей и цифровых подписей. Технология Curve25519 (часто используемая для поддержки обмена ключами ECDH) используется несколькими другими криптовалютами. Криптография Ed25519 (предназначенная для поддержки функциональности EdDSA) и криптография Curve25519 тесно связаны посредством преобразований, и существует тенденция начинать с ключей Ed25519 и преобразовывать их в пары ключей Curve25519.

Мы использовали эту ссылку в качестве источника восьми ED25519_SECRET_KEYS и соответствующих ED25519_PUBLIC_KEYS для использования в качестве тестовых векторов для применения реализаций пакета Ed25519.

Получил fludyberry/ed25519-donna , чтобы он функционировал должным образом. Однако я не смог вычислить ED25519_CURVE25519_PUBLIC_KEYS из ссылки, используя ed25519-donna, используя ее curved25519_scalarmult_basepoint()функцию для сопоставления. Это подтолкнуло меня к тому, чтобы попробовать jedisct1/libsodium . Получил crypto_scalarmult_base()результаты функций от libsodium, чтобы они соответствовали результатам от ed25519-donna :-)

Однако it is unclear how jedisct1/libsodium can be applied to generate public Ed25519 keys only from secret Ed25519 keys that are natively in an ASCII hexadecimal format:-( Кажется, что jedisct1/libsodium требует, чтобы ключи всегда генерировались из собственного процесса генерации пары ключей, а не из внешнего закрытого ключа.

Использовали натрия_hex2bin() для вставки закрытого ключа в шестнадцатеричной кодировке ASCII из ссылки в переменную ed25519_skpk из 64 символов без знака:

натрий_hex2bin(ed25519_skpk, 32, ED25519_SECRET_KEYS[ii], 64, NULL, NULL, NULL );

Результаты от следующей функции libsodium были такими, как и ожидалось:

crypto_scalarmult_base (curve25519_pk, ed25519_skpk)

Был немного разочарован, когда обнаружил, что crypto_sign_ed25519_sk_to_pk() был закодирован для извлечения открытого ключа из ed25519_skpk, который никогда не был инициализирован.

crypto_sign_ed25519_sk_to_pk (ed25519_pk, ed25519_skpk);

Немного разочаровался, не найдя функцию libsodium для вычисления ключа ed25519_pk, когда ed25519_skpk загружается с рабочим закрытым ключом из внешнего источника. Любая помощь будет принята с благодарностью.

Маленький нит: кривая Ed25519 используется для реализации EdDSA, а не ECDSA.
Фантастический взгляд на детали! Отражено изменение EdDSA.
К вашему сведению - существует множество разновидностей ed25519. tools.ietf.org/html/rfc8032#section-5 документы ed25519 , ed25519ph и ed25519ctx . Monero и I2P используют red25519 . См. geti2p.net/spec/proposals/146-red25519 для точки зрения I2P.

Ответы (2)

Невозможно напрямую вычислить открытый ключ ed25519 из закрытого ключа. Вместо этого используйте детерминированный закрытый ключ для создания начального числа, а затем используйте начальное число для повторного создания закрытого ключа с соответствующим ему открытым ключом. Предполагается, что следующий фрагмент кода ed25519_skpkуже инициализирован:

char           hex_ed_pk[65];                                      
unsigned char  seed[crypto_sign_SEEDBYTES];                       
unsigned char  ed25519_skpk[crypto_sign_ed25519_SECRETKEYBYTES];        
unsigned char  ed25519_pk[crypto_sign_ed25519_PUBLICKEYBYTES];

// COMPUTE ED25519 PUBLIC KEY, REQUIRES ESTABLISHING A SEED
(void)crypto_sign_ed25519_sk_to_seed( seed,ed25519_skpk);                
(void)crypto_sign_seed_keypair( ed25519_pk, ed25519_skpk, seed );      
(void)sodium_bin2hex( hex_ed_pk, 65, ed25519_pk, 32 );

В libsodium > 1.0.15 это crypto_scalarmult_ed25519_base()можно сделать.