1
1

Add error checking to publickey_from_privatekey().

git-svn-id: svn+ssh://svn.berlios.de/svnroot/repos/libssh/trunk@433 7dcaeef0-15fb-0310-b436-a5af3365683c
Этот коммит содержится в:
Andreas Schneider 2009-04-08 13:27:39 +00:00
родитель 89670904c0
Коммит 8333393470

Просмотреть файл

@ -299,81 +299,166 @@ error:
* \returns the public key * \returns the public key
* \see publickey_to_string() * \see publickey_to_string()
*/ */
PUBLIC_KEY *publickey_from_privatekey(PRIVATE_KEY *prv){ PUBLIC_KEY *publickey_from_privatekey(PRIVATE_KEY *prv) {
PUBLIC_KEY *key; PUBLIC_KEY *key = NULL;
#ifdef HAVE_LIBGCRYPT #ifdef HAVE_LIBGCRYPT
gcry_sexp_t sexp; gcry_sexp_t sexp;
const char *tmp; const char *tmp = NULL;
size_t size; size_t size;
STRING *p,*q,*g,*y,*e,*n; STRING *p = NULL;
STRING *q = NULL;
STRING *g = NULL;
STRING *y = NULL;
STRING *e = NULL;
STRING *n = NULL;
#endif /* HAVE_LIBGCRYPT */ #endif /* HAVE_LIBGCRYPT */
key=malloc(sizeof(PUBLIC_KEY)); key = malloc(sizeof(PUBLIC_KEY));
if (key == NULL) { if (key == NULL) {
return NULL; return NULL;
} }
key->type=prv->type;
switch(key->type){ key->type = prv->type;
case TYPE_DSS: switch(key->type) {
case TYPE_DSS:
#ifdef HAVE_LIBGCRYPT #ifdef HAVE_LIBGCRYPT
sexp=gcry_sexp_find_token(prv->dsa_priv,"p",0); sexp = gcry_sexp_find_token(prv->dsa_priv, "p", 0);
tmp=gcry_sexp_nth_data(sexp,1,&size); tmp = gcry_sexp_nth_data(sexp, 1, &size);
p=string_new(size); p = string_new(size);
string_fill(p,(char *)tmp,size); if (p == NULL) {
gcry_sexp_release(sexp); goto error;
sexp=gcry_sexp_find_token(prv->dsa_priv,"q",0); }
tmp=gcry_sexp_nth_data(sexp,1,&size); string_fill(p,(char *) tmp, size);
q=string_new(size); gcry_sexp_release(sexp);
string_fill(q,(char *)tmp,size);
gcry_sexp_release(sexp); sexp = gcry_sexp_find_token(prv->dsa_priv,"q",0);
sexp=gcry_sexp_find_token(prv->dsa_priv,"g",0); tmp = gcry_sexp_nth_data(sexp,1,&size);
tmp=gcry_sexp_nth_data(sexp,1,&size); q = string_new(size);
g=string_new(size); if (q == NULL) {
string_fill(g,(char *)tmp,size); goto error;
gcry_sexp_release(sexp); }
sexp=gcry_sexp_find_token(prv->dsa_priv,"y",0); string_fill(q,(char *) tmp,size);
tmp=gcry_sexp_nth_data(sexp,1,&size); gcry_sexp_release(sexp);
y=string_new(size);
string_fill(y,(char *)tmp,size); sexp = gcry_sexp_find_token(prv->dsa_priv, "g", 0);
gcry_sexp_release(sexp); tmp = gcry_sexp_nth_data(sexp,1,&size);
gcry_sexp_build(&key->dsa_pub,NULL,"(public-key(dsa(p %b)(q %b)(g %b)(y %b)))",string_len(p),p->string,string_len(q),q->string,string_len(g),g->string,string_len(y),y->string); g = string_new(size);
free(p); if (g == NULL) {
free(q); goto error;
free(g); }
free(y); string_fill(g,(char *) tmp,size);
gcry_sexp_release(sexp);
sexp=gcry_sexp_find_token(prv->dsa_priv,"y",0);
tmp=gcry_sexp_nth_data(sexp,1,&size);
y = string_new(size);
if (y == NULL) {
goto error;
}
string_fill(y,(char *) tmp,size);
gcry_sexp_release(sexp);
gcry_sexp_build(&key->dsa_pub, NULL,
"(public-key(dsa(p %b)(q %b)(g %b)(y %b)))",
string_len(p), p->string,
string_len(q), q->string,
string_len(g), g->string,
string_len(y), y->string);
string_burn(p);
string_free(p);
string_burn(q);
string_free(q);
string_burn(g);
string_free(g);
string_burn(y);
string_free(y);
#elif defined HAVE_LIBCRYPTO #elif defined HAVE_LIBCRYPTO
key->dsa_pub=DSA_new(); key->dsa_pub = DSA_new();
key->dsa_pub->p=BN_dup(prv->dsa_priv->p); if (key->dsa_pub == NULL) {
key->dsa_pub->q=BN_dup(prv->dsa_priv->q); goto error;
key->dsa_pub->pub_key=BN_dup(prv->dsa_priv->pub_key); }
key->dsa_pub->g=BN_dup(prv->dsa_priv->g); key->dsa_pub->p = BN_dup(prv->dsa_priv->p);
#endif key->dsa_pub->q = BN_dup(prv->dsa_priv->q);
break; key->dsa_pub->g = BN_dup(prv->dsa_priv->g);
case TYPE_RSA: key->dsa_pub->pub_key = BN_dup(prv->dsa_priv->pub_key);
case TYPE_RSA1: if (key->dsa_pub->p == NULL ||
key->dsa_pub->q == NULL ||
key->dsa_pub->g == NULL ||
key->dsa_pub->pub_key == NULL) {
goto error;
}
#endif /* HAVE_LIBCRYPTO */
break;
case TYPE_RSA:
case TYPE_RSA1:
#ifdef HAVE_LIBGCRYPT #ifdef HAVE_LIBGCRYPT
sexp=gcry_sexp_find_token(prv->rsa_priv,"n",0); sexp = gcry_sexp_find_token(prv->rsa_priv, "n", 0);
tmp=gcry_sexp_nth_data(sexp,1,&size); tmp = gcry_sexp_nth_data(sexp, 1, &size);
n=string_new(size); n = string_new(size);
string_fill(n,(char *)tmp,size); if (n == NULL) {
gcry_sexp_release(sexp); goto error;
sexp=gcry_sexp_find_token(prv->rsa_priv,"e",0); }
tmp=gcry_sexp_nth_data(sexp,1,&size); string_fill(n, (char *) tmp, size);
e=string_new(size); gcry_sexp_release(sexp);
string_fill(e,(char *)tmp,size);
gcry_sexp_release(sexp); sexp = gcry_sexp_find_token(prv->rsa_priv, "e", 0);
gcry_sexp_build(&key->rsa_pub,NULL,"(public-key(rsa(n %b)(e %b)))",string_len(n),n->string,string_len(e),e->string); tmp = gcry_sexp_nth_data(sexp, 1, &size);
free(e); e = string_new(size);
free(n); if (e == NULL) {
goto error;
}
string_fill(e, (char *) tmp, size);
gcry_sexp_release(sexp);
gcry_sexp_build(&key->rsa_pub, NULL,
"(public-key(rsa(n %b)(e %b)))",
string_len(n), n->string,
string_len(e), e->string);
if (key->rsa_pub == NULL) {
goto error;
}
string_burn(e);
string_free(e);
string_burn(n);
string_free(n);
#elif defined HAVE_LIBCRYPTO #elif defined HAVE_LIBCRYPTO
key->rsa_pub=RSA_new(); key->rsa_pub = RSA_new();
key->rsa_pub->e=BN_dup(prv->rsa_priv->e); if (key->rsa_pub == NULL) {
key->rsa_pub->n=BN_dup(prv->rsa_priv->n); goto error;
}
key->rsa_pub->e = BN_dup(prv->rsa_priv->e);
key->rsa_pub->n = BN_dup(prv->rsa_priv->n);
if (key->rsa_pub->e == NULL ||
key->rsa_pub->n == NULL) {
goto error;
}
#endif #endif
break; break;
} }
key->type_c=ssh_type_to_char(prv->type); key->type_c = ssh_type_to_char(prv->type);
return key;
return key;
error:
#ifdef HAVE_LIBGCRYPT
string_burn(p);
string_free(p);
string_burn(q);
string_free(q);
string_burn(g);
string_free(g);
string_burn(y);
string_free(y);
string_burn(e);
string_free(e);
string_burn(n);
string_free(n);
#endif
publickey_free(key);
return NULL;
} }
#ifdef HAVE_LIBGCRYPT #ifdef HAVE_LIBGCRYPT