diff --git a/test/cryptsuite.py b/test/cryptsuite.py index 281f3aab..1b0314f8 100755 --- a/test/cryptsuite.py +++ b/test/cryptsuite.py @@ -1025,6 +1025,46 @@ class crypt(MyTestBase): negativeTest(0x1751997d000000000000000000000001000000001) negativeTest(0x800000000000002000000000000000000f128a2d1) + def testAuxEncryptFns(self): + # Test helper functions such as aes256_encrypt_pubkey. The + # test cases are all just things I made up at random, and the + # expected outputs are generated by running PuTTY's own code; + # this doesn't independently check them against any other + # implementation, but it at least means we're protected + # against code reorganisations changing the behaviour from + # what it was before. + + p = b'three AES blocks, or six DES, of arbitrary input' + + k = b'thirty-two-byte aes-256 test key' + c = unhex('7b112d00c0fc95bc13fcdacfd43281bf' + 'de9389db1bbcfde79d59a303d41fd2eb' + '0955c9477ae4ee3a4d6c1fbe474c0ef6') + self.assertEqual(aes256_encrypt_pubkey(k, p), c) + self.assertEqual(aes256_decrypt_pubkey(k, c), p) + + k = b'3des with keys distinct.' + iv = b'randomIV' + c = unhex('be81ff840d885869a54d63b03d7cd8db' + 'd39ab875e5f7b9da1081f8434cb33c47' + 'dee5bcd530a3f6c13a9fc73e321a843a') + self.assertEqual(des3_encrypt_pubkey_ossh(k, iv, p), c) + self.assertEqual(des3_decrypt_pubkey_ossh(k, iv, c), p) + + k = b'3des, 2keys only' + c = unhex('0b845650d73f615cf16ee3ed20535b5c' + 'd2a8866ee628547bbdad916e2b4b9f19' + '67c15bde33c5b03ff7f403b4f8cf2364') + self.assertEqual(des3_encrypt_pubkey(k, p), c) + self.assertEqual(des3_decrypt_pubkey(k, c), p) + + k = b'7 bytes' + c = unhex('5cac9999cffc980a1d1184d84b71c8cb' + '313d12a1d25a7831179aeb11edaca5ad' + '9482b224105a61c27137587620edcba8') + self.assertEqual(des_encrypt_xdmauth(k, p), c) + self.assertEqual(des_decrypt_xdmauth(k, c), p) + class standard_test_vectors(MyTestBase): def testAES(self): def vector(cipher, key, plaintext, ciphertext): diff --git a/testcrypt.c b/testcrypt.c index 88093649..3fb8b73d 100644 --- a/testcrypt.c +++ b/testcrypt.c @@ -827,6 +827,88 @@ strbuf *des_decrypt_xdmauth_wrapper(ptrlen key, ptrlen data) } #define des_decrypt_xdmauth des_decrypt_xdmauth_wrapper +strbuf *des3_encrypt_pubkey_wrapper(ptrlen key, ptrlen data) +{ + if (key.len != 16) + fatal_error("des3_encrypt_pubkey: key must be 16 bytes long"); + if (data.len % 8 != 0) + fatal_error("des3_encrypt_pubkey: data must be a multiple of 8 bytes"); + strbuf *sb = strbuf_new(); + put_datapl(sb, data); + des3_encrypt_pubkey(key.ptr, sb->u, sb->len); + return sb; +} +#define des3_encrypt_pubkey des3_encrypt_pubkey_wrapper + +strbuf *des3_decrypt_pubkey_wrapper(ptrlen key, ptrlen data) +{ + if (key.len != 16) + fatal_error("des3_decrypt_pubkey: key must be 16 bytes long"); + if (data.len % 8 != 0) + fatal_error("des3_decrypt_pubkey: data must be a multiple of 8 bytes"); + strbuf *sb = strbuf_new(); + put_datapl(sb, data); + des3_decrypt_pubkey(key.ptr, sb->u, sb->len); + return sb; +} +#define des3_decrypt_pubkey des3_decrypt_pubkey_wrapper + +strbuf *des3_encrypt_pubkey_ossh_wrapper(ptrlen key, ptrlen iv, ptrlen data) +{ + if (key.len != 24) + fatal_error("des3_encrypt_pubkey_ossh: key must be 24 bytes long"); + if (iv.len != 8) + fatal_error("des3_encrypt_pubkey_ossh: iv must be 8 bytes long"); + if (data.len % 8 != 0) + fatal_error("des3_encrypt_pubkey_ossh: data must be a multiple of 8 bytes"); + strbuf *sb = strbuf_new(); + put_datapl(sb, data); + des3_encrypt_pubkey_ossh(key.ptr, iv.ptr, sb->u, sb->len); + return sb; +} +#define des3_encrypt_pubkey_ossh des3_encrypt_pubkey_ossh_wrapper + +strbuf *des3_decrypt_pubkey_ossh_wrapper(ptrlen key, ptrlen iv, ptrlen data) +{ + if (key.len != 24) + fatal_error("des3_decrypt_pubkey_ossh: key must be 24 bytes long"); + if (iv.len != 8) + fatal_error("des3_encrypt_pubkey_ossh: iv must be 8 bytes long"); + if (data.len % 8 != 0) + fatal_error("des3_decrypt_pubkey_ossh: data must be a multiple of 8 bytes"); + strbuf *sb = strbuf_new(); + put_datapl(sb, data); + des3_decrypt_pubkey_ossh(key.ptr, iv.ptr, sb->u, sb->len); + return sb; +} +#define des3_decrypt_pubkey_ossh des3_decrypt_pubkey_ossh_wrapper + +strbuf *aes256_encrypt_pubkey_wrapper(ptrlen key, ptrlen data) +{ + if (key.len != 32) + fatal_error("aes256_encrypt_pubkey: key must be 32 bytes long"); + if (data.len % 16 != 0) + fatal_error("aes256_encrypt_pubkey: data must be a multiple of 16 bytes"); + strbuf *sb = strbuf_new(); + put_datapl(sb, data); + aes256_encrypt_pubkey(key.ptr, sb->u, sb->len); + return sb; +} +#define aes256_encrypt_pubkey aes256_encrypt_pubkey_wrapper + +strbuf *aes256_decrypt_pubkey_wrapper(ptrlen key, ptrlen data) +{ + if (key.len != 32) + fatal_error("aes256_decrypt_pubkey: key must be 32 bytes long"); + if (data.len % 16 != 0) + fatal_error("aes256_decrypt_pubkey: data must be a multiple of 16 bytes"); + strbuf *sb = strbuf_new(); + put_datapl(sb, data); + aes256_decrypt_pubkey(key.ptr, sb->u, sb->len); + return sb; +} +#define aes256_decrypt_pubkey aes256_decrypt_pubkey_wrapper + bool crcda_detect(ptrlen packet, ptrlen iv) { if (iv.len != 0 && iv.len != 8) diff --git a/testcrypt.h b/testcrypt.h index b0c209bc..ee9777bf 100644 --- a/testcrypt.h +++ b/testcrypt.h @@ -218,6 +218,12 @@ FUNC2(val_wpoint, ecdsa_public, val_mpint, keyalg) FUNC2(val_epoint, eddsa_public, val_mpint, keyalg) FUNC2(val_string, des_encrypt_xdmauth, val_string_ptrlen, val_string_ptrlen) FUNC2(val_string, des_decrypt_xdmauth, val_string_ptrlen, val_string_ptrlen) +FUNC2(val_string, des3_encrypt_pubkey, val_string_ptrlen, val_string_ptrlen) +FUNC2(val_string, des3_decrypt_pubkey, val_string_ptrlen, val_string_ptrlen) +FUNC3(val_string, des3_encrypt_pubkey_ossh, val_string_ptrlen, val_string_ptrlen, val_string_ptrlen) +FUNC3(val_string, des3_decrypt_pubkey_ossh, val_string_ptrlen, val_string_ptrlen, val_string_ptrlen) +FUNC2(val_string, aes256_encrypt_pubkey, val_string_ptrlen, val_string_ptrlen) +FUNC2(val_string, aes256_decrypt_pubkey, val_string_ptrlen, val_string_ptrlen) FUNC1(uint, crc32_rfc1662, val_string_ptrlen) FUNC1(uint, crc32_ssh1, val_string_ptrlen) FUNC2(uint, crc32_update, uint, val_string_ptrlen)