diff options
author | Martin Willi <martin@strongswan.org> | 2015-07-16 13:14:00 -0400 |
---|---|---|
committer | Herbert Xu <herbert@gondor.apana.org.au> | 2015-07-17 09:20:21 -0400 |
commit | 31d7247da57226e847f0f102a10c27c0722c429b (patch) | |
tree | 3ca25c75fc443d974213e845d5999fd41b578091 | |
parent | 2dce063a31ae6cbaf39964663fc59d10bef38d15 (diff) |
crypto: chacha20 - Export common ChaCha20 helpers
As architecture specific drivers need a software fallback, export a
ChaCha20 en-/decryption function together with some helpers in a header
file.
Signed-off-by: Martin Willi <martin@strongswan.org>
Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
-rw-r--r-- | crypto/chacha20_generic.c | 28 | ||||
-rw-r--r-- | crypto/chacha20poly1305.c | 3 | ||||
-rw-r--r-- | include/crypto/chacha20.h | 25 |
3 files changed, 38 insertions, 18 deletions
diff --git a/crypto/chacha20_generic.c b/crypto/chacha20_generic.c index fa42e708aa96..da9c89968223 100644 --- a/crypto/chacha20_generic.c +++ b/crypto/chacha20_generic.c | |||
@@ -13,14 +13,7 @@ | |||
13 | #include <linux/crypto.h> | 13 | #include <linux/crypto.h> |
14 | #include <linux/kernel.h> | 14 | #include <linux/kernel.h> |
15 | #include <linux/module.h> | 15 | #include <linux/module.h> |
16 | 16 | #include <crypto/chacha20.h> | |
17 | #define CHACHA20_NONCE_SIZE 16 | ||
18 | #define CHACHA20_KEY_SIZE 32 | ||
19 | #define CHACHA20_BLOCK_SIZE 64 | ||
20 | |||
21 | struct chacha20_ctx { | ||
22 | u32 key[8]; | ||
23 | }; | ||
24 | 17 | ||
25 | static inline u32 rotl32(u32 v, u8 n) | 18 | static inline u32 rotl32(u32 v, u8 n) |
26 | { | 19 | { |
@@ -108,7 +101,7 @@ static void chacha20_docrypt(u32 *state, u8 *dst, const u8 *src, | |||
108 | } | 101 | } |
109 | } | 102 | } |
110 | 103 | ||
111 | static void chacha20_init(u32 *state, struct chacha20_ctx *ctx, u8 *iv) | 104 | void crypto_chacha20_init(u32 *state, struct chacha20_ctx *ctx, u8 *iv) |
112 | { | 105 | { |
113 | static const char constant[16] = "expand 32-byte k"; | 106 | static const char constant[16] = "expand 32-byte k"; |
114 | 107 | ||
@@ -129,8 +122,9 @@ static void chacha20_init(u32 *state, struct chacha20_ctx *ctx, u8 *iv) | |||
129 | state[14] = le32_to_cpuvp(iv + 8); | 122 | state[14] = le32_to_cpuvp(iv + 8); |
130 | state[15] = le32_to_cpuvp(iv + 12); | 123 | state[15] = le32_to_cpuvp(iv + 12); |
131 | } | 124 | } |
125 | EXPORT_SYMBOL_GPL(crypto_chacha20_init); | ||
132 | 126 | ||
133 | static int chacha20_setkey(struct crypto_tfm *tfm, const u8 *key, | 127 | int crypto_chacha20_setkey(struct crypto_tfm *tfm, const u8 *key, |
134 | unsigned int keysize) | 128 | unsigned int keysize) |
135 | { | 129 | { |
136 | struct chacha20_ctx *ctx = crypto_tfm_ctx(tfm); | 130 | struct chacha20_ctx *ctx = crypto_tfm_ctx(tfm); |
@@ -144,8 +138,9 @@ static int chacha20_setkey(struct crypto_tfm *tfm, const u8 *key, | |||
144 | 138 | ||
145 | return 0; | 139 | return 0; |
146 | } | 140 | } |
141 | EXPORT_SYMBOL_GPL(crypto_chacha20_setkey); | ||
147 | 142 | ||
148 | static int chacha20_crypt(struct blkcipher_desc *desc, struct scatterlist *dst, | 143 | int crypto_chacha20_crypt(struct blkcipher_desc *desc, struct scatterlist *dst, |
149 | struct scatterlist *src, unsigned int nbytes) | 144 | struct scatterlist *src, unsigned int nbytes) |
150 | { | 145 | { |
151 | struct blkcipher_walk walk; | 146 | struct blkcipher_walk walk; |
@@ -155,7 +150,7 @@ static int chacha20_crypt(struct blkcipher_desc *desc, struct scatterlist *dst, | |||
155 | blkcipher_walk_init(&walk, dst, src, nbytes); | 150 | blkcipher_walk_init(&walk, dst, src, nbytes); |
156 | err = blkcipher_walk_virt_block(desc, &walk, CHACHA20_BLOCK_SIZE); | 151 | err = blkcipher_walk_virt_block(desc, &walk, CHACHA20_BLOCK_SIZE); |
157 | 152 | ||
158 | chacha20_init(state, crypto_blkcipher_ctx(desc->tfm), walk.iv); | 153 | crypto_chacha20_init(state, crypto_blkcipher_ctx(desc->tfm), walk.iv); |
159 | 154 | ||
160 | while (walk.nbytes >= CHACHA20_BLOCK_SIZE) { | 155 | while (walk.nbytes >= CHACHA20_BLOCK_SIZE) { |
161 | chacha20_docrypt(state, walk.dst.virt.addr, walk.src.virt.addr, | 156 | chacha20_docrypt(state, walk.dst.virt.addr, walk.src.virt.addr, |
@@ -172,6 +167,7 @@ static int chacha20_crypt(struct blkcipher_desc *desc, struct scatterlist *dst, | |||
172 | 167 | ||
173 | return err; | 168 | return err; |
174 | } | 169 | } |
170 | EXPORT_SYMBOL_GPL(crypto_chacha20_crypt); | ||
175 | 171 | ||
176 | static struct crypto_alg alg = { | 172 | static struct crypto_alg alg = { |
177 | .cra_name = "chacha20", | 173 | .cra_name = "chacha20", |
@@ -187,11 +183,11 @@ static struct crypto_alg alg = { | |||
187 | .blkcipher = { | 183 | .blkcipher = { |
188 | .min_keysize = CHACHA20_KEY_SIZE, | 184 | .min_keysize = CHACHA20_KEY_SIZE, |
189 | .max_keysize = CHACHA20_KEY_SIZE, | 185 | .max_keysize = CHACHA20_KEY_SIZE, |
190 | .ivsize = CHACHA20_NONCE_SIZE, | 186 | .ivsize = CHACHA20_IV_SIZE, |
191 | .geniv = "seqiv", | 187 | .geniv = "seqiv", |
192 | .setkey = chacha20_setkey, | 188 | .setkey = crypto_chacha20_setkey, |
193 | .encrypt = chacha20_crypt, | 189 | .encrypt = crypto_chacha20_crypt, |
194 | .decrypt = chacha20_crypt, | 190 | .decrypt = crypto_chacha20_crypt, |
195 | }, | 191 | }, |
196 | }, | 192 | }, |
197 | }; | 193 | }; |
diff --git a/crypto/chacha20poly1305.c b/crypto/chacha20poly1305.c index 86260937b0f3..410554d3a1ff 100644 --- a/crypto/chacha20poly1305.c +++ b/crypto/chacha20poly1305.c | |||
@@ -13,6 +13,7 @@ | |||
13 | #include <crypto/internal/hash.h> | 13 | #include <crypto/internal/hash.h> |
14 | #include <crypto/internal/skcipher.h> | 14 | #include <crypto/internal/skcipher.h> |
15 | #include <crypto/scatterwalk.h> | 15 | #include <crypto/scatterwalk.h> |
16 | #include <crypto/chacha20.h> | ||
16 | #include <linux/err.h> | 17 | #include <linux/err.h> |
17 | #include <linux/init.h> | 18 | #include <linux/init.h> |
18 | #include <linux/kernel.h> | 19 | #include <linux/kernel.h> |
@@ -23,8 +24,6 @@ | |||
23 | #define POLY1305_BLOCK_SIZE 16 | 24 | #define POLY1305_BLOCK_SIZE 16 |
24 | #define POLY1305_DIGEST_SIZE 16 | 25 | #define POLY1305_DIGEST_SIZE 16 |
25 | #define POLY1305_KEY_SIZE 32 | 26 | #define POLY1305_KEY_SIZE 32 |
26 | #define CHACHA20_KEY_SIZE 32 | ||
27 | #define CHACHA20_IV_SIZE 16 | ||
28 | #define CHACHAPOLY_IV_SIZE 12 | 27 | #define CHACHAPOLY_IV_SIZE 12 |
29 | 28 | ||
30 | struct chachapoly_instance_ctx { | 29 | struct chachapoly_instance_ctx { |
diff --git a/include/crypto/chacha20.h b/include/crypto/chacha20.h new file mode 100644 index 000000000000..274bbaeeed0f --- /dev/null +++ b/include/crypto/chacha20.h | |||
@@ -0,0 +1,25 @@ | |||
1 | /* | ||
2 | * Common values for the ChaCha20 algorithm | ||
3 | */ | ||
4 | |||
5 | #ifndef _CRYPTO_CHACHA20_H | ||
6 | #define _CRYPTO_CHACHA20_H | ||
7 | |||
8 | #include <linux/types.h> | ||
9 | #include <linux/crypto.h> | ||
10 | |||
11 | #define CHACHA20_IV_SIZE 16 | ||
12 | #define CHACHA20_KEY_SIZE 32 | ||
13 | #define CHACHA20_BLOCK_SIZE 64 | ||
14 | |||
15 | struct chacha20_ctx { | ||
16 | u32 key[8]; | ||
17 | }; | ||
18 | |||
19 | void crypto_chacha20_init(u32 *state, struct chacha20_ctx *ctx, u8 *iv); | ||
20 | int crypto_chacha20_setkey(struct crypto_tfm *tfm, const u8 *key, | ||
21 | unsigned int keysize); | ||
22 | int crypto_chacha20_crypt(struct blkcipher_desc *desc, struct scatterlist *dst, | ||
23 | struct scatterlist *src, unsigned int nbytes); | ||
24 | |||
25 | #endif | ||