1
0
mirror of https://git.tartarus.org/simon/putty.git synced 2025-04-15 18:18:05 -05:00

Localise AESContext into sshaes.c.

All access to AES throughout the code is now done via the ssh2_cipher
vtable interface. All code that previously made direct calls to the
underlying functions (for encrypting and decrypting private key files)
now does it by instantiating an ssh2_cipher.

This removes constraints on the AES module's internal structure, and
allows me to reorganise it as much as I like.
This commit is contained in:
Simon Tatham 2019-01-11 06:32:00 +00:00
parent a3e63c7079
commit 9128454750
3 changed files with 34 additions and 47 deletions

View File

@ -547,13 +547,11 @@ static ssh2_userkey *openssh_pem_read(
des3_decrypt_pubkey_ossh(keybuf, key->iv, des3_decrypt_pubkey_ossh(keybuf, key->iv,
key->keyblob->u, key->keyblob->len); key->keyblob->u, key->keyblob->len);
else { else {
AESContext *ctx; ssh2_cipher *cipher = ssh2_cipher_new(&ssh_aes128);
assert(key->encryption == OP_E_AES); ssh2_cipher_setkey(cipher, keybuf);
ctx = aes_make_context(); ssh2_cipher_setiv(cipher, key->iv);
aes128_key(ctx, keybuf); ssh2_cipher_decrypt(cipher, key->keyblob->u, key->keyblob->len);
aes_iv(ctx, key->iv); ssh2_cipher_free(cipher);
aes_ssh2_decrypt_blk(ctx, key->keyblob->u, key->keyblob->len);
aes_free_context(ctx);
} }
smemclr(&md5c, sizeof(md5c)); smemclr(&md5c, sizeof(md5c));
@ -1390,20 +1388,16 @@ static ssh2_userkey *openssh_new_read(
goto error; goto error;
} }
{ {
void *ctx = aes_make_context(); ssh2_cipher *cipher = ssh2_cipher_new(
aes256_key(ctx, keybuf); key->cipher == ON_E_AES256CBC ?
aes_iv(ctx, keybuf + 32); &ssh_aes256 : &ssh_aes256_ctr);
ssh2_cipher_setkey(cipher, keybuf);
ssh2_cipher_setiv(cipher, keybuf + 32);
/* Decrypt the private section in place, casting away /* Decrypt the private section in place, casting away
* the const from key->private being a ptrlen */ * the const from key->private being a ptrlen */
if (key->cipher == ON_E_AES256CBC) { ssh2_cipher_decrypt(cipher, (char *)key->private.ptr,
aes_ssh2_decrypt_blk(ctx, (char *)key->private.ptr, key->private.len);
key->private.len); ssh2_cipher_free(cipher);
}
else {
aes_ssh2_sdctr(ctx, (char *)key->private.ptr,
key->private.len);
}
aes_free_context(ctx);
} }
break; break;
default: default:
@ -1594,18 +1588,17 @@ static bool openssh_new_write(
* material: 32 bytes AES key + 16 bytes iv. * material: 32 bytes AES key + 16 bytes iv.
*/ */
unsigned char keybuf[48]; unsigned char keybuf[48];
void *ctx; ssh2_cipher *cipher;
openssh_bcrypt(passphrase, openssh_bcrypt(passphrase,
bcrypt_salt, sizeof(bcrypt_salt), bcrypt_rounds, bcrypt_salt, sizeof(bcrypt_salt), bcrypt_rounds,
keybuf, sizeof(keybuf)); keybuf, sizeof(keybuf));
ctx = aes_make_context(); cipher = ssh2_cipher_new(&ssh_aes256_ctr);
aes256_key(ctx, keybuf); ssh2_cipher_setkey(cipher, keybuf);
aes_iv(ctx, keybuf + 32); ssh2_cipher_setiv(cipher, keybuf + 32);
aes_ssh2_sdctr(ctx, cpblob->u, ssh2_cipher_encrypt(cipher, cpblob->u, cpblob->len);
cpblob->len); ssh2_cipher_free(cipher);
aes_free_context(ctx);
smemclr(keybuf, sizeof(keybuf)); smemclr(keybuf, sizeof(keybuf));
} }

11
ssh.h
View File

@ -903,17 +903,6 @@ extern const ssh2_macalg ssh_hmac_sha256;
extern const ssh2_macalg ssh2_poly1305; extern const ssh2_macalg ssh2_poly1305;
extern const ssh_compression_alg ssh_zlib; extern const ssh_compression_alg ssh_zlib;
typedef struct AESContext AESContext;
AESContext *aes_make_context(void);
void aes_free_context(AESContext *ctx);
void aes128_key(AESContext *ctx, const void *key);
void aes192_key(AESContext *ctx, const void *key);
void aes256_key(AESContext *ctx, const void *key);
void aes_iv(AESContext *ctx, const void *iv);
void aes_ssh2_encrypt_blk(AESContext *ctx, void *blk, int len);
void aes_ssh2_decrypt_blk(AESContext *ctx, void *blk, int len);
void aes_ssh2_sdctr(AESContext *ctx, void *blk, int len);
/* /*
* PuTTY version number formatted as an SSH version string. * PuTTY version number formatted as an SSH version string.
*/ */

View File

@ -48,6 +48,7 @@
# define INLINE # define INLINE
#endif #endif
typedef struct AESContext AESContext;
struct AESContext { struct AESContext {
uint32_t keysched_buf[(MAX_NR + 1) * NB + 3]; uint32_t keysched_buf[(MAX_NR + 1) * NB + 3];
uint32_t invkeysched_buf[(MAX_NR + 1) * NB + 3]; uint32_t invkeysched_buf[(MAX_NR + 1) * NB + 3];
@ -1024,20 +1025,24 @@ void aes_ssh2_sdctr(AESContext *ctx, void *blk, int len)
void aes256_encrypt_pubkey(const void *key, void *blk, int len) void aes256_encrypt_pubkey(const void *key, void *blk, int len)
{ {
AESContext ctx; char iv[16];
aes_setup(&ctx, key, 32); memset(iv, 0, 16);
memset(ctx.iv, 0, sizeof(ctx.iv)); ssh2_cipher *cipher = ssh2_cipher_new(&ssh_aes256);
aes_encrypt_cbc(blk, len, &ctx); ssh2_cipher_setkey(cipher, key);
smemclr(&ctx, sizeof(ctx)); ssh2_cipher_setiv(cipher, iv);
ssh2_cipher_encrypt(cipher, blk, len);
ssh2_cipher_free(cipher);
} }
void aes256_decrypt_pubkey(const void *key, void *blk, int len) void aes256_decrypt_pubkey(const void *key, void *blk, int len)
{ {
AESContext ctx; char iv[16];
aes_setup(&ctx, key, 32); memset(iv, 0, 16);
memset(ctx.iv, 0, sizeof(ctx.iv)); ssh2_cipher *cipher = ssh2_cipher_new(&ssh_aes256);
aes_decrypt_cbc(blk, len, &ctx); ssh2_cipher_setkey(cipher, key);
smemclr(&ctx, sizeof(ctx)); ssh2_cipher_setiv(cipher, iv);
ssh2_cipher_decrypt(cipher, blk, len);
ssh2_cipher_free(cipher);
} }
struct aes_ssh2_ctx { struct aes_ssh2_ctx {