mirror of
				https://github.com/libssh2/libssh2.git
				synced 2025-11-03 22:13:11 +03:00 
			
		
		
		
	Support AES-Counter ciphers.
This commit is contained in:
		
							
								
								
									
										1
									
								
								COPYING
									
									
									
									
									
								
							
							
						
						
									
										1
									
								
								COPYING
									
									
									
									
									
								
							@@ -1,6 +1,7 @@
 | 
			
		||||
/* Copyright (c) 2004-2007 Sara Golemon <sarag@libssh2.org>
 | 
			
		||||
 * Copyright (c) 2006-2007 The Written Word, Inc.
 | 
			
		||||
 * Copyright (c) 2009 Daniel Stenberg
 | 
			
		||||
 * Copyright (C) 2008, 2009 Simon Josefsson
 | 
			
		||||
 * All rights reserved.
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms,
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										4
									
								
								NEWS
									
									
									
									
									
								
							
							
						
						
									
										4
									
								
								NEWS
									
									
									
									
									
								
							@@ -7,6 +7,10 @@ Version 1.2.2 (unreleased)
 | 
			
		||||
    <http://thread.gmane.org/gmane.network.ssh.libssh2.devel/2530>.
 | 
			
		||||
    By Simon Josefsson.
 | 
			
		||||
 | 
			
		||||
  o Support for the "aes128-ctr", "aes192-ctr", "aes256-ctr" ciphers
 | 
			
		||||
    as per RFC 4344 for libgcrypt and OpenSSL.  They are now the
 | 
			
		||||
    preferred ciphers.  By Simon Josefsson.
 | 
			
		||||
 | 
			
		||||
  o Support for the "arcfour128" cipher as per RFC 4345 for libgcrypt
 | 
			
		||||
    and OpenSSL.  It is preferred over the normal "arcfour" cipher
 | 
			
		||||
    which is somewhat broken.  By Simon Josefsson.
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										47
									
								
								src/crypt.c
									
									
									
									
									
								
							
							
						
						
									
										47
									
								
								src/crypt.c
									
									
									
									
									
								
							@@ -1,5 +1,5 @@
 | 
			
		||||
/* Copyright (c) 2004-2007, Sara Golemon <sarag@libssh2.org>
 | 
			
		||||
 * Copyright (c) 2009 Simon Josefsson <simon@josefsson.org>
 | 
			
		||||
/* Copyright (c) 2009 Simon Josefsson <simon@josefsson.org>
 | 
			
		||||
 * Copyright (c) 2004-2007, Sara Golemon <sarag@libssh2.org>
 | 
			
		||||
 * All rights reserved.
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms,
 | 
			
		||||
@@ -115,6 +115,44 @@ crypt_dtor(LIBSSH2_SESSION * session, void **abstract)
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#if LIBSSH2_AES_CTR
 | 
			
		||||
static const LIBSSH2_CRYPT_METHOD libssh2_crypt_method_aes128_ctr = {
 | 
			
		||||
    "aes128-ctr",
 | 
			
		||||
    16,                         /* blocksize */
 | 
			
		||||
    16,                         /* initial value length */
 | 
			
		||||
    16,                         /* secret length -- 16*8 == 128bit */
 | 
			
		||||
    0,                          /* flags */
 | 
			
		||||
    &crypt_init,
 | 
			
		||||
    &crypt_encrypt,
 | 
			
		||||
    &crypt_dtor,
 | 
			
		||||
    _libssh2_cipher_aes128ctr
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static const LIBSSH2_CRYPT_METHOD libssh2_crypt_method_aes192_ctr = {
 | 
			
		||||
    "aes192-ctr",
 | 
			
		||||
    16,                         /* blocksize */
 | 
			
		||||
    16,                         /* initial value length */
 | 
			
		||||
    24,                         /* secret length -- 24*8 == 192bit */
 | 
			
		||||
    0,                          /* flags */
 | 
			
		||||
    &crypt_init,
 | 
			
		||||
    &crypt_encrypt,
 | 
			
		||||
    &crypt_dtor,
 | 
			
		||||
    _libssh2_cipher_aes192ctr
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
static const LIBSSH2_CRYPT_METHOD libssh2_crypt_method_aes256_ctr = {
 | 
			
		||||
    "aes256-ctr",
 | 
			
		||||
    16,                         /* blocksize */
 | 
			
		||||
    16,                         /* initial value length */
 | 
			
		||||
    32,                         /* secret length -- 32*8 == 256bit */
 | 
			
		||||
    0,                          /* flags */
 | 
			
		||||
    &crypt_init,
 | 
			
		||||
    &crypt_encrypt,
 | 
			
		||||
    &crypt_dtor,
 | 
			
		||||
    _libssh2_cipher_aes256ctr
 | 
			
		||||
};
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#if LIBSSH2_AES
 | 
			
		||||
static const LIBSSH2_CRYPT_METHOD libssh2_crypt_method_aes128_cbc = {
 | 
			
		||||
    "aes128-cbc",
 | 
			
		||||
@@ -258,6 +296,11 @@ static const LIBSSH2_CRYPT_METHOD libssh2_crypt_method_3des_cbc = {
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
static const LIBSSH2_CRYPT_METHOD *_libssh2_crypt_methods[] = {
 | 
			
		||||
#if LIBSSH2_AES_CTR
 | 
			
		||||
  &libssh2_crypt_method_aes128_ctr,
 | 
			
		||||
  &libssh2_crypt_method_aes192_ctr,
 | 
			
		||||
  &libssh2_crypt_method_aes256_ctr,
 | 
			
		||||
#endif /* LIBSSH2_AES */
 | 
			
		||||
#if LIBSSH2_AES
 | 
			
		||||
    &libssh2_crypt_method_aes256_cbc,
 | 
			
		||||
    &libssh2_crypt_method_rijndael_cbc_lysator_liu_se,  /* == aes256-cbc */
 | 
			
		||||
 
 | 
			
		||||
@@ -544,8 +544,11 @@ _libssh2_cipher_init(_libssh2_cipher_ctx * h,
 | 
			
		||||
 | 
			
		||||
    if (mode != GCRY_CIPHER_MODE_STREAM) {
 | 
			
		||||
        int blklen = gcry_cipher_get_algo_blklen(cipher);
 | 
			
		||||
        ret = gcry_cipher_setiv(*h, iv, blklen);
 | 
			
		||||
        if (ret) {
 | 
			
		||||
	if (mode == GCRY_CIPHER_MODE_CTR)
 | 
			
		||||
	  ret = gcry_cipher_setctr(*h, iv, blklen);
 | 
			
		||||
	else
 | 
			
		||||
	  ret = gcry_cipher_setiv(*h, iv, blklen);
 | 
			
		||||
	if (ret) {
 | 
			
		||||
            gcry_cipher_close(*h);
 | 
			
		||||
            return -1;
 | 
			
		||||
        }
 | 
			
		||||
 
 | 
			
		||||
@@ -44,6 +44,7 @@
 | 
			
		||||
#define LIBSSH2_HMAC_RIPEMD 1
 | 
			
		||||
 | 
			
		||||
#define LIBSSH2_AES 1
 | 
			
		||||
#define LIBSSH2_AES_CTR 1
 | 
			
		||||
#define LIBSSH2_BLOWFISH 1
 | 
			
		||||
#define LIBSSH2_RC4 1
 | 
			
		||||
#define LIBSSH2_CAST 1
 | 
			
		||||
@@ -160,7 +161,13 @@ int _libssh2_dsa_sha1_sign(libssh2_dsa_ctx * dsactx,
 | 
			
		||||
#define _libssh2_gcry_cipher(c) (c >> 8)
 | 
			
		||||
#define _libssh2_gcry_mode(m) (m & 0xFF)
 | 
			
		||||
 | 
			
		||||
#define _libssh2_cipher_aes256			\
 | 
			
		||||
#define _libssh2_cipher_aes256ctr		\
 | 
			
		||||
  _libssh2_gcry_ciphermode(GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_CTR)
 | 
			
		||||
#define _libssh2_cipher_aes192ctr		\
 | 
			
		||||
  _libssh2_gcry_ciphermode(GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_CTR)
 | 
			
		||||
#define _libssh2_cipher_aes128ctr					\
 | 
			
		||||
  _libssh2_gcry_ciphermode(GCRY_CIPHER_AES128, GCRY_CIPHER_MODE_CTR)
 | 
			
		||||
#define _libssh2_cipher_aes256						\
 | 
			
		||||
  _libssh2_gcry_ciphermode(GCRY_CIPHER_AES256, GCRY_CIPHER_MODE_CBC)
 | 
			
		||||
#define _libssh2_cipher_aes192			\
 | 
			
		||||
  _libssh2_gcry_ciphermode(GCRY_CIPHER_AES192, GCRY_CIPHER_MODE_CBC)
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										106
									
								
								src/openssl.c
									
									
									
									
									
								
							
							
						
						
									
										106
									
								
								src/openssl.c
									
									
									
									
									
								
							@@ -1,7 +1,9 @@
 | 
			
		||||
/* Copyright (C) 2006, 2007 The Written Word, Inc.  All rights reserved.
 | 
			
		||||
 * Author: Simon Josefsson
 | 
			
		||||
/* Copyright (C) 2009 Simon Josefsson
 | 
			
		||||
 * Copyright (C) 2006, 2007 The Written Word, Inc.  All rights reserved.
 | 
			
		||||
 * Copyright (c) 2004-2006, Sara Golemon <sarag@libssh2.org>
 | 
			
		||||
 *
 | 
			
		||||
 * Author: Simon Josefsson
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms,
 | 
			
		||||
 * with or without modification, are permitted provided
 | 
			
		||||
 * that the following conditions are met:
 | 
			
		||||
@@ -197,6 +199,106 @@ _libssh2_cipher_crypt(_libssh2_cipher_ctx * ctx,
 | 
			
		||||
    return ret == 1 ? 0 : 1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#include <openssl/aes.h>
 | 
			
		||||
 | 
			
		||||
typedef struct
 | 
			
		||||
{
 | 
			
		||||
    AES_KEY       key;
 | 
			
		||||
    unsigned char ctr[AES_BLOCK_SIZE];
 | 
			
		||||
} aes_ctr_ctx;
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
aes_ctr_init(EVP_CIPHER_CTX *ctx, const unsigned char *key,
 | 
			
		||||
	     const unsigned char *iv, int enc) /* init key */
 | 
			
		||||
{
 | 
			
		||||
    aes_ctr_ctx *c = malloc(sizeof(*c));
 | 
			
		||||
    if (c == NULL)
 | 
			
		||||
	return 0;
 | 
			
		||||
 | 
			
		||||
    AES_set_encrypt_key(key, 8 * ctx->key_len, &c->key);
 | 
			
		||||
    memcpy(c->ctr, iv, AES_BLOCK_SIZE);
 | 
			
		||||
 | 
			
		||||
    EVP_CIPHER_CTX_set_app_data(ctx, c);
 | 
			
		||||
 | 
			
		||||
    return 1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
aes_ctr_do_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
 | 
			
		||||
		  const unsigned char *in,
 | 
			
		||||
		  unsigned int inl) /* encrypt/decrypt data */
 | 
			
		||||
{
 | 
			
		||||
    aes_ctr_ctx *c = EVP_CIPHER_CTX_get_app_data(ctx);
 | 
			
		||||
    unsigned char b1[AES_BLOCK_SIZE];
 | 
			
		||||
    size_t i;
 | 
			
		||||
 | 
			
		||||
    if (inl != 16) /* libssh2 only ever encrypt one block */
 | 
			
		||||
	return 0;
 | 
			
		||||
 | 
			
		||||
/*
 | 
			
		||||
  To encrypt a packet P=P1||P2||...||Pn (where P1, P2, ..., Pn are each
 | 
			
		||||
  blocks of length L), the encryptor first encrypts <X> with <cipher>
 | 
			
		||||
  to obtain a block B1.  The block B1 is then XORed with P1 to generate
 | 
			
		||||
  the ciphertext block C1.  The counter X is then incremented
 | 
			
		||||
*/
 | 
			
		||||
 | 
			
		||||
    AES_encrypt(c->ctr, b1, &c->key);
 | 
			
		||||
 | 
			
		||||
    for (i = 0; i < 16; i++)
 | 
			
		||||
	*out++ = *in++ ^ b1[i];
 | 
			
		||||
 | 
			
		||||
    i = 15;
 | 
			
		||||
    while (c->ctr[i]++ == 0xFF) {
 | 
			
		||||
	if (i == 0)
 | 
			
		||||
	    break;
 | 
			
		||||
	i--;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return 1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int
 | 
			
		||||
aes_ctr_cleanup(EVP_CIPHER_CTX *ctx) /* cleanup ctx */
 | 
			
		||||
{
 | 
			
		||||
    free(EVP_CIPHER_CTX_get_app_data(ctx));
 | 
			
		||||
    return 1;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static const EVP_CIPHER *
 | 
			
		||||
make_ctr_evp (size_t keylen)
 | 
			
		||||
{
 | 
			
		||||
    static EVP_CIPHER aes_ctr_cipher;
 | 
			
		||||
 | 
			
		||||
    memset(&aes_ctr_cipher, 0, sizeof(aes_ctr_cipher));
 | 
			
		||||
 | 
			
		||||
    aes_ctr_cipher.block_size = 16;
 | 
			
		||||
    aes_ctr_cipher.key_len = keylen;
 | 
			
		||||
    aes_ctr_cipher.iv_len = 16;
 | 
			
		||||
    aes_ctr_cipher.init = aes_ctr_init;
 | 
			
		||||
    aes_ctr_cipher.do_cipher = aes_ctr_do_cipher;
 | 
			
		||||
    aes_ctr_cipher.cleanup = aes_ctr_cleanup;
 | 
			
		||||
 | 
			
		||||
    return &aes_ctr_cipher;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const EVP_CIPHER *
 | 
			
		||||
_libssh2_EVP_aes_128_ctr(void)
 | 
			
		||||
{
 | 
			
		||||
    return make_ctr_evp (16);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const EVP_CIPHER *
 | 
			
		||||
_libssh2_EVP_aes_192_ctr(void)
 | 
			
		||||
{
 | 
			
		||||
    return make_ctr_evp (24);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
const EVP_CIPHER *
 | 
			
		||||
_libssh2_EVP_aes_256_ctr(void)
 | 
			
		||||
{
 | 
			
		||||
    return make_ctr_evp (32);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* TODO: Optionally call a passphrase callback specified by the
 | 
			
		||||
 * calling program
 | 
			
		||||
 */
 | 
			
		||||
 
 | 
			
		||||
@@ -1,4 +1,6 @@
 | 
			
		||||
/* Copyright (C) 2006, 2007 The Written Word, Inc.  All rights reserved.
 | 
			
		||||
/* Copyright (C) 2009 Simon Josefsson
 | 
			
		||||
 * Copyright (C) 2006, 2007 The Written Word, Inc.  All rights reserved.
 | 
			
		||||
 *
 | 
			
		||||
 * Author: Simon Josefsson
 | 
			
		||||
 *
 | 
			
		||||
 * Redistribution and use in source and binary forms,
 | 
			
		||||
@@ -71,6 +73,7 @@
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#if OPENSSL_VERSION_NUMBER >= 0x00907000L && !defined(OPENSSL_NO_AES)
 | 
			
		||||
# define LIBSSH2_AES_CTR 1
 | 
			
		||||
# define LIBSSH2_AES 1
 | 
			
		||||
#else
 | 
			
		||||
# define LIBSSH2_AES 0
 | 
			
		||||
@@ -194,6 +197,9 @@ int _libssh2_dsa_sha1_sign(libssh2_dsa_ctx * dsactx,
 | 
			
		||||
#define _libssh2_cipher_aes256 EVP_aes_256_cbc
 | 
			
		||||
#define _libssh2_cipher_aes192 EVP_aes_192_cbc
 | 
			
		||||
#define _libssh2_cipher_aes128 EVP_aes_128_cbc
 | 
			
		||||
#define _libssh2_cipher_aes128ctr _libssh2_EVP_aes_128_ctr
 | 
			
		||||
#define _libssh2_cipher_aes192ctr _libssh2_EVP_aes_192_ctr
 | 
			
		||||
#define _libssh2_cipher_aes256ctr _libssh2_EVP_aes_256_ctr
 | 
			
		||||
#define _libssh2_cipher_blowfish EVP_bf_cbc
 | 
			
		||||
#define _libssh2_cipher_arcfour EVP_rc4
 | 
			
		||||
#define _libssh2_cipher_cast5 EVP_cast5_cbc
 | 
			
		||||
@@ -223,3 +229,7 @@ int _libssh2_cipher_crypt(_libssh2_cipher_ctx * ctx,
 | 
			
		||||
#define _libssh2_bn_bytes(bn) BN_num_bytes(bn)
 | 
			
		||||
#define _libssh2_bn_bits(bn) BN_num_bits(bn)
 | 
			
		||||
#define _libssh2_bn_free(bn) BN_clear_free(bn)
 | 
			
		||||
 | 
			
		||||
const EVP_CIPHER *_libssh2_EVP_aes_128_ctr(void);
 | 
			
		||||
const EVP_CIPHER *_libssh2_EVP_aes_192_ctr(void);
 | 
			
		||||
const EVP_CIPHER *_libssh2_EVP_aes_256_ctr(void);
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user