+2021-09-08 Niels Möller <nisse@lysator.liu.se>
+
+ * cbc-aes128-encrypt.c (nettle_cbc_aes128_encrypt): New file and
+ function.
+ * cbc-aes192-encrypt.c (cbc_aes192_set_encrypt_key): New file.
+ * cbc-aes256-encrypt.c (cbc_aes256_set_encrypt_key): New file.
+ * cbc.h (cbc_aes128_ctx, struct cbc_aes192_ctx, cbc_aes256_ctx):
+ New context structs. Declare new functions.
+ * Makefile.in (nettle_SOURCES): Add new files.
+ * nettle-internal.c (nettle_cbc_aes128, nettle_cbc_aes192)
+ (nettle_cbc_aes256): New algorithm structs, for tests and
+ benchmarking.
+ * testsuite/testutils.c (test_aead): Skip tests of decryption and
+ authentication, if corresponding function pointers are NULL.
+ * testsuite/cbc-test.c (test_main): Add tests of new cbc
+ functions.
+ * examples/nettle-benchmark.c (time_aead): Skip decrypt benchmark,
+ if corresponding function pointer is NULL.
+
2021-08-16 Niels Möller <nisse@lysator.liu.se>
S390x functions for sha1, sha256 and sha512, from Mamone Tarsha:
camellia256-set-encrypt-key.c camellia256-crypt.c \
camellia256-set-decrypt-key.c \
camellia256-meta.c \
- cast128.c cast128-meta.c cbc.c \
+ cast128.c cast128-meta.c \
+ cbc.c cbc-aes128-encrypt.c cbc-aes192-encrypt.c cbc-aes256-encrypt.c \
ccm.c ccm-aes128.c ccm-aes192.c ccm-aes256.c cfb.c \
siv-cmac.c siv-cmac-aes128.c siv-cmac-aes256.c \
cnd-memcpy.c \
--- /dev/null
+/* cbc-aes128-encrypt.c
+
+ Copyright (C) 2021 Niels Möller
+
+ This file is part of GNU Nettle.
+
+ GNU Nettle is free software: you can redistribute it and/or
+ modify it under the terms of either:
+
+ * the GNU Lesser General Public License as published by the Free
+ Software Foundation; either version 3 of the License, or (at your
+ option) any later version.
+
+ or
+
+ * the GNU General Public License as published by the Free
+ Software Foundation; either version 2 of the License, or (at your
+ option) any later version.
+
+ or both in parallel, as here.
+
+ GNU Nettle is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received copies of the GNU General Public License and
+ the GNU Lesser General Public License along with this program. If
+ not, see http://www.gnu.org/licenses/.
+*/
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include "cbc.h"
+
+void
+cbc_aes128_encrypt(struct cbc_aes128_ctx *ctx, size_t length, uint8_t *dst, const uint8_t *src)
+{
+ CBC_ENCRYPT(ctx, aes128_encrypt, length, dst, src);
+}
--- /dev/null
+/* cbc-aes192-encrypt.c
+
+ Copyright (C) 2021 Niels Möller
+
+ This file is part of GNU Nettle.
+
+ GNU Nettle is free software: you can redistribute it and/or
+ modify it under the terms of either:
+
+ * the GNU Lesser General Public License as published by the Free
+ Software Foundation; either version 3 of the License, or (at your
+ option) any later version.
+
+ or
+
+ * the GNU General Public License as published by the Free
+ Software Foundation; either version 2 of the License, or (at your
+ option) any later version.
+
+ or both in parallel, as here.
+
+ GNU Nettle is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received copies of the GNU General Public License and
+ the GNU Lesser General Public License along with this program. If
+ not, see http://www.gnu.org/licenses/.
+*/
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include "cbc.h"
+
+void
+cbc_aes192_encrypt(struct cbc_aes192_ctx *ctx, size_t length, uint8_t *dst, const uint8_t *src)
+{
+ CBC_ENCRYPT(ctx, aes192_encrypt, length, dst, src);
+}
--- /dev/null
+/* cbc-aes256-encrypt.c
+
+ Copyright (C) 2021 Niels Möller
+
+ This file is part of GNU Nettle.
+
+ GNU Nettle is free software: you can redistribute it and/or
+ modify it under the terms of either:
+
+ * the GNU Lesser General Public License as published by the Free
+ Software Foundation; either version 3 of the License, or (at your
+ option) any later version.
+
+ or
+
+ * the GNU General Public License as published by the Free
+ Software Foundation; either version 2 of the License, or (at your
+ option) any later version.
+
+ or both in parallel, as here.
+
+ GNU Nettle is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received copies of the GNU General Public License and
+ the GNU Lesser General Public License along with this program. If
+ not, see http://www.gnu.org/licenses/.
+*/
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include "cbc.h"
+
+void
+cbc_aes256_encrypt(struct cbc_aes256_ctx *ctx, size_t length, uint8_t *dst, const uint8_t *src)
+{
+ CBC_ENCRYPT(ctx, aes256_encrypt, length, dst, src);
+}
#define NETTLE_CBC_H_INCLUDED
#include "nettle-types.h"
+#include "aes.h"
#ifdef __cplusplus
extern "C" {
/* Name mangling */
#define cbc_encrypt nettle_cbc_encrypt
#define cbc_decrypt nettle_cbc_decrypt
+#define cbc_aes128_encrypt nettle_cbc_aes128_encrypt
+#define cbc_aes192_encrypt nettle_cbc_aes192_encrypt
+#define cbc_aes256_encrypt nettle_cbc_aes256_encrypt
void
cbc_encrypt(const void *ctx, nettle_cipher_func *f,
sizeof((self)->iv), (self)->iv, \
(length), (dst), (src)))
+struct cbc_aes128_ctx CBC_CTX(struct aes128_ctx, AES_BLOCK_SIZE);
+void
+cbc_aes128_encrypt(struct cbc_aes128_ctx *ctx, size_t length, uint8_t *dst, const uint8_t *src);
+
+struct cbc_aes192_ctx CBC_CTX(struct aes192_ctx, AES_BLOCK_SIZE);
+void
+cbc_aes192_encrypt(struct cbc_aes192_ctx *ctx, size_t length, uint8_t *dst, const uint8_t *src);
+
+struct cbc_aes256_ctx CBC_CTX(struct aes256_ctx, AES_BLOCK_SIZE);
+void
+cbc_aes256_encrypt(struct cbc_aes256_ctx *ctx, size_t length, uint8_t *dst, const uint8_t *src);
+
#ifdef __cplusplus
}
#endif
display(aead->name, "encrypt", aead->block_size,
time_function(bench_aead_crypt, &info));
}
-
- {
- struct bench_aead_info info;
- info.ctx = ctx;
- info.crypt = aead->decrypt;
- info.data = data;
+
+ if (aead->decrypt)
+ {
+ struct bench_aead_info info;
+ info.ctx = ctx;
+ info.crypt = aead->decrypt;
+ info.data = data;
- init_key(aead->key_size, key);
- aead->set_decrypt_key(ctx, key);
- if (aead->set_nonce)
- aead->set_nonce (ctx, nonce);
+ init_key(aead->key_size, key);
+ aead->set_decrypt_key(ctx, key);
+ if (aead->set_nonce)
+ aead->set_nonce (ctx, nonce);
- display(aead->name, "decrypt", aead->block_size,
- time_function(bench_aead_crypt, &info));
- }
+ display(aead->name, "decrypt", aead->block_size,
+ time_function(bench_aead_crypt, &info));
+ }
if (aead->update)
{
/* Stream ciphers */
&nettle_arcfour128,
&nettle_salsa20, &nettle_salsa20r12, &nettle_chacha,
+ /* CBC encrypt */
+ &nettle_cbc_aes128, &nettle_cbc_aes192, &nettle_cbc_aes256,
/* Proper AEAD algorithme. */
&nettle_gcm_aes128,
&nettle_gcm_aes192,
#include <assert.h>
#include <stdlib.h>
+#include <string.h>
#include "nettle-internal.h"
#include "arcfour.h"
#include "blowfish.h"
-#include "des.h"
+#include "cbc.h"
#include "chacha.h"
+#include "des.h"
#include "salsa20.h"
/* Wrapper functions discarding the return value. Needed for the
(nettle_crypt_func *) salsa20r12_crypt,
NULL,
};
+
+static void
+cbc_aes128_set_encrypt_key(struct cbc_aes128_ctx *ctx, const uint8_t *key)
+{
+ aes128_set_encrypt_key(&ctx->ctx, key);
+}
+static void
+cbc_aes128_set_iv(struct cbc_aes128_ctx *ctx, const uint8_t *iv)
+{
+ CBC_SET_IV(ctx, iv);
+}
+const struct nettle_aead
+nettle_cbc_aes128 = {
+ "cbc_aes128", sizeof(struct cbc_aes128_ctx),
+ AES_BLOCK_SIZE, AES128_KEY_SIZE,
+ AES_BLOCK_SIZE, 0,
+ (nettle_set_key_func*) cbc_aes128_set_encrypt_key,
+ NULL,
+ (nettle_set_key_func*) cbc_aes128_set_iv,
+ NULL,
+ (nettle_crypt_func *) cbc_aes128_encrypt,
+ NULL,
+ NULL,
+};
+
+static void
+cbc_aes192_set_encrypt_key(struct cbc_aes192_ctx *ctx, const uint8_t *key)
+{
+ aes192_set_encrypt_key(&ctx->ctx, key);
+}
+static void
+cbc_aes192_set_iv(struct cbc_aes192_ctx *ctx, const uint8_t *iv)
+{
+ CBC_SET_IV(ctx, iv);
+}
+const struct nettle_aead
+nettle_cbc_aes192 = {
+ "cbc_aes192", sizeof(struct cbc_aes192_ctx),
+ AES_BLOCK_SIZE, AES192_KEY_SIZE,
+ AES_BLOCK_SIZE, 0,
+ (nettle_set_key_func*) cbc_aes192_set_encrypt_key,
+ NULL,
+ (nettle_set_key_func*) cbc_aes192_set_iv,
+ NULL,
+ (nettle_crypt_func *) cbc_aes192_encrypt,
+ NULL,
+ NULL,
+};
+
+static void
+cbc_aes256_set_encrypt_key(struct cbc_aes256_ctx *ctx, const uint8_t *key)
+{
+ aes256_set_encrypt_key(&ctx->ctx, key);
+}
+static void
+cbc_aes256_set_iv(struct cbc_aes256_ctx *ctx, const uint8_t *iv)
+{
+ CBC_SET_IV(ctx, iv);
+}
+const struct nettle_aead
+nettle_cbc_aes256 = {
+ "cbc_aes256", sizeof(struct cbc_aes256_ctx),
+ AES_BLOCK_SIZE, AES256_KEY_SIZE,
+ AES_BLOCK_SIZE, 0,
+ (nettle_set_key_func*) cbc_aes256_set_encrypt_key,
+ NULL,
+ (nettle_set_key_func*) cbc_aes256_set_iv,
+ NULL,
+ (nettle_crypt_func *) cbc_aes256_encrypt,
+ NULL,
+ NULL,
+};
extern const struct nettle_aead nettle_chacha;
extern const struct nettle_aead nettle_salsa20;
extern const struct nettle_aead nettle_salsa20r12;
+
+/* All-in-one CBC encrypt fucntinos treated as AEAD with no
+ authentication and no decrypt method. */
+extern const struct nettle_aead nettle_cbc_aes128;
+extern const struct nettle_aead nettle_cbc_aes192;
+extern const struct nettle_aead nettle_cbc_aes256;
+
extern const struct nettle_aead nettle_openssl_gcm_aes128;
extern const struct nettle_aead nettle_openssl_gcm_aes192;
extern const struct nettle_aead nettle_openssl_gcm_aes256;
+
/* Glue to openssl, for comparative benchmarking. Code in
* examples/nettle-openssl.c. */
extern void nettle_openssl_init(void);
#include "aes.h"
#include "cbc.h"
#include "knuth-lfib.h"
+#include "nettle-internal.h"
/* Test with more data and inplace decryption, to check that the
* cbc_decrypt buffering works. */
"73bed6b8e3c1743b7116e69e22229516"
"3ff1caa1681fac09120eca307586e1a7"),
SHEX("000102030405060708090a0b0c0d0e0f"));
+
+ test_aead(&nettle_cbc_aes128, NULL,
+ SHEX("2b7e151628aed2a6abf7158809cf4f3c"),
+ NULL,
+ SHEX("6bc1bee22e409f96e93d7e117393172a"
+ "ae2d8a571e03ac9c9eb76fac45af8e51"
+ "30c81c46a35ce411e5fbc1191a0a52ef"
+ "f69f2445df4f9b17ad2b417be66c3710"),
+ SHEX("7649abac8119b246cee98e9b12e9197d"
+ "5086cb9b507219ee95db113a917678b2"
+ "73bed6b8e3c1743b7116e69e22229516"
+ "3ff1caa1681fac09120eca307586e1a7"),
+ SHEX("000102030405060708090a0b0c0d0e0f"),
+ NULL);
/* F.2.3 CBC-AES192.Encrypt */
"571b242012fb7ae07fa9baac3df102e0"
"08b0e27988598881d920a9e64f5615cd"),
SHEX("000102030405060708090a0b0c0d0e0f"));
+
+ test_aead(&nettle_cbc_aes192, NULL,
+ SHEX("8e73b0f7da0e6452c810f32b809079e5"
+ "62f8ead2522c6b7b"),
+ NULL,
+ SHEX("6bc1bee22e409f96e93d7e117393172a"
+ "ae2d8a571e03ac9c9eb76fac45af8e51"
+ "30c81c46a35ce411e5fbc1191a0a52ef"
+ "f69f2445df4f9b17ad2b417be66c3710"),
+ SHEX("4f021db243bc633d7178183a9fa071e8"
+ "b4d9ada9ad7dedf4e5e738763f69145a"
+ "571b242012fb7ae07fa9baac3df102e0"
+ "08b0e27988598881d920a9e64f5615cd"),
+ SHEX("000102030405060708090a0b0c0d0e0f"),
+ NULL);
/* F.2.5 CBC-AES256.Encrypt */
"b2eb05e2c39be9fcda6c19078c6a9d1b"),
SHEX("000102030405060708090a0b0c0d0e0f"));
+ test_aead(&nettle_cbc_aes256, NULL,
+ SHEX("603deb1015ca71be2b73aef0857d7781"
+ "1f352c073b6108d72d9810a30914dff4"),
+ NULL,
+ SHEX("6bc1bee22e409f96e93d7e117393172a"
+ "ae2d8a571e03ac9c9eb76fac45af8e51"
+ "30c81c46a35ce411e5fbc1191a0a52ef"
+ "f69f2445df4f9b17ad2b417be66c3710"),
+ SHEX("f58c4c04d6e5f1ba779eabfb5f7bfbd6"
+ "9cfc4e967edb808d679f777bc6702c7d"
+ "39f23369a9d9bacfa530e26304231461"
+ "b2eb05e2c39be9fcda6c19078c6a9d1b"),
+ SHEX("000102030405060708090a0b0c0d0e0f"),
+ NULL);
+
test_cbc_bulk();
}
length = cleartext->length;
ASSERT (key->length == aead->key_size);
- ASSERT (digest->length <= aead->digest_size);
data = xalloc(length);
else
aead->set_nonce(ctx, nonce->data);
- if (authtext->length)
+ if (aead->update && authtext->length)
aead->update(ctx, authtext->length, authtext->data);
-
+
if (length)
aead->encrypt(ctx, length, data, cleartext->data);
- aead->digest(ctx, digest->length, buffer);
+ if (digest)
+ {
+ ASSERT (digest->length <= aead->digest_size);
+ aead->digest(ctx, digest->length, buffer);
+ ASSERT(MEMEQ(digest->length, buffer, digest->data));
+ }
+ else
+ ASSERT(!aead->digest);
ASSERT(MEMEQ(length, data, ciphertext->data));
- ASSERT(MEMEQ(digest->length, buffer, digest->data));
/* decryption */
- memset(buffer, 0, aead->digest_size);
+ if (aead->set_decrypt_key)
+ {
+ memset(buffer, 0, aead->digest_size);
- aead->set_decrypt_key(ctx, key->data);
+ aead->set_decrypt_key(ctx, key->data);
- if (nonce->length != aead->nonce_size)
- {
- ASSERT (set_nonce);
- set_nonce (ctx, nonce->length, nonce->data);
- }
- else
- aead->set_nonce(ctx, nonce->data);
+ if (nonce->length != aead->nonce_size)
+ {
+ ASSERT (set_nonce);
+ set_nonce (ctx, nonce->length, nonce->data);
+ }
+ else
+ aead->set_nonce(ctx, nonce->data);
- if (authtext->length)
- aead->update(ctx, authtext->length, authtext->data);
+ if (authtext->length)
+ aead->update(ctx, authtext->length, authtext->data);
- if (length)
- aead->decrypt(ctx, length, data, data);
+ if (length)
+ aead->decrypt(ctx, length, data, data);
- aead->digest(ctx, digest->length, buffer);
-
- ASSERT(MEMEQ(length, data, cleartext->data));
- ASSERT(MEMEQ(digest->length, buffer, digest->data));
+ aead->digest(ctx, digest->length, buffer);
+ ASSERT(MEMEQ(length, data, cleartext->data));
+ ASSERT(MEMEQ(digest->length, buffer, digest->data));
+ }
free(ctx);
free(data);
free(buffer);