mirror of
https://github.com/shadowsocks/shadowsocks-libev.git
synced 2026-10-28 11:43:50 +00:00
Refine buffer handling
This commit is contained in:
+159
-173
@@ -93,15 +93,14 @@ static void dump(char *tag, char *text, int len)
|
||||
{
|
||||
int i;
|
||||
printf("%s: ", tag);
|
||||
for (i = 0; i < len; i++) {
|
||||
for (i = 0; i < len; i++)
|
||||
printf("0x%02x ", (uint8_t)text[i]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
static const char * supported_ciphers[CIPHER_NUM] =
|
||||
{
|
||||
static const char *supported_ciphers[CIPHER_NUM] = {
|
||||
"table",
|
||||
"rc4",
|
||||
"rc4-md5",
|
||||
@@ -122,8 +121,7 @@ static const char * supported_ciphers[CIPHER_NUM] =
|
||||
};
|
||||
|
||||
#ifdef USE_CRYPTO_POLARSSL
|
||||
static const char * supported_ciphers_polarssl[CIPHER_NUM] =
|
||||
{
|
||||
static const char *supported_ciphers_polarssl[CIPHER_NUM] = {
|
||||
"table",
|
||||
"ARC4-128",
|
||||
"ARC4-128",
|
||||
@@ -145,8 +143,7 @@ static const char * supported_ciphers_polarssl[CIPHER_NUM] =
|
||||
#endif
|
||||
|
||||
#ifdef USE_CRYPTO_MBEDTLS
|
||||
static const char * supported_ciphers_mbedtls[CIPHER_NUM] =
|
||||
{
|
||||
static const char *supported_ciphers_mbedtls[CIPHER_NUM] = {
|
||||
"table",
|
||||
"ARC4-128",
|
||||
"ARC4-128",
|
||||
@@ -168,8 +165,7 @@ static const char * supported_ciphers_mbedtls[CIPHER_NUM] =
|
||||
#endif
|
||||
|
||||
#ifdef USE_CRYPTO_APPLECC
|
||||
static const CCAlgorithm supported_ciphers_applecc[CIPHER_NUM] =
|
||||
{
|
||||
static const CCAlgorithm supported_ciphers_applecc[CIPHER_NUM] = {
|
||||
kCCAlgorithmInvalid,
|
||||
kCCAlgorithmRC4,
|
||||
kCCAlgorithmRC4,
|
||||
@@ -191,20 +187,18 @@ static const CCAlgorithm supported_ciphers_applecc[CIPHER_NUM] =
|
||||
|
||||
#endif
|
||||
|
||||
static const int supported_ciphers_iv_size[CIPHER_NUM] =
|
||||
{
|
||||
static const int supported_ciphers_iv_size[CIPHER_NUM] = {
|
||||
0, 0, 16, 16, 16, 16, 8, 16, 16, 16, 8, 8, 8, 8, 16, 8, 8
|
||||
};
|
||||
|
||||
static const int supported_ciphers_key_size[CIPHER_NUM] =
|
||||
{
|
||||
static const int supported_ciphers_key_size[CIPHER_NUM] = {
|
||||
0, 16, 16, 16, 24, 32, 16, 16, 24, 32, 16, 8, 16, 16, 16, 32, 32
|
||||
};
|
||||
|
||||
int balloc(buffer_t *ptr, size_t capacity)
|
||||
{
|
||||
memset(ptr, 0 , sizeof(buffer_t));
|
||||
ptr->array = malloc(capacity);
|
||||
memset(ptr, 0, sizeof(buffer_t));
|
||||
ptr->array = malloc(capacity);
|
||||
ptr->capacity = capacity;
|
||||
return capacity;
|
||||
}
|
||||
@@ -221,8 +215,8 @@ int brealloc(buffer_t *ptr, size_t len, size_t capacity)
|
||||
|
||||
void bfree(buffer_t *ptr)
|
||||
{
|
||||
ptr->idx = 0;
|
||||
ptr->len = 0;
|
||||
ptr->idx = 0;
|
||||
ptr->len = 0;
|
||||
ptr->capacity = 0;
|
||||
if (ptr->array != NULL) {
|
||||
free(ptr->array);
|
||||
@@ -314,7 +308,7 @@ static void merge_sort(uint8_t array[], int length,
|
||||
|
||||
llength = length - middle;
|
||||
|
||||
left = array;
|
||||
left = array;
|
||||
right = array + llength;
|
||||
|
||||
merge_sort(left, llength, salt, key);
|
||||
@@ -359,20 +353,16 @@ void enc_table_init(const char *pass)
|
||||
|
||||
digest = enc_md5((const uint8_t *)pass, strlen(pass), NULL);
|
||||
|
||||
for (i = 0; i < 8; i++) {
|
||||
for (i = 0; i < 8; i++)
|
||||
key += OFFSET_ROL(digest, i);
|
||||
}
|
||||
|
||||
for (i = 0; i < 256; ++i) {
|
||||
for (i = 0; i < 256; ++i)
|
||||
enc_table[i] = i;
|
||||
}
|
||||
for (i = 1; i < 1024; ++i) {
|
||||
for (i = 1; i < 1024; ++i)
|
||||
merge_sort(enc_table, 256, i, key);
|
||||
}
|
||||
for (i = 0; i < 256; ++i) {
|
||||
for (i = 0; i < 256; ++i)
|
||||
// gen decrypt table from encrypt table
|
||||
dec_table[enc_table[i]] = i;
|
||||
}
|
||||
}
|
||||
|
||||
int cipher_iv_size(const cipher_kt_t *cipher)
|
||||
@@ -436,8 +426,8 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
int rv;
|
||||
|
||||
nkey = cipher_key_size(cipher);
|
||||
niv = cipher_iv_size(cipher);
|
||||
rv = nkey;
|
||||
niv = cipher_iv_size(cipher);
|
||||
rv = nkey;
|
||||
if (pass == NULL) {
|
||||
return nkey;
|
||||
}
|
||||
@@ -447,8 +437,8 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
return 0;
|
||||
}
|
||||
addmd = 0;
|
||||
mds = md_get_size(md);
|
||||
for (;; ) {
|
||||
mds = md_get_size(md);
|
||||
for (;;) {
|
||||
int error;
|
||||
do {
|
||||
error = 1;
|
||||
@@ -478,7 +468,7 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
|
||||
i = 0;
|
||||
if (nkey) {
|
||||
for (;; ) {
|
||||
for (;;) {
|
||||
if (nkey == 0) {
|
||||
break;
|
||||
}
|
||||
@@ -493,7 +483,7 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
}
|
||||
}
|
||||
if (niv && (i != mds)) {
|
||||
for (;; ) {
|
||||
for (;;) {
|
||||
if (niv == 0) {
|
||||
break;
|
||||
}
|
||||
@@ -518,26 +508,26 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
/*
|
||||
*
|
||||
* Generic message digest context.
|
||||
|
||||
typedef struct {
|
||||
Information about the associated message digest
|
||||
const mbedtls_md_info_t *md_info;
|
||||
|
||||
Digest-specific context
|
||||
void *md_ctx;
|
||||
|
||||
HMAC part of the context
|
||||
void *hmac_ctx;
|
||||
} mbedtls_md_context_t; // mbedtls 2.0.0
|
||||
|
||||
typedef struct {
|
||||
Information about the associated message digest
|
||||
const md_info_t *md_info;
|
||||
|
||||
Digest-specific context
|
||||
void *md_ctx;
|
||||
} md_context_t; //polarssl 1.3
|
||||
|
||||
*
|
||||
* typedef struct {
|
||||
* Information about the associated message digest
|
||||
* const mbedtls_md_info_t *md_info;
|
||||
*
|
||||
* Digest-specific context
|
||||
* void *md_ctx;
|
||||
*
|
||||
* HMAC part of the context
|
||||
* void *hmac_ctx;
|
||||
* } mbedtls_md_context_t; // mbedtls 2.0.0
|
||||
*
|
||||
* typedef struct {
|
||||
* Information about the associated message digest
|
||||
* const md_info_t *md_info;
|
||||
*
|
||||
* Digest-specific context
|
||||
* void *md_ctx;
|
||||
* } md_context_t; //polarssl 1.3
|
||||
*
|
||||
*/
|
||||
// NOTE: different struct body, initialize new param hmac 0 to disable HMAC
|
||||
mbedtls_md_context_t c;
|
||||
@@ -550,8 +540,8 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
int rv;
|
||||
|
||||
nkey = cipher_key_size(cipher);
|
||||
niv = cipher_iv_size(cipher);
|
||||
rv = nkey;
|
||||
niv = cipher_iv_size(cipher);
|
||||
rv = nkey;
|
||||
if (pass == NULL) {
|
||||
return nkey;
|
||||
}
|
||||
@@ -564,8 +554,8 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
return 0;
|
||||
}
|
||||
addmd = 0;
|
||||
mds = mbedtls_md_get_size(md);
|
||||
for (;; ) {
|
||||
mds = mbedtls_md_get_size(md);
|
||||
for (;;) {
|
||||
int error;
|
||||
do {
|
||||
error = 1;
|
||||
@@ -588,14 +578,14 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
error = 0;
|
||||
} while (0);
|
||||
if (error) {
|
||||
mbedtls_md_free(&c); //md_free_ctx deprecated, Use mbedtls_md_free() instead
|
||||
mbedtls_md_free(&c); // md_free_ctx deprecated, Use mbedtls_md_free() instead
|
||||
memset(md_buf, 0, MAX_MD_SIZE);
|
||||
return 0;
|
||||
}
|
||||
|
||||
i = 0;
|
||||
if (nkey) {
|
||||
for (;; ) {
|
||||
for (;;) {
|
||||
if (nkey == 0) {
|
||||
break;
|
||||
}
|
||||
@@ -610,7 +600,7 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
}
|
||||
}
|
||||
if (niv && (i != mds)) {
|
||||
for (;; ) {
|
||||
for (;;) {
|
||||
if (niv == 0) {
|
||||
break;
|
||||
}
|
||||
@@ -628,7 +618,7 @@ int bytes_to_key(const cipher_kt_t *cipher, const digest_type_t *md,
|
||||
break;
|
||||
}
|
||||
}
|
||||
mbedtls_md_free(&c); //NOTE: md_free_ctx deprecated, Use mbedtls_md_free() instead
|
||||
mbedtls_md_free(&c); // NOTE: md_free_ctx deprecated, Use mbedtls_md_free() instead
|
||||
memset(md_buf, 0, MAX_MD_SIZE);
|
||||
return rv;
|
||||
#endif
|
||||
@@ -642,7 +632,7 @@ int rand_bytes(uint8_t *output, int len)
|
||||
static entropy_context ec = {};
|
||||
static ctr_drbg_context cd_ctx = {};
|
||||
static unsigned char rand_initialised = 0;
|
||||
const size_t blen = min(len, CTR_DRBG_MAX_REQUEST);
|
||||
const size_t blen = min(len, CTR_DRBG_MAX_REQUEST);
|
||||
|
||||
if (!rand_initialised) {
|
||||
#ifdef _WIN32
|
||||
@@ -694,7 +684,7 @@ int rand_bytes(uint8_t *output, int len)
|
||||
return 0;
|
||||
}
|
||||
output += blen;
|
||||
len -= blen;
|
||||
len -= blen;
|
||||
}
|
||||
return 1;
|
||||
#elif defined(USE_CRYPTO_MBEDTLS)
|
||||
@@ -702,7 +692,7 @@ int rand_bytes(uint8_t *output, int len)
|
||||
// XXX: ctr_drbg_context changed, [if defined(MBEDTLS_THREADING_C) mbedtls_threading_mutex_t mutex;]
|
||||
static mbedtls_ctr_drbg_context cd_ctx = {};
|
||||
static unsigned char rand_initialised = 0;
|
||||
const size_t blen = min(len, MBEDTLS_CTR_DRBG_MAX_REQUEST);
|
||||
const size_t blen = min(len, MBEDTLS_CTR_DRBG_MAX_REQUEST);
|
||||
|
||||
if (!rand_initialised) {
|
||||
#ifdef _WIN32
|
||||
@@ -754,7 +744,7 @@ int rand_bytes(uint8_t *output, int len)
|
||||
return 0;
|
||||
}
|
||||
output += blen;
|
||||
len -= blen;
|
||||
len -= blen;
|
||||
}
|
||||
return 1;
|
||||
#endif
|
||||
@@ -829,23 +819,23 @@ void cipher_context_init(cipher_ctx_t *ctx, int method, int enc)
|
||||
#if defined(USE_CRYPTO_APPLECC)
|
||||
cipher_cc_t *cc = &ctx->cc;
|
||||
cc->cryptor = NULL;
|
||||
cc->cipher = supported_ciphers_applecc[method];
|
||||
cc->cipher = supported_ciphers_applecc[method];
|
||||
if (cc->cipher == kCCAlgorithmInvalid) {
|
||||
cc->valid = kCCContextInvalid;
|
||||
} else {
|
||||
cc->valid = kCCContextValid;
|
||||
if (cc->cipher == kCCAlgorithmRC4) {
|
||||
cc->mode = kCCModeRC4;
|
||||
cc->mode = kCCModeRC4;
|
||||
cc->padding = ccNoPadding;
|
||||
} else {
|
||||
cc->mode = kCCModeCFB;
|
||||
cc->mode = kCCModeCFB;
|
||||
cc->padding = ccPKCS7Padding;
|
||||
}
|
||||
return;
|
||||
}
|
||||
#endif
|
||||
|
||||
cipher_evp_t *evp = &ctx->evp;
|
||||
cipher_evp_t *evp = &ctx->evp;
|
||||
const cipher_kt_t *cipher = get_cipher_type(method);
|
||||
#if defined(USE_CRYPTO_OPENSSL)
|
||||
if (cipher == NULL) {
|
||||
@@ -912,7 +902,7 @@ void cipher_context_set_iv(cipher_ctx_t *ctx, uint8_t *iv, size_t iv_len,
|
||||
memcpy(key_iv, enc_key, 16);
|
||||
memcpy(key_iv + 16, iv, 16);
|
||||
true_key = enc_md5(key_iv, 32, NULL);
|
||||
iv_len = 0;
|
||||
iv_len = 0;
|
||||
} else {
|
||||
true_key = enc_key;
|
||||
}
|
||||
@@ -922,7 +912,7 @@ void cipher_context_set_iv(cipher_ctx_t *ctx, uint8_t *iv, size_t iv_len,
|
||||
if (cc->valid == kCCContextValid) {
|
||||
memcpy(cc->iv, iv, iv_len);
|
||||
memcpy(cc->key, true_key, enc_key_len);
|
||||
cc->iv_len = iv_len;
|
||||
cc->iv_len = iv_len;
|
||||
cc->key_len = enc_key_len;
|
||||
cc->encrypt = enc ? kCCEncrypt : kCCDecrypt;
|
||||
if (cc->cryptor != NULL) {
|
||||
@@ -1023,10 +1013,10 @@ void cipher_context_release(cipher_ctx_t *ctx)
|
||||
#if defined(USE_CRYPTO_OPENSSL)
|
||||
EVP_CIPHER_CTX_cleanup(evp);
|
||||
#elif defined(USE_CRYPTO_POLARSSL)
|
||||
//NOTE: cipher_free_ctx deprecated in PolarSSL 1.3.11
|
||||
// NOTE: cipher_free_ctx deprecated in PolarSSL 1.3.11
|
||||
cipher_free_ctx(evp);
|
||||
#elif defined(USE_CRYPTO_MBEDTLS)
|
||||
//NOTE: cipher_free_ctx deprecated
|
||||
// NOTE: cipher_free_ctx deprecated
|
||||
mbedtls_cipher_free(evp);
|
||||
#endif
|
||||
}
|
||||
@@ -1086,14 +1076,15 @@ int ss_onetimeauth_verify(buffer_t *buf, uint8_t *iv)
|
||||
uint8_t auth_key[MAX_IV_LENGTH + MAX_KEY_LENGTH];
|
||||
memcpy(auth_key, iv, enc_iv_len);
|
||||
memcpy(auth_key + enc_iv_len, enc_key, enc_key_len);
|
||||
size_t len = buf->len - ONETIMEAUTH_BYTES;
|
||||
|
||||
#if defined(USE_CRYPTO_OPENSSL)
|
||||
HMAC(EVP_sha1(), auth_key, enc_iv_len + enc_key_len, (uint8_t *)buf->array, buf->len, hash, NULL);
|
||||
HMAC(EVP_sha1(), auth_key, enc_iv_len + enc_key_len, (uint8_t *)buf->array, len, hash, NULL);
|
||||
#else
|
||||
ss_sha1_hmac(auth_key, enc_iv_len + enc_key_len, (uint8_t *)buf->array, buf->len, hash);
|
||||
ss_sha1_hmac(auth_key, enc_iv_len + enc_key_len, (uint8_t *)buf->array, len, hash);
|
||||
#endif
|
||||
|
||||
return memcmp(buf->array + buf->len - ONETIMEAUTH_BYTES, hash, ONETIMEAUTH_BYTES);
|
||||
return memcmp(buf->array + len, hash, ONETIMEAUTH_BYTES);
|
||||
}
|
||||
|
||||
int ss_encrypt_all(buffer_t *plain, int method, int auth)
|
||||
@@ -1102,34 +1093,34 @@ int ss_encrypt_all(buffer_t *plain, int method, int auth)
|
||||
cipher_ctx_t evp;
|
||||
cipher_context_init(&evp, method, 1);
|
||||
|
||||
size_t p_len = plain->len, c_len = plain->len;
|
||||
size_t iv_len = enc_iv_len;
|
||||
int err = 1;
|
||||
int err = 1;
|
||||
|
||||
static buffer_t tmp = {0};
|
||||
brealloc(&tmp, iv_len + c_len, plain->capacity);
|
||||
static buffer_t tmp = { 0 };
|
||||
brealloc(&tmp, iv_len + plain->len, plain->capacity);
|
||||
buffer_t *cipher = &tmp;
|
||||
cipher->len = plain->len;
|
||||
|
||||
uint8_t iv[MAX_IV_LENGTH];
|
||||
|
||||
rand_bytes(iv, iv_len);
|
||||
cipher_context_set_iv(&evp, iv, iv_len, 1);
|
||||
memcpy(cipher, iv, iv_len);
|
||||
memcpy(cipher->array, iv, iv_len);
|
||||
|
||||
if (auth) {
|
||||
ss_onetimeauth(plain, iv);
|
||||
p_len = c_len = p_len + ONETIMEAUTH_BYTES;
|
||||
cipher->len = plain->len;
|
||||
}
|
||||
|
||||
if (method >= SALSA20) {
|
||||
crypto_stream_xor_ic((uint8_t *)(cipher + iv_len),
|
||||
(const uint8_t *)plain->array, (uint64_t)(p_len),
|
||||
crypto_stream_xor_ic((uint8_t *)(cipher->array + iv_len),
|
||||
(const uint8_t *)plain->array, (uint64_t)(plain->len),
|
||||
(const uint8_t *)iv,
|
||||
0, enc_key, method);
|
||||
} else {
|
||||
err = cipher_context_update(&evp, (uint8_t *)(cipher + iv_len),
|
||||
&c_len, (const uint8_t *)plain->array,
|
||||
p_len);
|
||||
err = cipher_context_update(&evp, (uint8_t *)(cipher->array + iv_len),
|
||||
&cipher->len, (const uint8_t *)plain->array,
|
||||
plain->len);
|
||||
}
|
||||
|
||||
if (!err) {
|
||||
@@ -1139,20 +1130,20 @@ int ss_encrypt_all(buffer_t *plain, int method, int auth)
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
dump("PLAIN", plain->array, *len);
|
||||
dump("CIPHER", cipher->array + iv_len, c_len);
|
||||
dump("PLAIN", plain->array, plain->len);
|
||||
dump("CIPHER", cipher->array + iv_len, cipher->len);
|
||||
#endif
|
||||
|
||||
cipher_context_release(&evp);
|
||||
|
||||
brealloc(plain, iv_len + c_len, plain->capacity);
|
||||
memcpy(plain, cipher, iv_len + c_len);
|
||||
plain->len = iv_len + c_len;
|
||||
brealloc(plain, iv_len + cipher->len, plain->capacity);
|
||||
memcpy(plain->array, cipher->array, iv_len + cipher->len);
|
||||
plain->len = iv_len + cipher->len;
|
||||
|
||||
return 0;
|
||||
} else {
|
||||
char *begin = plain->array;
|
||||
char *ptr = plain->array;
|
||||
char *ptr = plain->array;
|
||||
while (ptr < begin + plain->len) {
|
||||
*ptr = (char)enc_table[(uint8_t)*ptr];
|
||||
ptr++;
|
||||
@@ -1164,69 +1155,68 @@ int ss_encrypt_all(buffer_t *plain, int method, int auth)
|
||||
int ss_encrypt(buffer_t *plain, enc_ctx_t *ctx)
|
||||
{
|
||||
if (ctx != NULL) {
|
||||
static buffer_t tmp = {0};
|
||||
static buffer_t tmp = { 0 };
|
||||
|
||||
int err = 1;
|
||||
int err = 1;
|
||||
size_t iv_len = 0;
|
||||
size_t p_len = plain->len, c_len = plain->len;
|
||||
if (!ctx->init) {
|
||||
iv_len = enc_iv_len;
|
||||
}
|
||||
|
||||
brealloc(&tmp, iv_len + c_len, plain->capacity);
|
||||
|
||||
brealloc(&tmp, iv_len + plain->len, plain->capacity);
|
||||
buffer_t *cipher = &tmp;
|
||||
cipher->len = plain->len;
|
||||
|
||||
if (!ctx->init) {
|
||||
cipher_context_set_iv(&ctx->evp, ctx->evp.iv, iv_len, 1);
|
||||
memcpy(cipher->array, ctx->evp.iv, iv_len);
|
||||
ctx->counter = 0;
|
||||
ctx->init = 1;
|
||||
ctx->init = 1;
|
||||
}
|
||||
|
||||
if (enc_method >= SALSA20) {
|
||||
int padding = ctx->counter % SODIUM_BLOCK_SIZE;
|
||||
brealloc(cipher, iv_len + (padding + c_len) * 2, cipher->capacity);
|
||||
brealloc(cipher, iv_len + (padding + cipher->len) * 2, cipher->capacity);
|
||||
if (padding) {
|
||||
brealloc(plain, p_len + padding, plain->capacity);
|
||||
memmove(plain->array + padding, plain->array, p_len);
|
||||
brealloc(plain, plain->len + padding, plain->capacity);
|
||||
memmove(plain->array + padding, plain->array, plain->len);
|
||||
memset(plain->array, 0, padding);
|
||||
}
|
||||
crypto_stream_xor_ic((uint8_t *)(cipher->array + iv_len),
|
||||
(const uint8_t *)plain->array,
|
||||
(uint64_t)(p_len + padding),
|
||||
(uint64_t)(plain->len + padding),
|
||||
(const uint8_t *)ctx->evp.iv,
|
||||
ctx->counter / SODIUM_BLOCK_SIZE, enc_key,
|
||||
enc_method);
|
||||
ctx->counter += p_len;
|
||||
ctx->counter += plain->len;
|
||||
if (padding) {
|
||||
memmove(cipher->array + iv_len,
|
||||
cipher->array + iv_len + padding, c_len);
|
||||
cipher->array + iv_len + padding, cipher->len);
|
||||
}
|
||||
} else {
|
||||
err =
|
||||
cipher_context_update(&ctx->evp,
|
||||
(uint8_t *)(cipher->array + iv_len),
|
||||
&c_len, (const uint8_t *)plain->array,
|
||||
p_len);
|
||||
&cipher->len, (const uint8_t *)plain->array,
|
||||
plain->len);
|
||||
if (!err) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
dump("PLAIN", plain->array, p_len);
|
||||
dump("CIPHER", cipher->array + iv_len, c_len);
|
||||
dump("PLAIN", plain->array, plain->len);
|
||||
dump("CIPHER", cipher->array + iv_len, cipher->len);
|
||||
#endif
|
||||
|
||||
brealloc(plain, iv_len + c_len, plain->capacity);
|
||||
memcpy(plain->array, cipher->array, iv_len + c_len);
|
||||
plain->len = iv_len + c_len;
|
||||
brealloc(plain, iv_len + cipher->len, plain->capacity);
|
||||
memcpy(plain->array, cipher->array, iv_len + cipher->len);
|
||||
plain->len = iv_len + cipher->len;
|
||||
|
||||
return 0;
|
||||
} else {
|
||||
char *begin = plain->array;
|
||||
char *ptr = plain->array;
|
||||
char *ptr = plain->array;
|
||||
while (ptr < begin + plain->len) {
|
||||
*ptr = (char)enc_table[(uint8_t)*ptr];
|
||||
ptr++;
|
||||
@@ -1239,41 +1229,40 @@ int ss_decrypt_all(buffer_t *cipher, int method, int auth)
|
||||
{
|
||||
if (method > TABLE) {
|
||||
size_t iv_len = enc_iv_len;
|
||||
size_t c_len = cipher->len;
|
||||
size_t p_len = cipher->len - iv_len;
|
||||
int ret = 1;
|
||||
int ret = 1;
|
||||
|
||||
if (c_len <= iv_len) {
|
||||
if (cipher->len <= iv_len) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
cipher_ctx_t evp;
|
||||
cipher_context_init(&evp, method, 0);
|
||||
|
||||
static buffer_t tmp = {0};
|
||||
static buffer_t tmp = { 0 };
|
||||
brealloc(&tmp, cipher->len, cipher->capacity);
|
||||
buffer_t *plain = &tmp;
|
||||
plain->len = cipher->len;
|
||||
|
||||
uint8_t iv[MAX_IV_LENGTH];
|
||||
memcpy(iv, cipher, iv_len);
|
||||
memcpy(iv, cipher->array, iv_len);
|
||||
cipher_context_set_iv(&evp, iv, iv_len, 0);
|
||||
|
||||
if (method >= SALSA20) {
|
||||
crypto_stream_xor_ic((uint8_t *)plain->array,
|
||||
(const uint8_t *)(cipher->array + iv_len),
|
||||
(uint64_t)(c_len - iv_len),
|
||||
(uint64_t)(cipher->len - iv_len),
|
||||
(const uint8_t *)iv, 0, enc_key, method);
|
||||
} else {
|
||||
ret = cipher_context_update(&evp, (uint8_t *)plain->array, &p_len,
|
||||
ret = cipher_context_update(&evp, (uint8_t *)plain->array, &plain->len,
|
||||
(const uint8_t *)(cipher->array + iv_len),
|
||||
c_len - iv_len);
|
||||
cipher->len - iv_len);
|
||||
}
|
||||
|
||||
if (auth || (plain->array[0] & ONETIMEAUTH_FLAG)) {
|
||||
if (p_len > ONETIMEAUTH_BYTES) {
|
||||
if (plain->len > ONETIMEAUTH_BYTES) {
|
||||
ret = !ss_onetimeauth_verify(plain, iv);
|
||||
if (ret) {
|
||||
p_len -= ONETIMEAUTH_BYTES;
|
||||
plain->len -= ONETIMEAUTH_BYTES;
|
||||
}
|
||||
} else {
|
||||
ret = 0;
|
||||
@@ -1287,20 +1276,20 @@ int ss_decrypt_all(buffer_t *cipher, int method, int auth)
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
dump("PLAIN", plain->array, p_len);
|
||||
dump("CIPHER", cipher->array + iv_len, c_len - iv_len);
|
||||
dump("PLAIN", plain->array, plain->len);
|
||||
dump("CIPHER", cipher->array + iv_len, cipher->len - iv_len);
|
||||
#endif
|
||||
|
||||
cipher_context_release(&evp);
|
||||
|
||||
brealloc(cipher, p_len, plain->capacity);
|
||||
memcpy(cipher, plain, p_len);
|
||||
cipher->len = p_len;
|
||||
brealloc(cipher, plain->len, plain->capacity);
|
||||
memcpy(cipher->array, plain->array, plain->len);
|
||||
cipher->len = plain->len;
|
||||
|
||||
return 0;
|
||||
} else {
|
||||
char *begin = cipher->array;
|
||||
char *ptr = cipher->array;
|
||||
char *ptr = cipher->array;
|
||||
while (ptr < begin + cipher->len) {
|
||||
*ptr = (char)dec_table[(uint8_t)*ptr];
|
||||
ptr++;
|
||||
@@ -1312,25 +1301,24 @@ int ss_decrypt_all(buffer_t *cipher, int method, int auth)
|
||||
int ss_decrypt(buffer_t *cipher, enc_ctx_t *ctx)
|
||||
{
|
||||
if (ctx != NULL) {
|
||||
static buffer_t tmp = {0};
|
||||
static buffer_t tmp = { 0 };
|
||||
|
||||
size_t c_len = cipher->len;
|
||||
size_t p_len = cipher->len;
|
||||
size_t iv_len = 0;
|
||||
int err = 1;
|
||||
int err = 1;
|
||||
|
||||
brealloc(&tmp, p_len, cipher->capacity);
|
||||
brealloc(&tmp, cipher->len, cipher->capacity);
|
||||
buffer_t *plain = &tmp;
|
||||
plain->len = cipher->len;
|
||||
|
||||
if (!ctx->init) {
|
||||
uint8_t iv[MAX_IV_LENGTH];
|
||||
iv_len = enc_iv_len;
|
||||
p_len -= iv_len;
|
||||
iv_len = enc_iv_len;
|
||||
plain->len -= iv_len;
|
||||
|
||||
memcpy(iv, cipher->array, iv_len);
|
||||
cipher_context_set_iv(&ctx->evp, iv, iv_len, 0);
|
||||
ctx->counter = 0;
|
||||
ctx->init = 1;
|
||||
ctx->init = 1;
|
||||
|
||||
if (enc_method >= RC4_MD5) {
|
||||
if (cache_key_exist(iv_cache, (char *)iv, iv_len)) {
|
||||
@@ -1344,28 +1332,28 @@ int ss_decrypt(buffer_t *cipher, enc_ctx_t *ctx)
|
||||
|
||||
if (enc_method >= SALSA20) {
|
||||
int padding = ctx->counter % SODIUM_BLOCK_SIZE;
|
||||
brealloc(plain, (p_len + padding) * 2, plain->capacity);
|
||||
brealloc(plain, (plain->len + padding) * 2, plain->capacity);
|
||||
|
||||
if (padding) {
|
||||
brealloc(cipher, c_len + padding, cipher->capacity);
|
||||
brealloc(cipher, cipher->len + padding, cipher->capacity);
|
||||
memmove(cipher->array + iv_len + padding, cipher->array + iv_len,
|
||||
c_len - iv_len);
|
||||
cipher->len - iv_len);
|
||||
memset(cipher->array + iv_len, 0, padding);
|
||||
}
|
||||
crypto_stream_xor_ic((uint8_t *)plain->array,
|
||||
(const uint8_t *)(cipher->array + iv_len),
|
||||
(uint64_t)(c_len - iv_len + padding),
|
||||
(uint64_t)(cipher->len - iv_len + padding),
|
||||
(const uint8_t *)ctx->evp.iv,
|
||||
ctx->counter / SODIUM_BLOCK_SIZE, enc_key,
|
||||
enc_method);
|
||||
ctx->counter += c_len - iv_len;
|
||||
ctx->counter += cipher->len - iv_len;
|
||||
if (padding) {
|
||||
memmove(plain->array, plain->array + padding, p_len);
|
||||
memmove(plain->array, plain->array + padding, plain->len);
|
||||
}
|
||||
} else {
|
||||
err = cipher_context_update(&ctx->evp, (uint8_t *)plain->array, &p_len,
|
||||
(const uint8_t *)(cipher + iv_len),
|
||||
c_len - iv_len);
|
||||
err = cipher_context_update(&ctx->evp, (uint8_t *)plain->array, &plain->len,
|
||||
(const uint8_t *)(cipher->array + iv_len),
|
||||
cipher->len - iv_len);
|
||||
}
|
||||
|
||||
if (!err) {
|
||||
@@ -1374,18 +1362,18 @@ int ss_decrypt(buffer_t *cipher, enc_ctx_t *ctx)
|
||||
}
|
||||
|
||||
#ifdef DEBUG
|
||||
dump("PLAIN", plain->array, p_len);
|
||||
dump("CIPHER", cipher->array + iv_len, c_len - iv_len);
|
||||
dump("PLAIN", plain->array, plain->len);
|
||||
dump("CIPHER", cipher->array + iv_len, cipher->len - iv_len);
|
||||
#endif
|
||||
|
||||
brealloc(cipher, p_len, cipher->capacity);
|
||||
memcpy(cipher->array, plain->array, p_len);
|
||||
cipher->len = p_len;
|
||||
brealloc(cipher, plain->len, cipher->capacity);
|
||||
memcpy(cipher->array, plain->array, plain->len);
|
||||
cipher->len = plain->len;
|
||||
|
||||
return 0;
|
||||
} else {
|
||||
char *begin = cipher->array;
|
||||
char *ptr = cipher->array;
|
||||
char *ptr = cipher->array;
|
||||
while (ptr < begin + cipher->len) {
|
||||
*ptr = (char)dec_table[(uint8_t)*ptr];
|
||||
ptr++;
|
||||
@@ -1431,18 +1419,18 @@ void enc_key_init(int method, const char *pass)
|
||||
cipher = (cipher_kt_t *)&cipher_info;
|
||||
#if defined(USE_CRYPTO_OPENSSL)
|
||||
cipher->key_len = supported_ciphers_key_size[method];
|
||||
cipher->iv_len = supported_ciphers_iv_size[method];
|
||||
cipher->iv_len = supported_ciphers_iv_size[method];
|
||||
#endif
|
||||
#if defined(USE_CRYPTO_POLARSSL)
|
||||
cipher->base = NULL;
|
||||
cipher->base = NULL;
|
||||
cipher->key_length = supported_ciphers_key_size[method] * 8;
|
||||
cipher->iv_size = supported_ciphers_iv_size[method];
|
||||
cipher->iv_size = supported_ciphers_iv_size[method];
|
||||
#endif
|
||||
#if defined(USE_CRYPTO_MBEDTLS)
|
||||
// XXX: key_length changed to key_bitlen in mbed TLS 2.0.0
|
||||
cipher->base = NULL;
|
||||
cipher->base = NULL;
|
||||
cipher->key_bitlen = supported_ciphers_key_size[method] * 8;
|
||||
cipher->iv_size = supported_ciphers_iv_size[method];
|
||||
cipher->iv_size = supported_ciphers_iv_size[method];
|
||||
#endif
|
||||
} else {
|
||||
cipher = (cipher_kt_t *)get_cipher_type(method);
|
||||
@@ -1452,20 +1440,20 @@ void enc_key_init(int method, const char *pass)
|
||||
do {
|
||||
#if defined(USE_CRYPTO_POLARSSL) && defined(USE_CRYPTO_APPLECC)
|
||||
if (supported_ciphers_applecc[method] != kCCAlgorithmInvalid) {
|
||||
cipher_info.base = NULL;
|
||||
cipher_info.base = NULL;
|
||||
cipher_info.key_length = supported_ciphers_key_size[method] * 8;
|
||||
cipher_info.iv_size = supported_ciphers_iv_size[method];
|
||||
cipher = (cipher_kt_t *)&cipher_info;
|
||||
cipher_info.iv_size = supported_ciphers_iv_size[method];
|
||||
cipher = (cipher_kt_t *)&cipher_info;
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
#if defined(USE_CRYPTO_MBEDTLS) && defined(USE_CRYPTO_APPLECC)
|
||||
// XXX: key_length changed to key_bitlen in mbed TLS 2.0.0
|
||||
if (supported_ciphers_applecc[method] != kCCAlgorithmInvalid) {
|
||||
cipher_info.base = NULL;
|
||||
cipher_info.base = NULL;
|
||||
cipher_info.key_bitlen = supported_ciphers_key_size[method] * 8;
|
||||
cipher_info.iv_size = supported_ciphers_iv_size[method];
|
||||
cipher = (cipher_kt_t *)&cipher_info;
|
||||
cipher_info.iv_size = supported_ciphers_iv_size[method];
|
||||
cipher = (cipher_kt_t *)&cipher_info;
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
@@ -1496,11 +1484,10 @@ int enc_init(const char *pass, const char *method)
|
||||
{
|
||||
int m = TABLE;
|
||||
if (method != NULL) {
|
||||
for (m = TABLE; m < CIPHER_NUM; m++) {
|
||||
for (m = TABLE; m < CIPHER_NUM; m++)
|
||||
if (strcmp(method, supported_ciphers[m]) == 0) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (m >= CIPHER_NUM) {
|
||||
LOGE("Invalid cipher name: %s, use table instead", method);
|
||||
m = TABLE;
|
||||
@@ -1517,14 +1504,13 @@ int enc_init(const char *pass, const char *method)
|
||||
int ss_check_hash(buffer_t *buf, chunk_t *chunk, enc_ctx_t *ctx)
|
||||
{
|
||||
int i, j, k;
|
||||
ssize_t blen = buf->len;
|
||||
ssize_t blen = buf->len;
|
||||
uint32_t cidx = chunk->idx;
|
||||
|
||||
brealloc(chunk->buf, blen, buf->capacity);
|
||||
brealloc(chunk->buf, chunk->len + blen, buf->capacity);
|
||||
brealloc(buf, chunk->len + blen, buf->capacity);
|
||||
|
||||
for (i = 0, j = 0, k = 0; i < blen; i++) {
|
||||
|
||||
chunk->buf->array[cidx++] = buf->array[k++];
|
||||
|
||||
if (cidx == CLEN_BYTES) {
|
||||
@@ -1558,21 +1544,21 @@ int ss_check_hash(buffer_t *buf, chunk_t *chunk, enc_ctx_t *ctx)
|
||||
memcpy(buf->array + j, chunk->buf->array + AUTH_BYTES, chunk->len);
|
||||
|
||||
// Reset the base offset
|
||||
j += chunk->len;
|
||||
k = j;
|
||||
j += chunk->len;
|
||||
k = j;
|
||||
cidx = 0;
|
||||
chunk->counter++;
|
||||
}
|
||||
}
|
||||
|
||||
buf->len = j;
|
||||
buf->len = j;
|
||||
chunk->idx = cidx;
|
||||
return 1;
|
||||
}
|
||||
|
||||
int ss_gen_hash(buffer_t *buf, uint32_t *counter, enc_ctx_t *ctx)
|
||||
{
|
||||
ssize_t blen = buf->len;
|
||||
ssize_t blen = buf->len;
|
||||
uint16_t chunk_len = htons((uint16_t)blen);
|
||||
uint8_t hash[ONETIMEAUTH_BYTES * 2];
|
||||
uint8_t key[MAX_IV_LENGTH + sizeof(uint32_t)];
|
||||
|
||||
Reference in New Issue
Block a user