scmno****@osdn*****
scmno****@osdn*****
2017年 11月 26日 (日) 00:26:45 JST
Revision: 6985 http://sourceforge.jp/projects/ttssh2/scm/svn/commits/6985 Author: doda Date: 2017-11-26 00:26:45 +0900 (Sun, 26 Nov 2017) Log Message: ----------- SSH2 暗号化アルゴリズムとして aes{128,256}-gcm****@opens***** に対応した。 Modified Paths: -------------- trunk/installer/release/TERATERM.INI trunk/ttssh2/ttxssh/cipher.h trunk/ttssh2/ttxssh/crypt.c trunk/ttssh2/ttxssh/crypt.h trunk/ttssh2/ttxssh/keyfiles.c trunk/ttssh2/ttxssh/pkt.c trunk/ttssh2/ttxssh/ssh.c trunk/ttssh2/ttxssh/ssh.h trunk/ttssh2/ttxssh/ttxssh.c -------------- next part -------------- Modified: trunk/installer/release/TERATERM.INI =================================================================== --- trunk/installer/release/TERATERM.INI 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/installer/release/TERATERM.INI 2017-11-25 15:26:45 UTC (rev 6985) @@ -797,9 +797,10 @@ ; @...Arcfour128, A...Arcfour256, B...CAST128-CBC, C...3DES-CTR, ; D...Blowfish-CTR, E...CAST128-CTR, F...Camellia128-CBC, ; G...Camellia192-CBC, H...Camellia256-CBC, I...Camellia128-CTR, -; J...Camellia192-CTR, K...Camellia256-CTR +; J...Camellia192-CTR, K...Camellia256-CTR L...A****@opens***** +; M...A****@opens***** ; 0...Ciphers below this line are disabled. -CipherOrder=K>H:J=G9I<F8C7D;EB30A@?62 +CipherOrder=MLK>H:J=G9I<F8C7D;EB30A@?62 ; KEX algorithm order(SSH2) ; 1...diffie-hellman-group1-sha1 Modified: trunk/ttssh2/ttxssh/cipher.h =================================================================== --- trunk/ttssh2/ttxssh/cipher.h 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/cipher.h 2017-11-25 15:26:45 UTC (rev 6985) @@ -95,6 +95,7 @@ int encrypt, const EVP_CIPHER *type, int discard_len, + unsigned int authlen, PTInstVar pvar ); Modified: trunk/ttssh2/ttxssh/crypt.c =================================================================== --- trunk/ttssh2/ttxssh/crypt.c 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/crypt.c 2017-11-25 15:26:45 UTC (rev 6985) @@ -198,6 +198,113 @@ } } +BOOL CRYPT_encrypt_aead(PTInstVar pvar, unsigned char *data, unsigned int bytes, unsigned int aadlen, unsigned int authlen) +{ + unsigned char *newbuf = NULL; + unsigned int block_size = pvar->ssh2_keys[MODE_OUT].enc.block_size; + unsigned char lastiv[1]; + char tmp[80]; + EVP_CIPHER_CTX *evp = &pvar->evpcip[MODE_OUT]; + + if (bytes == 0) + return TRUE; + + if (bytes % block_size) { + UTIL_get_lang_msg("MSG_ENCRYPT_ERROR1", pvar, "%s encrypt error(1): bytes %d (%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, + get_cipher_name(pvar->crypt_state.sender_cipher), + bytes, block_size); + notify_fatal_error(pvar, tmp, TRUE); + return FALSE; + } + + if ((newbuf = malloc(bytes)) == NULL) + goto err; + + if (!EVP_CIPHER_CTX_ctrl(evp, EVP_CTRL_GCM_IV_GEN, 1, lastiv)) + goto err; + + if (aadlen && !EVP_Cipher(evp, NULL, data, aadlen) < 0) + goto err; + + if (EVP_Cipher(evp, newbuf, data+aadlen, bytes) < 0) + goto err; + + memcpy(data+aadlen, newbuf, bytes); + + if (EVP_Cipher(evp, NULL, NULL, 0) < 0) + goto err; + + if (!EVP_CIPHER_CTX_ctrl(evp, EVP_CTRL_GCM_GET_TAG, authlen, data+aadlen+bytes)) + goto err; + + free(newbuf); + + return TRUE; + +err: + free(newbuf); + + UTIL_get_lang_msg("MSG_ENCRYPT_ERROR2", pvar, "%s encrypt error(2)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, + get_cipher_name(pvar->crypt_state.sender_cipher)); + notify_fatal_error(pvar, tmp, TRUE); + return FALSE; +} + +BOOL CRYPT_decrypt_aead(PTInstVar pvar, unsigned char *data, unsigned int bytes, unsigned int aadlen, unsigned int authlen) +{ + unsigned char *newbuf = NULL; + unsigned int block_size = pvar->ssh2_keys[MODE_IN].enc.block_size; + unsigned char lastiv[1]; + char tmp[80]; + EVP_CIPHER_CTX *evp = &pvar->evpcip[MODE_IN]; + + if (bytes == 0) + return TRUE; + + if (bytes % block_size) { + UTIL_get_lang_msg("MSG_DECRYPT_ERROR1", pvar, "%s decrypt error(1): bytes %d (%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, + get_cipher_name(pvar->crypt_state.receiver_cipher), + bytes, block_size); + notify_fatal_error(pvar, tmp, TRUE); + return FALSE; + } + + if ((newbuf = malloc(bytes)) == NULL) + goto err; + + if (!EVP_CIPHER_CTX_ctrl(evp, EVP_CTRL_GCM_IV_GEN, 1, lastiv)) + goto err; + + if (!EVP_CIPHER_CTX_ctrl(evp, EVP_CTRL_GCM_SET_TAG, authlen, data+aadlen+bytes)) + goto err; + + if (aadlen && !EVP_Cipher(evp, NULL, data, aadlen) < 0) + goto err; + + if (EVP_Cipher(evp, newbuf, data+aadlen, bytes) < 0) + goto err; + + memcpy(data+aadlen, newbuf, bytes); + free(newbuf); + + if (EVP_Cipher(evp, NULL, NULL, 0) < 0) + return FALSE; + else + return TRUE; + +err: + free(newbuf); + + UTIL_get_lang_msg("MSG_DECRYPT_ERROR2", pvar, "%s decrypt error(2)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, + get_cipher_name(pvar->crypt_state.receiver_cipher)); + notify_fatal_error(pvar, tmp, TRUE); + return FALSE; +} + static void no_encrypt(PTInstVar pvar, unsigned char *buf, int bytes) { } @@ -468,6 +575,8 @@ | (1 << SSH2_CIPHER_CAMELLIA128_CTR) | (1 << SSH2_CIPHER_CAMELLIA192_CTR) | (1 << SSH2_CIPHER_CAMELLIA256_CTR) + | (1 << SSH2_CIPHER_AES128_GCM) + | (1 << SSH2_CIPHER_AES256_GCM) ); } @@ -870,6 +979,7 @@ int encrypt, const EVP_CIPHER *type, int discard_len, + unsigned int authlen, PTInstVar pvar) { int klen; @@ -877,28 +987,44 @@ unsigned char *junk = NULL, *discard = NULL; EVP_CIPHER_CTX_init(evp); - if (EVP_CipherInit(evp, type, NULL, (u_char *)iv, (encrypt == CIPHER_ENCRYPT)) == 0) { - UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, - "Cipher initialize error(%d)"); + if (EVP_CipherInit(evp, type, NULL, NULL, (encrypt == CIPHER_ENCRYPT)) == 0) { + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 1); notify_fatal_error(pvar, tmp, TRUE); return; } + if (authlen > 0 && !EVP_CIPHER_CTX_ctrl(evp, EVP_CTRL_GCM_SET_IVLEN, ivlen, NULL)) { + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 2); + notify_fatal_error(pvar, tmp, TRUE); + return; + } + if (EVP_CipherInit(evp, NULL, NULL, (u_char *)iv, -1) == 0) { + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 3); + notify_fatal_error(pvar, tmp, TRUE); + return; + } + if (authlen > 0 && !EVP_CIPHER_CTX_ctrl(evp, EVP_CTRL_GCM_SET_IV_FIXED, -1, (u_char *)iv)) { + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 4); + notify_fatal_error(pvar, tmp, TRUE); + return; + } + klen = EVP_CIPHER_CTX_key_length(evp); if (klen > 0 && keylen != klen) { if (EVP_CIPHER_CTX_set_key_length(evp, keylen) == 0) { - UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, - "Cipher initialize error(%d)"); - _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 2); + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 5); notify_fatal_error(pvar, tmp, TRUE); return; } } if (EVP_CipherInit(evp, NULL, (u_char *)key, NULL, -1) == 0) { - UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, - "Cipher initialize error(%d)"); - _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 3); + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 6); notify_fatal_error(pvar, tmp, TRUE); return; } @@ -908,10 +1034,8 @@ discard = malloc(discard_len); if (junk == NULL || discard == NULL || EVP_Cipher(evp, discard, junk, discard_len) == 0) { - UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, - "Cipher initialize error(%d)"); - _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, - pvar->ts->UIMsg, 3); + UTIL_get_lang_msg("MSG_CIPHER_INIT_ERROR", pvar, "Cipher initialize error(%d)"); + _snprintf_s(tmp, sizeof(tmp), _TRUNCATE, pvar->ts->UIMsg, 7); notify_fatal_error(pvar, tmp, TRUE); } else { @@ -969,10 +1093,11 @@ enc = &pvar->ssh2_keys[MODE_OUT].enc; cipher_init_SSH2(&pvar->evpcip[MODE_OUT], enc->key, get_cipher_key_len(cipher), - enc->iv, get_cipher_block_size(cipher), + enc->iv, get_cipher_iv_len(cipher), CIPHER_ENCRYPT, get_cipher_EVP_CIPHER(cipher), get_cipher_discard_len(cipher), + get_cipher_auth_len(cipher), pvar); pvar->crypt_state.encrypt = crypt_SSH2_encrypt; @@ -1014,10 +1139,11 @@ enc = &pvar->ssh2_keys[MODE_IN].enc; cipher_init_SSH2(&pvar->evpcip[MODE_IN], enc->key, get_cipher_key_len(cipher), - enc->iv, get_cipher_block_size(cipher), + enc->iv, get_cipher_iv_len(cipher), CIPHER_DECRYPT, get_cipher_EVP_CIPHER(cipher), get_cipher_discard_len(cipher), + get_cipher_auth_len(cipher), pvar); pvar->crypt_state.decrypt = crypt_SSH2_decrypt; @@ -1110,6 +1236,10 @@ return "Camellia192-CTR"; case SSH2_CIPHER_CAMELLIA256_CTR: return "Camellia256-CTR"; + case SSH2_CIPHER_AES128_GCM: + return "AES12****@opens*****"; + case SSH2_CIPHER_AES256_GCM: + return "AES25****@opens*****"; default: return "Unknown"; Modified: trunk/ttssh2/ttxssh/crypt.h =================================================================== --- trunk/ttssh2/ttxssh/crypt.h 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/crypt.h 2017-11-25 15:26:45 UTC (rev 6985) @@ -150,6 +150,9 @@ #define CRYPT_decrypt(pvar, buf, bytes) \ ((pvar)->crypt_state.decrypt((pvar), (buf), (bytes))) +BOOL CRYPT_encrypt_aead(PTInstVar pvar, unsigned char *data, unsigned int len, unsigned int aadlen, unsigned int authlen); +BOOL CRYPT_decrypt_aead(PTInstVar pvar, unsigned char *data, unsigned int len, unsigned int aadlen, unsigned int authlen); + BOOL CRYPT_detect_attack(PTInstVar pvar, unsigned char *buf, int bytes); int CRYPT_passphrase_decrypt(int cipher, char *passphrase, char *buf, int len); RSA *make_key(PTInstVar pvar, Modified: trunk/ttssh2/ttxssh/keyfiles.c =================================================================== --- trunk/ttssh2/ttxssh/keyfiles.c 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/keyfiles.c 2017-11-25 15:26:45 UTC (rev 6985) @@ -542,7 +542,7 @@ // \x95\x9C\x8D\x86\x89\xBB cp = buffer_append_space(b, len); cipher_init_SSH2(&cipher_ctx, key, keylen, key + keylen, ivlen, CIPHER_DECRYPT, - get_cipher_EVP_CIPHER(ciphernameval), 0, pvar); + get_cipher_EVP_CIPHER(ciphernameval), 0, 0, pvar); if (EVP_Cipher(&cipher_ctx, cp, buffer_tail_ptr(copy_consumed), len) == 0) { cipher_cleanup_SSH2(&cipher_ctx); goto error; @@ -931,7 +931,7 @@ memset(iv, 0, sizeof(iv)); // decrypt - cipher_init_SSH2(&cipher_ctx, key, 32, iv, 16, CIPHER_DECRYPT, EVP_aes_256_cbc(), 0, pvar); + cipher_init_SSH2(&cipher_ctx, key, 32, iv, 16, CIPHER_DECRYPT, EVP_aes_256_cbc(), 0, 0, pvar); len = buffer_len(prikey); decrypted = (char *)malloc(len); if (EVP_Cipher(&cipher_ctx, decrypted, prikey->buf, len) == 0) { @@ -1466,7 +1466,7 @@ memset(iv, 0, sizeof(iv)); // decrypt - cipher_init_SSH2(&cipher_ctx, key, 24, iv, 8, CIPHER_DECRYPT, EVP_des_ede3_cbc(), 0, pvar); + cipher_init_SSH2(&cipher_ctx, key, 24, iv, 8, CIPHER_DECRYPT, EVP_des_ede3_cbc(), 0, 0, pvar); decrypted = (char *)malloc(len); if (EVP_Cipher(&cipher_ctx, decrypted, blob->buf + blob->offset, len) == 0) { strncpy_s(errmsg, errmsg_len, "Key decrypt error", _TRUNCATE); Modified: trunk/ttssh2/ttxssh/pkt.c =================================================================== --- trunk/ttssh2/ttxssh/pkt.c 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/pkt.c 2017-11-25 15:26:45 UTC (rev 6985) @@ -180,16 +180,30 @@ uint32 pktsize; uint32 total_packet_size; struct Mac *mac = &pvar->ssh2_keys[MODE_IN].mac; - int etm; + struct Enc *enc = &pvar->ssh2_keys[MODE_IN].enc; + int aadlen; - etm = mac && mac->enabled && mac->etm; + /* + * aadlen: Additional Authenticated Data Length + * - \x88Í\x86\x89\xBB\x82\xB5\x82Ȃ\xA2\x82\xAA MAC \x82\xE2 AEAD \x82ł̔F\x8F̑ΏۂƂȂ\xE9\x83f\x81[\x83^\x82̒\xB7\x82\xB3 + * + * EtM \x95\xFB\x8E\xAE\x82\xCC MAC \x82\xE2\x81AAEAD \x82ȈÍ\x86\x82ł̓p\x83P\x83b\x83g\x82̐擪\x82̃p\x83P\x83b\x83g\x92\xB7\x95\x94\x95\xAA\x82͈Í\x86\x89\xBB\x82\xB3\x82ꂸ + * \x94F\x8F݂̂\xAA\x8Ds\x82\xED\x82\xEA\x82\xE9\x81B\x83p\x83P\x83b\x83g\x92\xB7\x82\xCD uint32 (4\x83o\x83C\x83g) \x82Ŋi\x94[\x82\xB3\x82\xEA\x82Ă\xA2\x82\xE9\x81B + * \x92ʏ\xED\x82\xCC MAC \x95\xFB\x8E\xAE (E&M) \x82ŁA\x82\xA9\x82\xC2 AEAD \x82łȂ\xA2\x88Í\x86\x95\xFB\x8E\xAE\x82ł̓p\x83P\x83b\x83g\x92\xB7\x95\x94\x95\xAA\x82\xE0\x88Í\x86\x89\xBB + * \x82\xB3\x82\xEA\x82\xE9\x82̂\xC5 aadlen \x82\xCD 0 \x82ƂȂ\xE9\x81B + */ + if (SSHv2(pvar) && ((mac && mac->etm) || (enc && enc->auth_len > 0))) { + aadlen = 4; + } + else { + aadlen = 0; + } /* - * \x92ʏ\xED\x82\xCC MAC \x95\xFB\x8E\xAE (E&M: Encrypt & MAC) \x82ł̓p\x83P\x83b\x83g\x92\xB7\x95\x94\x95\xAA\x82\xE0\x88Í\x86\x89\xBB\x82\xB3\x82\xEA\x82Ă\xA2\x82邽\x82߁A - * \x90擪\x82\xCC 1 \x83u\x83\x8D\x83b\x83N\x82\x86\x82\xB7\x82\xE9\x81BMAC \x95\x{33AE0AA} EtM (Encrypt then MAC) \x82̎\x9E\x81A\x82\xA8\x82\xE6\x82\xD1 SSH1 \x82ł\xCD - * \x83p\x83P\x83b\x83g\x92\xB7\x95\x94\x95\xAA\x82͈Í\x86\x89\xBB\x82\xB3\x82\xEA\x82Ă\xA2\x82Ȃ\xA2\x82̂ŕ\x9C\x8D\x86\x82͕K\x97v\x96\xB3\x82\xA2\x81B + * aadlen \x82\xAA 0 \x82̎\x9E\x82̓p\x83P\x83b\x83g\x92\xB7\x95\x94\x95\xAA\x82\xAA\x88Í\x86\x89\xBB\x82\xB3\x82\xEA\x82Ă\xA2\x82\xE9\x81B\x83p\x83P\x83b\x83g\x91S\x91̂\xF0\x8E\xF3\x90M\x82\xB5\x82Ă\xA9\x82\xE7 + * \x8C\xE3\x92i\x82̏\x88\x97\x9D\x82\xF0\x8Ds\x82\xA4\x88ׂɃp\x83P\x83b\x83g\x92\xB7\x82\xF0\x92m\x82\xE9\x95K\x97v\x82\xAA\x97L\x82\xE9\x88ׁA\x90擪\x82\xCC 1 \x83u\x83\x8D\x83b\x83N\x82\x86\x82\xB7\x82\xE9\x81B */ - if (SSHv2(pvar) && !pvar->pkt_state.predecrypted_packet && !etm) { + if (SSHv2(pvar) && !pvar->pkt_state.predecrypted_packet && aadlen == 0) { SSH_predecrpyt_packet(pvar, data); pvar->pkt_state.predecrypted_packet = TRUE; } @@ -208,7 +222,7 @@ // \x83p\x83P\x83b\x83g(TCP\x83y\x83C\x83\x8D\x81[\x83h)\x82̑S\x91̂̃T\x83C\x83Y\x82́ASSH\x83y\x83C\x83\x8D\x81[\x83h+4\x81i+MAC\x81j\x82ƂȂ\xE9\x81B // +4\x82́ASSH\x83y\x83C\x83\x8D\x81[\x83h\x82̃T\x83C\x83Y\x82\xF0\x8Ai\x94[\x82\xB5\x82Ă\xA2\x82镔\x95\xAA\x81iint\x8C^\x81j\x81B - total_packet_size = pktsize + 4 + SSH_get_clear_MAC_size(pvar); + total_packet_size = pktsize + 4 + SSH_get_authdata_size(pvar, MODE_IN); if (total_packet_size <= pvar->pkt_state.datalen) { // \x8E\xF3\x90M\x8Dς݃f\x81[\x83^\x82\xAA\x8F\\x95\xAA\x97L\x82\xE9\x8Fꍇ\x82̓p\x83P\x83b\x83g\x82̎\xC0\x8F\x88\x97\x9D\x82\xF0\x8Ds\x82\xA4 @@ -219,7 +233,7 @@ else { // SSH2 \x82ł͂\xB1\x82̎\x9E\x93_\x82ł\xCD padding \x92\xB7\x95\x94\x95\xAA\x82\xAA\x95\x9C\x8D\x86\x82\xB3\x82\xEA\x82Ă\xA2\x82Ȃ\xA2\x8Fꍇ\x82\xAA\x82\xA0\x82\xE9\x82̂ŁA // padding \x92\xB7\x82͓n\x82\xB3\x82\xB8\x82ɁA\x95K\x97v\x82ɂȂ\xC1\x82\xBD\x8E\x9E\x82ɓ\xE0\x95\x94\x82Ŏ擾\x82\xB7\x82\xE9\x81B - SSH2_handle_packet(pvar, data, pktsize, etm); + SSH2_handle_packet(pvar, data, pktsize, aadlen, enc->auth_len); } pvar->pkt_state.predecrypted_packet = FALSE; Modified: trunk/ttssh2/ttxssh/ssh.c =================================================================== --- trunk/ttssh2/ttxssh/ssh.c 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/ssh.c 2017-11-25 15:26:45 UTC (rev 6985) @@ -784,14 +784,22 @@ * \x88\xF8\x90\x94: * data - ssh \x83p\x83P\x83b\x83g\x82̐擪\x82\xF0\x8Ew\x82\xB7\x83|\x83C\x83\x93\x83^ * len - \x83p\x83P\x83b\x83g\x92\xB7 (\x90擪\x82̃p\x83P\x83b\x83g\x92\xB7\x97̈\xE6(4\x83o\x83C\x83g)\x82\xF0\x8F\x9C\x82\xA2\x82\xBD\x92l) - * etm - MAC \x95\x{33AE0AA} EtM \x82\xA9\x82ǂ\xA4\x82\xA9\x82̃t\x83\x89\x83O + * aadlen - \x88Í\x86\x89\xBB\x82\xB3\x82\xEA\x82Ă\xA2\x82Ȃ\xA2\x82\xAA\x94F\x8F̑ΏۂƂȂ\xC1\x82Ă\xA2\x82\xE9\x83f\x81[\x83^\x82̒\xB7\x82\xB3 + * authlen - \x94F\x8Ff\x81[\x83^(AEAD tag)\x92\xB7 */ -static int prep_packet_ssh2(PTInstVar pvar, char *data, unsigned int len, int etm) +static int prep_packet_ssh2(PTInstVar pvar, char *data, unsigned int len, unsigned int aadlen, unsigned int authlen) { unsigned int padding; - if (etm) { + if (authlen > 0) { + if (!CRYPT_decrypt_aead(pvar, data, len, aadlen, authlen)) { + UTIL_get_lang_msg("MSG_SSH_CORRUPTDATA_ERROR", pvar, "Detected corrupted data; connection terminating."); + notify_fatal_error(pvar, pvar->ts->UIMsg, TRUE); + return SSH_MSG_NONE; + } + } + else if (aadlen > 0) { // EtM \x82̏ꍇ\x82͐\xE6\x82\xC9 MAC \x82̌\x9F\x8F\xF0\x8Ds\x82\xA4 if (!CRYPT_verify_receiver_MAC(pvar, pvar->ssh_state.receiver_sequence_number, data, len + 4, data + len + 4)) { UTIL_get_lang_msg("MSG_SSH_CORRUPTDATA_ERROR", pvar, "Detected corrupted data; connection terminating."); @@ -1025,7 +1033,8 @@ unsigned int padding; BOOL ret; struct Mac *mac = &pvar->ssh2_keys[MODE_OUT].mac; - unsigned int aadlen = 0, maclen = 0; + struct Enc *enc = &pvar->ssh2_keys[MODE_OUT].enc; + unsigned int aadlen = 0, maclen = 0, authlen = 0; /* \x83f\x81[\x83^\x8D\\x91\xA2 @@ -1078,7 +1087,11 @@ block_size = 8; } - if (mac && mac->etm) { + if (enc) { + authlen = enc->auth_len; + } + + if (mac && mac->etm || authlen > 0) { // \x88Í\x86\x89\xBB\x91Ώۂł͖\xB3\x82\xA2\x82\xAA\x81AMAC \x82̑ΏۂƂȂ镔\x95\xAA\x82̒\xB7\x82\xB3 aadlen = 4; } @@ -1099,25 +1112,31 @@ CRYPT_set_random_data(pvar, data + 5 + len, padding); - if (aadlen == 0) { - // E&M \x82ł͐\xE6\x82\xC9 MAC \x82\xF0\x8Cv\x8EZ\x82\xB7\x82\xE9 + if (authlen > 0) { + CRYPT_encrypt_aead(pvar, data, encryption_size, aadlen, authlen); + maclen = authlen; + } + else if (aadlen) { + // \x83p\x83P\x83b\x83g\x88Í\x86\x89\xBB + CRYPT_encrypt(pvar, data + aadlen, encryption_size); + + // EtM \x82ł͈Í\x86\x89\xBB\x8C\xE3\x82\xC9 MAC \x82\xF0\x8Cv\x8EZ\x82\xB7\x82\xE9 ret = CRYPT_build_sender_MAC(pvar, pvar->ssh_state.sender_sequence_number, - data, encryption_size, data + encryption_size); + data, aadlen + encryption_size, data + aadlen + encryption_size); if (ret) { maclen = CRYPT_get_sender_MAC_size(pvar); } } - - // \x83p\x83P\x83b\x83g\x82\xF0\x88Í\x86\x89\xBB\x82\xB7\x82\xE9\x81BMAC\x88ȍ~\x82͈Í\x86\x89\xBB\x91ΏۊO\x81B - CRYPT_encrypt(pvar, data + aadlen, encryption_size); - - if (aadlen) { - // EtM \x82ł͈Í\x86\x89\xBB\x8C\xE3\x82\xC9 MAC \x82\xF0\x8Cv\x8EZ\x82\xB7\x82\xE9 + else { + // E&M \x82ł͐\xE6\x82\xC9 MAC \x82\xF0\x8Cv\x8EZ\x82\xB7\x82\xE9 ret = CRYPT_build_sender_MAC(pvar, pvar->ssh_state.sender_sequence_number, - data, aadlen + encryption_size, data + aadlen + encryption_size); + data, encryption_size, data + encryption_size); if (ret) { maclen = CRYPT_get_sender_MAC_size(pvar); } + + // \x83p\x83P\x83b\x83g\x88Í\x86\x89\xBB + CRYPT_encrypt(pvar, data, encryption_size); } data_length = encryption_size + aadlen + maclen; @@ -2115,9 +2134,9 @@ } } -void SSH2_handle_packet(PTInstVar pvar, char *data, unsigned int len, int etm) +void SSH2_handle_packet(PTInstVar pvar, char *data, unsigned int len, unsigned int aadlen, unsigned int authlen) { - unsigned char message = prep_packet_ssh2(pvar, data, len, etm); + unsigned char message = prep_packet_ssh2(pvar, data, len, aadlen, authlen); // SSH\x82̃\x81\x83b\x83Z\x81[\x83W\x83^\x83C\x83v\x82\xF0\x83`\x83F\x83b\x83N if (message != SSH_MSG_NONE) { @@ -2925,6 +2944,28 @@ } } +unsigned int SSH_get_authdata_size(PTInstVar pvar, int direction) +{ + if (SSHv1(pvar)) { + return 0; + } + else { + struct Mac *mac = &pvar->ssh2_keys[direction].mac; + struct Enc *enc = &pvar->ssh2_keys[direction].enc; + + if (enc && enc->auth_len > 0) { + // AEAD + return enc->auth_len; + } + else if (mac && mac->enabled) { + return mac->mac_len; + } + else { + return 0; + } + } +} + void SSH_notify_user_name(PTInstVar pvar) { try_send_user_name(pvar); @@ -4095,6 +4136,41 @@ return 0; } +int get_cipher_iv_len(SSHCipher cipher) +{ + ssh2_cipher_t *ptr = ssh2_ciphers; + + while (ptr->name != NULL) { + if (cipher == ptr->cipher) { + if (ptr->iv_len != 0) { + return ptr->iv_len; + } + else { + return ptr->block_size; + } + } + ptr++; + } + + // not found. + return 8; // block_size +} + +int get_cipher_auth_len(SSHCipher cipher) +{ + ssh2_cipher_t *ptr = ssh2_ciphers; + + while (ptr->name != NULL) { + if (cipher == ptr->cipher) { + return ptr->auth_len; + } + ptr++; + } + + // not found. + return 0; +} + // \x88Í\x86\x83A\x83\x8B\x83S\x83\x8A\x83Y\x83\x80\x96\xBC\x82\xA9\x82猟\x8D\x{142DC2}\xE9\x81B SSHCipher get_cipher_by_name(char *name) { @@ -4410,6 +4486,12 @@ case SSH2_CIPHER_CAMELLIA256_CTR: c_str = "camellia256-ctr,"; break; + case SSH2_CIPHER_AES128_GCM: + c_str = "aes12****@opens*****,"; + break; + case SSH2_CIPHER_AES256_GCM: + c_str = "aes25****@opens*****,"; + break; default: continue; } @@ -4772,6 +4854,9 @@ // \x83L\x81[\x83T\x83C\x83Y\x82ƃu\x83\x8D\x83b\x83N\x83T\x83C\x83Y\x82\xE0\x82\xB1\x82\xB1\x82Őݒ肵\x82Ă\xA8\x82\xAD (2004.11.7 yutaka) current_keys[mode].enc.key_len = get_cipher_key_len(cipher); current_keys[mode].enc.block_size = get_cipher_block_size(cipher); + current_keys[mode].enc.iv_len = get_cipher_iv_len(cipher); + current_keys[mode].enc.auth_len = get_cipher_auth_len(cipher); + current_keys[mode].mac.enabled = 0; current_keys[mode].comp.enabled = 0; // (2005.7.9 yutaka) @@ -4783,6 +4868,7 @@ for (mode = 0; mode < MODE_MAX; mode++) { need = max(need, current_keys[mode].enc.key_len); need = max(need, current_keys[mode].enc.block_size); + need = max(need, current_keys[mode].enc.iv_len); need = max(need, current_keys[mode].mac.key_len); } pvar->we_need = need; @@ -5645,7 +5731,6 @@ } else { // \x8F\x89\x89\xF1\x90ڑ\xB1\x82̏ꍇ\x82͎\xC0\x8DۂɈÍ\x86\x83\x8B\x81[\x83`\x83\x93\x82\xAA\x90ݒ肳\x82\xEA\x82\xE9\x82̂́A\x82\xA0\x82ƂɂȂ\xC1\x82Ă\xA9\x82\xE7 // \x82Ȃ̂ŁiCRYPT_start_encryption\x8A\x94\x81j\x81A\x82\xB1\x82\xB1\x82Ō\xAE\x82̐ݒ\xE8\x82\xF0\x82\xB5\x82Ă\xB5\x82܂\xC1\x82Ă\xE0\x82悢\x81B - ssh2_set_newkeys(pvar, MODE_IN); ssh2_set_newkeys(pvar, MODE_OUT); // SSH2_MSG_NEWKEYS\x82𑗐M\x82\xB5\x82\xBD\x8E\x9E\x93_\x82ŁAMAC\x82\xF0\x97L\x8C\xF8\x82ɂ\xB7\x82\xE9\x81B(2006.10.30 yutaka) @@ -5880,7 +5965,6 @@ } else { // \x8F\x89\x89\xF1\x90ڑ\xB1\x82̏ꍇ\x82͎\xC0\x8DۂɈÍ\x86\x83\x8B\x81[\x83`\x83\x93\x82\xAA\x90ݒ肳\x82\xEA\x82\xE9\x82̂́A\x82\xA0\x82ƂɂȂ\xC1\x82Ă\xA9\x82\xE7 // \x82Ȃ̂ŁiCRYPT_start_encryption\x8A\x94\x81j\x81A\x82\xB1\x82\xB1\x82Ō\xAE\x82̐ݒ\xE8\x82\xF0\x82\xB5\x82Ă\xB5\x82܂\xC1\x82Ă\xE0\x82悢\x81B - ssh2_set_newkeys(pvar, MODE_IN); ssh2_set_newkeys(pvar, MODE_OUT); // SSH2_MSG_NEWKEYS\x82𑗐M\x82\xB5\x82\xBD\x8E\x9E\x93_\x82ŁAMAC\x82\xF0\x97L\x8C\xF8\x82ɂ\xB7\x82\xE9\x81B(2006.10.30 yutaka) @@ -6112,7 +6196,6 @@ } else { // \x8F\x89\x89\xF1\x90ڑ\xB1\x82̏ꍇ\x82͎\xC0\x8DۂɈÍ\x86\x83\x8B\x81[\x83`\x83\x93\x82\xAA\x90ݒ肳\x82\xEA\x82\xE9\x82̂́A\x82\xA0\x82ƂɂȂ\xC1\x82Ă\xA9\x82\xE7 // \x82Ȃ̂ŁiCRYPT_start_encryption\x8A\x94\x81j\x81A\x82\xB1\x82\xB1\x82Ō\xAE\x82̐ݒ\xE8\x82\xF0\x82\xB5\x82Ă\xB5\x82܂\xC1\x82Ă\xE0\x82悢\x81B - ssh2_set_newkeys(pvar, MODE_IN); ssh2_set_newkeys(pvar, MODE_OUT); // SSH2_MSG_NEWKEYS\x82𑗐M\x82\xB5\x82\xBD\x8E\x9E\x93_\x82ŁAMAC\x82\xF0\x97L\x8C\xF8\x82ɂ\xB7\x82\xE9\x81B(2006.10.30 yutaka) @@ -6238,6 +6321,8 @@ | 1 << SSH2_CIPHER_CAMELLIA128_CTR | 1 << SSH2_CIPHER_CAMELLIA192_CTR | 1 << SSH2_CIPHER_CAMELLIA256_CTR + | 1 << SSH2_CIPHER_AES128_GCM + | 1 << SSH2_CIPHER_AES256_GCM ); int type = (1 << SSH_AUTH_PASSWORD) | (1 << SSH_AUTH_RSA) | (1 << SSH_AUTH_TIS) | (1 << SSH_AUTH_PAGEANT); @@ -6268,6 +6353,7 @@ } else { // SSH2_MSG_NEWKEYS\x82\xF0\x8E\xE6\x82\xC1\x82\xBD\x8E\x9E\x93_\x82ŁAMAC\x82\xF0\x97L\x8C\xF8\x82ɂ\xB7\x82\xE9\x81B(2006.10.30 yutaka) + ssh2_set_newkeys(pvar, MODE_IN); pvar->ssh2_keys[MODE_IN].mac.enabled = 1; pvar->ssh2_keys[MODE_IN].comp.enabled = 1; Modified: trunk/ttssh2/ttxssh/ssh.h =================================================================== --- trunk/ttssh2/ttxssh/ssh.h 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/ssh.h 2017-11-25 15:26:45 UTC (rev 6985) @@ -95,7 +95,8 @@ SSH2_CIPHER_3DES_CTR, SSH2_CIPHER_BLOWFISH_CTR, SSH2_CIPHER_CAST128_CTR, SSH2_CIPHER_CAMELLIA128_CBC, SSH2_CIPHER_CAMELLIA192_CBC, SSH2_CIPHER_CAMELLIA256_CBC, SSH2_CIPHER_CAMELLIA128_CTR, SSH2_CIPHER_CAMELLIA192_CTR, SSH2_CIPHER_CAMELLIA256_CTR, - SSH_CIPHER_MAX = SSH2_CIPHER_CAMELLIA256_CTR, + SSH2_CIPHER_AES128_GCM, SSH2_CIPHER_AES256_GCM, + SSH_CIPHER_MAX = SSH2_CIPHER_AES256_GCM, } SSHCipher; typedef enum { @@ -380,40 +381,44 @@ int block_size; int key_len; int discard_len; + int iv_len; + int auth_len; const EVP_CIPHER *(*func)(void); } ssh2_cipher_t; static ssh2_cipher_t ssh2_ciphers[] = { - {SSH2_CIPHER_3DES_CBC, "3des-cbc", 8, 24, 0, EVP_des_ede3_cbc}, // RFC4253 - {SSH2_CIPHER_AES128_CBC, "aes128-cbc", 16, 16, 0, EVP_aes_128_cbc}, // RFC4253 - {SSH2_CIPHER_AES192_CBC, "aes192-cbc", 16, 24, 0, EVP_aes_192_cbc}, // RFC4253 - {SSH2_CIPHER_AES256_CBC, "aes256-cbc", 16, 32, 0, EVP_aes_256_cbc}, // RFC4253 - {SSH2_CIPHER_BLOWFISH_CBC, "blowfish-cbc", 8, 16, 0, EVP_bf_cbc}, // RFC4253 - {SSH2_CIPHER_AES128_CTR, "aes128-ctr", 16, 16, 0, evp_aes_128_ctr}, // RFC4344 - {SSH2_CIPHER_AES192_CTR, "aes192-ctr", 16, 24, 0, evp_aes_128_ctr}, // RFC4344 - {SSH2_CIPHER_AES256_CTR, "aes256-ctr", 16, 32, 0, evp_aes_128_ctr}, // RFC4344 - {SSH2_CIPHER_ARCFOUR, "arcfour", 8, 16, 0, EVP_rc4}, // RFC4253 - {SSH2_CIPHER_ARCFOUR128, "arcfour128", 8, 16, 1536, EVP_rc4}, // RFC4345 - {SSH2_CIPHER_ARCFOUR256, "arcfour256", 8, 32, 1536, EVP_rc4}, // RFC4345 - {SSH2_CIPHER_CAST128_CBC, "cast128-cbc", 8, 16, 0, EVP_cast5_cbc}, // RFC4253 - {SSH2_CIPHER_3DES_CTR, "3des-ctr", 8, 24, 0, evp_des3_ctr}, // RFC4344 - {SSH2_CIPHER_BLOWFISH_CTR, "blowfish-ctr", 8, 32, 0, evp_bf_ctr}, // RFC4344 - {SSH2_CIPHER_CAST128_CTR, "cast128-ctr", 8, 16, 0, evp_cast5_ctr}, // RFC4344 - {SSH2_CIPHER_CAMELLIA128_CBC, "camellia128-cbc", 16, 16, 0, EVP_camellia_128_cbc}, // draft-kanno-secsh-camellia-02 - {SSH2_CIPHER_CAMELLIA192_CBC, "camellia192-cbc", 16, 24, 0, EVP_camellia_192_cbc}, // draft-kanno-secsh-camellia-02 - {SSH2_CIPHER_CAMELLIA256_CBC, "camellia256-cbc", 16, 32, 0, EVP_camellia_256_cbc}, // draft-kanno-secsh-camellia-02 - {SSH2_CIPHER_CAMELLIA128_CTR, "camellia128-ctr", 16, 16, 0, evp_camellia_128_ctr}, // draft-kanno-secsh-camellia-02 - {SSH2_CIPHER_CAMELLIA192_CTR, "camellia192-ctr", 16, 24, 0, evp_camellia_128_ctr}, // draft-kanno-secsh-camellia-02 - {SSH2_CIPHER_CAMELLIA256_CTR, "camellia256-ctr", 16, 32, 0, evp_camellia_128_ctr}, // draft-kanno-secsh-camellia-02 + {SSH2_CIPHER_3DES_CBC, "3des-cbc", 8, 24, 0, 0, 0, EVP_des_ede3_cbc}, // RFC4253 + {SSH2_CIPHER_AES128_CBC, "aes128-cbc", 16, 16, 0, 0, 0, EVP_aes_128_cbc}, // RFC4253 + {SSH2_CIPHER_AES192_CBC, "aes192-cbc", 16, 24, 0, 0, 0, EVP_aes_192_cbc}, // RFC4253 + {SSH2_CIPHER_AES256_CBC, "aes256-cbc", 16, 32, 0, 0, 0, EVP_aes_256_cbc}, // RFC4253 + {SSH2_CIPHER_BLOWFISH_CBC, "blowfish-cbc", 8, 16, 0, 0, 0, EVP_bf_cbc}, // RFC4253 + {SSH2_CIPHER_AES128_CTR, "aes128-ctr", 16, 16, 0, 0, 0, evp_aes_128_ctr}, // RFC4344 + {SSH2_CIPHER_AES192_CTR, "aes192-ctr", 16, 24, 0, 0, 0, evp_aes_128_ctr}, // RFC4344 + {SSH2_CIPHER_AES256_CTR, "aes256-ctr", 16, 32, 0, 0, 0, evp_aes_128_ctr}, // RFC4344 + {SSH2_CIPHER_ARCFOUR, "arcfour", 8, 16, 0, 0, 0, EVP_rc4}, // RFC4253 + {SSH2_CIPHER_ARCFOUR128, "arcfour128", 8, 16, 1536, 0, 0, EVP_rc4}, // RFC4345 + {SSH2_CIPHER_ARCFOUR256, "arcfour256", 8, 32, 1536, 0, 0, EVP_rc4}, // RFC4345 + {SSH2_CIPHER_CAST128_CBC, "cast128-cbc", 8, 16, 0, 0, 0, EVP_cast5_cbc}, // RFC4253 + {SSH2_CIPHER_3DES_CTR, "3des-ctr", 8, 24, 0, 0, 0, evp_des3_ctr}, // RFC4344 + {SSH2_CIPHER_BLOWFISH_CTR, "blowfish-ctr", 8, 32, 0, 0, 0, evp_bf_ctr}, // RFC4344 + {SSH2_CIPHER_CAST128_CTR, "cast128-ctr", 8, 16, 0, 0, 0, evp_cast5_ctr}, // RFC4344 + {SSH2_CIPHER_CAMELLIA128_CBC, "camellia128-cbc", 16, 16, 0, 0, 0, EVP_camellia_128_cbc}, // draft-kanno-secsh-camellia-02 + {SSH2_CIPHER_CAMELLIA192_CBC, "camellia192-cbc", 16, 24, 0, 0, 0, EVP_camellia_192_cbc}, // draft-kanno-secsh-camellia-02 + {SSH2_CIPHER_CAMELLIA256_CBC, "camellia256-cbc", 16, 32, 0, 0, 0, EVP_camellia_256_cbc}, // draft-kanno-secsh-camellia-02 + {SSH2_CIPHER_CAMELLIA128_CTR, "camellia128-ctr", 16, 16, 0, 0, 0, evp_camellia_128_ctr}, // draft-kanno-secsh-camellia-02 + {SSH2_CIPHER_CAMELLIA192_CTR, "camellia192-ctr", 16, 24, 0, 0, 0, evp_camellia_128_ctr}, // draft-kanno-secsh-camellia-02 + {SSH2_CIPHER_CAMELLIA256_CTR, "camellia256-ctr", 16, 32, 0, 0, 0, evp_camellia_128_ctr}, // draft-kanno-secsh-camellia-02 #ifdef WITH_CAMELLIA_PRIVATE - {SSH2_CIPHER_CAMELLIA128_CBC, "camel****@opens*****", 16, 16, 0, EVP_camellia_128_cbc}, - {SSH2_CIPHER_CAMELLIA192_CBC, "camel****@opens*****", 16, 24, 0, EVP_camellia_192_cbc}, - {SSH2_CIPHER_CAMELLIA256_CBC, "camel****@opens*****", 16, 32, 0, EVP_camellia_256_cbc}, - {SSH2_CIPHER_CAMELLIA128_CTR, "camel****@opens*****", 16, 16, 0, evp_camellia_128_ctr}, - {SSH2_CIPHER_CAMELLIA192_CTR, "camel****@opens*****", 16, 24, 0, evp_camellia_128_ctr}, - {SSH2_CIPHER_CAMELLIA256_CTR, "camel****@opens*****", 16, 32, 0, evp_camellia_128_ctr}, + {SSH2_CIPHER_CAMELLIA128_CBC, "camel****@opens*****", 16, 16, 0, 0, 0, EVP_camellia_128_cbc}, + {SSH2_CIPHER_CAMELLIA192_CBC, "camel****@opens*****", 16, 24, 0, 0, 0, EVP_camellia_192_cbc}, + {SSH2_CIPHER_CAMELLIA256_CBC, "camel****@opens*****", 16, 32, 0, 0, 0, EVP_camellia_256_cbc}, + {SSH2_CIPHER_CAMELLIA128_CTR, "camel****@opens*****", 16, 16, 0, 0, 0, evp_camellia_128_ctr}, + {SSH2_CIPHER_CAMELLIA192_CTR, "camel****@opens*****", 16, 24, 0, 0, 0, evp_camellia_128_ctr}, + {SSH2_CIPHER_CAMELLIA256_CTR, "camel****@opens*****", 16, 32, 0, 0, 0, evp_camellia_128_ctr}, #endif // WITH_CAMELLIA_PRIVATE - {SSH_CIPHER_NONE, NULL, 0, 0, 0, NULL}, + {SSH2_CIPHER_AES128_GCM, "aes12****@opens*****", 16, 16, 0, 12, 16, EVP_aes_128_gcm}, + {SSH2_CIPHER_AES256_GCM, "aes25****@opens*****", 16, 32, 0, 12, 16, EVP_aes_256_gcm}, + {SSH_CIPHER_NONE, NULL, 0, 0, 0, 0, 0, NULL}, }; @@ -532,6 +537,8 @@ u_char *iv; unsigned int key_len; unsigned int block_size; + unsigned int iv_len; + unsigned int auth_len; }; struct Mac { @@ -713,7 +720,7 @@ 'data' points to the start of the packet data (the length field) */ void SSH1_handle_packet(PTInstVar pvar, char *data, unsigned int len, unsigned int padding); -void SSH2_handle_packet(PTInstVar pvar, char *data, unsigned int len, int etm); +void SSH2_handle_packet(PTInstVar pvar, char *data, unsigned int len, unsigned int aadlen, unsigned int authlen); void SSH_notify_win_size(PTInstVar pvar, int cols, int rows); void SSH_notify_user_name(PTInstVar pvar); void SSH_notify_cred(PTInstVar pvar); @@ -756,6 +763,7 @@ at least 5 bytes must be decrypted */ void SSH_predecrpyt_packet(PTInstVar pvar, char *data); unsigned int SSH_get_clear_MAC_size(PTInstVar pvar); +unsigned int SSH_get_authdata_size(PTInstVar pvar, int direction); #define SSH_is_any_payload(pvar) ((pvar)->ssh_state.payload_datalen > 0) #define SSH_get_host_name(pvar) ((pvar)->ssh_state.hostname) @@ -767,6 +775,8 @@ void debug_print(int no, char *msg, int len); int get_cipher_block_size(SSHCipher cipher); int get_cipher_key_len(SSHCipher cipher); +int get_cipher_iv_len(SSHCipher cipher); +int get_cipher_auth_len(SSHCipher cipher); SSHCipher get_cipher_by_name(char *name); char* get_kex_algorithm_name(kex_algorithm kextype); const EVP_CIPHER* get_cipher_EVP_CIPHER(SSHCipher cipher); Modified: trunk/ttssh2/ttxssh/ttxssh.c =================================================================== --- trunk/ttssh2/ttxssh/ttxssh.c 2017-11-25 15:26:39 UTC (rev 6984) +++ trunk/ttssh2/ttxssh/ttxssh.c 2017-11-25 15:26:45 UTC (rev 6985) @@ -280,6 +280,7 @@ /* SSH_CIPHER_NONE means that all ciphers below that one are disabled. We *never* allow no encryption. */ static char default_strings[] = { + SSH2_CIPHER_AES256_GCM, SSH2_CIPHER_CAMELLIA256_CTR, SSH2_CIPHER_AES256_CTR, SSH2_CIPHER_CAMELLIA256_CBC, @@ -288,6 +289,7 @@ SSH2_CIPHER_AES192_CTR, SSH2_CIPHER_CAMELLIA192_CBC, SSH2_CIPHER_AES192_CBC, + SSH2_CIPHER_AES128_GCM, SSH2_CIPHER_CAMELLIA128_CTR, SSH2_CIPHER_AES128_CTR, SSH2_CIPHER_CAMELLIA128_CBC, @@ -2603,6 +2605,10 @@ return "Camellia192-CTR(SSH2)"; case SSH2_CIPHER_CAMELLIA256_CTR: return "Camellia256-CTR(SSH2)"; + case SSH2_CIPHER_AES128_GCM: + return "AES12****@opens*****(SSH2)"; + case SSH2_CIPHER_AES256_GCM: + return "AES25****@opens*****(SSH2)"; default: return NULL; @@ -4170,7 +4176,7 @@ // TODO: OpenSSH 6.5\x82ł\xCD -Z \x83I\x83v\x83V\x83\x87\x83\x93\x82ŁA\x88Í\x86\x89\xBB\x83A\x83\x8B\x83S\x83\x8A\x83Y\x83\x80\x82\xF0\x8Ew\x92\xE8\x89\\x82\xBE\x82\xAA\x81A // \x82\xB1\x82\xB1\x82ł\xCD"AES256-CBC"\x82ɌŒ\xE8\x82Ƃ\xB7\x82\xE9\x81B cipher_init_SSH2(&cipher_ctx, key, keylen, key + keylen, ivlen, CIPHER_ENCRYPT, - get_cipher_EVP_CIPHER(ciphernameval), 0, pvar); + get_cipher_EVP_CIPHER(ciphernameval), 0, 0, pvar); SecureZeroMemory(key, keylen + ivlen); free(key); @@ -4983,9 +4989,9 @@ MD5_Update(&md, (const unsigned char *)passphrase, strlen(passphrase)); MD5_Final(digest, &md); if (cipher_num == SSH_CIPHER_NONE) { - cipher_init_SSH2(&cipher_ctx, digest, 16, NULL, 0, CIPHER_ENCRYPT, EVP_enc_null(), 0, pvar); + cipher_init_SSH2(&cipher_ctx, digest, 16, NULL, 0, CIPHER_ENCRYPT, EVP_enc_null(), 0, 0, pvar); } else { - cipher_init_SSH2(&cipher_ctx, digest, 16, NULL, 0, CIPHER_ENCRYPT, evp_ssh1_3des(), 0, pvar); + cipher_init_SSH2(&cipher_ctx, digest, 16, NULL, 0, CIPHER_ENCRYPT, evp_ssh1_3des(), 0, 0, pvar); } len = buffer_len(b); if (len % 8) { // fatal error