OpenVPN
proto.h
Go to the documentation of this file.
1/*
2 * OpenVPN -- An application to securely tunnel IP networks
3 * over a single TCP/UDP port, with support for SSL/TLS-based
4 * session authentication and key exchange,
5 * packet encryption, packet authentication, and
6 * packet compression.
7 *
8 * Copyright (C) 2002-2024 OpenVPN Inc <sales@openvpn.net>
9 *
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License version 2
12 * as published by the Free Software Foundation.
13 *
14 * This program is distributed in the hope that it will be useful,
15 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 * GNU General Public License for more details.
18 *
19 * You should have received a copy of the GNU General Public License along
20 * with this program; if not, write to the Free Software Foundation, Inc.,
21 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
22 */
23
24#ifndef PROTO_H
25#define PROTO_H
26
27#include "common.h"
28#include "buffer.h"
29
30#pragma pack(1)
31
32/*
33 * Tunnel types
34 */
35#define DEV_TYPE_UNDEF 0
36#define DEV_TYPE_TUN 2 /* point-to-point IP tunnel */
37#define DEV_TYPE_TAP 3 /* ethernet (802.3) tunnel */
38
39/* TUN topologies */
40
41#define TOP_UNDEF 0
42#define TOP_NET30 1
43#define TOP_P2P 2
44#define TOP_SUBNET 3
45
46/*
47 * IP and Ethernet protocol structs. For portability,
48 * OpenVPN needs its own definitions of these structs, and
49 * names have been adjusted to avoid collisions with
50 * native structs.
51 */
52
53#define OPENVPN_ETH_ALEN 6 /* ethernet address length */
55{
56 uint8_t dest[OPENVPN_ETH_ALEN]; /* destination ethernet addr */
57 uint8_t source[OPENVPN_ETH_ALEN]; /* source ethernet addr */
58
59#define OPENVPN_ETH_P_IPV4 0x0800 /* IPv4 protocol */
60#define OPENVPN_ETH_P_IPV6 0x86DD /* IPv6 protocol */
61#define OPENVPN_ETH_P_ARP 0x0806 /* ARP protocol */
62#define OPENVPN_ETH_P_8021Q 0x8100 /* 802.1Q protocol */
63 uint16_t proto; /* packet type ID field */
64};
65
67{
68 uint8_t dest[OPENVPN_ETH_ALEN]; /* destination ethernet addr */
69 uint8_t source[OPENVPN_ETH_ALEN]; /* source ethernet addr */
70
71 uint16_t tpid; /* 802.1Q Tag Protocol Identifier */
72#define OPENVPN_8021Q_MASK_PCP htons(0xE000) /* mask PCP out of pcp_cfi_vid */
73#define OPENVPN_8021Q_MASK_CFI htons(0x1000) /* mask CFI out of pcp_cfi_vid */
74#define OPENVPN_8021Q_MASK_VID htons(0x0FFF) /* mask VID out of pcp_cfi_vid */
75 uint16_t pcp_cfi_vid; /* bit fields, see IEEE 802.1Q */
76 uint16_t proto; /* contained packet type ID field */
77};
78
79/*
80 * Size difference between a regular Ethernet II header and an Ethernet II
81 * header with additional IEEE 802.1Q tagging.
82 */
83#define SIZE_ETH_TO_8021Q_HDR (sizeof(struct openvpn_8021qhdr) \
84 - sizeof(struct openvpn_ethhdr))
85
89#define OPENVPN_IN6_ARE_ADDR_EQUAL(a, b) \
90 (memcmp(a, b, sizeof(struct in6_addr)) == 0)
91
93#define OPENVPN_IPH_GET_VER(v) (((v) >> 4) & 0x0F)
94#define OPENVPN_IPH_GET_LEN(v) (((v) & 0x0F) << 2)
95 uint8_t version_len;
96
97 uint8_t tos;
98 uint16_t tot_len;
99 uint16_t id;
100
101#define OPENVPN_IP_OFFMASK 0x1fff
102 uint16_t frag_off;
103
104 uint8_t ttl;
105
106#define OPENVPN_IPPROTO_IGMP 2 /* IGMP protocol */
107#define OPENVPN_IPPROTO_TCP 6 /* TCP protocol */
108#define OPENVPN_IPPROTO_UDP 17 /* UDP protocol */
109#define OPENVPN_IPPROTO_ICMPV6 58 /* ICMPV6 protocol */
110 uint8_t protocol;
111
112 uint16_t check;
113 uint32_t saddr;
114 uint32_t daddr;
115 /*The options start here. */
116};
117
118/*
119 * IPv6 header
120 */
123 uint8_t flow_lbl[3];
124 uint16_t payload_len;
125 uint8_t nexthdr;
126 uint8_t hop_limit;
127
128 struct in6_addr saddr;
129 struct in6_addr daddr;
130};
131
132/*
133 * ICMPv6 header
134 */
136#define OPENVPN_ICMP6_DESTINATION_UNREACHABLE 1
137#define OPENVPN_ND_ROUTER_SOLICIT 133
138#define OPENVPN_ND_ROUTER_ADVERT 134
139#define OPENVPN_ND_NEIGHBOR_SOLICIT 135
140#define OPENVPN_ND_NEIGHBOR_ADVERT 136
141#define OPENVPN_ND_INVERSE_SOLICIT 141
142#define OPENVPN_ND_INVERSE_ADVERT 142
143 uint8_t icmp6_type;
144#define OPENVPN_ICMP6_DU_NOROUTE 0
145#define OPENVPN_ICMP6_DU_COMMUNICATION_PROHIBTED 1
146 uint8_t icmp6_code;
147 uint16_t icmp6_cksum;
148 uint8_t icmp6_dataun[4];
149};
150
151/*
152 * UDP header
153 */
160
161/*
162 * TCP header, per RFC 793.
163 */
165 uint16_t source; /* source port */
166 uint16_t dest; /* destination port */
167 uint32_t seq; /* sequence number */
168 uint32_t ack_seq; /* acknowledgement number */
169
170#define OPENVPN_TCPH_GET_DOFF(d) (((d) & 0xF0) >> 2)
171 uint8_t doff_res;
172
173#define OPENVPN_TCPH_FIN_MASK (1<<0)
174#define OPENVPN_TCPH_SYN_MASK (1<<1)
175#define OPENVPN_TCPH_RST_MASK (1<<2)
176#define OPENVPN_TCPH_PSH_MASK (1<<3)
177#define OPENVPN_TCPH_ACK_MASK (1<<4)
178#define OPENVPN_TCPH_URG_MASK (1<<5)
179#define OPENVPN_TCPH_ECE_MASK (1<<6)
180#define OPENVPN_TCPH_CWR_MASK (1<<7)
181 uint8_t flags;
182
183 uint16_t window;
184 uint16_t check;
185 uint16_t urg_ptr;
186};
187
188#define OPENVPN_TCPOPT_EOL 0
189#define OPENVPN_TCPOPT_NOP 1
190#define OPENVPN_TCPOPT_MAXSEG 2
191#define OPENVPN_TCPOLEN_MAXSEG 4
192
195 union {
196 struct openvpn_tcphdr tcp;
197 struct openvpn_udphdr udp;
198 } u;
199};
200
201#pragma pack()
202
203/*
204 * The following macro is used to update an
205 * internet checksum. "acc" is a 32-bit
206 * accumulation of all the changes to the
207 * checksum (adding in old 16-bit words and
208 * subtracting out new words), and "cksum"
209 * is the checksum value to be updated.
210 */
211#define ADJUST_CHECKSUM(acc, cksum) { \
212 int _acc = acc; \
213 _acc += (cksum); \
214 if (_acc < 0) { \
215 _acc = -_acc; \
216 _acc = (_acc >> 16) + (_acc & 0xffff); \
217 _acc += _acc >> 16; \
218 (cksum) = (uint16_t) ~_acc; \
219 } else { \
220 _acc = (_acc >> 16) + (_acc & 0xffff); \
221 _acc += _acc >> 16; \
222 (cksum) = (uint16_t) _acc; \
223 } \
224}
225
226#define ADD_CHECKSUM_32(acc, u32) { \
227 acc += (u32) & 0xffff; \
228 acc += (u32) >> 16; \
229}
230
231#define SUB_CHECKSUM_32(acc, u32) { \
232 acc -= (u32) & 0xffff; \
233 acc -= (u32) >> 16; \
234}
235
236/*
237 * This returns an ip protocol version of packet inside tun
238 * and offset of IP header (via parameter).
239 */
240static inline int
242{
243 int ip_ver = -1;
244
245 /* for tun get ip version from ip header */
247 {
248 *ip_hdr_offset = 0;
249 if (likely(BLEN(buf) >= (int) sizeof(struct openvpn_iphdr)))
250 {
252 }
253 }
254 else if (tunnel_type == DEV_TYPE_TAP)
255 {
256 *ip_hdr_offset = (int)(sizeof(struct openvpn_ethhdr));
257 /* for tap get ip version from eth header */
258 if (likely(BLEN(buf) >= *ip_hdr_offset))
259 {
260 const struct openvpn_ethhdr *eh = (const struct openvpn_ethhdr *) BPTR(buf);
261 uint16_t proto = ntohs(eh->proto);
263 {
264 ip_ver = 6;
265 }
266 else if (proto == OPENVPN_ETH_P_IPV4)
267 {
268 ip_ver = 4;
269 }
270 }
271 }
272
273 return ip_ver;
274}
275
276/*
277 * If raw tunnel packet is IPv4 or IPv6, return true and increment
278 * buffer offset to start of IP header.
279 */
280bool is_ipv4(int tunnel_type, struct buffer *buf);
281
282bool is_ipv6(int tunnel_type, struct buffer *buf);
283
297uint16_t
298ip_checksum(const sa_family_t af, const uint8_t *payload, const int len_payload,
299 const uint8_t *src_addr, const uint8_t *dest_addr, const int proto);
300
301#ifdef PACKET_TRUNCATION_CHECK
302void ipv4_packet_size_verify(const uint8_t *data,
303 const int size,
304 const int tunnel_type,
305 const char
306 *prefix,
307 counter_type *errors);
308
309#endif
310
311#define OPENVPN_8021Q_MIN_VID 1
312#define OPENVPN_8021Q_MAX_VID 4094
313
314#endif /* ifndef PROTO_H */
#define BPTR(buf)
Definition buffer.h:124
#define BLEN(buf)
Definition buffer.h:127
uint64_t counter_type
Definition common.h:30
static int get_tun_ip_ver(int tunnel_type, struct buffer *buf, int *ip_hdr_offset)
Definition proto.h:241
#define DEV_TYPE_TAP
Definition proto.h:37
bool is_ipv4(int tunnel_type, struct buffer *buf)
Definition proto.c:111
bool is_ipv6(int tunnel_type, struct buffer *buf)
Definition proto.c:116
#define OPENVPN_ETH_ALEN
Definition proto.h:53
#define OPENVPN_ETH_P_IPV6
Definition proto.h:60
#define DEV_TYPE_TUN
Definition proto.h:36
#define OPENVPN_ETH_P_IPV4
Definition proto.h:59
uint16_t ip_checksum(const sa_family_t af, const uint8_t *payload, const int len_payload, const uint8_t *src_addr, const uint8_t *dest_addr, const int proto)
Calculates an IP or IPv6 checksum with a pseudo header as required by TCP, UDP and ICMPv6.
Definition proto.c:123
#define OPENVPN_IPH_GET_VER(v)
Definition proto.h:93
Wrapper structure for dynamically allocated memory.
Definition buffer.h:61
union ip_tcp_udp_hdr::@18 u
struct openvpn_iphdr ip
Definition proto.h:194
uint16_t tpid
Definition proto.h:71
uint8_t source[OPENVPN_ETH_ALEN]
Definition proto.h:69
uint16_t pcp_cfi_vid
Definition proto.h:75
uint16_t proto
Definition proto.h:76
uint8_t dest[OPENVPN_ETH_ALEN]
Definition proto.h:68
uint8_t dest[OPENVPN_ETH_ALEN]
Definition proto.h:56
uint16_t proto
Definition proto.h:63
uint8_t source[OPENVPN_ETH_ALEN]
Definition proto.h:57
uint8_t icmp6_type
Definition proto.h:143
uint16_t icmp6_cksum
Definition proto.h:147
uint8_t icmp6_code
Definition proto.h:146
uint8_t icmp6_dataun[4]
Definition proto.h:148
uint32_t saddr
Definition proto.h:113
uint16_t frag_off
Definition proto.h:102
uint32_t daddr
Definition proto.h:114
uint16_t id
Definition proto.h:99
uint8_t tos
Definition proto.h:97
uint8_t protocol
Definition proto.h:110
uint16_t tot_len
Definition proto.h:98
uint16_t check
Definition proto.h:112
uint8_t ttl
Definition proto.h:104
uint8_t version_len
Definition proto.h:95
uint8_t version_prio
Definition proto.h:122
uint8_t hop_limit
Definition proto.h:126
struct in6_addr saddr
Definition proto.h:128
struct in6_addr daddr
Definition proto.h:129
uint8_t flow_lbl[3]
Definition proto.h:123
uint8_t nexthdr
Definition proto.h:125
uint16_t payload_len
Definition proto.h:124
uint16_t source
Definition proto.h:165
uint16_t window
Definition proto.h:183
uint8_t doff_res
Definition proto.h:171
uint16_t check
Definition proto.h:184
uint8_t flags
Definition proto.h:181
uint32_t ack_seq
Definition proto.h:168
uint32_t seq
Definition proto.h:167
uint16_t urg_ptr
Definition proto.h:185
uint16_t dest
Definition proto.h:166
uint16_t check
Definition proto.h:158
uint16_t source
Definition proto.h:155
uint16_t dest
Definition proto.h:156
uint16_t len
Definition proto.h:157
#define likely(x)
Definition syshead.h:35
unsigned short sa_family_t
Definition syshead.h:395