diff options
Diffstat (limited to 'sys/dev/ic')
-rw-r--r-- | sys/dev/ic/rt2560.c | 21 | ||||
-rw-r--r-- | sys/dev/ic/rt2661.c | 21 | ||||
-rw-r--r-- | sys/dev/ic/rt2860.c | 19 |
3 files changed, 53 insertions, 8 deletions
diff --git a/sys/dev/ic/rt2560.c b/sys/dev/ic/rt2560.c index 4981fc06a59..e24147275e5 100644 --- a/sys/dev/ic/rt2560.c +++ b/sys/dev/ic/rt2560.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rt2560.c,v 1.40 2008/11/25 21:43:57 damien Exp $ */ +/* $OpenBSD: rt2560.c,v 1.41 2008/12/21 18:19:58 damien Exp $ */ /*- * Copyright (c) 2005, 2006 @@ -1699,6 +1699,7 @@ rt2560_tx_data(struct rt2560_softc *sc, struct mbuf *m0, struct rt2560_tx_data *data; struct ieee80211_frame *wh; struct ieee80211_key *k; + struct mbuf *m1; uint16_t dur; uint32_t flags = 0; int pktlen, rate, needcts = 0, needrts = 0, error; @@ -1827,10 +1828,24 @@ rt2560_tx_data(struct rt2560_softc *sc, struct mbuf *m0, } if (error != 0) { /* too many fragments, linearize */ - if (m_defrag(m0, M_DONTWAIT) != 0) { + MGETHDR(m1, MT_DATA, M_DONTWAIT); + if (m1 == NULL) { m_freem(m0); - return ENOMEM; + return ENOBUFS; + } + if (m0->m_pkthdr.len > MHLEN) { + MCLGET(m1, M_DONTWAIT); + if (!(m1->m_flags & M_EXT)) { + m_freem(m0); + m_freem(m1); + return ENOBUFS; + } } + m_copydata(m0, 0, m0->m_pkthdr.len, mtod(m1, caddr_t)); + m1->m_pkthdr.len = m1->m_len = m0->m_pkthdr.len; + m_freem(m0); + m0 = m1; + error = bus_dmamap_load_mbuf(sc->sc_dmat, data->map, m0, BUS_DMA_NOWAIT); if (error != 0) { diff --git a/sys/dev/ic/rt2661.c b/sys/dev/ic/rt2661.c index c22fd40b010..b146edefd82 100644 --- a/sys/dev/ic/rt2661.c +++ b/sys/dev/ic/rt2661.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rt2661.c,v 1.45 2008/11/25 21:43:57 damien Exp $ */ +/* $OpenBSD: rt2661.c,v 1.46 2008/12/21 18:19:58 damien Exp $ */ /*- * Copyright (c) 2006 @@ -1546,6 +1546,7 @@ rt2661_tx_data(struct rt2661_softc *sc, struct mbuf *m0, struct rt2661_tx_data *data; struct ieee80211_frame *wh; struct ieee80211_key *k; + struct mbuf *m1; uint16_t dur; uint32_t flags = 0; int pktlen, rate, needcts = 0, needrts = 0, error; @@ -1671,10 +1672,24 @@ rt2661_tx_data(struct rt2661_softc *sc, struct mbuf *m0, } if (error != 0) { /* too many fragments, linearize */ - if (m_defrag(m0, M_DONTWAIT) != 0) { + MGETHDR(m1, MT_DATA, M_DONTWAIT); + if (m1 == NULL) { m_freem(m0); - return ENOMEM; + return ENOBUFS; + } + if (m0->m_pkthdr.len > MHLEN) { + MCLGET(m1, M_DONTWAIT); + if (!(m1->m_flags & M_EXT)) { + m_freem(m0); + m_freem(m1); + return ENOBUFS; + } } + m_copydata(m0, 0, m0->m_pkthdr.len, mtod(m1, caddr_t)); + m1->m_pkthdr.len = m1->m_len = m0->m_pkthdr.len; + m_freem(m0); + m0 = m1; + error = bus_dmamap_load_mbuf(sc->sc_dmat, data->map, m0, BUS_DMA_NOWAIT); if (error != 0) { diff --git a/sys/dev/ic/rt2860.c b/sys/dev/ic/rt2860.c index e15cb41e7ec..a9b17915a59 100644 --- a/sys/dev/ic/rt2860.c +++ b/sys/dev/ic/rt2860.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rt2860.c,v 1.27 2008/12/15 18:35:59 damien Exp $ */ +/* $OpenBSD: rt2860.c,v 1.28 2008/12/21 18:19:58 damien Exp $ */ /*- * Copyright (c) 2007, 2008 @@ -1356,6 +1356,7 @@ rt2860_tx(struct rt2860_softc *sc, struct mbuf *m, struct ieee80211_node *ni) struct rt2860_txd *txd; struct rt2860_txwi *txwi; struct ieee80211_frame *wh; + struct mbuf *m1; bus_dma_segment_t *seg; u_int hdrlen; uint16_t qos, dur; @@ -1500,10 +1501,24 @@ rt2860_tx(struct rt2860_softc *sc, struct mbuf *m, struct ieee80211_node *ni) } if (__predict_false(error != 0)) { /* too many fragments, linearize */ - if (m_defrag(m, M_DONTWAIT) != 0) { + MGETHDR(m1, MT_DATA, M_DONTWAIT); + if (m1 == NULL) { m_freem(m); return ENOBUFS; } + if (m->m_pkthdr.len > MHLEN) { + MCLGET(m1, M_DONTWAIT); + if (!(m1->m_flags & M_EXT)) { + m_freem(m); + m_freem(m1); + return ENOBUFS; + } + } + m_copydata(m, 0, m->m_pkthdr.len, mtod(m1, caddr_t)); + m1->m_pkthdr.len = m1->m_len = m->m_pkthdr.len; + m_freem(m); + m = m1; + error = bus_dmamap_load_mbuf(sc->sc_dmat, data->map, m, BUS_DMA_NOWAIT); if (__predict_false(error != 0)) { |