xref: /src/crypto/openssl/include/internal/bio_tfo.h (revision f25b8c9fb4f58cf61adb47d7570abe7caa6d385d)
1 /*
2  * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the Apache License 2.0 (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9 
10 /*
11  * Contains definitions for simplifying the use of TCP Fast Open
12  * (RFC7413) in OpenSSL socket BIOs.
13  */
14 
15 /* If a supported OS is added here, update test/bio_tfo_test.c */
16 #if defined(TCP_FASTOPEN) && !defined(OPENSSL_NO_TFO)
17 
18 #if defined(OPENSSL_SYS_MACOSX) || defined(__FreeBSD__)
19 #include <sys/sysctl.h>
20 #endif
21 
22 /*
23  * OSSL_TFO_SYSCTL is used to determine if TFO is supported by
24  * this kernel, and if supported, if it is enabled. This is more of
25  * a problem on FreeBSD 10.3 ~ 11.4, where TCP_FASTOPEN was defined,
26  * but not enabled by default in the kernel, and only for the server.
27  * Linux does not have sysctlbyname(), and the closest equivalent
28  * is to go into the /proc filesystem, but I'm not sure it's
29  * worthwhile.
30  *
31  * On MacOS and Linux:
32  * These operating systems use a single parameter to control TFO.
33  * The OSSL_TFO_CLIENT_FLAG and OSSL_TFO_SERVER_FLAGS are used to
34  * determine if TFO is enabled for the client and server respectively.
35  *
36  * OSSL_TFO_CLIENT_FLAG = 1 = client TFO enabled
37  * OSSL_TFO_SERVER_FLAG = 2 = server TFO enabled
38  *
39  * Such that:
40  * 0 = TFO disabled
41  * 3 = server and client TFO enabled
42  *
43  * macOS 10.14 and later support TFO.
44  * Linux kernel 3.6 added support for client TFO.
45  * Linux kernel 3.7 added support for server TFO.
46  * Linux kernel 3.13 enabled TFO by default.
47  * Linux kernel 4.11 added the TCP_FASTOPEN_CONNECT option.
48  *
49  * On FreeBSD:
50  * FreeBSD 10.3 ~ 11.4 uses a single sysctl for server enable.
51  * FreeBSD 12.0 and later uses separate sysctls for server and
52  * client enable.
53  *
54  * Some options are purposely NOT defined per-platform
55  *
56  * OSSL_TFO_SYSCTL
57  *     Defined as a sysctlbyname() option to determine if
58  *     TFO is enabled in the kernel (macOS, FreeBSD)
59  *
60  * OSSL_TFO_SERVER_SOCKOPT
61  *     Defined to indicate the socket option used to enable
62  *     TFO on a server socket (all)
63  *
64  * OSSL_TFO_SERVER_SOCKOPT_VALUE
65  *     Value to be used with OSSL_TFO_SERVER_SOCKOPT
66  *
67  * OSSL_TFO_CONNECTX
68  *     Use the connectx() function to make a client connection
69  *     (macOS)
70  *
71  * OSSL_TFO_CLIENT_SOCKOPT
72  *     Defined to indicate the socket option used to enable
73  *     TFO on a client socket (FreeBSD, Linux 4.14 and later)
74  *
75  * OSSL_TFO_SENDTO
76  *     Defined to indicate the sendto() message type to
77  *     be used to initiate a TFO connection (FreeBSD,
78  *     Linux pre-4.14)
79  *
80  * OSSL_TFO_DO_NOT_CONNECT
81  *     Defined to skip calling connect() when creating a
82  *     client socket (macOS, FreeBSD, Linux pre-4.14)
83  */
84 
85 #if defined(OPENSSL_SYS_WINDOWS)
86 /*
87  * NO WINDOWS SUPPORT
88  *
89  * But this is what would be used on the server:
90  *
91  * define OSSL_TFO_SERVER_SOCKOPT       TCP_FASTOPEN
92  * define OSSL_TFO_SERVER_SOCKOPT_VALUE 1
93  *
94  * Still have to figure out client support
95  */
96 #undef TCP_FASTOPEN
97 #endif
98 
99 /* NO VMS SUPPORT */
100 #if defined(OPENSSL_SYS_VMS)
101 #undef TCP_FASTOPEN
102 #endif
103 
104 #if defined(OPENSSL_SYS_MACOSX)
105 #define OSSL_TFO_SYSCTL "net.inet.tcp.fastopen"
106 #define OSSL_TFO_SERVER_SOCKOPT TCP_FASTOPEN
107 #define OSSL_TFO_SERVER_SOCKOPT_VALUE 1
108 #define OSSL_TFO_CONNECTX 1
109 #define OSSL_TFO_DO_NOT_CONNECT 1
110 #define OSSL_TFO_CLIENT_FLAG 1
111 #define OSSL_TFO_SERVER_FLAG 2
112 #endif
113 
114 #if defined(__FreeBSD__)
115 #if defined(TCP_FASTOPEN_PSK_LEN)
116 /* As of 12.0 these are the SYSCTLs */
117 #define OSSL_TFO_SYSCTL_SERVER "net.inet.tcp.fastopen.server_enable"
118 #define OSSL_TFO_SYSCTL_CLIENT "net.inet.tcp.fastopen.client_enable"
119 #define OSSL_TFO_SERVER_SOCKOPT TCP_FASTOPEN
120 #define OSSL_TFO_SERVER_SOCKOPT_VALUE MAX_LISTEN
121 #define OSSL_TFO_CLIENT_SOCKOPT TCP_FASTOPEN
122 #define OSSL_TFO_DO_NOT_CONNECT 1
123 #define OSSL_TFO_SENDTO 0
124 /* These are the same because the sysctl are client/server-specific */
125 #define OSSL_TFO_CLIENT_FLAG 1
126 #define OSSL_TFO_SERVER_FLAG 1
127 #else
128 /* 10.3 through 11.4 SYSCTL - ONLY SERVER SUPPORT */
129 #define OSSL_TFO_SYSCTL "net.inet.tcp.fastopen.enabled"
130 #define OSSL_TFO_SERVER_SOCKOPT TCP_FASTOPEN
131 #define OSSL_TFO_SERVER_SOCKOPT_VALUE MAX_LISTEN
132 #define OSSL_TFO_SERVER_FLAG 1
133 #endif
134 #endif
135 
136 #if defined(OPENSSL_SYS_LINUX)
137 /* OSSL_TFO_PROC not used, but of interest */
138 #define OSSL_TFO_PROC "/proc/sys/net/ipv4/tcp_fastopen"
139 #define OSSL_TFO_SERVER_SOCKOPT TCP_FASTOPEN
140 #define OSSL_TFO_SERVER_SOCKOPT_VALUE MAX_LISTEN
141 #if defined(TCP_FASTOPEN_CONNECT)
142 #define OSSL_TFO_CLIENT_SOCKOPT TCP_FASTOPEN_CONNECT
143 #else
144 #define OSSL_TFO_SENDTO MSG_FASTOPEN
145 #define OSSL_TFO_DO_NOT_CONNECT 1
146 #endif
147 #define OSSL_TFO_CLIENT_FLAG 1
148 #define OSSL_TFO_SERVER_FLAG 2
149 #endif
150 
151 #endif
152