Where Online Learning is simpler!
The C and C++ Include Header Files
cat -n /usr/include/c++/15/experimental/bits/net.h
1 // Networking implementation details -*- C++ -*- 2 3 // Copyright (C) 2015-2025 Free Software Foundation, Inc. 4 // 5 // This file is part of the GNU ISO C++ Library. This library is free 6 // software; you can redistribute it and/or modify it under the 7 // terms of the GNU General Public License as published by the 8 // Free Software Foundation; either version 3, or (at your option) 9 // any later version. 10 11 // This library is distributed in the hope that it will be useful, 12 // but WITHOUT ANY WARRANTY; without even the implied warranty of 13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 // GNU General Public License for more details. 15 16 // Under Section 7 of GPL version 3, you are granted additional 17 // permissions described in the GCC Runtime Library Exception, version 18 // 3.1, as published by the Free Software Foundation. 19 20 // You should have received a copy of the GNU General Public License and 21 // a copy of the GCC Runtime Library Exception along with this program; 22 // see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 23 // <http://www.gnu.org/licenses/>. 24 25 /** @file experimental/bits/net.h 26 * This is an internal header file, included by other library headers. 27 * Do not attempt to use it directly. @headername{experimental/net} 28 */ 29 30 #ifndef _GLIBCXX_EXPERIMENTAL_NET_H 31 #define _GLIBCXX_EXPERIMENTAL_NET_H 1 32 33 #ifdef _GLIBCXX_SYSHDR 34 #pragma GCC system_header 35 #endif 36 37 #if __cplusplus >= 201402L 38 39 #include <type_traits> 40 #include <system_error> 41 #include <experimental/netfwd> 42 43 #if __cplusplus > 201703L 44 # include <concepts> 45 #endif 46 47 namespace std _GLIBCXX_VISIBILITY(default) 48 { 49 _GLIBCXX_BEGIN_NAMESPACE_VERSION 50 namespace experimental 51 { 52 namespace net 53 { 54 inline namespace v1 55 { 56 57 /** @addtogroup networking-ts 58 * @{ 59 */ 60 61 template<typename _CompletionToken, typename _Signature, typename> 62 class async_result; 63 64 /// @cond undocumented 65 66 // A type denoted by DEDUCED in the TS. 67 template<typename _CompletionToken, typename _Signature> 68 using __deduced_t = typename 69 async_result<decay_t<_CompletionToken>, _Signature, void>::return_type; 70 71 // Trait to check for construction from const/non-const lvalue/rvalue. 72 template<typename _Tp> 73 using __is_value_constructible = typename __and_< 74 is_copy_constructible<_Tp>, is_move_constructible<_Tp>, 75 is_constructible<_Tp, _Tp&>, is_constructible<_Tp, const _Tp&&> 76 >::type; 77 78 struct __throw_on_error 79 { 80 explicit 81 __throw_on_error(const char* __msg) : _M_msg(__msg) { } 82 83 ~__throw_on_error() noexcept(false) 84 { 85 if (_M_ec) 86 _GLIBCXX_THROW_OR_ABORT(system_error(_M_ec, _M_msg)); 87 } 88 89 __throw_on_error(const __throw_on_error&) = delete; 90 __throw_on_error& operator=(const __throw_on_error&) = delete; 91 92 operator error_code&() noexcept { return _M_ec; } 93 94 const char* _M_msg; 95 error_code _M_ec; 96 }; 97 98 /// @endcond 99 100 // Base class for types meeting both GettableSocketOption and 101 // SettableSocketOption requirements. 102 // The bool parameter allows __sockopt_base<bool> to have a 103 // __sockopt_base<int, B> base class (so that its _M_value is an int) 104 // but to have that be a distinct type from __sockopt_base<int>. 105 template<typename _Tp, bool = true> 106 struct __sockopt_base 107 { 108 __sockopt_base() = default; 109 110 explicit 111 __sockopt_base(_Tp __val) noexcept(noexcept(_Tp(std::declval<_Tp&>()))) 112 : _M_value(__val) 113 { } 114 115 template<typename _Protocol> 116 void* 117 data(const _Protocol&) noexcept 118 { return std::addressof(_M_value); } 119 120 template<typename _Protocol> 121 const void* 122 data(const _Protocol&) const noexcept 123 { return std::addressof(_M_value); } 124 125 template<typename _Protocol> 126 size_t 127 size(const _Protocol&) const noexcept 128 { return sizeof(_M_value); } 129 130 template<typename _Protocol> 131 void 132 resize(const _Protocol&, size_t __s) 133 { 134 if (__s != sizeof(_M_value)) 135 __throw_length_error("invalid value for socket option resize"); 136 } 137 138 protected: 139 _Tp _M_value { }; 140 }; 141 142 // Base class for types meeting BooleanSocketOption requirements. 143 template<> 144 struct __sockopt_base<bool> : __sockopt_base<int, false> 145 { 146 __sockopt_base() = default; 147 148 explicit 149 __sockopt_base(bool __val) noexcept 150 : __sockopt_base<int, false>(__val) 151 { } 152 153 bool value() const noexcept { return this->_M_value; } 154 explicit operator bool() const noexcept { return value(); } 155 bool operator!() const noexcept { return !value(); } 156 }; 157 158 // Base class for types meeting IntegerSocketOption requirements. 159 template<> 160 struct __sockopt_base<int> : __sockopt_base<int, false> 161 { 162 using __sockopt_base<int, false>::__sockopt_base; 163 164 int value() const noexcept { return this->_M_value; } 165 }; 166 167 template<typename _Derived, typename _Tp = int> 168 struct __sockopt_crtp : __sockopt_base<_Tp> 169 { 170 using __sockopt_base<_Tp>::__sockopt_base; 171 172 _Derived& 173 operator=(_Tp __value) noexcept(noexcept(__value = __value)) 174 { 175 __sockopt_base<_Tp>::_M_value = __value; 176 return static_cast<_Derived&>(*this); 177 } 178 179 template<typename _Protocol> 180 int 181 level(const _Protocol&) const noexcept 182 { return _Derived::_S_level; } 183 184 template<typename _Protocol> 185 int 186 name(const _Protocol&) const noexcept 187 { return _Derived::_S_name; } 188 }; 189 190 namespace __detail 191 { 192 #if __cpp_lib_concepts 193 template<typename _Tp> 194 concept __protocol_like 195 = copyable<_Tp> && requires { typename _Tp::endpoint; }; 196 197 // Endpoint requirements for non-extensible implementations. 198 template<typename _Tp> 199 concept __endpoint_base = semiregular<_Tp> 200 && requires { typename _Tp::protocol_type; } 201 && __protocol_like<typename _Tp::protocol_type> 202 && requires(const _Tp __a) { 203 { __a.protocol() } -> same_as<typename _Tp::protocol_type>; 204 }; 205 206 // Endpoint requirements for extensible implementations. 207 template<typename _Tp> 208 concept __endpoint = __endpoint_base<_Tp> 209 && requires (const _Tp& __a, _Tp& __b, size_t __s) 210 { 211 { __a.data() } -> same_as<const void*>; 212 { __b.data() } -> same_as<void*>; 213 { __b.size() } -> same_as<size_t>; 214 __b.resize(__s); 215 { __a.capacity() } -> same_as<size_t>; 216 }; 217 218 // Protocol requirements for non-extensible implementations. 219 template<typename _Tp> 220 concept __protocol_base = __protocol_like<_Tp> 221 && __endpoint_base<typename _Tp::endpoint> 222 && same_as<typename _Tp::endpoint::protocol_type, _Tp>; 223 224 // Protocol requirements for extensible implementations. 225 template<typename _Tp> 226 concept __protocol = __protocol_base<_Tp> 227 && __endpoint<typename _Tp::endpoint> 228 && requires (const _Tp __a) { 229 { __a.family() } -> same_as<int>; 230 { __a.type() } -> same_as<int>; 231 { __a.protocol() } -> same_as<int>; 232 }; 233 234 template<typename _Tp> 235 concept __acceptable_protocol = __protocol<_Tp> 236 && requires { typename _Tp::socket; } 237 && move_constructible<typename _Tp::socket> 238 && derived_from<typename _Tp::socket, basic_socket<_Tp>>; 239 240 template<typename _Tp> 241 concept __inet_protocol = __acceptable_protocol<_Tp> 242 && equality_comparable<_Tp> && requires { 243 { _Tp::v4() } -> same_as<_Tp>; 244 { _Tp::v6() } -> same_as<_Tp>; 245 typename _Tp::resolver; 246 } 247 && same_as<typename _Tp::resolver, ip::basic_resolver<_Tp>>; 248 249 #else 250 // Check Endpoint requirements for extensible implementations 251 template<typename _Tp, typename = void> 252 struct __is_endpoint : false_type 253 { }; 254 255 template<typename _Tp> 256 auto 257 __endpoint_reqs(const _Tp* __a = nullptr, _Tp* __b = nullptr) 258 -> enable_if_t<__and_< 259 is_default_constructible<_Tp>, __is_value_constructible<_Tp>, 260 is_same<decltype(__a->protocol()), typename _Tp::protocol_type>, 261 is_same<decltype(__a->data()), const void*>, 262 is_same<decltype(__b->data()), void*>, 263 is_same<decltype(__a->size()), size_t>, 264 is_same<decltype(__a->capacity()), size_t> 265 >::value, 266 __void_t< typename _Tp::protocol_type::endpoint, 267 decltype(__b->resize(std::declval<size_t>())) >>; 268 269 template<typename _Tp> 270 struct __is_endpoint<_Tp, decltype(__detail::__endpoint_reqs<_Tp>())> 271 : true_type 272 { }; 273 274 // Check Protocol requirements for extensible implementations. 275 template<typename _Tp, typename = void> 276 struct __is_protocol 277 : false_type { }; 278 279 template<typename _Tp> 280 auto 281 __protocol_reqs(const _Tp* __a = nullptr) 282 -> enable_if_t<__and_< 283 is_copy_constructible<_Tp>, is_copy_assignable<_Tp>, 284 __is_endpoint<typename _Tp::endpoint>, 285 is_same<decltype(__a->family()), int>, 286 is_same<decltype(__a->type()), int>, 287 is_same<decltype(__a->protocol()), int> 288 >::value>; 289 290 template<typename _Tp> 291 struct __is_protocol<_Tp, decltype(__detail::__protocol_reqs<_Tp>())> 292 : true_type 293 { }; 294 295 // Check AcceptableProtocol requirements 296 template<typename _Tp, typename = void> 297 struct __is_acceptable_protocol 298 : false_type { }; 299 300 template<typename _Tp> 301 struct __is_acceptable_protocol<_Tp, __void_t<typename _Tp::socket>> 302 : __and_<__is_protocol<_Tp>, is_move_constructible<typename _Tp::socket>, 303 is_convertible<typename _Tp::socket*, basic_socket<_Tp>*>>::type 304 { }; 305 306 // Check InternetProtocol requirements 307 template<typename _Tp, typename = void> 308 struct __is_inet_protocol 309 : false_type { }; 310 311 template<typename _Tp> 312 auto 313 __inet_proto_reqs(const _Tp* __a = nullptr) 314 -> enable_if_t<__and_< 315 __is_acceptable_protocol<_Tp>, 316 is_same<typename _Tp::resolver, ip::basic_resolver<_Tp>>, 317 is_same<decltype(_Tp::v4()), _Tp>, 318 is_same<decltype(_Tp::v6()), _Tp>, 319 is_convertible<decltype(*__a == *__a), bool>, 320 is_convertible<decltype(*__a != *__a), bool> 321 >::value>; 322 323 template<typename _Tp> 324 struct __is_inet_protocol<_Tp, decltype(__inet_proto_reqs<_Tp>())> 325 : true_type { }; 326 327 // Variable templates for requirements (with same names as concepts above). 328 329 template<typename _Tp> 330 constexpr bool __endpoint = __is_endpoint<_Tp>::value; 331 template<typename _Tp> 332 constexpr bool __protocol = __is_protocol<_Tp>::value; 333 template<typename _Tp> 334 constexpr bool __acceptable_protocol = __is_acceptable_protocol<_Tp>::value; 335 #endif 336 } // namespace __detail 337 338 /// @} 339 340 } // namespace v1 341 } // namespace net 342 } // namespace experimental 343 _GLIBCXX_END_NAMESPACE_VERSION 344 } // namespace std 345 346 #endif // C++14 347 348 #endif // _GLIBCXX_EXPERIMENTAL_NET_H