unit_str_quote.c (31726B)
1 /* 2 This file is part of libmicrohttpd 3 Copyright (C) 2022 Karlson2k (Evgeny Grin) 4 5 This test tool is free software; you can redistribute it and/or 6 modify it under the terms of the GNU General Public License as 7 published by the Free Software Foundation; either version 2, or 8 (at your option) any later version. 9 10 This test tool is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public 16 License along with this library; if not, write to the Free Software 17 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 18 */ 19 20 /** 21 * @file src/tests/unit/unit_str_quote.c 22 * @brief Unit tests for quoted strings processing 23 * @author Karlson2k (Evgeny Grin) 24 */ 25 26 #include "mhd_sys_options.h" 27 #include <string.h> 28 #include <stdio.h> 29 30 #include "mhd_str.h" 31 #include "mhd_str.c" 32 33 #include "mhdt_checks.h" 34 #include "mhdt_has_param.h" 35 #include "mhd_assert.h" 36 37 #ifndef MHD_STATICSTR_LEN_ 38 /** 39 * Determine length of static string / macro strings at compile time. 40 */ 41 #define MHD_STATICSTR_LEN_(macro) (sizeof(macro) / sizeof(char) - 1) 42 #endif /* ! MHD_STATICSTR_LEN_ */ 43 44 45 #define TEST_STR_MAX_LEN 1024 46 47 /* return zero if succeed, non-zero otherwise */ 48 static unsigned int 49 expect_result_unquote_n (const char *const quoted, const size_t quoted_len, 50 const char *const unquoted, const size_t unquoted_len, 51 const unsigned int line_num) 52 { 53 static char buf[TEST_STR_MAX_LEN]; 54 size_t res_len; 55 unsigned int ret1; 56 unsigned int ret2; 57 unsigned int ret3; 58 unsigned int ret4; 59 60 mhd_assert (NULL != quoted); 61 mhd_assert (NULL != unquoted); 62 mhd_assert (TEST_STR_MAX_LEN > quoted_len); 63 mhd_assert (quoted_len >= unquoted_len); 64 65 /* First check: mhd_str_unquote () */ 66 ret1 = 0; 67 memset (buf, '#', sizeof(buf)); /* Fill buffer with character unused in the check */ 68 res_len = mhd_str_unquote (quoted, quoted_len, buf); 69 70 if (res_len != unquoted_len) 71 { 72 ret1 = 1; 73 fprintf (stderr, 74 "'mhd_str_unquote ()' FAILED: Wrong result size:\n"); 75 } 76 else if ((0 != unquoted_len) && (0 != memcmp (buf, unquoted, unquoted_len))) 77 { 78 ret1 = 1; 79 fprintf (stderr, 80 "'mhd_str_unquote ()' FAILED: Wrong result string:\n"); 81 } 82 if (0 != ret1) 83 { 84 /* This does NOT print part of the string after binary zero */ 85 fprintf (stderr, 86 "\tRESULT : mhd_str_unquote('%.*s', %u, ->'%.*s') -> %u\n" 87 "\tEXPECTED: mhd_str_unquote('%.*s', %u, ->'%.*s') -> %u\n", 88 (int) quoted_len, quoted, (unsigned) quoted_len, 89 (int) res_len, buf, (unsigned) res_len, 90 (int) quoted_len, quoted, (unsigned) quoted_len, 91 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 92 fprintf (stderr, 93 "The check is at line: %u\n\n", line_num); 94 } 95 96 /* Second check: mhd_str_equal_quoted_bin_n () */ 97 ret2 = 0; 98 if (! mhd_str_equal_quoted_bin_n (quoted, quoted_len, unquoted, unquoted_len)) 99 { 100 fprintf (stderr, 101 "'mhd_str_equal_quoted_bin_n ()' FAILED: Wrong result:\n"); 102 /* This does NOT print part of the string after binary zero */ 103 fprintf (stderr, 104 "\tRESULT : mhd_str_equal_quoted_bin_n('%.*s', %u, " 105 "'%.*s', %u) -> true\n" 106 "\tEXPECTED: mhd_str_equal_quoted_bin_n('%.*s', %u, " 107 "'%.*s', %u) -> false\n", 108 (int) quoted_len, quoted, (unsigned) quoted_len, 109 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 110 (int) quoted_len, quoted, (unsigned) quoted_len, 111 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 112 fprintf (stderr, 113 "The check is at line: %u\n\n", line_num); 114 ret2 = 1; 115 } 116 117 /* Third check: mhd_str_equal_caseless_quoted_bin_n () */ 118 ret3 = 0; 119 if (! mhd_str_equal_caseless_quoted_bin_n (quoted, 120 quoted_len, 121 unquoted, 122 unquoted_len)) 123 { 124 fprintf (stderr, 125 "'mhd_str_equal_caseless_quoted_bin_n ()' FAILED: Wrong result:\n") 126 ; 127 /* This does NOT print part of the string after binary zero */ 128 fprintf (stderr, 129 "\tRESULT : mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 130 "'%.*s', %u) -> true\n" 131 "\tEXPECTED: mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 132 "'%.*s', %u) -> false\n", 133 (int) quoted_len, quoted, (unsigned) quoted_len, 134 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 135 (int) quoted_len, quoted, (unsigned) quoted_len, 136 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 137 fprintf (stderr, 138 "The check is at line: %u\n\n", line_num); 139 ret3 = 1; 140 } 141 142 /* Fourth check: mhd_str_unquote () */ 143 ret4 = 0; 144 memset (buf, '#', sizeof(buf)); /* Fill buffer with character unused in the check */ 145 res_len = mhd_str_quote (unquoted, unquoted_len, buf, quoted_len); 146 if (res_len != quoted_len) 147 { 148 ret4 = 1; 149 fprintf (stderr, 150 "'mhd_str_quote ()' FAILED: Wrong result size:\n"); 151 } 152 else if ((0 != quoted_len) && (0 != memcmp (buf, quoted, quoted_len))) 153 { 154 ret4 = 1; 155 fprintf (stderr, 156 "'mhd_str_quote ()' FAILED: Wrong result string:\n"); 157 } 158 if (0 != ret4) 159 { 160 /* This does NOT print part of the string after binary zero */ 161 fprintf (stderr, 162 "\tRESULT : mhd_str_quote('%.*s', %u, ->'%.*s', %u) -> %u\n" 163 "\tEXPECTED: mhd_str_quote('%.*s', %u, ->'%.*s', %u) -> %u\n", 164 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 165 (int) res_len, buf, (unsigned) quoted_len, (unsigned) res_len, 166 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 167 (int) quoted_len, quoted, (unsigned) quoted_len, 168 (unsigned) unquoted_len); 169 fprintf (stderr, 170 "The check is at line: %u\n\n", line_num); 171 } 172 173 return ret1 + ret2 + ret3 + ret4; 174 } 175 176 177 #define expect_result_unquote(q,u) \ 178 expect_result_unquote_n (q,MHD_STATICSTR_LEN_ (q), \ 179 u,MHD_STATICSTR_LEN_ (u),__LINE__) 180 181 182 static unsigned int 183 check_match (void) 184 { 185 unsigned int r = 0; /**< The number of errors */ 186 187 r += expect_result_unquote ("", ""); 188 r += expect_result_unquote ("a", "a"); 189 r += expect_result_unquote ("abc", "abc"); 190 r += expect_result_unquote ("abcdef", "abcdef"); 191 r += expect_result_unquote ("a\0" "bc", "a\0" "bc"); 192 r += expect_result_unquote ("abc\\\"", "abc\""); 193 r += expect_result_unquote ("\\\"", "\""); 194 r += expect_result_unquote ("\\\"abc", "\"abc"); 195 r += expect_result_unquote ("abc\\\\", "abc\\"); 196 r += expect_result_unquote ("\\\\", "\\"); 197 r += expect_result_unquote ("\\\\abc", "\\abc"); 198 r += expect_result_unquote ("123\\\\\\\\\\\\\\\\", "123\\\\\\\\"); 199 r += expect_result_unquote ("\\\\\\\\\\\\\\\\", "\\\\\\\\"); 200 r += expect_result_unquote ("\\\\\\\\\\\\\\\\123", "\\\\\\\\123"); 201 r += expect_result_unquote ("\\\\\\\"\\\\\\\"\\\\\\\"\\\\\\\"\\\\\\\"" \ 202 "\\\\\\\"\\\\\\\"\\\\\\\"\\\\\\\"\\\\\\\"", \ 203 "\\\"\\\"\\\"\\\"\\\"\\\"\\\"\\\"\\\"\\\""); 204 205 return r; 206 } 207 208 209 /* return zero if succeed, non-zero otherwise */ 210 static unsigned int 211 expect_result_quote_failed_n (const char *const unquoted, 212 const size_t unquoted_len, 213 const size_t buf_size, 214 const unsigned int line_num) 215 { 216 static char buf[TEST_STR_MAX_LEN]; 217 size_t res_len; 218 unsigned int ret4; 219 220 mhd_assert (TEST_STR_MAX_LEN > buf_size); 221 222 /* The check: mhd_str_unquote () */ 223 ret4 = 0; 224 memset (buf, '#', sizeof(buf)); /* Fill buffer with character unused in the check */ 225 res_len = mhd_str_quote (unquoted, unquoted_len, buf, buf_size); 226 if (0 != res_len) 227 { 228 ret4 = 1; 229 fprintf (stderr, 230 "'mhd_str_quote ()' FAILED: Wrong result size:\n"); 231 } 232 if (0 != ret4) 233 { 234 /* This does NOT print part of the string after binary zero */ 235 fprintf (stderr, 236 "\tRESULT : mhd_str_quote('%.*s', %u, ->'%.*s', %u) -> %u\n" 237 "\tEXPECTED: mhd_str_quote('%.*s', %u, (not checked), %u) -> 0\n", 238 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 239 (int) res_len, buf, 240 (unsigned) buf_size, (unsigned) res_len, 241 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 242 (unsigned) buf_size); 243 fprintf (stderr, 244 "The check is at line: %u\n\n", line_num); 245 } 246 247 return ret4; 248 } 249 250 251 #define expect_result_quote_failed(q,s) \ 252 expect_result_quote_failed_n (q,MHD_STATICSTR_LEN_ (q), \ 253 s,__LINE__) 254 255 256 static unsigned int 257 check_quote_failed (void) 258 { 259 unsigned int r = 0; /**< The number of errors */ 260 261 r += expect_result_quote_failed ("a", 0); 262 r += expect_result_quote_failed ("aa", 1); 263 r += expect_result_quote_failed ("abc\\", 4); 264 r += expect_result_quote_failed ("abc\"", 4); 265 r += expect_result_quote_failed ("abc\"\"\"\"", 6); 266 r += expect_result_quote_failed ("abc\"\"\"\"", 7); 267 r += expect_result_quote_failed ("abc\"\"\"\"", 8); 268 r += expect_result_quote_failed ("abc\"\"\"\"", 9); 269 r += expect_result_quote_failed ("abc\"\"\"\"", 10); 270 r += expect_result_quote_failed ("abc\\\\\\\\", 9); 271 r += expect_result_quote_failed ("abc\\\\\\\\", 10); 272 r += expect_result_quote_failed ("abc\"\"\"\"", 9); 273 r += expect_result_quote_failed ("abc\"\"\"\"", 10); 274 r += expect_result_quote_failed ("abc\"\\\"\\", 9); 275 r += expect_result_quote_failed ("abc\\\"\\\"", 10); 276 r += expect_result_quote_failed ("\"\"\"\"abc", 6); 277 r += expect_result_quote_failed ("\"\"\"\"abc", 7); 278 r += expect_result_quote_failed ("\"\"\"\"abc", 8); 279 r += expect_result_quote_failed ("\"\"\"\"abc", 9); 280 r += expect_result_quote_failed ("\"\"\"\"abc", 10); 281 r += expect_result_quote_failed ("\\\\\\\\abc", 9); 282 r += expect_result_quote_failed ("\\\\\\\\abc", 10); 283 r += expect_result_quote_failed ("\"\"\"\"abc", 9); 284 r += expect_result_quote_failed ("\"\"\"\"abc", 10); 285 r += expect_result_quote_failed ("\"\\\"\\abc", 9); 286 r += expect_result_quote_failed ("\\\"\\\"abc", 10); 287 288 return r; 289 } 290 291 292 /* return zero if succeed, one otherwise */ 293 static unsigned int 294 expect_match_caseless_n (const char *const quoted, const size_t quoted_len, 295 const char *const unquoted, const size_t unquoted_len, 296 const unsigned int line_num) 297 { 298 unsigned int ret3; 299 300 mhd_assert (NULL != quoted); 301 mhd_assert (NULL != unquoted); 302 mhd_assert (TEST_STR_MAX_LEN > quoted_len); 303 304 /* The check: mhd_str_equal_caseless_quoted_bin_n () */ 305 ret3 = 0; 306 if (! mhd_str_equal_caseless_quoted_bin_n (quoted, 307 quoted_len, 308 unquoted, 309 unquoted_len)) 310 { 311 fprintf (stderr, 312 "'mhd_str_equal_caseless_quoted_bin_n ()' FAILED: Wrong result:\n") 313 ; 314 /* This does NOT print part of the string after binary zero */ 315 fprintf (stderr, 316 "\tRESULT : mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 317 "'%.*s', %u) -> true\n" 318 "\tEXPECTED: mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 319 "'%.*s', %u) -> false\n", 320 (int) quoted_len, quoted, (unsigned) quoted_len, 321 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 322 (int) quoted_len, quoted, (unsigned) quoted_len, 323 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 324 fprintf (stderr, 325 "The check is at line: %u\n\n", line_num); 326 ret3 = 1; 327 } 328 329 return ret3; 330 } 331 332 333 #define expect_match_caseless(q,u) \ 334 expect_match_caseless_n (q,MHD_STATICSTR_LEN_ (q), \ 335 u,MHD_STATICSTR_LEN_ (u),__LINE__) 336 337 static unsigned int 338 check_match_caseless (void) 339 { 340 unsigned int r = 0; /**< The number of errors */ 341 342 r += expect_match_caseless ("a", "A"); 343 r += expect_match_caseless ("abC", "aBc"); 344 r += expect_match_caseless ("AbCdeF", "aBCdEF"); 345 r += expect_match_caseless ("a\0" "Bc", "a\0" "bC"); 346 r += expect_match_caseless ("Abc\\\"", "abC\""); 347 r += expect_match_caseless ("\\\"", "\""); 348 r += expect_match_caseless ("\\\"aBc", "\"abc"); 349 r += expect_match_caseless ("abc\\\\", "ABC\\"); 350 r += expect_match_caseless ("\\\\", "\\"); 351 r += expect_match_caseless ("\\\\ABC", "\\abc"); 352 r += expect_match_caseless ("\\\\ZYX", "\\ZYX"); 353 r += expect_match_caseless ("abc", "ABC"); 354 r += expect_match_caseless ("ABCabc", "abcABC"); 355 r += expect_match_caseless ("abcXYZ", "ABCxyz"); 356 r += expect_match_caseless ("AbCdEfABCabc", "ABcdEFabcABC"); 357 r += expect_match_caseless ("a\\\\bc", "A\\BC"); 358 r += expect_match_caseless ("ABCa\\\\bc", "abcA\\BC"); 359 r += expect_match_caseless ("abcXYZ\\\\", "ABCxyz\\"); 360 r += expect_match_caseless ("\\\\AbCdEfABCabc", "\\ABcdEFabcABC"); 361 362 return r; 363 } 364 365 366 /* return zero if succeed, one otherwise */ 367 static unsigned int 368 expect_result_invalid_n (const char *const quoted, const size_t quoted_len, 369 const unsigned int line_num) 370 { 371 static char buf[TEST_STR_MAX_LEN]; 372 size_t res_len; 373 unsigned int ret1; 374 375 mhd_assert (NULL != quoted); 376 mhd_assert (TEST_STR_MAX_LEN > quoted_len); 377 378 /* The check: mhd_str_unquote () */ 379 ret1 = 0; 380 memset (buf, '#', sizeof(buf)); /* Fill buffer with character unused in the check */ 381 res_len = mhd_str_unquote (quoted, quoted_len, buf); 382 383 if (res_len != 0) 384 { 385 ret1 = 1; 386 fprintf (stderr, 387 "'mhd_str_unquote ()' FAILED: Wrong result size:\n"); 388 } 389 if (0 != ret1) 390 { 391 /* This does NOT print part of the string after binary zero */ 392 fprintf (stderr, 393 "\tRESULT : mhd_str_unquote('%.*s', %u, (not checked)) -> %u\n" 394 "\tEXPECTED: mhd_str_unquote('%.*s', %u, (not checked)) -> 0\n", 395 (int) quoted_len, quoted, (unsigned) quoted_len, 396 (unsigned) res_len, 397 (int) quoted_len, quoted, (unsigned) quoted_len); 398 fprintf (stderr, 399 "The check is at line: %u\n\n", line_num); 400 } 401 402 return ret1; 403 } 404 405 406 #define expect_result_invalid(q) \ 407 expect_result_invalid_n (q,MHD_STATICSTR_LEN_ (q),__LINE__) 408 409 410 static unsigned int 411 check_invalid (void) 412 { 413 unsigned int r = 0; /**< The number of errors */ 414 415 r += expect_result_invalid ("\\"); 416 r += expect_result_invalid ("\\\\\\"); 417 r += expect_result_invalid ("\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\"); 418 r += expect_result_invalid ("xyz\\"); 419 r += expect_result_invalid ("\\\"\\"); 420 r += expect_result_invalid ("\\\"\\\"\\\"\\"); 421 422 return r; 423 } 424 425 426 /* return zero if succeed, non-zero otherwise */ 427 static unsigned int 428 expect_result_unmatch_n (const char *const quoted, const size_t quoted_len, 429 const char *const unquoted, 430 const size_t unquoted_len, 431 const unsigned int line_num) 432 { 433 unsigned int ret2; 434 unsigned int ret3; 435 436 mhd_assert (NULL != quoted); 437 mhd_assert (NULL != unquoted); 438 439 /* The check: mhd_str_equal_quoted_bin_n () */ 440 ret2 = 0; 441 if (mhd_str_equal_quoted_bin_n (quoted, quoted_len, unquoted, unquoted_len)) 442 { 443 fprintf (stderr, 444 "'mhd_str_equal_quoted_bin_n ()' FAILED: Wrong result:\n"); 445 /* This does NOT print part of the string after binary zero */ 446 fprintf (stderr, 447 "\tRESULT : mhd_str_equal_quoted_bin_n('%.*s', %u, " 448 "'%.*s', %u) -> true\n" 449 "\tEXPECTED: mhd_str_equal_quoted_bin_n('%.*s', %u, " 450 "'%.*s', %u) -> false\n", 451 (int) quoted_len, quoted, (unsigned) quoted_len, 452 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 453 (int) quoted_len, quoted, (unsigned) quoted_len, 454 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 455 fprintf (stderr, 456 "The check is at line: %u\n\n", line_num); 457 ret2 = 1; 458 } 459 460 /* The check: mhd_str_equal_quoted_bin_n () */ 461 ret3 = 0; 462 if (mhd_str_equal_caseless_quoted_bin_n (quoted, quoted_len, unquoted, 463 unquoted_len)) 464 { 465 fprintf (stderr, 466 "'mhd_str_equal_caseless_quoted_bin_n ()' FAILED: Wrong result:\n") 467 ; 468 /* This does NOT print part of the string after binary zero */ 469 fprintf (stderr, 470 "\tRESULT : mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 471 "'%.*s', %u) -> true\n" 472 "\tEXPECTED: mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 473 "'%.*s', %u) -> false\n", 474 (int) quoted_len, quoted, (unsigned) quoted_len, 475 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 476 (int) quoted_len, quoted, (unsigned) quoted_len, 477 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 478 fprintf (stderr, 479 "The check is at line: %u\n\n", line_num); 480 ret3 = 1; 481 } 482 483 return ret2 + ret3; 484 } 485 486 487 #define expect_result_unmatch(q,u) \ 488 expect_result_unmatch_n (q,MHD_STATICSTR_LEN_ (q), \ 489 u,MHD_STATICSTR_LEN_ (u),__LINE__) 490 491 492 static unsigned int 493 check_unmatch (void) 494 { 495 unsigned int r = 0; /**< The number of errors */ 496 497 /* Matched sequence except invalid backslash at the end */ 498 r += expect_result_unmatch ("\\", ""); 499 r += expect_result_unmatch ("a\\", "a"); 500 r += expect_result_unmatch ("abc\\", "abc"); 501 r += expect_result_unmatch ("a\0" "bc\\", "a\0" "bc"); 502 r += expect_result_unmatch ("abc\\\"\\", "abc\""); 503 r += expect_result_unmatch ("\\\"\\", "\""); 504 r += expect_result_unmatch ("\\\"abc\\", "\"abc"); 505 r += expect_result_unmatch ("abc\\\\\\", "abc\\"); 506 r += expect_result_unmatch ("\\\\\\", "\\"); 507 r += expect_result_unmatch ("\\\\abc\\", "\\abc"); 508 r += expect_result_unmatch ("123\\\\\\\\\\\\\\\\\\", "123\\\\\\\\"); 509 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\\\", "\\\\\\\\"); 510 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\123\\", "\\\\\\\\123"); 511 /* Invalid backslash at the end and empty string */ 512 r += expect_result_unmatch ("\\", ""); 513 r += expect_result_unmatch ("a\\", ""); 514 r += expect_result_unmatch ("abc\\", ""); 515 r += expect_result_unmatch ("a\0" "bc\\", ""); 516 r += expect_result_unmatch ("abc\\\"\\", ""); 517 r += expect_result_unmatch ("\\\"\\", ""); 518 r += expect_result_unmatch ("\\\"abc\\", ""); 519 r += expect_result_unmatch ("abc\\\\\\", ""); 520 r += expect_result_unmatch ("\\\\\\", ""); 521 r += expect_result_unmatch ("\\\\abc\\", ""); 522 r += expect_result_unmatch ("123\\\\\\\\\\\\\\\\\\", ""); 523 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\\\", ""); 524 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\123\\", ""); 525 /* Difference at binary zero */ 526 r += expect_result_unmatch ("\0", ""); 527 r += expect_result_unmatch ("", "\0"); 528 r += expect_result_unmatch ("a\0", "a"); 529 r += expect_result_unmatch ("a", "a\0"); 530 r += expect_result_unmatch ("abc\0", "abc"); 531 r += expect_result_unmatch ("abc", "abc\0"); 532 r += expect_result_unmatch ("a\0" "bc\0", "a\0" "bc"); 533 r += expect_result_unmatch ("a\0" "bc", "a\0" "bc\0"); 534 r += expect_result_unmatch ("abc\\\"\0", "abc\""); 535 r += expect_result_unmatch ("abc\\\"", "abc\"\0"); 536 r += expect_result_unmatch ("\\\"\0", "\""); 537 r += expect_result_unmatch ("\\\"", "\"\0"); 538 r += expect_result_unmatch ("\\\"abc\0", "\"abc"); 539 r += expect_result_unmatch ("\\\"abc", "\"abc\0"); 540 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\\0", "\\\\\\\\"); 541 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\", "\\\\\\\\\0"); 542 r += expect_result_unmatch ("\\\\\\\\\\\\\0" "\\\\", "\\\\\\\\"); 543 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\", "\\\\\\\0" "\\"); 544 r += expect_result_unmatch ("\0" "abc", "abc"); 545 r += expect_result_unmatch ("abc", "\0" "abc"); 546 r += expect_result_unmatch ("\0" "abc", "0abc"); 547 r += expect_result_unmatch ("0abc", "\0" "abc"); 548 r += expect_result_unmatch ("xyz", "xy" "\0" "z"); 549 r += expect_result_unmatch ("xy" "\0" "z", "xyz"); 550 /* Difference after binary zero */ 551 r += expect_result_unmatch ("abc\0" "1", "abc\0" "2"); 552 r += expect_result_unmatch ("a\0" "bcx", "a\0" "bcy"); 553 r += expect_result_unmatch ("\0" "abc\\\"2", "\0" "abc\"1"); 554 r += expect_result_unmatch ("\0" "abc1\\\"", "\0" "abc2\""); 555 r += expect_result_unmatch ("\0" "\\\"c", "\0" "\"d"); 556 r += expect_result_unmatch ("\\\"ab" "\0" "1c", "\"ab" "\0" "2c"); 557 r += expect_result_unmatch ("a\0" "bcdef2", "a\0" "bcdef1"); 558 r += expect_result_unmatch ("a\0" "bc2def", "a\0" "bc1def"); 559 r += expect_result_unmatch ("a\0" "1bcdef", "a\0" "2bcdef"); 560 r += expect_result_unmatch ("abcde\0" "f2", "abcde\0" "f1"); 561 r += expect_result_unmatch ("123\\\\\\\\\\\\\0" "\\\\1", "123\\\\\\\0" "\\2"); 562 r += expect_result_unmatch ("\\\\\\\\\\\\\0" "1\\\\", "\\\\\\" "2\\"); 563 /* One side is empty */ 564 r += expect_result_unmatch ("abc", ""); 565 r += expect_result_unmatch ("", "abc"); 566 r += expect_result_unmatch ("1234567890", ""); 567 r += expect_result_unmatch ("", "1234567890"); 568 r += expect_result_unmatch ("abc\\\"", ""); 569 r += expect_result_unmatch ("", "abc\""); 570 r += expect_result_unmatch ("\\\"", ""); 571 r += expect_result_unmatch ("", "\""); 572 r += expect_result_unmatch ("\\\"abc", ""); 573 r += expect_result_unmatch ("", "\"abc"); 574 r += expect_result_unmatch ("abc\\\\", ""); 575 r += expect_result_unmatch ("", "abc\\"); 576 r += expect_result_unmatch ("\\\\", ""); 577 r += expect_result_unmatch ("", "\\"); 578 r += expect_result_unmatch ("\\\\abc", ""); 579 r += expect_result_unmatch ("", "\\abc"); 580 r += expect_result_unmatch ("123\\\\\\\\\\\\\\\\", ""); 581 r += expect_result_unmatch ("", "123\\\\\\\\"); 582 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\", ""); 583 r += expect_result_unmatch ("", "\\\\\\\\"); 584 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\123", ""); 585 r += expect_result_unmatch ("", "\\\\\\\\123"); 586 /* Various unmatched strings */ 587 r += expect_result_unmatch ("a", "x"); 588 r += expect_result_unmatch ("abc", "abcabc"); 589 r += expect_result_unmatch ("abc", "abcabcabc"); 590 r += expect_result_unmatch ("abc", "abcabcabcabc"); 591 r += expect_result_unmatch ("ABCABC", "ABC"); 592 r += expect_result_unmatch ("ABCABCABC", "ABC"); 593 r += expect_result_unmatch ("ABCABCABCABC", "ABC"); 594 r += expect_result_unmatch ("123\\\\\\\\\\\\\\\\\\\\", "123\\\\\\\\"); 595 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\\\\\", "\\\\\\\\"); 596 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\123\\\\", "\\\\\\\\123"); 597 r += expect_result_unmatch ("\\\\\\\\\\\\\\\\", "\\\\\\\\\\"); 598 599 return r; 600 } 601 602 603 /* return zero if succeed, one otherwise */ 604 static unsigned int 605 expect_result_case_unmatch_n (const char *const quoted, 606 const size_t quoted_len, 607 const char *const unquoted, 608 const size_t unquoted_len, 609 const unsigned int line_num) 610 { 611 unsigned int ret2; 612 613 mhd_assert (NULL != quoted); 614 mhd_assert (NULL != unquoted); 615 616 /* THe check: mhd_str_equal_quoted_bin_n () */ 617 ret2 = 0; 618 if (mhd_str_equal_quoted_bin_n (quoted, quoted_len, unquoted, unquoted_len)) 619 { 620 fprintf (stderr, 621 "'mhd_str_equal_quoted_bin_n ()' FAILED: Wrong result:\n"); 622 /* This does NOT print part of the string after binary zero */ 623 fprintf (stderr, 624 "\tRESULT : mhd_str_equal_quoted_bin_n('%.*s', %u, " 625 "'%.*s', %u) -> true\n" 626 "\tEXPECTED: mhd_str_equal_quoted_bin_n('%.*s', %u, " 627 "'%.*s', %u) -> false\n", 628 (int) quoted_len, quoted, (unsigned) quoted_len, 629 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 630 (int) quoted_len, quoted, (unsigned) quoted_len, 631 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 632 fprintf (stderr, 633 "The check is at line: %u\n\n", line_num); 634 ret2 = 1; 635 } 636 637 return ret2; 638 } 639 640 641 #define expect_result_case_unmatch(q,u) \ 642 expect_result_case_unmatch_n (q,MHD_STATICSTR_LEN_ (q), \ 643 u,MHD_STATICSTR_LEN_ (u),__LINE__) 644 645 static unsigned int 646 check_unmatch_case (void) 647 { 648 unsigned int r = 0; /**< The number of errors */ 649 650 r += expect_result_case_unmatch ("a", "A"); 651 r += expect_result_case_unmatch ("abC", "aBc"); 652 r += expect_result_case_unmatch ("AbCdeF", "aBCdEF"); 653 r += expect_result_case_unmatch ("a\0" "Bc", "a\0" "bC"); 654 r += expect_result_case_unmatch ("Abc\\\"", "abC\""); 655 r += expect_result_case_unmatch ("\\\"aBc", "\"abc"); 656 r += expect_result_case_unmatch ("abc\\\\", "ABC\\"); 657 r += expect_result_case_unmatch ("\\\\ABC", "\\abc"); 658 r += expect_result_case_unmatch ("\\\\ZYX", "\\ZYx"); 659 r += expect_result_case_unmatch ("abc", "ABC"); 660 r += expect_result_case_unmatch ("ABCabc", "abcABC"); 661 r += expect_result_case_unmatch ("abcXYZ", "ABCxyz"); 662 r += expect_result_case_unmatch ("AbCdEfABCabc", "ABcdEFabcABC"); 663 r += expect_result_case_unmatch ("a\\\\bc", "A\\BC"); 664 r += expect_result_case_unmatch ("ABCa\\\\bc", "abcA\\BC"); 665 r += expect_result_case_unmatch ("abcXYZ\\\\", "ABCxyz\\"); 666 r += expect_result_case_unmatch ("\\\\AbCdEfABCabc", "\\ABcdEFabcABC"); 667 668 return r; 669 } 670 671 672 /* return zero if succeed, one otherwise */ 673 static unsigned int 674 expect_result_caseless_unmatch_n (const char *const quoted, 675 const size_t quoted_len, 676 const char *const unquoted, 677 const size_t unquoted_len, 678 const unsigned int line_num) 679 { 680 unsigned int ret2; 681 unsigned int ret3; 682 683 mhd_assert (NULL != quoted); 684 mhd_assert (NULL != unquoted); 685 686 /* The check: mhd_str_equal_quoted_bin_n () */ 687 ret2 = 0; 688 if (mhd_str_equal_quoted_bin_n (quoted, quoted_len, unquoted, unquoted_len)) 689 { 690 fprintf (stderr, 691 "'mhd_str_equal_quoted_bin_n ()' FAILED: Wrong result:\n"); 692 /* This does NOT print part of the string after binary zero */ 693 fprintf (stderr, 694 "\tRESULT : mhd_str_equal_quoted_bin_n('%.*s', %u, " 695 "'%.*s', %u) -> true\n" 696 "\tEXPECTED: mhd_str_equal_quoted_bin_n('%.*s', %u, " 697 "'%.*s', %u) -> false\n", 698 (int) quoted_len, quoted, (unsigned) quoted_len, 699 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 700 (int) quoted_len, quoted, (unsigned) quoted_len, 701 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 702 fprintf (stderr, 703 "The check is at line: %u\n\n", line_num); 704 ret2 = 1; 705 } 706 707 /* The check: mhd_str_equal_quoted_bin_n () */ 708 ret3 = 0; 709 if (mhd_str_equal_caseless_quoted_bin_n (quoted, 710 quoted_len, 711 unquoted, 712 unquoted_len)) 713 { 714 fprintf (stderr, 715 "'mhd_str_equal_caseless_quoted_bin_n ()' FAILED: Wrong result:\n") 716 ; 717 /* This does NOT print part of the string after binary zero */ 718 fprintf (stderr, 719 "\tRESULT : mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 720 "'%.*s', %u) -> true\n" 721 "\tEXPECTED: mhd_str_equal_caseless_quoted_bin_n('%.*s', %u, " 722 "'%.*s', %u) -> false\n", 723 (int) quoted_len, quoted, (unsigned) quoted_len, 724 (int) unquoted_len, unquoted, (unsigned) unquoted_len, 725 (int) quoted_len, quoted, (unsigned) quoted_len, 726 (int) unquoted_len, unquoted, (unsigned) unquoted_len); 727 fprintf (stderr, 728 "The check is at line: %u\n\n", line_num); 729 ret3 = 1; 730 } 731 732 return ret2 + ret3; 733 } 734 735 736 #define expect_result_caseless_unmatch(q,u) \ 737 expect_result_caseless_unmatch_n (q,MHD_STATICSTR_LEN_ (q), \ 738 u,MHD_STATICSTR_LEN_ (u),__LINE__) 739 740 741 static unsigned int 742 check_unmatch_caseless (void) 743 { 744 unsigned int r = 0; /**< The number of errors */ 745 746 /* Matched sequence except invalid backslash at the end */ 747 r += expect_result_caseless_unmatch ("a\\", "A"); 748 r += expect_result_caseless_unmatch ("abC\\", "abc"); 749 r += expect_result_caseless_unmatch ("a\0" "Bc\\", "a\0" "bc"); 750 r += expect_result_caseless_unmatch ("abc\\\"\\", "ABC\""); 751 r += expect_result_caseless_unmatch ("\\\"\\", "\""); 752 r += expect_result_caseless_unmatch ("\\\"ABC\\", "\"abc"); 753 r += expect_result_caseless_unmatch ("Abc\\\\\\", "abC\\"); 754 r += expect_result_caseless_unmatch ("\\\\\\", "\\"); 755 r += expect_result_caseless_unmatch ("\\\\aBc\\", "\\abC"); 756 /* Difference at binary zero */ 757 r += expect_result_caseless_unmatch ("a\0", "A"); 758 r += expect_result_caseless_unmatch ("A", "a\0"); 759 r += expect_result_caseless_unmatch ("abC\0", "abc"); 760 r += expect_result_caseless_unmatch ("abc", "ABc\0"); 761 r += expect_result_caseless_unmatch ("a\0" "bC\0", "a\0" "bc"); 762 r += expect_result_caseless_unmatch ("a\0" "bc", "A\0" "bc\0"); 763 r += expect_result_caseless_unmatch ("ABC\\\"\0", "abc\""); 764 r += expect_result_caseless_unmatch ("abc\\\"", "ABC\"\0"); 765 r += expect_result_caseless_unmatch ("\\\"aBc\0", "\"abc"); 766 r += expect_result_caseless_unmatch ("\\\"Abc", "\"abc\0"); 767 r += expect_result_caseless_unmatch ("\\\\\\\\\\\\\\\\\0", "\\\\\\\\"); 768 r += expect_result_caseless_unmatch ("\\\\\\\\\\\\\\\\", "\\\\\\\\\0"); 769 r += expect_result_caseless_unmatch ("\\\\\\\\\\\\\0" "\\\\", "\\\\\\\\"); 770 r += expect_result_caseless_unmatch ("\\\\\\\\\\\\\\\\", "\\\\\\\0" "\\"); 771 r += expect_result_caseless_unmatch ("\0" "aBc", "abc"); 772 r += expect_result_caseless_unmatch ("abc", "\0" "abC"); 773 r += expect_result_caseless_unmatch ("\0" "abc", "0abc"); 774 r += expect_result_caseless_unmatch ("0abc", "\0" "aBc"); 775 r += expect_result_caseless_unmatch ("xyZ", "xy" "\0" "z"); 776 r += expect_result_caseless_unmatch ("Xy" "\0" "z", "xyz"); 777 /* Difference after binary zero */ 778 r += expect_result_caseless_unmatch ("abc\0" "1", "aBC\0" "2"); 779 r += expect_result_caseless_unmatch ("a\0" "bcX", "a\0" "bcy"); 780 r += expect_result_caseless_unmatch ("\0" "abc\\\"2", "\0" "Abc\"1"); 781 r += expect_result_caseless_unmatch ("\0" "Abc1\\\"", "\0" "abc2\""); 782 r += expect_result_caseless_unmatch ("\0" "\\\"c", "\0" "\"d"); 783 r += expect_result_caseless_unmatch ("\\\"ab" "\0" "1C", "\"ab" "\0" "2C"); 784 r += expect_result_caseless_unmatch ("a\0" "BCDef2", "a\0" "bcdef1"); 785 r += expect_result_caseless_unmatch ("a\0" "bc2def", "a\0" "BC1def"); 786 r += expect_result_caseless_unmatch ("a\0" "1bcdeF", "a\0" "2bcdef"); 787 r += expect_result_caseless_unmatch ("abcde\0" "f2", "ABCDE\0" "f1"); 788 r += expect_result_caseless_unmatch ("\\\"ab" "\0" "XC", "\"ab" "\0" "yC"); 789 r += expect_result_caseless_unmatch ("a\0" "BCDefY", "a\0" "bcdefx"); 790 r += expect_result_caseless_unmatch ("a\0" "bczdef", "a\0" "BCXdef"); 791 r += expect_result_caseless_unmatch ("a\0" "YbcdeF", "a\0" "zbcdef"); 792 r += expect_result_caseless_unmatch ("abcde\0" "fy", "ABCDE\0" "fX"); 793 794 return r; 795 } 796 797 798 int 799 main (int argc, char *argv[]) 800 { 801 unsigned int errcount = 0; 802 (void) argc; (void) argv; /* Unused. Silent compiler warning. */ 803 errcount += check_match (); 804 errcount += check_quote_failed (); 805 errcount += check_match_caseless (); 806 errcount += check_invalid (); 807 errcount += check_unmatch (); 808 errcount += check_unmatch_case (); 809 errcount += check_unmatch_caseless (); 810 if (0 == errcount) 811 printf ("All tests were passed without errors.\n"); 812 return errcount == 0 ? 0 : 1; 813 }