unit1660.c 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180
  1. /***************************************************************************
  2. * _ _ ____ _
  3. * Project ___| | | | _ \| |
  4. * / __| | | | |_) | |
  5. * | (__| |_| | _ <| |___
  6. * \___|\___/|_| \_\_____|
  7. *
  8. * Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
  9. *
  10. * This software is licensed as described in the file COPYING, which
  11. * you should have received as part of this distribution. The terms
  12. * are also available at https://curl.se/docs/copyright.html.
  13. *
  14. * You may opt to use, copy, modify, merge, publish, distribute and/or sell
  15. * copies of the Software, and permit persons to whom the Software is
  16. * furnished to do so, under the terms of the COPYING file.
  17. *
  18. * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
  19. * KIND, either express or implied.
  20. *
  21. * SPDX-License-Identifier: curl
  22. *
  23. ***************************************************************************/
  24. #include "curlcheck.h"
  25. #include "urldata.h"
  26. #include "hsts.h"
  27. static CURLcode
  28. unit_setup(void)
  29. {
  30. return CURLE_OK;
  31. }
  32. static void
  33. unit_stop(void)
  34. {
  35. curl_global_cleanup();
  36. }
  37. #if defined(CURL_DISABLE_HTTP) || defined(CURL_DISABLE_HSTS)
  38. UNITTEST_START
  39. {
  40. puts("nothing to do when HTTP or HSTS are disabled");
  41. }
  42. UNITTEST_STOP
  43. #else
  44. struct testit {
  45. const char *host;
  46. const char *chost; /* if non-NULL, use to lookup with */
  47. const char *hdr; /* if NULL, just do the lookup */
  48. const CURLcode result; /* parse result */
  49. };
  50. static const struct testit headers[] = {
  51. /* two entries read from disk cache, verify first */
  52. { "-", "readfrom.example", NULL, CURLE_OK},
  53. { "-", "old.example", NULL, CURLE_OK},
  54. /* delete the remaining one read from disk */
  55. { "readfrom.example", NULL, "max-age=\"0\"", CURLE_OK},
  56. { "example.com", NULL, "max-age=\"31536000\"\r\n", CURLE_OK },
  57. { "example.com", NULL, "max-age=\"21536000\"\r\n", CURLE_OK },
  58. { "example.com", NULL, "max-age=\"21536000\"; \r\n", CURLE_OK },
  59. { "example.com", NULL, "max-age=\"21536000\"; includeSubDomains\r\n",
  60. CURLE_OK },
  61. { "example.org", NULL, "max-age=\"31536000\"\r\n", CURLE_OK },
  62. { "this.example", NULL, "max=\"31536\";", CURLE_BAD_FUNCTION_ARGUMENT },
  63. { "this.example", NULL, "max-age=\"31536", CURLE_BAD_FUNCTION_ARGUMENT },
  64. { "this.example", NULL, "max-age=31536\"", CURLE_OK },
  65. /* max-age=0 removes the entry */
  66. { "this.example", NULL, "max-age=0", CURLE_OK },
  67. { "another.example", NULL, "includeSubDomains; ",
  68. CURLE_BAD_FUNCTION_ARGUMENT },
  69. /* Two max-age is illegal */
  70. { "example.com", NULL,
  71. "max-age=\"21536000\"; includeSubDomains; max-age=\"3\";",
  72. CURLE_BAD_FUNCTION_ARGUMENT },
  73. /* Two includeSubDomains is illegal */
  74. { "2.example.com", NULL,
  75. "max-age=\"21536000\"; includeSubDomains; includeSubDomains;",
  76. CURLE_BAD_FUNCTION_ARGUMENT },
  77. /* use a unknown directive "include" that should be ignored */
  78. { "3.example.com", NULL, "max-age=\"21536000\"; include; includeSubDomains;",
  79. CURLE_OK },
  80. /* remove the "3.example.com" one, should still match the example.com */
  81. { "3.example.com", NULL, "max-age=\"0\"; includeSubDomains;",
  82. CURLE_OK },
  83. { "-", "foo.example.com", NULL, CURLE_OK},
  84. { "-", "foo.xample.com", NULL, CURLE_OK},
  85. /* should not match */
  86. { "example.net", "forexample.net", "max-age=\"31536000\"\r\n", CURLE_OK },
  87. /* should not match either, since forexample.net is not in the example.net
  88. domain */
  89. { "example.net", "forexample.net",
  90. "max-age=\"31536000\"; includeSubDomains\r\n", CURLE_OK },
  91. /* remove example.net again */
  92. { "example.net", NULL, "max-age=\"0\"; includeSubDomains\r\n", CURLE_OK },
  93. /* make this live for 7 seconds */
  94. { "expire.example", NULL, "max-age=\"7\"\r\n", CURLE_OK },
  95. { NULL, NULL, NULL, CURLE_OK }
  96. };
  97. static void showsts(struct stsentry *e, const char *chost)
  98. {
  99. if(!e)
  100. printf("'%s' is not HSTS\n", chost);
  101. else {
  102. printf("%s [%s]: %" CURL_FORMAT_CURL_OFF_T "%s\n",
  103. chost, e->host, e->expires,
  104. e->includeSubDomains ? " includeSubDomains" : "");
  105. }
  106. }
  107. UNITTEST_START
  108. {
  109. CURLcode result;
  110. struct stsentry *e;
  111. struct hsts *h = Curl_hsts_init();
  112. int i;
  113. const char *chost;
  114. CURL *easy;
  115. char savename[256];
  116. abort_unless(h, "Curl_hsts_init()");
  117. curl_global_init(CURL_GLOBAL_ALL);
  118. easy = curl_easy_init();
  119. if(!easy) {
  120. Curl_hsts_cleanup(&h);
  121. curl_global_cleanup();
  122. abort_unless(easy, "curl_easy_init()");
  123. }
  124. Curl_hsts_loadfile(easy, h, arg);
  125. for(i = 0; headers[i].host ; i++) {
  126. if(headers[i].hdr) {
  127. result = Curl_hsts_parse(h, headers[i].host, headers[i].hdr);
  128. if(result != headers[i].result) {
  129. fprintf(stderr, "Curl_hsts_parse(%s) failed: %d\n",
  130. headers[i].hdr, result);
  131. unitfail++;
  132. continue;
  133. }
  134. else if(result) {
  135. printf("Input %u: error %d\n", i, (int) result);
  136. continue;
  137. }
  138. }
  139. chost = headers[i].chost ? headers[i].chost : headers[i].host;
  140. e = Curl_hsts(h, chost, strlen(chost), TRUE);
  141. showsts(e, chost);
  142. }
  143. printf("Number of entries: %zu\n", Curl_llist_count(&h->list));
  144. /* verify that it is exists for 7 seconds */
  145. chost = "expire.example";
  146. for(i = 100; i < 110; i++) {
  147. e = Curl_hsts(h, chost, strlen(chost), TRUE);
  148. showsts(e, chost);
  149. deltatime++; /* another second passed */
  150. }
  151. msnprintf(savename, sizeof(savename), "%s.save", arg);
  152. (void)Curl_hsts_save(easy, h, savename);
  153. Curl_hsts_cleanup(&h);
  154. curl_easy_cleanup(easy);
  155. curl_global_cleanup();
  156. }
  157. UNITTEST_STOP
  158. #endif