comparison common-kex.c @ 1672:3a97f14c0235

Add Chacha20-Poly1305, AES128-GCM and AES256-GCM support (#93) * Add Chacha20-Poly1305 authenticated encryption * Add general AEAD approach. * Add [email protected] algo using LibTomCrypt chacha and poly1305 routines. Chacha20-Poly1305 is generally faster than AES256 on CPU w/o dedicated AES instructions, having the same key size. Compiling in will add ~5,5kB to binary size on x86-64. function old new delta chacha_crypt - 1397 +1397 _poly1305_block - 608 +608 poly1305_done - 595 +595 dropbear_chachapoly_crypt - 457 +457 .rodata 26976 27392 +416 poly1305_process - 290 +290 poly1305_init - 221 +221 chacha_setup - 218 +218 encrypt_packet 1068 1270 +202 dropbear_chachapoly_getlength - 147 +147 decrypt_packet 756 897 +141 chacha_ivctr64 - 137 +137 read_packet 543 637 +94 dropbear_chachapoly_start - 94 +94 read_kex_algos 792 880 +88 chacha_keystream - 69 +69 dropbear_mode_chachapoly - 48 +48 sshciphers 280 320 +40 dropbear_mode_none 24 48 +24 dropbear_mode_ctr 24 48 +24 dropbear_mode_cbc 24 48 +24 dropbear_chachapoly_mac - 24 +24 dropbear_chachapoly - 24 +24 gen_new_keys 848 854 +6 ------------------------------------------------------------------------------ (add/remove: 14/0 grow/shrink: 10/0 up/down: 5388/0) Total: 5388 bytes * Add AES128-GCM and AES256-GCM authenticated encryption * Add general AES-GCM mode. * Add [email protected] and [email protected] algo using LibTomCrypt gcm routines. AES-GCM is combination of AES CTR mode and GHASH, slower than AES-CTR on CPU w/o dedicated AES/GHASH instructions therefore disabled by default. Compiling in will add ~6kB to binary size on x86-64. function old new delta gcm_process - 1060 +1060 .rodata 26976 27808 +832 gcm_gf_mult - 820 +820 gcm_add_aad - 660 +660 gcm_shift_table - 512 +512 gcm_done - 471 +471 gcm_add_iv - 384 +384 gcm_init - 347 +347 dropbear_gcm_crypt - 309 +309 encrypt_packet 1068 1270 +202 decrypt_packet 756 897 +141 gcm_reset - 118 +118 read_packet 543 637 +94 read_kex_algos 792 880 +88 sshciphers 280 360 +80 gcm_mult_h - 80 +80 dropbear_gcm_start - 62 +62 dropbear_mode_gcm - 48 +48 dropbear_mode_none 24 48 +24 dropbear_mode_ctr 24 48 +24 dropbear_mode_cbc 24 48 +24 dropbear_ghash - 24 +24 dropbear_gcm_getlength - 24 +24 gen_new_keys 848 854 +6 ------------------------------------------------------------------------------ (add/remove: 14/0 grow/shrink: 10/0 up/down: 6434/0) Total: 6434 bytes
author Vladislav Grishenko <themiron@users.noreply.github.com>
date Mon, 25 May 2020 20:50:25 +0500
parents d32bcb5c557d
children 41bf8f216644
comparison
equal deleted inserted replaced
1671:5c8913b7464c 1672:3a97f14c0235
327 hashkeys(S2C_IV, sizeof(S2C_IV), &hs, 'B'); 327 hashkeys(S2C_IV, sizeof(S2C_IV), &hs, 'B');
328 hashkeys(C2S_key, sizeof(C2S_key), &hs, 'C'); 328 hashkeys(C2S_key, sizeof(C2S_key), &hs, 'C');
329 hashkeys(S2C_key, sizeof(S2C_key), &hs, 'D'); 329 hashkeys(S2C_key, sizeof(S2C_key), &hs, 'D');
330 330
331 if (ses.newkeys->recv.algo_crypt->cipherdesc != NULL) { 331 if (ses.newkeys->recv.algo_crypt->cipherdesc != NULL) {
332 int recv_cipher = find_cipher(ses.newkeys->recv.algo_crypt->cipherdesc->name); 332 int recv_cipher = -1;
333 if (recv_cipher < 0) 333 if (ses.newkeys->recv.algo_crypt->cipherdesc->name != NULL) {
334 dropbear_exit("Crypto error"); 334 recv_cipher = find_cipher(ses.newkeys->recv.algo_crypt->cipherdesc->name);
335 if (recv_cipher < 0)
336 dropbear_exit("Crypto error");
337 }
335 if (ses.newkeys->recv.crypt_mode->start(recv_cipher, 338 if (ses.newkeys->recv.crypt_mode->start(recv_cipher,
336 recv_IV, recv_key, 339 recv_IV, recv_key,
337 ses.newkeys->recv.algo_crypt->keysize, 0, 340 ses.newkeys->recv.algo_crypt->keysize, 0,
338 &ses.newkeys->recv.cipher_state) != CRYPT_OK) { 341 &ses.newkeys->recv.cipher_state) != CRYPT_OK) {
339 dropbear_exit("Crypto error"); 342 dropbear_exit("Crypto error");
340 } 343 }
341 } 344 }
342 345
343 if (ses.newkeys->trans.algo_crypt->cipherdesc != NULL) { 346 if (ses.newkeys->trans.algo_crypt->cipherdesc != NULL) {
344 int trans_cipher = find_cipher(ses.newkeys->trans.algo_crypt->cipherdesc->name); 347 int trans_cipher = -1;
345 if (trans_cipher < 0) 348 if (ses.newkeys->trans.algo_crypt->cipherdesc->name != NULL) {
346 dropbear_exit("Crypto error"); 349 trans_cipher = find_cipher(ses.newkeys->trans.algo_crypt->cipherdesc->name);
350 if (trans_cipher < 0)
351 dropbear_exit("Crypto error");
352 }
347 if (ses.newkeys->trans.crypt_mode->start(trans_cipher, 353 if (ses.newkeys->trans.crypt_mode->start(trans_cipher,
348 trans_IV, trans_key, 354 trans_IV, trans_key,
349 ses.newkeys->trans.algo_crypt->keysize, 0, 355 ses.newkeys->trans.algo_crypt->keysize, 0,
350 &ses.newkeys->trans.cipher_state) != CRYPT_OK) { 356 &ses.newkeys->trans.cipher_state) != CRYPT_OK) {
351 dropbear_exit("Crypto error"); 357 dropbear_exit("Crypto error");
866 } 872 }
867 TRACE(("enc s2c is %s", s2c_cipher_algo->name)) 873 TRACE(("enc s2c is %s", s2c_cipher_algo->name))
868 874
869 /* mac_algorithms_client_to_server */ 875 /* mac_algorithms_client_to_server */
870 c2s_hash_algo = buf_match_algo(ses.payload, sshhashes, NULL, NULL); 876 c2s_hash_algo = buf_match_algo(ses.payload, sshhashes, NULL, NULL);
877 #if DROPBEAR_AEAD_MODE
878 if (((struct dropbear_cipher_mode*)c2s_cipher_algo->mode)->aead_crypt != NULL) {
879 c2s_hash_algo = NULL;
880 } else
881 #endif
871 if (c2s_hash_algo == NULL) { 882 if (c2s_hash_algo == NULL) {
872 erralgo = "mac c->s"; 883 erralgo = "mac c->s";
873 goto error; 884 goto error;
874 } 885 }
875 TRACE(("hash c2s is %s", c2s_hash_algo->name)) 886 TRACE(("hash c2s is %s", c2s_hash_algo ? c2s_hash_algo->name : "<implicit>"))
876 887
877 /* mac_algorithms_server_to_client */ 888 /* mac_algorithms_server_to_client */
878 s2c_hash_algo = buf_match_algo(ses.payload, sshhashes, NULL, NULL); 889 s2c_hash_algo = buf_match_algo(ses.payload, sshhashes, NULL, NULL);
890 #if DROPBEAR_AEAD_MODE
891 if (((struct dropbear_cipher_mode*)s2c_cipher_algo->mode)->aead_crypt != NULL) {
892 s2c_hash_algo = NULL;
893 } else
894 #endif
879 if (s2c_hash_algo == NULL) { 895 if (s2c_hash_algo == NULL) {
880 erralgo = "mac s->c"; 896 erralgo = "mac s->c";
881 goto error; 897 goto error;
882 } 898 }
883 TRACE(("hash s2c is %s", s2c_hash_algo->name)) 899 TRACE(("hash s2c is %s", s2c_hash_algo ? s2c_hash_algo->name : "<implicit>"))
884 900
885 /* compression_algorithms_client_to_server */ 901 /* compression_algorithms_client_to_server */
886 c2s_comp_algo = buf_match_algo(ses.payload, ses.compress_algos, NULL, NULL); 902 c2s_comp_algo = buf_match_algo(ses.payload, ses.compress_algos, NULL, NULL);
887 if (c2s_comp_algo == NULL) { 903 if (c2s_comp_algo == NULL) {
888 erralgo = "comp c->s"; 904 erralgo = "comp c->s";
923 ses.newkeys->recv.crypt_mode = 939 ses.newkeys->recv.crypt_mode =
924 (struct dropbear_cipher_mode*)s2c_cipher_algo->mode; 940 (struct dropbear_cipher_mode*)s2c_cipher_algo->mode;
925 ses.newkeys->trans.crypt_mode = 941 ses.newkeys->trans.crypt_mode =
926 (struct dropbear_cipher_mode*)c2s_cipher_algo->mode; 942 (struct dropbear_cipher_mode*)c2s_cipher_algo->mode;
927 ses.newkeys->recv.algo_mac = 943 ses.newkeys->recv.algo_mac =
944 #if DROPBEAR_AEAD_MODE
945 s2c_hash_algo == NULL ? ses.newkeys->recv.crypt_mode->aead_mac :
946 #endif
928 (struct dropbear_hash*)s2c_hash_algo->data; 947 (struct dropbear_hash*)s2c_hash_algo->data;
929 ses.newkeys->trans.algo_mac = 948 ses.newkeys->trans.algo_mac =
949 #if DROPBEAR_AEAD_MODE
950 c2s_hash_algo == NULL ? ses.newkeys->trans.crypt_mode->aead_mac :
951 #endif
930 (struct dropbear_hash*)c2s_hash_algo->data; 952 (struct dropbear_hash*)c2s_hash_algo->data;
931 ses.newkeys->recv.algo_comp = s2c_comp_algo->val; 953 ses.newkeys->recv.algo_comp = s2c_comp_algo->val;
932 ses.newkeys->trans.algo_comp = c2s_comp_algo->val; 954 ses.newkeys->trans.algo_comp = c2s_comp_algo->val;
933 } else { 955 } else {
934 /* SERVER */ 956 /* SERVER */
939 ses.newkeys->recv.crypt_mode = 961 ses.newkeys->recv.crypt_mode =
940 (struct dropbear_cipher_mode*)c2s_cipher_algo->mode; 962 (struct dropbear_cipher_mode*)c2s_cipher_algo->mode;
941 ses.newkeys->trans.crypt_mode = 963 ses.newkeys->trans.crypt_mode =
942 (struct dropbear_cipher_mode*)s2c_cipher_algo->mode; 964 (struct dropbear_cipher_mode*)s2c_cipher_algo->mode;
943 ses.newkeys->recv.algo_mac = 965 ses.newkeys->recv.algo_mac =
966 #if DROPBEAR_AEAD_MODE
967 c2s_hash_algo == NULL ? ses.newkeys->recv.crypt_mode->aead_mac :
968 #endif
944 (struct dropbear_hash*)c2s_hash_algo->data; 969 (struct dropbear_hash*)c2s_hash_algo->data;
945 ses.newkeys->trans.algo_mac = 970 ses.newkeys->trans.algo_mac =
971 #if DROPBEAR_AEAD_MODE
972 s2c_hash_algo == NULL ? ses.newkeys->trans.crypt_mode->aead_mac :
973 #endif
946 (struct dropbear_hash*)s2c_hash_algo->data; 974 (struct dropbear_hash*)s2c_hash_algo->data;
947 ses.newkeys->recv.algo_comp = c2s_comp_algo->val; 975 ses.newkeys->recv.algo_comp = c2s_comp_algo->val;
948 ses.newkeys->trans.algo_comp = s2c_comp_algo->val; 976 ses.newkeys->trans.algo_comp = s2c_comp_algo->val;
949 } 977 }
950 978