1 /*- 2 * Copyright (c) 2016 Andrey V. Elsukov <ae@FreeBSD.org> 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 9 * 1. Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * 2. Redistributions in binary form must reproduce the above copyright 12 * notice, this list of conditions and the following disclaimer in the 13 * documentation and/or other materials provided with the distribution. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 17 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 18 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 19 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 20 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 21 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 22 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 23 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 24 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 25 */ 26 27 #ifndef _NETIPSEC_IPSEC_SUPPORT_H_ 28 #define _NETIPSEC_IPSEC_SUPPORT_H_ 29 30 #ifdef _KERNEL 31 #if defined(IPSEC) || defined(IPSEC_SUPPORT) 32 struct mbuf; 33 struct inpcb; 34 struct tcphdr; 35 struct sockopt; 36 struct sockaddr; 37 struct ipsec_support; 38 struct tcpmd5_support; 39 struct icmp; 40 struct ip6ctlparam; 41 42 typedef union { 43 struct icmp *icmp; 44 struct ip6ctlparam *ip6cp; 45 } ipsec_ctlinput_param_t __attribute__((__transparent_union__)); 46 47 size_t ipsec_hdrsiz_inpcb(struct inpcb *); 48 int ipsec_init_pcbpolicy(struct inpcb *); 49 int ipsec_delete_pcbpolicy(struct inpcb *); 50 int ipsec_copy_pcbpolicy(struct inpcb *, struct inpcb *); 51 52 #if defined(INET) || defined(INET6) 53 int udp_ipsec_input(struct mbuf *, int, int); 54 int udp_ipsec_pcbctl(struct inpcb *, struct sockopt *); 55 #endif 56 #ifdef INET 57 int ipsec4_in_reject(const struct mbuf *, struct inpcb *); 58 int ipsec4_input(struct mbuf *, int, int); 59 int ipsec4_forward(struct mbuf *); 60 int ipsec4_pcbctl(struct inpcb *, struct sockopt *); 61 int ipsec4_output(struct mbuf *, struct inpcb *); 62 int ipsec4_capability(struct mbuf *, u_int); 63 int ipsec4_ctlinput(ipsec_ctlinput_param_t); 64 #endif /* INET */ 65 66 #ifdef INET6 67 int ipsec6_input(struct mbuf *, int, int); 68 int ipsec6_in_reject(const struct mbuf *, struct inpcb *); 69 int ipsec6_forward(struct mbuf *); 70 int ipsec6_pcbctl(struct inpcb *, struct sockopt *); 71 int ipsec6_output(struct mbuf *, struct inpcb *); 72 int ipsec6_capability(struct mbuf *, u_int); 73 int ipsec6_ctlinput(ipsec_ctlinput_param_t); 74 #endif /* INET6 */ 75 76 struct ipsec_methods { 77 int (*input)(struct mbuf *, int, int); 78 int (*check_policy)(const struct mbuf *, struct inpcb *); 79 int (*forward)(struct mbuf *); 80 int (*output)(struct mbuf *, struct inpcb *); 81 int (*pcbctl)(struct inpcb *, struct sockopt *); 82 size_t (*hdrsize)(struct inpcb *); 83 int (*capability)(struct mbuf *, u_int); 84 int (*ctlinput)(ipsec_ctlinput_param_t); 85 86 int (*udp_input)(struct mbuf *, int, int); 87 int (*udp_pcbctl)(struct inpcb *, struct sockopt *); 88 }; 89 #define IPSEC_CAP_OPERABLE 1 90 #define IPSEC_CAP_BYPASS_FILTER 2 91 92 struct tcpmd5_methods { 93 int (*input)(struct mbuf *, struct tcphdr *, u_char *); 94 int (*output)(struct mbuf *, struct tcphdr *, u_char *); 95 int (*pcbctl)(struct inpcb *, struct sockopt *); 96 }; 97 98 #define IPSEC_MODULE_ENABLED 0x0001 99 #define IPSEC_ENABLED(proto) \ 100 ((proto ## _ipsec_support)->enabled & IPSEC_MODULE_ENABLED) 101 #define TCPMD5_ENABLED() IPSEC_ENABLED(tcp) 102 103 #ifdef TCP_SIGNATURE 104 /* TCP-MD5 build in the kernel */ 105 struct tcpmd5_support { 106 const u_int enabled; 107 const struct tcpmd5_methods * const methods; 108 }; 109 extern const struct tcpmd5_support * const tcp_ipsec_support; 110 111 #define TCPMD5_INPUT(m, ...) \ 112 (*tcp_ipsec_support->methods->input)(m, __VA_ARGS__) 113 #define TCPMD5_OUTPUT(m, ...) \ 114 (*tcp_ipsec_support->methods->output)(m, __VA_ARGS__) 115 #define TCPMD5_PCBCTL(inp, sopt) \ 116 (*tcp_ipsec_support->methods->pcbctl)(inp, sopt) 117 #elif defined(IPSEC_SUPPORT) 118 /* TCP-MD5 build as module */ 119 struct tcpmd5_support { 120 volatile u_int enabled; 121 const struct tcpmd5_methods * volatile methods; 122 }; 123 extern struct tcpmd5_support * const tcp_ipsec_support; 124 125 void tcpmd5_support_enable(const struct tcpmd5_methods * const); 126 void tcpmd5_support_disable(void); 127 128 int tcpmd5_kmod_pcbctl(struct tcpmd5_support * const, struct inpcb *, 129 struct sockopt *); 130 int tcpmd5_kmod_input(struct tcpmd5_support * const, struct mbuf *, 131 struct tcphdr *, u_char *); 132 int tcpmd5_kmod_output(struct tcpmd5_support * const, struct mbuf *, 133 struct tcphdr *, u_char *); 134 #define TCPMD5_INPUT(m, ...) \ 135 tcpmd5_kmod_input(tcp_ipsec_support, m, __VA_ARGS__) 136 #define TCPMD5_OUTPUT(m, ...) \ 137 tcpmd5_kmod_output(tcp_ipsec_support, m, __VA_ARGS__) 138 #define TCPMD5_PCBCTL(inp, sopt) \ 139 tcpmd5_kmod_pcbctl(tcp_ipsec_support, inp, sopt) 140 #endif 141 142 #endif /* IPSEC || IPSEC_SUPPORT */ 143 144 #if defined(IPSEC) 145 struct ipsec_support { 146 const u_int enabled; 147 const struct ipsec_methods * const methods; 148 }; 149 extern const struct ipsec_support * const ipv4_ipsec_support; 150 extern const struct ipsec_support * const ipv6_ipsec_support; 151 152 #define IPSEC_INPUT(proto, m, ...) \ 153 (*(proto ## _ipsec_support)->methods->input)(m, __VA_ARGS__) 154 #define IPSEC_CHECK_POLICY(proto, m, ...) \ 155 (*(proto ## _ipsec_support)->methods->check_policy)(m, __VA_ARGS__) 156 #define IPSEC_FORWARD(proto, m) \ 157 (*(proto ## _ipsec_support)->methods->forward)(m) 158 #define IPSEC_OUTPUT(proto, m, ...) \ 159 (*(proto ## _ipsec_support)->methods->output)(m, __VA_ARGS__) 160 #define IPSEC_PCBCTL(proto, inp, sopt) \ 161 (*(proto ## _ipsec_support)->methods->pcbctl)(inp, sopt) 162 #define IPSEC_CAPS(proto, m, ...) \ 163 (*(proto ## _ipsec_support)->methods->capability)(m, __VA_ARGS__) 164 #define IPSEC_HDRSIZE(proto, inp) \ 165 (*(proto ## _ipsec_support)->methods->hdrsize)(inp) 166 #define IPSEC_CTLINPUT(proto, param) \ 167 (*(proto ## _ipsec_support)->methods->ctlinput)(param) 168 169 #define UDPENCAP_INPUT(proto, m, ...) \ 170 (*(proto ## _ipsec_support)->methods->udp_input)(m, __VA_ARGS__) 171 #define UDPENCAP_PCBCTL(proto, inp, sopt) \ 172 (*(proto ## _ipsec_support)->methods->udp_pcbctl)(inp, sopt) 173 174 #elif defined(IPSEC_SUPPORT) 175 struct ipsec_support { 176 volatile u_int enabled; 177 const struct ipsec_methods * volatile methods; 178 }; 179 extern struct ipsec_support * const ipv4_ipsec_support; 180 extern struct ipsec_support * const ipv6_ipsec_support; 181 182 void ipsec_support_enable(struct ipsec_support * const, 183 const struct ipsec_methods * const); 184 void ipsec_support_disable(struct ipsec_support * const); 185 186 int ipsec_kmod_input(struct ipsec_support * const, struct mbuf *, int, int); 187 int ipsec_kmod_check_policy(struct ipsec_support * const, struct mbuf *, 188 struct inpcb *); 189 int ipsec_kmod_forward(struct ipsec_support * const, struct mbuf *); 190 int ipsec_kmod_output(struct ipsec_support * const, struct mbuf *, 191 struct inpcb *); 192 int ipsec_kmod_pcbctl(struct ipsec_support * const, struct inpcb *, 193 struct sockopt *); 194 int ipsec_kmod_capability(struct ipsec_support * const, struct mbuf *, u_int); 195 size_t ipsec_kmod_hdrsize(struct ipsec_support * const, struct inpcb *); 196 int ipsec_kmod_ctlinput(struct ipsec_support *, ipsec_ctlinput_param_t); 197 int ipsec_kmod_udp_input(struct ipsec_support * const, struct mbuf *, int, int); 198 int ipsec_kmod_udp_pcbctl(struct ipsec_support * const, struct inpcb *, 199 struct sockopt *); 200 201 #define UDPENCAP_INPUT(proto, m, ...) \ 202 ipsec_kmod_udp_input(proto ## _ipsec_support, m, __VA_ARGS__) 203 #define UDPENCAP_PCBCTL(proto, inp, sopt) \ 204 ipsec_kmod_udp_pcbctl(proto ## _ipsec_support, inp, sopt) 205 206 #define IPSEC_INPUT(proto, ...) \ 207 ipsec_kmod_input(proto ## _ipsec_support, __VA_ARGS__) 208 #define IPSEC_CHECK_POLICY(proto, ...) \ 209 ipsec_kmod_check_policy(proto ## _ipsec_support, __VA_ARGS__) 210 #define IPSEC_FORWARD(proto, ...) \ 211 ipsec_kmod_forward(proto ## _ipsec_support, __VA_ARGS__) 212 #define IPSEC_OUTPUT(proto, ...) \ 213 ipsec_kmod_output(proto ## _ipsec_support, __VA_ARGS__) 214 #define IPSEC_PCBCTL(proto, ...) \ 215 ipsec_kmod_pcbctl(proto ## _ipsec_support, __VA_ARGS__) 216 #define IPSEC_CAPS(proto, ...) \ 217 ipsec_kmod_capability(proto ## _ipsec_support, __VA_ARGS__) 218 #define IPSEC_HDRSIZE(proto, ...) \ 219 ipsec_kmod_hdrsize(proto ## _ipsec_support, __VA_ARGS__) 220 #define IPSEC_CTLINPUT(proto, ...) \ 221 ipsec_kmod_ctlinput(proto ## _ipsec_support, __VA_ARGS__) 222 #endif /* IPSEC_SUPPORT */ 223 #endif /* _KERNEL */ 224 #endif /* _NETIPSEC_IPSEC_SUPPORT_H_ */ 225