pki: Add a ssh_key_cmp() function.
Этот коммит содержится в:
родитель
e799c0ce7d
Коммит
2c04994443
@ -242,6 +242,11 @@ enum ssh_keytypes_e{
|
||||
SSH_KEYTYPE_ECDSA
|
||||
};
|
||||
|
||||
enum ssh_keycmp_e {
|
||||
SSH_KEY_CMP_PUBLIC = 0,
|
||||
SSH_KEY_CMP_PRIVATE
|
||||
};
|
||||
|
||||
/* Error return codes */
|
||||
#define SSH_OK 0 /* No error */
|
||||
#define SSH_ERROR -1 /* Error of some kind */
|
||||
@ -458,6 +463,9 @@ LIBSSH_API const char *ssh_key_type_to_char(enum ssh_keytypes_e type);
|
||||
LIBSSH_API enum ssh_keytypes_e ssh_key_type_from_name(const char *name);
|
||||
LIBSSH_API int ssh_key_is_public(const ssh_key k);
|
||||
LIBSSH_API int ssh_key_is_private(const ssh_key k);
|
||||
LIBSSH_API int ssh_key_cmp(const ssh_key k1,
|
||||
const ssh_key k2,
|
||||
enum ssh_keycmp_e what);
|
||||
|
||||
LIBSSH_API int ssh_pki_generate(enum ssh_keytypes_e type, int parameter,
|
||||
ssh_key *pkey);
|
||||
|
@ -36,6 +36,9 @@ void _ssh_pki_log(const char *function,
|
||||
ssh_key pki_key_dup(const ssh_key key, int demote);
|
||||
int pki_key_generate_rsa(ssh_key key, int parameter);
|
||||
int pki_key_generate_dss(ssh_key key, int parameter);
|
||||
int pki_key_compare(const ssh_key k1,
|
||||
const ssh_key k2,
|
||||
enum ssh_keycmp_e what);
|
||||
|
||||
/* SSH Private Key Functions */
|
||||
enum ssh_keytypes_e pki_privatekey_type_from_string(const char *privkey);
|
||||
|
@ -307,6 +307,7 @@ LIBSSH_API const char *ssh_message_auth_password(ssh_message msg);
|
||||
* @return The public key or NULL.
|
||||
*
|
||||
* @see ssh_key_dup()
|
||||
* @see ssh_key_cmp()
|
||||
* @see ssh_message_get()
|
||||
* @see ssh_message_type()
|
||||
*/
|
||||
|
34
src/pki.c
34
src/pki.c
@ -257,6 +257,40 @@ int ssh_key_is_private(const ssh_key k) {
|
||||
return (k->flags & SSH_KEY_FLAG_PRIVATE);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Compare keys if they are equal.
|
||||
*
|
||||
* @param[in] k1 The first key to compare.
|
||||
*
|
||||
* @param[in] k2 The second key to compare.
|
||||
*
|
||||
* @param[in] what What part or type of the key do you want to compare.
|
||||
*
|
||||
* @return 0 if equal, 1 if not.
|
||||
*/
|
||||
int ssh_key_cmp(const ssh_key k1,
|
||||
const ssh_key k2,
|
||||
enum ssh_keycmp_e what)
|
||||
{
|
||||
if (k1 == NULL || k2 == NULL) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (k1->type != k2->type) {
|
||||
ssh_pki_log("key types don't macth!");
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (what == SSH_KEY_CMP_PRIVATE) {
|
||||
if (!ssh_key_is_private(k1) ||
|
||||
!ssh_key_is_private(k2)) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
return pki_key_compare(k1, k2, what);
|
||||
}
|
||||
|
||||
ssh_signature ssh_signature_new(void)
|
||||
{
|
||||
struct ssh_signature_struct *sig;
|
||||
|
@ -267,6 +267,64 @@ int pki_key_generate_dss(ssh_key key, int parameter){
|
||||
return SSH_OK;
|
||||
}
|
||||
|
||||
int pki_key_compare(const ssh_key k1,
|
||||
const ssh_key k2,
|
||||
enum ssh_keycmp_e what)
|
||||
{
|
||||
switch (k1->type) {
|
||||
case SSH_KEYTYPE_DSS:
|
||||
if (DSA_size(k1->dsa) != DSA_size(k2->dsa)) {
|
||||
return 1;
|
||||
}
|
||||
if (bignum_cmp(k1->dsa->p, k2->dsa->p) != 0) {
|
||||
return 1;
|
||||
}
|
||||
if (bignum_cmp(k1->dsa->q, k2->dsa->q) != 0) {
|
||||
return 1;
|
||||
}
|
||||
if (bignum_cmp(k1->dsa->g, k2->dsa->g) != 0) {
|
||||
return 1;
|
||||
}
|
||||
if (bignum_cmp(k1->dsa->pub_key, k2->dsa->pub_key) != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (what == SSH_KEY_CMP_PRIVATE) {
|
||||
if (bignum_cmp(k1->dsa->priv_key, k2->dsa->priv_key) != 0) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case SSH_KEYTYPE_RSA:
|
||||
case SSH_KEYTYPE_RSA1:
|
||||
if (RSA_size(k1->rsa) != RSA_size(k2->rsa)) {
|
||||
return 1;
|
||||
}
|
||||
if (bignum_cmp(k1->rsa->e, k2->rsa->e) != 0) {
|
||||
return 1;
|
||||
}
|
||||
if (bignum_cmp(k1->rsa->n, k2->rsa->n) != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (what == SSH_KEY_CMP_PRIVATE) {
|
||||
if (bignum_cmp(k1->rsa->p, k2->rsa->p) != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (bignum_cmp(k1->rsa->q, k2->rsa->q) != 0) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case SSH_KEYTYPE_ECDSA:
|
||||
case SSH_KEYTYPE_UNKNOWN:
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
ssh_key pki_private_key_from_base64(const char *b64_key,
|
||||
const char *passphrase,
|
||||
ssh_auth_callback auth_fn,
|
||||
|
@ -993,6 +993,105 @@ int pki_key_generate_dss(ssh_key key, int parameter){
|
||||
return pki_key_generate(key, parameter, "dsa", SSH_KEYTYPE_DSS);
|
||||
}
|
||||
|
||||
static int _bignum_cmp(const gcry_sexp_t s1,
|
||||
const gcry_sexp_t s2,
|
||||
const char *what)
|
||||
{
|
||||
gcry_sexp_t sexp;
|
||||
bignum b1;
|
||||
bignum b2;
|
||||
|
||||
sexp = gcry_sexp_find_token(s1, what, 0);
|
||||
if (sexp == NULL) {
|
||||
return 1;
|
||||
}
|
||||
b1 = gcry_sexp_nth_mpi(sexp, 1, GCRYMPI_FMT_USG);
|
||||
gcry_sexp_release(sexp);
|
||||
if (b1 == NULL) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
sexp = gcry_sexp_find_token(s2, what, 0);
|
||||
if (sexp == NULL) {
|
||||
return 1;
|
||||
}
|
||||
b2 = gcry_sexp_nth_mpi(sexp, 1, GCRYMPI_FMT_USG);
|
||||
gcry_sexp_release(sexp);
|
||||
if (b2 == NULL) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (bignum_cmp(b1, b2) != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int pki_key_compare(const ssh_key k1,
|
||||
const ssh_key k2,
|
||||
enum ssh_keycmp_e what)
|
||||
{
|
||||
switch (k1->type) {
|
||||
case SSH_KEYTYPE_DSS:
|
||||
if (_bignum_cmp(k1->dsa, k2->dsa, "p") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->dsa, k2->dsa, "q") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->dsa, k2->dsa, "g") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->dsa, k2->dsa, "y") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (what == SSH_KEY_CMP_PRIVATE) {
|
||||
if (_bignum_cmp(k1->dsa, k2->dsa, "x") != 0) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case SSH_KEYTYPE_RSA:
|
||||
case SSH_KEYTYPE_RSA1:
|
||||
if (_bignum_cmp(k1->rsa, k2->rsa, "e") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->rsa, k2->rsa, "n") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (what == SSH_KEY_CMP_PRIVATE) {
|
||||
if (_bignum_cmp(k1->rsa, k2->rsa, "d") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->rsa, k2->rsa, "p") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->rsa, k2->rsa, "q") != 0) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (_bignum_cmp(k1->rsa, k2->rsa, "u") != 0) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case SSH_KEYTYPE_ECDSA:
|
||||
case SSH_KEYTYPE_UNKNOWN:
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
ssh_string pki_publickey_to_blob(const ssh_key key)
|
||||
{
|
||||
ssh_buffer buffer;
|
||||
|
@ -517,6 +517,9 @@ static void torture_pki_duplicate_key_rsa(void **state)
|
||||
|
||||
assert_string_equal(b64_key, b64_key_gen);
|
||||
|
||||
rc = ssh_key_cmp(privkey, privkey_dup, SSH_KEY_CMP_PRIVATE);
|
||||
assert_true(rc == 0);
|
||||
|
||||
ssh_key_free(pubkey);
|
||||
ssh_key_free(privkey);
|
||||
ssh_key_free(privkey_dup);
|
||||
@ -560,6 +563,9 @@ static void torture_pki_duplicate_key_dsa(void **state)
|
||||
|
||||
assert_string_equal(b64_key, b64_key_gen);
|
||||
|
||||
rc = ssh_key_cmp(privkey, privkey_dup, SSH_KEY_CMP_PRIVATE);
|
||||
assert_true(rc == 0);
|
||||
|
||||
ssh_key_free(pubkey);
|
||||
ssh_key_free(privkey);
|
||||
ssh_key_free(privkey_dup);
|
||||
|
Загрузка…
Ссылка в новой задаче
Block a user