]> git.lizzy.rs Git - plan9front.git/blob - sys/src/9/ppc/devtls.c
kernel: move duplicated random.c to port
[plan9front.git] / sys / src / 9 / ppc / devtls.c
1 /*
2  *  devtls - record layer for transport layer security 1.0 and secure sockets layer 3.0
3  */
4 #include        "u.h"
5 #include        "../port/lib.h"
6 #include        "mem.h"
7 #include        "dat.h"
8 #include        "fns.h"
9 #include        "../port/error.h"
10
11 #include        <libsec.h>
12
13 typedef struct OneWay   OneWay;
14 typedef struct Secret           Secret;
15 typedef struct TlsRec   TlsRec;
16 typedef struct TlsErrs  TlsErrs;
17
18 enum {
19         Statlen=        1024,           /* max. length of status or stats message */
20         /* buffer limits */
21         MaxRecLen               = 1<<14,        /* max payload length of a record layer message */
22         MaxCipherRecLen = MaxRecLen + 2048,
23         RecHdrLen               = 5,
24         MaxMacLen               = SHA1dlen,
25
26         /* protocol versions we can accept */
27         TLSVersion              = 0x0301,
28         SSL3Version             = 0x0300,
29         ProtocolVersion = 0x0301,       /* maximum version we speak */
30         MinProtoVersion = 0x0300,       /* limits on version we accept */
31         MaxProtoVersion = 0x03ff,
32
33         /* connection states */
34         SHandshake      = 1 << 0,       /* doing handshake */
35         SOpen           = 1 << 1,       /* application data can be sent */
36         SRClose         = 1 << 2,       /* remote side has closed down */
37         SLClose         = 1 << 3,       /* sent a close notify alert */
38         SAlert          = 1 << 5,       /* sending or sent a fatal alert */
39         SError          = 1 << 6,       /* some sort of error has occured */
40         SClosed         = 1 << 7,       /* it is all over */
41
42         /* record types */
43         RChangeCipherSpec = 20,
44         RAlert,
45         RHandshake,
46         RApplication,
47
48         SSL2ClientHello = 1,
49         HSSL2ClientHello = 9,  /* local convention;  see tlshand.c */
50
51         /* alerts */
52         ECloseNotify                    = 0,
53         EUnexpectedMessage      = 10,
54         EBadRecordMac           = 20,
55         EDecryptionFailed               = 21,
56         ERecordOverflow                 = 22,
57         EDecompressionFailure   = 30,
58         EHandshakeFailure               = 40,
59         ENoCertificate                  = 41,
60         EBadCertificate                 = 42,
61         EUnsupportedCertificate         = 43,
62         ECertificateRevoked             = 44,
63         ECertificateExpired             = 45,
64         ECertificateUnknown     = 46,
65         EIllegalParameter               = 47,
66         EUnknownCa                      = 48,
67         EAccessDenied           = 49,
68         EDecodeError                    = 50,
69         EDecryptError                   = 51,
70         EExportRestriction              = 60,
71         EProtocolVersion                = 70,
72         EInsufficientSecurity   = 71,
73         EInternalError                  = 80,
74         EUserCanceled                   = 90,
75         ENoRenegotiation                = 100,
76
77         EMAX = 256
78 };
79
80 struct Secret
81 {
82         char            *encalg;        /* name of encryption alg */
83         char            *hashalg;       /* name of hash alg */
84         int             (*enc)(Secret*, uchar*, int);
85         int             (*dec)(Secret*, uchar*, int);
86         int             (*unpad)(uchar*, int, int);
87         DigestState     *(*mac)(uchar*, ulong, uchar*, ulong, uchar*, DigestState*);
88         int             block;          /* encryption block len, 0 if none */
89         int             maclen;
90         void            *enckey;
91         uchar   mackey[MaxMacLen];
92 };
93
94 struct OneWay
95 {
96         QLock           io;             /* locks io access */
97         QLock           seclock;        /* locks secret paramaters */
98         ulong           seq;
99         Secret          *sec;           /* cipher in use */
100         Secret          *new;           /* cipher waiting for enable */
101 };
102
103 struct TlsRec
104 {
105         Chan    *c;                             /* io channel */
106         int             ref;                            /* serialized by tdlock for atomic destroy */
107         int             version;                        /* version of the protocol we are speaking */
108         char            verset;                 /* version has been set */
109         char            opened;                 /* opened command every issued? */
110         char            err[ERRMAX];            /* error message to return to handshake requests */
111         vlong   handin;                 /* bytes communicated by the record layer */
112         vlong   handout;
113         vlong   datain;
114         vlong   dataout;
115
116         Lock            statelk;
117         int             state;
118
119         /* record layer mac functions for different protocol versions */
120         void            (*packMac)(Secret*, uchar*, uchar*, uchar*, uchar*, int, uchar*);
121
122         /* input side -- protected by in.io */
123         OneWay          in;
124         Block           *processed;     /* next bunch of application data */
125         Block           *unprocessed;   /* data read from c but not parsed into records */
126
127         /* handshake queue */
128         Lock            hqlock;                 /* protects hqref, alloc & free of handq, hprocessed */
129         int             hqref;
130         Queue           *handq;         /* queue of handshake messages */
131         Block           *hprocessed;    /* remainder of last block read from handq */
132         QLock           hqread;         /* protects reads for hprocessed, handq */
133
134         /* output side */
135         OneWay          out;
136
137         /* protections */
138         char            *user;
139         int             perm;
140 };
141
142 struct TlsErrs{
143         int     err;
144         int     sslerr;
145         int     tlserr;
146         int     fatal;
147         char    *msg;
148 };
149
150 static TlsErrs tlserrs[] = {
151         {ECloseNotify,                  ECloseNotify,                   ECloseNotify,                   0,      "close notify"},
152         {EUnexpectedMessage,    EUnexpectedMessage,     EUnexpectedMessage,     1, "unexpected message"},
153         {EBadRecordMac,         EBadRecordMac,          EBadRecordMac,          1, "bad record mac"},
154         {EDecryptionFailed,             EIllegalParameter,              EDecryptionFailed,              1, "decryption failed"},
155         {ERecordOverflow,               EIllegalParameter,              ERecordOverflow,                1, "record too long"},
156         {EDecompressionFailure, EDecompressionFailure,  EDecompressionFailure,  1, "decompression failed"},
157         {EHandshakeFailure,             EHandshakeFailure,              EHandshakeFailure,              1, "could not negotiate acceptable security paramters"},
158         {ENoCertificate,                ENoCertificate,                 ECertificateUnknown,    1, "no appropriate certificate available"},
159         {EBadCertificate,               EBadCertificate,                EBadCertificate,                1, "corrupted or invalid certificate"},
160         {EUnsupportedCertificate,       EUnsupportedCertificate,        EUnsupportedCertificate,        1, "unsupported certificate type"},
161         {ECertificateRevoked,   ECertificateRevoked,            ECertificateRevoked,            1, "revoked certificate"},
162         {ECertificateExpired,           ECertificateExpired,            ECertificateExpired,            1, "expired certificate"},
163         {ECertificateUnknown,   ECertificateUnknown,    ECertificateUnknown,    1, "unacceptable certificate"},
164         {EIllegalParameter,             EIllegalParameter,              EIllegalParameter,              1, "illegal parameter"},
165         {EUnknownCa,                    EHandshakeFailure,              EUnknownCa,                     1, "unknown certificate authority"},
166         {EAccessDenied,         EHandshakeFailure,              EAccessDenied,          1, "access denied"},
167         {EDecodeError,                  EIllegalParameter,              EDecodeError,                   1, "error decoding message"},
168         {EDecryptError,                 EIllegalParameter,              EDecryptError,                  1, "error decrypting message"},
169         {EExportRestriction,            EHandshakeFailure,              EExportRestriction,             1, "export restriction violated"},
170         {EProtocolVersion,              EIllegalParameter,              EProtocolVersion,               1, "protocol version not supported"},
171         {EInsufficientSecurity, EHandshakeFailure,              EInsufficientSecurity,  1, "stronger security routines required"},
172         {EInternalError,                        EHandshakeFailure,              EInternalError,                 1, "internal error"},
173         {EUserCanceled,         ECloseNotify,                   EUserCanceled,                  0, "handshake canceled by user"},
174         {ENoRenegotiation,              EUnexpectedMessage,     ENoRenegotiation,               0, "no renegotiation"},
175 };
176
177 enum
178 {
179         /* max. open tls connections */
180         MaxTlsDevs      = 1024
181 };
182
183 static  Lock    tdlock;
184 static  int     tdhiwat;
185 static  int     maxtlsdevs = 128;
186 static  TlsRec  **tlsdevs;
187 static  char    **trnames;
188 static  char    *encalgs;
189 static  char    *hashalgs;
190
191 enum{
192         Qtopdir         = 1,    /* top level directory */
193         Qprotodir,
194         Qclonus,
195         Qencalgs,
196         Qhashalgs,
197         Qconvdir,               /* directory for a conversation */
198         Qdata,
199         Qctl,
200         Qhand,
201         Qstatus,
202         Qstats,
203 };
204
205 #define TYPE(x)         ((x).path & 0xf)
206 #define CONV(x)         (((x).path >> 5)&(MaxTlsDevs-1))
207 #define QID(c, y)       (((c)<<5) | (y))
208
209 static void     checkstate(TlsRec *, int, int);
210 static void     ensure(TlsRec*, Block**, int);
211 static void     consume(Block**, uchar*, int);
212 static Chan*    buftochan(char*);
213 static void     tlshangup(TlsRec*);
214 static void     tlsError(TlsRec*, char *);
215 static void     alertHand(TlsRec*, char *);
216 static TlsRec   *newtls(Chan *c);
217 static TlsRec   *mktlsrec(void);
218 static DigestState*sslmac_md5(uchar *p, ulong len, uchar *key, ulong klen, uchar *digest, DigestState *s);
219 static DigestState*sslmac_sha1(uchar *p, ulong len, uchar *key, ulong klen, uchar *digest, DigestState *s);
220 static DigestState*nomac(uchar *p, ulong len, uchar *key, ulong klen, uchar *digest, DigestState *s);
221 static void     sslPackMac(Secret *sec, uchar *mackey, uchar *seq, uchar *header, uchar *body, int len, uchar *mac);
222 static void     tlsPackMac(Secret *sec, uchar *mackey, uchar *seq, uchar *header, uchar *body, int len, uchar *mac);
223 static void     put64(uchar *p, vlong x);
224 static void     put32(uchar *p, u32int);
225 static void     put24(uchar *p, int);
226 static void     put16(uchar *p, int);
227 static u32int   get32(uchar *p);
228 static int      get16(uchar *p);
229 static void     tlsSetState(TlsRec *tr, int new, int old);
230 static void     rcvAlert(TlsRec *tr, int err);
231 static void     sendAlert(TlsRec *tr, int err);
232 static void     rcvError(TlsRec *tr, int err, char *msg, ...);
233 static int      rc4enc(Secret *sec, uchar *buf, int n);
234 static int      des3enc(Secret *sec, uchar *buf, int n);
235 static int      des3dec(Secret *sec, uchar *buf, int n);
236 static int      noenc(Secret *sec, uchar *buf, int n);
237 static int      sslunpad(uchar *buf, int n, int block);
238 static int      tlsunpad(uchar *buf, int n, int block);
239 static void     freeSec(Secret *sec);
240 static char     *tlsstate(int s);
241
242 #pragma varargck        argpos  rcvError        3
243
244 static char *tlsnames[] = {
245 [Qclonus]               "clone",
246 [Qencalgs]      "encalgs",
247 [Qhashalgs]     "hashalgs",
248 [Qdata]         "data",
249 [Qctl]          "ctl",
250 [Qhand]         "hand",
251 [Qstatus]               "status",
252 [Qstats]                "stats",
253 };
254
255 static int convdir[] = { Qctl, Qdata, Qhand, Qstatus, Qstats };
256
257 static int
258 tlsgen(Chan *c, char*, Dirtab *, int, int s, Dir *dp)
259 {
260         Qid q;
261         TlsRec *tr;
262         char *name, *nm;
263         int perm, t;
264
265         q.vers = 0;
266         q.type = QTFILE;
267
268         t = TYPE(c->qid);
269         switch(t) {
270         case Qtopdir:
271                 if(s == DEVDOTDOT){
272                         q.path = QID(0, Qtopdir);
273                         q.type = QTDIR;
274                         devdir(c, q, "#a", 0, eve, 0555, dp);
275                         return 1;
276                 }
277                 if(s > 0)
278                         return -1;
279                 q.path = QID(0, Qprotodir);
280                 q.type = QTDIR;
281                 devdir(c, q, "tls", 0, eve, 0555, dp);
282                 return 1;
283         case Qprotodir:
284                 if(s == DEVDOTDOT){
285                         q.path = QID(0, Qtopdir);
286                         q.type = QTDIR;
287                         devdir(c, q, ".", 0, eve, 0555, dp);
288                         return 1;
289                 }
290                 if(s < 3){
291                         switch(s) {
292                         default:
293                                 return -1;
294                         case 0:
295                                 q.path = QID(0, Qclonus);
296                                 break;
297                         case 1:
298                                 q.path = QID(0, Qencalgs);
299                                 break;
300                         case 2:
301                                 q.path = QID(0, Qhashalgs);
302                                 break;
303                         }
304                         perm = 0444;
305                         if(TYPE(q) == Qclonus)
306                                 perm = 0555;
307                         devdir(c, q, tlsnames[TYPE(q)], 0, eve, perm, dp);
308                         return 1;
309                 }
310                 s -= 3;
311                 if(s >= tdhiwat)
312                         return -1;
313                 q.path = QID(s, Qconvdir);
314                 q.type = QTDIR;
315                 lock(&tdlock);
316                 tr = tlsdevs[s];
317                 if(tr != nil)
318                         nm = tr->user;
319                 else
320                         nm = eve;
321                 if((name = trnames[s]) == nil) {
322                         name = trnames[s] = smalloc(16);
323                         sprint(name, "%d", s);
324                 }
325                 devdir(c, q, name, 0, nm, 0555, dp);
326                 unlock(&tdlock);
327                 return 1;
328         case Qconvdir:
329                 if(s == DEVDOTDOT){
330                         q.path = QID(0, Qprotodir);
331                         q.type = QTDIR;
332                         devdir(c, q, "tls", 0, eve, 0555, dp);
333                         return 1;
334                 }
335                 if(s < 0 || s >= nelem(convdir))
336                         return -1;
337                 lock(&tdlock);
338                 tr = tlsdevs[CONV(c->qid)];
339                 if(tr != nil){
340                         nm = tr->user;
341                         perm = tr->perm;
342                 }else{
343                         perm = 0;
344                         nm = eve;
345                 }
346                 t = convdir[s];
347                 if(t == Qstatus || t == Qstats)
348                         perm &= 0444;
349                 q.path = QID(CONV(c->qid), t);
350                 devdir(c, q, tlsnames[t], 0, nm, perm, dp);
351                 unlock(&tdlock);
352                 return 1;
353         case Qclonus:
354         case Qencalgs:
355         case Qhashalgs:
356                 perm = 0444;
357                 if(t == Qclonus)
358                         perm = 0555;
359                 devdir(c, c->qid, tlsnames[t], 0, eve, perm, dp);
360                 return 1;
361         default:
362                 lock(&tdlock);
363                 tr = tlsdevs[CONV(c->qid)];
364                 if(tr != nil){
365                         nm = tr->user;
366                         perm = tr->perm;
367                 }else{
368                         perm = 0;
369                         nm = eve;
370                 }
371                 if(t == Qstatus || t == Qstats)
372                         perm &= 0444;
373                 devdir(c, c->qid, tlsnames[t], 0, nm, perm, dp);
374                 unlock(&tdlock);
375                 return 1;
376         }
377         return -1;
378 }
379
380 static Chan*
381 tlsattach(char *spec)
382 {
383         Chan *c;
384
385         c = devattach('a', spec);
386         c->qid.path = QID(0, Qtopdir);
387         c->qid.type = QTDIR;
388         c->qid.vers = 0;
389         return c;
390 }
391
392 static Walkqid*
393 tlswalk(Chan *c, Chan *nc, char **name, int nname)
394 {
395         return devwalk(c, nc, name, nname, nil, 0, tlsgen);
396 }
397
398 static int
399 tlsstat(Chan *c, uchar *db, int n)
400 {
401         return devstat(c, db, n, nil, 0, tlsgen);
402 }
403
404 static Chan*
405 tlsopen(Chan *c, int omode)
406 {
407         TlsRec *tr, **pp;
408         int t, perm;
409
410         perm = 0;
411         omode &= 3;
412         switch(omode) {
413         case OREAD:
414                 perm = 4;
415                 break;
416         case OWRITE:
417                 perm = 2;
418                 break;
419         case ORDWR:
420                 perm = 6;
421                 break;
422         }
423
424         t = TYPE(c->qid);
425         switch(t) {
426         default:
427                 panic("tlsopen");
428         case Qtopdir:
429         case Qprotodir:
430         case Qconvdir:
431                 if(omode != OREAD)
432                         error(Eperm);
433                 break;
434         case Qclonus:
435                 tr = newtls(c);
436                 if(tr == nil)
437                         error(Enodev);
438                 break;
439         case Qctl:
440         case Qdata:
441         case Qhand:
442         case Qstatus:
443         case Qstats:
444                 if((t == Qstatus || t == Qstats) && omode != OREAD)
445                         error(Eperm);
446                 if(waserror()) {
447                         unlock(&tdlock);
448                         nexterror();
449                 }
450                 lock(&tdlock);
451                 pp = &tlsdevs[CONV(c->qid)];
452                 tr = *pp;
453                 if(tr == nil)
454                         error("must open connection using clone");
455                 if((perm & (tr->perm>>6)) != perm
456                 && (strcmp(up->user, tr->user) != 0
457                     || (perm & tr->perm) != perm))
458                         error(Eperm);
459                 if(t == Qhand){
460                         if(waserror()){
461                                 unlock(&tr->hqlock);
462                                 nexterror();
463                         }
464                         lock(&tr->hqlock);
465                         if(tr->handq != nil)
466                                 error(Einuse);
467                         tr->handq = qopen(2 * MaxCipherRecLen, 0, nil, nil);
468                         if(tr->handq == nil)
469                                 error("can't allocate handshake queue");
470                         tr->hqref = 1;
471                         unlock(&tr->hqlock);
472                         poperror();
473                 }
474                 tr->ref++;
475                 unlock(&tdlock);
476                 poperror();
477                 break;
478         case Qencalgs:
479         case Qhashalgs:
480                 if(omode != OREAD)
481                         error(Eperm);
482                 break;
483         }
484         c->mode = openmode(omode);
485         c->flag |= COPEN;
486         c->offset = 0;
487         c->iounit = qiomaxatomic;
488         return c;
489 }
490
491 static int
492 tlswstat(Chan *c, uchar *dp, int n)
493 {
494         Dir *d;
495         TlsRec *tr;
496         int rv;
497
498         d = nil;
499         if(waserror()){
500                 free(d);
501                 unlock(&tdlock);
502                 nexterror();
503         }
504
505         lock(&tdlock);
506         tr = tlsdevs[CONV(c->qid)];
507         if(tr == nil)
508                 error(Ebadusefd);
509         if(strcmp(tr->user, up->user) != 0)
510                 error(Eperm);
511
512         d = smalloc(n + sizeof *d);
513         rv = convM2D(dp, n, &d[0], (char*) &d[1]);
514         if(rv == 0)
515                 error(Eshortstat);
516         if(!emptystr(d->uid))
517                 kstrdup(&tr->user, d->uid);
518         if(d->mode != ~0UL)
519                 tr->perm = d->mode;
520
521         free(d);
522         poperror();
523         unlock(&tdlock);
524
525         return rv;
526 }
527
528 static void
529 dechandq(TlsRec *tr)
530 {
531         lock(&tr->hqlock);
532         if(--tr->hqref == 0){
533                 if(tr->handq != nil){
534                         qfree(tr->handq);
535                         tr->handq = nil;
536                 }
537                 if(tr->hprocessed != nil){
538                         freeb(tr->hprocessed);
539                         tr->hprocessed = nil;
540                 }
541         }
542         unlock(&tr->hqlock);
543 }
544
545 static void
546 tlsclose(Chan *c)
547 {
548         TlsRec *tr;
549         int t;
550
551         t = TYPE(c->qid);
552         switch(t) {
553         case Qctl:
554         case Qdata:
555         case Qhand:
556         case Qstatus:
557         case Qstats:
558                 if((c->flag & COPEN) == 0)
559                         break;
560
561                 tr = tlsdevs[CONV(c->qid)];
562                 if(tr == nil)
563                         break;
564
565                 if(t == Qhand)
566                         dechandq(tr);
567
568                 lock(&tdlock);
569                 if(--tr->ref > 0) {
570                         unlock(&tdlock);
571                         return;
572                 }
573                 tlsdevs[CONV(c->qid)] = nil;
574                 unlock(&tdlock);
575
576                 if(tr->c != nil && !waserror()){
577                         checkstate(tr, 0, SOpen|SHandshake|SRClose);
578                         sendAlert(tr, ECloseNotify);
579                         poperror();
580                 }
581                 tlshangup(tr);
582                 if(tr->c != nil)
583                         cclose(tr->c);
584                 freeSec(tr->in.sec);
585                 freeSec(tr->in.new);
586                 freeSec(tr->out.sec);
587                 freeSec(tr->out.new);
588                 free(tr->user);
589                 free(tr);
590                 break;
591         }
592 }
593
594 /*
595  *  make sure we have at least 'n' bytes in list 'l'
596  */
597 static void
598 ensure(TlsRec *s, Block **l, int n)
599 {
600         int sofar, i;
601         Block *b, *bl;
602
603         sofar = 0;
604         for(b = *l; b; b = b->next){
605                 sofar += BLEN(b);
606                 if(sofar >= n)
607                         return;
608                 l = &b->next;
609         }
610
611         while(sofar < n){
612                 bl = devtab[s->c->type]->bread(s->c, MaxCipherRecLen + RecHdrLen, 0);
613                 if(bl == 0)
614                         error(Ehungup);
615                 *l = bl;
616                 i = 0;
617                 for(b = bl; b; b = b->next){
618                         i += BLEN(b);
619                         l = &b->next;
620                 }
621                 if(i == 0)
622                         error(Ehungup);
623                 sofar += i;
624         }
625 }
626
627 /*
628  *  copy 'n' bytes from 'l' into 'p' and free
629  *  the bytes in 'l'
630  */
631 static void
632 consume(Block **l, uchar *p, int n)
633 {
634         Block *b;
635         int i;
636
637         for(; *l && n > 0; n -= i){
638                 b = *l;
639                 i = BLEN(b);
640                 if(i > n)
641                         i = n;
642                 memmove(p, b->rp, i);
643                 b->rp += i;
644                 p += i;
645                 if(BLEN(b) < 0)
646                         panic("consume");
647                 if(BLEN(b))
648                         break;
649                 *l = b->next;
650                 freeb(b);
651         }
652 }
653
654 /*
655  *  give back n bytes
656  */
657 static void
658 regurgitate(TlsRec *s, uchar *p, int n)
659 {
660         Block *b;
661
662         if(n <= 0)
663                 return;
664         b = s->unprocessed;
665         if(s->unprocessed == nil || b->rp - b->base < n) {
666                 b = allocb(n);
667                 memmove(b->wp, p, n);
668                 b->wp += n;
669                 b->next = s->unprocessed;
670                 s->unprocessed = b;
671         } else {
672                 b->rp -= n;
673                 memmove(b->rp, p, n);
674         }
675 }
676
677 /*
678  *  remove at most n bytes from the queue
679  */
680 static Block*
681 qgrab(Block **l, int n)
682 {
683         Block *bb, *b;
684         int i;
685
686         b = *l;
687         if(BLEN(b) == n){
688                 *l = b->next;
689                 b->next = nil;
690                 return b;
691         }
692
693         i = 0;
694         for(bb = b; bb != nil && i < n; bb = bb->next)
695                 i += BLEN(bb);
696         if(i > n)
697                 i = n;
698
699         bb = allocb(i);
700         consume(l, bb->wp, i);
701         bb->wp += i;
702         return bb;
703 }
704
705 static void
706 tlsclosed(TlsRec *tr, int new)
707 {
708         lock(&tr->statelk);
709         if(tr->state == SOpen || tr->state == SHandshake)
710                 tr->state = new;
711         else if((new | tr->state) == (SRClose|SLClose))
712                 tr->state = SClosed;
713         unlock(&tr->statelk);
714         alertHand(tr, "close notify");
715 }
716
717 /*
718  *  read and process one tls record layer message
719  *  must be called with tr->in.io held
720  *  We can't let Eintrs lose data, since doing so will get
721  *  us out of sync with the sender and break the reliablity
722  *  of the channel.  Eintr only happens during the reads in
723  *  consume.  Therefore we put back any bytes consumed before
724  *  the last call to ensure.
725  */
726 static void
727 tlsrecread(TlsRec *tr)
728 {
729         OneWay *volatile in;
730         Block *volatile b;
731         uchar *p, seq[8], header[RecHdrLen], hmac[MD5dlen];
732         int volatile nconsumed;
733         int len, type, ver, unpad_len;
734
735         nconsumed = 0;
736         if(waserror()){
737                 if(strcmp(up->errstr, Eintr) == 0 && !waserror()){
738                         regurgitate(tr, header, nconsumed);
739                         poperror();
740                 }else
741                         tlsError(tr, "channel error");
742                 nexterror();
743         }
744         ensure(tr, &tr->unprocessed, RecHdrLen);
745         consume(&tr->unprocessed, header, RecHdrLen);
746         nconsumed = RecHdrLen;
747
748         if((tr->handin == 0) && (header[0] & 0x80)){
749                 /* Cope with an SSL3 ClientHello expressed in SSL2 record format.
750                         This is sent by some clients that we must interoperate
751                         with, such as Java's JSSE and Microsoft's Internet Explorer. */
752                 len = (get16(header) & ~0x8000) - 3;
753                 type = header[2];
754                 ver = get16(header + 3);
755                 if(type != SSL2ClientHello || len < 22)
756                         rcvError(tr, EProtocolVersion, "invalid initial SSL2-like message");
757         }else{  /* normal SSL3 record format */
758                 type = header[0];
759                 ver = get16(header+1);
760                 len = get16(header+3);
761         }
762         if(ver != tr->version && (tr->verset || ver < MinProtoVersion || ver > MaxProtoVersion))
763                 rcvError(tr, EProtocolVersion, "devtls expected ver=%x%s, saw (len=%d) type=%x ver=%x '%.12s'",
764                         tr->version, tr->verset?"/set":"", len, type, ver, (char*)header);
765         if(len > MaxCipherRecLen || len < 0)
766                 rcvError(tr, ERecordOverflow, "record message too long %d", len);
767         ensure(tr, &tr->unprocessed, len);
768         nconsumed = 0;
769         poperror();
770
771         /*
772          * If an Eintr happens after this, we'll get out of sync.
773          * Make sure nothing we call can sleep.
774          * Errors are ok, as they kill the connection.
775          * Luckily, allocb won't sleep, it'll just error out.
776          */
777         b = nil;
778         if(waserror()){
779                 if(b != nil)
780                         freeb(b);
781                 tlsError(tr, "channel error");
782                 nexterror();
783         }
784         b = qgrab(&tr->unprocessed, len);
785
786         in = &tr->in;
787         if(waserror()){
788                 qunlock(&in->seclock);
789                 nexterror();
790         }
791         qlock(&in->seclock);
792         p = b->rp;
793         if(in->sec != nil) {
794                 /* to avoid Canvel-Hiltgen-Vaudenay-Vuagnoux attack, all errors here
795                         should look alike, including timing of the response. */
796                 unpad_len = (*in->sec->dec)(in->sec, p, len);
797                 if(unpad_len > in->sec->maclen)
798                         len = unpad_len - in->sec->maclen;
799
800                 /* update length */
801                 put16(header+3, len);
802                 put64(seq, in->seq);
803                 in->seq++;
804                 (*tr->packMac)(in->sec, in->sec->mackey, seq, header, p, len, hmac);
805                 if(unpad_len <= in->sec->maclen || memcmp(hmac, p+len, in->sec->maclen) != 0)
806                         rcvError(tr, EBadRecordMac, "record mac mismatch");
807                 b->wp = b->rp + len;
808         }
809         qunlock(&in->seclock);
810         poperror();
811         if(len <= 0)
812                 rcvError(tr, EDecodeError, "runt record message");
813
814         switch(type) {
815         default:
816                 rcvError(tr, EIllegalParameter, "invalid record message 0x%x", type);
817                 break;
818         case RChangeCipherSpec:
819                 if(len != 1 || p[0] != 1)
820                         rcvError(tr, EDecodeError, "invalid change cipher spec");
821                 qlock(&in->seclock);
822                 if(in->new == nil){
823                         qunlock(&in->seclock);
824                         rcvError(tr, EUnexpectedMessage, "unexpected change cipher spec");
825                 }
826                 freeSec(in->sec);
827                 in->sec = in->new;
828                 in->new = nil;
829                 in->seq = 0;
830                 qunlock(&in->seclock);
831                 break;
832         case RAlert:
833                 if(len != 2)
834                         rcvError(tr, EDecodeError, "invalid alert");
835                 if(p[0] == 2)
836                         rcvAlert(tr, p[1]);
837                 if(p[0] != 1)
838                         rcvError(tr, EIllegalParameter, "invalid alert fatal code");
839
840                 /*
841                  * propate non-fatal alerts to handshaker
842                  */
843                 if(p[1] == ECloseNotify) {
844                         tlsclosed(tr, SRClose);
845                         if(tr->opened)
846                                 error("tls hungup");
847                         error("close notify");
848                 }
849                 if(p[1] == ENoRenegotiation)
850                         alertHand(tr, "no renegotiation");
851                 else if(p[1] == EUserCanceled)
852                         alertHand(tr, "handshake canceled by user");
853                 else
854                         rcvError(tr, EIllegalParameter, "invalid alert code");
855                 break;
856         case RHandshake:
857                 /*
858                  * don't worry about dropping the block
859                  * qbwrite always queues even if flow controlled and interrupted.
860                  *
861                  * if there isn't any handshaker, ignore the request,
862                  * but notify the other side we are doing so.
863                  */
864                 lock(&tr->hqlock);
865                 if(tr->handq != nil){
866                         tr->hqref++;
867                         unlock(&tr->hqlock);
868                         if(waserror()){
869                                 dechandq(tr);
870                                 nexterror();
871                         }
872                         b = padblock(b, 1);
873                         *b->rp = RHandshake;
874                         qbwrite(tr->handq, b);
875                         b = nil;
876                         poperror();
877                         dechandq(tr);
878                 }else{
879                         unlock(&tr->hqlock);
880                         if(tr->verset && tr->version != SSL3Version && !waserror()){
881                                 sendAlert(tr, ENoRenegotiation);
882                                 poperror();
883                         }
884                 }
885                 break;
886         case SSL2ClientHello:
887                 lock(&tr->hqlock);
888                 if(tr->handq != nil){
889                         tr->hqref++;
890                         unlock(&tr->hqlock);
891                         if(waserror()){
892                                 dechandq(tr);
893                                 nexterror();
894                         }
895                         /* Pass the SSL2 format data, so that the handshake code can compute
896                                 the correct checksums.  HSSL2ClientHello = HandshakeType 9 is
897                                 unused in RFC2246. */
898                         b = padblock(b, 8);
899                         b->rp[0] = RHandshake;
900                         b->rp[1] = HSSL2ClientHello;
901                         put24(&b->rp[2], len+3);
902                         b->rp[5] = SSL2ClientHello;
903                         put16(&b->rp[6], ver);
904                         qbwrite(tr->handq, b);
905                         b = nil;
906                         poperror();
907                         dechandq(tr);
908                 }else{
909                         unlock(&tr->hqlock);
910                         if(tr->verset && tr->version != SSL3Version && !waserror()){
911                                 sendAlert(tr, ENoRenegotiation);
912                                 poperror();
913                         }
914                 }
915                 break;
916         case RApplication:
917                 if(!tr->opened)
918                         rcvError(tr, EUnexpectedMessage, "application message received before handshake completed");
919                 tr->processed = b;
920                 b = nil;
921                 break;
922         }
923         if(b != nil)
924                 freeb(b);
925         poperror();
926 }
927
928 /*
929  * got a fatal alert message
930  */
931 static void
932 rcvAlert(TlsRec *tr, int err)
933 {
934         char *s;
935         int i;
936
937         s = "unknown error";
938         for(i=0; i < nelem(tlserrs); i++){
939                 if(tlserrs[i].err == err){
940                         s = tlserrs[i].msg;
941                         break;
942                 }
943         }
944
945         tlsError(tr, s);
946         if(!tr->opened)
947                 error(s);
948         error("tls error");
949 }
950
951 /*
952  * found an error while decoding the input stream
953  */
954 static void
955 rcvError(TlsRec *tr, int err, char *fmt, ...)
956 {
957         char msg[ERRMAX];
958         va_list arg;
959
960         va_start(arg, fmt);
961         vseprint(msg, msg+sizeof(msg), fmt, arg);
962         va_end(arg);
963
964         sendAlert(tr, err);
965
966         if(!tr->opened)
967                 error(msg);
968         error("tls error");
969 }
970
971 /*
972  * make sure the next hand operation returns with a 'msg' error
973  */
974 static void
975 alertHand(TlsRec *tr, char *msg)
976 {
977         Block *b;
978         int n;
979
980         lock(&tr->hqlock);
981         if(tr->handq == nil){
982                 unlock(&tr->hqlock);
983                 return;
984         }
985         tr->hqref++;
986         unlock(&tr->hqlock);
987
988         n = strlen(msg);
989         if(waserror()){
990                 dechandq(tr);
991                 nexterror();
992         }
993         b = allocb(n + 2);
994         *b->wp++ = RAlert;
995         memmove(b->wp, msg, n + 1);
996         b->wp += n + 1;
997
998         qbwrite(tr->handq, b);
999
1000         poperror();
1001         dechandq(tr);
1002 }
1003
1004 static void
1005 checkstate(TlsRec *tr, int ishand, int ok)
1006 {
1007         int state;
1008
1009         lock(&tr->statelk);
1010         state = tr->state;
1011         unlock(&tr->statelk);
1012         if(state & ok)
1013                 return;
1014         switch(state){
1015         case SHandshake:
1016         case SOpen:
1017                 break;
1018         case SError:
1019         case SAlert:
1020                 if(ishand)
1021                         error(tr->err);
1022                 error("tls error");
1023         case SRClose:
1024         case SLClose:
1025         case SClosed:
1026                 error("tls hungup");
1027         }
1028         error("tls improperly configured");
1029 }
1030
1031 static Block*
1032 tlsbread(Chan *c, long n, ulong offset)
1033 {
1034         int ty;
1035         Block *b;
1036         TlsRec *volatile tr;
1037
1038         ty = TYPE(c->qid);
1039         switch(ty) {
1040         default:
1041                 return devbread(c, n, offset);
1042         case Qhand:
1043         case Qdata:
1044                 break;
1045         }
1046
1047         tr = tlsdevs[CONV(c->qid)];
1048         if(tr == nil)
1049                 panic("tlsbread");
1050
1051         if(waserror()){
1052                 qunlock(&tr->in.io);
1053                 nexterror();
1054         }
1055         qlock(&tr->in.io);
1056         if(ty == Qdata){
1057                 checkstate(tr, 0, SOpen);
1058                 while(tr->processed == nil)
1059                         tlsrecread(tr);
1060
1061                 /* return at most what was asked for */
1062                 b = qgrab(&tr->processed, n);
1063                 qunlock(&tr->in.io);
1064                 poperror();
1065                 tr->datain += BLEN(b);
1066         }else{
1067                 checkstate(tr, 1, SOpen|SHandshake|SLClose);
1068
1069                 /*
1070                  * it's ok to look at state without the lock
1071                  * since it only protects reading records,
1072                  * and we have that tr->in.io held.
1073                  */
1074                 while(!tr->opened && tr->hprocessed == nil && !qcanread(tr->handq))
1075                         tlsrecread(tr);
1076
1077                 qunlock(&tr->in.io);
1078                 poperror();
1079
1080                 if(waserror()){
1081                         qunlock(&tr->hqread);
1082                         nexterror();
1083                 }
1084                 qlock(&tr->hqread);
1085                 if(tr->hprocessed == nil){
1086                         b = qbread(tr->handq, MaxRecLen + 1);
1087                         if(*b->rp++ == RAlert){
1088                                 strecpy(up->errstr, up->errstr+ERRMAX, (char*)b->rp);
1089                                 freeb(b);
1090                                 nexterror();
1091                         }
1092                         tr->hprocessed = b;
1093                 }
1094                 b = qgrab(&tr->hprocessed, n);
1095                 poperror();
1096                 qunlock(&tr->hqread);
1097                 tr->handin += BLEN(b);
1098         }
1099
1100         return b;
1101 }
1102
1103 static long
1104 tlsread(Chan *c, void *a, long n, vlong off)
1105 {
1106         Block *volatile b;
1107         Block *nb;
1108         uchar *va;
1109         int i, ty;
1110         char *buf, *s, *e;
1111         ulong offset = off;
1112         TlsRec * tr;
1113
1114         if(c->qid.type & QTDIR)
1115                 return devdirread(c, a, n, 0, 0, tlsgen);
1116
1117         tr = tlsdevs[CONV(c->qid)];
1118         ty = TYPE(c->qid);
1119         switch(ty) {
1120         default:
1121                 error(Ebadusefd);
1122         case Qstatus:
1123                 buf = smalloc(Statlen);
1124                 qlock(&tr->in.seclock);
1125                 qlock(&tr->out.seclock);
1126                 s = buf;
1127                 e = buf + Statlen;
1128                 s = seprint(s, e, "State: %s\n", tlsstate(tr->state));
1129                 s = seprint(s, e, "Version: 0x%x\n", tr->version);
1130                 if(tr->in.sec != nil)
1131                         s = seprint(s, e, "EncIn: %s\nHashIn: %s\n", tr->in.sec->encalg, tr->in.sec->hashalg);
1132                 if(tr->in.new != nil)
1133                         s = seprint(s, e, "NewEncIn: %s\nNewHashIn: %s\n", tr->in.new->encalg, tr->in.new->hashalg);
1134                 if(tr->out.sec != nil)
1135                         s = seprint(s, e, "EncOut: %s\nHashOut: %s\n", tr->out.sec->encalg, tr->out.sec->hashalg);
1136                 if(tr->out.new != nil)
1137                         seprint(s, e, "NewEncOut: %s\nNewHashOut: %s\n", tr->out.new->encalg, tr->out.new->hashalg);
1138                 qunlock(&tr->in.seclock);
1139                 qunlock(&tr->out.seclock);
1140                 n = readstr(offset, a, n, buf);
1141                 free(buf);
1142                 return n;
1143         case Qstats:
1144                 buf = smalloc(Statlen);
1145                 s = buf;
1146                 e = buf + Statlen;
1147                 s = seprint(s, e, "DataIn: %lld\n", tr->datain);
1148                 s = seprint(s, e, "DataOut: %lld\n", tr->dataout);
1149                 s = seprint(s, e, "HandIn: %lld\n", tr->handin);
1150                 seprint(s, e, "HandOut: %lld\n", tr->handout);
1151                 n = readstr(offset, a, n, buf);
1152                 free(buf);
1153                 return n;
1154         case Qctl:
1155                 buf = smalloc(Statlen);
1156                 snprint(buf, Statlen, "%llud", CONV(c->qid));
1157                 n = readstr(offset, a, n, buf);
1158                 free(buf);
1159                 return n;
1160         case Qdata:
1161         case Qhand:
1162                 b = tlsbread(c, n, offset);
1163                 break;
1164         case Qencalgs:
1165                 return readstr(offset, a, n, encalgs);
1166         case Qhashalgs:
1167                 return readstr(offset, a, n, hashalgs);
1168         }
1169
1170         if(waserror()){
1171                 freeblist(b);
1172                 nexterror();
1173         }
1174
1175         n = 0;
1176         va = a;
1177         for(nb = b; nb; nb = nb->next){
1178                 i = BLEN(nb);
1179                 memmove(va+n, nb->rp, i);
1180                 n += i;
1181         }
1182
1183         freeblist(b);
1184         poperror();
1185
1186         return n;
1187 }
1188
1189 /*
1190  *  write a block in tls records
1191  */
1192 static void
1193 tlsrecwrite(TlsRec *tr, int type, Block *b)
1194 {
1195         Block *volatile bb;
1196         Block *nb;
1197         uchar *p, seq[8];
1198         OneWay *volatile out;
1199         int n, maclen, pad, ok;
1200
1201         out = &tr->out;
1202         bb = b;
1203         if(waserror()){
1204                 qunlock(&out->io);
1205                 if(bb != nil)
1206                         freeb(bb);
1207                 nexterror();
1208         }
1209         qlock(&out->io);
1210
1211         ok = SHandshake|SOpen|SRClose;
1212         if(type == RAlert)
1213                 ok |= SAlert;
1214         while(bb != nil){
1215                 checkstate(tr, type != RApplication, ok);
1216
1217                 /*
1218                  * get at most one maximal record's input,
1219                  * with padding on the front for header and
1220                  * back for mac and maximal block padding.
1221                  */
1222                 if(waserror()){
1223                         qunlock(&out->seclock);
1224                         nexterror();
1225                 }
1226                 qlock(&out->seclock);
1227                 maclen = 0;
1228                 pad = 0;
1229                 if(out->sec != nil){
1230                         maclen = out->sec->maclen;
1231                         pad = maclen + out->sec->block;
1232                 }
1233                 n = BLEN(bb);
1234                 if(n > MaxRecLen){
1235                         n = MaxRecLen;
1236                         nb = allocb(n + pad + RecHdrLen);
1237                         memmove(nb->wp + RecHdrLen, bb->rp, n);
1238                         bb->rp += n;
1239                 }else{
1240                         /*
1241                          * carefully reuse bb so it will get freed if we're out of memory
1242                          */
1243                         bb = padblock(bb, RecHdrLen);
1244                         if(pad)
1245                                 nb = padblock(bb, -pad);
1246                         else
1247                                 nb = bb;
1248                         bb = nil;
1249                 }
1250
1251                 p = nb->rp;
1252                 p[0] = type;
1253                 put16(p+1, tr->version);
1254                 put16(p+3, n);
1255
1256                 if(out->sec != nil){
1257                         put64(seq, out->seq);
1258                         out->seq++;
1259                         (*tr->packMac)(out->sec, out->sec->mackey, seq, p, p + RecHdrLen, n, p + RecHdrLen + n);
1260                         n += maclen;
1261
1262                         /* encrypt */
1263                         n = (*out->sec->enc)(out->sec, p + RecHdrLen, n);
1264                         nb->wp = p + RecHdrLen + n;
1265
1266                         /* update length */
1267                         put16(p+3, n);
1268                 }
1269                 if(type == RChangeCipherSpec){
1270                         if(out->new == nil)
1271                                 error("change cipher without a new cipher");
1272                         freeSec(out->sec);
1273                         out->sec = out->new;
1274                         out->new = nil;
1275                         out->seq = 0;
1276                 }
1277                 qunlock(&out->seclock);
1278                 poperror();
1279
1280                 /*
1281                  * if bwrite error's, we assume the block is queued.
1282                  * if not, we're out of sync with the receiver and will not recover.
1283                  */
1284                 if(waserror()){
1285                         if(strcmp(up->errstr, "interrupted") != 0)
1286                                 tlsError(tr, "channel error");
1287                         nexterror();
1288                 }
1289                 devtab[tr->c->type]->bwrite(tr->c, nb, 0);
1290                 poperror();
1291         }
1292         qunlock(&out->io);
1293         poperror();
1294 }
1295
1296 static long
1297 tlsbwrite(Chan *c, Block *b, ulong offset)
1298 {
1299         int ty;
1300         ulong n;
1301         TlsRec *tr;
1302
1303         n = BLEN(b);
1304
1305         tr = tlsdevs[CONV(c->qid)];
1306         if(tr == nil)
1307                 panic("tlsbread");
1308
1309         ty = TYPE(c->qid);
1310         switch(ty) {
1311         default:
1312                 return devbwrite(c, b, offset);
1313         case Qhand:
1314                 tlsrecwrite(tr, RHandshake, b);
1315                 tr->handout += n;
1316                 break;
1317         case Qdata:
1318                 checkstate(tr, 0, SOpen);
1319                 tlsrecwrite(tr, RApplication, b);
1320                 tr->dataout += n;
1321                 break;
1322         }
1323
1324         return n;
1325 }
1326
1327 typedef struct Hashalg Hashalg;
1328 struct Hashalg
1329 {
1330         char    *name;
1331         int     maclen;
1332         void    (*initkey)(Hashalg *, int, Secret *, uchar*);
1333 };
1334
1335 static void
1336 initmd5key(Hashalg *ha, int version, Secret *s, uchar *p)
1337 {
1338         s->maclen = ha->maclen;
1339         if(version == SSL3Version)
1340                 s->mac = sslmac_md5;
1341         else
1342                 s->mac = hmac_md5;
1343         memmove(s->mackey, p, ha->maclen);
1344 }
1345
1346 static void
1347 initclearmac(Hashalg *, int, Secret *s, uchar *)
1348 {
1349         s->maclen = 0;
1350         s->mac = nomac;
1351 }
1352
1353 static void
1354 initsha1key(Hashalg *ha, int version, Secret *s, uchar *p)
1355 {
1356         s->maclen = ha->maclen;
1357         if(version == SSL3Version)
1358                 s->mac = sslmac_sha1;
1359         else
1360                 s->mac = hmac_sha1;
1361         memmove(s->mackey, p, ha->maclen);
1362 }
1363
1364 static Hashalg hashtab[] =
1365 {
1366         { "clear", 0, initclearmac, },
1367         { "md5", MD5dlen, initmd5key, },
1368         { "sha1", SHA1dlen, initsha1key, },
1369         { 0 }
1370 };
1371
1372 static Hashalg*
1373 parsehashalg(char *p)
1374 {
1375         Hashalg *ha;
1376
1377         for(ha = hashtab; ha->name; ha++)
1378                 if(strcmp(p, ha->name) == 0)
1379                         return ha;
1380         error("unsupported hash algorithm");
1381         return nil;
1382 }
1383
1384 typedef struct Encalg Encalg;
1385 struct Encalg
1386 {
1387         char    *name;
1388         int     keylen;
1389         int     ivlen;
1390         void    (*initkey)(Encalg *ea, Secret *, uchar*, uchar*);
1391 };
1392
1393 static void
1394 initRC4key(Encalg *ea, Secret *s, uchar *p, uchar *)
1395 {
1396         s->enckey = smalloc(sizeof(RC4state));
1397         s->enc = rc4enc;
1398         s->dec = rc4enc;
1399         s->block = 0;
1400         setupRC4state(s->enckey, p, ea->keylen);
1401 }
1402
1403 static void
1404 initDES3key(Encalg *, Secret *s, uchar *p, uchar *iv)
1405 {
1406         s->enckey = smalloc(sizeof(DES3state));
1407         s->enc = des3enc;
1408         s->dec = des3dec;
1409         s->block = 8;
1410         setupDES3state(s->enckey, (uchar(*)[8])p, iv);
1411 }
1412
1413 static void
1414 initclearenc(Encalg *, Secret *s, uchar *, uchar *)
1415 {
1416         s->enc = noenc;
1417         s->dec = noenc;
1418         s->block = 0;
1419 }
1420
1421 static Encalg encrypttab[] =
1422 {
1423         { "clear", 0, 0, initclearenc },
1424         { "rc4_128", 128/8, 0, initRC4key },
1425         { "3des_ede_cbc", 3 * 8, 8, initDES3key },
1426         { 0 }
1427 };
1428
1429 static Encalg*
1430 parseencalg(char *p)
1431 {
1432         Encalg *ea;
1433
1434         for(ea = encrypttab; ea->name; ea++)
1435                 if(strcmp(p, ea->name) == 0)
1436                         return ea;
1437         error("unsupported encryption algorithm");
1438         return nil;
1439 }
1440
1441 static long
1442 tlswrite(Chan *c, void *a, long n, vlong off)
1443 {
1444         Encalg *ea;
1445         Hashalg *ha;
1446         TlsRec *volatile tr;
1447         Secret *volatile tos, *volatile toc;
1448         Block *volatile b;
1449         Cmdbuf *volatile cb;
1450         int m, ty;
1451         char *p, *e;
1452         uchar *volatile x;
1453         ulong offset = off;
1454
1455         tr = tlsdevs[CONV(c->qid)];
1456         if(tr == nil)
1457                 panic("tlswrite");
1458
1459         ty = TYPE(c->qid);
1460         switch(ty){
1461         case Qdata:
1462         case Qhand:
1463                 p = a;
1464                 e = p + n;
1465                 do{
1466                         m = e - p;
1467                         if(m > MaxRecLen)
1468                                 m = MaxRecLen;
1469
1470                         b = allocb(m);
1471                         if(waserror()){
1472                                 freeb(b);
1473                                 nexterror();
1474                         }
1475                         memmove(b->wp, p, m);
1476                         poperror();
1477                         b->wp += m;
1478
1479                         tlsbwrite(c, b, offset);
1480
1481                         p += m;
1482                 }while(p < e);
1483                 return n;
1484         case Qctl:
1485                 break;
1486         default:
1487                 error(Ebadusefd);
1488                 return -1;
1489         }
1490
1491         cb = parsecmd(a, n);
1492         if(waserror()){
1493                 free(cb);
1494                 nexterror();
1495         }
1496         if(cb->nf < 1)
1497                 error("short control request");
1498
1499         /* mutex with operations using what we're about to change */
1500         if(waserror()){
1501                 qunlock(&tr->in.seclock);
1502                 qunlock(&tr->out.seclock);
1503                 nexterror();
1504         }
1505         qlock(&tr->in.seclock);
1506         qlock(&tr->out.seclock);
1507
1508         if(strcmp(cb->f[0], "fd") == 0){
1509                 if(cb->nf != 3)
1510                         error("usage: fd open-fd version");
1511                 if(tr->c != nil)
1512                         error(Einuse);
1513                 m = strtol(cb->f[2], nil, 0);
1514                 if(m < MinProtoVersion || m > MaxProtoVersion)
1515                         error("unsupported version");
1516                 tr->c = buftochan(cb->f[1]);
1517                 tr->version = m;
1518                 tlsSetState(tr, SHandshake, SClosed);
1519         }else if(strcmp(cb->f[0], "version") == 0){
1520                 if(cb->nf != 2)
1521                         error("usage: version vers");
1522                 if(tr->c == nil)
1523                         error("must set fd before version");
1524                 if(tr->verset)
1525                         error("version already set");
1526                 m = strtol(cb->f[1], nil, 0);
1527                 if(m == SSL3Version)
1528                         tr->packMac = sslPackMac;
1529                 else if(m == TLSVersion)
1530                         tr->packMac = tlsPackMac;
1531                 else
1532                         error("unsupported version");
1533                 tr->verset = 1;
1534                 tr->version = m;
1535         }else if(strcmp(cb->f[0], "secret") == 0){
1536                 if(cb->nf != 5)
1537                         error("usage: secret hashalg encalg isclient secretdata");
1538                 if(tr->c == nil || !tr->verset)
1539                         error("must set fd and version before secrets");
1540
1541                 if(tr->in.new != nil){
1542                         freeSec(tr->in.new);
1543                         tr->in.new = nil;
1544                 }
1545                 if(tr->out.new != nil){
1546                         freeSec(tr->out.new);
1547                         tr->out.new = nil;
1548                 }
1549
1550                 ha = parsehashalg(cb->f[1]);
1551                 ea = parseencalg(cb->f[2]);
1552
1553                 p = cb->f[4];
1554                 m = (strlen(p)*3)/2;
1555                 x = smalloc(m);
1556                 tos = nil;
1557                 toc = nil;
1558                 if(waserror()){
1559                         freeSec(tos);
1560                         freeSec(toc);
1561                         free(x);
1562                         nexterror();
1563                 }
1564                 m = dec64(x, m, p, strlen(p));
1565                 if(m < 2 * ha->maclen + 2 * ea->keylen + 2 * ea->ivlen)
1566                         error("not enough secret data provided");
1567
1568                 tos = smalloc(sizeof(Secret));
1569                 toc = smalloc(sizeof(Secret));
1570                 if(!ha->initkey || !ea->initkey)
1571                         error("misimplemented secret algorithm");
1572                 (*ha->initkey)(ha, tr->version, tos, &x[0]);
1573                 (*ha->initkey)(ha, tr->version, toc, &x[ha->maclen]);
1574                 (*ea->initkey)(ea, tos, &x[2 * ha->maclen], &x[2 * ha->maclen + 2 * ea->keylen]);
1575                 (*ea->initkey)(ea, toc, &x[2 * ha->maclen + ea->keylen], &x[2 * ha->maclen + 2 * ea->keylen + ea->ivlen]);
1576
1577                 if(!tos->mac || !tos->enc || !tos->dec
1578                 || !toc->mac || !toc->enc || !toc->dec)
1579                         error("missing algorithm implementations");
1580                 if(strtol(cb->f[3], nil, 0) == 0){
1581                         tr->in.new = tos;
1582                         tr->out.new = toc;
1583                 }else{
1584                         tr->in.new = toc;
1585                         tr->out.new = tos;
1586                 }
1587                 if(tr->version == SSL3Version){
1588                         toc->unpad = sslunpad;
1589                         tos->unpad = sslunpad;
1590                 }else{
1591                         toc->unpad = tlsunpad;
1592                         tos->unpad = tlsunpad;
1593                 }
1594                 toc->encalg = ea->name;
1595                 toc->hashalg = ha->name;
1596                 tos->encalg = ea->name;
1597                 tos->hashalg = ha->name;
1598
1599                 free(x);
1600                 poperror();
1601         }else if(strcmp(cb->f[0], "changecipher") == 0){
1602                 if(cb->nf != 1)
1603                         error("usage: changecipher");
1604                 if(tr->out.new == nil)
1605                         error("can't change cipher spec without setting secret");
1606
1607                 qunlock(&tr->in.seclock);
1608                 qunlock(&tr->out.seclock);
1609                 poperror();
1610                 free(cb);
1611                 poperror();
1612
1613                 /*
1614                  * the real work is done as the message is written
1615                  * so the stream is encrypted in sync.
1616                  */
1617                 b = allocb(1);
1618                 *b->wp++ = 1;
1619                 tlsrecwrite(tr, RChangeCipherSpec, b);
1620                 return n;
1621         }else if(strcmp(cb->f[0], "opened") == 0){
1622                 if(cb->nf != 1)
1623                         error("usage: opened");
1624                 if(tr->in.sec == nil || tr->out.sec == nil)
1625                         error("cipher must be configured before enabling data messages");
1626                 lock(&tr->statelk);
1627                 if(tr->state != SHandshake && tr->state != SOpen){
1628                         unlock(&tr->statelk);
1629                         error("can't enable data messages");
1630                 }
1631                 tr->state = SOpen;
1632                 unlock(&tr->statelk);
1633                 tr->opened = 1;
1634         }else if(strcmp(cb->f[0], "alert") == 0){
1635                 if(cb->nf != 2)
1636                         error("usage: alert n");
1637                 if(tr->c == nil)
1638                         error("must set fd before sending alerts");
1639                 m = strtol(cb->f[1], nil, 0);
1640
1641                 qunlock(&tr->in.seclock);
1642                 qunlock(&tr->out.seclock);
1643                 poperror();
1644                 free(cb);
1645                 poperror();
1646
1647                 sendAlert(tr, m);
1648
1649                 if(m == ECloseNotify)
1650                         tlsclosed(tr, SLClose);
1651
1652                 return n;
1653         } else
1654                 error(Ebadarg);
1655
1656         qunlock(&tr->in.seclock);
1657         qunlock(&tr->out.seclock);
1658         poperror();
1659         free(cb);
1660         poperror();
1661
1662         return n;
1663 }
1664
1665 static void
1666 tlsinit(void)
1667 {
1668         struct Encalg *e;
1669         struct Hashalg *h;
1670         int n;
1671         char *cp;
1672
1673         tlsdevs = smalloc(sizeof(TlsRec*) * maxtlsdevs);
1674         trnames = smalloc((sizeof *trnames) * maxtlsdevs);
1675
1676         n = 1;
1677         for(e = encrypttab; e->name != nil; e++)
1678                 n += strlen(e->name) + 1;
1679         cp = encalgs = smalloc(n);
1680         for(e = encrypttab;;){
1681                 strcpy(cp, e->name);
1682                 cp += strlen(e->name);
1683                 e++;
1684                 if(e->name == nil)
1685                         break;
1686                 *cp++ = ' ';
1687         }
1688         *cp = 0;
1689
1690         n = 1;
1691         for(h = hashtab; h->name != nil; h++)
1692                 n += strlen(h->name) + 1;
1693         cp = hashalgs = smalloc(n);
1694         for(h = hashtab;;){
1695                 strcpy(cp, h->name);
1696                 cp += strlen(h->name);
1697                 h++;
1698                 if(h->name == nil)
1699                         break;
1700                 *cp++ = ' ';
1701         }
1702         *cp = 0;
1703 }
1704
1705 Dev tlsdevtab = {
1706         'a',
1707         "tls",
1708
1709         devreset,
1710         tlsinit,
1711         devshutdown,
1712         tlsattach,
1713         tlswalk,
1714         tlsstat,
1715         tlsopen,
1716         devcreate,
1717         tlsclose,
1718         tlsread,
1719         tlsbread,
1720         tlswrite,
1721         tlsbwrite,
1722         devremove,
1723         tlswstat,
1724 };
1725
1726 /* get channel associated with an fd */
1727 static Chan*
1728 buftochan(char *p)
1729 {
1730         Chan *c;
1731         int fd;
1732
1733         if(p == 0)
1734                 error(Ebadarg);
1735         fd = strtoul(p, 0, 0);
1736         if(fd < 0)
1737                 error(Ebadarg);
1738         c = fdtochan(fd, -1, 0, 1);     /* error check and inc ref */
1739         return c;
1740 }
1741
1742 static void
1743 sendAlert(TlsRec *tr, int err)
1744 {
1745         Block *b;
1746         int i, fatal;
1747         char *msg;
1748
1749         fatal = 1;
1750         msg = "tls unknown alert";
1751         for(i=0; i < nelem(tlserrs); i++) {
1752                 if(tlserrs[i].err == err) {
1753                         msg = tlserrs[i].msg;
1754                         if(tr->version == SSL3Version)
1755                                 err = tlserrs[i].sslerr;
1756                         else
1757                                 err = tlserrs[i].tlserr;
1758                         fatal = tlserrs[i].fatal;
1759                         break;
1760                 }
1761         }
1762
1763         if(!waserror()){
1764                 b = allocb(2);
1765                 *b->wp++ = fatal + 1;
1766                 *b->wp++ = err;
1767                 if(fatal)
1768                         tlsSetState(tr, SAlert, SOpen|SHandshake|SRClose);
1769                 tlsrecwrite(tr, RAlert, b);
1770                 poperror();
1771         }
1772         if(fatal)
1773                 tlsError(tr, msg);
1774 }
1775
1776 static void
1777 tlsError(TlsRec *tr, char *msg)
1778 {
1779         int s;
1780
1781         lock(&tr->statelk);
1782         s = tr->state;
1783         tr->state = SError;
1784         if(s != SError){
1785                 strncpy(tr->err, msg, ERRMAX - 1);
1786                 tr->err[ERRMAX - 1] = '\0';
1787         }
1788         unlock(&tr->statelk);
1789         if(s != SError)
1790                 alertHand(tr, msg);
1791 }
1792
1793 static void
1794 tlsSetState(TlsRec *tr, int new, int old)
1795 {
1796         lock(&tr->statelk);
1797         if(tr->state & old)
1798                 tr->state = new;
1799         unlock(&tr->statelk);
1800 }
1801
1802 /* hand up a digest connection */
1803 static void
1804 tlshangup(TlsRec *tr)
1805 {
1806         Block *b;
1807
1808         qlock(&tr->in.io);
1809         for(b = tr->processed; b; b = tr->processed){
1810                 tr->processed = b->next;
1811                 freeb(b);
1812         }
1813         if(tr->unprocessed != nil){
1814                 freeb(tr->unprocessed);
1815                 tr->unprocessed = nil;
1816         }
1817         qunlock(&tr->in.io);
1818
1819         tlsSetState(tr, SClosed, ~0);
1820 }
1821
1822 static TlsRec*
1823 newtls(Chan *ch)
1824 {
1825         TlsRec **pp, **ep, **np;
1826         char **nmp;
1827         int t, newmax;
1828
1829         if(waserror()) {
1830                 unlock(&tdlock);
1831                 nexterror();
1832         }
1833         lock(&tdlock);
1834         ep = &tlsdevs[maxtlsdevs];
1835         for(pp = tlsdevs; pp < ep; pp++)
1836                 if(*pp == nil)
1837                         break;
1838         if(pp >= ep) {
1839                 if(maxtlsdevs >= MaxTlsDevs) {
1840                         unlock(&tdlock);
1841                         poperror();
1842                         return nil;
1843                 }
1844                 newmax = 2 * maxtlsdevs;
1845                 if(newmax > MaxTlsDevs)
1846                         newmax = MaxTlsDevs;
1847                 np = smalloc(sizeof(TlsRec*) * newmax);
1848                 memmove(np, tlsdevs, sizeof(TlsRec*) * maxtlsdevs);
1849                 tlsdevs = np;
1850                 pp = &tlsdevs[maxtlsdevs];
1851                 memset(pp, 0, sizeof(TlsRec*)*(newmax - maxtlsdevs));
1852
1853                 nmp = smalloc(sizeof *nmp * newmax);
1854                 memmove(nmp, trnames, sizeof *nmp * maxtlsdevs);
1855                 trnames = nmp;
1856
1857                 maxtlsdevs = newmax;
1858         }
1859         *pp = mktlsrec();
1860         if(pp - tlsdevs >= tdhiwat)
1861                 tdhiwat++;
1862         t = TYPE(ch->qid);
1863         if(t == Qclonus)
1864                 t = Qctl;
1865         ch->qid.path = QID(pp - tlsdevs, t);
1866         ch->qid.vers = 0;
1867         unlock(&tdlock);
1868         poperror();
1869         return *pp;
1870 }
1871
1872 static TlsRec *
1873 mktlsrec(void)
1874 {
1875         TlsRec *tr;
1876
1877         tr = mallocz(sizeof(*tr), 1);
1878         if(tr == nil)
1879                 error(Enomem);
1880         tr->state = SClosed;
1881         tr->ref = 1;
1882         kstrdup(&tr->user, up->user);
1883         tr->perm = 0660;
1884         return tr;
1885 }
1886
1887 static char*
1888 tlsstate(int s)
1889 {
1890         switch(s){
1891         case SHandshake:
1892                 return "Handshaking";
1893         case SOpen:
1894                 return "Established";
1895         case SRClose:
1896                 return "RemoteClosed";
1897         case SLClose:
1898                 return "LocalClosed";
1899         case SAlert:
1900                 return "Alerting";
1901         case SError:
1902                 return "Errored";
1903         case SClosed:
1904                 return "Closed";
1905         }
1906         return "Unknown";
1907 }
1908
1909 static void
1910 freeSec(Secret *s)
1911 {
1912         if(s != nil){
1913                 free(s->enckey);
1914                 free(s);
1915         }
1916 }
1917
1918 static int
1919 noenc(Secret *, uchar *, int n)
1920 {
1921         return n;
1922 }
1923
1924 static int
1925 rc4enc(Secret *sec, uchar *buf, int n)
1926 {
1927         rc4(sec->enckey, buf, n);
1928         return n;
1929 }
1930
1931 static int
1932 tlsunpad(uchar *buf, int n, int block)
1933 {
1934         int pad, nn;
1935
1936         pad = buf[n - 1];
1937         nn = n - 1 - pad;
1938         if(nn <= 0 || n % block)
1939                 return -1;
1940         while(--n > nn)
1941                 if(pad != buf[n - 1])
1942                         return -1;
1943         return nn;
1944 }
1945
1946 static int
1947 sslunpad(uchar *buf, int n, int block)
1948 {
1949         int pad, nn;
1950
1951         pad = buf[n - 1];
1952         nn = n - 1 - pad;
1953         if(nn <= 0 || n % block)
1954                 return -1;
1955         return nn;
1956 }
1957
1958 static int
1959 blockpad(uchar *buf, int n, int block)
1960 {
1961         int pad, nn;
1962
1963         nn = n + block;
1964         nn -= nn % block;
1965         pad = nn - (n + 1);
1966         while(n < nn)
1967                 buf[n++] = pad;
1968         return nn;
1969 }
1970                 
1971 static int
1972 des3enc(Secret *sec, uchar *buf, int n)
1973 {
1974         n = blockpad(buf, n, 8);
1975         des3CBCencrypt(buf, n, sec->enckey);
1976         return n;
1977 }
1978
1979 static int
1980 des3dec(Secret *sec, uchar *buf, int n)
1981 {
1982         des3CBCdecrypt(buf, n, sec->enckey);
1983         return (*sec->unpad)(buf, n, 8);
1984 }
1985 static DigestState*
1986 nomac(uchar *, ulong, uchar *, ulong, uchar *, DigestState *)
1987 {
1988         return nil;
1989 }
1990
1991 /*
1992  * sslmac: mac calculations for ssl 3.0 only; tls 1.0 uses the standard hmac.
1993  */
1994 static DigestState*
1995 sslmac_x(uchar *p, ulong len, uchar *key, ulong klen, uchar *digest, DigestState *s,
1996         DigestState*(*x)(uchar*, ulong, uchar*, DigestState*), int xlen, int padlen)
1997 {
1998         int i;
1999         uchar pad[48], innerdigest[20];
2000
2001         if(xlen > sizeof(innerdigest)
2002         || padlen > sizeof(pad))
2003                 return nil;
2004
2005         if(klen>64)
2006                 return nil;
2007
2008         /* first time through */
2009         if(s == nil){
2010                 for(i=0; i<padlen; i++)
2011                         pad[i] = 0x36;
2012                 s = (*x)(key, klen, nil, nil);
2013                 s = (*x)(pad, padlen, nil, s);
2014                 if(s == nil)
2015                         return nil;
2016         }
2017
2018         s = (*x)(p, len, nil, s);
2019         if(digest == nil)
2020                 return s;
2021
2022         /* last time through */
2023         for(i=0; i<padlen; i++)
2024                 pad[i] = 0x5c;
2025         (*x)(nil, 0, innerdigest, s);
2026         s = (*x)(key, klen, nil, nil);
2027         s = (*x)(pad, padlen, nil, s);
2028         (*x)(innerdigest, xlen, digest, s);
2029         return nil;
2030 }
2031
2032 static DigestState*
2033 sslmac_sha1(uchar *p, ulong len, uchar *key, ulong klen, uchar *digest, DigestState *s)
2034 {
2035         return sslmac_x(p, len, key, klen, digest, s, sha1, SHA1dlen, 40);
2036 }
2037
2038 static DigestState*
2039 sslmac_md5(uchar *p, ulong len, uchar *key, ulong klen, uchar *digest, DigestState *s)
2040 {
2041         return sslmac_x(p, len, key, klen, digest, s, md5, MD5dlen, 48);
2042 }
2043
2044 static void
2045 sslPackMac(Secret *sec, uchar *mackey, uchar *seq, uchar *header, uchar *body, int len, uchar *mac)
2046 {
2047         DigestState *s;
2048         uchar buf[11];
2049
2050         memmove(buf, seq, 8);
2051         buf[8] = header[0];
2052         buf[9] = header[3];
2053         buf[10] = header[4];
2054
2055         s = (*sec->mac)(buf, 11, mackey, sec->maclen, 0, 0);
2056         (*sec->mac)(body, len, mackey, sec->maclen, mac, s);
2057 }
2058
2059 static void
2060 tlsPackMac(Secret *sec, uchar *mackey, uchar *seq, uchar *header, uchar *body, int len, uchar *mac)
2061 {
2062         DigestState *s;
2063         uchar buf[13];
2064
2065         memmove(buf, seq, 8);
2066         memmove(&buf[8], header, 5);
2067
2068         s = (*sec->mac)(buf, 13, mackey, sec->maclen, 0, 0);
2069         (*sec->mac)(body, len, mackey, sec->maclen, mac, s);
2070 }
2071
2072 static void
2073 put32(uchar *p, u32int x)
2074 {
2075         p[0] = x>>24;
2076         p[1] = x>>16;
2077         p[2] = x>>8;
2078         p[3] = x;
2079 }
2080
2081 static void
2082 put64(uchar *p, vlong x)
2083 {
2084         put32(p, (u32int)(x >> 32));
2085         put32(p+4, (u32int)x);
2086 }
2087
2088 static void
2089 put24(uchar *p, int x)
2090 {
2091         p[0] = x>>16;
2092         p[1] = x>>8;
2093         p[2] = x;
2094 }
2095
2096 static void
2097 put16(uchar *p, int x)
2098 {
2099         p[0] = x>>8;
2100         p[1] = x;
2101 }
2102
2103 static u32int
2104 get32(uchar *p)
2105 {
2106         return (p[0]<<24)|(p[1]<<16)|(p[2]<<8)|p[3];
2107 }
2108
2109 static int
2110 get16(uchar *p)
2111 {
2112         return (p[0]<<8)|p[1];
2113 }