RT5592 devices have a larger TXWI and RXWI than other adapters supported
by run(4). The following patch adds the offset adjustments that were
overlooked in r1.98.

Using the patch, I can connect to 11g and 11b APs, though there's still
one nit: after scanning channels in the 5GHz range, the adapter can't
reliably transmit and receive on 2.4GHz channels. Until I figure out
what isn't being reset properly, I'm working around it by specifying
"media OFDM54 mode 11g".

(Sent with a DWA 160 rev. B2.)


Index: if_run.c
===================================================================
RCS file: /home/cvsync/openbsd/src/sys/dev/usb/if_run.c,v
retrieving revision 1.98
diff -u -p -r1.98 if_run.c
--- if_run.c    24 May 2014 10:10:17 -0000      1.98
+++ if_run.c    4 Jun 2014 15:31:31 -0000
@@ -781,6 +781,11 @@ run_alloc_tx_ring(struct run_softc *sc, 
 {
        struct run_tx_ring *txq = &sc->txq[qid];
        int i, error;
+       uint16_t txwisize;
+
+       txwisize = sizeof(struct rt2860_txwi);
+       if (sc->mac_ver == 0x5592)
+               txwisize += sizeof(uint32_t);
 
        txq->cur = txq->queued = 0;
 
@@ -805,8 +810,7 @@ run_alloc_tx_ring(struct run_softc *sc, 
                        goto fail;
                }
                /* zeroize the TXD + TXWI part */
-               memset(data->buf, 0, sizeof (struct rt2870_txd) +
-                   sizeof (struct rt2860_txwi));
+               memset(data->buf, 0, sizeof(struct rt2870_txd) + txwisize);
        }
        if (error != 0)
 fail:          run_free_tx_ring(sc, qid);
@@ -2312,6 +2316,13 @@ run_rxeof(struct usbd_xfer *xfer, void *
        uint8_t *buf;
        uint32_t dmalen;
        int xferlen;
+       uint16_t rxwisize;
+
+       rxwisize = sizeof(struct rt2860_rxwi);
+       if (sc->mac_ver == 0x5592)
+               rxwisize += sizeof(uint64_t);
+       else if (sc->mac_ver == 0x3593)
+               rxwisize += sizeof(uint32_t);
 
        if (__predict_false(status != USBD_NORMAL_COMPLETION)) {
                DPRINTF(("RX status=%d\n", status));
@@ -2323,8 +2334,8 @@ run_rxeof(struct usbd_xfer *xfer, void *
        }
        usbd_get_xfer_status(xfer, NULL, NULL, &xferlen, NULL);
 
-       if (__predict_false(xferlen < sizeof (uint32_t) +
-           sizeof (struct rt2860_rxwi) + sizeof (struct rt2870_rxd))) {
+       if (__predict_false(xferlen < sizeof (uint32_t) + rxwisize +
+           sizeof(struct rt2870_rxd))) {
                DPRINTF(("xfer too short %d\n", xferlen));
                goto skip;
        }
@@ -2394,6 +2405,7 @@ run_tx(struct run_softc *sc, struct mbuf
        struct rt2870_txd *txd;
        struct rt2860_txwi *txwi;
        uint16_t qos, dur;
+       uint16_t txwisize;
        uint8_t type, mcs, tid, qid;
        int error, hasqos, ridx, ctl_ridx, xferlen;
 
@@ -2429,7 +2441,11 @@ run_tx(struct run_softc *sc, struct mbuf
        /* get MCS code from rate index */
        mcs = rt2860_rates[ridx].mcs;
 
-       xferlen = sizeof (*txwi) + m->m_pkthdr.len;
+       txwisize = sizeof(struct rt2860_txwi);
+       if (sc->mac_ver == 0x5592)
+               txwisize += sizeof(uint32_t);
+       xferlen = txwisize + m->m_pkthdr.len;
+
        /* roundup to 32-bit alignment */
        xferlen = (xferlen + 3) & ~3;
 
@@ -2489,7 +2505,7 @@ run_tx(struct run_softc *sc, struct mbuf
        }
 #endif
 
-       m_copydata(m, 0, m->m_pkthdr.len, (caddr_t)(txwi + 1));
+       m_copydata(m, 0, m->m_pkthdr.len, (caddr_t)txwi + txwisize);
        m_freem(m);
 
        xferlen += sizeof (*txd) + 4;

Reply via email to