http_status_str.c (11229B)
1 /* SPDX-License-Identifier: LGPL-2.1-or-later OR (GPL-2.0-or-later WITH eCos-exception-2.0) */ 2 /* 3 This file is part of GNU libmicrohttpd. 4 Copyright (C) 2017-2024 Evgeny Grin (Karlson2k) 5 Copyright (C) 2007, 2011, 2017, 2019 Christian Grothoff 6 7 GNU libmicrohttpd is free software; you can redistribute it and/or 8 modify it under the terms of the GNU Lesser General Public 9 License as published by the Free Software Foundation; either 10 version 2.1 of the License, or (at your option) any later version. 11 12 GNU libmicrohttpd is distributed in the hope that it will be useful, 13 but WITHOUT ANY WARRANTY; without even the implied warranty of 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 Lesser General Public License for more details. 16 17 Alternatively, you can redistribute GNU libmicrohttpd and/or 18 modify it under the terms of the GNU General Public License as 19 published by the Free Software Foundation; either version 2 of 20 the License, or (at your option) any later version, together 21 with the eCos exception, as follows: 22 23 As a special exception, if other files instantiate templates or 24 use macros or inline functions from this file, or you compile this 25 file and link it with other works to produce a work based on this 26 file, this file does not by itself cause the resulting work to be 27 covered by the GNU General Public License. However the source code 28 for this file must still be made available in accordance with 29 section (3) of the GNU General Public License v2. 30 31 This exception does not invalidate any other reasons why a work 32 based on this file might be covered by the GNU General Public 33 License. 34 35 You should have received copies of the GNU Lesser General Public 36 License and the GNU General Public License along with this library; 37 if not, see <https://www.gnu.org/licenses/>. 38 */ 39 /** 40 * @file src/mhd2/http_status_str.c 41 * @brief Tables of the string response phrases 42 * @author Elliot Glaysher 43 * @author Christian Grothoff (minor code clean up) 44 * @author Karlson2k (Evgeny Grin) (massively refactored and updated) 45 */ 46 #include "mhd_sys_options.h" 47 48 #include "http_status_str.h" 49 50 #include "sys_base_types.h" 51 #include "mhd_public_api.h" 52 #include "mhd_str_macros.h" 53 #include "mhd_arr_num_elems.h" 54 55 #define UNUSED_STATUS {0, NULL} 56 57 static const struct MHD_String invalid_hundred[] = { 58 { 0, NULL } 59 }; 60 61 static const struct MHD_String one_hundred[] = { 62 /* 100 */ mhd_MSTR_INIT ("Continue"), /* RFC9110, Section 15.2.1 */ 63 /* 101 */ mhd_MSTR_INIT ("Switching Protocols"), /* RFC9110, Section 15.2.2 */ 64 /* 102 */ mhd_MSTR_INIT ("Processing"), /* RFC2518 */ 65 /* 103 */ mhd_MSTR_INIT ("Early Hints") /* RFC8297 */ 66 }; 67 68 static const struct MHD_String two_hundred[] = { 69 /* 200 */ mhd_MSTR_INIT ("OK"), /* RFC9110, Section 15.3.1 */ 70 /* 201 */ mhd_MSTR_INIT ("Created"), /* RFC9110, Section 15.3.2 */ 71 /* 202 */ mhd_MSTR_INIT ("Accepted"), /* RFC9110, Section 15.3.3 */ 72 /* 203 */ mhd_MSTR_INIT ("Non-Authoritative Information"), /* RFC9110, Section 15.3.4 */ 73 /* 204 */ mhd_MSTR_INIT ("No Content"), /* RFC9110, Section 15.3.5 */ 74 /* 205 */ mhd_MSTR_INIT ("Reset Content"), /* RFC9110, Section 15.3.6 */ 75 /* 206 */ mhd_MSTR_INIT ("Partial Content"), /* RFC9110, Section 15.3.7 */ 76 /* 207 */ mhd_MSTR_INIT ("Multi-Status"), /* RFC4918 */ 77 /* 208 */ mhd_MSTR_INIT ("Already Reported"), /* RFC5842 */ 78 /* 209 */ UNUSED_STATUS, /* Not used */ 79 /* 210 */ UNUSED_STATUS, /* Not used */ 80 /* 211 */ UNUSED_STATUS, /* Not used */ 81 /* 212 */ UNUSED_STATUS, /* Not used */ 82 /* 213 */ UNUSED_STATUS, /* Not used */ 83 /* 214 */ UNUSED_STATUS, /* Not used */ 84 /* 215 */ UNUSED_STATUS, /* Not used */ 85 /* 216 */ UNUSED_STATUS, /* Not used */ 86 /* 217 */ UNUSED_STATUS, /* Not used */ 87 /* 218 */ UNUSED_STATUS, /* Not used */ 88 /* 219 */ UNUSED_STATUS, /* Not used */ 89 /* 220 */ UNUSED_STATUS, /* Not used */ 90 /* 221 */ UNUSED_STATUS, /* Not used */ 91 /* 222 */ UNUSED_STATUS, /* Not used */ 92 /* 223 */ UNUSED_STATUS, /* Not used */ 93 /* 224 */ UNUSED_STATUS, /* Not used */ 94 /* 225 */ UNUSED_STATUS, /* Not used */ 95 /* 226 */ mhd_MSTR_INIT ("IM Used") /* RFC3229 */ 96 }; 97 98 static const struct MHD_String three_hundred[] = { 99 /* 300 */ mhd_MSTR_INIT ("Multiple Choices"), /* RFC9110, Section 15.4.1 */ 100 /* 301 */ mhd_MSTR_INIT ("Moved Permanently"), /* RFC9110, Section 15.4.2 */ 101 /* 302 */ mhd_MSTR_INIT ("Found"), /* RFC9110, Section 15.4.3 */ 102 /* 303 */ mhd_MSTR_INIT ("See Other"), /* RFC9110, Section 15.4.4 */ 103 /* 304 */ mhd_MSTR_INIT ("Not Modified"), /* RFC9110, Section 15.4.5 */ 104 /* 305 */ mhd_MSTR_INIT ("Use Proxy"), /* RFC9110, Section 15.4.6 */ 105 /* 306 */ mhd_MSTR_INIT ("Switch Proxy"), /* Not used! RFC9110, Section 15.4.7 */ 106 /* 307 */ mhd_MSTR_INIT ("Temporary Redirect"), /* RFC9110, Section 15.4.8 */ 107 /* 308 */ mhd_MSTR_INIT ("Permanent Redirect") /* RFC9110, Section 15.4.9 */ 108 }; 109 110 static const struct MHD_String four_hundred[] = { 111 /* 400 */ mhd_MSTR_INIT ("Bad Request"), /* RFC9110, Section 15.5.1 */ 112 /* 401 */ mhd_MSTR_INIT ("Unauthorized"), /* RFC9110, Section 15.5.2 */ 113 /* 402 */ mhd_MSTR_INIT ("Payment Required"), /* RFC9110, Section 15.5.3 */ 114 /* 403 */ mhd_MSTR_INIT ("Forbidden"), /* RFC9110, Section 15.5.4 */ 115 /* 404 */ mhd_MSTR_INIT ("Not Found"), /* RFC9110, Section 15.5.5 */ 116 /* 405 */ mhd_MSTR_INIT ("Method Not Allowed"), /* RFC9110, Section 15.5.6 */ 117 /* 406 */ mhd_MSTR_INIT ("Not Acceptable"), /* RFC9110, Section 15.5.7 */ 118 /* 407 */ mhd_MSTR_INIT ("Proxy Authentication Required"), /* RFC9110, Section 15.5.8 */ 119 /* 408 */ mhd_MSTR_INIT ("Request Timeout"), /* RFC9110, Section 15.5.9 */ 120 /* 409 */ mhd_MSTR_INIT ("Conflict"), /* RFC9110, Section 15.5.10 */ 121 /* 410 */ mhd_MSTR_INIT ("Gone"), /* RFC9110, Section 15.5.11 */ 122 /* 411 */ mhd_MSTR_INIT ("Length Required"), /* RFC9110, Section 15.5.12 */ 123 /* 412 */ mhd_MSTR_INIT ("Precondition Failed"), /* RFC9110, Section 15.5.13 */ 124 /* 413 */ mhd_MSTR_INIT ("Content Too Large"), /* RFC9110, Section 15.5.14 */ 125 /* 414 */ mhd_MSTR_INIT ("URI Too Long"), /* RFC9110, Section 15.5.15 */ 126 /* 415 */ mhd_MSTR_INIT ("Unsupported Media Type"), /* RFC9110, Section 15.5.16 */ 127 /* 416 */ mhd_MSTR_INIT ("Range Not Satisfiable"), /* RFC9110, Section 15.5.17 */ 128 /* 417 */ mhd_MSTR_INIT ("Expectation Failed"), /* RFC9110, Section 15.5.18 */ 129 /* 418 */ UNUSED_STATUS, /* Not used */ 130 /* 419 */ UNUSED_STATUS, /* Not used */ 131 /* 420 */ UNUSED_STATUS, /* Not used */ 132 /* 421 */ mhd_MSTR_INIT ("Misdirected Request"), /* RFC9110, Section 15.5.20 */ 133 /* 422 */ mhd_MSTR_INIT ("Unprocessable Content"), /* RFC9110, Section 15.5.21 */ 134 /* 423 */ mhd_MSTR_INIT ("Locked"), /* RFC4918 */ 135 /* 424 */ mhd_MSTR_INIT ("Failed Dependency"), /* RFC4918 */ 136 /* 425 */ mhd_MSTR_INIT ("Too Early"), /* RFC8470 */ 137 /* 426 */ mhd_MSTR_INIT ("Upgrade Required"), /* RFC9110, Section 15.5.22 */ 138 /* 427 */ UNUSED_STATUS, /* Not used */ 139 /* 428 */ mhd_MSTR_INIT ("Precondition Required"), /* RFC6585 */ 140 /* 429 */ mhd_MSTR_INIT ("Too Many Requests"), /* RFC6585 */ 141 /* 430 */ UNUSED_STATUS, /* Not used */ 142 /* 431 */ mhd_MSTR_INIT ("Request Header Fields Too Large"), /* RFC6585 */ 143 /* 432 */ UNUSED_STATUS, /* Not used */ 144 /* 433 */ UNUSED_STATUS, /* Not used */ 145 /* 434 */ UNUSED_STATUS, /* Not used */ 146 /* 435 */ UNUSED_STATUS, /* Not used */ 147 /* 436 */ UNUSED_STATUS, /* Not used */ 148 /* 437 */ UNUSED_STATUS, /* Not used */ 149 /* 438 */ UNUSED_STATUS, /* Not used */ 150 /* 439 */ UNUSED_STATUS, /* Not used */ 151 /* 440 */ UNUSED_STATUS, /* Not used */ 152 /* 441 */ UNUSED_STATUS, /* Not used */ 153 /* 442 */ UNUSED_STATUS, /* Not used */ 154 /* 443 */ UNUSED_STATUS, /* Not used */ 155 /* 444 */ UNUSED_STATUS, /* Not used */ 156 /* 445 */ UNUSED_STATUS, /* Not used */ 157 /* 446 */ UNUSED_STATUS, /* Not used */ 158 /* 447 */ UNUSED_STATUS, /* Not used */ 159 /* 448 */ UNUSED_STATUS, /* Not used */ 160 /* 449 */ mhd_MSTR_INIT ("Reply With"), /* MS IIS extension */ 161 /* 450 */ mhd_MSTR_INIT ("Blocked by Windows Parental Controls"), /* MS extension */ 162 /* 451 */ mhd_MSTR_INIT ("Unavailable For Legal Reasons") /* RFC7725 */ 163 }; 164 165 static const struct MHD_String five_hundred[] = { 166 /* 500 */ mhd_MSTR_INIT ("Internal Server Error"), /* RFC9110, Section 15.6.1 */ 167 /* 501 */ mhd_MSTR_INIT ("Not Implemented"), /* RFC9110, Section 15.6.2 */ 168 /* 502 */ mhd_MSTR_INIT ("Bad Gateway"), /* RFC9110, Section 15.6.3 */ 169 /* 503 */ mhd_MSTR_INIT ("Service Unavailable"), /* RFC9110, Section 15.6.4 */ 170 /* 504 */ mhd_MSTR_INIT ("Gateway Timeout"), /* RFC9110, Section 15.6.5 */ 171 /* 505 */ mhd_MSTR_INIT ("HTTP Version Not Supported"), /* RFC9110, Section 15.6.6 */ 172 /* 506 */ mhd_MSTR_INIT ("Variant Also Negotiates"), /* RFC2295 */ 173 /* 507 */ mhd_MSTR_INIT ("Insufficient Storage"), /* RFC4918 */ 174 /* 508 */ mhd_MSTR_INIT ("Loop Detected"), /* RFC5842 */ 175 /* 509 */ mhd_MSTR_INIT ("Bandwidth Limit Exceeded"), /* Apache extension */ 176 /* 510 */ mhd_MSTR_INIT ("Not Extended"), /* (OBSOLETED) RFC2774; status-change-http-experiments-to-historic */ 177 /* 511 */ mhd_MSTR_INIT ("Network Authentication Required") /* RFC6585 */ 178 }; 179 180 181 struct mhd_HttpStatusesBlock 182 { 183 size_t num_elmnts; 184 const struct MHD_String *const data; 185 }; 186 187 #define STATUSES_BLOCK(m) { mhd_ARR_NUM_ELEMS (m), m} 188 189 static const struct mhd_HttpStatusesBlock statuses[] = { 190 STATUSES_BLOCK (invalid_hundred), 191 STATUSES_BLOCK (one_hundred), 192 STATUSES_BLOCK (two_hundred), 193 STATUSES_BLOCK (three_hundred), 194 STATUSES_BLOCK (four_hundred), 195 STATUSES_BLOCK (five_hundred) 196 }; 197 198 MHD_EXTERN_ MHD_FN_CONST_ const struct MHD_String * 199 MHD_HTTP_status_code_to_string (enum MHD_HTTP_StatusCode code) 200 { 201 const struct MHD_String *res; 202 const unsigned int code_i = (unsigned int) code; 203 if (100 > code_i) 204 return NULL; 205 if (600 < code) 206 return NULL; 207 if (statuses[code_i / 100].num_elmnts <= (code_i % 100)) 208 return NULL; 209 res = statuses[code_i / 100].data + (code_i % 100); 210 if (NULL == res->cstr) 211 return NULL; 212 return res; 213 } 214 215 216 MHD_INTERNAL MHD_FN_CONST_ const struct MHD_String * 217 mhd_HTTP_status_code_to_string_int (uint_fast16_t code) 218 { 219 static const struct MHD_String no_status = 220 mhd_MSTR_INIT ("Nonstandard Status"); 221 const struct MHD_String *res; 222 223 res = MHD_HTTP_status_code_to_string ((enum MHD_HTTP_StatusCode) code); 224 if (NULL != res) 225 return res; 226 227 return &no_status; 228 }