Push generic parts of input/output queue config code to upper level (into odp_packet_io.c).
Signed-off-by: Petri Savolainen <petri.savolai...@nokia.com> --- platform/linux-generic/include/odp_packet_netmap.h | 7 +- platform/linux-generic/odp_packet_io.c | 186 ++++++++++++++------- platform/linux-generic/pktio/netmap.c | 108 ++---------- 3 files changed, 139 insertions(+), 162 deletions(-) diff --git a/platform/linux-generic/include/odp_packet_netmap.h b/platform/linux-generic/include/odp_packet_netmap.h index dae770d..26a8da1 100644 --- a/platform/linux-generic/include/odp_packet_netmap.h +++ b/platform/linux-generic/include/odp_packet_netmap.h @@ -48,13 +48,10 @@ typedef struct { unsigned cur_rx_queue; /**< current pktin queue */ uint32_t num_rx_rings; /**< number of nm rx rings */ uint32_t num_tx_rings; /**< number of nm tx rings */ + unsigned num_rx_desc_rings; /**< number of rx descriptor rings */ + unsigned num_tx_desc_rings; /**< number of tx descriptor rings */ odp_bool_t lockless_rx; /**< no locking for rx */ odp_bool_t lockless_tx; /**< no locking for tx */ - /** State of netmap descriptors */ - enum { - NM_DESC_INVALID = 0, - NM_DESC_VALID - } desc_state; /** mapping of pktin queues to netmap rx descriptors */ netmap_ring_t rx_desc_ring[PKTIO_MAX_QUEUES]; /** mapping of pktout queues to netmap tx descriptors */ diff --git a/platform/linux-generic/odp_packet_io.c b/platform/linux-generic/odp_packet_io.c index 95b8904..1b1f811 100644 --- a/platform/linux-generic/odp_packet_io.c +++ b/platform/linux-generic/odp_packet_io.c @@ -279,6 +279,18 @@ static int _pktio_close(pktio_entry_t *entry) return 0; } +static void destroy_in_queues(pktio_entry_t *entry, int num) +{ + int i; + + for (i = 0; i < num; i++) { + if (entry->s.in_queue[i].queue != ODP_QUEUE_INVALID) { + odp_queue_destroy(entry->s.in_queue[i].queue); + entry->s.in_queue[i].queue = ODP_QUEUE_INVALID; + } + } +} + int odp_pktio_close(odp_pktio_t id) { pktio_entry_t *entry; @@ -289,6 +301,9 @@ int odp_pktio_close(odp_pktio_t id) return -1; lock_entry(entry); + + destroy_in_queues(entry, entry->s.num_in_queue); + if (!is_free(entry)) { res = _pktio_close(entry); if (res) @@ -971,9 +986,16 @@ int odp_pktio_input_queues_config(odp_pktio_t pktio, const odp_pktio_input_queue_param_t *param) { pktio_entry_t *entry; + odp_pktio_input_mode_t mode; + odp_pktio_capability_t capa; + unsigned num_queues; + unsigned i; + odp_queue_t queue; - if (param == NULL) + if (param == NULL) { + ODP_DBG("no parameters\n"); return -1; + } entry = get_pktio_entry(pktio); if (entry == NULL) { @@ -981,10 +1003,69 @@ int odp_pktio_input_queues_config(odp_pktio_t pktio, return -1; } + if (entry->s.state != STATE_STOP) { + ODP_DBG("pktio %s: not stopped\n", entry->s.name); + return -1; + } + + mode = entry->s.param.in_mode; + + if (mode == ODP_PKTIN_MODE_DISABLED) { + ODP_DBG("pktio %s: packet input is disabled\n", entry->s.name); + return -1; + } + + num_queues = param->num_queues; + + if (num_queues == 0) { + ODP_DBG("pktio %s: zero input queues\n", entry->s.name); + return -1; + } + + odp_pktio_capability(pktio, &capa); + + if (num_queues > capa.max_input_queues) { + ODP_DBG("pktio %s: too many input queues\n", entry->s.name); + return -1; + } + + /* If re-configuring, destroy old queues */ + if (entry->s.num_in_queue) + destroy_in_queues(entry, entry->s.num_in_queue); + + for (i = 0; i < num_queues; i++) { + if (mode == ODP_PKTIN_MODE_POLL || + mode == ODP_PKTIN_MODE_SCHED) { + odp_queue_type_t type = ODP_QUEUE_TYPE_POLL; + + if (mode == ODP_PKTIN_MODE_SCHED) + type = ODP_QUEUE_TYPE_SCHED; + + /* Ugly cast to uintptr_t is needed since queue_param + * is not defined as const in odp_queue_create() */ + queue = odp_queue_create("pktio_in", type, + (odp_queue_param_t *) + (uintptr_t) + ¶m->queue_param); + if (queue == ODP_QUEUE_INVALID) { + destroy_in_queues(entry, i + 1); + return -1; + } + entry->s.in_queue[i].queue = queue; + } else { + entry->s.in_queue[i].queue = ODP_QUEUE_INVALID; + } + + entry->s.in_queue[i].pktin.index = i; + entry->s.in_queue[i].pktin.pktio = entry->s.handle; + } + + entry->s.num_in_queue = num_queues; + if (entry->s.ops->input_queues_config) return entry->s.ops->input_queues_config(entry, param); - return single_input_queues_config(entry, param); + return 0; } int odp_pktio_output_queues_config(odp_pktio_t pktio, @@ -992,9 +1073,14 @@ int odp_pktio_output_queues_config(odp_pktio_t pktio, { pktio_entry_t *entry; odp_pktio_output_mode_t mode; + odp_pktio_capability_t capa; + unsigned num_queues; + unsigned i; - if (param == NULL) + if (param == NULL) { + ODP_DBG("no parameters\n"); return -1; + } entry = get_pktio_entry(pktio); if (entry == NULL) { @@ -1002,15 +1088,48 @@ int odp_pktio_output_queues_config(odp_pktio_t pktio, return -1; } + if (entry->s.state != STATE_STOP) { + ODP_DBG("pktio %s: not stopped\n", entry->s.name); + return -1; + } + mode = entry->s.param.out_mode; - if (mode != ODP_PKTOUT_MODE_SEND) + if (mode == ODP_PKTOUT_MODE_DISABLED) { + ODP_DBG("pktio %s: packet output is disabled\n", entry->s.name); return -1; + } + + if (mode != ODP_PKTOUT_MODE_SEND) { + ODP_DBG("pktio %s: bad packet output mode\n", entry->s.name); + return -1; + } + + num_queues = param->num_queues; + + if (num_queues == 0) { + ODP_DBG("pktio %s: zero output queues\n", entry->s.name); + return -1; + } + + odp_pktio_capability(pktio, &capa); + + if (num_queues > capa.max_output_queues) { + ODP_DBG("pktio %s: too many output queues\n", entry->s.name); + return -1; + } + + for (i = 0; i < num_queues; i++) { + entry->s.out_queue[i].pktout.index = i; + entry->s.out_queue[i].pktout.pktio = entry->s.handle; + } + + entry->s.num_out_queue = num_queues; if (entry->s.ops->output_queues_config) return entry->s.ops->output_queues_config(entry, param); - return single_output_queues_config(entry, param); + return 0; } int odp_pktio_in_queues(odp_pktio_t pktio, odp_queue_t queues[], int num) @@ -1129,63 +1248,6 @@ int single_capability(odp_pktio_capability_t *capa) return 0; } -int single_input_queues_config(pktio_entry_t *entry, - const odp_pktio_input_queue_param_t *param) -{ - odp_queue_t queue; - odp_pktio_input_mode_t mode; - - mode = entry->s.param.in_mode; - - if (param->num_queues != 1) - return -1; - - if (mode == ODP_PKTIN_MODE_DISABLED) - return -1; - - if (mode == ODP_PKTIN_MODE_POLL || - mode == ODP_PKTIN_MODE_SCHED) { - odp_queue_type_t type = ODP_QUEUE_TYPE_POLL; - - if (mode == ODP_PKTIN_MODE_SCHED) - type = ODP_QUEUE_TYPE_SCHED; - - /* Ugly cast to uintptr_t is needed since queue_param is - * not defined as const in odp_queue_create() */ - queue = odp_queue_create("pktio_in", type, - (odp_queue_param_t *)(uintptr_t) - ¶m->queue_param); - - if (queue == ODP_QUEUE_INVALID) - return -1; - - entry->s.in_queue[0].queue = queue; - } else { - entry->s.in_queue[0].queue = ODP_QUEUE_INVALID; - } - - entry->s.in_queue[0].pktin.pktio = entry->s.handle; - entry->s.in_queue[0].pktin.index = 0; - - entry->s.num_in_queue = 1; - - return 0; -} - -int single_output_queues_config(pktio_entry_t *entry, - const odp_pktio_output_queue_param_t *param) -{ - if (param->num_queues != 1) - return -1; - - entry->s.out_queue[0].pktout.pktio = entry->s.handle; - entry->s.out_queue[0].pktout.index = 0; - - entry->s.num_out_queue = 1; - - return 0; -} - int single_in_queues(pktio_entry_t *entry, odp_queue_t queues[], int num) { if (queues && num > 0) diff --git a/platform/linux-generic/pktio/netmap.c b/platform/linux-generic/pktio/netmap.c index a347d29..a1bb361 100644 --- a/platform/linux-generic/pktio/netmap.c +++ b/platform/linux-generic/pktio/netmap.c @@ -124,42 +124,14 @@ static inline void map_netmap_rings(netmap_ring_t *rings, } } -/** - * Close pktio queues - * - * @param pktio_entry Packet IO entry - */ -static inline void netmap_close_queues(pktio_entry_t *pktio_entry) -{ - int i; - struct pktio_entry *pktio = &pktio_entry->s; - odp_pktio_input_mode_t mode = pktio_entry->s.param.in_mode; - - for (i = 0; i < PKTIO_MAX_QUEUES; i++) { - if (mode != ODP_PKTIN_MODE_POLL && mode != ODP_PKTIN_MODE_SCHED) - continue; - - if (pktio->in_queue[i].queue != ODP_QUEUE_INVALID) { - odp_queue_destroy(pktio->in_queue[i].queue); - pktio->in_queue[i].queue = ODP_QUEUE_INVALID; - } - } -} - static int netmap_input_queues_config(pktio_entry_t *pktio_entry, const odp_pktio_input_queue_param_t *p) { - struct pktio_entry *pktio = &pktio_entry->s; pkt_netmap_t *pkt_nm = &pktio_entry->s.pkt_nm; odp_pktio_input_mode_t mode = pktio_entry->s.param.in_mode; - odp_queue_t queue; unsigned num_queues = p->num_queues; - unsigned i; odp_bool_t single_user; - if (mode == ODP_PKTIN_MODE_DISABLED || pktio->state != STATE_STOP) - return -1; - /* Scheduler synchronizes input queue polls. Only single thread * at a time polls a queue */ if (mode == ODP_PKTIN_MODE_SCHED) @@ -167,11 +139,6 @@ static int netmap_input_queues_config(pktio_entry_t *pktio_entry, else single_user = p->single_user; - if (num_queues <= 0 || num_queues > pkt_nm->capa.max_input_queues) { - ODP_ERR("Invalid input queue count: %u\n", num_queues); - return -1; - } - if (p->hash_enable && num_queues > 1) { if (rss_conf_set_fd(pktio_entry->s.pkt_nm.sockfd, pktio_entry->s.name, &p->hash_proto)) { @@ -180,71 +147,18 @@ static int netmap_input_queues_config(pktio_entry_t *pktio_entry, } } - netmap_close_queues(pktio_entry); - - for (i = 0; i < num_queues; i++) { - if (mode == ODP_PKTIN_MODE_POLL || - mode == ODP_PKTIN_MODE_SCHED) { - odp_queue_type_t type = ODP_QUEUE_TYPE_POLL; - - if (mode == ODP_PKTIN_MODE_SCHED) - type = ODP_QUEUE_TYPE_SCHED; - - /* Ugly cast to uintptr_t is needed since queue_param - * is not defined as const in odp_queue_create() */ - queue = odp_queue_create("pktio_in", type, - (odp_queue_param_t *) - (uintptr_t)&p->queue_param); - if (queue == ODP_QUEUE_INVALID) { - netmap_close_queues(pktio_entry); - return -1; - } - pktio->in_queue[i].queue = queue; - } else { - pktio->in_queue[i].queue = ODP_QUEUE_INVALID; - } - - pktio->in_queue[i].pktin.index = i; - pktio->in_queue[i].pktin.pktio = pktio_entry->s.handle; - } - pkt_nm->lockless_rx = single_user; - if (pktio_entry->s.num_in_queue != num_queues) - pkt_nm->desc_state = NM_DESC_INVALID; - - pktio_entry->s.num_in_queue = num_queues; return 0; } static int netmap_output_queues_config(pktio_entry_t *pktio_entry, const odp_pktio_output_queue_param_t *p) { - struct pktio_entry *pktio = &pktio_entry->s; pkt_netmap_t *pkt_nm = &pktio_entry->s.pkt_nm; - odp_pktio_output_mode_t mode = pktio_entry->s.param.out_mode; - unsigned num_queues = p->num_queues; - unsigned i; - if (mode == ODP_PKTOUT_MODE_DISABLED || pktio->state != STATE_STOP) - return -1; - - if (num_queues <= 0 || num_queues > pkt_nm->capa.max_output_queues) { - ODP_ERR("Invalid output queue count: %u\n", num_queues); - return -1; - } pkt_nm->lockless_tx = p->single_user; - if (num_queues == pktio_entry->s.num_out_queue) /* Already configured */ - return 0; - - for (i = 0; i < num_queues; i++) { - pktio->out_queue[i].pktout.index = i; - pktio->out_queue[i].pktout.pktio = pktio_entry->s.handle; - } - pkt_nm->desc_state = NM_DESC_INVALID; - pktio_entry->s.num_out_queue = num_queues; - return 0; } @@ -274,7 +188,9 @@ static inline void netmap_close_descriptors(pktio_entry_t *pktio_entry) } } } - pkt_nm->desc_state = NM_DESC_INVALID; + + pkt_nm->num_rx_desc_rings = 0; + pkt_nm->num_tx_desc_rings = 0; } static int netmap_close(pktio_entry_t *pktio_entry) @@ -283,8 +199,6 @@ static int netmap_close(pktio_entry_t *pktio_entry) netmap_close_descriptors(pktio_entry); - netmap_close_queues(pktio_entry); - if (pkt_nm->sockfd != -1 && close(pkt_nm->sockfd) != 0) { __odp_errno = errno; ODP_ERR("close(sockfd): %s\n", strerror(errno)); @@ -457,21 +371,24 @@ static int netmap_start(pktio_entry_t *pktio_entry) in_mode != ODP_PKTIN_MODE_DISABLED) { odp_pktio_input_queue_param_t param; - memset(¶m, 0, sizeof(odp_pktio_input_queue_param_t)); + odp_pktio_input_queue_param_init(¶m); param.num_queues = 1; - if (netmap_input_queues_config(pktio_entry, ¶m)) + if (odp_pktio_input_queues_config(pktio_entry->s.handle, + ¶m)) return -1; } if (!pktio_entry->s.num_out_queue && out_mode == ODP_PKTOUT_MODE_SEND) { odp_pktio_output_queue_param_t param; - memset(¶m, 0, sizeof(odp_pktio_output_queue_param_t)); + odp_pktio_output_queue_param_init(¶m); param.num_queues = 1; - if (netmap_output_queues_config(pktio_entry, ¶m)) + if (odp_pktio_output_queues_config(pktio_entry->s.handle, + ¶m)) return -1; } - if (pkt_nm->desc_state == NM_DESC_VALID) + if (pkt_nm->num_rx_desc_rings == pktio_entry->s.num_in_queue && + pkt_nm->num_tx_desc_rings == pktio_entry->s.num_out_queue) return (netmap_wait_for_link(pktio_entry) == 1) ? 0 : -1; netmap_close_descriptors(pktio_entry); @@ -535,7 +452,8 @@ static int netmap_start(pktio_entry_t *pktio_entry) } } } - pkt_nm->desc_state = NM_DESC_VALID; + pkt_nm->num_rx_desc_rings = pktio_entry->s.num_in_queue; + pkt_nm->num_tx_desc_rings = pktio_entry->s.num_out_queue; /* Wait for the link to come up */ return (netmap_wait_for_link(pktio_entry) == 1) ? 0 : -1; -- 2.6.3 _______________________________________________ lng-odp mailing list lng-odp@lists.linaro.org https://lists.linaro.org/mailman/listinfo/lng-odp