[dpdk-dev] [PATCH 2/4] eventdev: implement the northbound APIs

Eads, Gage gage.eads at intel.com
Tue Nov 22 20:43:03 CET 2016



>  -----Original Message-----
>  From: Jerin Jacob [mailto:jerin.jacob at caviumnetworks.com]
>  Sent: Tuesday, November 22, 2016 12:19 PM
>  To: Eads, Gage <gage.eads at intel.com>
>  Cc: dev at dpdk.org; Richardson, Bruce <bruce.richardson at intel.com>; Van
>  Haaren, Harry <harry.van.haaren at intel.com>; hemant.agrawal at nxp.com
>  Subject: Re: [dpdk-dev] [PATCH 2/4] eventdev: implement the northbound APIs
>  
>  On Tue, Nov 22, 2016 at 03:15:52PM +0000, Eads, Gage wrote:
>  >
>  >
>  > >  -----Original Message-----
>  > >  From: Jerin Jacob [mailto:jerin.jacob at caviumnetworks.com]
>  > >  Sent: Monday, November 21, 2016 1:32 PM
>  > >  To: Eads, Gage <gage.eads at intel.com>
>  > >  Cc: dev at dpdk.org; Richardson, Bruce <bruce.richardson at intel.com>; Van
>  > >  Haaren, Harry <harry.van.haaren at intel.com>; hemant.agrawal at nxp.com
>  > >  Subject: Re: [dpdk-dev] [PATCH 2/4] eventdev: implement the northbound
>  APIs
>  > >
>  > >  On Tue, Nov 22, 2016 at 12:43:58AM +0530, Jerin Jacob wrote:
>  > >  > On Mon, Nov 21, 2016 at 05:45:51PM +0000, Eads, Gage wrote:
>  > >  > > Hi Jerin,
>  > >  > >
>  > >  > > I did a quick review and overall this implementation looks good. I
>  noticed
>  > >  just one issue in rte_event_queue_setup(): the check of
>  > >  nb_atomic_order_sequences is being applied to atomic-type queues, but
>  that
>  > >  field applies to ordered-type queues.
>  > >  >
>  > >  > Thanks Gage. I will fix that in v2.
>  > >  >
>  > >  > >
>  > >  > > One open issue I noticed is the "typical workflow" description starting in
>  > >  rte_eventdev.h:204 conflicts with the centralized software PMD that Harry
>  > >  posted last week. Specifically, that PMD expects a single core to call the
>  > >  schedule function. We could extend the documentation to account for this
>  > >  alternative style of scheduler invocation, or discuss ways to make the
>  software
>  > >  PMD work with the documented workflow. I prefer the former, but either
>  way I
>  > >  think we ought to expose the scheduler's expected usage to the user --
>  perhaps
>  > >  through an RTE_EVENT_DEV_CAP flag?
>  > >  >
>  > >  > I prefer former too, you can propose the documentation change required
>  for
>  > >  software PMD.
>  >
>  > Sure, proposal follows. The "typical workflow" isn't the most optimal by
>  having a conditional in the fast-path, of course, but it demonstrates the idea
>  simply.
>  >
>  > (line 204)
>  >  * An event driven based application has following typical workflow on
>  fastpath:
>  >  * \code{.c}
>  >  *      while (1) {
>  >  *
>  >  *              if (dev_info.event_dev_cap &
>  >  *                      RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED)
>  >  *                      rte_event_schedule(dev_id);
>  
>  Yes, I like the idea of RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED.
>  It  can be input to application/subsystem to
>  launch separate core(s) for schedule functions.
>  But, I think, the "dev_info.event_dev_cap &
>  RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED"
>  check can be moved inside the implementation(to make the better decisions
>  and
>  avoiding consuming cycles on HW based schedulers.

How would this check work? Wouldn't it prevent any core from running the software scheduler in the centralized case?

>  
>  >  *
>  >  *              rte_event_dequeue(...);
>  >  *
>  >  *              (event processing)
>  >  *
>  >  *              rte_event_enqueue(...);
>  >  *      }
>  >  * \endcode
>  >  *
>  >  * The *schedule* operation is intended to do event scheduling, and the
>  >  * *dequeue* operation returns the scheduled events. An implementation
>  >  * is free to define the semantics between *schedule* and *dequeue*. For
>  >  * example, a system based on a hardware scheduler can define its
>  >  * rte_event_schedule() to be an NOOP, whereas a software scheduler can
>  use
>  >  * the *schedule* operation to schedule events. The
>  >  * RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED capability flag indicates
>  whether
>  >  * rte_event_schedule() should be called by all cores or by a single (typically
>  >  * dedicated) core.
>  >
>  > (line 308)
>  > #define RTE_EVENT_DEV_CAP_DISTRIBUTED_SCHED (1ULL < 2)
>  > /**< Event scheduling implementation is distributed and all cores must
>  execute
>  >  *  rte_event_schedule(). If unset, the implementation is centralized and
>  >  *  a single core must execute the schedule operation.
>  >  *
>  >  *  \see rte_event_schedule()
>  >  */
>  >
>  > >  >
>  > >  > On same note, If software PMD based workflow need  a separate core(s)
>  for
>  > >  > schedule function then, Can we hide that from API specification and pass
>  an
>  > >  > argument to SW pmd to define the scheduling core(s)?
>  > >  >
>  > >  > Something like --vdev=eventsw0,schedule_cmask=0x2
>  >
>  > An API for controlling the scheduler coremask instead of (or perhaps in
>  addition to) the vdev argument would be good, to allow runtime control. I can
>  imagine apps that scale the number of cores based on load, and in doing so
>  may want to migrate the scheduler to a different core.
>  
>  Yes, an API for number of scheduler core looks OK. But if we are going to
>  have service core approach then we just need to specify at one place as
>  application will not creating the service functions.
>  
>  >
>  > >
>  > >  Just a thought,
>  > >
>  > >  Perhaps, We could introduce generic "service" cores concept to DPDK to
>  hide
>  > >  the
>  > >  requirement where the implementation needs dedicated core to do certain
>  > >  work. I guess it would useful for other NPU integration in DPDK.
>  > >
>  >
>  > That's an interesting idea. As you suggested in the other thread, this concept
>  could be extended to the "producer" code in the example for configurations
>  where the NIC requires software to feed into the eventdev. And to the other
>  subsystems mentioned in your original PDF, crypto and timer.
>  
>  Yes. Producers should come in service core category. I think, that
>  enables us to have better NPU integration.(same application code for
>  NPU vs non NPU)
>  
>  >
>  > >  >
>  > >  > >
>  > >  > > Thanks,
>  > >  > > Gage
>  > >  > >
>  > >  > > >  -----Original Message-----
>  > >  > > >  From: Jerin Jacob [mailto:jerin.jacob at caviumnetworks.com]
>  > >  > > >  Sent: Thursday, November 17, 2016 11:45 PM
>  > >  > > >  To: dev at dpdk.org
>  > >  > > >  Cc: Richardson, Bruce <bruce.richardson at intel.com>; Van Haaren,
>  Harry
>  > >  > > >  <harry.van.haaren at intel.com>; hemant.agrawal at nxp.com; Eads,
>  Gage
>  > >  > > >  <gage.eads at intel.com>; Jerin Jacob
>  > >  <jerin.jacob at caviumnetworks.com>
>  > >  > > >  Subject: [dpdk-dev] [PATCH 2/4] eventdev: implement the
>  northbound
>  > >  APIs
>  > >  > > >
>  > >  > > >  This patch set defines the southbound driver interface
>  > >  > > >  and implements the common code required for northbound
>  > >  > > >  eventdev API interface.
>  > >  > > >
>  > >  > > >  Signed-off-by: Jerin Jacob <jerin.jacob at caviumnetworks.com>
>  > >  > > >  ---
>  > >  > > >   config/common_base                           |    6 +
>  > >  > > >   lib/Makefile                                 |    1 +
>  > >  > > >   lib/librte_eal/common/include/rte_log.h      |    1 +
>  > >  > > >   lib/librte_eventdev/Makefile                 |   57 ++
>  > >  > > >   lib/librte_eventdev/rte_eventdev.c           | 1211
>  > >  > > >  ++++++++++++++++++++++++++
>  > >  > > >   lib/librte_eventdev/rte_eventdev_pmd.h       |  504 +++++++++++
>  > >  > > >   lib/librte_eventdev/rte_eventdev_version.map |   39 +
>  > >  > > >   mk/rte.app.mk                                |    1 +
>  > >  > > >   8 files changed, 1820 insertions(+)
>  > >  > > >   create mode 100644 lib/librte_eventdev/Makefile
>  > >  > > >   create mode 100644 lib/librte_eventdev/rte_eventdev.c
>  > >  > > >   create mode 100644 lib/librte_eventdev/rte_eventdev_pmd.h
>  > >  > > >   create mode 100644 lib/librte_eventdev/rte_eventdev_version.map
>  > >  > > >
>  > >  > > >  diff --git a/config/common_base b/config/common_base
>  > >  > > >  index 4bff83a..7a8814e 100644
>  > >  > > >  --- a/config/common_base
>  > >  > > >  +++ b/config/common_base
>  > >  > > >  @@ -411,6 +411,12 @@ CONFIG_RTE_LIBRTE_PMD_ZUC_DEBUG=n
>  > >  > > >   CONFIG_RTE_LIBRTE_PMD_NULL_CRYPTO=y
>  > >  > > >
>  > >  > > >   #
>  > >  > > >  +# Compile generic event device library
>  > >  > > >  +#
>  > >  > > >  +CONFIG_RTE_LIBRTE_EVENTDEV=y
>  > >  > > >  +CONFIG_RTE_LIBRTE_EVENTDEV_DEBUG=n
>  > >  > > >  +CONFIG_RTE_EVENT_MAX_DEVS=16
>  > >  > > >  +CONFIG_RTE_EVENT_MAX_QUEUES_PER_DEV=64
>  > >  > > >   # Compile librte_ring
>  > >  > > >   #
>  > >  > > >   CONFIG_RTE_LIBRTE_RING=y
>  > >  > > >  diff --git a/lib/Makefile b/lib/Makefile
>  > >  > > >  index 990f23a..1a067bf 100644
>  > >  > > >  --- a/lib/Makefile
>  > >  > > >  +++ b/lib/Makefile
>  > >  > > >  @@ -41,6 +41,7 @@ DIRS-$(CONFIG_RTE_LIBRTE_CFGFILE) +=
>  > >  librte_cfgfile
>  > >  > > >   DIRS-$(CONFIG_RTE_LIBRTE_CMDLINE) += librte_cmdline
>  > >  > > >   DIRS-$(CONFIG_RTE_LIBRTE_ETHER) += librte_ether
>  > >  > > >   DIRS-$(CONFIG_RTE_LIBRTE_CRYPTODEV) += librte_cryptodev
>  > >  > > >  +DIRS-$(CONFIG_RTE_LIBRTE_EVENTDEV) += librte_eventdev
>  > >  > > >   DIRS-$(CONFIG_RTE_LIBRTE_VHOST) += librte_vhost
>  > >  > > >   DIRS-$(CONFIG_RTE_LIBRTE_HASH) += librte_hash
>  > >  > > >   DIRS-$(CONFIG_RTE_LIBRTE_LPM) += librte_lpm
>  > >  > > >  diff --git a/lib/librte_eal/common/include/rte_log.h
>  > >  > > >  b/lib/librte_eal/common/include/rte_log.h
>  > >  > > >  index 29f7d19..9a07d92 100644
>  > >  > > >  --- a/lib/librte_eal/common/include/rte_log.h
>  > >  > > >  +++ b/lib/librte_eal/common/include/rte_log.h
>  > >  > > >  @@ -79,6 +79,7 @@ extern struct rte_logs rte_logs;
>  > >  > > >   #define RTE_LOGTYPE_PIPELINE 0x00008000 /**< Log related to
>  > >  pipeline. */
>  > >  > > >   #define RTE_LOGTYPE_MBUF    0x00010000 /**< Log related to
>  mbuf.
>  > >  */
>  > >  > > >   #define RTE_LOGTYPE_CRYPTODEV 0x00020000 /**< Log related to
>  > >  > > >  cryptodev. */
>  > >  > > >  +#define RTE_LOGTYPE_EVENTDEV 0x00040000 /**< Log related to
>  > >  eventdev.
>  > >  > > >  */
>  > >  > > >
>  > >  > > >   /* these log types can be used in an application */
>  > >  > > >   #define RTE_LOGTYPE_USER1   0x01000000 /**< User-defined log
>  type
>  > >  1. */
>  > >  > > >  diff --git a/lib/librte_eventdev/Makefile
>  b/lib/librte_eventdev/Makefile
>  > >  > > >  new file mode 100644
>  > >  > > >  index 0000000..dac0663
>  > >  > > >  --- /dev/null
>  > >  > > >  +++ b/lib/librte_eventdev/Makefile
>  > >  > > >  @@ -0,0 +1,57 @@
>  > >  > > >  +#   BSD LICENSE
>  > >  > > >  +#
>  > >  > > >  +#   Copyright(c) 2016 Cavium networks. All rights reserved.
>  > >  > > >  +#
>  > >  > > >  +#   Redistribution and use in source and binary forms, with or
>  without
>  > >  > > >  +#   modification, are permitted provided that the following
>  conditions
>  > >  > > >  +#   are met:
>  > >  > > >  +#
>  > >  > > >  +#     * Redistributions of source code must retain the above
>  copyright
>  > >  > > >  +#       notice, this list of conditions and the following disclaimer.
>  > >  > > >  +#     * Redistributions in binary form must reproduce the above
>  copyright
>  > >  > > >  +#       notice, this list of conditions and the following disclaimer in
>  > >  > > >  +#       the documentation and/or other materials provided with the
>  > >  > > >  +#       distribution.
>  > >  > > >  +#     * Neither the name of Cavium networks nor the names of its
>  > >  > > >  +#       contributors may be used to endorse or promote products
>  derived
>  > >  > > >  +#       from this software without specific prior written permission.
>  > >  > > >  +#
>  > >  > > >  +#   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
>  > >  > > >  CONTRIBUTORS
>  > >  > > >  +#   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
>  INCLUDING,
>  > >  BUT
>  > >  > > >  NOT
>  > >  > > >  +#   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
>  AND
>  > >  > > >  FITNESS FOR
>  > >  > > >  +#   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
>  THE
>  > >  > > >  COPYRIGHT
>  > >  > > >  +#   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
>  INDIRECT,
>  > >  > > >  INCIDENTAL,
>  > >  > > >  +#   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
>  (INCLUDING,
>  > >  BUT
>  > >  > > >  NOT
>  > >  > > >  +#   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
>  SERVICES;
>  > >  LOSS
>  > >  > > >  OF USE,
>  > >  > > >  +#   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
>  > >  CAUSED AND
>  > >  > > >  ON ANY
>  > >  > > >  +#   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
>  LIABILITY,
>  > >  OR
>  > >  > > >  TORT
>  > >  > > >  +#   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
>  > >  OUT OF
>  > >  > > >  THE USE
>  > >  > > >  +#   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
>  SUCH
>  > >  > > >  DAMAGE.
>  > >  > > >  +
>  > >  > > >  +include $(RTE_SDK)/mk/rte.vars.mk
>  > >  > > >  +
>  > >  > > >  +# library name
>  > >  > > >  +LIB = librte_eventdev.a
>  > >  > > >  +
>  > >  > > >  +# library version
>  > >  > > >  +LIBABIVER := 1
>  > >  > > >  +
>  > >  > > >  +# build flags
>  > >  > > >  +CFLAGS += -O3
>  > >  > > >  +CFLAGS += $(WERROR_FLAGS)
>  > >  > > >  +
>  > >  > > >  +# library source files
>  > >  > > >  +SRCS-y += rte_eventdev.c
>  > >  > > >  +
>  > >  > > >  +# export include files
>  > >  > > >  +SYMLINK-y-include += rte_eventdev.h
>  > >  > > >  +SYMLINK-y-include += rte_eventdev_pmd.h
>  > >  > > >  +
>  > >  > > >  +# versioning export map
>  > >  > > >  +EXPORT_MAP := rte_eventdev_version.map
>  > >  > > >  +
>  > >  > > >  +# library dependencies
>  > >  > > >  +DEPDIRS-y += lib/librte_eal
>  > >  > > >  +DEPDIRS-y += lib/librte_mbuf
>  > >  > > >  +
>  > >  > > >  +include $(RTE_SDK)/mk/rte.lib.mk
>  > >  > > >  diff --git a/lib/librte_eventdev/rte_eventdev.c
>  > >  > > >  b/lib/librte_eventdev/rte_eventdev.c
>  > >  > > >  new file mode 100644
>  > >  > > >  index 0000000..17ce5c3
>  > >  > > >  --- /dev/null
>  > >  > > >  +++ b/lib/librte_eventdev/rte_eventdev.c
>  > >  > > >  @@ -0,0 +1,1211 @@
>  > >  > > >  +/*
>  > >  > > >  + *   BSD LICENSE
>  > >  > > >  + *
>  > >  > > >  + *   Copyright(c) 2016 Cavium networks. All rights reserved.
>  > >  > > >  + *
>  > >  > > >  + *   Redistribution and use in source and binary forms, with or
>  without
>  > >  > > >  + *   modification, are permitted provided that the following
>  conditions
>  > >  > > >  + *   are met:
>  > >  > > >  + *
>  > >  > > >  + *     * Redistributions of source code must retain the above
>  copyright
>  > >  > > >  + *       notice, this list of conditions and the following disclaimer.
>  > >  > > >  + *     * Redistributions in binary form must reproduce the above
>  > >  copyright
>  > >  > > >  + *       notice, this list of conditions and the following disclaimer in
>  > >  > > >  + *       the documentation and/or other materials provided with the
>  > >  > > >  + *       distribution.
>  > >  > > >  + *     * Neither the name of Cavium networks nor the names of its
>  > >  > > >  + *       contributors may be used to endorse or promote products
>  derived
>  > >  > > >  + *       from this software without specific prior written permission.
>  > >  > > >  + *
>  > >  > > >  + *   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
>  > >  > > >  CONTRIBUTORS
>  > >  > > >  + *   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
>  INCLUDING,
>  > >  BUT
>  > >  > > >  NOT
>  > >  > > >  + *   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
>  AND
>  > >  > > >  FITNESS FOR
>  > >  > > >  + *   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
>  THE
>  > >  > > >  COPYRIGHT
>  > >  > > >  + *   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
>  INDIRECT,
>  > >  > > >  INCIDENTAL,
>  > >  > > >  + *   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
>  (INCLUDING,
>  > >  BUT
>  > >  > > >  NOT
>  > >  > > >  + *   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
>  SERVICES;
>  > >  LOSS
>  > >  > > >  OF USE,
>  > >  > > >  + *   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
>  > >  CAUSED
>  > >  > > >  AND ON ANY
>  > >  > > >  + *   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
>  LIABILITY,
>  > >  OR
>  > >  > > >  TORT
>  > >  > > >  + *   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY
>  WAY
>  > >  OUT OF
>  > >  > > >  THE USE
>  > >  > > >  + *   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
>  SUCH
>  > >  > > >  DAMAGE.
>  > >  > > >  + */
>  > >  > > >  +
>  > >  > > >  +#include <ctype.h>
>  > >  > > >  +#include <stdio.h>
>  > >  > > >  +#include <stdlib.h>
>  > >  > > >  +#include <string.h>
>  > >  > > >  +#include <stdarg.h>
>  > >  > > >  +#include <errno.h>
>  > >  > > >  +#include <stdint.h>
>  > >  > > >  +#include <inttypes.h>
>  > >  > > >  +#include <sys/types.h>
>  > >  > > >  +#include <sys/queue.h>
>  > >  > > >  +
>  > >  > > >  +#include <rte_byteorder.h>
>  > >  > > >  +#include <rte_log.h>
>  > >  > > >  +#include <rte_debug.h>
>  > >  > > >  +#include <rte_dev.h>
>  > >  > > >  +#include <rte_pci.h>
>  > >  > > >  +#include <rte_memory.h>
>  > >  > > >  +#include <rte_memcpy.h>
>  > >  > > >  +#include <rte_memzone.h>
>  > >  > > >  +#include <rte_eal.h>
>  > >  > > >  +#include <rte_per_lcore.h>
>  > >  > > >  +#include <rte_lcore.h>
>  > >  > > >  +#include <rte_atomic.h>
>  > >  > > >  +#include <rte_branch_prediction.h>
>  > >  > > >  +#include <rte_common.h>
>  > >  > > >  +#include <rte_malloc.h>
>  > >  > > >  +#include <rte_errno.h>
>  > >  > > >  +
>  > >  > > >  +#include "rte_eventdev.h"
>  > >  > > >  +#include "rte_eventdev_pmd.h"
>  > >  > > >  +
>  > >  > > >  +struct rte_eventdev rte_event_devices[RTE_EVENT_MAX_DEVS];
>  > >  > > >  +
>  > >  > > >  +struct rte_eventdev *rte_eventdevs = &rte_event_devices[0];
>  > >  > > >  +
>  > >  > > >  +static struct rte_eventdev_global eventdev_globals = {
>  > >  > > >  +	.nb_devs		= 0
>  > >  > > >  +};
>  > >  > > >  +
>  > >  > > >  +struct rte_eventdev_global *rte_eventdev_globals =
>  > >  &eventdev_globals;
>  > >  > > >  +
>  > >  > > >  +/* Event dev north bound API implementation */
>  > >  > > >  +
>  > >  > > >  +uint8_t
>  > >  > > >  +rte_event_dev_count(void)
>  > >  > > >  +{
>  > >  > > >  +	return rte_eventdev_globals->nb_devs;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_get_dev_id(const char *name)
>  > >  > > >  +{
>  > >  > > >  +	int i;
>  > >  > > >  +
>  > >  > > >  +	if (!name)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	for (i = 0; i < rte_eventdev_globals->nb_devs; i++)
>  > >  > > >  +		if ((strcmp(rte_event_devices[i].data->name, name)
>  > >  > > >  +				== 0) &&
>  > >  > > >  +				(rte_event_devices[i].attached ==
>  > >  > > >  +
>  	RTE_EVENTDEV_ATTACHED))
>  > >  > > >  +			return i;
>  > >  > > >  +	return -ENODEV;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_socket_id(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	return dev->data->socket_id;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_info_get(uint8_t dev_id, struct rte_event_dev_info
>  > >  *dev_info)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	if (dev_info == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	memset(dev_info, 0, sizeof(struct rte_event_dev_info));
>  > >  > > >  +
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >dev_infos_get, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +	(*dev->dev_ops->dev_infos_get)(dev, dev_info);
>  > >  > > >  +
>  > >  > > >  +	dev_info->pci_dev = dev->pci_dev;
>  > >  > > >  +	if (dev->driver)
>  > >  > > >  +		dev_info->driver_name = dev->driver-
>  >pci_drv.driver.name;
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static inline int
>  > >  > > >  +rte_event_dev_queue_config(struct rte_eventdev *dev, uint8_t
>  > >  nb_queues)
>  > >  > > >  +{
>  > >  > > >  +	uint8_t old_nb_queues = dev->data->nb_queues;
>  > >  > > >  +	void **queues;
>  > >  > > >  +	uint8_t *queues_prio;
>  > >  > > >  +	unsigned int i;
>  > >  > > >  +
>  > >  > > >  +	EDEV_LOG_DEBUG("Setup %d queues on device %u",
>  nb_queues,
>  > >  > > >  +			 dev->data->dev_id);
>  > >  > > >  +
>  > >  > > >  +	/* First time configuration */
>  > >  > > >  +	if (dev->data->queues == NULL && nb_queues != 0) {
>  > >  > > >  +		dev->data->queues = rte_zmalloc_socket("eventdev-
>  >data-
>  > >  > > >  >queues",
>  > >  > > >  +				sizeof(dev->data->queues[0]) *
>  nb_queues,
>  > >  > > >  +				RTE_CACHE_LINE_SIZE, dev->data-
>  > >  > > >  >socket_id);
>  > >  > > >  +		if (dev->data->queues == NULL) {
>  > >  > > >  +			dev->data->nb_queues = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to get memory for
>  queue meta
>  > >  > > >  data,"
>  > >  > > >  +					"nb_queues %u", nb_queues);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +		/* Allocate memory to store queue priority */
>  > >  > > >  +		dev->data->queues_prio = rte_zmalloc_socket(
>  > >  > > >  +				"eventdev->data->queues_prio",
>  > >  > > >  +				sizeof(dev->data->queues_prio[0]) *
>  > >  > > >  nb_queues,
>  > >  > > >  +				RTE_CACHE_LINE_SIZE, dev->data-
>  > >  > > >  >socket_id);
>  > >  > > >  +		if (dev->data->queues_prio == NULL) {
>  > >  > > >  +			dev->data->nb_queues = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to get memory for
>  queue
>  > >  > > >  priority,"
>  > >  > > >  +					"nb_queues %u", nb_queues);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +	} else if (dev->data->queues != NULL && nb_queues != 0) {/*
>  re-config
>  > >  > > >  */
>  > >  > > >  +		RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  > >  > > >  >queue_release, -ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +		queues = dev->data->queues;
>  > >  > > >  +		for (i = nb_queues; i < old_nb_queues; i++)
>  > >  > > >  +			(*dev->dev_ops->queue_release)(queues[i]);
>  > >  > > >  +
>  > >  > > >  +		queues = rte_realloc(queues, sizeof(queues[0]) *
>  nb_queues,
>  > >  > > >  +				RTE_CACHE_LINE_SIZE);
>  > >  > > >  +		if (queues == NULL) {
>  > >  > > >  +			EDEV_LOG_ERR("failed to realloc queue meta
>  data,"
>  > >  > > >  +						" nb_queues %u",
>  > >  > > >  nb_queues);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +		dev->data->queues = queues;
>  > >  > > >  +
>  > >  > > >  +		/* Re allocate memory to store queue priority */
>  > >  > > >  +		queues_prio = dev->data->queues_prio;
>  > >  > > >  +		queues_prio = rte_realloc(queues_prio,
>  > >  > > >  +				sizeof(queues_prio[0]) * nb_queues,
>  > >  > > >  +				RTE_CACHE_LINE_SIZE);
>  > >  > > >  +		if (queues_prio == NULL) {
>  > >  > > >  +			EDEV_LOG_ERR("failed to realloc queue
>  priority,"
>  > >  > > >  +						" nb_queues %u",
>  > >  > > >  nb_queues);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +		dev->data->queues_prio = queues_prio;
>  > >  > > >  +
>  > >  > > >  +		if (nb_queues > old_nb_queues) {
>  > >  > > >  +			uint8_t new_qs = nb_queues - old_nb_queues;
>  > >  > > >  +
>  > >  > > >  +			memset(queues + old_nb_queues, 0,
>  > >  > > >  +				sizeof(queues[0]) * new_qs);
>  > >  > > >  +			memset(queues_prio + old_nb_queues, 0,
>  > >  > > >  +				sizeof(queues_prio[0]) * new_qs);
>  > >  > > >  +		}
>  > >  > > >  +	} else if (dev->data->queues != NULL && nb_queues == 0) {
>  > >  > > >  +		RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  > >  > > >  >queue_release, -ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +		queues = dev->data->queues;
>  > >  > > >  +		for (i = nb_queues; i < old_nb_queues; i++)
>  > >  > > >  +			(*dev->dev_ops->queue_release)(queues[i]);
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev->data->nb_queues = nb_queues;
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static inline int
>  > >  > > >  +rte_event_dev_port_config(struct rte_eventdev *dev, uint8_t
>  nb_ports)
>  > >  > > >  +{
>  > >  > > >  +	uint8_t old_nb_ports = dev->data->nb_ports;
>  > >  > > >  +	void **ports;
>  > >  > > >  +	uint16_t *links_map;
>  > >  > > >  +	uint8_t *ports_dequeue_depth;
>  > >  > > >  +	uint8_t *ports_enqueue_depth;
>  > >  > > >  +	unsigned int i;
>  > >  > > >  +
>  > >  > > >  +	EDEV_LOG_DEBUG("Setup %d ports on device %u", nb_ports,
>  > >  > > >  +			 dev->data->dev_id);
>  > >  > > >  +
>  > >  > > >  +	/* First time configuration */
>  > >  > > >  +	if (dev->data->ports == NULL && nb_ports != 0) {
>  > >  > > >  +		dev->data->ports = rte_zmalloc_socket("eventdev-
>  >data-
>  > >  > > >  >ports",
>  > >  > > >  +				sizeof(dev->data->ports[0]) *
>  nb_ports,
>  > >  > > >  +				RTE_CACHE_LINE_SIZE, dev->data-
>  > >  > > >  >socket_id);
>  > >  > > >  +		if (dev->data->ports == NULL) {
>  > >  > > >  +			dev->data->nb_ports = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to get memory for
>  port meta
>  > >  > > >  data,"
>  > >  > > >  +					"nb_ports %u", nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		/* Allocate memory to store ports dequeue depth */
>  > >  > > >  +		dev->data->ports_dequeue_depth =
>  > >  > > >  +			rte_zmalloc_socket("eventdev-
>  > >  > > >  >ports_dequeue_depth",
>  > >  > > >  +			sizeof(dev->data->ports_dequeue_depth[0]) *
>  > >  > > >  nb_ports,
>  > >  > > >  +			RTE_CACHE_LINE_SIZE, dev->data-
>  >socket_id);
>  > >  > > >  +		if (dev->data->ports_dequeue_depth == NULL) {
>  > >  > > >  +			dev->data->nb_ports = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to get memory for
>  port deq
>  > >  > > >  meta,"
>  > >  > > >  +					"nb_ports %u", nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		/* Allocate memory to store ports enqueue depth */
>  > >  > > >  +		dev->data->ports_enqueue_depth =
>  > >  > > >  +			rte_zmalloc_socket("eventdev-
>  > >  > > >  >ports_enqueue_depth",
>  > >  > > >  +			sizeof(dev->data->ports_enqueue_depth[0]) *
>  > >  > > >  nb_ports,
>  > >  > > >  +			RTE_CACHE_LINE_SIZE, dev->data-
>  >socket_id);
>  > >  > > >  +		if (dev->data->ports_enqueue_depth == NULL) {
>  > >  > > >  +			dev->data->nb_ports = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to get memory for
>  port enq
>  > >  > > >  meta,"
>  > >  > > >  +					"nb_ports %u", nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		/* Allocate memory to store queue to port link
>  connection */
>  > >  > > >  +		dev->data->links_map =
>  > >  > > >  +			rte_zmalloc_socket("eventdev->links_map",
>  > >  > > >  +			sizeof(dev->data->links_map[0]) * nb_ports *
>  > >  > > >  +			RTE_EVENT_MAX_QUEUES_PER_DEV,
>  > >  > > >  +			RTE_CACHE_LINE_SIZE, dev->data-
>  >socket_id);
>  > >  > > >  +		if (dev->data->links_map == NULL) {
>  > >  > > >  +			dev->data->nb_ports = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to get memory for
>  port_map
>  > >  > > >  area,"
>  > >  > > >  +					"nb_ports %u", nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +	} else if (dev->data->ports != NULL && nb_ports != 0) {/* re-
>  config */
>  > >  > > >  +		RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >port_release,
>  > >  > > >  -ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +		ports = dev->data->ports;
>  > >  > > >  +		ports_dequeue_depth = dev->data-
>  >ports_dequeue_depth;
>  > >  > > >  +		ports_enqueue_depth = dev->data-
>  >ports_enqueue_depth;
>  > >  > > >  +		links_map = dev->data->links_map;
>  > >  > > >  +
>  > >  > > >  +		for (i = nb_ports; i < old_nb_ports; i++)
>  > >  > > >  +			(*dev->dev_ops->port_release)(ports[i]);
>  > >  > > >  +
>  > >  > > >  +		/* Realloc memory for ports */
>  > >  > > >  +		ports = rte_realloc(ports, sizeof(ports[0]) * nb_ports,
>  > >  > > >  +				RTE_CACHE_LINE_SIZE);
>  > >  > > >  +		if (ports == NULL) {
>  > >  > > >  +			EDEV_LOG_ERR("failed to realloc port meta
>  data,"
>  > >  > > >  +						" nb_ports %u",
>  nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		/* Realloc memory for ports_dequeue_depth */
>  > >  > > >  +		ports_dequeue_depth =
>  rte_realloc(ports_dequeue_depth,
>  > >  > > >  +			sizeof(ports_dequeue_depth[0]) * nb_ports,
>  > >  > > >  +			RTE_CACHE_LINE_SIZE);
>  > >  > > >  +		if (ports_dequeue_depth == NULL) {
>  > >  > > >  +			EDEV_LOG_ERR("failed to realloc port deqeue
>  meta
>  > >  > > >  data,"
>  > >  > > >  +						" nb_ports %u",
>  nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		/* Realloc memory for ports_enqueue_depth */
>  > >  > > >  +		ports_enqueue_depth =
>  rte_realloc(ports_enqueue_depth,
>  > >  > > >  +			sizeof(ports_enqueue_depth[0]) * nb_ports,
>  > >  > > >  +			RTE_CACHE_LINE_SIZE);
>  > >  > > >  +		if (ports_enqueue_depth == NULL) {
>  > >  > > >  +			EDEV_LOG_ERR("failed to realloc port
>  enqueue meta
>  > >  > > >  data,"
>  > >  > > >  +						" nb_ports %u",
>  nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		/* Realloc memory to store queue to port link
>  connection */
>  > >  > > >  +		links_map = rte_realloc(links_map,
>  > >  > > >  +			sizeof(dev->data->links_map[0]) * nb_ports *
>  > >  > > >  +			RTE_EVENT_MAX_QUEUES_PER_DEV,
>  > >  > > >  +			RTE_CACHE_LINE_SIZE);
>  > >  > > >  +		if (dev->data->links_map == NULL) {
>  > >  > > >  +			dev->data->nb_ports = 0;
>  > >  > > >  +			EDEV_LOG_ERR("failed to realloc mem for
>  port_map
>  > >  > > >  area,"
>  > >  > > >  +					"nb_ports %u", nb_ports);
>  > >  > > >  +			return -(ENOMEM);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		if (nb_ports > old_nb_ports) {
>  > >  > > >  +			uint8_t new_ps = nb_ports - old_nb_ports;
>  > >  > > >  +
>  > >  > > >  +			memset(ports + old_nb_ports, 0,
>  > >  > > >  +				sizeof(ports[0]) * new_ps);
>  > >  > > >  +			memset(ports_dequeue_depth +
>  old_nb_ports, 0,
>  > >  > > >  +				sizeof(ports_dequeue_depth[0]) *
>  new_ps);
>  > >  > > >  +			memset(ports_enqueue_depth +
>  old_nb_ports, 0,
>  > >  > > >  +				sizeof(ports_enqueue_depth[0]) *
>  new_ps);
>  > >  > > >  +			memset(links_map +
>  > >  > > >  +				(old_nb_ports *
>  > >  > > >  RTE_EVENT_MAX_QUEUES_PER_DEV),
>  > >  > > >  +				0, sizeof(ports_enqueue_depth[0]) *
>  new_ps);
>  > >  > > >  +		}
>  > >  > > >  +
>  > >  > > >  +		dev->data->ports = ports;
>  > >  > > >  +		dev->data->ports_dequeue_depth =
>  ports_dequeue_depth;
>  > >  > > >  +		dev->data->ports_enqueue_depth =
>  ports_enqueue_depth;
>  > >  > > >  +		dev->data->links_map = links_map;
>  > >  > > >  +	} else if (dev->data->ports != NULL && nb_ports == 0) {
>  > >  > > >  +		RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >port_release,
>  > >  > > >  -ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +		ports = dev->data->ports;
>  > >  > > >  +		for (i = nb_ports; i < old_nb_ports; i++)
>  > >  > > >  +			(*dev->dev_ops->port_release)(ports[i]);
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev->data->nb_ports = nb_ports;
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_configure(uint8_t dev_id, struct
>  rte_event_dev_config
>  > >  > > >  *dev_conf)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	struct rte_event_dev_info info;
>  > >  > > >  +	int diag;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >dev_infos_get, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >dev_configure, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (dev->data->dev_started) {
>  > >  > > >  +		EDEV_LOG_ERR(
>  > >  > > >  +		    "device %d must be stopped to allow configuration",
>  > >  > > >  dev_id);
>  > >  > > >  +		return -EBUSY;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	if (dev_conf == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	(*dev->dev_ops->dev_infos_get)(dev, &info);
>  > >  > > >  +
>  > >  > > >  +	/* Check dequeue_wait_ns value is in limit */
>  > >  > > >  +	if (!dev_conf->event_dev_cfg &
>  > >  > > >  RTE_EVENT_DEV_CFG_PER_DEQUEUE_WAIT) {
>  > >  > > >  +		if (dev_conf->dequeue_wait_ns <
>  info.min_dequeue_wait_ns
>  > >  > > >  ||
>  > >  > > >  +			dev_conf->dequeue_wait_ns >
>  > >  > > >  info.max_dequeue_wait_ns) {
>  > >  > > >  +			EDEV_LOG_ERR("dev%d invalid
>  dequeue_wait_ns=%d"
>  > >  > > >  +			" min_dequeue_wait_ns=%d
>  > >  > > >  max_dequeue_wait_ns=%d",
>  > >  > > >  +			dev_id, dev_conf->dequeue_wait_ns,
>  > >  > > >  +			info.min_dequeue_wait_ns,
>  > >  > > >  +			info.max_dequeue_wait_ns);
>  > >  > > >  +			return -EINVAL;
>  > >  > > >  +		}
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_events_limit is in limit */
>  > >  > > >  +	if (dev_conf->nb_events_limit > info.max_num_events) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_events_limit=%d >
>  > >  > > >  max_num_events=%d",
>  > >  > > >  +		dev_id, dev_conf->nb_events_limit,
>  info.max_num_events);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_event_queues is in limit */
>  > >  > > >  +	if (!dev_conf->nb_event_queues) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_event_queues cannot be
>  zero",
>  > >  > > >  dev_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +	if (dev_conf->nb_event_queues > info.max_event_queues) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_event_queues=%d >
>  > >  > > >  max_event_queues=%d",
>  > >  > > >  +		dev_id, dev_conf->nb_event_queues,
>  > >  > > >  info.max_event_queues);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_event_ports is in limit */
>  > >  > > >  +	if (!dev_conf->nb_event_ports) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_event_ports cannot be
>  zero",
>  > >  > > >  dev_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +	if (dev_conf->nb_event_ports > info.max_event_ports) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_event_ports=%d >
>  > >  > > >  max_event_ports= %d",
>  > >  > > >  +		dev_id, dev_conf->nb_event_ports,
>  info.max_event_ports);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_event_queue_flows is in limit */
>  > >  > > >  +	if (!dev_conf->nb_event_queue_flows) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_flows cannot be zero",
>  dev_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +	if (dev_conf->nb_event_queue_flows >
>  info.max_event_queue_flows)
>  > >  > > >  {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_flows=%x >
>  max_flows=%x",
>  > >  > > >  +		dev_id, dev_conf->nb_event_queue_flows,
>  > >  > > >  +		info.max_event_queue_flows);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_event_port_dequeue_depth is in limit */
>  > >  > > >  +	if (!dev_conf->nb_event_port_dequeue_depth) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_dequeue_depth cannot be
>  zero",
>  > >  > > >  dev_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +	if (dev_conf->nb_event_port_dequeue_depth >
>  > >  > > >  +			 info.max_event_port_dequeue_depth) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_dequeue_depth=%d >
>  > >  > > >  max_dequeue_depth=%d",
>  > >  > > >  +		dev_id, dev_conf->nb_event_port_dequeue_depth,
>  > >  > > >  +		info.max_event_port_dequeue_depth);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_event_port_enqueue_depth is in limit */
>  > >  > > >  +	if (!dev_conf->nb_event_port_enqueue_depth) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_enqueue_depth cannot be
>  zero",
>  > >  > > >  dev_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +	if (dev_conf->nb_event_port_enqueue_depth >
>  > >  > > >  +			 info.max_event_port_enqueue_depth) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d nb_enqueue_depth=%d >
>  > >  > > >  max_enqueue_depth=%d",
>  > >  > > >  +		dev_id, dev_conf->nb_event_port_enqueue_depth,
>  > >  > > >  +		info.max_event_port_enqueue_depth);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Copy the dev_conf parameter into the dev structure */
>  > >  > > >  +	memcpy(&dev->data->dev_conf, dev_conf, sizeof(dev->data-
>  > >  > > >  >dev_conf));
>  > >  > > >  +
>  > >  > > >  +	/* Setup new number of queues and reconfigure device. */
>  > >  > > >  +	diag = rte_event_dev_queue_config(dev, dev_conf-
>  > >  > > >  >nb_event_queues);
>  > >  > > >  +	if (diag != 0) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d rte_event_dev_queue_config
>  = %d",
>  > >  > > >  +				dev_id, diag);
>  > >  > > >  +		return diag;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Setup new number of ports and reconfigure device. */
>  > >  > > >  +	diag = rte_event_dev_port_config(dev, dev_conf-
>  >nb_event_ports);
>  > >  > > >  +	if (diag != 0) {
>  > >  > > >  +		rte_event_dev_queue_config(dev, 0);
>  > >  > > >  +		EDEV_LOG_ERR("dev%d rte_event_dev_port_config =
>  %d",
>  > >  > > >  +				dev_id, diag);
>  > >  > > >  +		return diag;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Configure the device */
>  > >  > > >  +	diag = (*dev->dev_ops->dev_configure)(dev);
>  > >  > > >  +	if (diag != 0) {
>  > >  > > >  +		EDEV_LOG_ERR("dev%d dev_configure = %d", dev_id,
>  diag);
>  > >  > > >  +		rte_event_dev_queue_config(dev, 0);
>  > >  > > >  +		rte_event_dev_port_config(dev, 0);
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev->data->event_dev_cap = info.event_dev_cap;
>  > >  > > >  +	return diag;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static inline int
>  > >  > > >  +is_valid_queue(struct rte_eventdev *dev, uint8_t queue_id)
>  > >  > > >  +{
>  > >  > > >  +	if (queue_id < dev->data->nb_queues && queue_id <
>  > >  > > >  +
>  	RTE_EVENT_MAX_QUEUES_PER_DEV)
>  > >  > > >  +		return 1;
>  > >  > > >  +	else
>  > >  > > >  +		return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_queue_default_conf_get(uint8_t dev_id, uint8_t
>  queue_id,
>  > >  > > >  +				 struct rte_event_queue_conf
>  *queue_conf)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	if (queue_conf == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	if (!is_valid_queue(dev, queue_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid queue_id=%" PRIu8,
>  queue_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >queue_def_conf, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +	memset(queue_conf, 0, sizeof(struct rte_event_queue_conf));
>  > >  > > >  +	(*dev->dev_ops->queue_def_conf)(dev, queue_id,
>  queue_conf);
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static inline int
>  > >  > > >  +is_valid_atomic_queue_conf(struct rte_event_queue_conf
>  > >  *queue_conf)
>  > >  > > >  +{
>  > >  > > >  +	if (queue_conf && (
>  > >  > > >  +		((queue_conf->event_queue_cfg &
>  > >  > > >  RTE_EVENT_QUEUE_CFG_TYPE_MASK)
>  > >  > > >  +			== RTE_EVENT_QUEUE_CFG_ALL_TYPES) ||
>  > >  > > >  +		((queue_conf->event_queue_cfg &
>  > >  > > >  RTE_EVENT_QUEUE_CFG_TYPE_MASK)
>  > >  > > >  +			== RTE_EVENT_QUEUE_CFG_ATOMIC_ONLY)
>  > >  > > >  +		))
>  > >  > > >  +		return 1;
>  > >  > > >  +	else
>  > >  > > >  +		return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_queue_setup(uint8_t dev_id, uint8_t queue_id,
>  > >  > > >  +		      struct rte_event_queue_conf *queue_conf)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	struct rte_event_queue_conf def_conf;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	if (!is_valid_queue(dev, queue_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid queue_id=%" PRIu8,
>  queue_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_atomic_flows limit */
>  > >  > > >  +	if (is_valid_atomic_queue_conf(queue_conf)) {
>  > >  > > >  +		if (queue_conf->nb_atomic_flows == 0 ||
>  > >  > > >  +		    queue_conf->nb_atomic_flows >
>  > >  > > >  +			dev->data->dev_conf.nb_event_queue_flows)
>  {
>  > >  > > >  +			EDEV_LOG_ERR(
>  > >  > > >  +		"dev%d queue%d Invalid nb_atomic_flows=%d
>  > >  > > >  max_flows=%d",
>  > >  > > >  +			dev_id, queue_id, queue_conf-
>  >nb_atomic_flows,
>  > >  > > >  +			dev->data-
>  >dev_conf.nb_event_queue_flows);
>  > >  > > >  +			return -EINVAL;
>  > >  > > >  +		}
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check nb_atomic_order_sequences limit */
>  > >  > > >  +	if (is_valid_atomic_queue_conf(queue_conf)) {
>  > >  > > >  +		if (queue_conf->nb_atomic_order_sequences == 0 ||
>  > >  > > >  +		    queue_conf->nb_atomic_order_sequences >
>  > >  > > >  +			dev->data->dev_conf.nb_event_queue_flows)
>  {
>  > >  > > >  +			EDEV_LOG_ERR(
>  > >  > > >  +		"dev%d queue%d Invalid nb_atomic_order_seq=%d
>  > >  > > >  max_flows=%d",
>  > >  > > >  +			dev_id, queue_id, queue_conf-
>  > >  > > >  >nb_atomic_order_sequences,
>  > >  > > >  +			dev->data-
>  >dev_conf.nb_event_queue_flows);
>  > >  > > >  +			return -EINVAL;
>  > >  > > >  +		}
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	if (dev->data->dev_started) {
>  > >  > > >  +		EDEV_LOG_ERR(
>  > >  > > >  +		    "device %d must be stopped to allow queue setup",
>  dev_id);
>  > >  > > >  +		return -EBUSY;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->queue_setup,
>  -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (queue_conf == NULL) {
>  > >  > > >  +		RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  > >  > > >  >queue_def_conf,
>  > >  > > >  +					-ENOTSUP);
>  > >  > > >  +		(*dev->dev_ops->queue_def_conf)(dev, queue_id,
>  &def_conf);
>  > >  > > >  +		def_conf.event_queue_cfg =
>  > >  > > >  RTE_EVENT_QUEUE_CFG_DEFAULT;
>  > >  > > >  +		queue_conf = &def_conf;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev->data->queues_prio[queue_id] = queue_conf->priority;
>  > >  > > >  +	return (*dev->dev_ops->queue_setup)(dev, queue_id,
>  queue_conf);
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +uint8_t
>  > >  > > >  +rte_event_queue_count(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	return dev->data->nb_queues;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +uint8_t
>  > >  > > >  +rte_event_queue_priority(uint8_t dev_id, uint8_t queue_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	if (dev->data->event_dev_cap &
>  RTE_EVENT_DEV_CAP_QUEUE_QOS)
>  > >  > > >  +		return dev->data->queues_prio[queue_id];
>  > >  > > >  +	else
>  > >  > > >  +		return RTE_EVENT_QUEUE_PRIORITY_NORMAL;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static inline int
>  > >  > > >  +is_valid_port(struct rte_eventdev *dev, uint8_t port_id)
>  > >  > > >  +{
>  > >  > > >  +	if (port_id < dev->data->nb_ports)
>  > >  > > >  +		return 1;
>  > >  > > >  +	else
>  > >  > > >  +		return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_port_default_conf_get(uint8_t dev_id, uint8_t port_id,
>  > >  > > >  +				 struct rte_event_port_conf
>  *port_conf)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	if (port_conf == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	if (!is_valid_port(dev, port_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid port_id=%" PRIu8, port_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  >port_def_conf, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +	memset(port_conf, 0, sizeof(struct rte_event_port_conf));
>  > >  > > >  +	(*dev->dev_ops->port_def_conf)(dev, port_id, port_conf);
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_port_setup(uint8_t dev_id, uint8_t port_id,
>  > >  > > >  +		      struct rte_event_port_conf *port_conf)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	struct rte_event_port_conf def_conf;
>  > >  > > >  +	int diag;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	if (!is_valid_port(dev, port_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid port_id=%" PRIu8, port_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check new_event_threshold limit */
>  > >  > > >  +	if ((port_conf && !port_conf->new_event_threshold) ||
>  > >  > > >  +			(port_conf && port_conf-
>  >new_event_threshold >
>  > >  > > >  +				 dev->data-
>  >dev_conf.nb_events_limit)) {
>  > >  > > >  +		EDEV_LOG_ERR(
>  > >  > > >  +		   "dev%d port%d Invalid event_threshold=%d
>  > >  > > >  nb_events_limit=%d",
>  > >  > > >  +			dev_id, port_id, port_conf-
>  >new_event_threshold,
>  > >  > > >  +			dev->data->dev_conf.nb_events_limit);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check dequeue_depth limit */
>  > >  > > >  +	if ((port_conf && !port_conf->dequeue_depth) ||
>  > >  > > >  +			(port_conf && port_conf->dequeue_depth >
>  > >  > > >  +		dev->data-
>  >dev_conf.nb_event_port_dequeue_depth)) {
>  > >  > > >  +		EDEV_LOG_ERR(
>  > >  > > >  +		   "dev%d port%d Invalid dequeue depth=%d
>  > >  > > >  max_dequeue_depth=%d",
>  > >  > > >  +			dev_id, port_id, port_conf->dequeue_depth,
>  > >  > > >  +			dev->data-
>  > >  > > >  >dev_conf.nb_event_port_dequeue_depth);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Check enqueue_depth limit */
>  > >  > > >  +	if ((port_conf && !port_conf->enqueue_depth) ||
>  > >  > > >  +			(port_conf && port_conf->enqueue_depth >
>  > >  > > >  +		dev->data-
>  >dev_conf.nb_event_port_enqueue_depth)) {
>  > >  > > >  +		EDEV_LOG_ERR(
>  > >  > > >  +		   "dev%d port%d Invalid enqueue depth=%d
>  > >  > > >  max_enqueue_depth=%d",
>  > >  > > >  +			dev_id, port_id, port_conf->enqueue_depth,
>  > >  > > >  +			dev->data-
>  > >  > > >  >dev_conf.nb_event_port_enqueue_depth);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	if (dev->data->dev_started) {
>  > >  > > >  +		EDEV_LOG_ERR(
>  > >  > > >  +		    "device %d must be stopped to allow port setup",
>  dev_id);
>  > >  > > >  +		return -EBUSY;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->port_setup, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (port_conf == NULL) {
>  > >  > > >  +		RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops-
>  > >  > > >  >port_def_conf,
>  > >  > > >  +					-ENOTSUP);
>  > >  > > >  +		(*dev->dev_ops->port_def_conf)(dev, port_id,
>  &def_conf);
>  > >  > > >  +		port_conf = &def_conf;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev->data->ports_dequeue_depth[port_id] =
>  > >  > > >  +			port_conf->dequeue_depth;
>  > >  > > >  +	dev->data->ports_enqueue_depth[port_id] =
>  > >  > > >  +			port_conf->enqueue_depth;
>  > >  > > >  +
>  > >  > > >  +	diag = (*dev->dev_ops->port_setup)(dev, port_id, port_conf);
>  > >  > > >  +
>  > >  > > >  +	/* Unlink all the queues from this port(default state after
>  setup) */
>  > >  > > >  +	if (!diag)
>  > >  > > >  +		diag = rte_event_port_unlink(dev_id, port_id, NULL,
>  0);
>  > >  > > >  +
>  > >  > > >  +	if (diag < 0)
>  > >  > > >  +		return diag;
>  > >  > > >  +
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +uint8_t
>  > >  > > >  +rte_event_port_dequeue_depth(uint8_t dev_id, uint8_t port_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	return dev->data->ports_dequeue_depth[port_id];
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +uint8_t
>  > >  > > >  +rte_event_port_enqueue_depth(uint8_t dev_id, uint8_t port_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	return dev->data->ports_enqueue_depth[port_id];
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +uint8_t
>  > >  > > >  +rte_event_port_count(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	return dev->data->nb_ports;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_port_link(uint8_t dev_id, uint8_t port_id,
>  > >  > > >  +		    struct rte_event_queue_link link[], uint16_t nb_links)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	struct rte_event_queue_link
>  > >  > > >  all_queues[RTE_EVENT_MAX_QUEUES_PER_DEV];
>  > >  > > >  +	uint16_t *links_map;
>  > >  > > >  +	int i, diag;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->port_link, -
>  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (!is_valid_port(dev, port_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid port_id=%" PRIu8, port_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	if (link == NULL) {
>  > >  > > >  +		for (i = 0; i < dev->data->nb_queues; i++) {
>  > >  > > >  +			all_queues[i].queue_id = i;
>  > >  > > >  +			all_queues[i].priority =
>  > >  > > >  +
>  > >  > > >  	RTE_EVENT_QUEUE_SERVICE_PRIORITY_NORMAL;
>  > >  > > >  +		}
>  > >  > > >  +		link = all_queues;
>  > >  > > >  +		nb_links = dev->data->nb_queues;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	for (i = 0; i < nb_links; i++)
>  > >  > > >  +		if (link[i].queue_id >=
>  RTE_EVENT_MAX_QUEUES_PER_DEV)
>  > >  > > >  +			return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	diag = (*dev->dev_ops->port_link)(dev->data->ports[port_id],
>  link,
>  > >  > > >  +						 nb_links);
>  > >  > > >  +	if (diag < 0)
>  > >  > > >  +		return diag;
>  > >  > > >  +
>  > >  > > >  +	links_map = dev->data->links_map;
>  > >  > > >  +	/* Point links_map to this port specific area */
>  > >  > > >  +	links_map += (port_id * RTE_EVENT_MAX_QUEUES_PER_DEV);
>  > >  > > >  +	for (i = 0; i < diag; i++)
>  > >  > > >  +		links_map[link[i].queue_id] = (uint8_t)link[i].priority;
>  > >  > > >  +
>  > >  > > >  +	return diag;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +#define EVENT_QUEUE_SERVICE_PRIORITY_INVALID (0xdead)
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_port_unlink(uint8_t dev_id, uint8_t port_id,
>  > >  > > >  +		      uint8_t queues[], uint16_t nb_unlinks)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	uint8_t all_queues[RTE_EVENT_MAX_QUEUES_PER_DEV];
>  > >  > > >  +	int i, diag;
>  > >  > > >  +	uint16_t *links_map;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->port_unlink, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (!is_valid_port(dev, port_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid port_id=%" PRIu8, port_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	if (queues == NULL) {
>  > >  > > >  +		for (i = 0; i < dev->data->nb_queues; i++)
>  > >  > > >  +			all_queues[i] = i;
>  > >  > > >  +		queues = all_queues;
>  > >  > > >  +		nb_unlinks = dev->data->nb_queues;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	for (i = 0; i < nb_unlinks; i++)
>  > >  > > >  +		if (queues[i] >= RTE_EVENT_MAX_QUEUES_PER_DEV)
>  > >  > > >  +			return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	diag = (*dev->dev_ops->port_unlink)(dev->data-
>  >ports[port_id],
>  > >  > > >  queues,
>  > >  > > >  +					nb_unlinks);
>  > >  > > >  +
>  > >  > > >  +	if (diag < 0)
>  > >  > > >  +		return diag;
>  > >  > > >  +
>  > >  > > >  +	links_map = dev->data->links_map;
>  > >  > > >  +	/* Point links_map to this port specific area */
>  > >  > > >  +	links_map += (port_id * RTE_EVENT_MAX_QUEUES_PER_DEV);
>  > >  > > >  +	for (i = 0; i < diag; i++)
>  > >  > > >  +		links_map[queues[i]] =
>  > >  > > >  EVENT_QUEUE_SERVICE_PRIORITY_INVALID;
>  > >  > > >  +
>  > >  > > >  +	return diag;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_port_links_get(uint8_t dev_id, uint8_t port_id,
>  > >  > > >  +			struct rte_event_queue_link link[])
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	uint16_t *links_map;
>  > >  > > >  +	int i, count = 0;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	if (!is_valid_port(dev, port_id)) {
>  > >  > > >  +		EDEV_LOG_ERR("Invalid port_id=%" PRIu8, port_id);
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	links_map = dev->data->links_map;
>  > >  > > >  +	/* Point links_map to this port specific area */
>  > >  > > >  +	links_map += (port_id * RTE_EVENT_MAX_QUEUES_PER_DEV);
>  > >  > > >  +	for (i = 0; i < RTE_EVENT_MAX_QUEUES_PER_DEV; i++) {
>  > >  > > >  +		if (links_map[i] !=
>  > >  > > >  EVENT_QUEUE_SERVICE_PRIORITY_INVALID) {
>  > >  > > >  +			link[count].queue_id = i;
>  > >  > > >  +			link[count].priority = (uint8_t)links_map[i];
>  > >  > > >  +			++count;
>  > >  > > >  +		}
>  > >  > > >  +	}
>  > >  > > >  +	return count;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dequeue_wait_time(uint8_t dev_id, uint64_t ns, uint64_t
>  > >  > > >  *wait_ticks)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->wait_time, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (wait_ticks == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	(*dev->dev_ops->wait_time)(dev, ns, wait_ticks);
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_dump(uint8_t dev_id, FILE *f)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->dump, -
>  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	(*dev->dev_ops->dump)(dev, f);
>  > >  > > >  +	return 0;
>  > >  > > >  +
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_start(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	int diag;
>  > >  > > >  +
>  > >  > > >  +	EDEV_LOG_DEBUG("Start dev_id=%" PRIu8, dev_id);
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->dev_start, -
>  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	if (dev->data->dev_started != 0) {
>  > >  > > >  +		EDEV_LOG_ERR("Device with dev_id=%" PRIu8 "
>  already
>  > >  > > >  started",
>  > >  > > >  +			dev_id);
>  > >  > > >  +		return 0;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	diag = (*dev->dev_ops->dev_start)(dev);
>  > >  > > >  +	if (diag == 0)
>  > >  > > >  +		dev->data->dev_started = 1;
>  > >  > > >  +	else
>  > >  > > >  +		return diag;
>  > >  > > >  +
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +void
>  > >  > > >  +rte_event_dev_stop(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	EDEV_LOG_DEBUG("Stop dev_id=%" PRIu8, dev_id);
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_RET(dev_id);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_RET(*dev->dev_ops->dev_stop);
>  > >  > > >  +
>  > >  > > >  +	if (dev->data->dev_started == 0) {
>  > >  > > >  +		EDEV_LOG_ERR("Device with dev_id=%" PRIu8 "
>  already
>  > >  > > >  stopped",
>  > >  > > >  +			dev_id);
>  > >  > > >  +		return;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev->data->dev_started = 0;
>  > >  > > >  +	(*dev->dev_ops->dev_stop)(dev);
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_event_dev_close(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, -
>  EINVAL);
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	RTE_FUNC_PTR_OR_ERR_RET(*dev->dev_ops->dev_close, -
>  > >  > > >  ENOTSUP);
>  > >  > > >  +
>  > >  > > >  +	/* Device must be stopped before it can be closed */
>  > >  > > >  +	if (dev->data->dev_started == 1) {
>  > >  > > >  +		EDEV_LOG_ERR("Device %u must be stopped before
>  closing",
>  > >  > > >  +				dev_id);
>  > >  > > >  +		return -EBUSY;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	return (*dev->dev_ops->dev_close)(dev);
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static inline int
>  > >  > > >  +rte_eventdev_data_alloc(uint8_t dev_id, struct rte_eventdev_data
>  > >  **data,
>  > >  > > >  +		int socket_id)
>  > >  > > >  +{
>  > >  > > >  +	char mz_name[RTE_EVENTDEV_NAME_MAX_LEN];
>  > >  > > >  +	const struct rte_memzone *mz;
>  > >  > > >  +	int n;
>  > >  > > >  +
>  > >  > > >  +	/* Generate memzone name */
>  > >  > > >  +	n = snprintf(mz_name, sizeof(mz_name),
>  "rte_eventdev_data_%u",
>  > >  > > >  dev_id);
>  > >  > > >  +	if (n >= (int)sizeof(mz_name))
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	if (rte_eal_process_type() == RTE_PROC_PRIMARY) {
>  > >  > > >  +		mz = rte_memzone_reserve(mz_name,
>  > >  > > >  +				sizeof(struct rte_eventdev_data),
>  > >  > > >  +				socket_id, 0);
>  > >  > > >  +	} else
>  > >  > > >  +		mz = rte_memzone_lookup(mz_name);
>  > >  > > >  +
>  > >  > > >  +	if (mz == NULL)
>  > >  > > >  +		return -ENOMEM;
>  > >  > > >  +
>  > >  > > >  +	*data = mz->addr;
>  > >  > > >  +	if (rte_eal_process_type() == RTE_PROC_PRIMARY)
>  > >  > > >  +		memset(*data, 0, sizeof(struct rte_eventdev_data));
>  > >  > > >  +
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +static uint8_t
>  > >  > > >  +rte_eventdev_find_free_device_index(void)
>  > >  > > >  +{
>  > >  > > >  +	uint8_t dev_id;
>  > >  > > >  +
>  > >  > > >  +	for (dev_id = 0; dev_id < RTE_EVENT_MAX_DEVS; dev_id++) {
>  > >  > > >  +		if (rte_eventdevs[dev_id].attached ==
>  > >  > > >  +				RTE_EVENTDEV_DETACHED)
>  > >  > > >  +			return dev_id;
>  > >  > > >  +	}
>  > >  > > >  +	return RTE_EVENT_MAX_DEVS;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +struct rte_eventdev *
>  > >  > > >  +rte_eventdev_pmd_allocate(const char *name, int socket_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *eventdev;
>  > >  > > >  +	uint8_t dev_id;
>  > >  > > >  +
>  > >  > > >  +	if (rte_eventdev_pmd_get_named_dev(name) != NULL) {
>  > >  > > >  +		EDEV_LOG_ERR("Event device with name %s already "
>  > >  > > >  +				"allocated!", name);
>  > >  > > >  +		return NULL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	dev_id = rte_eventdev_find_free_device_index();
>  > >  > > >  +	if (dev_id == RTE_EVENT_MAX_DEVS) {
>  > >  > > >  +		EDEV_LOG_ERR("Reached maximum number of event
>  > >  > > >  devices");
>  > >  > > >  +		return NULL;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	eventdev = &rte_eventdevs[dev_id];
>  > >  > > >  +
>  > >  > > >  +	if (eventdev->data == NULL) {
>  > >  > > >  +		struct rte_eventdev_data *eventdev_data = NULL;
>  > >  > > >  +
>  > >  > > >  +		int retval = rte_eventdev_data_alloc(dev_id,
>  &eventdev_data,
>  > >  > > >  +				socket_id);
>  > >  > > >  +
>  > >  > > >  +		if (retval < 0 || eventdev_data == NULL)
>  > >  > > >  +			return NULL;
>  > >  > > >  +
>  > >  > > >  +		eventdev->data = eventdev_data;
>  > >  > > >  +
>  > >  > > >  +		snprintf(eventdev->data->name,
>  > >  > > >  RTE_EVENTDEV_NAME_MAX_LEN,
>  > >  > > >  +				"%s", name);
>  > >  > > >  +
>  > >  > > >  +		eventdev->data->dev_id = dev_id;
>  > >  > > >  +		eventdev->data->socket_id = socket_id;
>  > >  > > >  +		eventdev->data->dev_started = 0;
>  > >  > > >  +
>  > >  > > >  +		eventdev->attached = RTE_EVENTDEV_ATTACHED;
>  > >  > > >  +
>  > >  > > >  +		eventdev_globals.nb_devs++;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	return eventdev;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_eventdev_pmd_release(struct rte_eventdev *eventdev)
>  > >  > > >  +{
>  > >  > > >  +	int ret;
>  > >  > > >  +
>  > >  > > >  +	if (eventdev == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	ret = rte_event_dev_close(eventdev->data->dev_id);
>  > >  > > >  +	if (ret < 0)
>  > >  > > >  +		return ret;
>  > >  > > >  +
>  > >  > > >  +	eventdev->attached = RTE_EVENTDEV_DETACHED;
>  > >  > > >  +	eventdev_globals.nb_devs--;
>  > >  > > >  +	eventdev->data = NULL;
>  > >  > > >  +
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +struct rte_eventdev *
>  > >  > > >  +rte_eventdev_pmd_vdev_init(const char *name, size_t
>  > >  dev_private_size,
>  > >  > > >  +		int socket_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *eventdev;
>  > >  > > >  +
>  > >  > > >  +	/* Allocate device structure */
>  > >  > > >  +	eventdev = rte_eventdev_pmd_allocate(name, socket_id);
>  > >  > > >  +	if (eventdev == NULL)
>  > >  > > >  +		return NULL;
>  > >  > > >  +
>  > >  > > >  +	/* Allocate private device structure */
>  > >  > > >  +	if (rte_eal_process_type() == RTE_PROC_PRIMARY) {
>  > >  > > >  +		eventdev->data->dev_private =
>  > >  > > >  +				rte_zmalloc_socket("eventdev device
>  private",
>  > >  > > >  +						dev_private_size,
>  > >  > > >  +
>  	RTE_CACHE_LINE_SIZE,
>  > >  > > >  +						socket_id);
>  > >  > > >  +
>  > >  > > >  +		if (eventdev->data->dev_private == NULL)
>  > >  > > >  +			rte_panic("Cannot allocate memzone for
>  private
>  > >  > > >  device"
>  > >  > > >  +					" data");
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	return eventdev;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_eventdev_pmd_pci_probe(struct rte_pci_driver *pci_drv,
>  > >  > > >  +			struct rte_pci_device *pci_dev)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev_driver *eventdrv;
>  > >  > > >  +	struct rte_eventdev *eventdev;
>  > >  > > >  +
>  > >  > > >  +	char eventdev_name[RTE_EVENTDEV_NAME_MAX_LEN];
>  > >  > > >  +
>  > >  > > >  +	int retval;
>  > >  > > >  +
>  > >  > > >  +	eventdrv = (struct rte_eventdev_driver *)pci_drv;
>  > >  > > >  +	if (eventdrv == NULL)
>  > >  > > >  +		return -ENODEV;
>  > >  > > >  +
>  > >  > > >  +	rte_eal_pci_device_name(&pci_dev->addr, eventdev_name,
>  > >  > > >  +			sizeof(eventdev_name));
>  > >  > > >  +
>  > >  > > >  +	eventdev = rte_eventdev_pmd_allocate(eventdev_name,
>  > >  > > >  +			 pci_dev->device.numa_node);
>  > >  > > >  +	if (eventdev == NULL)
>  > >  > > >  +		return -ENOMEM;
>  > >  > > >  +
>  > >  > > >  +	if (rte_eal_process_type() == RTE_PROC_PRIMARY) {
>  > >  > > >  +		eventdev->data->dev_private =
>  > >  > > >  +				rte_zmalloc_socket(
>  > >  > > >  +						"eventdev private
>  structure",
>  > >  > > >  +						eventdrv-
>  >dev_private_size,
>  > >  > > >  +
>  	RTE_CACHE_LINE_SIZE,
>  > >  > > >  +						rte_socket_id());
>  > >  > > >  +
>  > >  > > >  +		if (eventdev->data->dev_private == NULL)
>  > >  > > >  +			rte_panic("Cannot allocate memzone for
>  private "
>  > >  > > >  +					"device data");
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	eventdev->pci_dev = pci_dev;
>  > >  > > >  +	eventdev->driver = eventdrv;
>  > >  > > >  +
>  > >  > > >  +	/* Invoke PMD device initialization function */
>  > >  > > >  +	retval = (*eventdrv->eventdev_init)(eventdev);
>  > >  > > >  +	if (retval == 0)
>  > >  > > >  +		return 0;
>  > >  > > >  +
>  > >  > > >  +	EDEV_LOG_ERR("driver %s: event_dev_init(vendor_id=0x%x
>  > >  > > >  device_id=0x%x)"
>  > >  > > >  +			" failed", pci_drv->driver.name,
>  > >  > > >  +			(unsigned int) pci_dev->id.vendor_id,
>  > >  > > >  +			(unsigned int) pci_dev->id.device_id);
>  > >  > > >  +
>  > >  > > >  +	if (rte_eal_process_type() == RTE_PROC_PRIMARY)
>  > >  > > >  +		rte_free(eventdev->data->dev_private);
>  > >  > > >  +
>  > >  > > >  +	eventdev->attached = RTE_EVENTDEV_DETACHED;
>  > >  > > >  +	eventdev_globals.nb_devs--;
>  > >  > > >  +
>  > >  > > >  +	return -ENXIO;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +int
>  > >  > > >  +rte_eventdev_pmd_pci_remove(struct rte_pci_device *pci_dev)
>  > >  > > >  +{
>  > >  > > >  +	const struct rte_eventdev_driver *eventdrv;
>  > >  > > >  +	struct rte_eventdev *eventdev;
>  > >  > > >  +	char eventdev_name[RTE_EVENTDEV_NAME_MAX_LEN];
>  > >  > > >  +	int ret;
>  > >  > > >  +
>  > >  > > >  +	if (pci_dev == NULL)
>  > >  > > >  +		return -EINVAL;
>  > >  > > >  +
>  > >  > > >  +	rte_eal_pci_device_name(&pci_dev->addr, eventdev_name,
>  > >  > > >  +			sizeof(eventdev_name));
>  > >  > > >  +
>  > >  > > >  +	eventdev =
>  rte_eventdev_pmd_get_named_dev(eventdev_name);
>  > >  > > >  +	if (eventdev == NULL)
>  > >  > > >  +		return -ENODEV;
>  > >  > > >  +
>  > >  > > >  +	eventdrv = (const struct rte_eventdev_driver *)pci_dev->driver;
>  > >  > > >  +	if (eventdrv == NULL)
>  > >  > > >  +		return -ENODEV;
>  > >  > > >  +
>  > >  > > >  +	/* Invoke PMD device uninit function */
>  > >  > > >  +	if (*eventdrv->eventdev_uninit) {
>  > >  > > >  +		ret = (*eventdrv->eventdev_uninit)(eventdev);
>  > >  > > >  +		if (ret)
>  > >  > > >  +			return ret;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	/* Free event device */
>  > >  > > >  +	rte_eventdev_pmd_release(eventdev);
>  > >  > > >  +
>  > >  > > >  +	if (rte_eal_process_type() == RTE_PROC_PRIMARY)
>  > >  > > >  +		rte_free(eventdev->data->dev_private);
>  > >  > > >  +
>  > >  > > >  +	eventdev->pci_dev = NULL;
>  > >  > > >  +	eventdev->driver = NULL;
>  > >  > > >  +
>  > >  > > >  +	return 0;
>  > >  > > >  +}
>  > >  > > >  diff --git a/lib/librte_eventdev/rte_eventdev_pmd.h
>  > >  > > >  b/lib/librte_eventdev/rte_eventdev_pmd.h
>  > >  > > >  new file mode 100644
>  > >  > > >  index 0000000..e9d9b83
>  > >  > > >  --- /dev/null
>  > >  > > >  +++ b/lib/librte_eventdev/rte_eventdev_pmd.h
>  > >  > > >  @@ -0,0 +1,504 @@
>  > >  > > >  +/*
>  > >  > > >  + *
>  > >  > > >  + *   Copyright(c) 2016 Cavium networks. All rights reserved.
>  > >  > > >  + *
>  > >  > > >  + *   Redistribution and use in source and binary forms, with or
>  without
>  > >  > > >  + *   modification, are permitted provided that the following
>  conditions
>  > >  > > >  + *   are met:
>  > >  > > >  + *
>  > >  > > >  + *     * Redistributions of source code must retain the above
>  copyright
>  > >  > > >  + *       notice, this list of conditions and the following disclaimer.
>  > >  > > >  + *     * Redistributions in binary form must reproduce the above
>  > >  copyright
>  > >  > > >  + *       notice, this list of conditions and the following disclaimer in
>  > >  > > >  + *       the documentation and/or other materials provided with the
>  > >  > > >  + *       distribution.
>  > >  > > >  + *     * Neither the name of Cavium networks nor the names of its
>  > >  > > >  + *       contributors may be used to endorse or promote products
>  derived
>  > >  > > >  + *       from this software without specific prior written permission.
>  > >  > > >  + *
>  > >  > > >  + *   THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
>  > >  > > >  CONTRIBUTORS
>  > >  > > >  + *   "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
>  INCLUDING,
>  > >  BUT
>  > >  > > >  NOT
>  > >  > > >  + *   LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
>  AND
>  > >  > > >  FITNESS FOR
>  > >  > > >  + *   A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
>  THE
>  > >  > > >  COPYRIGHT
>  > >  > > >  + *   OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
>  INDIRECT,
>  > >  > > >  INCIDENTAL,
>  > >  > > >  + *   SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
>  (INCLUDING,
>  > >  BUT
>  > >  > > >  NOT
>  > >  > > >  + *   LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
>  SERVICES;
>  > >  LOSS
>  > >  > > >  OF USE,
>  > >  > > >  + *   DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
>  > >  CAUSED
>  > >  > > >  AND ON ANY
>  > >  > > >  + *   THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
>  LIABILITY,
>  > >  OR
>  > >  > > >  TORT
>  > >  > > >  + *   (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY
>  WAY
>  > >  OUT OF
>  > >  > > >  THE USE
>  > >  > > >  + *   OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
>  SUCH
>  > >  > > >  DAMAGE.
>  > >  > > >  + */
>  > >  > > >  +
>  > >  > > >  +#ifndef _RTE_EVENTDEV_PMD_H_
>  > >  > > >  +#define _RTE_EVENTDEV_PMD_H_
>  > >  > > >  +
>  > >  > > >  +/** @file
>  > >  > > >  + * RTE Event PMD APIs
>  > >  > > >  + *
>  > >  > > >  + * @note
>  > >  > > >  + * These API are from event PMD only and user applications should
>  not
>  > >  call
>  > >  > > >  + * them directly.
>  > >  > > >  + */
>  > >  > > >  +
>  > >  > > >  +#ifdef __cplusplus
>  > >  > > >  +extern "C" {
>  > >  > > >  +#endif
>  > >  > > >  +
>  > >  > > >  +#include <string.h>
>  > >  > > >  +
>  > >  > > >  +#include <rte_dev.h>
>  > >  > > >  +#include <rte_pci.h>
>  > >  > > >  +#include <rte_malloc.h>
>  > >  > > >  +#include <rte_log.h>
>  > >  > > >  +#include <rte_common.h>
>  > >  > > >  +
>  > >  > > >  +#include "rte_eventdev.h"
>  > >  > > >  +
>  > >  > > >  +#ifdef RTE_LIBRTE_EVENTDEV_DEBUG
>  > >  > > >  +#define RTE_PMD_DEBUG_TRACE(...) \
>  > >  > > >  +	rte_pmd_debug_trace(__func__, __VA_ARGS__)
>  > >  > > >  +#else
>  > >  > > >  +#define RTE_PMD_DEBUG_TRACE(...)
>  > >  > > >  +#endif
>  > >  > > >  +
>  > >  > > >  +/* Logging Macros */
>  > >  > > >  +#define EDEV_LOG_ERR(fmt, args...) \
>  > >  > > >  +	RTE_LOG(ERR, EVENTDEV, "%s() line %u: " fmt "\n",  \
>  > >  > > >  +			__func__, __LINE__, ## args)
>  > >  > > >  +
>  > >  > > >  +#ifdef RTE_LIBRTE_EVENTDEV_DEBUG
>  > >  > > >  +#define EDEV_LOG_DEBUG(fmt, args...) \
>  > >  > > >  +	RTE_LOG(DEBUG, EVENTDEV, "%s() line %u: " fmt "\n",  \
>  > >  > > >  +			__func__, __LINE__, ## args)
>  > >  > > >  +#else
>  > >  > > >  +#define EDEV_LOG_DEBUG(fmt, args...) (void)0
>  > >  > > >  +#endif
>  > >  > > >  +
>  > >  > > >  +/* Macros to check for valid device */
>  > >  > > >  +#define RTE_EVENTDEV_VALID_DEVID_OR_ERR_RET(dev_id, retval)
>  do
>  > >  { \
>  > >  > > >  +	if (!rte_eventdev_pmd_is_valid_dev((dev_id))) { \
>  > >  > > >  +		EDEV_LOG_ERR("Invalid dev_id=%d\n", dev_id); \
>  > >  > > >  +		return retval; \
>  > >  > > >  +	} \
>  > >  > > >  +} while (0)
>  > >  > > >  +
>  > >  > > >  +#define RTE_EVENTDEV_VALID_DEVID_OR_RET(dev_id) do { \
>  > >  > > >  +	if (!rte_eventdev_pmd_is_valid_dev((dev_id))) { \
>  > >  > > >  +		EDEV_LOG_ERR("Invalid dev_id=%d\n", dev_id); \
>  > >  > > >  +		return; \
>  > >  > > >  +	} \
>  > >  > > >  +} while (0)
>  > >  > > >  +
>  > >  > > >  +#define RTE_EVENTDEV_DETACHED  (0)
>  > >  > > >  +#define RTE_EVENTDEV_ATTACHED  (1)
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Initialisation function of a event driver invoked for each matching
>  > >  > > >  + * event PCI device detected during the PCI probing phase.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   The dev pointer is the address of the *rte_eventdev* structure
>  > >  associated
>  > >  > > >  + *   with the matching device and which has been [automatically]
>  > >  allocated in
>  > >  > > >  + *   the *rte_event_devices* array.
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   - 0: Success, the device is properly initialised by the driver.
>  > >  > > >  + *        In particular, the driver MUST have set up the *dev_ops*
>  pointer
>  > >  > > >  + *        of the *dev* structure.
>  > >  > > >  + *   - <0: Error code of the device initialisation failure.
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_init_t)(struct rte_eventdev *dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Finalisation function of a driver invoked for each matching
>  > >  > > >  + * PCI device detected during the PCI closing phase.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   The dev pointer is the address of the *rte_eventdev* structure
>  > >  associated
>  > >  > > >  + *   with the matching device and which	has been
>  [automatically]
>  > >  allocated in
>  > >  > > >  + *   the *rte_event_devices* array.
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   - 0: Success, the device is properly finalised by the driver.
>  > >  > > >  + *        In particular, the driver MUST free the *dev_ops* pointer
>  > >  > > >  + *        of the *dev* structure.
>  > >  > > >  + *   - <0: Error code of the device initialisation failure.
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_uninit_t)(struct rte_eventdev *dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * The structure associated with a PMD driver.
>  > >  > > >  + *
>  > >  > > >  + * Each driver acts as a PCI driver and is represented by a generic
>  > >  > > >  + * *event_driver* structure that holds:
>  > >  > > >  + *
>  > >  > > >  + * - An *rte_pci_driver* structure (which must be the first field).
>  > >  > > >  + *
>  > >  > > >  + * - The *eventdev_init* function invoked for each matching PCI
>  device.
>  > >  > > >  + *
>  > >  > > >  + * - The size of the private data to allocate for each matching
>  device.
>  > >  > > >  + */
>  > >  > > >  +struct rte_eventdev_driver {
>  > >  > > >  +	struct rte_pci_driver pci_drv;	/**< The PMD is also a PCI
>  driver. */
>  > >  > > >  +	unsigned int dev_private_size;	/**< Size of device private
>  data. */
>  > >  > > >  +
>  > >  > > >  +	eventdev_init_t eventdev_init;	/**< Device init function. */
>  > >  > > >  +	eventdev_uninit_t eventdev_uninit; /**< Device uninit
>  function. */
>  > >  > > >  +};
>  > >  > > >  +
>  > >  > > >  +/** Global structure used for maintaining state of allocated event
>  > >  devices */
>  > >  > > >  +struct rte_eventdev_global {
>  > >  > > >  +	uint8_t nb_devs;	/**< Number of devices found */
>  > >  > > >  +	uint8_t max_devs;	/**< Max number of devices */
>  > >  > > >  +};
>  > >  > > >  +
>  > >  > > >  +extern struct rte_eventdev_global *rte_eventdev_globals;
>  > >  > > >  +/** Pointer to global event devices data structure. */
>  > >  > > >  +extern struct rte_eventdev *rte_eventdevs;
>  > >  > > >  +/** The pool of rte_eventdev structures. */
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Get the rte_eventdev structure device pointer for the named
>  device.
>  > >  > > >  + *
>  > >  > > >  + * @param name
>  > >  > > >  + *   device name to select the device structure.
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   - The rte_eventdev structure pointer for the given device ID.
>  > >  > > >  + */
>  > >  > > >  +static inline struct rte_eventdev *
>  > >  > > >  +rte_eventdev_pmd_get_named_dev(const char *name)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +	unsigned int i;
>  > >  > > >  +
>  > >  > > >  +	if (name == NULL)
>  > >  > > >  +		return NULL;
>  > >  > > >  +
>  > >  > > >  +	for (i = 0, dev = &rte_eventdevs[i];
>  > >  > > >  +			i < rte_eventdev_globals->max_devs; i++) {
>  > >  > > >  +		if ((dev->attached == RTE_EVENTDEV_ATTACHED) &&
>  > >  > > >  +				(strcmp(dev->data->name, name) ==
>  0))
>  > >  > > >  +			return dev;
>  > >  > > >  +	}
>  > >  > > >  +
>  > >  > > >  +	return NULL;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Validate if the event device index is valid attached event device.
>  > >  > > >  + *
>  > >  > > >  + * @param dev_id
>  > >  > > >  + *   Event device index.
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   - If the device index is valid (1) or not (0).
>  > >  > > >  + */
>  > >  > > >  +static inline unsigned
>  > >  > > >  +rte_eventdev_pmd_is_valid_dev(uint8_t dev_id)
>  > >  > > >  +{
>  > >  > > >  +	struct rte_eventdev *dev;
>  > >  > > >  +
>  > >  > > >  +	if (dev_id >= rte_eventdev_globals->nb_devs)
>  > >  > > >  +		return 0;
>  > >  > > >  +
>  > >  > > >  +	dev = &rte_eventdevs[dev_id];
>  > >  > > >  +	if (dev->attached != RTE_EVENTDEV_ATTACHED)
>  > >  > > >  +		return 0;
>  > >  > > >  +	else
>  > >  > > >  +		return 1;
>  > >  > > >  +}
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Definitions of all functions exported by a driver through the
>  > >  > > >  + * the generic structure of type *event_dev_ops* supplied in the
>  > >  > > >  + * *rte_eventdev* structure associated with a device.
>  > >  > > >  + */
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Get device information of a device.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param dev_info
>  > >  > > >  + *   Event device information structure
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_info_get_t)(struct rte_eventdev *dev,
>  > >  > > >  +		struct rte_event_dev_info *dev_info);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Configure a device.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_configure_t)(struct rte_eventdev *dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Start a configured device.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_start_t)(struct rte_eventdev *dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Stop a configured device.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_stop_t)(struct rte_eventdev *dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Close a configured device.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + * - 0 on success
>  > >  > > >  + * - (-EAGAIN) if can't close as device is busy
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_close_t)(struct rte_eventdev *dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Retrieve the default event queue configuration.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param queue_id
>  > >  > > >  + *   Event queue index
>  > >  > > >  + * @param[out] queue_conf
>  > >  > > >  + *   Event queue configuration structure
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_queue_default_conf_get_t)(struct
>  > >  rte_eventdev
>  > >  > > >  *dev,
>  > >  > > >  +		uint8_t queue_id, struct rte_event_queue_conf
>  *queue_conf);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Setup an event queue.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param queue_id
>  > >  > > >  + *   Event queue index
>  > >  > > >  + * @param queue_conf
>  > >  > > >  + *   Event queue configuration structure
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success.
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_queue_setup_t)(struct rte_eventdev *dev,
>  > >  > > >  +		uint8_t queue_id, struct rte_event_queue_conf
>  *queue_conf);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Release memory resources allocated by given event queue.
>  > >  > > >  + *
>  > >  > > >  + * @param queue
>  > >  > > >  + *   Event queue pointer
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_queue_release_t)(void *queue);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Retrieve the default event port configuration.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param port_id
>  > >  > > >  + *   Event port index
>  > >  > > >  + * @param[out] port_conf
>  > >  > > >  + *   Event port configuration structure
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_port_default_conf_get_t)(struct
>  rte_eventdev
>  > >  *dev,
>  > >  > > >  +		uint8_t port_id, struct rte_event_port_conf
>  *port_conf);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Setup an event port.
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param port_id
>  > >  > > >  + *   Event port index
>  > >  > > >  + * @param port_conf
>  > >  > > >  + *   Event port configuration structure
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success.
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_port_setup_t)(struct rte_eventdev *dev,
>  > >  > > >  +		uint8_t port_id, struct rte_event_port_conf
>  *port_conf);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Release memory resources allocated by given event port.
>  > >  > > >  + *
>  > >  > > >  + * @param port
>  > >  > > >  + *   Event port pointer
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_port_release_t)(void *port);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Link multiple source event queues to destination event port.
>  > >  > > >  + *
>  > >  > > >  + * @param port
>  > >  > > >  + *   Event port pointer
>  > >  > > >  + * @param link
>  > >  > > >  + *   An array of *nb_links* pointers to *rte_event_queue_link*
>  structure
>  > >  > > >  + * @param nb_links
>  > >  > > >  + *   The number of links to establish
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success.
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_port_link_t)(void *port,
>  > >  > > >  +		struct rte_event_queue_link link[], uint16_t nb_links);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Unlink multiple source event queues from destination event port.
>  > >  > > >  + *
>  > >  > > >  + * @param port
>  > >  > > >  + *   Event port pointer
>  > >  > > >  + * @param queues
>  > >  > > >  + *   An array of *nb_unlinks* event queues to be unlinked from the
>  event
>  > >  port.
>  > >  > > >  + * @param nb_unlinks
>  > >  > > >  + *   The number of unlinks to establish
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   Returns 0 on success.
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef int (*eventdev_port_unlink_t)(void *port,
>  > >  > > >  +		uint8_t queues[], uint16_t nb_unlinks);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Converts nanoseconds to *wait* value for rte_event_dequeue()
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param ns
>  > >  > > >  + *   Wait time in nanosecond
>  > >  > > >  + * @param[out] wait_ticks
>  > >  > > >  + *   Value for the *wait* parameter in rte_event_dequeue() function
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_dequeue_wait_time_t)(struct
>  rte_eventdev
>  > >  *dev,
>  > >  > > >  +		uint64_t ns, uint64_t *wait_ticks);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Dump internal information
>  > >  > > >  + *
>  > >  > > >  + * @param dev
>  > >  > > >  + *   Event device pointer
>  > >  > > >  + * @param f
>  > >  > > >  + *   A pointer to a file for output
>  > >  > > >  + *
>  > >  > > >  + */
>  > >  > > >  +typedef void (*eventdev_dump_t)(struct rte_eventdev *dev, FILE
>  *f);
>  > >  > > >  +
>  > >  > > >  +/** Event device operations function pointer table */
>  > >  > > >  +struct rte_eventdev_ops {
>  > >  > > >  +	eventdev_info_get_t dev_infos_get;	/**< Get device info.
>  */
>  > >  > > >  +	eventdev_configure_t dev_configure;	/**< Configure
>  device. */
>  > >  > > >  +	eventdev_start_t dev_start;		/**< Start device. */
>  > >  > > >  +	eventdev_stop_t dev_stop;		/**< Stop device. */
>  > >  > > >  +	eventdev_close_t dev_close;		/**< Close device. */
>  > >  > > >  +
>  > >  > > >  +	eventdev_queue_default_conf_get_t queue_def_conf;
>  > >  > > >  +	/**< Get default queue configuration. */
>  > >  > > >  +	eventdev_queue_setup_t queue_setup;
>  > >  > > >  +	/**< Set up an event queue. */
>  > >  > > >  +	eventdev_queue_release_t queue_release;
>  > >  > > >  +	/**< Release an event queue. */
>  > >  > > >  +
>  > >  > > >  +	eventdev_port_default_conf_get_t port_def_conf;
>  > >  > > >  +	/**< Get default port configuration. */
>  > >  > > >  +	eventdev_port_setup_t port_setup;
>  > >  > > >  +	/**< Set up an event port. */
>  > >  > > >  +	eventdev_port_release_t port_release;
>  > >  > > >  +	/**< Release an event port. */
>  > >  > > >  +
>  > >  > > >  +	eventdev_port_link_t port_link;
>  > >  > > >  +	/**< Link event queues to an event port. */
>  > >  > > >  +	eventdev_port_unlink_t port_unlink;
>  > >  > > >  +	/**< Unlink event queues from an event port. */
>  > >  > > >  +	eventdev_dequeue_wait_time_t wait_time;
>  > >  > > >  +	/**< Converts nanoseconds to *wait* value for
>  rte_event_dequeue()
>  > >  > > >  */
>  > >  > > >  +	eventdev_dump_t dump;
>  > >  > > >  +	/* Dump internal information */
>  > >  > > >  +};
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Allocates a new eventdev slot for an event device and returns the
>  > >  pointer
>  > >  > > >  + * to that slot for the driver to use.
>  > >  > > >  + *
>  > >  > > >  + * @param name
>  > >  > > >  + *   Unique identifier name for each device
>  > >  > > >  + * @param socket_id
>  > >  > > >  + *   Socket to allocate resources on.
>  > >  > > >  + * @return
>  > >  > > >  + *   - Slot in the rte_dev_devices array for a new device;
>  > >  > > >  + */
>  > >  > > >  +struct rte_eventdev *
>  > >  > > >  +rte_eventdev_pmd_allocate(const char *name, int socket_id);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Release the specified eventdev device.
>  > >  > > >  + *
>  > >  > > >  + * @param eventdev
>  > >  > > >  + * The *eventdev* pointer is the address of the *rte_eventdev*
>  > >  structure.
>  > >  > > >  + * @return
>  > >  > > >  + *   - 0 on success, negative on error
>  > >  > > >  + */
>  > >  > > >  +int
>  > >  > > >  +rte_eventdev_pmd_release(struct rte_eventdev *eventdev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Creates a new virtual event device and returns the pointer to that
>  > >  device.
>  > >  > > >  + *
>  > >  > > >  + * @param name
>  > >  > > >  + *   PMD type name
>  > >  > > >  + * @param dev_private_size
>  > >  > > >  + *   Size of event PMDs private data
>  > >  > > >  + * @param socket_id
>  > >  > > >  + *   Socket to allocate resources on.
>  > >  > > >  + *
>  > >  > > >  + * @return
>  > >  > > >  + *   - Eventdev pointer if device is successfully created.
>  > >  > > >  + *   - NULL if device cannot be created.
>  > >  > > >  + */
>  > >  > > >  +struct rte_eventdev *
>  > >  > > >  +rte_eventdev_pmd_vdev_init(const char *name, size_t
>  > >  dev_private_size,
>  > >  > > >  +		int socket_id);
>  > >  > > >  +
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Wrapper for use by pci drivers as a .probe function to attach to a
>  > >  event
>  > >  > > >  + * interface.
>  > >  > > >  + */
>  > >  > > >  +int rte_eventdev_pmd_pci_probe(struct rte_pci_driver *pci_drv,
>  > >  > > >  +			    struct rte_pci_device *pci_dev);
>  > >  > > >  +
>  > >  > > >  +/**
>  > >  > > >  + * Wrapper for use by pci drivers as a .remove function to detach a
>  > >  event
>  > >  > > >  + * interface.
>  > >  > > >  + */
>  > >  > > >  +int rte_eventdev_pmd_pci_remove(struct rte_pci_device *pci_dev);
>  > >  > > >  +
>  > >  > > >  +#ifdef __cplusplus
>  > >  > > >  +}
>  > >  > > >  +#endif
>  > >  > > >  +
>  > >  > > >  +#endif /* _RTE_EVENTDEV_PMD_H_ */
>  > >  > > >  diff --git a/lib/librte_eventdev/rte_eventdev_version.map
>  > >  > > >  b/lib/librte_eventdev/rte_eventdev_version.map
>  > >  > > >  new file mode 100644
>  > >  > > >  index 0000000..ef40aae
>  > >  > > >  --- /dev/null
>  > >  > > >  +++ b/lib/librte_eventdev/rte_eventdev_version.map
>  > >  > > >  @@ -0,0 +1,39 @@
>  > >  > > >  +DPDK_17.02 {
>  > >  > > >  +	global:
>  > >  > > >  +
>  > >  > > >  +	rte_eventdevs;
>  > >  > > >  +
>  > >  > > >  +	rte_event_dev_count;
>  > >  > > >  +	rte_event_dev_get_dev_id;
>  > >  > > >  +	rte_event_dev_socket_id;
>  > >  > > >  +	rte_event_dev_info_get;
>  > >  > > >  +	rte_event_dev_configure;
>  > >  > > >  +	rte_event_dev_start;
>  > >  > > >  +	rte_event_dev_stop;
>  > >  > > >  +	rte_event_dev_close;
>  > >  > > >  +	rte_event_dev_dump;
>  > >  > > >  +
>  > >  > > >  +	rte_event_port_default_conf_get;
>  > >  > > >  +	rte_event_port_setup;
>  > >  > > >  +	rte_event_port_dequeue_depth;
>  > >  > > >  +	rte_event_port_enqueue_depth;
>  > >  > > >  +	rte_event_port_count;
>  > >  > > >  +	rte_event_port_link;
>  > >  > > >  +	rte_event_port_unlink;
>  > >  > > >  +	rte_event_port_links_get;
>  > >  > > >  +
>  > >  > > >  +	rte_event_queue_default_conf_get
>  > >  > > >  +	rte_event_queue_setup;
>  > >  > > >  +	rte_event_queue_count;
>  > >  > > >  +	rte_event_queue_priority;
>  > >  > > >  +
>  > >  > > >  +	rte_event_dequeue_wait_time;
>  > >  > > >  +
>  > >  > > >  +	rte_eventdev_pmd_allocate;
>  > >  > > >  +	rte_eventdev_pmd_release;
>  > >  > > >  +	rte_eventdev_pmd_vdev_init;
>  > >  > > >  +	rte_eventdev_pmd_pci_probe;
>  > >  > > >  +	rte_eventdev_pmd_pci_remove;
>  > >  > > >  +
>  > >  > > >  +	local: *;
>  > >  > > >  +};
>  > >  > > >  diff --git a/mk/rte.app.mk b/mk/rte.app.mk
>  > >  > > >  index f75f0e2..716725a 100644
>  > >  > > >  --- a/mk/rte.app.mk
>  > >  > > >  +++ b/mk/rte.app.mk
>  > >  > > >  @@ -93,6 +93,7 @@ _LDLIBS-$(CONFIG_RTE_LIBRTE_MBUF)
>  += -
>  > >  > > >  lrte_mbuf
>  > >  > > >   _LDLIBS-$(CONFIG_RTE_LIBRTE_NET)            += -lrte_net
>  > >  > > >   _LDLIBS-$(CONFIG_RTE_LIBRTE_ETHER)          += -lrte_ethdev
>  > >  > > >   _LDLIBS-$(CONFIG_RTE_LIBRTE_CRYPTODEV)      += -lrte_cryptodev
>  > >  > > >  +_LDLIBS-$(CONFIG_RTE_LIBRTE_EVENTDEV)       += -lrte_eventdev
>  > >  > > >   _LDLIBS-$(CONFIG_RTE_LIBRTE_MEMPOOL)        += -lrte_mempool
>  > >  > > >   _LDLIBS-$(CONFIG_RTE_LIBRTE_RING)           += -lrte_ring
>  > >  > > >   _LDLIBS-$(CONFIG_RTE_LIBRTE_EAL)            += -lrte_eal
>  > >  > > >  --
>  > >  > > >  2.5.5
>  > >  > >


More information about the dev mailing list