Changeset View
Changeset View
Standalone View
Standalone View
head/sys/dev/netmap/netmap.c
Show First 20 Lines • Show All 824 Lines • ▼ Show 20 Lines | |||||
/* call with NMG_LOCK held */ | /* call with NMG_LOCK held */ | ||||
int | int | ||||
netmap_krings_create(struct netmap_adapter *na, u_int tailroom) | netmap_krings_create(struct netmap_adapter *na, u_int tailroom) | ||||
{ | { | ||||
u_int i, len, ndesc; | u_int i, len, ndesc; | ||||
struct netmap_kring *kring; | struct netmap_kring *kring; | ||||
u_int n[NR_TXRX]; | u_int n[NR_TXRX]; | ||||
enum txrx t; | enum txrx t; | ||||
int err = 0; | |||||
if (na->tx_rings != NULL) { | if (na->tx_rings != NULL) { | ||||
if (netmap_debug & NM_DEBUG_ON) | if (netmap_debug & NM_DEBUG_ON) | ||||
nm_prerr("warning: krings were already created"); | nm_prerr("warning: krings were already created"); | ||||
return 0; | return 0; | ||||
} | } | ||||
/* account for the (possibly fake) host rings */ | /* account for the (possibly fake) host rings */ | ||||
Show All 23 Lines | netmap_krings_create(struct netmap_adapter *na, u_int tailroom) | ||||
* All fields in krings are 0 except the one initialized below. | * All fields in krings are 0 except the one initialized below. | ||||
* but better be explicit on important kring fields. | * but better be explicit on important kring fields. | ||||
*/ | */ | ||||
for_rx_tx(t) { | for_rx_tx(t) { | ||||
ndesc = nma_get_ndesc(na, t); | ndesc = nma_get_ndesc(na, t); | ||||
for (i = 0; i < n[t]; i++) { | for (i = 0; i < n[t]; i++) { | ||||
kring = NMR(na, t)[i]; | kring = NMR(na, t)[i]; | ||||
bzero(kring, sizeof(*kring)); | bzero(kring, sizeof(*kring)); | ||||
kring->na = na; | |||||
kring->notify_na = na; | kring->notify_na = na; | ||||
kring->ring_id = i; | kring->ring_id = i; | ||||
kring->tx = t; | kring->tx = t; | ||||
kring->nkr_num_slots = ndesc; | kring->nkr_num_slots = ndesc; | ||||
kring->nr_mode = NKR_NETMAP_OFF; | kring->nr_mode = NKR_NETMAP_OFF; | ||||
kring->nr_pending_mode = NKR_NETMAP_OFF; | kring->nr_pending_mode = NKR_NETMAP_OFF; | ||||
if (i < nma_get_nrings(na, t)) { | if (i < nma_get_nrings(na, t)) { | ||||
kring->nm_sync = (t == NR_TX ? na->nm_txsync : na->nm_rxsync); | kring->nm_sync = (t == NR_TX ? na->nm_txsync : na->nm_rxsync); | ||||
Show All 9 Lines | for (i = 0; i < n[t]; i++) { | ||||
/* | /* | ||||
* IMPORTANT: Always keep one slot empty. | * IMPORTANT: Always keep one slot empty. | ||||
*/ | */ | ||||
kring->rtail = kring->nr_hwtail = (t == NR_TX ? ndesc - 1 : 0); | kring->rtail = kring->nr_hwtail = (t == NR_TX ? ndesc - 1 : 0); | ||||
snprintf(kring->name, sizeof(kring->name) - 1, "%s %s%d", na->name, | snprintf(kring->name, sizeof(kring->name) - 1, "%s %s%d", na->name, | ||||
nm_txrx2str(t), i); | nm_txrx2str(t), i); | ||||
ND("ktx %s h %d c %d t %d", | ND("ktx %s h %d c %d t %d", | ||||
kring->name, kring->rhead, kring->rcur, kring->rtail); | kring->name, kring->rhead, kring->rcur, kring->rtail); | ||||
err = nm_os_selinfo_init(&kring->si, kring->name); | |||||
if (err) { | |||||
netmap_krings_delete(na); | |||||
return err; | |||||
} | |||||
mtx_init(&kring->q_lock, (t == NR_TX ? "nm_txq_lock" : "nm_rxq_lock"), NULL, MTX_DEF); | mtx_init(&kring->q_lock, (t == NR_TX ? "nm_txq_lock" : "nm_rxq_lock"), NULL, MTX_DEF); | ||||
nm_os_selinfo_init(&kring->si); | kring->na = na; /* setting this field marks the mutex as initialized */ | ||||
} | } | ||||
nm_os_selinfo_init(&na->si[t]); | err = nm_os_selinfo_init(&na->si[t], na->name); | ||||
if (err) { | |||||
netmap_krings_delete(na); | |||||
return err; | |||||
} | } | ||||
} | |||||
return 0; | return 0; | ||||
} | } | ||||
/* undo the actions performed by netmap_krings_create */ | /* undo the actions performed by netmap_krings_create */ | ||||
/* call with NMG_LOCK held */ | /* call with NMG_LOCK held */ | ||||
void | void | ||||
netmap_krings_delete(struct netmap_adapter *na) | netmap_krings_delete(struct netmap_adapter *na) | ||||
{ | { | ||||
struct netmap_kring **kring = na->tx_rings; | struct netmap_kring **kring = na->tx_rings; | ||||
enum txrx t; | enum txrx t; | ||||
if (na->tx_rings == NULL) { | if (na->tx_rings == NULL) { | ||||
if (netmap_debug & NM_DEBUG_ON) | if (netmap_debug & NM_DEBUG_ON) | ||||
nm_prerr("warning: krings were already deleted"); | nm_prerr("warning: krings were already deleted"); | ||||
return; | return; | ||||
} | } | ||||
for_rx_tx(t) | for_rx_tx(t) | ||||
nm_os_selinfo_uninit(&na->si[t]); | nm_os_selinfo_uninit(&na->si[t]); | ||||
/* we rely on the krings layout described above */ | /* we rely on the krings layout described above */ | ||||
for ( ; kring != na->tailroom; kring++) { | for ( ; kring != na->tailroom; kring++) { | ||||
if ((*kring)->na != NULL) | |||||
mtx_destroy(&(*kring)->q_lock); | mtx_destroy(&(*kring)->q_lock); | ||||
nm_os_selinfo_uninit(&(*kring)->si); | nm_os_selinfo_uninit(&(*kring)->si); | ||||
} | } | ||||
nm_os_free(na->tx_rings); | nm_os_free(na->tx_rings); | ||||
na->tx_rings = na->rx_rings = na->tailroom = NULL; | na->tx_rings = na->rx_rings = na->tailroom = NULL; | ||||
} | } | ||||
/* | /* | ||||
▲ Show 20 Lines • Show All 3,252 Lines • Show Last 20 Lines |