[dpdk-dev] [PATCH v5 1/4] app/eventdev: add event timer adapter as a producer
Maxime Coquelin
maxime.coquelin at redhat.com
Tue Apr 17 10:18:55 CEST 2018
On 04/06/2018 05:13 PM, Pavan Nikhilesh wrote:
> Add event timer adapter as producer option that can be selected by
> passing --prod_type_timerdev.
>
> Signed-off-by: Pavan Nikhilesh <pbhagavatula at caviumnetworks.com>
> Acked-by: Erik Gabriel Carrillo <erik.g.carrillo at intel.com>
> Acked-by: Jerin Jacob <jerin.jacob at caviumnetworks.com>
> ---
>
> v5 Changes:
> - Resending cause missing Acked-by.
>
> v4 Changes:
> - reuse struct rte_event_timer's unused data portion to store timestamp
> instead of spilling timestamp into a new cacheline.
> - change bkt_tck_nsec to timer_tick_nsec
> - change nb_bkt_tcks to expiry_nsec
>
> v3 Changes:
> - Add detailed options dump.
> - Fix few typos.
>
> v2 Changes:
> - set timer to NOT_ARMED before trying to arm it.
> - prevent edge cases for timeout_ticks being set to 0.
>
> app/test-eventdev/evt_options.c | 54 ++++++---
> app/test-eventdev/evt_options.h | 24 ++++
> app/test-eventdev/test_perf_atq.c | 10 +-
> app/test-eventdev/test_perf_common.c | 171 +++++++++++++++++++++++++--
> app/test-eventdev/test_perf_common.h | 14 ++-
> app/test-eventdev/test_perf_queue.c | 7 +-
> 6 files changed, 243 insertions(+), 37 deletions(-)
>
> diff --git a/app/test-eventdev/evt_options.c b/app/test-eventdev/evt_options.c
> index 9683b2224..47e37bc9b 100644
> --- a/app/test-eventdev/evt_options.c
> +++ b/app/test-eventdev/evt_options.c
> @@ -27,6 +27,11 @@ evt_options_default(struct evt_options *opt)
> opt->pool_sz = 16 * 1024;
> opt->wkr_deq_dep = 16;
> opt->nb_pkts = (1ULL << 26); /* do ~64M packets */
> + opt->nb_timers = 1E8;
> + opt->nb_timer_adptrs = 1;
> + opt->timer_tick_nsec = 1E3; /* 1000ns ~ 1us */
> + opt->max_tmo_nsec = 1E5; /* 100000ns ~100us */
> + opt->expiry_nsec = 1E4; /* 10000ns ~10us */
> opt->prod_type = EVT_PROD_TYPE_SYNT;
> }
>
> @@ -86,6 +91,13 @@ evt_parse_eth_prod_type(struct evt_options *opt, const char *arg __rte_unused)
> return 0;
> }
>
> +static int
> +evt_parse_timer_prod_type(struct evt_options *opt, const char *arg __rte_unused)
> +{
> + opt->prod_type = EVT_PROD_TYPE_EVENT_TIMER_ADPTR;
> + return 0;
> +}
> +
> static int
> evt_parse_test_name(struct evt_options *opt, const char *arg)
> {
> @@ -169,7 +181,10 @@ usage(char *program)
> "\t--worker_deq_depth : dequeue depth of the worker\n"
> "\t--fwd_latency : perform fwd_latency measurement\n"
> "\t--queue_priority : enable queue priority\n"
> - "\t--prod_type_ethdev : use ethernet device as producer\n."
> + "\t--prod_type_ethdev : use ethernet device as producer.\n"
> + "\t--prod_type_timerdev : use event timer device as producer.\n"
> + "\t expity_nsec would be the timeout\n"
> + "\t in ns.\n"
> );
> printf("available tests:\n");
> evt_test_dump_names();
> @@ -217,22 +232,23 @@ evt_parse_sched_type_list(struct evt_options *opt, const char *arg)
> }
>
> static struct option lgopts[] = {
> - { EVT_NB_FLOWS, 1, 0, 0 },
> - { EVT_DEVICE, 1, 0, 0 },
> - { EVT_VERBOSE, 1, 0, 0 },
> - { EVT_TEST, 1, 0, 0 },
> - { EVT_PROD_LCORES, 1, 0, 0 },
> - { EVT_WORK_LCORES, 1, 0, 0 },
> - { EVT_SOCKET_ID, 1, 0, 0 },
> - { EVT_POOL_SZ, 1, 0, 0 },
> - { EVT_NB_PKTS, 1, 0, 0 },
> - { EVT_WKR_DEQ_DEP, 1, 0, 0 },
> - { EVT_SCHED_TYPE_LIST, 1, 0, 0 },
> - { EVT_FWD_LATENCY, 0, 0, 0 },
> - { EVT_QUEUE_PRIORITY, 0, 0, 0 },
> - { EVT_PROD_ETHDEV, 0, 0, 0 },
> - { EVT_HELP, 0, 0, 0 },
> - { NULL, 0, 0, 0 }
> + { EVT_NB_FLOWS, 1, 0, 0 },
> + { EVT_DEVICE, 1, 0, 0 },
> + { EVT_VERBOSE, 1, 0, 0 },
> + { EVT_TEST, 1, 0, 0 },
> + { EVT_PROD_LCORES, 1, 0, 0 },
> + { EVT_WORK_LCORES, 1, 0, 0 },
> + { EVT_SOCKET_ID, 1, 0, 0 },
> + { EVT_POOL_SZ, 1, 0, 0 },
> + { EVT_NB_PKTS, 1, 0, 0 },
> + { EVT_WKR_DEQ_DEP, 1, 0, 0 },
> + { EVT_SCHED_TYPE_LIST, 1, 0, 0 },
> + { EVT_FWD_LATENCY, 0, 0, 0 },
> + { EVT_QUEUE_PRIORITY, 0, 0, 0 },
> + { EVT_PROD_ETHDEV, 0, 0, 0 },
> + { EVT_PROD_TIMERDEV, 0, 0, 0 },
> + { EVT_HELP, 0, 0, 0 },
> + { NULL, 0, 0, 0 }
> };
>
> static int
> @@ -255,11 +271,12 @@ evt_opts_parse_long(int opt_idx, struct evt_options *opt)
> { EVT_FWD_LATENCY, evt_parse_fwd_latency},
> { EVT_QUEUE_PRIORITY, evt_parse_queue_priority},
> { EVT_PROD_ETHDEV, evt_parse_eth_prod_type},
> + { EVT_PROD_TIMERDEV, evt_parse_timer_prod_type},
> };
>
> for (i = 0; i < RTE_DIM(parsermap); i++) {
> if (strncmp(lgopts[opt_idx].name, parsermap[i].lgopt_name,
> - strlen(parsermap[i].lgopt_name)) == 0)
> + strlen(lgopts[opt_idx].name)) == 0)
> return parsermap[i].parser_fn(opt, optarg);
> }
>
> @@ -305,6 +322,7 @@ evt_options_dump(struct evt_options *opt)
> evt_dump("pool_sz", "%d", opt->pool_sz);
> evt_dump("master lcore", "%d", rte_get_master_lcore());
> evt_dump("nb_pkts", "%"PRIu64, opt->nb_pkts);
> + evt_dump("nb_timers", "%"PRIu64, opt->nb_timers);
> evt_dump_begin("available lcores");
> RTE_LCORE_FOREACH(lcore_id)
> printf("%d ", lcore_id);
> diff --git a/app/test-eventdev/evt_options.h b/app/test-eventdev/evt_options.h
> index 46d122229..b51d8d5b3 100644
> --- a/app/test-eventdev/evt_options.h
> +++ b/app/test-eventdev/evt_options.h
> @@ -9,6 +9,7 @@
> #include <stdbool.h>
>
> #include <rte_common.h>
> +#include <rte_ethdev.h>
> #include <rte_eventdev.h>
> #include <rte_lcore.h>
>
> @@ -31,12 +32,14 @@
> #define EVT_FWD_LATENCY ("fwd_latency")
> #define EVT_QUEUE_PRIORITY ("queue_priority")
> #define EVT_PROD_ETHDEV ("prod_type_ethdev")
> +#define EVT_PROD_TIMERDEV ("prod_type_timerdev")
> #define EVT_HELP ("help")
>
> enum evt_prod_type {
> EVT_PROD_TYPE_NONE,
> EVT_PROD_TYPE_SYNT, /* Producer type Synthetic i.e. CPU. */
> EVT_PROD_TYPE_ETH_RX_ADPTR, /* Producer type Eth Rx Adapter. */
> + EVT_PROD_TYPE_EVENT_TIMER_ADPTR, /* Producer type Timer Adapter. */
> EVT_PROD_TYPE_MAX,
> };
>
> @@ -52,11 +55,18 @@ struct evt_options {
> int nb_stages;
> int verbose_level;
> uint64_t nb_pkts;
> + uint8_t nb_timer_adptrs;
> + uint64_t nb_timers;
> + uint64_t timer_tick_nsec;
> + uint64_t optm_timer_tick_nsec;
> + uint64_t max_tmo_nsec;
> + uint64_t expiry_nsec;
> uint16_t wkr_deq_dep;
> uint8_t dev_id;
> uint32_t fwd_latency:1;
> uint32_t q_priority:1;
> enum evt_prod_type prod_type;
> + uint8_t timdev_cnt;
> };
>
> void evt_options_default(struct evt_options *opt);
> @@ -262,6 +272,20 @@ evt_dump_producer_type(struct evt_options *opt)
> case EVT_PROD_TYPE_ETH_RX_ADPTR:
> snprintf(name, EVT_PROD_MAX_NAME_LEN,
> "Ethdev Rx Adapter producers");
> + evt_dump("nb_ethdev", "%d", rte_eth_dev_count());
> + break;
> + case EVT_PROD_TYPE_EVENT_TIMER_ADPTR:
> + snprintf(name, EVT_PROD_MAX_NAME_LEN,
> + "Event timer adapter producer");
> + evt_dump("nb_timer_adapters", "%d", opt->nb_timer_adptrs);
> + evt_dump("max_tmo_nsec", "%"PRIu64"", opt->max_tmo_nsec);
> + evt_dump("expiry_nsec", "%"PRIu64"", opt->expiry_nsec);
> + if (opt->optm_timer_tick_nsec)
> + evt_dump("optm_timer_tick_ns", "%"PRIu64"",
> + opt->optm_timer_tick_nsec);
> + else
> + evt_dump("timer_tick_ns", "%"PRIu64"",
> + opt->timer_tick_nsec);
> break;
> }
> evt_dump("prod_type", "%s", name);
> diff --git a/app/test-eventdev/test_perf_atq.c b/app/test-eventdev/test_perf_atq.c
> index b36b22a77..b3a312722 100644
> --- a/app/test-eventdev/test_perf_atq.c
> +++ b/app/test-eventdev/test_perf_atq.c
> @@ -43,15 +43,12 @@ perf_atq_worker(void *arg, const int enable_fwd_latency)
> while (t->done == false) {
> uint16_t event = rte_event_dequeue_burst(dev, port, &ev, 1, 0);
>
> - if (enable_fwd_latency)
> - rte_prefetch0(ev.event_ptr);
> -
> if (!event) {
> rte_pause();
> continue;
> }
>
> - if (enable_fwd_latency)
> + if (enable_fwd_latency && !prod_timer_type)
> /* first stage in pipeline, mark ts to compute fwd latency */
> atq_mark_fwd_latency(&ev);
>
> @@ -90,7 +87,7 @@ perf_atq_worker_burst(void *arg, const int enable_fwd_latency)
> }
>
> for (i = 0; i < nb_rx; i++) {
> - if (enable_fwd_latency) {
> + if (enable_fwd_latency && !prod_timer_type) {
> rte_prefetch0(ev[i+1].event_ptr);
> /* first stage in pipeline.
> * mark time stamp to compute fwd latency
> @@ -163,7 +160,8 @@ perf_atq_eventdev_setup(struct evt_test *test, struct evt_options *opt)
> struct rte_event_dev_info dev_info;
>
> nb_ports = evt_nr_active_lcores(opt->wlcores);
> - nb_ports += opt->prod_type == EVT_PROD_TYPE_ETH_RX_ADPTR ? 0 :
> + nb_ports += (opt->prod_type == EVT_PROD_TYPE_ETH_RX_ADPTR ||
> + opt->prod_type == EVT_PROD_TYPE_EVENT_TIMER_ADPTR) ? 0 :
> evt_nr_active_lcores(opt->plcores);
>
> nb_queues = atq_nb_event_queues(opt);
> diff --git a/app/test-eventdev/test_perf_common.c b/app/test-eventdev/test_perf_common.c
> index 59fa0a49e..b6cc00e60 100644
> --- a/app/test-eventdev/test_perf_common.c
> +++ b/app/test-eventdev/test_perf_common.c
> @@ -72,6 +72,67 @@ perf_producer(void *arg)
> return 0;
> }
>
> +static inline int
> +perf_event_timer_producer(void *arg)
> +{
> + struct prod_data *p = arg;
> + struct test_perf *t = p->t;
> + struct evt_options *opt = t->opt;
> + uint32_t flow_counter = 0;
> + uint64_t count = 0;
> + uint64_t arm_latency = 0;
> + const uint8_t nb_timer_adptrs = opt->nb_timer_adptrs;
> + const uint32_t nb_flows = t->nb_flows;
> + const uint64_t nb_timers = opt->nb_timers;
> + struct rte_mempool *pool = t->pool;
> + struct perf_elt *m;
> + struct rte_event_timer_adapter **adptr = t->timer_adptr;
> + uint64_t timeout_ticks = opt->expiry_nsec / opt->timer_tick_nsec;
> +
> + timeout_ticks = opt->optm_timer_tick_nsec ?
> + (timeout_ticks * opt->timer_tick_nsec)
> + / opt->optm_timer_tick_nsec : timeout_ticks;
> + timeout_ticks += timeout_ticks ? 0 : 1;
> + const struct rte_event_timer tim = {
> + .ev.op = RTE_EVENT_OP_NEW,
> + .ev.queue_id = p->queue_id,
> + .ev.sched_type = t->opt->sched_type_list[0],
> + .ev.priority = RTE_EVENT_DEV_PRIORITY_NORMAL,
> + .ev.event_type = RTE_EVENT_TYPE_TIMER,
> + .state = RTE_EVENT_TIMER_NOT_ARMED,
> + .timeout_ticks = timeout_ticks,
> + };
It seems your patch introduce build regression on RHEL 7.5:
$ gcc --version
gcc (GCC) 4.8.5 20150623 (Red Hat 4.8.5-28)
$ make -j32 install T=x86_64-native-linuxapp-gcc DESTDIR=legacy_destdir
== Build app/test-eventdev
CC test_perf_common.o
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c: In function
‘perf_event_timer_producer’:
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:99:3: error:
missing initializer for field ‘priority’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.ev.sched_type = t->opt->sched_type_list[0],
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1049:12:
note: ‘priority’ declared here
uint8_t priority;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:100:3: error:
missing initializer for field ‘priority’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.ev.priority = RTE_EVENT_DEV_PRIORITY_NORMAL,
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1049:12:
note: ‘priority’ declared here
uint8_t priority;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:101:3: error:
missing initializer for field ‘impl_opaque’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.ev.event_type = RTE_EVENT_TYPE_TIMER,
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1059:12:
note: ‘impl_opaque’ declared here
uint8_t impl_opaque;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:102:3: error:
missing initializer for field ‘impl_opaque’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.state = RTE_EVENT_TIMER_NOT_ARMED,
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1059:12:
note: ‘impl_opaque’ declared here
uint8_t impl_opaque;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c: In function
‘perf_event_timer_producer_burst’:
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:161:3: error:
missing initializer for field ‘priority’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.ev.sched_type = t->opt->sched_type_list[0],
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1049:12:
note: ‘priority’ declared here
uint8_t priority;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:162:3: error:
missing initializer for field ‘priority’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.ev.priority = RTE_EVENT_DEV_PRIORITY_NORMAL,
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1049:12:
note: ‘priority’ declared here
uint8_t priority;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:163:3: error:
missing initializer for field ‘impl_opaque’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.ev.event_type = RTE_EVENT_TYPE_TIMER,
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1059:12:
note: ‘impl_opaque’ declared here
uint8_t impl_opaque;
^
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:164:3: error:
missing initializer for field ‘impl_opaque’ of ‘struct <anonymous>’
[-Werror=missing-field-initializers]
.state = RTE_EVENT_TIMER_NOT_ARMED,
^
In file included from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.h:14:0,
from
/tmp/dpdk_build/app/test-eventdev/test_perf_common.c:5:
/tmp/dpdk_build/x86_64-native-linuxapp-gcc/include/rte_eventdev.h:1059:12:
note: ‘impl_opaque’ declared here
uint8_t impl_opaque;
^
cc1: all warnings being treated as errors
make[5]: *** [test_perf_common.o] Error 1
make[4]: *** [test-eventdev] Error 2
make[3]: *** [app] Error 2
make[2]: *** [all] Error 2
make[1]: *** [pre_install] Error 2
make: *** [install] Error 2
Regards,
Maxime
More information about the dev
mailing list