From aec9415e448bb71d2f4b8507c6525a493431004c Mon Sep 17 00:00:00 2001 From: Ludvig Strigeus Date: Mon, 10 Dec 2018 23:13:13 +0100 Subject: [PATCH] Add chacha20_streaming_init api for use by tcp obfuscator --- crypto/chacha20poly1305.cpp | 29 +++++++++++++++++++++++++++++ crypto/chacha20poly1305.h | 12 +++++++++++- 2 files changed, 40 insertions(+), 1 deletion(-) diff --git a/crypto/chacha20poly1305.cpp b/crypto/chacha20poly1305.cpp index 7287aca..5095b46 100644 --- a/crypto/chacha20poly1305.cpp +++ b/crypto/chacha20poly1305.cpp @@ -13,6 +13,7 @@ #include "crypto_ops.h" #include #include +#include "util.h" enum { CHACHA20_IV_SIZE = 16, @@ -631,3 +632,31 @@ bool xchacha20poly1305_decrypt(uint8 *dst, const uint8 *src, const size_t src_le return ret; } +void chacha20_streaming_init(chacha20_streaming *state, uint8 key[CHACHA20POLY1305_KEYLEN]) { + state->left = 0; + uint32 *st = state->state; + WriteLE64((uint8*)st, 0x3320646e61707865); + WriteLE64((uint8*)st + 8, 0x6b20657479622d32); + Write64((uint8*)st + 16, Read64(key + 0)); + Write64((uint8*)st + 24, Read64(key + 8)); + Write64((uint8*)st + 32, Read64(key + 16)); + Write64((uint8*)st + 40, Read64(key + 24)); + Write64((uint8*)st + 48, 0); + Write64((uint8*)st + 56, 0); +} + +void chacha20_streaming_crypt(chacha20_streaming *state, uint8 *dst, size_t size) { + uint32 left = state->left; + while (size) { + if (left == 0) { + memset(state->buf, 0, sizeof(state->buf)); + chacha20_crypt((struct chacha20_ctx *)state->state, state->buf, state->buf, sizeof(state->buf)); + left = 64; + } + size_t step = left > size ? size : left; + crypto_xor(postinc(dst, step), state->buf + 64 - exch(left, left - (uint32)step), exch(size, size - step)); + } + state->left = left; +} + + diff --git a/crypto/chacha20poly1305.h b/crypto/chacha20poly1305.h index 90b701d..2bbaddb 100644 --- a/crypto/chacha20poly1305.h +++ b/crypto/chacha20poly1305.h @@ -36,4 +36,14 @@ bool xchacha20poly1305_decrypt(uint8 *dst, const uint8 *src, const size_t src_le void poly1305_get_mac(const uint8 *src, size_t src_len, const uint8 *ad, const size_t ad_len, const uint64 nonce, const uint8 key[CHACHA20POLY1305_KEYLEN], - uint8 mac[CHACHA20POLY1305_AUTHTAGLEN]); \ No newline at end of file + uint8 mac[CHACHA20POLY1305_AUTHTAGLEN]); + + +struct chacha20_streaming { + uint32 left; + uint8 buf[64]; + uint32 state[16]; +}; + +void chacha20_streaming_init(chacha20_streaming *state, uint8 key[CHACHA20POLY1305_KEYLEN]); +void chacha20_streaming_crypt(chacha20_streaming *state, uint8 *dst, size_t size);