ifnet_ret_t pdq_ifstart( struct ifnet *ifp) { pdq_softc_t *sc = (pdq_softc_t *) ((caddr_t) ifp - offsetof(pdq_softc_t, sc_arpcom.ac_if)); struct mbuf *m; int tx = 0; if ((ifp->if_flags & IFF_RUNNING) == 0) return; if (sc->sc_if.if_timer == 0) sc->sc_if.if_timer = PDQ_OS_TX_TIMEOUT; if ((sc->sc_pdq->pdq_flags & PDQ_TXOK) == 0) { sc->sc_if.if_flags |= IFF_OACTIVE; return; } for (;; tx = 1) { IFQ_POLL(&ifp->if_snd, m); if (m == NULL) break; if (pdq_queue_transmit_data(sc->sc_pdq, m) == PDQ_FALSE) { ifp->if_flags |= IFF_OACTIVE; break; } IFQ_DEQUEUE(&ifp->if_snd, m); } if (tx) PDQ_DO_TYPE2_PRODUCER(sc->sc_pdq); }
static void pdq_ifstart_locked(struct ifnet *ifp) { pdq_softc_t * const sc = PDQ_OS_IFP_TO_SOFTC(ifp); struct mbuf *m; int tx = 0; PDQ_LOCK_ASSERT(sc); if ((ifp->if_drv_flags & IFF_DRV_RUNNING) == 0) return; if (sc->timer == 0) sc->timer = PDQ_OS_TX_TIMEOUT; if ((sc->sc_pdq->pdq_flags & PDQ_TXOK) == 0) { PDQ_IFNET(sc)->if_drv_flags |= IFF_DRV_OACTIVE; return; } sc->sc_flags |= PDQIF_DOWNCALL; for (;; tx = 1) { IF_DEQUEUE(&ifp->if_snd, m); if (m == NULL) break; #if defined(PDQ_BUS_DMA) && !defined(PDQ_BUS_DMA_NOTX) if ((m->m_flags & M_HASTXDMAMAP) == 0) { bus_dmamap_t map; if (PDQ_OS_HDR_OFFSET != PDQ_RX_FC_OFFSET) { m->m_data[0] = PDQ_FDDI_PH0; m->m_data[1] = PDQ_FDDI_PH1; m->m_data[2] = PDQ_FDDI_PH2; } if (!bus_dmamap_create(sc->sc_dmatag, m->m_pkthdr.len, 255, m->m_pkthdr.len, 0, BUS_DMA_NOWAIT, &map)) { if (!bus_dmamap_load_mbuf(sc->sc_dmatag, map, m, BUS_DMA_WRITE|BUS_DMA_NOWAIT)) { bus_dmamap_sync(sc->sc_dmatag, map, 0, m->m_pkthdr.len, BUS_DMASYNC_PREWRITE); M_SETCTX(m, map); m->m_flags |= M_HASTXDMAMAP; } } if ((m->m_flags & M_HASTXDMAMAP) == 0) break; } #else if (PDQ_OS_HDR_OFFSET != PDQ_RX_FC_OFFSET) { m->m_data[0] = PDQ_FDDI_PH0; m->m_data[1] = PDQ_FDDI_PH1; m->m_data[2] = PDQ_FDDI_PH2; } #endif if (pdq_queue_transmit_data(sc->sc_pdq, m) == PDQ_FALSE) break; } if (m != NULL) { ifp->if_drv_flags |= IFF_DRV_OACTIVE; IF_PREPEND(&ifp->if_snd, m); } if (tx) PDQ_DO_TYPE2_PRODUCER(sc->sc_pdq); sc->sc_flags &= ~PDQIF_DOWNCALL; }