]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sys/opencrypto/cryptodev.c
Move cryptodev_cb earlier before it is used.
[FreeBSD/FreeBSD.git] / sys / opencrypto / cryptodev.c
1 /*      $OpenBSD: cryptodev.c,v 1.52 2002/06/19 07:22:46 deraadt Exp $  */
2
3 /*-
4  * Copyright (c) 2001 Theo de Raadt
5  * Copyright (c) 2002-2006 Sam Leffler, Errno Consulting
6  * Copyright (c) 2014 The FreeBSD Foundation
7  * All rights reserved.
8  *
9  * Portions of this software were developed by John-Mark Gurney
10  * under sponsorship of the FreeBSD Foundation and
11  * Rubicon Communications, LLC (Netgate).
12  *
13  * Redistribution and use in source and binary forms, with or without
14  * modification, are permitted provided that the following conditions
15  * are met:
16  *
17  * 1. Redistributions of source code must retain the above copyright
18  *   notice, this list of conditions and the following disclaimer.
19  * 2. Redistributions in binary form must reproduce the above copyright
20  *   notice, this list of conditions and the following disclaimer in the
21  *   documentation and/or other materials provided with the distribution.
22  * 3. The name of the author may not be used to endorse or promote products
23  *   derived from this software without specific prior written permission.
24  *
25  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
26  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
27  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
28  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
29  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
30  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
31  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
32  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
33  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
34  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35  *
36  * Effort sponsored in part by the Defense Advanced Research Projects
37  * Agency (DARPA) and Air Force Research Laboratory, Air Force
38  * Materiel Command, USAF, under agreement number F30602-01-2-0537.
39  */
40
41 #include <sys/cdefs.h>
42 __FBSDID("$FreeBSD$");
43
44 #include <sys/param.h>
45 #include <sys/systm.h>
46 #include <sys/malloc.h>
47 #include <sys/mbuf.h>
48 #include <sys/lock.h>
49 #include <sys/mutex.h>
50 #include <sys/sysctl.h>
51 #include <sys/file.h>
52 #include <sys/filedesc.h>
53 #include <sys/errno.h>
54 #include <sys/random.h>
55 #include <sys/conf.h>
56 #include <sys/kernel.h>
57 #include <sys/module.h>
58 #include <sys/fcntl.h>
59 #include <sys/bus.h>
60 #include <sys/user.h>
61 #include <sys/sdt.h>
62
63 #include <opencrypto/cryptodev.h>
64 #include <opencrypto/xform.h>
65
66 SDT_PROVIDER_DECLARE(opencrypto);
67
68 SDT_PROBE_DEFINE1(opencrypto, dev, ioctl, error, "int"/*line number*/);
69
70 #ifdef COMPAT_FREEBSD32
71 #include <sys/mount.h>
72 #include <compat/freebsd32/freebsd32.h>
73
74 struct session_op32 {
75         uint32_t        cipher;
76         uint32_t        mac;
77         uint32_t        keylen;
78         uint32_t        key;
79         int             mackeylen;
80         uint32_t        mackey;
81         uint32_t        ses;
82 };
83
84 struct session2_op32 {
85         uint32_t        cipher;
86         uint32_t        mac;
87         uint32_t        keylen;
88         uint32_t        key;
89         int             mackeylen;
90         uint32_t        mackey;
91         uint32_t        ses;
92         int             crid;
93         int             pad[4];
94 };
95
96 struct crypt_op32 {
97         uint32_t        ses;
98         uint16_t        op;
99         uint16_t        flags;
100         u_int           len;
101         uint32_t        src, dst;
102         uint32_t        mac;
103         uint32_t        iv;
104 };
105
106 struct crypt_aead32 {
107         uint32_t        ses;
108         uint16_t        op;
109         uint16_t        flags;
110         u_int           len;
111         u_int           aadlen;
112         u_int           ivlen;
113         uint32_t        src;
114         uint32_t        dst;
115         uint32_t        aad;
116         uint32_t        tag;
117         uint32_t        iv;
118 };
119
120 struct crparam32 {
121         uint32_t        crp_p;
122         u_int           crp_nbits;
123 };
124
125 struct crypt_kop32 {
126         u_int           crk_op;
127         u_int           crk_status;
128         u_short         crk_iparams;
129         u_short         crk_oparams;
130         u_int           crk_crid;
131         struct crparam32        crk_param[CRK_MAXPARAM];
132 };
133
134 #define CIOCGSESSION32  _IOWR('c', 101, struct session_op32)
135 #define CIOCCRYPT32     _IOWR('c', 103, struct crypt_op32)
136 #define CIOCKEY32       _IOWR('c', 104, struct crypt_kop32)
137 #define CIOCGSESSION232 _IOWR('c', 106, struct session2_op32)
138 #define CIOCKEY232      _IOWR('c', 107, struct crypt_kop32)
139 #define CIOCCRYPTAEAD32 _IOWR('c', 109, struct crypt_aead32)
140
141 static void
142 session_op_from_32(const struct session_op32 *from, struct session2_op *to)
143 {
144
145         memset(to, 0, sizeof(*to));
146         CP(*from, *to, cipher);
147         CP(*from, *to, mac);
148         CP(*from, *to, keylen);
149         PTRIN_CP(*from, *to, key);
150         CP(*from, *to, mackeylen);
151         PTRIN_CP(*from, *to, mackey);
152         CP(*from, *to, ses);
153         to->crid = CRYPTOCAP_F_HARDWARE;
154 }
155
156 static void
157 session2_op_from_32(const struct session2_op32 *from, struct session2_op *to)
158 {
159
160         session_op_from_32((const struct session_op32 *)from, to);
161         CP(*from, *to, crid);
162 }
163
164 static void
165 session_op_to_32(const struct session2_op *from, struct session_op32 *to)
166 {
167
168         CP(*from, *to, cipher);
169         CP(*from, *to, mac);
170         CP(*from, *to, keylen);
171         PTROUT_CP(*from, *to, key);
172         CP(*from, *to, mackeylen);
173         PTROUT_CP(*from, *to, mackey);
174         CP(*from, *to, ses);
175 }
176
177 static void
178 session2_op_to_32(const struct session2_op *from, struct session2_op32 *to)
179 {
180
181         session_op_to_32(from, (struct session_op32 *)to);
182         CP(*from, *to, crid);
183 }
184
185 static void
186 crypt_op_from_32(const struct crypt_op32 *from, struct crypt_op *to)
187 {
188
189         CP(*from, *to, ses);
190         CP(*from, *to, op);
191         CP(*from, *to, flags);
192         CP(*from, *to, len);
193         PTRIN_CP(*from, *to, src);
194         PTRIN_CP(*from, *to, dst);
195         PTRIN_CP(*from, *to, mac);
196         PTRIN_CP(*from, *to, iv);
197 }
198
199 static void
200 crypt_op_to_32(const struct crypt_op *from, struct crypt_op32 *to)
201 {
202
203         CP(*from, *to, ses);
204         CP(*from, *to, op);
205         CP(*from, *to, flags);
206         CP(*from, *to, len);
207         PTROUT_CP(*from, *to, src);
208         PTROUT_CP(*from, *to, dst);
209         PTROUT_CP(*from, *to, mac);
210         PTROUT_CP(*from, *to, iv);
211 }
212
213 static void
214 crypt_aead_from_32(const struct crypt_aead32 *from, struct crypt_aead *to)
215 {
216
217         CP(*from, *to, ses);
218         CP(*from, *to, op);
219         CP(*from, *to, flags);
220         CP(*from, *to, len);
221         CP(*from, *to, aadlen);
222         CP(*from, *to, ivlen);
223         PTRIN_CP(*from, *to, src);
224         PTRIN_CP(*from, *to, dst);
225         PTRIN_CP(*from, *to, aad);
226         PTRIN_CP(*from, *to, tag);
227         PTRIN_CP(*from, *to, iv);
228 }
229
230 static void
231 crypt_aead_to_32(const struct crypt_aead *from, struct crypt_aead32 *to)
232 {
233
234         CP(*from, *to, ses);
235         CP(*from, *to, op);
236         CP(*from, *to, flags);
237         CP(*from, *to, len);
238         CP(*from, *to, aadlen);
239         CP(*from, *to, ivlen);
240         PTROUT_CP(*from, *to, src);
241         PTROUT_CP(*from, *to, dst);
242         PTROUT_CP(*from, *to, aad);
243         PTROUT_CP(*from, *to, tag);
244         PTROUT_CP(*from, *to, iv);
245 }
246
247 static void
248 crparam_from_32(const struct crparam32 *from, struct crparam *to)
249 {
250
251         PTRIN_CP(*from, *to, crp_p);
252         CP(*from, *to, crp_nbits);
253 }
254
255 static void
256 crparam_to_32(const struct crparam *from, struct crparam32 *to)
257 {
258
259         PTROUT_CP(*from, *to, crp_p);
260         CP(*from, *to, crp_nbits);
261 }
262
263 static void
264 crypt_kop_from_32(const struct crypt_kop32 *from, struct crypt_kop *to)
265 {
266         int i;
267
268         CP(*from, *to, crk_op);
269         CP(*from, *to, crk_status);
270         CP(*from, *to, crk_iparams);
271         CP(*from, *to, crk_oparams);
272         CP(*from, *to, crk_crid);
273         for (i = 0; i < CRK_MAXPARAM; i++)
274                 crparam_from_32(&from->crk_param[i], &to->crk_param[i]);
275 }
276
277 static void
278 crypt_kop_to_32(const struct crypt_kop *from, struct crypt_kop32 *to)
279 {
280         int i;
281
282         CP(*from, *to, crk_op);
283         CP(*from, *to, crk_status);
284         CP(*from, *to, crk_iparams);
285         CP(*from, *to, crk_oparams);
286         CP(*from, *to, crk_crid);
287         for (i = 0; i < CRK_MAXPARAM; i++)
288                 crparam_to_32(&from->crk_param[i], &to->crk_param[i]);
289 }
290 #endif
291
292 static void
293 session2_op_from_op(const struct session_op *from, struct session2_op *to)
294 {
295
296         memset(to, 0, sizeof(*to));
297         memcpy(to, from, sizeof(*from));
298         to->crid = CRYPTOCAP_F_HARDWARE;
299 }
300
301 static void
302 session2_op_to_op(const struct session2_op *from, struct session_op *to)
303 {
304
305         memcpy(to, from, sizeof(*to));
306 }
307
308 struct csession {
309         TAILQ_ENTRY(csession) next;
310         crypto_session_t cses;
311         volatile u_int  refs;
312         uint32_t        ses;
313         struct mtx      lock;           /* for op submission */
314
315         struct enc_xform *txform;
316         int             hashsize;
317         int             ivsize;
318         int             mode;
319
320         void            *key;
321         void            *mackey;
322 };
323
324 struct cryptop_data {
325         struct csession *cse;
326
327         char            *buf;
328         char            *obuf;
329         char            *aad;
330         bool            done;
331 };
332
333 struct fcrypt {
334         TAILQ_HEAD(csessionlist, csession) csessions;
335         int             sesn;
336         struct mtx      lock;
337 };
338
339 static bool use_outputbuffers;
340 SYSCTL_BOOL(_kern_crypto, OID_AUTO, cryptodev_use_output, CTLFLAG_RW,
341     &use_outputbuffers, 0,
342     "Use separate output buffers for /dev/crypto requests.");
343
344 static bool use_separate_aad;
345 SYSCTL_BOOL(_kern_crypto, OID_AUTO, cryptodev_separate_aad, CTLFLAG_RW,
346     &use_separate_aad, 0,
347     "Use separate AAD buffer for /dev/crypto requests.");
348
349 static struct timeval warninterval = { .tv_sec = 60, .tv_usec = 0 };
350 SYSCTL_TIMEVAL_SEC(_kern, OID_AUTO, cryptodev_warn_interval, CTLFLAG_RW,
351     &warninterval,
352     "Delay in seconds between warnings of deprecated /dev/crypto algorithms");
353
354 static int cryptof_ioctl(struct file *, u_long, void *, struct ucred *,
355     struct thread *);
356 static int cryptof_stat(struct file *, struct stat *, struct ucred *,
357     struct thread *);
358 static int cryptof_close(struct file *, struct thread *);
359 static int cryptof_fill_kinfo(struct file *, struct kinfo_file *,
360     struct filedesc *);
361
362 static struct fileops cryptofops = {
363     .fo_read = invfo_rdwr,
364     .fo_write = invfo_rdwr,
365     .fo_truncate = invfo_truncate,
366     .fo_ioctl = cryptof_ioctl,
367     .fo_poll = invfo_poll,
368     .fo_kqfilter = invfo_kqfilter,
369     .fo_stat = cryptof_stat,
370     .fo_close = cryptof_close,
371     .fo_chmod = invfo_chmod,
372     .fo_chown = invfo_chown,
373     .fo_sendfile = invfo_sendfile,
374     .fo_fill_kinfo = cryptof_fill_kinfo,
375 };
376
377 static struct csession *csefind(struct fcrypt *, u_int);
378 static bool csedelete(struct fcrypt *, u_int);
379 static struct csession *csecreate(struct fcrypt *, crypto_session_t,
380     struct crypto_session_params *, struct enc_xform *, void *,
381     struct auth_hash *, void *);
382 static void csefree(struct csession *);
383
384 static int cryptodev_op(struct csession *, const struct crypt_op *,
385     struct ucred *, struct thread *);
386 static int cryptodev_aead(struct csession *, struct crypt_aead *,
387     struct ucred *, struct thread *);
388 static int cryptodev_key(struct crypt_kop *);
389 static int cryptodev_find(struct crypt_find_op *);
390
391 /*
392  * Check a crypto identifier to see if it requested
393  * a software device/driver.  This can be done either
394  * by device name/class or through search constraints.
395  */
396 static int
397 checkforsoftware(int *cridp)
398 {
399         int crid;
400
401         crid = *cridp;
402
403         if (!crypto_devallowsoft) {
404                 if (crid & CRYPTOCAP_F_SOFTWARE) {
405                         if (crid & CRYPTOCAP_F_HARDWARE) {
406                                 *cridp = CRYPTOCAP_F_HARDWARE;
407                                 return 0;
408                         }
409                         return EINVAL;
410                 }
411                 if ((crid & CRYPTOCAP_F_HARDWARE) == 0 &&
412                     (crypto_getcaps(crid) & CRYPTOCAP_F_HARDWARE) == 0)
413                         return EINVAL;
414         }
415         return 0;
416 }
417
418 /* ARGSUSED */
419 static int
420 cryptof_ioctl(struct file *fp, u_long cmd, void *data,
421     struct ucred *active_cred, struct thread *td)
422 {
423         static struct timeval keywarn, featwarn;
424         struct crypto_session_params csp;
425         struct fcrypt *fcr = fp->f_data;
426         struct csession *cse;
427         struct session2_op *sop;
428         struct crypt_op *cop;
429         struct crypt_aead *caead;
430         struct enc_xform *txform = NULL;
431         struct auth_hash *thash = NULL;
432         void *key = NULL;
433         void *mackey = NULL;
434         struct crypt_kop *kop;
435         crypto_session_t cses;
436         uint32_t ses;
437         int error = 0, crid;
438         union {
439                 struct session2_op sopc;
440 #ifdef COMPAT_FREEBSD32
441                 struct crypt_op copc;
442                 struct crypt_aead aeadc;
443                 struct crypt_kop kopc;
444 #endif
445         } thunk;
446 #ifdef COMPAT_FREEBSD32
447         u_long cmd32;
448         void *data32;
449
450         cmd32 = 0;
451         data32 = NULL;
452         switch (cmd) {
453         case CIOCGSESSION32:
454                 cmd32 = cmd;
455                 data32 = data;
456                 cmd = CIOCGSESSION;
457                 data = &thunk.sopc;
458                 session_op_from_32((struct session_op32 *)data32, &thunk.sopc);
459                 break;
460         case CIOCGSESSION232:
461                 cmd32 = cmd;
462                 data32 = data;
463                 cmd = CIOCGSESSION2;
464                 data = &thunk.sopc;
465                 session2_op_from_32((struct session2_op32 *)data32,
466                     &thunk.sopc);
467                 break;
468         case CIOCCRYPT32:
469                 cmd32 = cmd;
470                 data32 = data;
471                 cmd = CIOCCRYPT;
472                 data = &thunk.copc;
473                 crypt_op_from_32((struct crypt_op32 *)data32, &thunk.copc);
474                 break;
475         case CIOCCRYPTAEAD32:
476                 cmd32 = cmd;
477                 data32 = data;
478                 cmd = CIOCCRYPTAEAD;
479                 data = &thunk.aeadc;
480                 crypt_aead_from_32((struct crypt_aead32 *)data32, &thunk.aeadc);
481                 break;
482         case CIOCKEY32:
483         case CIOCKEY232:
484                 cmd32 = cmd;
485                 data32 = data;
486                 if (cmd == CIOCKEY32)
487                         cmd = CIOCKEY;
488                 else
489                         cmd = CIOCKEY2;
490                 data = &thunk.kopc;
491                 crypt_kop_from_32((struct crypt_kop32 *)data32, &thunk.kopc);
492                 break;
493         }
494 #endif
495
496         switch (cmd) {
497         case CIOCGSESSION:
498         case CIOCGSESSION2:
499                 if (cmd == CIOCGSESSION) {
500                         session2_op_from_op(data, &thunk.sopc);
501                         sop = &thunk.sopc;
502                 } else
503                         sop = (struct session2_op *)data;
504
505                 switch (sop->cipher) {
506                 case 0:
507                         break;
508                 case CRYPTO_AES_CBC:
509                         txform = &enc_xform_rijndael128;
510                         break;
511                 case CRYPTO_AES_XTS:
512                         txform = &enc_xform_aes_xts;
513                         break;
514                 case CRYPTO_NULL_CBC:
515                         txform = &enc_xform_null;
516                         break;
517                 case CRYPTO_CAMELLIA_CBC:
518                         txform = &enc_xform_camellia;
519                         break;
520                 case CRYPTO_AES_ICM:
521                         txform = &enc_xform_aes_icm;
522                         break;
523                 case CRYPTO_AES_NIST_GCM_16:
524                         txform = &enc_xform_aes_nist_gcm;
525                         break;
526                 case CRYPTO_CHACHA20:
527                         txform = &enc_xform_chacha20;
528                         break;
529                 case CRYPTO_AES_CCM_16:
530                         txform = &enc_xform_ccm;
531                         break;
532
533                 default:
534                         CRYPTDEB("invalid cipher");
535                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
536                         return (EINVAL);
537                 }
538
539                 switch (sop->mac) {
540                 case 0:
541                         break;
542                 case CRYPTO_POLY1305:
543                         thash = &auth_hash_poly1305;
544                         break;
545                 case CRYPTO_SHA1_HMAC:
546                         thash = &auth_hash_hmac_sha1;
547                         break;
548                 case CRYPTO_SHA2_224_HMAC:
549                         thash = &auth_hash_hmac_sha2_224;
550                         break;
551                 case CRYPTO_SHA2_256_HMAC:
552                         thash = &auth_hash_hmac_sha2_256;
553                         break;
554                 case CRYPTO_SHA2_384_HMAC:
555                         thash = &auth_hash_hmac_sha2_384;
556                         break;
557                 case CRYPTO_SHA2_512_HMAC:
558                         thash = &auth_hash_hmac_sha2_512;
559                         break;
560                 case CRYPTO_RIPEMD160_HMAC:
561                         thash = &auth_hash_hmac_ripemd_160;
562                         break;
563 #ifdef COMPAT_FREEBSD12
564                 case CRYPTO_AES_128_NIST_GMAC:
565                 case CRYPTO_AES_192_NIST_GMAC:
566                 case CRYPTO_AES_256_NIST_GMAC:
567                         /* Should always be paired with GCM. */
568                         if (sop->cipher != CRYPTO_AES_NIST_GCM_16) {
569                                 CRYPTDEB("GMAC without GCM");
570                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
571                                     __LINE__);
572                                 return (EINVAL);
573                         }
574                         break;
575 #endif
576                 case CRYPTO_AES_NIST_GMAC:
577                         switch (sop->mackeylen * 8) {
578                         case 128:
579                                 thash = &auth_hash_nist_gmac_aes_128;
580                                 break;
581                         case 192:
582                                 thash = &auth_hash_nist_gmac_aes_192;
583                                 break;
584                         case 256:
585                                 thash = &auth_hash_nist_gmac_aes_256;
586                                 break;
587                         default:
588                                 CRYPTDEB("invalid GMAC key length");
589                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
590                                     __LINE__);
591                                 return (EINVAL);
592                         }
593                         break;
594                 case CRYPTO_AES_CCM_CBC_MAC:
595                         switch (sop->mackeylen) {
596                         case 16:
597                                 thash = &auth_hash_ccm_cbc_mac_128;
598                                 break;
599                         case 24:
600                                 thash = &auth_hash_ccm_cbc_mac_192;
601                                 break;
602                         case 32:
603                                 thash = &auth_hash_ccm_cbc_mac_256;
604                                 break;
605                         default:
606                                 CRYPTDEB("Invalid CBC MAC key size %d",
607                                     sop->keylen);
608                                 SDT_PROBE1(opencrypto, dev, ioctl,
609                                     error, __LINE__);
610                                 return (EINVAL);
611                         }
612                         break;
613                 case CRYPTO_SHA1:
614                         thash = &auth_hash_sha1;
615                         break;
616                 case CRYPTO_SHA2_224:
617                         thash = &auth_hash_sha2_224;
618                         break;
619                 case CRYPTO_SHA2_256:
620                         thash = &auth_hash_sha2_256;
621                         break;
622                 case CRYPTO_SHA2_384:
623                         thash = &auth_hash_sha2_384;
624                         break;
625                 case CRYPTO_SHA2_512:
626                         thash = &auth_hash_sha2_512;
627                         break;
628
629                 case CRYPTO_NULL_HMAC:
630                         thash = &auth_hash_null;
631                         break;
632
633                 case CRYPTO_BLAKE2B:
634                         thash = &auth_hash_blake2b;
635                         break;
636                 case CRYPTO_BLAKE2S:
637                         thash = &auth_hash_blake2s;
638                         break;
639
640                 default:
641                         CRYPTDEB("invalid mac");
642                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
643                         return (EINVAL);
644                 }
645
646                 if (txform == NULL && thash == NULL) {
647                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
648                         return (EINVAL);
649                 }
650
651                 memset(&csp, 0, sizeof(csp));
652                 if (use_outputbuffers)
653                         csp.csp_flags |= CSP_F_SEPARATE_OUTPUT;
654
655                 if (sop->cipher == CRYPTO_AES_NIST_GCM_16) {
656                         switch (sop->mac) {
657 #ifdef COMPAT_FREEBSD12
658                         case CRYPTO_AES_128_NIST_GMAC:
659                         case CRYPTO_AES_192_NIST_GMAC:
660                         case CRYPTO_AES_256_NIST_GMAC:
661                                 if (sop->keylen != sop->mackeylen) {
662                                         SDT_PROBE1(opencrypto, dev, ioctl,
663                                             error, __LINE__);
664                                         return (EINVAL);
665                                 }
666                                 break;
667 #endif
668                         case 0:
669                                 break;
670                         default:
671                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
672                                     __LINE__);
673                                 return (EINVAL);
674                         }
675                         csp.csp_mode = CSP_MODE_AEAD;
676                 } else if (sop->cipher == CRYPTO_AES_CCM_16) {
677                         switch (sop->mac) {
678 #ifdef COMPAT_FREEBSD12
679                         case CRYPTO_AES_CCM_CBC_MAC:
680                                 if (sop->keylen != sop->mackeylen) {
681                                         SDT_PROBE1(opencrypto, dev, ioctl,
682                                             error, __LINE__);
683                                         return (EINVAL);
684                                 }
685                                 thash = NULL;
686                                 break;
687 #endif
688                         case 0:
689                                 break;
690                         default:
691                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
692                                     __LINE__);
693                                 return (EINVAL);
694                         }
695                         csp.csp_mode = CSP_MODE_AEAD;
696                 } else if (txform && thash)
697                         csp.csp_mode = CSP_MODE_ETA;
698                 else if (txform)
699                         csp.csp_mode = CSP_MODE_CIPHER;
700                 else
701                         csp.csp_mode = CSP_MODE_DIGEST;
702
703                 switch (csp.csp_mode) {
704                 case CSP_MODE_AEAD:
705                 case CSP_MODE_ETA:
706                         if (use_separate_aad)
707                                 csp.csp_flags |= CSP_F_SEPARATE_AAD;
708                         break;
709                 }
710
711                 if (txform) {
712                         csp.csp_cipher_alg = txform->type;
713                         csp.csp_cipher_klen = sop->keylen;
714                         if (sop->keylen > txform->maxkey ||
715                             sop->keylen < txform->minkey) {
716                                 CRYPTDEB("invalid cipher parameters");
717                                 error = EINVAL;
718                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
719                                     __LINE__);
720                                 goto bail;
721                         }
722
723                         key = malloc(csp.csp_cipher_klen, M_XDATA, M_WAITOK);
724                         error = copyin(sop->key, key, csp.csp_cipher_klen);
725                         if (error) {
726                                 CRYPTDEB("invalid key");
727                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
728                                     __LINE__);
729                                 goto bail;
730                         }
731                         csp.csp_cipher_key = key;
732                         csp.csp_ivlen = txform->ivsize;
733                 }
734
735                 if (thash) {
736                         csp.csp_auth_alg = thash->type;
737                         csp.csp_auth_klen = sop->mackeylen;
738                         if (sop->mackeylen > thash->keysize ||
739                             sop->mackeylen < 0) {
740                                 CRYPTDEB("invalid mac key length");
741                                 error = EINVAL;
742                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
743                                     __LINE__);
744                                 goto bail;
745                         }
746
747                         if (csp.csp_auth_klen) {
748                                 mackey = malloc(csp.csp_auth_klen, M_XDATA,
749                                     M_WAITOK);
750                                 error = copyin(sop->mackey, mackey,
751                                     csp.csp_auth_klen);
752                                 if (error) {
753                                         CRYPTDEB("invalid mac key");
754                                         SDT_PROBE1(opencrypto, dev, ioctl,
755                                             error, __LINE__);
756                                         goto bail;
757                                 }
758                                 csp.csp_auth_key = mackey;
759                         }
760
761                         if (csp.csp_auth_alg == CRYPTO_AES_NIST_GMAC)
762                                 csp.csp_ivlen = AES_GCM_IV_LEN;
763                         if (csp.csp_auth_alg == CRYPTO_AES_CCM_CBC_MAC)
764                                 csp.csp_ivlen = AES_CCM_IV_LEN;
765                 }
766
767                 crid = sop->crid;
768                 error = checkforsoftware(&crid);
769                 if (error) {
770                         CRYPTDEB("checkforsoftware");
771                         SDT_PROBE1(opencrypto, dev, ioctl, error,
772                             __LINE__);
773                         goto bail;
774                 }
775                 error = crypto_newsession(&cses, &csp, crid);
776                 if (error) {
777                         CRYPTDEB("crypto_newsession");
778                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
779                         goto bail;
780                 }
781
782                 cse = csecreate(fcr, cses, &csp, txform, key, thash, mackey);
783
784                 if (cse == NULL) {
785                         crypto_freesession(cses);
786                         error = EINVAL;
787                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
788                         CRYPTDEB("csecreate");
789                         goto bail;
790                 }
791                 sop->ses = cse->ses;
792
793                 /* return hardware/driver id */
794                 sop->crid = crypto_ses2hid(cse->cses);
795 bail:
796                 if (error) {
797                         free(key, M_XDATA);
798                         free(mackey, M_XDATA);
799                 }
800
801                 if (cmd == CIOCGSESSION && error == 0)
802                         session2_op_to_op(sop, data);
803                 break;
804         case CIOCFSESSION:
805                 ses = *(uint32_t *)data;
806                 if (!csedelete(fcr, ses)) {
807                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
808                         return (EINVAL);
809                 }
810                 break;
811         case CIOCCRYPT:
812                 cop = (struct crypt_op *)data;
813                 cse = csefind(fcr, cop->ses);
814                 if (cse == NULL) {
815                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
816                         return (EINVAL);
817                 }
818                 error = cryptodev_op(cse, cop, active_cred, td);
819                 csefree(cse);
820                 break;
821         case CIOCKEY:
822         case CIOCKEY2:
823                 if (ratecheck(&keywarn, &warninterval))
824                         gone_in(14,
825                             "Asymmetric crypto operations via /dev/crypto");
826
827                 if (!crypto_userasymcrypto) {
828                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
829                         return (EPERM);         /* XXX compat? */
830                 }
831                 kop = (struct crypt_kop *)data;
832                 if (cmd == CIOCKEY) {
833                         /* NB: crypto core enforces s/w driver use */
834                         kop->crk_crid =
835                             CRYPTOCAP_F_HARDWARE | CRYPTOCAP_F_SOFTWARE;
836                 }
837                 mtx_lock(&Giant);
838                 error = cryptodev_key(kop);
839                 mtx_unlock(&Giant);
840                 break;
841         case CIOCASYMFEAT:
842                 if (ratecheck(&featwarn, &warninterval))
843                         gone_in(14,
844                             "Asymmetric crypto features via /dev/crypto");
845
846                 if (!crypto_userasymcrypto) {
847                         /*
848                          * NB: if user asym crypto operations are
849                          * not permitted return "no algorithms"
850                          * so well-behaved applications will just
851                          * fallback to doing them in software.
852                          */
853                         *(int *)data = 0;
854                 } else {
855                         error = crypto_getfeat((int *)data);
856                         if (error)
857                                 SDT_PROBE1(opencrypto, dev, ioctl, error,
858                                     __LINE__);
859                 }
860                 break;
861         case CIOCFINDDEV:
862                 error = cryptodev_find((struct crypt_find_op *)data);
863                 break;
864         case CIOCCRYPTAEAD:
865                 caead = (struct crypt_aead *)data;
866                 cse = csefind(fcr, caead->ses);
867                 if (cse == NULL) {
868                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
869                         return (EINVAL);
870                 }
871                 error = cryptodev_aead(cse, caead, active_cred, td);
872                 csefree(cse);
873                 break;
874         default:
875                 error = EINVAL;
876                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
877                 break;
878         }
879
880 #ifdef COMPAT_FREEBSD32
881         switch (cmd32) {
882         case CIOCGSESSION32:
883                 if (error == 0)
884                         session_op_to_32(data, data32);
885                 break;
886         case CIOCGSESSION232:
887                 if (error == 0)
888                         session2_op_to_32(data, data32);
889                 break;
890         case CIOCCRYPT32:
891                 if (error == 0)
892                         crypt_op_to_32(data, data32);
893                 break;
894         case CIOCCRYPTAEAD32:
895                 if (error == 0)
896                         crypt_aead_to_32(data, data32);
897                 break;
898         case CIOCKEY32:
899         case CIOCKEY232:
900                 crypt_kop_to_32(data, data32);
901                 break;
902         }
903 #endif
904         return (error);
905 }
906
907 static struct cryptop_data *
908 cod_alloc(struct csession *cse, size_t aad_len, size_t len, struct thread *td)
909 {
910         struct cryptop_data *cod;
911
912         cod = malloc(sizeof(struct cryptop_data), M_XDATA, M_WAITOK | M_ZERO);
913
914         cod->cse = cse;
915         if (crypto_get_params(cse->cses)->csp_flags & CSP_F_SEPARATE_AAD) {
916                 if (aad_len != 0)
917                         cod->aad = malloc(aad_len, M_XDATA, M_WAITOK);
918                 cod->buf = malloc(len, M_XDATA, M_WAITOK);
919         } else
920                 cod->buf = malloc(aad_len + len, M_XDATA, M_WAITOK);
921         if (crypto_get_params(cse->cses)->csp_flags & CSP_F_SEPARATE_OUTPUT)
922                 cod->obuf = malloc(len, M_XDATA, M_WAITOK);
923         return (cod);
924 }
925
926 static void
927 cod_free(struct cryptop_data *cod)
928 {
929
930         free(cod->aad, M_XDATA);
931         free(cod->obuf, M_XDATA);
932         free(cod->buf, M_XDATA);
933         free(cod, M_XDATA);
934 }
935
936 static int
937 cryptodev_cb(struct cryptop *crp)
938 {
939         struct cryptop_data *cod = crp->crp_opaque;
940
941         /*
942          * Lock to ensure the wakeup() is not missed by the loops
943          * waiting on cod->done in cryptodev_op() and
944          * cryptodev_aead().
945          */
946         mtx_lock(&cod->cse->lock);
947         cod->done = true;
948         mtx_unlock(&cod->cse->lock);
949         wakeup(cod);
950         return (0);
951 }
952
953 static int
954 cryptodev_op(struct csession *cse, const struct crypt_op *cop,
955     struct ucred *active_cred, struct thread *td)
956 {
957         struct cryptop_data *cod = NULL;
958         struct cryptop *crp = NULL;
959         char *dst;
960         int error;
961
962         if (cop->len > 256*1024-4) {
963                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
964                 return (E2BIG);
965         }
966
967         if (cse->txform) {
968                 if (cop->len == 0 || (cop->len % cse->txform->blocksize) != 0) {
969                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
970                         return (EINVAL);
971                 }
972         }
973
974         if (cop->mac && cse->hashsize == 0) {
975                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
976                 return (EINVAL);
977         }
978
979         /*
980          * The COP_F_CIPHER_FIRST flag predates explicit session
981          * modes, but the only way it was used was for EtA so allow it
982          * as long as it is consistent with EtA.
983          */
984         if (cop->flags & COP_F_CIPHER_FIRST) {
985                 if (cop->op != COP_ENCRYPT) {
986                         SDT_PROBE1(opencrypto, dev, ioctl, error,  __LINE__);
987                         return (EINVAL);
988                 }
989         }
990
991         cod = cod_alloc(cse, 0, cop->len + cse->hashsize, td);
992         dst = cop->dst;
993
994         crp = crypto_getreq(cse->cses, M_WAITOK);
995
996         error = copyin(cop->src, cod->buf, cop->len);
997         if (error) {
998                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
999                 goto bail;
1000         }
1001         crp->crp_payload_start = 0;
1002         crp->crp_payload_length = cop->len;
1003         if (cse->hashsize)
1004                 crp->crp_digest_start = cop->len;
1005
1006         switch (cse->mode) {
1007         case CSP_MODE_COMPRESS:
1008                 switch (cop->op) {
1009                 case COP_ENCRYPT:
1010                         crp->crp_op = CRYPTO_OP_COMPRESS;
1011                         break;
1012                 case COP_DECRYPT:
1013                         crp->crp_op = CRYPTO_OP_DECOMPRESS;
1014                         break;
1015                 default:
1016                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1017                         error = EINVAL;
1018                         goto bail;
1019                 }
1020                 break;
1021         case CSP_MODE_CIPHER:
1022                 switch (cop->op) {
1023                 case COP_ENCRYPT:
1024                         crp->crp_op = CRYPTO_OP_ENCRYPT;
1025                         break;
1026                 case COP_DECRYPT:
1027                         crp->crp_op = CRYPTO_OP_DECRYPT;
1028                         break;
1029                 default:
1030                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1031                         error = EINVAL;
1032                         goto bail;
1033                 }
1034                 break;
1035         case CSP_MODE_DIGEST:
1036                 switch (cop->op) {
1037                 case 0:
1038                 case COP_ENCRYPT:
1039                 case COP_DECRYPT:
1040                         crp->crp_op = CRYPTO_OP_COMPUTE_DIGEST;
1041                         if (cod->obuf != NULL)
1042                                 crp->crp_digest_start = 0;
1043                         break;
1044                 default:
1045                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1046                         error = EINVAL;
1047                         goto bail;
1048                 }
1049                 break;
1050         case CSP_MODE_ETA:
1051                 switch (cop->op) {
1052                 case COP_ENCRYPT:
1053                         crp->crp_op = CRYPTO_OP_ENCRYPT |
1054                             CRYPTO_OP_COMPUTE_DIGEST;
1055                         break;
1056                 case COP_DECRYPT:
1057                         crp->crp_op = CRYPTO_OP_DECRYPT |
1058                             CRYPTO_OP_VERIFY_DIGEST;
1059                         break;
1060                 default:
1061                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1062                         error = EINVAL;
1063                         goto bail;
1064                 }
1065                 break;
1066         default:
1067                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1068                 error = EINVAL;
1069                 goto bail;
1070         }
1071
1072         crp->crp_flags = CRYPTO_F_CBIMM | (cop->flags & COP_F_BATCH);
1073         crypto_use_buf(crp, cod->buf, cop->len + cse->hashsize);
1074         if (cod->obuf)
1075                 crypto_use_output_buf(crp, cod->obuf, cop->len + cse->hashsize);
1076         crp->crp_callback = cryptodev_cb;
1077         crp->crp_opaque = cod;
1078
1079         if (cop->iv) {
1080                 if (cse->ivsize == 0) {
1081                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1082                         error = EINVAL;
1083                         goto bail;
1084                 }
1085                 error = copyin(cop->iv, crp->crp_iv, cse->ivsize);
1086                 if (error) {
1087                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1088                         goto bail;
1089                 }
1090                 crp->crp_flags |= CRYPTO_F_IV_SEPARATE;
1091         } else if (cse->ivsize != 0) {
1092                 crp->crp_iv_start = 0;
1093                 crp->crp_payload_start += cse->ivsize;
1094                 crp->crp_payload_length -= cse->ivsize;
1095                 dst += cse->ivsize;
1096         }
1097
1098         if (cop->mac != NULL && crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) {
1099                 error = copyin(cop->mac, cod->buf + crp->crp_digest_start,
1100                     cse->hashsize);
1101                 if (error) {
1102                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1103                         goto bail;
1104                 }
1105         }
1106 again:
1107         /*
1108          * Let the dispatch run unlocked, then, interlock against the
1109          * callback before checking if the operation completed and going
1110          * to sleep.  This insures drivers don't inherit our lock which
1111          * results in a lock order reversal between crypto_dispatch forced
1112          * entry and the crypto_done callback into us.
1113          */
1114         error = crypto_dispatch(crp);
1115         if (error != 0) {
1116                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1117                 goto bail;
1118         }
1119
1120         mtx_lock(&cse->lock);
1121         while (!cod->done)
1122                 mtx_sleep(cod, &cse->lock, PWAIT, "crydev", 0);
1123         mtx_unlock(&cse->lock);
1124
1125         if (crp->crp_etype == EAGAIN) {
1126                 crp->crp_etype = 0;
1127                 crp->crp_flags &= ~CRYPTO_F_DONE;
1128                 cod->done = false;
1129                 goto again;
1130         }
1131
1132         if (crp->crp_etype != 0) {
1133                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1134                 error = crp->crp_etype;
1135                 goto bail;
1136         }
1137
1138         if (cop->dst != NULL) {
1139                 error = copyout(cod->obuf != NULL ? cod->obuf :
1140                     cod->buf + crp->crp_payload_start, dst,
1141                     crp->crp_payload_length);
1142                 if (error) {
1143                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1144                         goto bail;
1145                 }
1146         }
1147
1148         if (cop->mac != NULL && (crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) == 0) {
1149                 error = copyout((cod->obuf != NULL ? cod->obuf : cod->buf) +
1150                     crp->crp_digest_start, cop->mac, cse->hashsize);
1151                 if (error) {
1152                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1153                         goto bail;
1154                 }
1155         }
1156
1157 bail:
1158         crypto_freereq(crp);
1159         cod_free(cod);
1160
1161         return (error);
1162 }
1163
1164 static int
1165 cryptodev_aead(struct csession *cse, struct crypt_aead *caead,
1166     struct ucred *active_cred, struct thread *td)
1167 {
1168         struct cryptop_data *cod = NULL;
1169         struct cryptop *crp = NULL;
1170         char *dst;
1171         int error;
1172
1173         if (caead->len > 256*1024-4 || caead->aadlen > 256*1024-4) {
1174                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1175                 return (E2BIG);
1176         }
1177
1178         if (cse->txform == NULL || cse->hashsize == 0 || caead->tag == NULL ||
1179             (caead->len % cse->txform->blocksize) != 0) {
1180                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1181                 return (EINVAL);
1182         }
1183
1184         /*
1185          * The COP_F_CIPHER_FIRST flag predates explicit session
1186          * modes, but the only way it was used was for EtA so allow it
1187          * as long as it is consistent with EtA.
1188          */
1189         if (caead->flags & COP_F_CIPHER_FIRST) {
1190                 if (caead->op != COP_ENCRYPT) {
1191                         SDT_PROBE1(opencrypto, dev, ioctl, error,  __LINE__);
1192                         return (EINVAL);
1193                 }
1194         }
1195
1196         cod = cod_alloc(cse, caead->aadlen, caead->len + cse->hashsize, td);
1197         dst = caead->dst;
1198
1199         crp = crypto_getreq(cse->cses, M_WAITOK);
1200
1201         if (cod->aad != NULL)
1202                 error = copyin(caead->aad, cod->aad, caead->aadlen);
1203         else
1204                 error = copyin(caead->aad, cod->buf, caead->aadlen);
1205         if (error) {
1206                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1207                 goto bail;
1208         }
1209         crp->crp_aad = cod->aad;
1210         crp->crp_aad_start = 0;
1211         crp->crp_aad_length = caead->aadlen;
1212
1213         if (cod->aad != NULL)
1214                 crp->crp_payload_start = 0;
1215         else
1216                 crp->crp_payload_start = caead->aadlen;
1217         error = copyin(caead->src, cod->buf + crp->crp_payload_start,
1218             caead->len);
1219         if (error) {
1220                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1221                 goto bail;
1222         }
1223         crp->crp_payload_length = caead->len;
1224         if (caead->op == COP_ENCRYPT && cod->obuf != NULL)
1225                 crp->crp_digest_start = crp->crp_payload_output_start +
1226                     caead->len;
1227         else
1228                 crp->crp_digest_start = crp->crp_payload_start + caead->len;
1229
1230         switch (cse->mode) {
1231         case CSP_MODE_AEAD:
1232         case CSP_MODE_ETA:
1233                 switch (caead->op) {
1234                 case COP_ENCRYPT:
1235                         crp->crp_op = CRYPTO_OP_ENCRYPT |
1236                             CRYPTO_OP_COMPUTE_DIGEST;
1237                         break;
1238                 case COP_DECRYPT:
1239                         crp->crp_op = CRYPTO_OP_DECRYPT |
1240                             CRYPTO_OP_VERIFY_DIGEST;
1241                         break;
1242                 default:
1243                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1244                         error = EINVAL;
1245                         goto bail;
1246                 }
1247                 break;
1248         default:
1249                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1250                 error = EINVAL;
1251                 goto bail;
1252         }
1253
1254         crp->crp_flags = CRYPTO_F_CBIMM | (caead->flags & COP_F_BATCH);
1255         crypto_use_buf(crp, cod->buf, crp->crp_payload_start + caead->len +
1256             cse->hashsize);
1257         if (cod->obuf != NULL)
1258                 crypto_use_output_buf(crp, cod->obuf, caead->len +
1259                     cse->hashsize);
1260         crp->crp_callback = cryptodev_cb;
1261         crp->crp_opaque = cod;
1262
1263         if (caead->iv) {
1264                 /*
1265                  * Permit a 16-byte IV for AES-XTS, but only use the
1266                  * first 8 bytes as a block number.
1267                  */
1268                 if (cse->mode == CSP_MODE_ETA &&
1269                     caead->ivlen == AES_BLOCK_LEN &&
1270                     cse->ivsize == AES_XTS_IV_LEN)
1271                         caead->ivlen = AES_XTS_IV_LEN;
1272
1273                 if (caead->ivlen != cse->ivsize) {
1274                         error = EINVAL;
1275                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1276                         goto bail;
1277                 }
1278
1279                 error = copyin(caead->iv, crp->crp_iv, cse->ivsize);
1280                 if (error) {
1281                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1282                         goto bail;
1283                 }
1284                 crp->crp_flags |= CRYPTO_F_IV_SEPARATE;
1285         } else {
1286                 crp->crp_iv_start = crp->crp_payload_start;
1287                 crp->crp_payload_start += cse->ivsize;
1288                 crp->crp_payload_length -= cse->ivsize;
1289                 dst += cse->ivsize;
1290         }
1291
1292         if (crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) {
1293                 error = copyin(caead->tag, cod->buf + crp->crp_digest_start,
1294                     cse->hashsize);
1295                 if (error) {
1296                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1297                         goto bail;
1298                 }
1299         }
1300 again:
1301         /*
1302          * Let the dispatch run unlocked, then, interlock against the
1303          * callback before checking if the operation completed and going
1304          * to sleep.  This insures drivers don't inherit our lock which
1305          * results in a lock order reversal between crypto_dispatch forced
1306          * entry and the crypto_done callback into us.
1307          */
1308         error = crypto_dispatch(crp);
1309         if (error != 0) {
1310                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1311                 goto bail;
1312         }
1313
1314         mtx_lock(&cse->lock);
1315         while (!cod->done)
1316                 mtx_sleep(cod, &cse->lock, PWAIT, "crydev", 0);
1317         mtx_unlock(&cse->lock);
1318
1319         if (crp->crp_etype == EAGAIN) {
1320                 crp->crp_etype = 0;
1321                 crp->crp_flags &= ~CRYPTO_F_DONE;
1322                 cod->done = false;
1323                 goto again;
1324         }
1325
1326         if (crp->crp_etype != 0) {
1327                 error = crp->crp_etype;
1328                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1329                 goto bail;
1330         }
1331
1332         if (caead->dst != NULL) {
1333                 error = copyout(cod->obuf != NULL ? cod->obuf :
1334                     cod->buf + crp->crp_payload_start, dst,
1335                     crp->crp_payload_length);
1336                 if (error) {
1337                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1338                         goto bail;
1339                 }
1340         }
1341
1342         if ((crp->crp_op & CRYPTO_OP_VERIFY_DIGEST) == 0) {
1343                 error = copyout((cod->obuf != NULL ? cod->obuf : cod->buf) +
1344                     crp->crp_digest_start, caead->tag, cse->hashsize);
1345                 if (error) {
1346                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1347                         goto bail;
1348                 }
1349         }
1350
1351 bail:
1352         crypto_freereq(crp);
1353         cod_free(cod);
1354
1355         return (error);
1356 }
1357
1358 static void
1359 cryptodevkey_cb(struct cryptkop *krp)
1360 {
1361
1362         wakeup_one(krp);
1363 }
1364
1365 static int
1366 cryptodev_key(struct crypt_kop *kop)
1367 {
1368         struct cryptkop *krp = NULL;
1369         int error = EINVAL;
1370         int in, out, size, i;
1371
1372         if (kop->crk_iparams + kop->crk_oparams > CRK_MAXPARAM) {
1373                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1374                 return (EFBIG);
1375         }
1376
1377         in = kop->crk_iparams;
1378         out = kop->crk_oparams;
1379         switch (kop->crk_op) {
1380         case CRK_MOD_EXP:
1381                 if (in == 3 && out == 1)
1382                         break;
1383                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1384                 return (EINVAL);
1385         case CRK_MOD_EXP_CRT:
1386                 if (in == 6 && out == 1)
1387                         break;
1388                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1389                 return (EINVAL);
1390         case CRK_DSA_SIGN:
1391                 if (in == 5 && out == 2)
1392                         break;
1393                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1394                 return (EINVAL);
1395         case CRK_DSA_VERIFY:
1396                 if (in == 7 && out == 0)
1397                         break;
1398                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1399                 return (EINVAL);
1400         case CRK_DH_COMPUTE_KEY:
1401                 if (in == 3 && out == 1)
1402                         break;
1403                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1404                 return (EINVAL);
1405         default:
1406                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1407                 return (EINVAL);
1408         }
1409
1410         krp = malloc(sizeof(*krp), M_XDATA, M_WAITOK | M_ZERO);
1411         krp->krp_op = kop->crk_op;
1412         krp->krp_status = kop->crk_status;
1413         krp->krp_iparams = kop->crk_iparams;
1414         krp->krp_oparams = kop->crk_oparams;
1415         krp->krp_crid = kop->crk_crid;
1416         krp->krp_status = 0;
1417         krp->krp_callback = cryptodevkey_cb;
1418
1419         for (i = 0; i < CRK_MAXPARAM; i++) {
1420                 if (kop->crk_param[i].crp_nbits > 65536) {
1421                         /* Limit is the same as in OpenBSD */
1422                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1423                         goto fail;
1424                 }
1425                 krp->krp_param[i].crp_nbits = kop->crk_param[i].crp_nbits;
1426         }
1427         for (i = 0; i < krp->krp_iparams + krp->krp_oparams; i++) {
1428                 size = (krp->krp_param[i].crp_nbits + 7) / 8;
1429                 if (size == 0)
1430                         continue;
1431                 krp->krp_param[i].crp_p = malloc(size, M_XDATA, M_WAITOK);
1432                 if (i >= krp->krp_iparams)
1433                         continue;
1434                 error = copyin(kop->crk_param[i].crp_p, krp->krp_param[i].crp_p, size);
1435                 if (error) {
1436                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1437                         goto fail;
1438                 }
1439         }
1440
1441         error = crypto_kdispatch(krp);
1442         if (error) {
1443                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1444                 goto fail;
1445         }
1446         error = tsleep(krp, PSOCK, "crydev", 0);
1447         if (error) {
1448                 /* XXX can this happen?  if so, how do we recover? */
1449                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1450                 goto fail;
1451         }
1452         
1453         kop->crk_crid = krp->krp_hid;           /* device that did the work */
1454         if (krp->krp_status != 0) {
1455                 error = krp->krp_status;
1456                 SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1457                 goto fail;
1458         }
1459
1460         for (i = krp->krp_iparams; i < krp->krp_iparams + krp->krp_oparams; i++) {
1461                 size = (krp->krp_param[i].crp_nbits + 7) / 8;
1462                 if (size == 0)
1463                         continue;
1464                 error = copyout(krp->krp_param[i].crp_p, kop->crk_param[i].crp_p, size);
1465                 if (error) {
1466                         SDT_PROBE1(opencrypto, dev, ioctl, error, __LINE__);
1467                         goto fail;
1468                 }
1469         }
1470
1471 fail:
1472         if (krp) {
1473                 kop->crk_status = krp->krp_status;
1474                 for (i = 0; i < CRK_MAXPARAM; i++) {
1475                         if (krp->krp_param[i].crp_p)
1476                                 free(krp->krp_param[i].crp_p, M_XDATA);
1477                 }
1478                 free(krp, M_XDATA);
1479         }
1480         return (error);
1481 }
1482
1483 static int
1484 cryptodev_find(struct crypt_find_op *find)
1485 {
1486         device_t dev;
1487         size_t fnlen = sizeof find->name;
1488
1489         if (find->crid != -1) {
1490                 dev = crypto_find_device_byhid(find->crid);
1491                 if (dev == NULL)
1492                         return (ENOENT);
1493                 strncpy(find->name, device_get_nameunit(dev), fnlen);
1494                 find->name[fnlen - 1] = '\x0';
1495         } else {
1496                 find->name[fnlen - 1] = '\x0';
1497                 find->crid = crypto_find_driver(find->name);
1498                 if (find->crid == -1)
1499                         return (ENOENT);
1500         }
1501         return (0);
1502 }
1503
1504 /* ARGSUSED */
1505 static int
1506 cryptof_stat(struct file *fp, struct stat *sb, struct ucred *active_cred,
1507     struct thread *td)
1508 {
1509
1510         return (EOPNOTSUPP);
1511 }
1512
1513 /* ARGSUSED */
1514 static int
1515 cryptof_close(struct file *fp, struct thread *td)
1516 {
1517         struct fcrypt *fcr = fp->f_data;
1518         struct csession *cse;
1519
1520         while ((cse = TAILQ_FIRST(&fcr->csessions))) {
1521                 TAILQ_REMOVE(&fcr->csessions, cse, next);
1522                 KASSERT(cse->refs == 1,
1523                     ("%s: crypto session %p with %d refs", __func__, cse,
1524                     cse->refs));
1525                 csefree(cse);
1526         }
1527         free(fcr, M_XDATA);
1528         fp->f_data = NULL;
1529         return 0;
1530 }
1531
1532 static int
1533 cryptof_fill_kinfo(struct file *fp, struct kinfo_file *kif,
1534     struct filedesc *fdp)
1535 {
1536
1537         kif->kf_type = KF_TYPE_CRYPTO;
1538         return (0);
1539 }
1540
1541 static struct csession *
1542 csefind(struct fcrypt *fcr, u_int ses)
1543 {
1544         struct csession *cse;
1545
1546         mtx_lock(&fcr->lock);
1547         TAILQ_FOREACH(cse, &fcr->csessions, next) {
1548                 if (cse->ses == ses) {
1549                         refcount_acquire(&cse->refs);
1550                         mtx_unlock(&fcr->lock);
1551                         return (cse);
1552                 }
1553         }
1554         mtx_unlock(&fcr->lock);
1555         return (NULL);
1556 }
1557
1558 static bool
1559 csedelete(struct fcrypt *fcr, u_int ses)
1560 {
1561         struct csession *cse;
1562
1563         mtx_lock(&fcr->lock);
1564         TAILQ_FOREACH(cse, &fcr->csessions, next) {
1565                 if (cse->ses == ses) {
1566                         TAILQ_REMOVE(&fcr->csessions, cse, next);
1567                         mtx_unlock(&fcr->lock);
1568                         csefree(cse);
1569                         return (true);
1570                 }
1571         }
1572         mtx_unlock(&fcr->lock);
1573         return (false);
1574 }
1575         
1576 struct csession *
1577 csecreate(struct fcrypt *fcr, crypto_session_t cses,
1578     struct crypto_session_params *csp, struct enc_xform *txform,
1579     void *key, struct auth_hash *thash, void *mackey)
1580 {
1581         struct csession *cse;
1582
1583         cse = malloc(sizeof(struct csession), M_XDATA, M_NOWAIT | M_ZERO);
1584         if (cse == NULL)
1585                 return NULL;
1586         mtx_init(&cse->lock, "cryptodev", "crypto session lock", MTX_DEF);
1587         refcount_init(&cse->refs, 1);
1588         cse->key = key;
1589         cse->mackey = mackey;
1590         cse->mode = csp->csp_mode;
1591         cse->cses = cses;
1592         cse->txform = txform;
1593         if (thash != NULL)
1594                 cse->hashsize = thash->hashsize;
1595         else if (csp->csp_cipher_alg == CRYPTO_AES_NIST_GCM_16)
1596                 cse->hashsize = AES_GMAC_HASH_LEN;
1597         else if (csp->csp_cipher_alg == CRYPTO_AES_CCM_16)
1598                 cse->hashsize = AES_CBC_MAC_HASH_LEN;
1599         cse->ivsize = csp->csp_ivlen;
1600         mtx_lock(&fcr->lock);
1601         TAILQ_INSERT_TAIL(&fcr->csessions, cse, next);
1602         cse->ses = fcr->sesn++;
1603         mtx_unlock(&fcr->lock);
1604         return (cse);
1605 }
1606
1607 static void
1608 csefree(struct csession *cse)
1609 {
1610
1611         if (!refcount_release(&cse->refs))
1612                 return;
1613         crypto_freesession(cse->cses);
1614         mtx_destroy(&cse->lock);
1615         if (cse->key)
1616                 free(cse->key, M_XDATA);
1617         if (cse->mackey)
1618                 free(cse->mackey, M_XDATA);
1619         free(cse, M_XDATA);
1620 }
1621
1622 static int
1623 cryptoioctl(struct cdev *dev, u_long cmd, caddr_t data, int flag,
1624     struct thread *td)
1625 {
1626         struct file *f;
1627         struct fcrypt *fcr;
1628         int fd, error;
1629
1630         switch (cmd) {
1631         case CRIOGET:
1632                 error = falloc_noinstall(td, &f);
1633                 if (error)
1634                         break;
1635
1636                 fcr = malloc(sizeof(struct fcrypt), M_XDATA, M_WAITOK | M_ZERO);
1637                 TAILQ_INIT(&fcr->csessions);
1638                 mtx_init(&fcr->lock, "fcrypt", NULL, MTX_DEF);
1639
1640                 finit(f, FREAD | FWRITE, DTYPE_CRYPTO, fcr, &cryptofops);
1641                 error = finstall(td, f, &fd, 0, NULL);
1642                 if (error) {
1643                         mtx_destroy(&fcr->lock);
1644                         free(fcr, M_XDATA);
1645                 } else
1646                         *(uint32_t *)data = fd;
1647                 fdrop(f, td);
1648                 break;
1649         case CRIOFINDDEV:
1650                 error = cryptodev_find((struct crypt_find_op *)data);
1651                 break;
1652         case CRIOASYMFEAT:
1653                 error = crypto_getfeat((int *)data);
1654                 break;
1655         default:
1656                 error = EINVAL;
1657                 break;
1658         }
1659         return (error);
1660 }
1661
1662 static struct cdevsw crypto_cdevsw = {
1663         .d_version =    D_VERSION,
1664         .d_ioctl =      cryptoioctl,
1665         .d_name =       "crypto",
1666 };
1667 static struct cdev *crypto_dev;
1668
1669 /*
1670  * Initialization code, both for static and dynamic loading.
1671  */
1672 static int
1673 cryptodev_modevent(module_t mod, int type, void *unused)
1674 {
1675         switch (type) {
1676         case MOD_LOAD:
1677                 if (bootverbose)
1678                         printf("crypto: <crypto device>\n");
1679                 crypto_dev = make_dev(&crypto_cdevsw, 0, 
1680                                       UID_ROOT, GID_WHEEL, 0666,
1681                                       "crypto");
1682                 return 0;
1683         case MOD_UNLOAD:
1684                 /*XXX disallow if active sessions */
1685                 destroy_dev(crypto_dev);
1686                 return 0;
1687         }
1688         return EINVAL;
1689 }
1690
1691 static moduledata_t cryptodev_mod = {
1692         "cryptodev",
1693         cryptodev_modevent,
1694         0
1695 };
1696 MODULE_VERSION(cryptodev, 1);
1697 DECLARE_MODULE(cryptodev, cryptodev_mod, SI_SUB_PSEUDO, SI_ORDER_ANY);
1698 MODULE_DEPEND(cryptodev, crypto, 1, 1, 1);
1699 MODULE_DEPEND(cryptodev, zlib, 1, 1, 1);