void kex_ecdh_hash( const EVP_MD *evp_md, const EC_GROUP *ec_group, char *client_version_string, char *server_version_string, char *ckexinit, int ckexinitlen, char *skexinit, int skexinitlen, u_char *serverhostkeyblob, int sbloblen, const EC_POINT *client_dh_pub, const EC_POINT *server_dh_pub, const BIGNUM *shared_secret, u_char **hash, u_int *hashlen) { Buffer b; EVP_MD_CTX md; static u_char digest[EVP_MAX_MD_SIZE]; buffer_init(&b); buffer_put_cstring(&b, client_version_string); buffer_put_cstring(&b, server_version_string); /* kexinit messages: fake header: len+SSH2_MSG_KEXINIT */ buffer_put_int(&b, ckexinitlen+1); buffer_put_char(&b, SSH2_MSG_KEXINIT); buffer_append(&b, ckexinit, ckexinitlen); buffer_put_int(&b, skexinitlen+1); buffer_put_char(&b, SSH2_MSG_KEXINIT); buffer_append(&b, skexinit, skexinitlen); buffer_put_string(&b, serverhostkeyblob, sbloblen); buffer_put_ecpoint(&b, ec_group, client_dh_pub); buffer_put_ecpoint(&b, ec_group, server_dh_pub); buffer_put_bignum2(&b, shared_secret); #ifdef DEBUG_KEX buffer_dump(&b); #endif EVP_DigestInit(&md, evp_md); EVP_DigestUpdate(&md, buffer_ptr(&b), buffer_len(&b)); EVP_DigestFinal(&md, digest, NULL); buffer_free(&b); #ifdef DEBUG_KEX dump_digest("hash", digest, EVP_MD_size(evp_md)); #endif *hash = digest; *hashlen = EVP_MD_size(evp_md); }
unsigned char *kex_ecdh_hash(const EVP_MD *evp_md, const EC_GROUP *ec_group, char *client_version_string, char *server_version_string, char *ckexinit, int ckexinitlen, char *skexinit, int skexinitlen, u_char *serverhostkeyblob, int sbloblen, const EC_POINT *client_dh_pub, const EC_POINT *server_dh_pub, BIGNUM *shared_secret, unsigned int *hashlen) { buffer_t *b; static unsigned char digest[EVP_MAX_MD_SIZE]; EVP_MD_CTX md; b = buffer_init(); buffer_put_string(b, client_version_string, strlen(client_version_string)); buffer_put_string(b, server_version_string, strlen(server_version_string)); /* kexinit messages: fake header: len+SSH2_MSG_KEXINIT */ buffer_put_int(b, ckexinitlen+1); buffer_put_char(b, SSH2_MSG_KEXINIT); buffer_append(b, ckexinit, ckexinitlen); buffer_put_int(b, skexinitlen+1); buffer_put_char(b, SSH2_MSG_KEXINIT); buffer_append(b, skexinit, skexinitlen); buffer_put_string(b, serverhostkeyblob, sbloblen); buffer_put_ecpoint(b, ec_group, client_dh_pub); buffer_put_ecpoint(b, ec_group, server_dh_pub); buffer_put_bignum2(b, shared_secret); // yutaka //debug_print(38, buffer_ptr(b), buffer_len(b)); EVP_DigestInit(&md, evp_md); EVP_DigestUpdate(&md, buffer_ptr(b), buffer_len(b)); EVP_DigestFinal(&md, digest, NULL); buffer_free(b); //write_buffer_file(digest, EVP_MD_size(evp_md)); *hashlen = EVP_MD_size(evp_md); return digest; }
// // キー情報からバッファへ変換する (for SSH2) // NOTE: // int key_to_blob(Key *key, char **blobp, int *lenp) { buffer_t *b; char *sshname, *tmp; int len; int ret = 1; // success b = buffer_init(); sshname = get_sshname_from_key(key); switch (key->type) { case KEY_RSA: buffer_put_string(b, sshname, strlen(sshname)); buffer_put_bignum2(b, key->rsa->e); buffer_put_bignum2(b, key->rsa->n); break; case KEY_DSA: buffer_put_string(b, sshname, strlen(sshname)); buffer_put_bignum2(b, key->dsa->p); buffer_put_bignum2(b, key->dsa->q); buffer_put_bignum2(b, key->dsa->g); buffer_put_bignum2(b, key->dsa->pub_key); break; case KEY_ECDSA256: case KEY_ECDSA384: case KEY_ECDSA521: buffer_put_string(b, sshname, strlen(sshname)); tmp = curve_keytype_to_name(key->type); buffer_put_string(b, tmp, strlen(tmp)); buffer_put_ecpoint(b, EC_KEY_get0_group(key->ecdsa), EC_KEY_get0_public_key(key->ecdsa)); break; case KEY_ED25519: buffer_put_cstring(b, sshname); buffer_put_string(b, key->ed25519_pk, ED25519_PK_SZ); break; default: ret = 0; goto error; } len = buffer_len(b); if (lenp != NULL) *lenp = len; if (blobp != NULL) { *blobp = malloc(len); if (*blobp == NULL) { ret = 0; goto error; } memcpy(*blobp, buffer_ptr(b), len); } error: buffer_free(b); return (ret); }
static void ssh_encode_identity_ssh2(Buffer *b, Key *key, const char *comment) { buffer_put_cstring(b, key_ssh_name(key)); switch (key->type) { case KEY_RSA: buffer_put_bignum2(b, key->rsa->n); buffer_put_bignum2(b, key->rsa->e); buffer_put_bignum2(b, key->rsa->d); buffer_put_bignum2(b, key->rsa->iqmp); buffer_put_bignum2(b, key->rsa->p); buffer_put_bignum2(b, key->rsa->q); break; case KEY_RSA_CERT_V00: case KEY_RSA_CERT: if (key->cert == NULL || buffer_len(&key->cert->certblob) == 0) fatal("%s: no cert/certblob", __func__); buffer_put_string(b, buffer_ptr(&key->cert->certblob), buffer_len(&key->cert->certblob)); buffer_put_bignum2(b, key->rsa->d); buffer_put_bignum2(b, key->rsa->iqmp); buffer_put_bignum2(b, key->rsa->p); buffer_put_bignum2(b, key->rsa->q); break; case KEY_DSA: buffer_put_bignum2(b, key->dsa->p); buffer_put_bignum2(b, key->dsa->q); buffer_put_bignum2(b, key->dsa->g); buffer_put_bignum2(b, key->dsa->pub_key); buffer_put_bignum2(b, key->dsa->priv_key); break; case KEY_DSA_CERT_V00: case KEY_DSA_CERT: if (key->cert == NULL || buffer_len(&key->cert->certblob) == 0) fatal("%s: no cert/certblob", __func__); buffer_put_string(b, buffer_ptr(&key->cert->certblob), buffer_len(&key->cert->certblob)); buffer_put_bignum2(b, key->dsa->priv_key); break; #ifdef OPENSSL_HAS_ECC case KEY_ECDSA: buffer_put_cstring(b, key_curve_nid_to_name(key->ecdsa_nid)); buffer_put_ecpoint(b, EC_KEY_get0_group(key->ecdsa), EC_KEY_get0_public_key(key->ecdsa)); buffer_put_bignum2(b, EC_KEY_get0_private_key(key->ecdsa)); break; case KEY_ECDSA_CERT: if (key->cert == NULL || buffer_len(&key->cert->certblob) == 0) fatal("%s: no cert/certblob", __func__); buffer_put_string(b, buffer_ptr(&key->cert->certblob), buffer_len(&key->cert->certblob)); buffer_put_bignum2(b, EC_KEY_get0_private_key(key->ecdsa)); break; #endif } buffer_put_cstring(b, comment); }
BOOL get_SSH2_publickey_blob(PTInstVar pvar, buffer_t **blobptr, int *bloblen) { buffer_t *msg = NULL; Key *keypair; char *s, *tmp; msg = buffer_init(); if (msg == NULL) { // TODO: error check return FALSE; } keypair = pvar->auth_state.cur_cred.key_pair; switch (keypair->type) { case KEY_RSA: // RSA s = get_sshname_from_key(keypair); buffer_put_string(msg, s, strlen(s)); buffer_put_bignum2(msg, keypair->rsa->e); // 公開指数 buffer_put_bignum2(msg, keypair->rsa->n); // p×q break; case KEY_DSA: // DSA s = get_sshname_from_key(keypair); buffer_put_string(msg, s, strlen(s)); buffer_put_bignum2(msg, keypair->dsa->p); // 素数 buffer_put_bignum2(msg, keypair->dsa->q); // (p-1)の素因数 buffer_put_bignum2(msg, keypair->dsa->g); // 整数 buffer_put_bignum2(msg, keypair->dsa->pub_key); // 公開鍵 break; case KEY_ECDSA256: // ECDSA case KEY_ECDSA384: case KEY_ECDSA521: s = get_sshname_from_key(keypair); buffer_put_string(msg, s, strlen(s)); tmp = curve_keytype_to_name(keypair->type); buffer_put_string(msg, tmp, strlen(tmp)); buffer_put_ecpoint(msg, EC_KEY_get0_group(keypair->ecdsa), EC_KEY_get0_public_key(keypair->ecdsa)); break; case KEY_ED25519: s = get_sshname_from_key(keypair); buffer_put_cstring(msg, s); buffer_put_string(msg, keypair->ed25519_pk, ED25519_PK_SZ); break; default: return FALSE; } *blobptr = msg; *bloblen = buffer_len(msg); return TRUE; }
void key_private_serialize(Key *key, buffer_t *b) { char *s; s = get_sshname_from_key(key); buffer_put_cstring(b, s); switch (key->type) { case KEY_RSA: buffer_put_bignum2(b, key->rsa->n); buffer_put_bignum2(b, key->rsa->e); buffer_put_bignum2(b, key->rsa->d); buffer_put_bignum2(b, key->rsa->iqmp); buffer_put_bignum2(b, key->rsa->p); buffer_put_bignum2(b, key->rsa->q); break; case KEY_DSA: buffer_put_bignum2(b, key->dsa->p); buffer_put_bignum2(b, key->dsa->q); buffer_put_bignum2(b, key->dsa->g); buffer_put_bignum2(b, key->dsa->pub_key); buffer_put_bignum2(b, key->dsa->priv_key); break; case KEY_ECDSA256: case KEY_ECDSA384: case KEY_ECDSA521: buffer_put_cstring(b, curve_keytype_to_name(key->type)); buffer_put_ecpoint(b, EC_KEY_get0_group(key->ecdsa), EC_KEY_get0_public_key(key->ecdsa)); buffer_put_bignum2(b, (BIGNUM *)EC_KEY_get0_private_key(key->ecdsa)); break; case KEY_ED25519: buffer_put_string(b, key->ed25519_pk, ED25519_PK_SZ); buffer_put_string(b, key->ed25519_sk, ED25519_SK_SZ); break; default: break; } }