xref: /openbmc/linux/crypto/authencesn.c (revision 4161b450)
1 /*
2  * authencesn.c - AEAD wrapper for IPsec with extended sequence numbers,
3  *                 derived from authenc.c
4  *
5  * Copyright (C) 2010 secunet Security Networks AG
6  * Copyright (C) 2010 Steffen Klassert <steffen.klassert@secunet.com>
7  *
8  * This program is free software; you can redistribute it and/or modify it
9  * under the terms of the GNU General Public License as published by the Free
10  * Software Foundation; either version 2 of the License, or (at your option)
11  * any later version.
12  *
13  */
14 
15 #include <crypto/aead.h>
16 #include <crypto/internal/hash.h>
17 #include <crypto/internal/skcipher.h>
18 #include <crypto/authenc.h>
19 #include <crypto/scatterwalk.h>
20 #include <linux/err.h>
21 #include <linux/init.h>
22 #include <linux/kernel.h>
23 #include <linux/module.h>
24 #include <linux/rtnetlink.h>
25 #include <linux/slab.h>
26 #include <linux/spinlock.h>
27 
28 struct authenc_esn_instance_ctx {
29 	struct crypto_ahash_spawn auth;
30 	struct crypto_skcipher_spawn enc;
31 };
32 
33 struct crypto_authenc_esn_ctx {
34 	unsigned int reqoff;
35 	struct crypto_ahash *auth;
36 	struct crypto_ablkcipher *enc;
37 };
38 
39 struct authenc_esn_request_ctx {
40 	unsigned int cryptlen;
41 	unsigned int headlen;
42 	unsigned int trailen;
43 	struct scatterlist *sg;
44 	struct scatterlist hsg[2];
45 	struct scatterlist tsg[1];
46 	struct scatterlist cipher[2];
47 	crypto_completion_t complete;
48 	crypto_completion_t update_complete;
49 	crypto_completion_t update_complete2;
50 	char tail[];
51 };
52 
53 static void authenc_esn_request_complete(struct aead_request *req, int err)
54 {
55 	if (err != -EINPROGRESS)
56 		aead_request_complete(req, err);
57 }
58 
59 static int crypto_authenc_esn_setkey(struct crypto_aead *authenc_esn, const u8 *key,
60 				     unsigned int keylen)
61 {
62 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
63 	struct crypto_ahash *auth = ctx->auth;
64 	struct crypto_ablkcipher *enc = ctx->enc;
65 	struct crypto_authenc_keys keys;
66 	int err = -EINVAL;
67 
68 	if (crypto_authenc_extractkeys(&keys, key, keylen) != 0)
69 		goto badkey;
70 
71 	crypto_ahash_clear_flags(auth, CRYPTO_TFM_REQ_MASK);
72 	crypto_ahash_set_flags(auth, crypto_aead_get_flags(authenc_esn) &
73 				     CRYPTO_TFM_REQ_MASK);
74 	err = crypto_ahash_setkey(auth, keys.authkey, keys.authkeylen);
75 	crypto_aead_set_flags(authenc_esn, crypto_ahash_get_flags(auth) &
76 					   CRYPTO_TFM_RES_MASK);
77 
78 	if (err)
79 		goto out;
80 
81 	crypto_ablkcipher_clear_flags(enc, CRYPTO_TFM_REQ_MASK);
82 	crypto_ablkcipher_set_flags(enc, crypto_aead_get_flags(authenc_esn) &
83 					 CRYPTO_TFM_REQ_MASK);
84 	err = crypto_ablkcipher_setkey(enc, keys.enckey, keys.enckeylen);
85 	crypto_aead_set_flags(authenc_esn, crypto_ablkcipher_get_flags(enc) &
86 					   CRYPTO_TFM_RES_MASK);
87 
88 out:
89 	return err;
90 
91 badkey:
92 	crypto_aead_set_flags(authenc_esn, CRYPTO_TFM_RES_BAD_KEY_LEN);
93 	goto out;
94 }
95 
96 static void authenc_esn_geniv_ahash_update_done(struct crypto_async_request *areq,
97 						int err)
98 {
99 	struct aead_request *req = areq->data;
100 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
101 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
102 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
103 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
104 
105 	if (err)
106 		goto out;
107 
108 	ahash_request_set_crypt(ahreq, areq_ctx->sg, ahreq->result,
109 				areq_ctx->cryptlen);
110 	ahash_request_set_callback(ahreq, aead_request_flags(req) &
111 					  CRYPTO_TFM_REQ_MAY_SLEEP,
112 				   areq_ctx->update_complete2, req);
113 
114 	err = crypto_ahash_update(ahreq);
115 	if (err)
116 		goto out;
117 
118 	ahash_request_set_crypt(ahreq, areq_ctx->tsg, ahreq->result,
119 				areq_ctx->trailen);
120 	ahash_request_set_callback(ahreq, aead_request_flags(req) &
121 					  CRYPTO_TFM_REQ_MAY_SLEEP,
122 				   areq_ctx->complete, req);
123 
124 	err = crypto_ahash_finup(ahreq);
125 	if (err)
126 		goto out;
127 
128 	scatterwalk_map_and_copy(ahreq->result, areq_ctx->sg,
129 				 areq_ctx->cryptlen,
130 				 crypto_aead_authsize(authenc_esn), 1);
131 
132 out:
133 	authenc_esn_request_complete(req, err);
134 }
135 
136 static void authenc_esn_geniv_ahash_update_done2(struct crypto_async_request *areq,
137 						 int err)
138 {
139 	struct aead_request *req = areq->data;
140 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
141 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
142 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
143 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
144 
145 	if (err)
146 		goto out;
147 
148 	ahash_request_set_crypt(ahreq, areq_ctx->tsg, ahreq->result,
149 				areq_ctx->trailen);
150 	ahash_request_set_callback(ahreq, aead_request_flags(req) &
151 					  CRYPTO_TFM_REQ_MAY_SLEEP,
152 				   areq_ctx->complete, req);
153 
154 	err = crypto_ahash_finup(ahreq);
155 	if (err)
156 		goto out;
157 
158 	scatterwalk_map_and_copy(ahreq->result, areq_ctx->sg,
159 				 areq_ctx->cryptlen,
160 				 crypto_aead_authsize(authenc_esn), 1);
161 
162 out:
163 	authenc_esn_request_complete(req, err);
164 }
165 
166 
167 static void authenc_esn_geniv_ahash_done(struct crypto_async_request *areq,
168 					 int err)
169 {
170 	struct aead_request *req = areq->data;
171 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
172 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
173 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
174 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
175 
176 	if (err)
177 		goto out;
178 
179 	scatterwalk_map_and_copy(ahreq->result, areq_ctx->sg,
180 				 areq_ctx->cryptlen,
181 				 crypto_aead_authsize(authenc_esn), 1);
182 
183 out:
184 	aead_request_complete(req, err);
185 }
186 
187 
188 static void authenc_esn_verify_ahash_update_done(struct crypto_async_request *areq,
189 						 int err)
190 {
191 	u8 *ihash;
192 	unsigned int authsize;
193 	struct ablkcipher_request *abreq;
194 	struct aead_request *req = areq->data;
195 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
196 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
197 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
198 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
199 	unsigned int cryptlen = req->cryptlen;
200 
201 	if (err)
202 		goto out;
203 
204 	ahash_request_set_crypt(ahreq, areq_ctx->sg, ahreq->result,
205 				areq_ctx->cryptlen);
206 
207 	ahash_request_set_callback(ahreq,
208 				   aead_request_flags(req) &
209 				   CRYPTO_TFM_REQ_MAY_SLEEP,
210 				   areq_ctx->update_complete2, req);
211 
212 	err = crypto_ahash_update(ahreq);
213 	if (err)
214 		goto out;
215 
216 	ahash_request_set_crypt(ahreq, areq_ctx->tsg, ahreq->result,
217 				areq_ctx->trailen);
218 	ahash_request_set_callback(ahreq, aead_request_flags(req) &
219 					  CRYPTO_TFM_REQ_MAY_SLEEP,
220 				   areq_ctx->complete, req);
221 
222 	err = crypto_ahash_finup(ahreq);
223 	if (err)
224 		goto out;
225 
226 	authsize = crypto_aead_authsize(authenc_esn);
227 	cryptlen -= authsize;
228 	ihash = ahreq->result + authsize;
229 	scatterwalk_map_and_copy(ihash, areq_ctx->sg, areq_ctx->cryptlen,
230 				 authsize, 0);
231 
232 	err = crypto_memneq(ihash, ahreq->result, authsize) ? -EBADMSG : 0;
233 	if (err)
234 		goto out;
235 
236 	abreq = aead_request_ctx(req);
237 	ablkcipher_request_set_tfm(abreq, ctx->enc);
238 	ablkcipher_request_set_callback(abreq, aead_request_flags(req),
239 					req->base.complete, req->base.data);
240 	ablkcipher_request_set_crypt(abreq, req->src, req->dst,
241 				     cryptlen, req->iv);
242 
243 	err = crypto_ablkcipher_decrypt(abreq);
244 
245 out:
246 	authenc_esn_request_complete(req, err);
247 }
248 
249 static void authenc_esn_verify_ahash_update_done2(struct crypto_async_request *areq,
250 						  int err)
251 {
252 	u8 *ihash;
253 	unsigned int authsize;
254 	struct ablkcipher_request *abreq;
255 	struct aead_request *req = areq->data;
256 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
257 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
258 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
259 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
260 	unsigned int cryptlen = req->cryptlen;
261 
262 	if (err)
263 		goto out;
264 
265 	ahash_request_set_crypt(ahreq, areq_ctx->tsg, ahreq->result,
266 				areq_ctx->trailen);
267 	ahash_request_set_callback(ahreq, aead_request_flags(req) &
268 					  CRYPTO_TFM_REQ_MAY_SLEEP,
269 				   areq_ctx->complete, req);
270 
271 	err = crypto_ahash_finup(ahreq);
272 	if (err)
273 		goto out;
274 
275 	authsize = crypto_aead_authsize(authenc_esn);
276 	cryptlen -= authsize;
277 	ihash = ahreq->result + authsize;
278 	scatterwalk_map_and_copy(ihash, areq_ctx->sg, areq_ctx->cryptlen,
279 				 authsize, 0);
280 
281 	err = crypto_memneq(ihash, ahreq->result, authsize) ? -EBADMSG : 0;
282 	if (err)
283 		goto out;
284 
285 	abreq = aead_request_ctx(req);
286 	ablkcipher_request_set_tfm(abreq, ctx->enc);
287 	ablkcipher_request_set_callback(abreq, aead_request_flags(req),
288 					req->base.complete, req->base.data);
289 	ablkcipher_request_set_crypt(abreq, req->src, req->dst,
290 				     cryptlen, req->iv);
291 
292 	err = crypto_ablkcipher_decrypt(abreq);
293 
294 out:
295 	authenc_esn_request_complete(req, err);
296 }
297 
298 
299 static void authenc_esn_verify_ahash_done(struct crypto_async_request *areq,
300 					  int err)
301 {
302 	u8 *ihash;
303 	unsigned int authsize;
304 	struct ablkcipher_request *abreq;
305 	struct aead_request *req = areq->data;
306 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
307 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
308 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
309 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
310 	unsigned int cryptlen = req->cryptlen;
311 
312 	if (err)
313 		goto out;
314 
315 	authsize = crypto_aead_authsize(authenc_esn);
316 	cryptlen -= authsize;
317 	ihash = ahreq->result + authsize;
318 	scatterwalk_map_and_copy(ihash, areq_ctx->sg, areq_ctx->cryptlen,
319 				 authsize, 0);
320 
321 	err = crypto_memneq(ihash, ahreq->result, authsize) ? -EBADMSG : 0;
322 	if (err)
323 		goto out;
324 
325 	abreq = aead_request_ctx(req);
326 	ablkcipher_request_set_tfm(abreq, ctx->enc);
327 	ablkcipher_request_set_callback(abreq, aead_request_flags(req),
328 					req->base.complete, req->base.data);
329 	ablkcipher_request_set_crypt(abreq, req->src, req->dst,
330 				     cryptlen, req->iv);
331 
332 	err = crypto_ablkcipher_decrypt(abreq);
333 
334 out:
335 	authenc_esn_request_complete(req, err);
336 }
337 
338 static u8 *crypto_authenc_esn_ahash(struct aead_request *req,
339 				    unsigned int flags)
340 {
341 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
342 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
343 	struct crypto_ahash *auth = ctx->auth;
344 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
345 	struct ahash_request *ahreq = (void *)(areq_ctx->tail + ctx->reqoff);
346 	u8 *hash = areq_ctx->tail;
347 	int err;
348 
349 	hash = (u8 *)ALIGN((unsigned long)hash + crypto_ahash_alignmask(auth),
350 			    crypto_ahash_alignmask(auth) + 1);
351 
352 	ahash_request_set_tfm(ahreq, auth);
353 
354 	err = crypto_ahash_init(ahreq);
355 	if (err)
356 		return ERR_PTR(err);
357 
358 	ahash_request_set_crypt(ahreq, areq_ctx->hsg, hash, areq_ctx->headlen);
359 	ahash_request_set_callback(ahreq, aead_request_flags(req) & flags,
360 				   areq_ctx->update_complete, req);
361 
362 	err = crypto_ahash_update(ahreq);
363 	if (err)
364 		return ERR_PTR(err);
365 
366 	ahash_request_set_crypt(ahreq, areq_ctx->sg, hash, areq_ctx->cryptlen);
367 	ahash_request_set_callback(ahreq, aead_request_flags(req) & flags,
368 				   areq_ctx->update_complete2, req);
369 
370 	err = crypto_ahash_update(ahreq);
371 	if (err)
372 		return ERR_PTR(err);
373 
374 	ahash_request_set_crypt(ahreq, areq_ctx->tsg, hash,
375 				areq_ctx->trailen);
376 	ahash_request_set_callback(ahreq, aead_request_flags(req) & flags,
377 				   areq_ctx->complete, req);
378 
379 	err = crypto_ahash_finup(ahreq);
380 	if (err)
381 		return ERR_PTR(err);
382 
383 	return hash;
384 }
385 
386 static int crypto_authenc_esn_genicv(struct aead_request *req, u8 *iv,
387 				     unsigned int flags)
388 {
389 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
390 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
391 	struct scatterlist *dst = req->dst;
392 	struct scatterlist *assoc = req->assoc;
393 	struct scatterlist *cipher = areq_ctx->cipher;
394 	struct scatterlist *hsg = areq_ctx->hsg;
395 	struct scatterlist *tsg = areq_ctx->tsg;
396 	struct scatterlist *assoc1;
397 	struct scatterlist *assoc2;
398 	unsigned int ivsize = crypto_aead_ivsize(authenc_esn);
399 	unsigned int cryptlen = req->cryptlen;
400 	struct page *dstp;
401 	u8 *vdst;
402 	u8 *hash;
403 
404 	dstp = sg_page(dst);
405 	vdst = PageHighMem(dstp) ? NULL : page_address(dstp) + dst->offset;
406 
407 	if (ivsize) {
408 		sg_init_table(cipher, 2);
409 		sg_set_buf(cipher, iv, ivsize);
410 		scatterwalk_crypto_chain(cipher, dst, vdst == iv + ivsize, 2);
411 		dst = cipher;
412 		cryptlen += ivsize;
413 	}
414 
415 	if (sg_is_last(assoc))
416 		return -EINVAL;
417 
418 	assoc1 = assoc + 1;
419 	if (sg_is_last(assoc1))
420 		return -EINVAL;
421 
422 	assoc2 = assoc + 2;
423 	if (!sg_is_last(assoc2))
424 		return -EINVAL;
425 
426 	sg_init_table(hsg, 2);
427 	sg_set_page(hsg, sg_page(assoc), assoc->length, assoc->offset);
428 	sg_set_page(hsg + 1, sg_page(assoc2), assoc2->length, assoc2->offset);
429 
430 	sg_init_table(tsg, 1);
431 	sg_set_page(tsg, sg_page(assoc1), assoc1->length, assoc1->offset);
432 
433 	areq_ctx->cryptlen = cryptlen;
434 	areq_ctx->headlen = assoc->length + assoc2->length;
435 	areq_ctx->trailen = assoc1->length;
436 	areq_ctx->sg = dst;
437 
438 	areq_ctx->complete = authenc_esn_geniv_ahash_done;
439 	areq_ctx->update_complete = authenc_esn_geniv_ahash_update_done;
440 	areq_ctx->update_complete2 = authenc_esn_geniv_ahash_update_done2;
441 
442 	hash = crypto_authenc_esn_ahash(req, flags);
443 	if (IS_ERR(hash))
444 		return PTR_ERR(hash);
445 
446 	scatterwalk_map_and_copy(hash, dst, cryptlen,
447 				 crypto_aead_authsize(authenc_esn), 1);
448 	return 0;
449 }
450 
451 
452 static void crypto_authenc_esn_encrypt_done(struct crypto_async_request *req,
453 					    int err)
454 {
455 	struct aead_request *areq = req->data;
456 
457 	if (!err) {
458 		struct crypto_aead *authenc_esn = crypto_aead_reqtfm(areq);
459 		struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
460 		struct ablkcipher_request *abreq = aead_request_ctx(areq);
461 		u8 *iv = (u8 *)(abreq + 1) +
462 			 crypto_ablkcipher_reqsize(ctx->enc);
463 
464 		err = crypto_authenc_esn_genicv(areq, iv, 0);
465 	}
466 
467 	authenc_esn_request_complete(areq, err);
468 }
469 
470 static int crypto_authenc_esn_encrypt(struct aead_request *req)
471 {
472 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
473 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
474 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
475 	struct crypto_ablkcipher *enc = ctx->enc;
476 	struct scatterlist *dst = req->dst;
477 	unsigned int cryptlen = req->cryptlen;
478 	struct ablkcipher_request *abreq = (void *)(areq_ctx->tail
479 						    + ctx->reqoff);
480 	u8 *iv = (u8 *)abreq - crypto_ablkcipher_ivsize(enc);
481 	int err;
482 
483 	ablkcipher_request_set_tfm(abreq, enc);
484 	ablkcipher_request_set_callback(abreq, aead_request_flags(req),
485 					crypto_authenc_esn_encrypt_done, req);
486 	ablkcipher_request_set_crypt(abreq, req->src, dst, cryptlen, req->iv);
487 
488 	memcpy(iv, req->iv, crypto_aead_ivsize(authenc_esn));
489 
490 	err = crypto_ablkcipher_encrypt(abreq);
491 	if (err)
492 		return err;
493 
494 	return crypto_authenc_esn_genicv(req, iv, CRYPTO_TFM_REQ_MAY_SLEEP);
495 }
496 
497 static void crypto_authenc_esn_givencrypt_done(struct crypto_async_request *req,
498 					       int err)
499 {
500 	struct aead_request *areq = req->data;
501 
502 	if (!err) {
503 		struct skcipher_givcrypt_request *greq = aead_request_ctx(areq);
504 
505 		err = crypto_authenc_esn_genicv(areq, greq->giv, 0);
506 	}
507 
508 	authenc_esn_request_complete(areq, err);
509 }
510 
511 static int crypto_authenc_esn_givencrypt(struct aead_givcrypt_request *req)
512 {
513 	struct crypto_aead *authenc_esn = aead_givcrypt_reqtfm(req);
514 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
515 	struct aead_request *areq = &req->areq;
516 	struct skcipher_givcrypt_request *greq = aead_request_ctx(areq);
517 	u8 *iv = req->giv;
518 	int err;
519 
520 	skcipher_givcrypt_set_tfm(greq, ctx->enc);
521 	skcipher_givcrypt_set_callback(greq, aead_request_flags(areq),
522 				       crypto_authenc_esn_givencrypt_done, areq);
523 	skcipher_givcrypt_set_crypt(greq, areq->src, areq->dst, areq->cryptlen,
524 				    areq->iv);
525 	skcipher_givcrypt_set_giv(greq, iv, req->seq);
526 
527 	err = crypto_skcipher_givencrypt(greq);
528 	if (err)
529 		return err;
530 
531 	return crypto_authenc_esn_genicv(areq, iv, CRYPTO_TFM_REQ_MAY_SLEEP);
532 }
533 
534 static int crypto_authenc_esn_verify(struct aead_request *req)
535 {
536 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
537 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
538 	u8 *ohash;
539 	u8 *ihash;
540 	unsigned int authsize;
541 
542 	areq_ctx->complete = authenc_esn_verify_ahash_done;
543 	areq_ctx->update_complete = authenc_esn_verify_ahash_update_done;
544 
545 	ohash = crypto_authenc_esn_ahash(req, CRYPTO_TFM_REQ_MAY_SLEEP);
546 	if (IS_ERR(ohash))
547 		return PTR_ERR(ohash);
548 
549 	authsize = crypto_aead_authsize(authenc_esn);
550 	ihash = ohash + authsize;
551 	scatterwalk_map_and_copy(ihash, areq_ctx->sg, areq_ctx->cryptlen,
552 				 authsize, 0);
553 	return crypto_memneq(ihash, ohash, authsize) ? -EBADMSG : 0;
554 }
555 
556 static int crypto_authenc_esn_iverify(struct aead_request *req, u8 *iv,
557 				      unsigned int cryptlen)
558 {
559 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
560 	struct authenc_esn_request_ctx *areq_ctx = aead_request_ctx(req);
561 	struct scatterlist *src = req->src;
562 	struct scatterlist *assoc = req->assoc;
563 	struct scatterlist *cipher = areq_ctx->cipher;
564 	struct scatterlist *hsg = areq_ctx->hsg;
565 	struct scatterlist *tsg = areq_ctx->tsg;
566 	struct scatterlist *assoc1;
567 	struct scatterlist *assoc2;
568 	unsigned int ivsize = crypto_aead_ivsize(authenc_esn);
569 	struct page *srcp;
570 	u8 *vsrc;
571 
572 	srcp = sg_page(src);
573 	vsrc = PageHighMem(srcp) ? NULL : page_address(srcp) + src->offset;
574 
575 	if (ivsize) {
576 		sg_init_table(cipher, 2);
577 		sg_set_buf(cipher, iv, ivsize);
578 		scatterwalk_crypto_chain(cipher, src, vsrc == iv + ivsize, 2);
579 		src = cipher;
580 		cryptlen += ivsize;
581 	}
582 
583 	if (sg_is_last(assoc))
584 		return -EINVAL;
585 
586 	assoc1 = assoc + 1;
587 	if (sg_is_last(assoc1))
588 		return -EINVAL;
589 
590 	assoc2 = assoc + 2;
591 	if (!sg_is_last(assoc2))
592 		return -EINVAL;
593 
594 	sg_init_table(hsg, 2);
595 	sg_set_page(hsg, sg_page(assoc), assoc->length, assoc->offset);
596 	sg_set_page(hsg + 1, sg_page(assoc2), assoc2->length, assoc2->offset);
597 
598 	sg_init_table(tsg, 1);
599 	sg_set_page(tsg, sg_page(assoc1), assoc1->length, assoc1->offset);
600 
601 	areq_ctx->cryptlen = cryptlen;
602 	areq_ctx->headlen = assoc->length + assoc2->length;
603 	areq_ctx->trailen = assoc1->length;
604 	areq_ctx->sg = src;
605 
606 	areq_ctx->complete = authenc_esn_verify_ahash_done;
607 	areq_ctx->update_complete = authenc_esn_verify_ahash_update_done;
608 	areq_ctx->update_complete2 = authenc_esn_verify_ahash_update_done2;
609 
610 	return crypto_authenc_esn_verify(req);
611 }
612 
613 static int crypto_authenc_esn_decrypt(struct aead_request *req)
614 {
615 	struct crypto_aead *authenc_esn = crypto_aead_reqtfm(req);
616 	struct crypto_authenc_esn_ctx *ctx = crypto_aead_ctx(authenc_esn);
617 	struct ablkcipher_request *abreq = aead_request_ctx(req);
618 	unsigned int cryptlen = req->cryptlen;
619 	unsigned int authsize = crypto_aead_authsize(authenc_esn);
620 	u8 *iv = req->iv;
621 	int err;
622 
623 	if (cryptlen < authsize)
624 		return -EINVAL;
625 	cryptlen -= authsize;
626 
627 	err = crypto_authenc_esn_iverify(req, iv, cryptlen);
628 	if (err)
629 		return err;
630 
631 	ablkcipher_request_set_tfm(abreq, ctx->enc);
632 	ablkcipher_request_set_callback(abreq, aead_request_flags(req),
633 					req->base.complete, req->base.data);
634 	ablkcipher_request_set_crypt(abreq, req->src, req->dst, cryptlen, iv);
635 
636 	return crypto_ablkcipher_decrypt(abreq);
637 }
638 
639 static int crypto_authenc_esn_init_tfm(struct crypto_tfm *tfm)
640 {
641 	struct crypto_instance *inst = crypto_tfm_alg_instance(tfm);
642 	struct authenc_esn_instance_ctx *ictx = crypto_instance_ctx(inst);
643 	struct crypto_authenc_esn_ctx *ctx = crypto_tfm_ctx(tfm);
644 	struct crypto_ahash *auth;
645 	struct crypto_ablkcipher *enc;
646 	int err;
647 
648 	auth = crypto_spawn_ahash(&ictx->auth);
649 	if (IS_ERR(auth))
650 		return PTR_ERR(auth);
651 
652 	enc = crypto_spawn_skcipher(&ictx->enc);
653 	err = PTR_ERR(enc);
654 	if (IS_ERR(enc))
655 		goto err_free_ahash;
656 
657 	ctx->auth = auth;
658 	ctx->enc = enc;
659 
660 	ctx->reqoff = ALIGN(2 * crypto_ahash_digestsize(auth) +
661 			    crypto_ahash_alignmask(auth),
662 			    crypto_ahash_alignmask(auth) + 1) +
663 		      crypto_ablkcipher_ivsize(enc);
664 
665 	tfm->crt_aead.reqsize = sizeof(struct authenc_esn_request_ctx) +
666 				ctx->reqoff +
667 				max_t(unsigned int,
668 				crypto_ahash_reqsize(auth) +
669 				sizeof(struct ahash_request),
670 				sizeof(struct skcipher_givcrypt_request) +
671 				crypto_ablkcipher_reqsize(enc));
672 
673 	return 0;
674 
675 err_free_ahash:
676 	crypto_free_ahash(auth);
677 	return err;
678 }
679 
680 static void crypto_authenc_esn_exit_tfm(struct crypto_tfm *tfm)
681 {
682 	struct crypto_authenc_esn_ctx *ctx = crypto_tfm_ctx(tfm);
683 
684 	crypto_free_ahash(ctx->auth);
685 	crypto_free_ablkcipher(ctx->enc);
686 }
687 
688 static struct crypto_instance *crypto_authenc_esn_alloc(struct rtattr **tb)
689 {
690 	struct crypto_attr_type *algt;
691 	struct crypto_instance *inst;
692 	struct hash_alg_common *auth;
693 	struct crypto_alg *auth_base;
694 	struct crypto_alg *enc;
695 	struct authenc_esn_instance_ctx *ctx;
696 	const char *enc_name;
697 	int err;
698 
699 	algt = crypto_get_attr_type(tb);
700 	if (IS_ERR(algt))
701 		return ERR_CAST(algt);
702 
703 	if ((algt->type ^ CRYPTO_ALG_TYPE_AEAD) & algt->mask)
704 		return ERR_PTR(-EINVAL);
705 
706 	auth = ahash_attr_alg(tb[1], CRYPTO_ALG_TYPE_HASH,
707 			       CRYPTO_ALG_TYPE_AHASH_MASK);
708 	if (IS_ERR(auth))
709 		return ERR_CAST(auth);
710 
711 	auth_base = &auth->base;
712 
713 	enc_name = crypto_attr_alg_name(tb[2]);
714 	err = PTR_ERR(enc_name);
715 	if (IS_ERR(enc_name))
716 		goto out_put_auth;
717 
718 	inst = kzalloc(sizeof(*inst) + sizeof(*ctx), GFP_KERNEL);
719 	err = -ENOMEM;
720 	if (!inst)
721 		goto out_put_auth;
722 
723 	ctx = crypto_instance_ctx(inst);
724 
725 	err = crypto_init_ahash_spawn(&ctx->auth, auth, inst);
726 	if (err)
727 		goto err_free_inst;
728 
729 	crypto_set_skcipher_spawn(&ctx->enc, inst);
730 	err = crypto_grab_skcipher(&ctx->enc, enc_name, 0,
731 				   crypto_requires_sync(algt->type,
732 							algt->mask));
733 	if (err)
734 		goto err_drop_auth;
735 
736 	enc = crypto_skcipher_spawn_alg(&ctx->enc);
737 
738 	err = -ENAMETOOLONG;
739 	if (snprintf(inst->alg.cra_name, CRYPTO_MAX_ALG_NAME,
740 		     "authencesn(%s,%s)", auth_base->cra_name, enc->cra_name) >=
741 	    CRYPTO_MAX_ALG_NAME)
742 		goto err_drop_enc;
743 
744 	if (snprintf(inst->alg.cra_driver_name, CRYPTO_MAX_ALG_NAME,
745 		     "authencesn(%s,%s)", auth_base->cra_driver_name,
746 		     enc->cra_driver_name) >= CRYPTO_MAX_ALG_NAME)
747 		goto err_drop_enc;
748 
749 	inst->alg.cra_flags = CRYPTO_ALG_TYPE_AEAD;
750 	inst->alg.cra_flags |= enc->cra_flags & CRYPTO_ALG_ASYNC;
751 	inst->alg.cra_priority = enc->cra_priority *
752 				 10 + auth_base->cra_priority;
753 	inst->alg.cra_blocksize = enc->cra_blocksize;
754 	inst->alg.cra_alignmask = auth_base->cra_alignmask | enc->cra_alignmask;
755 	inst->alg.cra_type = &crypto_aead_type;
756 
757 	inst->alg.cra_aead.ivsize = enc->cra_ablkcipher.ivsize;
758 	inst->alg.cra_aead.maxauthsize = auth->digestsize;
759 
760 	inst->alg.cra_ctxsize = sizeof(struct crypto_authenc_esn_ctx);
761 
762 	inst->alg.cra_init = crypto_authenc_esn_init_tfm;
763 	inst->alg.cra_exit = crypto_authenc_esn_exit_tfm;
764 
765 	inst->alg.cra_aead.setkey = crypto_authenc_esn_setkey;
766 	inst->alg.cra_aead.encrypt = crypto_authenc_esn_encrypt;
767 	inst->alg.cra_aead.decrypt = crypto_authenc_esn_decrypt;
768 	inst->alg.cra_aead.givencrypt = crypto_authenc_esn_givencrypt;
769 
770 out:
771 	crypto_mod_put(auth_base);
772 	return inst;
773 
774 err_drop_enc:
775 	crypto_drop_skcipher(&ctx->enc);
776 err_drop_auth:
777 	crypto_drop_ahash(&ctx->auth);
778 err_free_inst:
779 	kfree(inst);
780 out_put_auth:
781 	inst = ERR_PTR(err);
782 	goto out;
783 }
784 
785 static void crypto_authenc_esn_free(struct crypto_instance *inst)
786 {
787 	struct authenc_esn_instance_ctx *ctx = crypto_instance_ctx(inst);
788 
789 	crypto_drop_skcipher(&ctx->enc);
790 	crypto_drop_ahash(&ctx->auth);
791 	kfree(inst);
792 }
793 
794 static struct crypto_template crypto_authenc_esn_tmpl = {
795 	.name = "authencesn",
796 	.alloc = crypto_authenc_esn_alloc,
797 	.free = crypto_authenc_esn_free,
798 	.module = THIS_MODULE,
799 };
800 
801 static int __init crypto_authenc_esn_module_init(void)
802 {
803 	return crypto_register_template(&crypto_authenc_esn_tmpl);
804 }
805 
806 static void __exit crypto_authenc_esn_module_exit(void)
807 {
808 	crypto_unregister_template(&crypto_authenc_esn_tmpl);
809 }
810 
811 module_init(crypto_authenc_esn_module_init);
812 module_exit(crypto_authenc_esn_module_exit);
813 
814 MODULE_LICENSE("GPL");
815 MODULE_AUTHOR("Steffen Klassert <steffen.klassert@secunet.com>");
816 MODULE_DESCRIPTION("AEAD wrapper for IPsec with extended sequence numbers");
817 MODULE_ALIAS_CRYPTO("authencesn");
818