Hi,

* I was thinking of adding custom tags for optional function.
But I am no Doxygen expert if you think @note is the way forward we can
follow that.

* I will follow the current syntax of 0 for Success and -1 for error and
change my current patch and make it consistent. We can take up #define as a
separate discussion if required

* Should I add ODP_UNIMPLEMENTED as part of my current patch?

Regards,
Bala

On 7 October 2014 00:16, Mike Holmes <mike.hol...@linaro.org> wrote:

>
>
> On 6 October 2014 14:33, Bala Manoharan <bala.manoha...@linaro.org> wrote:
>
>> Hi Mike,
>>
>> Comments inline.
>>
>> Regards,
>> Bala
>>
>> On 6 October 2014 23:34, Mike Holmes <mike.hol...@linaro.org> wrote:
>>
>>>
>>>
>>> On 6 October 2014 12:05, Balasubramanian Manoharan <
>>> bala.manoha...@linaro.org> wrote:
>>>
>>>> This patch contains ODP Classification API Header Files.
>>>> The intent of this patch is to port the APIs from Classification design
>>>> document into linux-generic repo.
>>>> The dummy functions in the classification source code will be replaced
>>>> during linux-generic implementation.
>>>>
>>>> Signed-off-by: Balasubramanian Manoharan <bala.manoha...@linaro.org>
>>>> ---
>>>>  platform/linux-generic/Makefile.am                 |   2 +
>>>>  .../linux-generic/include/api/odp_classification.h | 532
>>>> +++++++++++++++++++++
>>>>  platform/linux-generic/include/api/odp_packet_io.h |   5 +
>>>>  platform/linux-generic/include/api/odp_queue.h     |   5 +
>>>>  platform/linux-generic/odp_classification.c        | 235 +++++++++
>>>>  5 files changed, 779 insertions(+)
>>>>  create mode 100644
>>>> platform/linux-generic/include/api/odp_classification.h
>>>>  create mode 100644 platform/linux-generic/odp_classification.c
>>>>
>>>> diff --git a/platform/linux-generic/Makefile.am
>>>> b/platform/linux-generic/Makefile.am
>>>> index d076d50..38dfdd1 100644
>>>> --- a/platform/linux-generic/Makefile.am
>>>> +++ b/platform/linux-generic/Makefile.am
>>>> @@ -12,6 +12,7 @@ include_HEADERS = \
>>>>
>>>> $(top_srcdir)/platform/linux-generic/include/api/odp_barrier.h \
>>>>
>>>> $(top_srcdir)/platform/linux-generic/include/api/odp_buffer.h \
>>>>
>>>> $(top_srcdir)/platform/linux-generic/include/api/odp_buffer_pool.h \
>>>> +
>>>>  $(top_srcdir)/platform/linux-generic/include/api/odp_classification.h \
>>>>
>>>> $(top_srcdir)/platform/linux-generic/include/api/odp_byteorder.h \
>>>>
>>>> $(top_srcdir)/platform/linux-generic/include/api/odp_compiler.h \
>>>>
>>>> $(top_srcdir)/platform/linux-generic/include/api/odp_config.h \
>>>> @@ -51,6 +52,7 @@ __LIB__libodp_la_SOURCES = \
>>>>                            odp_barrier.c \
>>>>                            odp_buffer.c \
>>>>                            odp_buffer_pool.c \
>>>> +                          odp_classification.c \
>>>>                            odp_coremask.c \
>>>>                            odp_crypto.c \
>>>>                            odp_init.c \
>>>> diff --git a/platform/linux-generic/include/api/odp_classification.h
>>>> b/platform/linux-generic/include/api/odp_classification.h
>>>> new file mode 100644
>>>> index 0000000..f325c99
>>>> --- /dev/null
>>>> +++ b/platform/linux-generic/include/api/odp_classification.h
>>>> @@ -0,0 +1,532 @@
>>>> +/* Copyright (c) 2013, Linaro Limited
>>>> + * All rights reserved.
>>>> + *
>>>> + * SPDX-License-Identifier:     BSD-3-Clause
>>>> + */
>>>> +
>>>> +
>>>> +/**
>>>> + * @file
>>>> + *
>>>> + * ODP classification descriptor
>>>> + */
>>>> +
>>>> +#ifndef ODP_CLASSIFY_H_
>>>> +#define ODP_CLASSIFY_H_
>>>> +
>>>> +#ifdef __cplusplus
>>>> +extern "C" {
>>>> +#endif
>>>> +
>>>> +
>>>> +#include <odp_std_types.h>
>>>> +#include <odp_buffer_pool.h>
>>>> +#include <odp_packet.h>
>>>> +#include <odp_packet_io.h>
>>>> +#include <odp_queue.h>
>>>> +
>>>> +/**
>>>> + * Class of service instance type
>>>> + */
>>>> +typedef uint32_t odp_cos_t;
>>>> +
>>>> +
>>>> +/**
>>>> + * flow signature type, only used for packet meta data field.
>>>> + */
>>>> +typedef uint32_t odp_flowsig_t;
>>>> +
>>>> +/**
>>>> + * This value is returned from odp_cos_create() on failure,
>>>> + * May also be used as a “sink” class of service that
>>>> + * results in packets being discarded.
>>>> +*/
>>>> +#define ODP_COS_INVALID    ((odp_cos_t)~0)
>>>> +
>>>> +/**
>>>> + * Class-of-service packet drop policies
>>>> + */
>>>> +typedef enum odp_cos_drop {
>>>> +       ODP_COS_DROP_POOL,    /**< Follow buffer pool drop policy */
>>>> +       ODP_COS_DROP_NEVER,    /**< Never drop, ignoring buffer pool
>>>> policy */
>>>> +} odp_drop_e;
>>>> +
>>>> +/**
>>>> + * Packet header field enumeration
>>>> + * for fields that may be used to calculate
>>>> + * the flow signature, if present in a packet.
>>>> + */
>>>> +typedef enum odp_cos_hdr_flow_fields {
>>>> +       ODP_COS_FHDR_IN_PKTIO,  /**< Ingress port number */
>>>> +       ODP_COS_FHDR_L2_SAP,    /**< Ethernet Source MAC address */
>>>> +       ODP_COS_FHDR_L2_DAP,    /**< Ethernet Destination MAC address */
>>>> +       ODP_COS_FHDR_L2_VID,    /**< Ethernet VLAN ID */
>>>> +       ODP_COS_FHDR_L3_FLOW,   /**< IPv6 flow_id */
>>>> +       ODP_COS_FHDR_L3_SAP,    /**< IP source address */
>>>> +       ODP_COS_FHDR_L3_DAP,    /**< IP destination address */
>>>> +       ODP_COS_FHDR_L4_PROTO,  /**< IP protocol (e.g. TCP/UDP/ICMP) */
>>>> +       ODP_COS_FHDR_L4_SAP,    /**< Transport source port */
>>>> +       ODP_COS_FHDR_L4_DAP,    /**< Transport destination port */
>>>> +       ODP_COS_FHDR_IPSEC_SPI, /**< IPsec session identifier */
>>>> +       ODP_COS_FHDR_LD_VNI,    /**< NVGRE/VXLAN network identifier */
>>>> +       ODP_COS_FHDR_USER       /**< Application-specific header
>>>> field(s) */
>>>> +} odp_cos_hdr_flow_fields_e;
>>>> +
>>>> +/**
>>>> + * Create a class-of-service
>>>> + *
>>>> + * @param  name is a string intended for debugging purposes.
>>>>
>>>
>>> Placed here but in general
>>> Please use  "[in]", "[in,out]", and "[out]" to mark the arguments
>>> http://www.stack.nl/~dimitri/doxygen/manual/commands.html#cmdparam
>>>
>>> Some you can figure out, but it is not always obvious.
>>>
>>> >> Sure will add the suitable markers.
>>
>>> + *
>>>> + * @return Class of service instance identifier,
>>>> + *         or ODP_COS_INVALID on error.
>>>> + */
>>>> +odp_cos_t odp_cos_create(const char *name);
>>>> +
>>>> +/**
>>>> + * Discard a class-of-service along with all its associated resources
>>>> + *
>>>> + * @param cos_id class-of-service instance.
>>>> + *
>>>> + * @return 0 on success, -1 on error.
>>>> + */
>>>> +int odp_cos_destroy(odp_cos_t cos_id);
>>>> +
>>>> +/**
>>>> + * Assign a queue for a class-of-service
>>>> + *
>>>> + * @param cos_id   class-of-service instance.
>>>> + *
>>>> + * @param          queue_id is the identifier of a queue where all
>>>> packets
>>>> + *                 of this specific class of service will be enqueued.
>>>> + *
>>>> + * @return         0 on success, negative error code on failure.
>>>> + */
>>>> +int odp_cos_set_queue(odp_cos_t cos_id, odp_queue_t queue_id);
>>>> +
>>>> +/**
>>>> + * Assign a homogenous queue-group to a class-of-service.
>>>> + *
>>>> + * @param cos_id         identifier of class-of-service instance
>>>> + * @param queue_group_id identifier of the queue group to receive
>>>> packets
>>>> + *                       associated with this class of service.
>>>> + *
>>>> + * @return               0 on success, negative error code on failure.
>>>> + */
>>>> +int odp_cos_set_queue_group(odp_cos_t cos_id,
>>>> +                           odp_queue_group_t queue_group_id);
>>>> +
>>>> +/**
>>>> + * Assign packet buffer pool for specific class-of-service
>>>> + *
>>>> + * @param cos_id  class-of-service instance.
>>>> + * @param pool_id is a buffer pool identifier where all packet buffers
>>>> + *                will be sourced to store packet that belong to this
>>>> + *                class of service.
>>>> + *
>>>> + * @return        0 on success negative error code on failure.
>>>> + *
>>>> + * @status Optional.
>>>>
>>>
>>> How is status reported in Doxygen ? I could not find that keyword,
>>> should this be @note Optional API
>>>
>> >> I am okay with any approach. @note or can it be simply @optional
>> especially if we are planning to have mandatory as default.
>>
>
> How would @optional  work ?  I cant find a doxygen keyword called optional
> either, I suggested @note because it will be highlighted in the final
> document but I don't think doxygen would understand @status or @optional.
>
>
>>
>>>
>>>> + */
>>>> +int odp_cos_set_pool(odp_cos_t cos_id, odp_buffer_pool_t pool_id);
>>>> +
>>>> +
>>>> +/**
>>>> + * Assign packet drop policy for specific class-of-service
>>>> + *
>>>> + * @param   cos_id class-of-service instance.
>>>> + * @param   drop_policy is the desired packet drop policy for this
>>>> class.
>>>> + *
>>>> + * @return  0 on success negative error code on failure.
>>>> + *
>>>> + * @status Optional.
>>>> + */
>>>> +int odp_cos_set_drop(odp_cos_t cos_id, odp_drop_e drop_policy);
>>>> +
>>>> +/**
>>>> + * Setup per-port default class-of-service
>>>> + *
>>>> + * @param   pktio_in ingress port identifier.
>>>> + * @param   default_cos class-of-service set to all packets arriving
>>>> + *          at the 'pktio_in' ingress port, unless overridden by
>>>> subsequent
>>>> + *          header-based filters.
>>>> + *
>>>> + * @return  0 on success negative error code on failure.
>>>> + *
>>>> + * @status  Mandatory.
>>>> + * @note    This may replace the default queue per pktio.
>>>> + */
>>>> +int odp_pktio_set_default_cos(odp_pktio_t pktio_in, odp_cos_t
>>>> default_cos);
>>>> +
>>>> +/**
>>>> + * Setup per-port error class-of-service
>>>> + *
>>>> + * @param   pktio_in ingress port identifier.
>>>> + * @param   error_cos class-of-service set to all packets arriving
>>>> + *          at the 'pktio_in' ingress port that contain an error.
>>>> + *
>>>> + * @return  0 on success negative error code on failure.
>>>> + *
>>>> + *
>>>> + * @status Optional.
>>>> + */
>>>> +int odp_pktio_set_error_cos(odp_pktio_t pktio_in, odp_cos_t error_cos);
>>>> +
>>>> +/**
>>>> + * Setup per-port header offset
>>>> + *
>>>> + * @param   pktio_in ingress port identifier.
>>>> + * @param   offset is the number of bytes the classifier must skip.
>>>> + *
>>>> + * @return  Success or ODP_FUNCTION_NOT_AVAILABLE
>>>>
>>>
>>> What do I test for to determine Success - 0 ?
>>>
>> A value of 0 for Success and -1 for failure is the current standard which
>> is followed in all buffer and packet header files.
>> Maybe we can create ODP_SUCCESS and ODP_FAILURE #defines in odp_debug.h
>> file and follow the same everywhere.
>>
>
> I think that could help, we would need to patch up quite a lot of API code
> though, it should make the code slightly more readable.
> In this case for your patch my point was more consistency in the
> descriptions though, on some APIs you spell out that 0 is a success, and on
> other others you just say success but leave it up to the reader to find out
> what that means.
>
>
>>
>>>
>>> + * @status  Optional.
>>>> + *
>>>> + */
>>>> +int odp_pktio_set_skip(odp_pktio_t pktio_in, size_t offset);
>>>> +
>>>> +/**
>>>> + * Specify per-port buffer headroom
>>>> + *
>>>> + * @param   pktio_in  ingress port identifier.
>>>> + * @param   headroom  number of bytes of space preceding packet data
>>>> to reserve
>>>> + *                    for use as headroom.  Must not exceed the
>>>> implementation
>>>> + *                    defined ODP_PACKET_MAX_HEADROOM.
>>>> + *
>>>> + * @return  Success or ODP_PARAMETER_ERROR,
>>>> + *                  or ODP_FUNCTION_NOT_AVAILABLE
>>>>
>>>
>>> What do I test for to determine Success - 0 ?
>>>
>>>
>>>> + *
>>>> + * @status Optional.
>>>
>>> + */
>>>> +int odp_pktio_set_headroom(odp_pktio_t port_id, size_t headroom);
>>>> +
>>>> +/**
>>>> + * Specify per-cos buffer headroom
>>>> + *
>>>> + * @param   cos_id     class-of-service instance
>>>> + * @param   headroom  number of bytes of space preceding packet data
>>>> to reserve
>>>> + *                    for use as headroom.  Must not exceed the
>>>> implementation
>>>> + *                    defined ODP_PACKET_MAX_HEADROOM.
>>>> + *
>>>> + * @return  Success or ODP_PARAMETER_ERROR,
>>>> + *                  or ODP_FUNCTION_NOT_AVAILABLE
>>>>
>>>
>>> What do I test for to determine Success - 0 ?
>>>
>>> + *
>>>> + * @status Optional.
>>>> + */
>>>> +int odp_cos_set_headroom(odp_cos_t cos_id, size_t req_room);
>>>> +
>>>> +/**
>>>> + * Request to override per-port class of service
>>>> + * based on Layer-2 priority field if present.
>>>> + *
>>>> + * @param   pktio_in ingress port identifier.
>>>> + * @param   num_qos is the number of QoS levels, typically 8.
>>>> + * @param   qos_table are the values of the Layer-2 QoS header field.
>>>> + * @param   cos_table is the class-of-service assigned to each of the
>>>> + *          allowed Layer-2 QOS levels.
>>>> + * @return  0 on success negative error code on failure.
>>>> + *
>>>> + * @status Mandatory.
>>>> + */
>>>> +int odp_cos_with_l2_priority(odp_pktio_t pktio_in,
>>>> +                            size_t num_qos,
>>>> +                            uint8_t qos_table[],
>>>> +                            odp_cos_t cos_table[]);
>>>> +
>>>> +/**
>>>> + *
>>>> + * @param   pktio_in ingress port identifier.
>>>> + * @param   num_qos is the number of allowed Layer-3 QoS levels.
>>>> + * @param   qos_table are the values of the Layer-3 QoS header field.
>>>> + * @param   cos_table is the class-of-service assigned to each of the
>>>> + *          allowed Layer-3 QOS levels.
>>>> + * @param   l3_preference when true, Layer-3 QoS overrides L2 QoS when
>>>> present.
>>>> + *
>>>> + * @return  0 on success negative error code on failure.
>>>> + *
>>>> + * @status Optional.
>>>> + */
>>>> +int odp_cos_with_l3_qos(odp_pktio_t pktio_in,
>>>> +                       size_t num_qos,
>>>> +                       uint8_t qos_table[],
>>>> +                       odp_cos_t cos_table[],
>>>> +                       bool l3_preference);
>>>> +
>>>> +
>>>> +/**
>>>> + * Set of header fields that take part in flow signature hash
>>>> calculation:
>>>> + * bit positions per 'odp_cos_hdr_flow_fields_e' enumeration.
>>>> + */
>>>> +typedef uint16_t odp_cos_flow_set_t;
>>>> +
>>>> +/**
>>>> + * Set a member of the flow signature fields data set
>>>> + */
>>>> +static inline
>>>> +odp_cos_flow_set_t odp_cos_flow_set(odp_cos_flow_set_t set,
>>>> +                                   odp_cos_hdr_flow_fields_e field)
>>>> +{
>>>> +       return set | (1U << field);
>>>> +}
>>>> +
>>>> +/**
>>>> + * Test a member of the flow signature fields data set
>>>> + */
>>>> +static inline bool
>>>> +odp_cos_flow_is_set(odp_cos_flow_set_t set, odp_cos_hdr_flow_fields_e
>>>> field)
>>>> +{
>>>> +       return (set & (1U << field)) != 0;
>>>> +}
>>>> +
>>>> +/**
>>>> + * Set up set of headers used to calculate a flow signature
>>>> + * based on class-of-service.
>>>> + *
>>>> + * @param cos_id class of service instance identifier
>>>> + * @param req_data_set requested data-set for flow signature
>>>> calculation
>>>> + *
>>>> + * @return data-set that was successfully applied. All-zeros data set
>>>> + * indicates a failure to assign any of the requested fields, or other
>>>> + * error.
>>>> + * @status Optional.
>>>> + */
>>>> +odp_cos_flow_set_t
>>>> +odp_cos_class_flow_signature(odp_cos_t cos_id,
>>>> +                            odp_cos_flow_set_t req_data_set);
>>>> +
>>>> +/**
>>>> + * Set up set of headers used to calculate a flow signature
>>>> + * based on ingress port.
>>>> + *
>>>> + * @param pktio_in ingress port identifier.
>>>> + * @param req_data_set requested data-set for flow signature
>>>> calculation
>>>> + *
>>>> + * @return data-set that was successfully applied. An all-zeros
>>>> data-set
>>>> + * indicates a failure to assign any of the requested fields, or other
>>>> + * error.
>>>> + * @status Mandatory.
>>>>
>>>
>>> I imagine that this is the default, should we label all the ODP APIs as
>>> Mandatory
>>> rather than it selectively here.
>>>
>>>
>> I am okay with this approach.
>>
>>> + */
>>>> +odp_cos_flow_set_t
>>>> +odp_cos_port_flow_signature(odp_pktio_t pktio_in,
>>>> +                           odp_cos_flow_set_t req_data_set);
>>>> +
>>>> +/**
>>>> + * PMR - Packet Matching Rule
>>>> + * Up to 32 bit of ternary matching of one of the available header
>>>> fields
>>>> + */
>>>> +#define    ODP_PMR_INVAL ((odp_pmr_t)NULL)
>>>> +typedef struct odp_pmr_s *odp_pmr_t;
>>>> +
>>>> +/**
>>>> + * Packet Matching Rule field enumeration
>>>> + * for fields that may be used to calculate
>>>> + * the PMR, if present in a packet.
>>>> + */
>>>> +typedef enum odp_pmr_term {
>>>> +       ODP_PMR_LEN,            /**< Total length of received packet*/
>>>> +       ODP_PMR_ETHTYPE_0,      /**< Initial (outer)
>>>> +                               Ethertype only (*val=uint16_t)*/
>>>> +       ODP_PMR_ETHTYPE_X,      /**< Ethertype of most inner VLAN tag
>>>> +                               (*val=uint16_t)*/
>>>> +       ODP_PMR_VLAN_ID_0,      /**< First VLAN ID (outer)
>>>> (*val=uint16_t) */
>>>> +       ODP_PMR_VLAN_ID_X,      /**< Last VLAN ID (inner)
>>>> (*val=uint16_t) */
>>>> +       ODP_PMR_DMAC,           /**< destination MAC address
>>>> (*val=uint64_t)*/
>>>> +       ODP_PMR_IPPROTO,        /**< IP Protocol or IPv6 Next Header
>>>> +                               (*val=uint8_t) */
>>>> +       ODP_PMR_UDP_DPORT,      /**< Destination UDP port, implies
>>>> IPPROTO=17*/
>>>> +       ODP_PMR_TCP_DPORT,      /**< Destination TCP port implies
>>>> IPPROTO=6*/
>>>> +       ODP_PMR_UDP_SPORT,      /**< Source UDP Port (*val=uint16_t)*/
>>>> +       ODP_PMR_TCP_SPORT,      /**< Source TCP port (*val=uint16_t)*/
>>>> +       ODP_PMR_SIP_ADDR,       /**< Source IP address (uint32_t)*/
>>>> +       ODP_PMR_DIP_ADDR,       /**< Destination IP address (uint32_t)*/
>>>> +       ODP_PMR_SIP6_ADDR,      /**< Source IP address (uint8_t[16])*/
>>>> +       ODP_PMR_DIP6_ADDR,      /**< Destination IP address
>>>> (uint8_t[16])*/
>>>> +       ODP_PMR_IPSEC_SPI,      /**< IPsec session
>>>> identifier(*val=uint32_t)*/
>>>> +       ODP_PMR_LD_VNI,         /**< NVGRE/VXLAN network identifier
>>>> +                               (*val=uint32_t)*/
>>>> +
>>>> +       /** Inner header may repeat above values with this offset */
>>>> +       ODP_PMR_INNER_HDR_OFF = 32
>>>> +} odp_pmr_term_e;
>>>> +
>>>> +/**
>>>> + * Create a packet match rule with mask and value
>>>> + *
>>>> + * @param term      is one value of the enumerated values supported
>>>> + * @param val       is the value to match against the packet header
>>>> + *                  in native byte order.
>>>> + * @param   mask    is the mask to indicate which bits of the header
>>>> + *                  should be matched ('1') and which should be
>>>> ignored ('0')
>>>> + * @param   val_sz  size of the ‘val’ and ‘mask’ arguments,
>>>> + *                  that must match the value size requirement of the
>>>> + *                  specific ‘term’.
>>>> + *
>>>> + * @return a handle of the matching rule or ODP_PMR_INVAL on error
>>>> + */
>>>> +odp_pmr_t odp_pmr_create_match(odp_pmr_term_e term,
>>>> +                              const void *val,
>>>> +                              const void *mask,
>>>> +                              size_t val_sz);
>>>> +
>>>> +/**
>>>> + * Create a packet match rule with value range
>>>> + *
>>>> + * @param term      is one value of the enumerated values supported
>>>> + * @param val1      is the lower bound of the header field range.
>>>> + * @param val2      is the upper bound of the header field range.
>>>> + * @param val_sz    size of the ‘val1’ and ‘val2’ arguments,
>>>> + *                  that must match the value size requirement of the
>>>> + *                  specific ‘term’.
>>>> + *
>>>> + * @return a handle of the matching rule or ODP_PMR_INVAL on error
>>>> + * @note: Range is inclusive [val1..val2].
>>>> + */
>>>> +odp_pmr_t odp_pmr_create_range(odp_pmr_term_e term,
>>>> +                              const void *val1,
>>>> +                              const void *val2,
>>>> +                              size_t val_sz);
>>>> +/**
>>>> + * Invalidate a packet match rule and vacate its resources
>>>> + *
>>>> + * @param pmr_id    the identifier of the PMR to be destroyed
>>>> + *
>>>> + * @return Success or ODP_PMR_INVALID if the specified pmr_id not
>>>> found.
>>>>
>>> What do I test for to determine Success - 0 ?
>>>
>>>> + */
>>>> +int odp_pmr_destroy(odp_pmr_t pmr_id);
>>>> +
>>>> +/**
>>>> + * Apply a PMR to a pktio to assign a CoS.
>>>> + *
>>>> + * @param pmr_id     the id of the PMR to be activated
>>>> + * @param src_pktio  the pktio to which this PMR is to be applied
>>>> + * @param dst_cos    the CoS to be assigned by this PMR
>>>> + *
>>>> + * @return Success or ODP_PARAMETER_ERROR
>>>>
>>> What do I test for to determine Success - 0 ?
>>>
>>>> + */
>>>> +int odp_pktio_pmr_cos(odp_pmr_t pmr_id,
>>>> +                     odp_pktio_t src_pktio, odp_cos_t dst_cos);
>>>> +
>>>> +/**
>>>> + * Cascade a PMR to refine packets from one CoS to another.
>>>> + *
>>>> + * @param pmr_id     the id of the PMR to be activated
>>>> + * @param src_cos    the id of the CoS to be filtered
>>>> + * @param dst_cos    the id of the CoS to be assigned to packets
>>>> filtered
>>>> + *                   from src_cos that match pmr_id.
>>>> + *
>>>> + * @return Success or ODP_PARAMETER_ERROR if an input is in error
>>>> + *                 or ODP_IMPLEMENTATION_LIMIT if cascade depth is
>>>> exceeded
>>>>
>>>
>>> What do I test for to determine Success - 0 ?
>>>
>>>
>>>> + */
>>>> +int odp_cos_pmr_cos(odp_pmr_t pmr_id, odp_cos_t src_cos, odp_cos_t
>>>> dst_cos);
>>>> +
>>>> +/**
>>>> + * Retrieve packet matcher statistics
>>>> + *
>>>> + * @param pmr_id    the id of the PMR from which to retrieve the count
>>>> + *
>>>> + * @return The current number of matches for a given matcher instance.
>>>> + */
>>>> +signed long odp_pmr_match_count(odp_pmr_t pmr_id);
>>>> +
>>>> +/**
>>>> + * Inquire about matching terms supported by the classifier
>>>> + *
>>>> + * @return A mask one bit per enumerated term, one for each of
>>>> op_pmr_term_e
>>>> + */
>>>> +unsigned long long odp_pmr_terms_cap(void);
>>>> +
>>>> +/**
>>>> + * Return the number of packet matching terms available for use
>>>> + *
>>>> + * @return A number of packet matcher resources available for use.
>>>> + */
>>>> +unsigned odp_pmr_terms_avail(void);
>>>> +
>>>> +/**
>>>> + * Packet Match Type field enumeration
>>>> + * for fields that may be used to identify
>>>> + * the different PMR match type.
>>>> + */
>>>> +typedef enum odp_pmr_match_type {
>>>> +               ODP_PMR_MASK,       /**< Match a masked set of bits */
>>>> +               ODP_PMR_RANGE,      /**< Match an integer range */
>>>> +       } odp_pmr_match_type_e;
>>>> +
>>>> +/**
>>>> + * Following structure is used to define composite packet matching
>>>> rules
>>>> + * in the form of an array of individual match or range rules.
>>>> + * The underlying platform may not support all or any specific
>>>> combination
>>>> + * of value match or range rules, and the application should take care
>>>> + * of inspecting the return value when installing such rules, and
>>>> perform
>>>> + * appropriate fallback action.
>>>> + */
>>>> +typedef struct odp_pmr_match_t {
>>>> +       odp_pmr_match_type_e match_type;
>>>> +       union {
>>>> +               struct {
>>>> +                       odp_pmr_term_e  term;
>>>> +                       const void          *val;
>>>> +                       const void          *mask;
>>>> +                       unsigned int         val_sz;
>>>> +               } mask; /**< Match a masked set of bits */
>>>> +               struct {
>>>> +                       odp_pmr_term_e  term;
>>>> +                       const void          *val1;
>>>> +                       const void          *val2;
>>>> +                       unsigned int         val_sz;
>>>> +               } range; /**< Match an integer range */
>>>> +       };
>>>> +} odp_pmr_match_t;
>>>> +
>>>> +/** An opaque handle to a composite packet match rule-set */
>>>> +typedef struct odp_pmr_set_s *odp_pmr_set_t;
>>>> +
>>>> +/**
>>>> + * Create a composite packet match rule
>>>> + *
>>>> + * @param num_terms  is the number of terms in the match rule.
>>>> + * @param terms      is an array of num_terms entries, one entry per
>>>> + *                   term desired.
>>>> + * @param dst_cos    is the class-of-service to be assigned to packets
>>>> + *                   that match the compound rule-set, or a subset
>>>> thereof,
>>>> + *                   if partly applied.
>>>> + * @param pmr_set_id is the returned handle to the composite rule set.
>>>> + *
>>>> + * @return The return value may be a negative number indicating a
>>>> general
>>>> + * error, or a positive number indicating the number of ‘terms’
>>>> elements
>>>> + * that have been successfully mapped to the underlying platform
>>>> + * classification engine and may be in the range from 1 to ‘num_terms’.
>>>> + */
>>>> +int odp_pmr_match_set_create(int num_terms, odp_pmr_match_t *terms,
>>>> +                            odp_pmr_set_t *pmr_set_id);
>>>> +
>>>> +/**
>>>> + * Function to delete a composite packet match rule set
>>>> + *
>>>> + * All of the resources pertaining to the match set associated with the
>>>> + * class-of-service will be released, but the class-of-service will
>>>> + * remain intact.
>>>> + *
>>>> + * @param pmr_set_id a composite rule-set handle returned when created.
>>>> + *
>>>> + * @note Depending on the implementation details, destroying a rule-set
>>>> + * may not guarantee the availability of hardware resources to create
>>>> the
>>>> + * same or essentially similar rule-set.
>>>> + */
>>>> +int odp_pmr_match_set_destroy(odp_pmr_set_t pmr_set_id);
>>>> +
>>>> +/**
>>>> + * Apply a PMR Match Set to a pktio to assign a CoS.
>>>> + *
>>>> + * @param pmr_set_id the id of the PMR match set to be activated
>>>> + * @param src_pktio  the pktio to which this PMR match set is to be
>>>> applied
>>>> + * @param dst_cos    the CoS to be assigned by this PMR match set
>>>> + *
>>>> + * @return Success or ODP_PARAMETER_ERROR
>>>>
>>>
>>> What is Success, should we say 0 ?
>>>
>>>> + */
>>>> +int odp_pktio_pmr_match_set_cos(odp_pmr_t pmr_id, odp_pktio_t
>>>> src_pktio,
>>>> +                               odp_cos_t dst_cos);
>>>> +
>>>> +#ifdef __cplusplus
>>>> +}
>>>> +#endif
>>>> +
>>>> +#endif
>>>> diff --git a/platform/linux-generic/include/api/odp_packet_io.h
>>>> b/platform/linux-generic/include/api/odp_packet_io.h
>>>> index 29fd105..b532927 100644
>>>> --- a/platform/linux-generic/include/api/odp_packet_io.h
>>>> +++ b/platform/linux-generic/include/api/odp_packet_io.h
>>>> @@ -30,6 +30,11 @@ typedef uint32_t odp_pktio_t;
>>>>  #define ODP_PKTIO_INVALID 0
>>>>
>>>>  /**
>>>> + * 'odp_pktio_t' value to indicate any port
>>>> + */
>>>> +#define ODP_PKTIO_ANY ((odp_pktio_t)~0)
>>>> +
>>>> +/**
>>>>   * Open an ODP packet IO instance
>>>>   *
>>>>   * @param dev    Packet IO device
>>>> diff --git a/platform/linux-generic/include/api/odp_queue.h
>>>> b/platform/linux-generic/include/api/odp_queue.h
>>>> index 5e083f1..6e8efa9 100644
>>>> --- a/platform/linux-generic/include/api/odp_queue.h
>>>> +++ b/platform/linux-generic/include/api/odp_queue.h
>>>> @@ -28,6 +28,11 @@ extern "C" {
>>>>   */
>>>>  typedef uint32_t odp_queue_t;
>>>>
>>>> +/**
>>>> + * Queue group instance type
>>>> + */
>>>> +typedef uint32_t odp_queue_group_t;
>>>> +
>>>>  /** Invalid queue */
>>>>  #define ODP_QUEUE_INVALID  0
>>>>
>>>> diff --git a/platform/linux-generic/odp_classification.c
>>>> b/platform/linux-generic/odp_classification.c
>>>> new file mode 100644
>>>> index 0000000..183c9b9
>>>> --- /dev/null
>>>> +++ b/platform/linux-generic/odp_classification.c
>>>> @@ -0,0 +1,235 @@
>>>> +#include <odp_classification.h>
>>>> +#include <odp_align.h>
>>>> +#include <odp_queue.h>
>>>> +#include <odp_debug.h>
>>>> +#include <odp_packet_io.h>
>>>> +
>>>> +odp_cos_t odp_cos_create(const char *name)
>>>> +{
>>>> +       (void) name;
>>>> +       ODP_ERR("odp_cos_create() function is yet to be implemented");
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_destroy(odp_cos_t cos_id)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>>
>>>
>>> ODP_ERR already displays the function name so __func__ is not needed -
>>> same for FN below also.
>>>
>>> Do we want to define an ODP_UNIMPLIMENTED and add it to odp_debug.h?
>>> It might make greping different platforms easier for developers moving
>>> between releases and implimentations
>>>
>>> Maybe like this ?
>>>
>>> #define ODP_UNIMPLIMANTED
>>> do { fprintf(stderr, "%s:%d:%s(): " fmt, __FILE__, \
>>> __LINE__, __func__, ##__VA_ARGS__); \
>>> } while (0)
>>>
>>>
>>> Agreed. ODP_UNIMPLEMENTED is a good suggestion.
>>
>>>
>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_set_queue(odp_cos_t cos_id, odp_queue_t queue_id)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       (void)queue_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_set_queue_group(odp_cos_t cos_id, odp_queue_group_t
>>>> queue_group_id)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       (void)queue_group_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_set_pool(odp_cos_t cos_id, odp_buffer_pool_t pool_id)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       (void) pool_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +
>>>> +int odp_cos_set_drop(odp_cos_t cos_id, odp_drop_e drop_policy)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       (void)drop_policy;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pktio_set_default_cos(odp_pktio_t pktio_in, odp_cos_t
>>>> default_cos)
>>>> +{
>>>> +       (void)pktio_in;
>>>> +       (void)default_cos;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +int odp_pktio_set_error_cos(odp_pktio_t pktio_in, odp_cos_t error_cos)
>>>> +{
>>>> +       (void)pktio_in;
>>>> +       (void)error_cos;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pktio_set_skip(odp_pktio_t pktio_in, size_t offset)
>>>> +{
>>>> +       (void)pktio_in;
>>>> +       (void)offset;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pktio_set_headroom(odp_pktio_t port_id, size_t headroom)
>>>> +{
>>>> +       (void)port_id;
>>>> +       (void)headroom;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +int odp_cos_set_headroom(odp_cos_t cos_id, size_t req_room)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       (void)req_room;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_with_l2_priority(odp_pktio_t pktio_in,
>>>> +                            size_t num_qos,
>>>> +                            uint8_t qos_table[],
>>>> +                            odp_cos_t cos_table[])
>>>> +{
>>>> +       (void)pktio_in;
>>>> +       (void)num_qos;
>>>> +       (void)qos_table;
>>>> +       (void)cos_table;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_with_l3_qos(odp_pktio_t pktio_in,
>>>> +                       size_t num_qos,
>>>> +                       uint8_t qos_table[],
>>>> +                       odp_cos_t cos_table[],
>>>> +                       bool l3_preference)
>>>> +{
>>>> +       (void)pktio_in;
>>>> +       (void)num_qos;
>>>> +       (void)qos_table;
>>>> +       (void)cos_table;
>>>> +       (void)l3_preference;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +odp_cos_flow_set_t
>>>> +odp_cos_class_flow_signature(odp_cos_t cos_id,
>>>> +                            odp_cos_flow_set_t req_data_set)
>>>> +{
>>>> +       (void)cos_id;
>>>> +       (void)req_data_set;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +odp_cos_flow_set_t
>>>> +odp_cos_port_flow_signature(odp_pktio_t pktio_in,
>>>> +                           odp_cos_flow_set_t req_data_set)
>>>> +{
>>>> +       (void)pktio_in;
>>>> +       (void)req_data_set;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +odp_pmr_t odp_pmr_create_match(odp_pmr_term_e term,
>>>> +                              const void *val,
>>>> +                              const void *mask,
>>>> +                              size_t val_sz)
>>>> +{
>>>> +       (void)term;
>>>> +       (void)val;
>>>> +       (void)mask;
>>>> +       (void)val_sz;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +odp_pmr_t odp_pmr_create_range(odp_pmr_term_e term,
>>>> +                              const void *val1,
>>>> +                              const void *val2,
>>>> +                              size_t val_sz)
>>>> +{
>>>> +       (void)term;
>>>> +       (void)val1;
>>>> +       (void)val2;
>>>> +       (void)val_sz;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +int odp_pmr_destroy(odp_pmr_t pmr_id)
>>>> +{
>>>> +       (void)pmr_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pktio_pmr_cos(odp_pmr_t pmr_id,
>>>> +                     odp_pktio_t src_pktio,
>>>> +                     odp_cos_t dst_cos)
>>>> +{
>>>> +       (void)pmr_id;
>>>> +       (void)src_pktio;
>>>> +       (void)dst_cos;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_cos_pmr_cos(odp_pmr_t pmr_id, odp_cos_t src_cos, odp_cos_t
>>>> dst_cos)
>>>> +{
>>>> +       (void)pmr_id;
>>>> +       (void)src_cos;
>>>> +       (void)dst_cos;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +signed long odp_pmr_match_count(odp_pmr_t pmr_id)
>>>> +{
>>>> +       (void)pmr_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +unsigned long long odp_pmr_terms_cap(void)
>>>> +{
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +unsigned odp_pmr_terms_avail(void)
>>>> +{
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pmr_match_set_create(int num_terms, odp_pmr_match_t *terms,
>>>> +                            odp_pmr_set_t *pmr_set_id)
>>>> +{
>>>> +       (void)num_terms;
>>>> +       (void)terms;
>>>> +       (void)pmr_set_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pmr_match_set_destroy(odp_pmr_set_t pmr_set_id)
>>>> +{
>>>> +       (void)pmr_set_id;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> +
>>>> +int odp_pktio_pmr_match_set_cos(odp_pmr_t pmr_id, odp_pktio_t
>>>> src_pktio,
>>>> +                               odp_cos_t dst_cos)
>>>> +{
>>>> +       (void)pmr_id;
>>>> +       (void)src_pktio;
>>>> +       (void)dst_cos;
>>>> +       ODP_ERR("%s function is yet to be implemented", __func__);
>>>> +       return 0;
>>>> +}
>>>> --
>>>> 2.0.1.472.g6f92e5f
>>>>
>>>>
>>>>
>>>> _______________________________________________
>>>> lng-odp mailing list
>>>> lng-odp@lists.linaro.org
>>>> http://lists.linaro.org/mailman/listinfo/lng-odp
>>>>
>>>>
>>>
>>>
>>> --
>>> *Mike Holmes*
>>> Linaro  Sr Technical Manager
>>> LNG - ODP
>>>
>>
>>
>
>
> --
> *Mike Holmes*
> Linaro  Sr Technical Manager
> LNG - ODP
>
_______________________________________________
lng-odp mailing list
lng-odp@lists.linaro.org
http://lists.linaro.org/mailman/listinfo/lng-odp

Reply via email to