/* * Copyright (c) 2015 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ /* Copyright (c) 2006 Eliot Dresselhaus Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include /** * @file * @brief String Handling routines, including a performant * implementation of many c-11 "safe" string functions. */ /* Exchanges source and destination. */ void clib_memswap (void *_a, void *_b, uword bytes) { uword pa = pointer_to_uword (_a); uword pb = pointer_to_uword (_b); #define _(TYPE) \ if (0 == ((pa | pb) & (sizeof (TYPE) - 1))) \ { \ TYPE * a = uword_to_pointer (pa, TYPE *); \ TYPE * b = uword_to_pointer (pb, TYPE *); \ \ while (bytes >= 2*sizeof (TYPE)) \ { \ TYPE a0, a1, b0, b1; \ bytes -= 2*sizeof (TYPE); \ a += 2; \ b += 2; \ a0 = a[-2]; a1 = a[-1]; \ b0 = b[-2]; b1 = b[-1]; \ a[-2] = b0; a[-1] = b1; \ b[-2] = a0; b[-1] = a1; \ } \ pa = pointer_to_uword (a); \ pb = pointer_to_uword (b); \ } if (BITS (uword) == BITS (u64)) _(u64); _(u32); _(u16); _(u8); #undef _ ASSERT (bytes < 2); if (bytes) { u8 *a = uword_to_pointer (pa, u8 *); u8 *b = uword_to_pointer (pb, u8 *); u8 a0 = a[0], b0 = b[0]; a[0] = b0; b[0] = a0; } } __clib_export void clib_c11_violation (const char *s) { _clib_error (CLIB_ERROR_WARNING, (char *) __FUNCTION__, 0, (char *) s); } /** * @brief copy src to dest, at most n bytes, up to dmax * * ISO/IEC 9899:2017(C11), Porgramming languages -- C * Annex K; Bounds-checking interfaces * * @param *dest pointer to memory to copy to * @param dmax maximum length of resulting dest * @param *src pointer to memory to copy from * @param n maximum number of characters to copy from src * * @constraints No null pointers * n shall not be greater than dmax * no memory overlap between src and dest * * @return EOK success * EINVAL runtime constraint error * */ __clib_export errno_t memcpy_s (void *__restrict__ dest, rsize_t dmax, const void *__restrict__ src, rsize_t n) { return memcpy_s_inline (dest, dmax, src, n); } /** * @brief set n bytes starting at s to the specified c value * * ISO/IEC 9899:2017(C11), Porgramming languages -- C * Annex K; Bounds-checking interfaces * * @param *s pointer to memory to set the c value * @param smax maximum length of resulting s * @param c byte value * @param n maximum number of characters to set in s * * @constraints No null pointers * n shall not be greater than smax * * @return EOK success * EINVAL runtime constraint error * */ __clib_export errno_t memset_s (void *s, rsize_t smax, int c, rsize_t n) { return memset_s_inline (s, smax, c, n); } /** * @brief compare memory until they differ, and their difference is returned in * diff * * ISO/IEC 9899:2017(C11), Porgramming languages -- C * Annex K; Bounds-checking interfaces * * @param *s1 pointer to memory to compare against * @param s1max maximum length of s1 * @param *s2 pointer to memory to compare with s1 * @param s2max length of s2 * @param *diff pointer to the diff which is an integer greater than, equal to, * or less than zero according to s1 is greater than, equal to, * or less than s2. * * @constraints No null pointers * s1max and s2max shall not be zero * s2max shall not be greater than s1max * * @return EOK success * diff when the return code is EOK * >0 s1 greater s2 * 0 s1 == s2 * <0 s1 < s2 * EINVAL runtime constraint error * */ __clib_export errno_t memcmp_s (const void *s1, rsize_t s1max, const void *s2, rsize_t s2max, int *diff) { return memcmp_s_inline (s1, s1max, s2, s2max, diff); } /** * @brief compare string s2 to string s1, and their difference is returned in * indicator * * ISO/IEC 9899:2017(C11), Porgramming languages -- C * Annex K; Bounds-checking interfaces * * @param *s1 pointer to string to compare against * @param s1max maximum length of s1, excluding null * @param *s2 pointer to string to compare with s1 * @param *indicator pointer to the comparison result, which is an integer * greater than, equal to, or less than zero according to * s1 is greater than, equal to, or less than s2. * * @constraints No null pointers * s1max shall not be zero * s1 shall be null terminated * n shall not be greater than the smaller of s1max and strlen * of s1 * * @return EOK success * indicator when the return code is EOK * >0 s1 greater s2 * 0 s1 == s2 * <0 s1 < s2 * EINVAL runtime constraint error * */ __clib_export errno_t strcmp_s (const char *s1, rsize_t s1max, const char *s2, int *indicator) { return strcmp_s_inline (s1, s1max, s2, indicator); } /** * @brief compare string s2 to string s1, no more than n characters, and their * difference is returned in indicator * * ISO/IEC 9899:2017(C11), Porgramming languages -- C * Annex K; Bounds-checking interfaces * * @param *s1 pointer to string to compare against * @param s1max maximum length of s1, excluding null * @param *s2 pointer to string to compare with s1 * @param n maximum num
/*
 *------------------------------------------------------------------
 * Copyright (c) 2017 Cisco and/or its affiliates.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at:
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *------------------------------------------------------------------
 */

#ifndef __IGMP_PKT_H__
#define __IGMP_PKT_H__

#include <igmp/igmp.h>

typedef struct igmp_pkt_build_t_
{
  u32 *buffers;
  u32 sw_if_index;
  u32 n_avail;
  u32 n_bytes;
} igmp_pkt_build_t;

typedef struct igmp_pkt_build_report_t_
{
  igmp_pkt_build_t base;
  u32 n_groups;
  u16 n_srcs;
} igmp_pkt_build_report_t;

extern void igmp_pkt_build_report_init (igmp_pkt_build_report_t * br,
					u32 sw_if_index);

extern void igmp_pkt_report_v3_add_report (igmp_pkt_build_report_t * br,
					   const ip46_address_t * grp,
					   const ip46_address_t * srcs,
					   igmp_membership_group_v3_type_t
					   type);

extern void igmp_pkt_report_v3_add_group (igmp_pkt_build_report_t *