2016-11-11 23:13:24 +01:00
|
|
|
/** @file
|
|
|
|
* @brief IPv6 and IPv4 definitions
|
|
|
|
*
|
|
|
|
* Generic IPv6 and IPv4 address definitions.
|
|
|
|
*/
|
|
|
|
|
2015-04-23 10:20:42 +02:00
|
|
|
/*
|
2016-04-29 14:52:09 +02:00
|
|
|
* Copyright (c) 2016 Intel Corporation
|
2015-04-23 10:20:42 +02:00
|
|
|
*
|
2017-01-19 02:01:01 +01:00
|
|
|
* SPDX-License-Identifier: Apache-2.0
|
2015-04-23 10:20:42 +02:00
|
|
|
*/
|
|
|
|
|
2018-09-14 19:43:44 +02:00
|
|
|
#ifndef ZEPHYR_INCLUDE_NET_NET_IP_H_
|
|
|
|
#define ZEPHYR_INCLUDE_NET_NET_IP_H_
|
2016-11-11 23:13:24 +01:00
|
|
|
|
2017-01-06 14:10:06 +01:00
|
|
|
/**
|
|
|
|
* @brief IPv4/IPv6 primitives and helpers
|
|
|
|
* @defgroup ip_4_6 IPv4/IPv6 primitives and helpers
|
2017-11-17 17:43:53 +01:00
|
|
|
* @ingroup networking
|
2017-01-06 14:10:06 +01:00
|
|
|
* @{
|
|
|
|
*/
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
#include <string.h>
|
Introduce new sized integer typedefs
This is a start to move away from the C99 {u}int{8,16,32,64}_t types to
Zephyr defined u{8,16,32,64}_t and s{8,16,32,64}_t. This allows Zephyr
to define the sized types in a consistent manor across all the
architectures we support and not conflict with what various compilers
and libc might do with regards to the C99 types.
We introduce <zephyr/types.h> as part of this and have it include
<stdint.h> for now until we transition all the code away from the C99
types.
We go with u{8,16,32,64}_t and s{8,16,32,64}_t as there are some
existing variables defined u8 & u16 as well as to be consistent with
Zephyr naming conventions.
Jira: ZEP-2051
Change-Id: I451fed0623b029d65866622e478225dfab2c0ca8
Signed-off-by: Kumar Gala <kumar.gala@linaro.org>
2017-04-19 17:32:08 +02:00
|
|
|
#include <zephyr/types.h>
|
2016-11-11 23:13:24 +01:00
|
|
|
#include <stdbool.h>
|
2018-04-27 21:13:23 +02:00
|
|
|
#include <misc/util.h>
|
2016-11-11 23:13:24 +01:00
|
|
|
#include <misc/byteorder.h>
|
|
|
|
#include <toolchain.h>
|
|
|
|
|
|
|
|
#include <net/net_linkaddr.h>
|
|
|
|
|
|
|
|
#ifdef __cplusplus
|
|
|
|
extern "C" {
|
|
|
|
#endif
|
|
|
|
|
2019-02-01 17:21:32 +01:00
|
|
|
/** @cond INTERNAL_HIDDEN */
|
2018-01-19 11:24:33 +01:00
|
|
|
/* Specifying VLAN tag here in order to avoid circular dependencies */
|
|
|
|
#define NET_VLAN_TAG_UNSPEC 0x0fff
|
2019-02-01 17:21:32 +01:00
|
|
|
/** @endcond */
|
2018-01-19 11:24:33 +01:00
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/** Protocol families */
|
2018-11-23 13:37:28 +01:00
|
|
|
#define PF_UNSPEC 0 /* Unspecified. */
|
|
|
|
#define PF_INET 1 /* IP protocol family version 4. */
|
|
|
|
#define PF_INET6 2 /* IP protocol family version 6. */
|
2018-11-09 09:22:26 +01:00
|
|
|
#define PF_PACKET 3 /* Packet family. */
|
2019-01-23 08:08:40 +01:00
|
|
|
#define PF_CAN 4 /* Controller Area Network. */
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
/** Address families. */
|
|
|
|
#define AF_UNSPEC PF_UNSPEC
|
|
|
|
#define AF_INET PF_INET
|
|
|
|
#define AF_INET6 PF_INET6
|
2018-11-09 09:22:26 +01:00
|
|
|
#define AF_PACKET PF_PACKET
|
2019-01-23 08:08:40 +01:00
|
|
|
#define AF_CAN PF_CAN
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
/** Protocol numbers from IANA */
|
|
|
|
enum net_ip_protocol {
|
|
|
|
IPPROTO_ICMP = 1,
|
|
|
|
IPPROTO_TCP = 6,
|
|
|
|
IPPROTO_UDP = 17,
|
|
|
|
IPPROTO_ICMPV6 = 58,
|
|
|
|
};
|
|
|
|
|
2018-07-02 16:14:27 +02:00
|
|
|
/* Protocol numbers for TLS protocols */
|
|
|
|
enum net_ip_protocol_secure {
|
|
|
|
IPPROTO_TLS_1_0 = 256,
|
|
|
|
IPPROTO_TLS_1_1 = 257,
|
|
|
|
IPPROTO_TLS_1_2 = 258,
|
2018-08-06 14:31:07 +02:00
|
|
|
IPPROTO_DTLS_1_0 = 272,
|
|
|
|
IPPROTO_DTLS_1_2 = 273,
|
2018-07-02 16:14:27 +02:00
|
|
|
};
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/** Socket type */
|
|
|
|
enum net_sock_type {
|
2017-04-26 06:49:51 +02:00
|
|
|
SOCK_STREAM = 1,
|
|
|
|
SOCK_DGRAM,
|
2018-11-09 09:22:26 +01:00
|
|
|
SOCK_RAW
|
2016-11-11 23:13:24 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
#define ntohs(x) sys_be16_to_cpu(x)
|
|
|
|
#define ntohl(x) sys_be32_to_cpu(x)
|
2018-01-24 13:33:35 +01:00
|
|
|
#define ntohll(x) sys_be64_to_cpu(x)
|
2016-11-11 23:13:24 +01:00
|
|
|
#define htons(x) sys_cpu_to_be16(x)
|
|
|
|
#define htonl(x) sys_cpu_to_be32(x)
|
2018-01-24 13:33:35 +01:00
|
|
|
#define htonll(x) sys_cpu_to_be64(x)
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
/** IPv6 address structure */
|
|
|
|
struct in6_addr {
|
|
|
|
union {
|
2018-09-27 09:27:42 +02:00
|
|
|
u8_t s6_addr[16];
|
|
|
|
u16_t s6_addr16[8]; /* In big endian */
|
|
|
|
u32_t s6_addr32[4]; /* In big endian */
|
|
|
|
};
|
2016-11-11 23:13:24 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
/** IPv4 address */
|
|
|
|
struct in_addr {
|
|
|
|
union {
|
2018-09-27 09:27:42 +02:00
|
|
|
u8_t s4_addr[4];
|
|
|
|
u16_t s4_addr16[2]; /* In big endian */
|
|
|
|
u32_t s4_addr32[1]; /* In big endian */
|
|
|
|
u32_t s_addr; /* In big endian, for POSIX compatibility. */
|
|
|
|
};
|
2016-11-11 23:13:24 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
typedef unsigned short int sa_family_t;
|
|
|
|
typedef size_t socklen_t;
|
|
|
|
|
|
|
|
/**
|
|
|
|
* Note that the sin_port and sin6_port are in network byte order
|
|
|
|
* in various sockaddr* structs.
|
|
|
|
*/
|
|
|
|
struct sockaddr_in6 {
|
|
|
|
sa_family_t sin6_family; /* AF_INET6 */
|
2017-08-08 13:41:23 +02:00
|
|
|
u16_t sin6_port; /* Port number */
|
2016-11-11 23:13:24 +01:00
|
|
|
struct in6_addr sin6_addr; /* IPv6 address */
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t sin6_scope_id; /* interfaces for a scope */
|
2016-11-11 23:13:24 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
struct sockaddr_in6_ptr {
|
|
|
|
sa_family_t sin6_family; /* AF_INET6 */
|
2017-08-08 13:41:23 +02:00
|
|
|
u16_t sin6_port; /* Port number */
|
2016-11-11 23:13:24 +01:00
|
|
|
struct in6_addr *sin6_addr; /* IPv6 address */
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t sin6_scope_id; /* interfaces for a scope */
|
2016-11-11 23:13:24 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
struct sockaddr_in {
|
|
|
|
sa_family_t sin_family; /* AF_INET */
|
2017-08-08 13:41:23 +02:00
|
|
|
u16_t sin_port; /* Port number */
|
2016-11-11 23:13:24 +01:00
|
|
|
struct in_addr sin_addr; /* IPv4 address */
|
|
|
|
};
|
|
|
|
|
|
|
|
struct sockaddr_in_ptr {
|
|
|
|
sa_family_t sin_family; /* AF_INET */
|
2017-08-08 13:41:23 +02:00
|
|
|
u16_t sin_port; /* Port number */
|
2016-11-11 23:13:24 +01:00
|
|
|
struct in_addr *sin_addr; /* IPv4 address */
|
|
|
|
};
|
|
|
|
|
2018-11-09 09:22:26 +01:00
|
|
|
struct sockaddr_ll {
|
|
|
|
sa_family_t sll_family; /* Always AF_PACKET */
|
|
|
|
u16_t sll_protocol; /* Physical-layer protocol */
|
|
|
|
int sll_ifindex; /* Interface number */
|
|
|
|
u16_t sll_hatype; /* ARP hardware type */
|
|
|
|
u8_t sll_pkttype; /* Packet type */
|
|
|
|
u8_t sll_halen; /* Length of address */
|
|
|
|
u8_t sll_addr[8]; /* Physical-layer address */
|
|
|
|
};
|
|
|
|
|
|
|
|
struct sockaddr_ll_ptr {
|
|
|
|
sa_family_t sll_family; /* Always AF_PACKET */
|
|
|
|
u16_t sll_protocol; /* Physical-layer protocol */
|
|
|
|
int sll_ifindex; /* Interface number */
|
|
|
|
u16_t sll_hatype; /* ARP hardware type */
|
|
|
|
u8_t sll_pkttype; /* Packet type */
|
|
|
|
u8_t sll_halen; /* Length of address */
|
|
|
|
u8_t *sll_addr; /* Physical-layer address */
|
|
|
|
};
|
|
|
|
|
2019-01-23 08:50:08 +01:00
|
|
|
struct sockaddr_can_ptr {
|
|
|
|
sa_family_t can_family;
|
|
|
|
int can_ifindex;
|
|
|
|
};
|
|
|
|
|
2018-11-09 09:22:26 +01:00
|
|
|
/* Packet types. */
|
|
|
|
#define PACKET_HOST 0 /* To us */
|
|
|
|
#define PACKET_BROADCAST 1 /* To all */
|
|
|
|
#define PACKET_MULTICAST 2 /* To group */
|
|
|
|
#define PACKET_OTHERHOST 3 /* To someone else */
|
|
|
|
#define PACKET_OUTGOING 4 /* Originated by us */
|
|
|
|
#define PACKET_LOOPBACK 5
|
|
|
|
#define PACKET_FASTROUTE 6
|
|
|
|
|
|
|
|
/* Note: These macros are defined in a specific order.
|
|
|
|
* The largest sockaddr size is the last one.
|
|
|
|
*/
|
|
|
|
#if defined(CONFIG_NET_IPV4)
|
|
|
|
#undef NET_SOCKADDR_MAX_SIZE
|
|
|
|
#undef NET_SOCKADDR_PTR_MAX_SIZE
|
2016-11-11 23:13:24 +01:00
|
|
|
#define NET_SOCKADDR_MAX_SIZE (sizeof(struct sockaddr_in))
|
|
|
|
#define NET_SOCKADDR_PTR_MAX_SIZE (sizeof(struct sockaddr_in_ptr))
|
2018-11-09 09:22:26 +01:00
|
|
|
#endif
|
|
|
|
|
|
|
|
#if defined(CONFIG_NET_SOCKETS_PACKET)
|
|
|
|
#undef NET_SOCKADDR_MAX_SIZE
|
|
|
|
#undef NET_SOCKADDR_PTR_MAX_SIZE
|
|
|
|
#define NET_SOCKADDR_MAX_SIZE (sizeof(struct sockaddr_ll))
|
|
|
|
#define NET_SOCKADDR_PTR_MAX_SIZE (sizeof(struct sockaddr_ll_ptr))
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#if defined(CONFIG_NET_IPV6)
|
|
|
|
#undef NET_SOCKADDR_MAX_SIZE
|
|
|
|
#undef NET_SOCKADDR_PTR_MAX_SIZE
|
2016-11-11 23:13:24 +01:00
|
|
|
#define NET_SOCKADDR_MAX_SIZE (sizeof(struct sockaddr_in6))
|
|
|
|
#define NET_SOCKADDR_PTR_MAX_SIZE (sizeof(struct sockaddr_in6_ptr))
|
|
|
|
#endif
|
|
|
|
|
2018-11-09 09:22:26 +01:00
|
|
|
#if !defined(CONFIG_NET_IPV4)
|
|
|
|
#if !defined(CONFIG_NET_IPV6)
|
|
|
|
#if !defined(CONFIG_NET_SOCKETS_PACKET)
|
|
|
|
#define NET_SOCKADDR_MAX_SIZE (sizeof(struct sockaddr_in6))
|
|
|
|
#define NET_SOCKADDR_PTR_MAX_SIZE (sizeof(struct sockaddr_in6_ptr))
|
|
|
|
#endif
|
|
|
|
#endif
|
|
|
|
#endif
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
struct sockaddr {
|
2017-08-18 09:03:46 +02:00
|
|
|
sa_family_t sa_family;
|
2016-11-11 23:13:24 +01:00
|
|
|
char data[NET_SOCKADDR_MAX_SIZE - sizeof(sa_family_t)];
|
|
|
|
};
|
|
|
|
|
|
|
|
struct sockaddr_ptr {
|
|
|
|
sa_family_t family;
|
|
|
|
char data[NET_SOCKADDR_PTR_MAX_SIZE - sizeof(sa_family_t)];
|
2017-08-18 08:06:58 +02:00
|
|
|
};
|
|
|
|
|
|
|
|
/* Same as sockaddr in our case */
|
|
|
|
struct sockaddr_storage {
|
|
|
|
sa_family_t ss_family;
|
|
|
|
char data[NET_SOCKADDR_MAX_SIZE - sizeof(sa_family_t)];
|
2016-11-11 23:13:24 +01:00
|
|
|
};
|
|
|
|
|
|
|
|
struct net_addr {
|
|
|
|
sa_family_t family;
|
|
|
|
union {
|
|
|
|
#if defined(CONFIG_NET_IPV6)
|
|
|
|
struct in6_addr in6_addr;
|
|
|
|
#endif
|
|
|
|
#if defined(CONFIG_NET_IPV4)
|
|
|
|
struct in_addr in_addr;
|
|
|
|
#endif
|
|
|
|
};
|
|
|
|
};
|
|
|
|
|
|
|
|
#define IN6ADDR_ANY_INIT { { { 0, 0, 0, 0, 0, 0, 0, 0, 0, \
|
|
|
|
0, 0, 0, 0, 0, 0, 0 } } }
|
|
|
|
#define IN6ADDR_LOOPBACK_INIT { { { 0, 0, 0, 0, 0, 0, 0, \
|
|
|
|
0, 0, 0, 0, 0, 0, 0, 0, 1 } } }
|
|
|
|
|
2017-11-20 08:09:15 +01:00
|
|
|
extern const struct in6_addr in6addr_any;
|
|
|
|
extern const struct in6_addr in6addr_loopback;
|
|
|
|
|
2018-09-07 15:08:29 +02:00
|
|
|
/* Defined by POSIX. INET6_ADDRSTRLEN accounts for mapped IPv4 addresses. */
|
|
|
|
#define INET_ADDRSTRLEN 16
|
2016-11-11 23:13:24 +01:00
|
|
|
#define INET6_ADDRSTRLEN 46
|
2018-09-07 15:08:29 +02:00
|
|
|
|
|
|
|
/* These are for internal usage of the stack */
|
2016-11-11 23:13:24 +01:00
|
|
|
#define NET_IPV6_ADDR_LEN sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx")
|
|
|
|
#define NET_IPV4_ADDR_LEN sizeof("xxx.xxx.xxx.xxx")
|
|
|
|
|
|
|
|
#define INADDR_ANY 0
|
2017-01-20 11:07:21 +01:00
|
|
|
#define INADDR_ANY_INIT { { { INADDR_ANY } } }
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
#define NET_IPV6_MTU 1280
|
2017-11-17 14:32:19 +01:00
|
|
|
#define NET_IPV4_MTU 576
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
/** IPv6 extension headers types */
|
|
|
|
#define NET_IPV6_NEXTHDR_HBHO 0
|
|
|
|
#define NET_IPV6_NEXTHDR_DESTO 60
|
|
|
|
#define NET_IPV6_NEXTHDR_ROUTING 43
|
|
|
|
#define NET_IPV6_NEXTHDR_FRAG 44
|
|
|
|
#define NET_IPV6_NEXTHDR_NONE 59
|
|
|
|
|
2018-02-07 14:00:08 +01:00
|
|
|
/** Network packet priority settings described in IEEE 802.1Q Annex I.1 */
|
|
|
|
enum net_priority {
|
2018-08-03 10:03:11 +02:00
|
|
|
NET_PRIORITY_BK = 1, /* Background (lowest) */
|
|
|
|
NET_PRIORITY_BE = 0, /* Best effort (default) */
|
2018-02-07 14:00:08 +01:00
|
|
|
NET_PRIORITY_EE = 2, /* Excellent effort */
|
|
|
|
NET_PRIORITY_CA = 3, /* Critical applications (highest) */
|
|
|
|
NET_PRIORITY_VI = 4, /* Video, < 100 ms latency and jitter */
|
|
|
|
NET_PRIORITY_VO = 5, /* Voice, < 10 ms latency and jitter */
|
|
|
|
NET_PRIORITY_IC = 6, /* Internetwork control */
|
|
|
|
NET_PRIORITY_NC = 7 /* Network control */
|
2018-08-14 12:18:29 +02:00
|
|
|
} __packed;
|
2018-02-07 14:00:08 +01:00
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/** IPv6/IPv4 network connection tuple */
|
|
|
|
struct net_tuple {
|
|
|
|
/** IPv6/IPv4 remote address */
|
|
|
|
struct net_addr *remote_addr;
|
|
|
|
/** IPv6/IPv4 local address */
|
|
|
|
struct net_addr *local_addr;
|
|
|
|
/** UDP/TCP remote port */
|
2017-04-21 16:27:50 +02:00
|
|
|
u16_t remote_port;
|
2016-11-11 23:13:24 +01:00
|
|
|
/** UDP/TCP local port */
|
2017-04-21 16:27:50 +02:00
|
|
|
u16_t local_port;
|
2016-11-11 23:13:24 +01:00
|
|
|
/** IP protocol */
|
|
|
|
enum net_ip_protocol ip_proto;
|
|
|
|
};
|
|
|
|
|
|
|
|
/** How the network address is assigned to network interface */
|
|
|
|
enum net_addr_type {
|
|
|
|
NET_ADDR_ANY = 0,
|
|
|
|
NET_ADDR_AUTOCONF,
|
|
|
|
NET_ADDR_DHCP,
|
|
|
|
NET_ADDR_MANUAL,
|
2018-01-19 14:44:22 +01:00
|
|
|
NET_ADDR_OVERRIDABLE,
|
2018-08-14 12:18:29 +02:00
|
|
|
} __packed;
|
2016-11-11 23:13:24 +01:00
|
|
|
|
2018-09-05 16:15:02 +02:00
|
|
|
static inline const char *net_addr_type2str(enum net_addr_type type)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
switch (type) {
|
|
|
|
case NET_ADDR_AUTOCONF:
|
|
|
|
return "AUTO";
|
|
|
|
case NET_ADDR_DHCP:
|
|
|
|
return "DHCP";
|
|
|
|
case NET_ADDR_MANUAL:
|
|
|
|
return "MANUAL";
|
2018-01-19 14:44:22 +01:00
|
|
|
case NET_ADDR_OVERRIDABLE:
|
|
|
|
return "OVERRIDE";
|
2016-11-11 23:13:24 +01:00
|
|
|
case NET_ADDR_ANY:
|
|
|
|
default:
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
return "<unknown>";
|
|
|
|
}
|
|
|
|
|
|
|
|
/** What is the current state of the network address */
|
|
|
|
enum net_addr_state {
|
|
|
|
NET_ADDR_ANY_STATE = -1,
|
|
|
|
NET_ADDR_TENTATIVE = 0,
|
|
|
|
NET_ADDR_PREFERRED,
|
|
|
|
NET_ADDR_DEPRECATED,
|
2018-08-14 12:18:29 +02:00
|
|
|
} __packed;
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
struct net_ipv6_hdr {
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t vtc;
|
|
|
|
u8_t tcflow;
|
|
|
|
u16_t flow;
|
2018-08-13 08:57:00 +02:00
|
|
|
u16_t len;
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t nexthdr;
|
|
|
|
u8_t hop_limit;
|
2016-11-11 23:13:24 +01:00
|
|
|
struct in6_addr src;
|
|
|
|
struct in6_addr dst;
|
|
|
|
} __packed;
|
|
|
|
|
2017-03-28 16:43:32 +02:00
|
|
|
struct net_ipv6_frag_hdr {
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t nexthdr;
|
|
|
|
u8_t reserved;
|
|
|
|
u16_t offset;
|
|
|
|
u32_t id;
|
2017-03-28 16:43:32 +02:00
|
|
|
} __packed;
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
struct net_ipv4_hdr {
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t vhl;
|
|
|
|
u8_t tos;
|
2018-08-08 14:22:00 +02:00
|
|
|
u16_t len;
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t id[2];
|
|
|
|
u8_t offset[2];
|
|
|
|
u8_t ttl;
|
|
|
|
u8_t proto;
|
|
|
|
u16_t chksum;
|
2016-11-11 23:13:24 +01:00
|
|
|
struct in_addr src;
|
|
|
|
struct in_addr dst;
|
|
|
|
} __packed;
|
|
|
|
|
|
|
|
struct net_icmp_hdr {
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t type;
|
|
|
|
u8_t code;
|
|
|
|
u16_t chksum;
|
2016-11-11 23:13:24 +01:00
|
|
|
} __packed;
|
|
|
|
|
|
|
|
struct net_udp_hdr {
|
2017-04-21 16:27:50 +02:00
|
|
|
u16_t src_port;
|
|
|
|
u16_t dst_port;
|
|
|
|
u16_t len;
|
|
|
|
u16_t chksum;
|
2016-11-11 23:13:24 +01:00
|
|
|
} __packed;
|
|
|
|
|
|
|
|
struct net_tcp_hdr {
|
2017-04-21 16:27:50 +02:00
|
|
|
u16_t src_port;
|
|
|
|
u16_t dst_port;
|
|
|
|
u8_t seq[4];
|
|
|
|
u8_t ack[4];
|
|
|
|
u8_t offset;
|
|
|
|
u8_t flags;
|
|
|
|
u8_t wnd[2];
|
|
|
|
u16_t chksum;
|
|
|
|
u8_t urg[2];
|
|
|
|
u8_t optdata[0];
|
2016-11-11 23:13:24 +01:00
|
|
|
} __packed;
|
|
|
|
|
2019-01-30 10:07:10 +01:00
|
|
|
/**
|
2019-02-15 22:58:08 +01:00
|
|
|
* This 2 unions are here temporarily, as long as net_context.h will
|
2019-01-30 10:07:10 +01:00
|
|
|
* be still public and not part of the core only.
|
|
|
|
*/
|
|
|
|
union net_ip_header {
|
|
|
|
struct net_ipv4_hdr *ipv4;
|
|
|
|
struct net_ipv6_hdr *ipv6;
|
|
|
|
};
|
|
|
|
|
|
|
|
union net_proto_header {
|
|
|
|
struct net_udp_hdr *udp;
|
|
|
|
struct net_tcp_hdr *tcp;
|
|
|
|
};
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
#define NET_UDPH_LEN 8 /* Size of UDP header */
|
|
|
|
#define NET_TCPH_LEN 20 /* Size of TCP header */
|
|
|
|
#define NET_ICMPH_LEN 4 /* Size of ICMP header */
|
|
|
|
|
|
|
|
#define NET_IPV6H_LEN 40 /* Size of IPv6 header */
|
|
|
|
#define NET_ICMPV6H_LEN NET_ICMPH_LEN /* Size of ICMPv6 header */
|
|
|
|
#define NET_IPV6UDPH_LEN (NET_UDPH_LEN + NET_IPV6H_LEN) /* IPv6 + UDP */
|
|
|
|
#define NET_IPV6TCPH_LEN (NET_TCPH_LEN + NET_IPV6H_LEN) /* IPv6 + TCP */
|
|
|
|
#define NET_IPV6ICMPH_LEN (NET_IPV6H_LEN + NET_ICMPH_LEN) /* ICMPv6 + IPv6 */
|
|
|
|
#define NET_IPV6_FRAGH_LEN 8
|
|
|
|
|
|
|
|
#define NET_IPV4H_LEN 20 /* Size of IPv4 header */
|
|
|
|
#define NET_ICMPV4H_LEN NET_ICMPH_LEN /* Size of ICMPv4 header */
|
|
|
|
#define NET_IPV4UDPH_LEN (NET_UDPH_LEN + NET_IPV4H_LEN) /* IPv4 + UDP */
|
|
|
|
#define NET_IPV4TCPH_LEN (NET_TCPH_LEN + NET_IPV4H_LEN) /* IPv4 + TCP */
|
|
|
|
#define NET_IPV4ICMPH_LEN (NET_IPV4H_LEN + NET_ICMPH_LEN) /* ICMPv4 + IPv4 */
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is a loopback address (::1).
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
*
|
|
|
|
* @return True if address is a loopback address, False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_loopback(struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2017-04-10 16:13:35 +02:00
|
|
|
return UNALIGNED_GET(&addr->s6_addr32[0]) == 0 &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[1]) == 0 &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[2]) == 0 &&
|
|
|
|
ntohl(UNALIGNED_GET(&addr->s6_addr32[3])) == 1;
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is a multicast address.
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
*
|
|
|
|
* @return True if address is multicast address, False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast(const struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
return addr->s6_addr[0] == 0xFF;
|
|
|
|
}
|
|
|
|
|
|
|
|
struct net_if;
|
2018-01-11 15:06:53 +01:00
|
|
|
struct net_if_config;
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
extern struct net_if_addr *net_if_ipv6_addr_lookup(const struct in6_addr *addr,
|
|
|
|
struct net_if **iface);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if IPv6 address is found in one of the network interfaces.
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
*
|
|
|
|
* @return True if address was found, False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_my_addr(struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
return net_if_ipv6_addr_lookup(addr, NULL) != NULL;
|
|
|
|
}
|
|
|
|
|
2017-08-08 13:41:23 +02:00
|
|
|
extern struct net_if_mcast_addr *net_if_ipv6_maddr_lookup(
|
|
|
|
const struct in6_addr *addr, struct net_if **iface);
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if IPv6 multicast address is found in one of the
|
|
|
|
* network interfaces.
|
|
|
|
*
|
|
|
|
* @param maddr Multicast IPv6 address
|
|
|
|
*
|
|
|
|
* @return True if address was found, False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_my_maddr(struct in6_addr *maddr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
return net_if_ipv6_maddr_lookup(maddr, NULL) != NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if two IPv6 addresses are same when compared after prefix mask.
|
|
|
|
*
|
|
|
|
* @param addr1 First IPv6 address.
|
|
|
|
* @param addr2 Second IPv6 address.
|
|
|
|
* @param length Prefix length (max length is 128).
|
|
|
|
*
|
2017-01-18 08:38:20 +01:00
|
|
|
* @return True if IPv6 prefixes are the same, False otherwise.
|
2016-11-11 23:13:24 +01:00
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_prefix(const u8_t *addr1,
|
2017-04-21 16:27:50 +02:00
|
|
|
const u8_t *addr2,
|
|
|
|
u8_t length)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2017-04-21 16:27:50 +02:00
|
|
|
u8_t bits = 128 - length;
|
|
|
|
u8_t bytes = length / 8;
|
|
|
|
u8_t remain = bits % 8;
|
|
|
|
u8_t mask;
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
if (length > 128) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2017-01-18 08:38:20 +01:00
|
|
|
if (memcmp(addr1, addr2, bytes)) {
|
2016-11-11 23:13:24 +01:00
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2017-01-18 08:38:20 +01:00
|
|
|
if (!remain) {
|
|
|
|
/* No remaining bits, the prefixes are the same as first
|
|
|
|
* bytes are the same.
|
|
|
|
*/
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Create a mask that has remaining most significant bits set */
|
|
|
|
mask = ((0xff << (8 - remain)) ^ 0xff) << remain;
|
|
|
|
|
|
|
|
return (addr1[bytes] & mask) == (addr2[bytes] & mask);
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv4 address is a loopback address (127.0.0.0/8).
|
|
|
|
*
|
|
|
|
* @param addr IPv4 address
|
|
|
|
*
|
|
|
|
* @return True if address is a loopback address, False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv4_is_addr_loopback(struct in_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
return addr->s4_addr[0] == 127;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv4 address is unspecified (all bits zero)
|
|
|
|
*
|
|
|
|
* @param addr IPv4 address.
|
|
|
|
*
|
|
|
|
* @return True if the address is unspecified, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv4_is_addr_unspecified(const struct in_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2018-01-15 22:38:30 +01:00
|
|
|
return UNALIGNED_GET(&addr->s_addr) == 0;
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv4 address is a multicast address.
|
|
|
|
*
|
|
|
|
* @param addr IPv4 address
|
|
|
|
*
|
|
|
|
* @return True if address is multicast address, False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv4_is_addr_mcast(const struct in_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2018-01-15 22:38:30 +01:00
|
|
|
return (ntohl(UNALIGNED_GET(&addr->s_addr)) & 0xE0000000) == 0xE0000000;
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
2018-04-27 12:01:33 +02:00
|
|
|
/**
|
|
|
|
* @brief Check if the given IPv4 address is a link local address.
|
|
|
|
*
|
|
|
|
* @param addr A valid pointer on an IPv4 address
|
|
|
|
*
|
|
|
|
* @return True if it is, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv4_is_ll_addr(const struct in_addr *addr)
|
2018-04-27 12:01:33 +02:00
|
|
|
{
|
|
|
|
return (ntohl(UNALIGNED_GET(&addr->s_addr)) & 0xA9FE0000) == 0xA9FE0000;
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/**
|
|
|
|
* @def net_ipaddr_copy
|
|
|
|
* @brief Copy an IPv4 or IPv6 address
|
|
|
|
*
|
|
|
|
* @param dest Destination IP address.
|
|
|
|
* @param src Source IP address.
|
|
|
|
*
|
|
|
|
* @return Destination address.
|
|
|
|
*/
|
|
|
|
#define net_ipaddr_copy(dest, src) \
|
|
|
|
UNALIGNED_PUT(UNALIGNED_GET(src), dest)
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Compare two IPv4 addresses
|
|
|
|
*
|
|
|
|
* @param addr1 Pointer to IPv4 address.
|
|
|
|
* @param addr2 Pointer to IPv4 address.
|
|
|
|
*
|
|
|
|
* @return True if the addresses are the same, false otherwise.
|
|
|
|
*/
|
|
|
|
static inline bool net_ipv4_addr_cmp(const struct in_addr *addr1,
|
|
|
|
const struct in_addr *addr2)
|
|
|
|
{
|
2017-08-21 11:13:36 +02:00
|
|
|
return UNALIGNED_GET(&addr1->s_addr) == UNALIGNED_GET(&addr2->s_addr);
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Compare two IPv6 addresses
|
|
|
|
*
|
|
|
|
* @param addr1 Pointer to IPv6 address.
|
|
|
|
* @param addr2 Pointer to IPv6 address.
|
|
|
|
*
|
|
|
|
* @return True if the addresses are the same, false otherwise.
|
|
|
|
*/
|
|
|
|
static inline bool net_ipv6_addr_cmp(const struct in6_addr *addr1,
|
|
|
|
const struct in6_addr *addr2)
|
|
|
|
{
|
|
|
|
return !memcmp(addr1, addr2, sizeof(struct in6_addr));
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the given IPv6 address is a link local address.
|
|
|
|
*
|
|
|
|
* @param addr A valid pointer on an IPv6 address
|
|
|
|
*
|
|
|
|
* @return True if it is, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_ll_addr(const struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2017-04-10 16:13:35 +02:00
|
|
|
return UNALIGNED_GET(&addr->s6_addr16[0]) == htons(0xFE80);
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Return pointer to any (all bits zeros) IPv6 address.
|
|
|
|
*
|
|
|
|
* @return Any IPv6 address.
|
|
|
|
*/
|
|
|
|
const struct in6_addr *net_ipv6_unspecified_address(void);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Return pointer to any (all bits zeros) IPv4 address.
|
|
|
|
*
|
|
|
|
* @return Any IPv4 address.
|
|
|
|
*/
|
|
|
|
const struct in_addr *net_ipv4_unspecified_address(void);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Return pointer to broadcast (all bits ones) IPv4 address.
|
|
|
|
*
|
|
|
|
* @return Broadcast IPv4 address.
|
|
|
|
*/
|
|
|
|
const struct in_addr *net_ipv4_broadcast_address(void);
|
|
|
|
|
|
|
|
struct net_if;
|
|
|
|
extern bool net_if_ipv4_addr_mask_cmp(struct net_if *iface,
|
2018-10-23 16:43:22 +02:00
|
|
|
const struct in_addr *addr);
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the given address belongs to same subnet that
|
|
|
|
* has been configured for the interface.
|
|
|
|
*
|
|
|
|
* @param iface A valid pointer on an interface
|
2018-10-23 16:43:22 +02:00
|
|
|
* @param addr IPv4 address
|
2016-11-11 23:13:24 +01:00
|
|
|
*
|
|
|
|
* @return True if address is in same subnet, false otherwise.
|
|
|
|
*/
|
|
|
|
static inline bool net_ipv4_addr_mask_cmp(struct net_if *iface,
|
2018-10-23 16:43:22 +02:00
|
|
|
const struct in_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
return net_if_ipv4_addr_mask_cmp(iface, addr);
|
|
|
|
}
|
|
|
|
|
2018-10-23 16:49:32 +02:00
|
|
|
extern bool net_if_ipv4_is_addr_bcast(struct net_if *iface,
|
|
|
|
const struct in_addr *addr);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the given IPv4 address is a broadcast address.
|
|
|
|
*
|
|
|
|
* @param iface Interface to use. Must be a valid pointer to an interface.
|
|
|
|
* @param addr IPv4 address
|
|
|
|
*
|
|
|
|
* @return True if address is a broadcast address, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv4_is_addr_bcast(struct net_if *iface,
|
2018-10-23 16:49:32 +02:00
|
|
|
const struct in_addr *addr)
|
|
|
|
{
|
|
|
|
if (net_ipv4_addr_cmp(addr, net_ipv4_broadcast_address())) {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
return net_if_ipv4_is_addr_bcast(iface, addr);
|
|
|
|
}
|
|
|
|
|
2018-10-24 12:40:03 +02:00
|
|
|
extern struct net_if_addr *net_if_ipv4_addr_lookup(const struct in_addr *addr,
|
|
|
|
struct net_if **iface);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv4 address is assigned to any network interface
|
|
|
|
* in the system.
|
|
|
|
*
|
|
|
|
* @param addr A valid pointer on an IPv4 address
|
|
|
|
*
|
|
|
|
* @return True if IPv4 address is found in one of the network interfaces,
|
|
|
|
* False otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv4_is_my_addr(const struct in_addr *addr)
|
2018-10-24 12:40:03 +02:00
|
|
|
{
|
|
|
|
bool ret;
|
|
|
|
|
|
|
|
ret = net_if_ipv4_addr_lookup(addr, NULL) != NULL;
|
|
|
|
if (!ret) {
|
2018-11-02 15:05:58 +01:00
|
|
|
ret = net_ipv4_is_addr_bcast(NULL, addr);
|
2018-10-24 12:40:03 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
return ret;
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is unspecified (all bits zero)
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
*
|
|
|
|
* @return True if the address is unspecified, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_unspecified(const struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2017-04-10 16:13:35 +02:00
|
|
|
return UNALIGNED_GET(&addr->s6_addr32[0]) == 0 &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[1]) == 0 &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[2]) == 0 &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[3]) == 0;
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is solicited node multicast address
|
|
|
|
* FF02:0:0:0:0:1:FFXX:XXXX defined in RFC 3513
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
*
|
|
|
|
* @return True if the address is solicited node address, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_solicited_node(const struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2017-04-10 16:13:35 +02:00
|
|
|
return UNALIGNED_GET(&addr->s6_addr32[0]) == htonl(0xff020000) &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[1]) == 0x00000000 &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[2]) == htonl(0x00000001) &&
|
|
|
|
((UNALIGNED_GET(&addr->s6_addr32[3]) & htonl(0xff000000)) ==
|
|
|
|
htonl(0xff000000));
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
2018-10-31 10:12:56 +01:00
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is a given scope multicast
|
|
|
|
* address (FFyx::).
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
* @param scope Scope to check
|
|
|
|
*
|
|
|
|
* @return True if the address is in given scope multicast address,
|
|
|
|
* false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast_scope(const struct in6_addr *addr,
|
2018-10-31 10:12:56 +01:00
|
|
|
int scope)
|
|
|
|
{
|
|
|
|
return (addr->s6_addr[0] == 0xff) && (addr->s6_addr[1] == scope);
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is a global multicast address (FFxE::/16).
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
*
|
|
|
|
* @return True if the address is global multicast address, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast_global(const struct in6_addr *addr)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2018-11-02 15:05:58 +01:00
|
|
|
return net_ipv6_is_addr_mcast_scope(addr, 0x0e);
|
2018-10-31 10:12:56 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is a interface scope multicast
|
|
|
|
* address (FFx1::).
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
*
|
|
|
|
* @return True if the address is a interface scope multicast address,
|
|
|
|
* false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast_iface(const struct in6_addr *addr)
|
2018-10-31 10:12:56 +01:00
|
|
|
{
|
2018-11-02 15:05:58 +01:00
|
|
|
return net_ipv6_is_addr_mcast_scope(addr, 0x01);
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
2018-10-31 15:49:12 +01:00
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address is a site scope multicast
|
|
|
|
* address (FFx5::).
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
*
|
|
|
|
* @return True if the address is a site scope multicast address,
|
|
|
|
* false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast_site(const struct in6_addr *addr)
|
2018-10-31 15:49:12 +01:00
|
|
|
{
|
2018-11-02 15:05:58 +01:00
|
|
|
return net_ipv6_is_addr_mcast_scope(addr, 0x05);
|
2018-10-31 15:49:12 +01:00
|
|
|
}
|
|
|
|
|
2018-11-01 08:55:43 +01:00
|
|
|
/**
|
2018-11-02 19:49:04 +01:00
|
|
|
* @brief Check if the IPv6 address is an organization scope multicast
|
2018-11-01 08:55:43 +01:00
|
|
|
* address (FFx8::).
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
*
|
2018-11-02 19:49:04 +01:00
|
|
|
* @return True if the address is an organization scope multicast address,
|
2018-11-01 08:55:43 +01:00
|
|
|
* false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast_org(const struct in6_addr *addr)
|
2018-11-01 08:55:43 +01:00
|
|
|
{
|
2018-11-02 15:05:58 +01:00
|
|
|
return net_ipv6_is_addr_mcast_scope(addr, 0x08);
|
2018-11-01 08:55:43 +01:00
|
|
|
}
|
|
|
|
|
2018-10-31 15:49:12 +01:00
|
|
|
/**
|
|
|
|
* @brief Check if the IPv6 address belongs to certain multicast group
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address.
|
|
|
|
* @param group Group id IPv6 address, the values must be in network
|
|
|
|
* byte order
|
|
|
|
*
|
|
|
|
* @return True if the IPv6 multicast address belongs to given multicast
|
|
|
|
* group, false otherwise.
|
|
|
|
*/
|
2018-11-02 15:05:58 +01:00
|
|
|
static inline bool net_ipv6_is_addr_mcast_group(const struct in6_addr *addr,
|
2018-10-31 15:49:12 +01:00
|
|
|
const struct in6_addr *group)
|
|
|
|
{
|
|
|
|
return UNALIGNED_GET(&addr->s6_addr16[1]) == group->s6_addr16[1] &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr16[2]) == group->s6_addr16[2] &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr16[3]) == group->s6_addr16[3] &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[1]) == group->s6_addr32[1] &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[2]) == group->s6_addr32[1] &&
|
|
|
|
UNALIGNED_GET(&addr->s6_addr32[3]) == group->s6_addr32[3];
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/**
|
|
|
|
* @brief Create solicited node IPv6 multicast address
|
|
|
|
* FF02:0:0:0:0:1:FFXX:XXXX defined in RFC 3513
|
|
|
|
*
|
|
|
|
* @param src IPv6 address.
|
|
|
|
* @param dst IPv6 address.
|
|
|
|
*/
|
2017-04-12 09:34:59 +02:00
|
|
|
static inline
|
|
|
|
void net_ipv6_addr_create_solicited_node(const struct in6_addr *src,
|
|
|
|
struct in6_addr *dst)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
|
|
|
dst->s6_addr[0] = 0xFF;
|
|
|
|
dst->s6_addr[1] = 0x02;
|
2017-04-10 16:13:35 +02:00
|
|
|
UNALIGNED_PUT(0, &dst->s6_addr16[1]);
|
|
|
|
UNALIGNED_PUT(0, &dst->s6_addr16[2]);
|
|
|
|
UNALIGNED_PUT(0, &dst->s6_addr16[3]);
|
|
|
|
UNALIGNED_PUT(0, &dst->s6_addr16[4]);
|
2016-11-11 23:13:24 +01:00
|
|
|
dst->s6_addr[10] = 0;
|
|
|
|
dst->s6_addr[11] = 0x01;
|
|
|
|
dst->s6_addr[12] = 0xFF;
|
|
|
|
dst->s6_addr[13] = src->s6_addr[13];
|
2017-04-10 16:13:35 +02:00
|
|
|
UNALIGNED_PUT(UNALIGNED_GET(&src->s6_addr16[7]), &dst->s6_addr16[7]);
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/** @brief Construct an IPv6 address from eight 16-bit words.
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
* @param addr0 16-bit word which is part of the address
|
|
|
|
* @param addr1 16-bit word which is part of the address
|
|
|
|
* @param addr2 16-bit word which is part of the address
|
|
|
|
* @param addr3 16-bit word which is part of the address
|
|
|
|
* @param addr4 16-bit word which is part of the address
|
|
|
|
* @param addr5 16-bit word which is part of the address
|
|
|
|
* @param addr6 16-bit word which is part of the address
|
|
|
|
* @param addr7 16-bit word which is part of the address
|
|
|
|
*/
|
|
|
|
static inline void net_ipv6_addr_create(struct in6_addr *addr,
|
2017-04-21 16:27:50 +02:00
|
|
|
u16_t addr0, u16_t addr1,
|
|
|
|
u16_t addr2, u16_t addr3,
|
|
|
|
u16_t addr4, u16_t addr5,
|
|
|
|
u16_t addr6, u16_t addr7)
|
2016-11-11 23:13:24 +01:00
|
|
|
{
|
2017-04-10 16:13:35 +02:00
|
|
|
UNALIGNED_PUT(htons(addr0), &addr->s6_addr16[0]);
|
|
|
|
UNALIGNED_PUT(htons(addr1), &addr->s6_addr16[1]);
|
|
|
|
UNALIGNED_PUT(htons(addr2), &addr->s6_addr16[2]);
|
|
|
|
UNALIGNED_PUT(htons(addr3), &addr->s6_addr16[3]);
|
|
|
|
UNALIGNED_PUT(htons(addr4), &addr->s6_addr16[4]);
|
|
|
|
UNALIGNED_PUT(htons(addr5), &addr->s6_addr16[5]);
|
|
|
|
UNALIGNED_PUT(htons(addr6), &addr->s6_addr16[6]);
|
|
|
|
UNALIGNED_PUT(htons(addr7), &addr->s6_addr16[7]);
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Create link local allnodes multicast IPv6 address
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
*/
|
|
|
|
static inline void net_ipv6_addr_create_ll_allnodes_mcast(struct in6_addr *addr)
|
|
|
|
{
|
|
|
|
net_ipv6_addr_create(addr, 0xff02, 0, 0, 0, 0, 0, 0, 0x0001);
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Create IPv6 address interface identifier
|
|
|
|
*
|
|
|
|
* @param addr IPv6 address
|
|
|
|
* @param lladdr Link local address
|
|
|
|
*/
|
|
|
|
static inline void net_ipv6_addr_create_iid(struct in6_addr *addr,
|
|
|
|
struct net_linkaddr *lladdr)
|
|
|
|
{
|
|
|
|
addr->s6_addr[0] = 0xfe;
|
|
|
|
addr->s6_addr[1] = 0x80;
|
2017-04-10 16:13:35 +02:00
|
|
|
UNALIGNED_PUT(0, &addr->s6_addr16[1]);
|
|
|
|
UNALIGNED_PUT(0, &addr->s6_addr32[1]);
|
2016-11-11 23:13:24 +01:00
|
|
|
|
|
|
|
switch (lladdr->len) {
|
|
|
|
case 2:
|
2017-02-15 12:46:35 +01:00
|
|
|
/* The generated IPv6 shall not toggle the
|
|
|
|
* Universal/Local bit. RFC 6282 ch 3.2.2
|
|
|
|
*/
|
|
|
|
if (lladdr->type == NET_LINK_IEEE802154) {
|
2017-04-10 16:13:35 +02:00
|
|
|
UNALIGNED_PUT(0, &addr->s6_addr32[2]);
|
2017-02-15 12:46:35 +01:00
|
|
|
addr->s6_addr[11] = 0xff;
|
|
|
|
addr->s6_addr[12] = 0xfe;
|
|
|
|
addr->s6_addr[13] = 0;
|
|
|
|
addr->s6_addr[14] = lladdr->addr[0];
|
|
|
|
addr->s6_addr[15] = lladdr->addr[1];
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
break;
|
|
|
|
case 6:
|
2017-02-15 12:48:25 +01:00
|
|
|
/* We do not toggle the Universal/Local bit
|
|
|
|
* in Bluetooth. See RFC 7668 ch 3.2.2
|
|
|
|
*/
|
2016-11-11 23:13:24 +01:00
|
|
|
memcpy(&addr->s6_addr[8], lladdr->addr, 3);
|
|
|
|
addr->s6_addr[11] = 0xff;
|
|
|
|
addr->s6_addr[12] = 0xfe;
|
|
|
|
memcpy(&addr->s6_addr[13], lladdr->addr + 3, 3);
|
|
|
|
|
2017-08-09 08:21:11 +02:00
|
|
|
#if defined(CONFIG_NET_L2_BT_ZEP1656)
|
2017-02-15 12:48:25 +01:00
|
|
|
/* Workaround against older Linux kernel BT IPSP code.
|
|
|
|
* This will be removed eventually.
|
|
|
|
*/
|
|
|
|
if (lladdr->type == NET_LINK_BLUETOOTH) {
|
|
|
|
addr->s6_addr[8] ^= 0x02;
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
|
|
|
if (lladdr->type == NET_LINK_ETHERNET) {
|
|
|
|
addr->s6_addr[8] ^= 0x02;
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
2016-11-11 23:13:24 +01:00
|
|
|
case 8:
|
|
|
|
memcpy(&addr->s6_addr[8], lladdr->addr, lladdr->len);
|
|
|
|
addr->s6_addr[8] ^= 0x02;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check if given address is based on link layer address
|
|
|
|
*
|
|
|
|
* @return True if it is, False otherwise
|
|
|
|
*/
|
|
|
|
static inline bool net_ipv6_addr_based_on_ll(const struct in6_addr *addr,
|
|
|
|
const struct net_linkaddr *lladdr)
|
|
|
|
{
|
2017-01-25 13:35:32 +01:00
|
|
|
if (!addr || !lladdr) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
switch (lladdr->len) {
|
|
|
|
case 2:
|
|
|
|
if (!memcmp(&addr->s6_addr[14], lladdr->addr, lladdr->len) &&
|
2017-02-15 12:46:35 +01:00
|
|
|
addr->s6_addr[8] == 0 &&
|
|
|
|
addr->s6_addr[9] == 0 &&
|
|
|
|
addr->s6_addr[10] == 0 &&
|
2016-11-11 23:13:24 +01:00
|
|
|
addr->s6_addr[11] == 0xff &&
|
|
|
|
addr->s6_addr[12] == 0xfe) {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
case 6:
|
2017-02-15 12:48:25 +01:00
|
|
|
if (lladdr->type == NET_LINK_ETHERNET) {
|
|
|
|
if (!memcmp(&addr->s6_addr[9], &lladdr->addr[1], 2) &&
|
|
|
|
!memcmp(&addr->s6_addr[13], &lladdr->addr[3], 3) &&
|
|
|
|
addr->s6_addr[11] == 0xff &&
|
|
|
|
addr->s6_addr[12] == 0xfe &&
|
|
|
|
(addr->s6_addr[8] ^ 0x02) == lladdr->addr[0]) {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
} else if (lladdr->type == NET_LINK_BLUETOOTH) {
|
|
|
|
if (!memcmp(&addr->s6_addr[9], &lladdr->addr[1], 2) &&
|
|
|
|
!memcmp(&addr->s6_addr[13], &lladdr->addr[3], 3) &&
|
|
|
|
addr->s6_addr[11] == 0xff &&
|
|
|
|
addr->s6_addr[12] == 0xfe
|
2017-08-09 08:21:11 +02:00
|
|
|
#if defined(CONFIG_NET_L2_BT_ZEP1656)
|
2017-02-15 12:48:25 +01:00
|
|
|
/* Workaround against older Linux kernel BT IPSP
|
|
|
|
* code. This will be removed eventually.
|
|
|
|
*/
|
|
|
|
&& (addr->s6_addr[8] ^ 0x02) == lladdr->addr[0]
|
|
|
|
#endif
|
|
|
|
) {
|
|
|
|
return true;
|
|
|
|
}
|
2016-11-11 23:13:24 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
case 8:
|
|
|
|
if (!memcmp(&addr->s6_addr[9], &lladdr->addr[1],
|
|
|
|
lladdr->len - 1) &&
|
|
|
|
(addr->s6_addr[8] ^ 0x02) == lladdr->addr[0]) {
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Get sockaddr_in6 from sockaddr. This is a helper so that
|
|
|
|
* the code calling this function can be made shorter.
|
|
|
|
*
|
|
|
|
* @param addr Socket address
|
|
|
|
*
|
|
|
|
* @return Pointer to IPv6 socket address
|
|
|
|
*/
|
|
|
|
static inline struct sockaddr_in6 *net_sin6(const struct sockaddr *addr)
|
|
|
|
{
|
|
|
|
return (struct sockaddr_in6 *)addr;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Get sockaddr_in from sockaddr. This is a helper so that
|
|
|
|
* the code calling this function can be made shorter.
|
|
|
|
*
|
|
|
|
* @param addr Socket address
|
|
|
|
*
|
|
|
|
* @return Pointer to IPv4 socket address
|
|
|
|
*/
|
|
|
|
static inline struct sockaddr_in *net_sin(const struct sockaddr *addr)
|
|
|
|
{
|
|
|
|
return (struct sockaddr_in *)addr;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Get sockaddr_in6_ptr from sockaddr_ptr. This is a helper so that
|
|
|
|
* the code calling this function can be made shorter.
|
|
|
|
*
|
|
|
|
* @param addr Socket address
|
|
|
|
*
|
|
|
|
* @return Pointer to IPv6 socket address
|
|
|
|
*/
|
|
|
|
static inline
|
|
|
|
struct sockaddr_in6_ptr *net_sin6_ptr(const struct sockaddr_ptr *addr)
|
|
|
|
{
|
|
|
|
return (struct sockaddr_in6_ptr *)addr;
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Get sockaddr_in_ptr from sockaddr_ptr. This is a helper so that
|
|
|
|
* the code calling this function can be made shorter.
|
|
|
|
*
|
|
|
|
* @param addr Socket address
|
|
|
|
*
|
|
|
|
* @return Pointer to IPv4 socket address
|
|
|
|
*/
|
|
|
|
static inline
|
|
|
|
struct sockaddr_in_ptr *net_sin_ptr(const struct sockaddr_ptr *addr)
|
|
|
|
{
|
|
|
|
return (struct sockaddr_in_ptr *)addr;
|
|
|
|
}
|
|
|
|
|
2018-11-09 09:22:26 +01:00
|
|
|
/**
|
|
|
|
* @brief Get sockaddr_ll_ptr from sockaddr_ptr. This is a helper so that
|
|
|
|
* the code calling this function can be made shorter.
|
|
|
|
*
|
|
|
|
* @param addr Socket address
|
|
|
|
*
|
|
|
|
* @return Pointer to linklayer socket address
|
|
|
|
*/
|
|
|
|
static inline
|
|
|
|
struct sockaddr_ll_ptr *net_sll_ptr(const struct sockaddr_ptr *addr)
|
|
|
|
{
|
|
|
|
return (struct sockaddr_ll_ptr *)addr;
|
|
|
|
}
|
|
|
|
|
2019-01-23 08:50:08 +01:00
|
|
|
/**
|
|
|
|
* @brief Get sockaddr_can_ptr from sockaddr_ptr. This is a helper so that
|
|
|
|
* the code needing this functionality can be made shorter.
|
|
|
|
*
|
|
|
|
* @param addr Socket address
|
|
|
|
*
|
|
|
|
* @return Pointer to CAN socket address
|
|
|
|
*/
|
|
|
|
static inline
|
|
|
|
struct sockaddr_can_ptr *net_can_ptr(const struct sockaddr_ptr *addr)
|
|
|
|
{
|
|
|
|
return (struct sockaddr_can_ptr *)addr;
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
/**
|
|
|
|
* @brief Convert a string to IP address.
|
|
|
|
*
|
|
|
|
* @param family IP address family (AF_INET or AF_INET6)
|
|
|
|
* @param src IP address in a null terminated string
|
|
|
|
* @param dst Pointer to struct in_addr if family is AF_INET or
|
|
|
|
* pointer to struct in6_addr if family is AF_INET6
|
|
|
|
*
|
|
|
|
* @note This function doesn't do precise error checking,
|
|
|
|
* do not use for untrusted strings.
|
|
|
|
*
|
|
|
|
* @return 0 if ok, < 0 if error
|
|
|
|
*/
|
2017-01-24 22:14:33 +01:00
|
|
|
int net_addr_pton(sa_family_t family, const char *src, void *dst);
|
2016-11-11 23:13:24 +01:00
|
|
|
|
2017-01-30 11:30:13 +01:00
|
|
|
/**
|
|
|
|
* @brief Convert IP address to string form.
|
|
|
|
*
|
|
|
|
* @param family IP address family (AF_INET or AF_INET6)
|
|
|
|
* @param src Pointer to struct in_addr if family is AF_INET or
|
|
|
|
* pointer to struct in6_addr if family is AF_INET6
|
2018-09-06 10:36:03 +02:00
|
|
|
* @param dst Buffer for IP address as a null terminated string
|
2017-01-30 11:30:13 +01:00
|
|
|
* @param size Number of bytes available in the buffer
|
|
|
|
*
|
|
|
|
* @return dst pointer if ok, NULL if error
|
|
|
|
*/
|
|
|
|
char *net_addr_ntop(sa_family_t family, const void *src,
|
|
|
|
char *dst, size_t size);
|
|
|
|
|
2017-08-20 20:55:23 +02:00
|
|
|
/**
|
|
|
|
* @brief Parse a string that contains either IPv4 or IPv6 address
|
|
|
|
* and optional port, and store the information in user supplied
|
|
|
|
* sockaddr struct.
|
|
|
|
*
|
|
|
|
* @details Syntax of the IP address string:
|
|
|
|
* 192.0.2.1:80
|
|
|
|
* 192.0.2.42
|
|
|
|
* [2001:db8::1]:8080
|
|
|
|
* [2001:db8::2]
|
|
|
|
* 2001:db::42
|
|
|
|
* Note that the str_len parameter is used to restrict the amount of
|
|
|
|
* characters that are checked. If the string does not contain port
|
|
|
|
* number, then the port number in sockaddr is not modified.
|
|
|
|
*
|
|
|
|
* @param str String that contains the IP address.
|
|
|
|
* @param str_len Length of the string to be parsed.
|
|
|
|
* @param addr Pointer to user supplied struct sockaddr.
|
|
|
|
*
|
|
|
|
* @return True if parsing could be done, false otherwise.
|
|
|
|
*/
|
|
|
|
bool net_ipaddr_parse(const char *str, size_t str_len,
|
|
|
|
struct sockaddr *addr);
|
|
|
|
|
2017-05-15 12:03:17 +02:00
|
|
|
/**
|
|
|
|
* @brief Compare TCP sequence numbers.
|
|
|
|
*
|
|
|
|
* @details This function compares TCP sequence numbers,
|
|
|
|
* accounting for wraparound effects.
|
|
|
|
*
|
|
|
|
* @param seq1 First sequence number
|
|
|
|
* @param seq2 Seconds sequence number
|
|
|
|
*
|
|
|
|
* @return < 0 if seq1 < seq2, 0 if seq1 == seq2, > 0 if seq > seq2
|
|
|
|
*/
|
|
|
|
static inline s32_t net_tcp_seq_cmp(u32_t seq1, u32_t seq2)
|
|
|
|
{
|
|
|
|
return (s32_t)(seq1 - seq2);
|
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Check that one TCP sequence number is greater.
|
|
|
|
*
|
|
|
|
* @details This is convenience function on top of net_tcp_seq_cmp().
|
|
|
|
*
|
|
|
|
* @param seq1 First sequence number
|
|
|
|
* @param seq2 Seconds sequence number
|
|
|
|
*
|
|
|
|
* @return True if seq > seq2
|
|
|
|
*/
|
|
|
|
static inline bool net_tcp_seq_greater(u32_t seq1, u32_t seq2)
|
|
|
|
{
|
|
|
|
return net_tcp_seq_cmp(seq1, seq2) > 0;
|
|
|
|
}
|
|
|
|
|
2018-02-23 11:22:00 +01:00
|
|
|
/**
|
|
|
|
* @brief Convert a string of hex values to array of bytes.
|
|
|
|
*
|
|
|
|
* @details The syntax of the string is "ab:02:98:fa:42:01"
|
|
|
|
*
|
|
|
|
* @param buf Pointer to memory where the bytes are written.
|
|
|
|
* @param buf_len Length of the memory area.
|
|
|
|
* @param src String of bytes.
|
|
|
|
*
|
|
|
|
* @return 0 if ok, <0 if error
|
|
|
|
*/
|
|
|
|
int net_bytes_from_str(u8_t *buf, int buf_len, const char *src);
|
|
|
|
|
2018-02-07 14:00:08 +01:00
|
|
|
/**
|
|
|
|
* @brief Convert Tx network packet priority to traffic class so we can place
|
|
|
|
* the packet into correct Tx queue.
|
|
|
|
*
|
|
|
|
* @param prio Network priority
|
|
|
|
*
|
|
|
|
* @return Tx traffic class that handles that priority network traffic.
|
|
|
|
*/
|
|
|
|
int net_tx_priority2tc(enum net_priority prio);
|
|
|
|
|
|
|
|
/**
|
|
|
|
* @brief Convert Rx network packet priority to traffic class so we can place
|
|
|
|
* the packet into correct Rx queue.
|
|
|
|
*
|
|
|
|
* @param prio Network priority
|
|
|
|
*
|
|
|
|
* @return Rx traffic class that handles that priority network traffic.
|
|
|
|
*/
|
|
|
|
int net_rx_priority2tc(enum net_priority prio);
|
|
|
|
|
2018-03-08 15:44:15 +01:00
|
|
|
/**
|
|
|
|
* @brief Convert network packet VLAN priority to network packet priority so we
|
|
|
|
* can place the packet into correct queue.
|
|
|
|
*
|
|
|
|
* @param priority VLAN priority
|
|
|
|
*
|
|
|
|
* @return Network priority
|
|
|
|
*/
|
|
|
|
static inline enum net_priority net_vlan2priority(u8_t priority)
|
|
|
|
{
|
2018-04-27 21:13:23 +02:00
|
|
|
/* Map according to IEEE 802.1Q */
|
|
|
|
static const u8_t vlan2priority[] = {
|
|
|
|
NET_PRIORITY_BE,
|
|
|
|
NET_PRIORITY_BK,
|
|
|
|
NET_PRIORITY_EE,
|
|
|
|
NET_PRIORITY_CA,
|
|
|
|
NET_PRIORITY_VI,
|
|
|
|
NET_PRIORITY_VO,
|
|
|
|
NET_PRIORITY_IC,
|
|
|
|
NET_PRIORITY_NC
|
|
|
|
};
|
|
|
|
|
|
|
|
if (priority >= ARRAY_SIZE(vlan2priority)) {
|
|
|
|
/* Use Best Effort as the default priority */
|
|
|
|
return NET_PRIORITY_BE;
|
|
|
|
}
|
|
|
|
|
2018-11-14 14:43:10 +01:00
|
|
|
return (enum net_priority)vlan2priority[priority];
|
2018-03-08 15:44:15 +01:00
|
|
|
}
|
|
|
|
|
2018-06-25 15:25:33 +02:00
|
|
|
/**
|
|
|
|
* @brief Convert network packet priority to network packet VLAN priority.
|
|
|
|
*
|
|
|
|
* @param priority Packet priority
|
|
|
|
*
|
|
|
|
* @return VLAN priority (PCP)
|
|
|
|
*/
|
|
|
|
static inline u8_t net_priority2vlan(enum net_priority priority)
|
|
|
|
{
|
|
|
|
/* The conversion works both ways */
|
|
|
|
return (u8_t)net_vlan2priority(priority);
|
|
|
|
}
|
|
|
|
|
2016-11-11 23:13:24 +01:00
|
|
|
#ifdef __cplusplus
|
|
|
|
}
|
|
|
|
#endif
|
|
|
|
|
2017-01-06 14:10:06 +01:00
|
|
|
/**
|
|
|
|
* @}
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
2018-09-14 19:43:44 +02:00
|
|
|
#endif /* ZEPHYR_INCLUDE_NET_NET_IP_H_ */
|