diff options
author | Hakan Olsson <ho@cvs.openbsd.org> | 2001-06-25 22:30:09 +0000 |
---|---|---|
committer | Hakan Olsson <ho@cvs.openbsd.org> | 2001-06-25 22:30:09 +0000 |
commit | 48210fc5236c653a5d6209ae5aaefdaae673974e (patch) | |
tree | 4bb39387f3b51f7f103b066a77e1db1027599992 | |
parent | f54cfa87738ce51a146834e3f11aeb2e065bdb77 (diff) |
Cleanup/rewrite. Some further work. No crypto yet.
-rw-r--r-- | sys/dev/pci/ises.c | 706 | ||||
-rw-r--r-- | sys/dev/pci/isesreg.h | 9 | ||||
-rw-r--r-- | sys/dev/pci/isesvar.h | 36 |
3 files changed, 429 insertions, 322 deletions
diff --git a/sys/dev/pci/ises.c b/sys/dev/pci/ises.c index d2635ccc577..9d7e8f71086 100644 --- a/sys/dev/pci/ises.c +++ b/sys/dev/pci/ises.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ises.c,v 1.10 2001/06/24 21:08:07 ho Exp $ */ +/* $OpenBSD: ises.c,v 1.11 2001/06/25 22:30:07 ho Exp $ */ /* * Copyright (c) 2000, 2001 Håkan Olsson (ho@crt.se) @@ -80,7 +80,9 @@ int ises_process __P((struct cryptop *)); void ises_callback __P((struct ises_q *)); int ises_feed __P((struct ises_softc *)); void ises_bchu_switch_session __P((struct ises_softc *, - struct ises_bchu_session *)); + struct ises_session *)); + +void ises_read_dma __P((struct ises_softc *)); /* XXX for now... */ void ubsec_mcopy __P((struct mbuf *, struct mbuf *, int, int)); @@ -221,15 +223,15 @@ ises_attach(struct device *parent, struct device *self, void *aux) state++; /* Allocate in DMAable memory. */ - if (bus_dmamem_alloc(sc->sc_dmat, sizeof sc->sc_dma_data, 1, 0, &seg, - 1, &nsegs, BUS_DMA_NOWAIT)) { + if (bus_dmamem_alloc(sc->sc_dmat, ISES_B_DATASIZE, 1, 0, &seg, 1, + &nsegs, BUS_DMA_NOWAIT)) { printf(": can't alloc dma buffer space\n"); goto fail; } state++; - if (bus_dmamem_map(sc->sc_dmat, &seg, nsegs, sizeof sc->sc_dma_data, - (caddr_t *)&sc->sc_dma_data, 0)) { + if (bus_dmamem_map(sc->sc_dmat, &seg, nsegs, ISES_B_DATASIZE, + &sc->sc_dma_data, 0)) { printf(": can't map dma buffer space\n"); goto fail; } @@ -290,9 +292,9 @@ ises_initstate(void *v) ticks = hz; -#if 0 /* Too noisy */ - DPRINTF (("%s: entered initstate %d\n", dv, sc->sc_initstate)); -#endif + p = ISES_STAT_IDP_STATE(READ_REG(sc, ISES_A_STAT)); + DPRINTF (("%s: initstate %d, IDP state is %d \"%s\"\n", dv, + sc->sc_initstate, p, ises_idp_state[p])); switch (sc->sc_initstate) { case 0: @@ -501,8 +503,14 @@ ises_queue_cmd(struct ises_softc *sc, u_int32_t cmd, u_int32_t *data, len = cmd >> 24; code = (cmd >> 16) & 0xFF; - - s = splimp(); + +#ifdef ISESDEBUG + if (code != ISES_CMD_HBITS) /* ... since this happens 100 times/s */ + DPRINTF(("%s: queuing cmd %d len %d\n", sc->sc_dv.dv_xname, + cmd, len)); +#endif + + s = splnet(); if (len > READ_REG(sc, ISES_A_IQF)) { splx(s); @@ -519,6 +527,7 @@ ises_queue_cmd(struct ises_softc *sc, u_int32_t cmd, u_int32_t *data, bzero(cq, sizeof (struct ises_cmd)); cq->cmd_code = code; cq->cmd_cb = callback; + cq->cmd_session = sc->sc_cursession; SIMPLEQ_INSERT_TAIL(&sc->sc_cmdq, cq, cmd_next); WRITE_REG(sc, ISES_A_IQD, cmd); @@ -547,8 +556,9 @@ ises_process_oqueue(struct ises_softc *sc) char *dv = sc->sc_dv.dv_xname; #endif struct ises_cmd *cq; + struct ises_session *ses; u_int32_t oqs, r, d; - int cmd, len, c; + int cmd, len, c, s; r = READ_REG(sc, ISES_A_OQS); if (r > 1) @@ -562,6 +572,7 @@ ises_process_oqueue(struct ises_softc *sc) cmd = (r >> 16) & 0xff; r = r & 0xffff; + s = splnet(); if (!SIMPLEQ_EMPTY(&sc->sc_cmdq)) { cq = SIMPLEQ_FIRST(&sc->sc_cmdq); SIMPLEQ_REMOVE_HEAD(&sc->sc_cmdq, cq, cmd_next); @@ -570,6 +581,7 @@ ises_process_oqueue(struct ises_softc *sc) cq = NULL; DPRINTF(("%s:process_oqueue: cmd queue empty!\n", dv)); } + splx(s); if (r) { /* This command generated an error */ @@ -631,9 +643,10 @@ ises_process_oqueue(struct ises_softc *sc) break; case ISES_CMD_BR_OMR: - sc->sc_bsession.omr = READ_REG(sc, ISES_A_OQD); + ses = &sc->sc_sessions[cq->cmd_session]; + ses->omr = READ_REG(sc, ISES_A_OQD); DPRINTF(("%s:process_oqueue: read OMR[%08x]\n", - dv, sc->sc_bsession.omr)); + dv, ses->omr)); #ifdef ISESDEBUG ises_debug_parse_omr(sc); #endif @@ -641,10 +654,30 @@ ises_process_oqueue(struct ises_softc *sc) case ISES_CMD_BSWITCH: DPRINTF(("%s:process_oqueue: BCHU_SWITCH\n")); - /* Put switched BCHU session in sc_bsession. */ + /* Put switched BCHU session in cur session. */ + ses = &sc->sc_sessions[cq->cmd_session]; for(c = 0; len > 0; len--, c++) - *((u_int32_t *)&sc->sc_bsession + c) = +#if 0 /* Don't store the key, just drain the data */ + *((u_int32_t *)&ses + c) = +#endif READ_REG(sc, ISES_A_OQD); + + sc->sc_switching = 0; + ises_feed (sc); + break; + + case ISES_CMD_BW_HMLR: + /* + * This return indicates our homecooked + * session switch is complete. Start data + * feed. + */ + DPRINTF(("%s:process_oqueue: sesn switched\n", + dv)); + sc->sc_switching = 0; + + /* Retry/restart */ + ises_feed(sc); break; default: @@ -672,17 +705,45 @@ int ises_intr(void *arg) { struct ises_softc *sc = arg; - volatile u_int32_t ints; - u_int32_t cmd; -#ifdef ISESDEBUG + u_int32_t ints, dma_status, cmd; char *dv = sc->sc_dv.dv_xname; -#endif + + dma_status = READ_REG(sc, ISES_DMA_STATUS); + + if (!(dma_status & (ISES_DMA_STATUS_R_ERR | ISES_DMA_STATUS_W_ERR))) { + if ((sc->sc_dma_mask & ISES_DMA_STATUS_R_RUN) != 0 && + (dma_status & ISES_DMA_STATUS_R_RUN) == 0) { + DPRINTF(("%s: DMA read complete\n", dv)); + + bus_dmamap_sync(sc->sc_dmat, sc->sc_dmamap, + BUS_DMASYNC_POSTREAD); + + /* XXX */ + + WRITE_REG(sc, ISES_DMA_RESET, 0); + } + + if ((sc->sc_dma_mask & ISES_DMA_STATUS_W_RUN) != 0 && + (dma_status & ISES_DMA_STATUS_W_RUN) == 0) { + DPRINTF(("%s: DMA write complete\n", dv)); + + bus_dmamap_sync(sc->sc_dmat, sc->sc_dmamap, + BUS_DMASYNC_POSTWRITE); + + WRITE_REG(sc, ISES_DMA_RESET, 0); + ises_feed(sc); + } + } else { + printf ("%s: DMA error\n", dv); + WRITE_REG(sc, ISES_DMA_RESET, 0); + } ints = READ_REG(sc, ISES_A_INTS); if (!(ints & sc->sc_intrmask)) return (0); /* Not our interrupt. */ - WRITE_REG(sc, ISES_A_INTS, ints); /* Clear all set intr bits. */ + /* Clear all set intr bits. */ + WRITE_REG(sc, ISES_A_INTS, ints); #if 0 /* Check it we've got room for more data. */ @@ -691,9 +752,9 @@ ises_intr(void *arg) ises_feed(sc); #endif - if (ints & ISES_STAT_SW_OQSINC) { /* A-intf output q has data */ + /* Does the A-intf output queue have data we need to process? */ + if (ints & ISES_STAT_SW_OQSINC) ises_process_oqueue(sc); - } if (ints & ISES_STAT_LNAU_BUSY_1) { DPRINTF(("%s:ises_intr: LNAU 1 job complete\n", dv)); @@ -746,21 +807,66 @@ int ises_feed(struct ises_softc *sc) { struct ises_q *q; - - while (!SIMPLEQ_EMPTY(&sc->sc_queue)) { - if (READ_REG(sc, ISES_A_STAT) & ISES_STAT_BCHU_IFF) - break; - q = SIMPLEQ_FIRST(&sc->sc_queue); -#if 0 - WRITE_REG(sc, ISES_OFFSET_BCHU_DATA, - (u_int32_t)vtophys(&q->q_mcr)); - printf("feed: q->chip %08x %08x\n", q, - (u_int32_t)vtophys(&q->q_mcr)); + bus_dma_segment_t *ds = &sc->sc_dmamap->dm_segs[0]; + u_int32_t dma_status; + int s; +#ifdef ISESDEBUG + char *dv = sc->sc_dv.dv_xname; #endif - SIMPLEQ_REMOVE_HEAD(&sc->sc_queue, q, q_next); - --sc->sc_nqueue; - SIMPLEQ_INSERT_TAIL(&sc->sc_qchip, q, q_next); + + s = splnet(); + /* Anything to do? */ + if (SIMPLEQ_EMPTY(&sc->sc_queue) || + (READ_REG(sc, ISES_A_STAT) & ISES_STAT_BCHU_IFF)) { + splx(s); + return (0); + } + + /* Pick the first */ + q = SIMPLEQ_FIRST(&sc->sc_queue); + splx(s); + + /* If we're currently switching sessions, we'll have to wait. */ + if (sc->sc_switching != 0) { + DPRINTF(("%s:ises_feed: waiting for session switch\n", dv)); + return (0); + } + + /* If on-chip data is not correct for this data, switch session. */ + if (sc->sc_cursession != q->q_sesn) { + /* Session switch required */ + DPRINTF(("%s:ises_feed: initiating session switch\n", dv)); + ises_bchu_switch_session (sc, &q->q_session); + sc->sc_cursession = q->q_sesn; + return (0); } + + s = splnet(); + SIMPLEQ_REMOVE_HEAD(&sc->sc_queue, q, q_next); + SIMPLEQ_INSERT_TAIL(&sc->sc_qchip, q, q_next); + --sc->sc_nqueue; + splx(s); + + if (q->q_crp->crp_flags & CRYPTO_F_IMBUF) + bus_dmamap_load_mbuf(sc->sc_dmat, sc->sc_dmamap, + q->q_src.mbuf, BUS_DMA_NOWAIT); + else if (q->q_crp->crp_flags & CRYPTO_F_IOV) + bus_dmamap_load_uio(sc->sc_dmat, sc->sc_dmamap, q->q_src.uio, + BUS_DMA_NOWAIT); + /* ... else */ + + /* Start writing data to the ises. */ + bus_dmamap_sync(sc->sc_dmat, sc->sc_dmamap, BUS_DMASYNC_PREWRITE); + + DPRINTF(("%s:ises_feed: writing DMA\n", dv)); + + WRITE_REG(sc, ISES_DMA_WRITE_START, ds->ds_addr); + WRITE_REG(sc, ISES_DMA_WRITE_COUNT, ISES_DMA_WCOUNT(ds->ds_len)); + + dma_status = READ_REG(sc, ISES_DMA_STATUS); + dma_status |= ISES_DMA_CTRL_ILT | ISES_DMA_CTRL_RLINE; + WRITE_REG(sc, ISES_DMA_CTRL, dma_status); + return (0); } @@ -779,6 +885,9 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) SHA1_CTX sha1ctx; RMD160_CTX rmd160ctx; int i, sesn; +#ifdef ISESDEBUG + char *dv; +#endif if (sidp == NULL || cri == NULL) return (EINVAL); @@ -790,6 +899,9 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) } if (sc == NULL) return (EINVAL); +#ifdef ISESDEBUG + dv = sc->sc_dv.dv_xname; +#endif for (c = cri; c != NULL; c = c->cri_next) { if (c->cri_alg == CRYPTO_MD5_HMAC || @@ -809,6 +921,11 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) if (mac == 0 && enc == 0) return (EINVAL); +#ifdef ISESDEBUG + printf ("%s:ises_newsession: mac=%p(%d) enc=%p(%d)\n", + dv, mac, (mac ? mac->cri_alg : -1), enc, (enc ? enc->cri_alg : -1)); +#endif + /* Allocate a new session */ if (sc->sc_sessions == NULL) { ses = sc->sc_sessions = (struct ises_session *) @@ -817,13 +934,14 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) isesstats.nomem++; return (ENOMEM); } - sesn = 0; + sc->sc_cursession = sesn = 0; sc->sc_nsessions = 1; } else { ses = NULL; for (sesn = 0; sesn < sc->sc_nsessions; sesn++) - if (sc->sc_sessions[sesn].ses_used == 0) { + if (sc->sc_sessions[sesn].omr == 0) { ses = &sc->sc_sessions[sesn]; + sc->sc_cursession = sesn; break; } @@ -842,32 +960,38 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) free(sc->sc_sessions, M_DEVBUF); sc->sc_sessions = ses; ses = &sc->sc_sessions[sc->sc_nsessions]; + sc->sc_cursession = sc->sc_nsessions; sc->sc_nsessions++; } } + DPRINTF(("%s:ises_newsession: nsessions=%d cursession=%d\n", dv, + sc->sc_nsessions, sc->sc_cursession)); + bzero(ses, sizeof(struct ises_session)); - ses->ses_used = 1; + + /* Select data path through B-interface. */ + ses->omr |= ISES_SELR_BCHU_DIS; if (enc) { /* get an IV, network byte order */ /* XXX switch to using builtin HRNG ! */ - get_random_bytes(ses->ses_iv, sizeof(ses->ses_iv)); + get_random_bytes(ses->sccr, sizeof(ses->sccr)); /* crypto key */ if (c->cri_alg == CRYPTO_DES_CBC) { - bcopy(enc->cri_key, &ses->ses_deskey[0], 8); - bcopy(enc->cri_key, &ses->ses_deskey[2], 8); - bcopy(enc->cri_key, &ses->ses_deskey[4], 8); + bcopy(enc->cri_key, &ses->kr[0], 8); + bcopy(enc->cri_key, &ses->kr[2], 8); + bcopy(enc->cri_key, &ses->kr[4], 8); } else - bcopy(enc->cri_key, &ses->ses_deskey[0], 24); - - SWAP32(ses->ses_deskey[0]); - SWAP32(ses->ses_deskey[1]); - SWAP32(ses->ses_deskey[2]); - SWAP32(ses->ses_deskey[3]); - SWAP32(ses->ses_deskey[4]); - SWAP32(ses->ses_deskey[5]); + bcopy(enc->cri_key, &ses->kr[0], 24); + + SWAP32(ses->kr[0]); + SWAP32(ses->kr[1]); + SWAP32(ses->kr[2]); + SWAP32(ses->kr[3]); + SWAP32(ses->kr[4]); + SWAP32(ses->kr[5]); } if (mac) { @@ -880,16 +1004,14 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) MD5Update(&md5ctx, mac->cri_key, mac->cri_klen / 8); MD5Update(&md5ctx, hmac_ipad_buffer, HMAC_BLOCK_LEN - (mac->cri_klen / 8)); - bcopy(md5ctx.state, ses->ses_hminner, - sizeof(md5ctx.state)); + MD5Final((u_int8_t *)&ses->cvr, &md5ctx); break; case CRYPTO_SHA1_HMAC: SHA1Init(&sha1ctx); SHA1Update(&sha1ctx, mac->cri_key, mac->cri_klen / 8); SHA1Update(&sha1ctx, hmac_ipad_buffer, HMAC_BLOCK_LEN - (mac->cri_klen / 8)); - bcopy(sha1ctx.state, ses->ses_hminner, - sizeof(sha1ctx.state)); + SHA1Final((u_int8_t *)ses->cvr, &sha1ctx); break; case CRYPTO_RIPEMD160_HMAC: default: @@ -898,8 +1020,7 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) mac->cri_klen / 8); RMD160Update(&rmd160ctx, hmac_ipad_buffer, HMAC_BLOCK_LEN - (mac->cri_klen / 8)); - bcopy(rmd160ctx.state, ses->ses_hminner, - sizeof(rmd160ctx.state)); + RMD160Final((u_int8_t *)ses->cvr, &rmd160ctx); break; } @@ -910,28 +1031,31 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) case CRYPTO_MD5_HMAC: MD5Init(&md5ctx); MD5Update(&md5ctx, mac->cri_key, mac->cri_klen / 8); - MD5Update(&md5ctx, hmac_ipad_buffer, HMAC_BLOCK_LEN - + MD5Update(&md5ctx, hmac_opad_buffer, HMAC_BLOCK_LEN - (mac->cri_klen / 8)); - bcopy(md5ctx.state, ses->ses_hmouter, + MD5Update(&md5ctx, (u_int8_t *)ses->cvr, sizeof(md5ctx.state)); + MD5Final((u_int8_t *)ses->cvr, &md5ctx); break; case CRYPTO_SHA1_HMAC: SHA1Init(&sha1ctx); SHA1Update(&sha1ctx, mac->cri_key, mac->cri_klen / 8); - SHA1Update(&sha1ctx, hmac_ipad_buffer, HMAC_BLOCK_LEN - + SHA1Update(&sha1ctx, hmac_opad_buffer, HMAC_BLOCK_LEN - (mac->cri_klen / 8)); - bcopy(sha1ctx.state, ses->ses_hmouter, + SHA1Update(&sha1ctx, (u_int8_t *)ses->cvr, sizeof(sha1ctx.state)); + SHA1Final((u_int8_t *)ses->cvr, &sha1ctx); break; case CRYPTO_RIPEMD160_HMAC: default: RMD160Init(&rmd160ctx); RMD160Update(&rmd160ctx, mac->cri_key, mac->cri_klen / 8); - RMD160Update(&rmd160ctx, hmac_ipad_buffer, + RMD160Update(&rmd160ctx, hmac_opad_buffer, HMAC_BLOCK_LEN - (mac->cri_klen / 8)); - bcopy(rmd160ctx.state, ses->ses_hmouter, + RMD160Update(&rmd160ctx, (u_int8_t *)ses->cvr, sizeof(rmd160ctx.state)); + RMD160Final((u_int8_t *)ses->cvr, &rmd160ctx); break; } @@ -939,13 +1063,12 @@ ises_newsession(u_int32_t *sidp, struct cryptoini *cri) mac->cri_key[i] ^= HMAC_OPAD_VAL; } + DPRINTF(("%s:ises_newsession: done\n", dv)); *sidp = ISES_SID(sc->sc_dv.dv_unit, sesn); return (0); } -/* - * Deallocate a session. - */ +/* Deallocate a session. */ int ises_freesession(u_int64_t tsid) { @@ -959,67 +1082,70 @@ ises_freesession(u_int64_t tsid) sc = ises_cd.cd_devs[card]; sesn = ISES_SESSION(sid); + + DPRINTF(("%s:ises_freesession: freeing session %d\n", + sc->sc_dv.dv_xname, sesn)); + bzero(&sc->sc_sessions[sesn], sizeof(sc->sc_sessions[sesn])); return (0); } +/* Called by the crypto framework, crypto(9). */ int ises_process(struct cryptop *crp) { - int card, err; struct ises_softc *sc; struct ises_q *q; struct cryptodesc *maccrd, *enccrd, *crd; struct ises_session *ses; -#if 0 - int s, i, j; -#else - int s; + int card, s, err = EINVAL; + int encoffset, macoffset, cpskip, sskip, dskip, stheend, dtheend; + int cpoffset, coffset, nicealign; +#ifdef ISESDEBUG + char *dv; #endif - int encoffset = 0, macoffset = 0; - int sskip, stheend, dtheend, cpskip, cpoffset, dskip, nicealign; - int16_t coffset; if (crp == NULL || crp->crp_callback == NULL) return (EINVAL); card = ISES_CARD(crp->crp_sid); - if (card >= ises_cd.cd_ndevs || ises_cd.cd_devs[card] == NULL) { - err = EINVAL; + if (card >= ises_cd.cd_ndevs || ises_cd.cd_devs[card] == NULL) goto errout; - } sc = ises_cd.cd_devs[card]; +#ifdef ISESDEBUG + dv = sc->sc_dv.dv_xname; +#endif s = splnet(); if (sc->sc_nqueue == ISES_MAX_NQUEUE) { splx(s); - err = ENOMEM; - goto errout; + goto memerr; } splx(s); q = (struct ises_q *)malloc(sizeof(struct ises_q), M_DEVBUF, M_NOWAIT); - if (q == NULL) { - err = ENOMEM; - goto errout; - } + if (q == NULL) + goto memerr; bzero(q, sizeof(struct ises_q)); q->q_sesn = ISES_SESSION(crp->crp_sid); ses = &sc->sc_sessions[q->q_sesn]; - /* XXX */ + DPRINTF(("%s:ises_process: session %d selected\n", dv, q->q_sesn)); q->q_sc = sc; q->q_crp = crp; if (crp->crp_flags & CRYPTO_F_IMBUF) { - q->q_src_m = (struct mbuf *)crp->crp_buf; - q->q_dst_m = (struct mbuf *)crp->crp_buf; + q->q_src.mbuf = (struct mbuf *)crp->crp_buf; + q->q_dst.mbuf = (struct mbuf *)crp->crp_buf; + } else if (crp->crp_flags & CRYPTO_F_IOV) { + q->q_src.uio = (struct uio *)crp->crp_buf; + q->q_dst.uio = (struct uio *)crp->crp_buf; } else { - err = EINVAL; + /* XXX for now... */ goto errout; } @@ -1031,7 +1157,6 @@ ises_process(struct cryptop *crp) * for decryption the second one should be crypto. */ maccrd = enccrd = NULL; - err = EINVAL; for (crd = crp->crp_desc; crd; crd = crd->crd_next) { switch (crd->crd_alg) { case CRYPTO_MD5_HMAC: @@ -1055,80 +1180,93 @@ ises_process(struct cryptop *crp) } if (!maccrd && !enccrd) goto errout; - err = 0; + + /* Select data path through B-interface. */ + q->q_session.omr |= ISES_SELR_BCHU_DIS; if (enccrd) { encoffset = enccrd->crd_skip; + /* Select algorithm */ if (enccrd->crd_alg == CRYPTO_3DES_CBC) - q->q_bsession.omr |= ISES_SOMR_BOMR_3DES; + q->q_session.omr |= ISES_SOMR_BOMR_3DES; else - q->q_bsession.omr |= ISES_SOMR_BOMR_DES; - q->q_bsession.omr |= ISES_SOMR_FMR_CBC; + q->q_session.omr |= ISES_SOMR_BOMR_DES; + + /* Set CBC mode */ + q->q_session.omr |= ISES_SOMR_FMR_CBC; if (enccrd->crd_flags & CRD_F_ENCRYPT) { - q->q_bsession.omr |= ISES_SOMR_EDR; /* XXX */ + /* Set encryption bit */ + q->q_session.omr |= ISES_SOMR_EDR; if (enccrd->crd_flags & CRD_F_IV_EXPLICIT) - bcopy(enccrd->crd_iv, q->q_bsession.sccr, 8); + bcopy(enccrd->crd_iv, q->q_session.sccr, 8); else { - q->q_bsession.sccr[0] = ses->ses_iv[0]; - q->q_bsession.sccr[1] = ses->ses_iv[1]; + q->q_session.sccr[0] = ses->sccr[0]; + q->q_session.sccr[1] = ses->sccr[1]; } - if ((enccrd->crd_flags & CRD_F_IV_PRESENT) == 0) - m_copyback(q->q_src_m, enccrd->crd_inject, - 8, (caddr_t)q->q_bsession.sccr); + if ((enccrd->crd_flags & CRD_F_IV_PRESENT) == 0) { + if (crp->crp_flags & CRYPTO_F_IMBUF) + m_copyback(q->q_src.mbuf, + enccrd->crd_inject, 8, + (caddr_t)q->q_session.sccr); + else if (crp->crp_flags & CRYPTO_F_IOV) + cuio_copyback(q->q_src.uio, + enccrd->crd_inject, 8, + (caddr_t)q->q_session.sccr); + /* XXX else ... */ + } } else { - q->q_bsession.omr &= ~ISES_SOMR_EDR; /* XXX */ + /* Clear encryption bit == decrypt mode */ + q->q_session.omr &= ~ISES_SOMR_EDR; if (enccrd->crd_flags & CRD_F_IV_EXPLICIT) - bcopy(enccrd->crd_iv, q->q_bsession.sccr, 8); - else - m_copyback(q->q_src_m, enccrd->crd_inject, - 8, (caddr_t)q->q_bsession.sccr); + bcopy(enccrd->crd_iv, q->q_session.sccr, 8); + else if (crp->crp_flags & CRYPTO_F_IMBUF) + m_copydata(q->q_src.mbuf, enccrd->crd_inject, + 8, (caddr_t)q->q_session.sccr); + else if (crp->crp_flags & CRYPTO_F_IOV) + cuio_copydata(q->q_src.uio, + enccrd->crd_inject, 8, + (caddr_t)q->q_session.sccr); + /* XXX else ... */ } - q->q_bsession.kr[0] = ses->ses_deskey[0]; - q->q_bsession.kr[1] = ses->ses_deskey[1]; - q->q_bsession.kr[2] = ses->ses_deskey[2]; - q->q_bsession.kr[3] = ses->ses_deskey[3]; - q->q_bsession.kr[4] = ses->ses_deskey[4]; - q->q_bsession.kr[5] = ses->ses_deskey[5]; + q->q_session.kr[0] = ses->kr[0]; + q->q_session.kr[1] = ses->kr[1]; + q->q_session.kr[2] = ses->kr[2]; + q->q_session.kr[3] = ses->kr[3]; + q->q_session.kr[4] = ses->kr[4]; + q->q_session.kr[5] = ses->kr[5]; - SWAP32(q->q_bsession.sccr[0]); - SWAP32(q->q_bsession.sccr[1]); + SWAP32(q->q_session.sccr[0]); + SWAP32(q->q_session.sccr[1]); } if (maccrd) { macoffset = maccrd->crd_skip; + /* Select algorithm */ switch (crd->crd_alg) { case CRYPTO_MD5_HMAC: - q->q_bsession.omr |= ISES_HOMR_HFR_MD5; + q->q_session.omr |= ISES_HOMR_HFR_MD5; break; case CRYPTO_SHA1_HMAC: - q->q_bsession.omr |= ISES_HOMR_HFR_SHA1; + q->q_session.omr |= ISES_HOMR_HFR_SHA1; break; case CRYPTO_RIPEMD160_HMAC: default: - q->q_bsession.omr |= ISES_HOMR_HFR_RMD160; + q->q_session.omr |= ISES_HOMR_HFR_RMD160; break; } - q->q_hminner[0] = ses->ses_hminner[0]; - q->q_hminner[1] = ses->ses_hminner[1]; - q->q_hminner[2] = ses->ses_hminner[2]; - q->q_hminner[3] = ses->ses_hminner[3]; - q->q_hminner[4] = ses->ses_hminner[4]; - q->q_hminner[5] = ses->ses_hminner[5]; - - q->q_hmouter[0] = ses->ses_hmouter[0]; - q->q_hmouter[1] = ses->ses_hmouter[1]; - q->q_hmouter[2] = ses->ses_hmouter[2]; - q->q_hmouter[3] = ses->ses_hmouter[3]; - q->q_hmouter[4] = ses->ses_hmouter[4]; - q->q_hmouter[5] = ses->ses_hmouter[5]; + q->q_session.cvr[0] = ses->cvr[0]; + q->q_session.cvr[1] = ses->cvr[1]; + q->q_session.cvr[2] = ses->cvr[2]; + q->q_session.cvr[3] = ses->cvr[3]; + q->q_session.cvr[4] = ses->cvr[4]; } if (enccrd && maccrd) { @@ -1137,7 +1275,6 @@ ises_process(struct cryptop *crp) if (((encoffset + enccrd->crd_len) != (macoffset + maccrd->crd_len)) || (enccrd->crd_skip < maccrd->crd_skip)) { - err = EINVAL; goto errout; } @@ -1157,76 +1294,40 @@ ises_process(struct cryptop *crp) } q->q_offset = coffset >> 2; - q->q_src_l = mbuf2pages(q->q_src_m, &q->q_src_npa, &q->q_src_packp, - &q->q_src_packl, 1, &nicealign); - if (q->q_src_l == 0) { - err = ENOMEM; - goto errout; - } - - /* XXX mcr stuff; q->q_mcr->mcr_pktlen = stheend; */ - -#if 0 /* XXX */ - for (i = j = 0; i < q->q_src_npa; i++) { - bus_dma_segment_t *ds; - - /* XXX DEBUG? */ - - if (sskip) { - if (sskip >= q->q_src_packl) { - sskip -= q->q_src_packl; - continue; - } - q->q_src_packp += sskip; - q->q_src_packl -= sskip; - sskip = 0; - } - - ds = NULL; /* XXX initial packet */ - - ds->ds_addr = q->q_src_packp; - if (stheend) { - if (q->q_src_packl > stheend) { - ds->ds_len = stheend; - stheend = 0; - } else { - ds->ds_len = q->q_src_packl; - stheend -= ds->ds_len; - } - } else - ds->ds_len = q->q_src_packl; - - if ((i + 1) == q->q_src_npa) - ds->ds_next = 0; - else - ds->ds_next = vtophys(&q->q_srcpkt); +#if 0 + /* XXX not sure about this, in bus_dma context */ + if (crp->crp_flags & CRYPTO_F_IMBUF) + q->q_src_l = mbuf2pages(q->q_src.mbuf, &q->q_src_npa, + &q->q_src_packp, &q->q_src_packl, 1, &nicealign); + else if (crp->crp_flags & CRYPTO_F_IOV) + q->q_src_l = iov2pages(q->q_src.uio, &q->q_src_npa, + &q->q_src_packp, &q->q_src_packl, 1, &nicealign); + /* XXX else */ +#endif - j++; - } + if (q->q_src_l == 0) + goto memerr; -#endif /* XXX */ - /* XXX DEBUG ? */ + /* XXX ... */ if (enccrd == NULL && maccrd != NULL) { - /* XXX mcr stuff */ + /* XXX ... */ } else { if (!nicealign) { int totlen, len; struct mbuf *m, *top, **mp; totlen = q->q_dst_l = q->q_src_l; - if (q->q_src_m->m_flags & M_PKTHDR) { + if (q->q_src.mbuf->m_flags & M_PKTHDR) { MGETHDR(m, M_DONTWAIT, MT_DATA); - M_DUP_PKTHDR(m, q->q_src_m); + M_DUP_PKTHDR(m, q->q_src.mbuf); len = MHLEN; } else { MGET(m, M_DONTWAIT, MT_DATA); len = MLEN; } - if (m == NULL) { - err = ENOMEM; - goto errout; - } + if (m == NULL) + goto memerr; if (totlen >= MINCLSIZE) { MCLGET(m, M_DONTWAIT); if (m->m_flags & M_EXT) @@ -1241,8 +1342,7 @@ ises_process(struct cryptop *crp) MGET(m, M_DONTWAIT, MT_DATA); if (m == NULL) { m_freem(top); - err = ENOMEM; - goto errout; + goto memerr; } len = MLEN; } @@ -1257,75 +1357,41 @@ ises_process(struct cryptop *crp) mp = &m->m_next; } - q->q_dst_m = top; - ubsec_mcopy(q->q_src_m, q->q_dst_m, cpskip, cpoffset); + q->q_dst.mbuf = top; + ubsec_mcopy(q->q_src.mbuf, q->q_dst.mbuf, cpskip, cpoffset); } else - q->q_dst_m = q->q_src_m; - - q->q_dst_l = mbuf2pages(q->q_dst_m, &q->q_dst_npa, - &q->q_dst_packp, &q->q_dst_packl, 1, NULL); + q->q_dst.mbuf = q->q_src.mbuf; #if 0 - for (i = j = 0; i < q->q_dst_npa; i++) { - struct bus_dma_segment_t *ds; - - if (dskip) { - if (dskip >= q->q_dst_packl[i]) { - dskip -= q->q_dst_packl[i]; - continue; - } - q->q_dst_packp[i] += dskip; - q->q_dst_packl[i] -= dskip; - dskip = 0; - } - - if (j == 0) - ds = NULL; /* &q->q_mcr->mcr_opktbuf; */ - else - ds = &q->q_dstpkt[j - 1]; - - ds->ds_addr = q->q_dst_packp[i]; - - if (dtheend) { - if (q->q_dst_packl[i] > dtheend) { - ds->ds_len = dtheend; - dtheend = 0; - } else { - ds->ds_len = q->q_dst_packl[i]; - dtheend -= ds->ds_len; - } - } else - ds->ds_len = q->q_dst_packl[i]; - - if ((i + 1) == q->q_dst_npa) { - if (maccrd) - ds->ds_next = vtophys(q->q_macbuf); - else - ds->ds_next = 0; - } else - ds->ds_next = vtophys(&q->q_dstpkt[j]); - j++; - } + /* XXX ? */ + q->q_dst_l = mbuf2pages(q->q_dst.mbuf, &q->q_dst_npa, + &q->q_dst_packp, &q->q_dst_packl, 1, NULL); #endif } + DPRINTF(("%s:ises_process: queueing request\n", dv)); + s = splnet(); SIMPLEQ_INSERT_TAIL(&sc->sc_queue, q, q_next); sc->sc_nqueue++; - ises_feed(sc); splx(s); + ises_feed(sc); return (0); +memerr: + err = ENOMEM; + isesstats.nomem++; errout: - if (err == ENOMEM) - isesstats.nomem++; - else if (err == EINVAL) + DPRINTF(("%s:ises_process: an error occurred, err=%d, q=%p\n", dv, + err, q)); + + if (err == EINVAL) isesstats.invalid++; if (q) { - if (q->q_src_m != q->q_dst_m) - m_freem(q->q_dst_m); + if (q->q_src.mbuf != q->q_dst.mbuf) + m_freem(q->q_dst.mbuf); free(q, M_DEVBUF); } crp->crp_etype = err; @@ -1338,10 +1404,29 @@ ises_callback(struct ises_q *q) { struct cryptop *crp = (struct cryptop *)q->q_crp; struct cryptodesc *crd; + struct ises_softc *sc = q->q_sc; + u_int8_t *sccr; + + if ((crp->crp_flags & CRYPTO_F_IMBUF) && + (q->q_src.mbuf != q->q_dst.mbuf)) { + m_freem(q->q_src.mbuf); + crp->crp_buf = (caddr_t)q->q_dst.mbuf; + } - if ((crp->crp_flags & CRYPTO_F_IMBUF) && (q->q_src_m != q->q_dst_m)) { - m_freem(q->q_src_m); - crp->crp_buf = (caddr_t)q->q_dst_m; + if (q->q_session.omr & ISES_SOMR_EDR) { + /* Copy out IV after encryption. */ + sccr = (u_int8_t *)&sc->sc_sessions[q->q_sesn].sccr; + for (crd = crp->crp_desc; crd; crd = crd->crd_next) { + if (crd->crd_alg != CRYPTO_DES_CBC && + crd->crd_alg != CRYPTO_3DES_CBC) + continue; + if (crp->crp_flags & CRYPTO_F_IMBUF) + m_copydata((struct mbuf *)crp->crp_buf, + crd->crd_skip + crd->crd_len - 8, 8, sccr); + else if (crp->crp_flags & CRYPTO_F_IOV) + cuio_copydata((struct uio *)crp->crp_buf, + crd->crd_skip + crd->crd_len - 8, 8, sccr); + } } for (crd = crp->crp_desc; crd; crd = crd->crd_next) { @@ -1349,12 +1434,18 @@ ises_callback(struct ises_q *q) crd->crd_alg != CRYPTO_SHA1_HMAC && crd->crd_alg != CRYPTO_RIPEMD160_HMAC) continue; - m_copyback((struct mbuf *)crp->crp_buf, - crd->crd_inject, 12, (u_int8_t *)&q->q_macbuf[0]); + if (crp->crp_flags & CRYPTO_F_IMBUF) + m_copyback((struct mbuf *)crp->crp_buf, + crd->crd_inject, 12, (u_int8_t *)q->q_macbuf); + else if (crp->crp_flags & CRYPTO_F_IOV) + bcopy((u_int8_t *)q->q_macbuf, crp->crp_mac, 12); + /* XXX else ... */ break; } free(q, M_DEVBUF); + DPRINTF(("%s:ises_callback: calling crypto_done\n", + sc->sc_dv.dv_xname)); crypto_done(crp); } @@ -1525,6 +1616,63 @@ ises_assert_cmd_mode(struct ises_softc *sc) } } +void +ises_bchu_switch_session (struct ises_softc *sc, struct ises_session *ss) +{ + /* It appears that the BCHU_SWITCH_SESSION command is broken. */ + /* We have to work around it. */ + + u_int32_t cmd; + + /* Mark 'switch' in progress. */ + sc->sc_switching = 1; + + /* Write the key. */ + cmd = ISES_MKCMD(ISES_CMD_BW_KR0, 2); + ises_queue_cmd(sc, cmd, &ss->kr[4], NULL); + cmd = ISES_MKCMD(ISES_CMD_BW_KR1, 2); + ises_queue_cmd(sc, cmd, &ss->kr[2], NULL); + cmd = ISES_MKCMD(ISES_CMD_BW_KR2, 2); + ises_queue_cmd(sc, cmd, &ss->kr[0], NULL); + + /* Write OMR - Operation Method Register, clears SCCR+CVR+DBCR+HMLR */ + cmd = ISES_MKCMD(ISES_CMD_BW_OMR, 1); + ises_queue_cmd(sc, cmd, &ss->omr, NULL); + + /* Write SCCR - Symmetric Crypto Chaining Register (IV) */ + cmd = ISES_MKCMD(ISES_CMD_BW_SCCR, 1); + ises_queue_cmd(sc, cmd, &ss->sccr[0], NULL); + + /* Write CVR - Chaining Variables Register (hash state) */ + cmd = ISES_MKCMD(ISES_CMD_BW_SCCR, 5); + ises_queue_cmd(sc, cmd, &ss->cvr[0], NULL); + + /* Write DBCR - Data Block Count Register */ + cmd = ISES_MKCMD(ISES_CMD_BW_SCCR, 2); + ises_queue_cmd(sc, cmd, &ss->dbcr[0], NULL); + + /* Write HMLR - Hash Message Length Register */ + cmd = ISES_MKCMD(ISES_CMD_BW_HMLR, 2); + ises_queue_cmd(sc, cmd, &ss->hmlr[0], NULL); +} + +/* XXX Currently unused. */ +void +ises_read_dma (struct ises_softc *sc) +{ + bus_dma_segment_t *ds = &sc->sc_dmamap->dm_segs[0]; + u_int32_t dma_status; + + bus_dmamap_sync(sc->sc_dmat, sc->sc_dmamap, BUS_DMASYNC_PREREAD); + + WRITE_REG(sc, ISES_DMA_READ_START, ds->ds_addr); + WRITE_REG(sc, ISES_DMA_READ_START, ISES_DMA_RCOUNT(ds->ds_len)); + + dma_status = READ_REG(sc, ISES_DMA_STATUS); + dma_status |= ISES_DMA_CTRL_ILT | ISES_DMA_CTRL_WRITE; + WRITE_REG(sc, ISES_DMA_CTRL, dma_status); +} + #ifdef ISESDEBUG /* * Development code section below here. @@ -1559,37 +1707,10 @@ ises_debug_simple_cmd (struct ises_softc *sc, u_int32_t code, u_int32_t d) } void -ises_bchu_switch_session (struct ises_softc *sc, struct ises_bchu_session *ss) -{ - /* It appears that the BCHU_SWITCH_SESSION command is broken. */ - /* We have to work around it. */ - - u_int32_t cmd; - - cmd = ISES_MKCMD(ISES_CMD_BR_KR0, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - cmd = ISES_MKCMD(ISES_CMD_BR_KR1, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - cmd = ISES_MKCMD(ISES_CMD_BR_KR2, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - - cmd = ISES_MKCMD(ISES_CMD_BR_OMR, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - cmd = ISES_MKCMD(ISES_CMD_BR_SCCR, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - cmd = ISES_MKCMD(ISES_CMD_BR_DBCR, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - cmd = ISES_MKCMD(ISES_CMD_BR_HMLR, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); - cmd = ISES_MKCMD(ISES_CMD_BR_CVR, 0); - ises_queue_cmd(sc, cmd, NULL, NULL); -} - -void ises_debug_loop (void *v) { struct ises_softc *sc = (struct ises_softc *)v; - struct ises_bchu_session bses; + struct ises_session ses; u_int32_t cmd, stat; int i; @@ -1641,36 +1762,27 @@ ises_debug_loop (void *v) /* Crypto. */ /* Load BCHU session data */ - bzero(&bses, sizeof bses); - bses.kr[0] = 0xD0; - bses.kr[1] = 0xD1; - bses.kr[2] = 0xD2; - bses.kr[3] = 0xD3; - bses.kr[4] = 0xD4; - bses.kr[5] = 0xD5; + bzero(&ses, sizeof ses); + ses.kr[0] = 0xD0; + ses.kr[1] = 0xD1; + ses.kr[2] = 0xD2; + ses.kr[3] = 0xD3; + ses.kr[4] = 0xD4; + ses.kr[5] = 0xD5; /* cipher data out is hash in, SHA1, 3DES, encrypt, ECB */ - bses.omr = ISES_SELR_BCHU_HISOF | ISES_HOMR_HFR_SHA1 | + ses.omr = ISES_SELR_BCHU_HISOF | ISES_HOMR_HFR_SHA1 | ISES_SOMR_BOMR_3DES | ISES_SOMR_EDR | ISES_SOMR_FMR_ECB; - printf ("Queueing OMR write\n"); - cmd = ISES_MKCMD(ISES_CMD_BW_OMR, 1); - ises_queue_cmd(sc, cmd, &bses.omr, NULL); - - printf ("Queueing KR0, KR1, KR2 writes\n"); - cmd = ISES_MKCMD(ISES_CMD_BW_KR0, 2); - ises_queue_cmd(sc, cmd, &bses.kr[4], NULL); - cmd = ISES_MKCMD(ISES_CMD_BW_KR1, 2); - ises_queue_cmd(sc, cmd, &bses.kr[2], NULL); - cmd = ISES_MKCMD(ISES_CMD_BW_KR2, 2); - ises_queue_cmd(sc, cmd, &bses.kr[0], NULL); - -#if 0 /* switch session does not appear to work - it never returns */ +#if 1 + printf ("Queueing home-cooked session switch\n"); + ises_bchu_switch_session(sc, &ses); +#else /* switch session does not appear to work - it never returns */ printf ("Queueing BCHU session switch\n"); - cmd = ISES_MKCMD(ISES_CMD_BSWITCH, sizeof bses / 4); + cmd = ISES_MKCMD(ISES_CMD_BSWITCH, sizeof ses / 4); printf ("session is %d 32bit words (== 18 ?), cmd = [%08x]\n", - sizeof bses / 4, cmd); - ises_queue_cmd(sc, cmd, (u_int32_t *)&bses, NULL); + sizeof ses / 4, cmd); + ises_queue_cmd(sc, cmd, (u_int32_t *)&ses, NULL); #endif break; @@ -1857,7 +1969,7 @@ ises_showreg (void) void ises_debug_parse_omr (struct ises_softc *sc) { - u_int32_t omr = sc->sc_bsession.omr; + u_int32_t omr = sc->sc_sessions[sc->sc_cursession].omr; printf ("SELR : "); if (omr & ISES_SELR_BCHU_EH) @@ -1869,7 +1981,9 @@ ises_debug_parse_omr (struct ises_softc *sc) printf ("HU-input-is-SCU-output "); if (omr & ISES_SELR_BCHU_DIS) - printf ("data-interface-select "); + printf ("data-interface-select=B "); + else + printf ("data-interface-select=DataIn/DataOut "); printf ("\n"); diff --git a/sys/dev/pci/isesreg.h b/sys/dev/pci/isesreg.h index faa2f620639..cc4fcd0d72e 100644 --- a/sys/dev/pci/isesreg.h +++ b/sys/dev/pci/isesreg.h @@ -1,4 +1,4 @@ -/* $OpenBSD: isesreg.h,v 1.5 2001/06/24 21:08:06 ho Exp $ $ */ +/* $OpenBSD: isesreg.h,v 1.6 2001/06/25 22:30:08 ho Exp $ $ */ /* * Copyright (c) 2000 Håkan Olsson (ho@crt.se) @@ -348,9 +348,9 @@ static const char *ises_sw_mode[] = #define ISES_CARD(sid) (((sid) & 0xf0000000) >> 28) #define ISES_SID(crd,ses) (((crd) << 28) | ((ses) & 0x0fffffff)) -/* Size and layout of ises_bchu_session is firmware dependent. */ +/* Size and layout of ises_session is firmware dependent. */ /* This structure should be usable for the SWITCH_SESSION command. */ -struct ises_bchu_session { +struct ises_session { u_int32_t kr[6]; /* Key register KR2,KR1,KR0 */ u_int32_t omr; /* Operation method register */ @@ -362,9 +362,6 @@ struct ises_bchu_session { } __attribute__((packed)); #define ISES_B_DATASIZE 4096 -struct ises_databuf { - u_int8_t data[ISES_B_DATASIZE]; -} __attribute__((packed)); /* * ------------------------------------------ diff --git a/sys/dev/pci/isesvar.h b/sys/dev/pci/isesvar.h index ae5e30b548a..85e5512046b 100644 --- a/sys/dev/pci/isesvar.h +++ b/sys/dev/pci/isesvar.h @@ -1,4 +1,4 @@ -/* $OpenBSD: isesvar.h,v 1.3 2001/06/24 21:08:06 ho Exp $ */ +/* $OpenBSD: isesvar.h,v 1.4 2001/06/25 22:30:08 ho Exp $ */ /* * Copyright (c) 2000 Håkan Olsson (ho@crt.se) @@ -34,44 +34,47 @@ struct ises_softc { bus_space_tag_t sc_memt; /* memory tag */ bus_dma_tag_t sc_dmat; /* dma tag */ bus_dmamap_t sc_dmamap; /* dma xfer map */ - struct ises_databuf sc_dma_data; /* data area */ + caddr_t sc_dma_data; /* data area */ int32_t sc_cid; /* crypto tag */ u_int32_t sc_intrmask; /* interrupt mask */ + u_int32_t sc_dma_mask; /* DMA running mask */ SIMPLEQ_HEAD(,ises_q) sc_queue; /* packet queue */ int sc_nqueue; /* count enqueued */ SIMPLEQ_HEAD(,ises_q) sc_qchip; /* on chip */ struct timeout sc_timeout; /* init + hrng timeout */ int sc_nsessions; /* nr of sessions */ struct ises_session *sc_sessions; /* sessions */ + int sc_cursession; /* current session */ + int sc_switching; /* we're switching sessions */ int sc_initstate; /* card initialization state */ SIMPLEQ_HEAD(,ises_cmd) sc_cmdq; /* Commands in A-queue */ - struct ises_bchu_session sc_bsession; /* Current BCHU session */ u_int32_t sc_lnau1_r[64]; /* LNAU 1 result (2048 bits) */ int sc_lnau1_rlen; /* LNAU 1 result len (bytes) */ u_int32_t sc_lnau2_r[64]; /* LNAU 2 result (2048 bits) */ int sc_lnau2_rlen; /* LNAU 2 result len (bytes) */ }; +union ises_q_u { + struct mbuf *mbuf; + struct uio *uio; + /* XXX more ? */ +}; + struct ises_q { SIMPLEQ_ENTRY(ises_q) q_next; struct cryptop *q_crp; struct ises_softc *q_sc; - struct mbuf *q_src_m, *q_dst_m; - bus_dma_segment_t q_srcpkt, q_dstpkt; + union ises_q_u q_src, q_dst; /* src/dst data bufs */ + + bus_dma_segment_t q_src_ds, q_dst_ds; - struct ises_bchu_session q_bsession; - u_int32_t q_hminner[5]; /* hmac inner state */ - u_int32_t q_hmouter[5]; /* hmac outer state */ - u_int32_t q_paddr; + struct ises_session q_session; u_int16_t q_offset; /* crypto offset */ - u_int8_t q_pad[16]; int q_sesn; - long q_src_packp; - int q_src_packl; int q_src_npa, q_src_l; long q_dst_packp; @@ -84,18 +87,11 @@ struct ises_cmd { SIMPLEQ_ENTRY(ises_cmd) cmd_next; u_int32_t cmd_code; /* Command code */ u_int32_t cmd_rlen; /* Response length */ + u_int32_t cmd_session; /* Current ises_session */ u_int32_t (*cmd_cb)(struct ises_softc *, struct ises_cmd *); /* Callback */ }; -struct ises_session { - u_int32_t ses_used; - u_int32_t ses_deskey[6]; /* 3DES key */ - u_int32_t ses_hminner[5]; /* hmac inner state */ - u_int32_t ses_hmouter[5]; /* hmac outer state */ - u_int32_t ses_iv[2]; /* DES/3DES iv */ -}; - /* Maximum queue length */ #ifndef ISES_MAX_NQUEUE #define ISES_MAX_NQUEUE 24 |