/[james]/httplint/httplint.c
ViewVC logotype

Diff of /httplint/httplint.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 40 by james, Mon Dec 15 15:07:31 2003 UTC revision 41 by james, Wed Dec 17 17:44:40 2003 UTC
# Line 36  CURL *curl; Line 36  CURL *curl;
36  int status_code;  int status_code;
37  char error_buffer[CURL_ERROR_SIZE];  char error_buffer[CURL_ERROR_SIZE];
38  regex_t re_status_line, re_token, re_token_value, re_content_type, re_ugly,  regex_t re_status_line, re_token, re_token_value, re_content_type, re_ugly,
39      re_absolute_uri, re_etag, re_server, re_transfer_coding, re_upgrade;      re_absolute_uri, re_etag, re_server, re_transfer_coding, re_upgrade,
40        re_rfc1123, re_rfc1036, re_asctime;
41    
42    
43  void init(void);  void init(void);
# Line 47  size_t data_callback(void *ptr, size_t s Line 48  size_t data_callback(void *ptr, size_t s
48  void check_status_line(const char *s);  void check_status_line(const char *s);
49  void check_header(const char *name, const char *value);  void check_header(const char *name, const char *value);
50  bool parse_date(const char *s, struct tm *tm);  bool parse_date(const char *s, struct tm *tm);
51    int month(const char *s);
52  const char *skip_lws(const char *s);  const char *skip_lws(const char *s);
53  bool parse_list(const char *s, regex_t *preg, unsigned int n, unsigned int m,  bool parse_list(const char *s, regex_t *preg, unsigned int n, unsigned int m,
54      void (*callback)(const char *s, regmatch_t pmatch[]));      void (*callback)(const char *s, regmatch_t pmatch[]));
# Line 204  void init(void) Line 206  void init(void)
206    regcomp_wrapper(&re_ugly,    regcomp_wrapper(&re_ugly,
207        "^[a-zA-Z0-9]+://[^/]+[/a-zA-Z0-9-_]*$",        "^[a-zA-Z0-9]+://[^/]+[/a-zA-Z0-9-_]*$",
208        REG_EXTENDED);        REG_EXTENDED);
209      regcomp_wrapper(&re_rfc1123,
210          "^(Mon|Tue|Wed|Thu|Fri|Sat|Sun), ([0123][0-9]) "
211          "(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec) ([0-9]{4}) "
212          "([012][0-9]):([0-5][0-9]):([0-5][0-9]) GMT$",
213          REG_EXTENDED);
214      regcomp_wrapper(&re_rfc1036,
215          "^(Monday|Tuesday|Wednesday|Thursday|Friday|Saturday|Sunday), "
216          "([0123][0-9])-(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)-"
217          "([0-9][0-9]) ([012][0-9]):([0-5][0-9]):([0-5][0-9]) GMT$",
218          REG_EXTENDED);
219      regcomp_wrapper(&re_asctime,
220          "^(Mon|Tue|Wed|Thu|Fri|Sat|Sun) "
221          "(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec) ([ 12][0-9]) "
222          "([012][0-9]):([0-5][0-9]):([0-5][0-9]) ([0-9]{4})$",
223          REG_EXTENDED);
224  }  }
225    
226    
# Line 390  void check_header(const char *name, cons Line 407  void check_header(const char *name, cons
407   */   */
408  bool parse_date(const char *s, struct tm *tm)  bool parse_date(const char *s, struct tm *tm)
409  {  {
410    char *r;    int r;
411    int len = strlen(s);    int len = strlen(s);
412      regmatch_t pmatch[20];
413    
414      tm->tm_wday = 0;
415      tm->tm_yday = 0;
416      tm->tm_isdst = 0;
417      tm->tm_gmtoff = 0;
418      tm->tm_zone = "GMT";
419    
420    if (len == 29) {    if (len == 29) {
421      /* RFC 1123 */      /* RFC 1123 */
422      r = strptime(s, "%a, %d %b %Y %H:%M:%S GMT", tm);      r = regexec(&re_rfc1123, s, 20, pmatch, 0);
423      if (r == s + len)      if (r == 0) {
424          tm->tm_mday = atoi(s + pmatch[2].rm_so);
425          tm->tm_mon = month(s + pmatch[3].rm_so);
426          tm->tm_year = atoi(s + pmatch[4].rm_so) - 1900;
427          tm->tm_hour = atoi(s + pmatch[5].rm_so);
428          tm->tm_min = atoi(s + pmatch[6].rm_so);
429          tm->tm_sec = atoi(s + pmatch[7].rm_so);
430        return true;        return true;
431        }
432    
433    } else if (len == 24) {    } else if (len == 24) {
434      /* asctime() format */      /* asctime() format */
435      r = strptime(s, "%a %b %d %H:%M:%S %Y", tm);      r = regexec(&re_asctime, s, 20, pmatch, 0);
436      if (r == s + len) {      if (r == 0) {
437        lookup("asctime");        if (s[pmatch[3].rm_so] == ' ')
438        return true;          tm->tm_mday = atoi(s + pmatch[3].rm_so + 1);
439      }        else
440      r = strptime(s, "%a %b  %d %H:%M:%S %Y", tm);          tm->tm_mday = atoi(s + pmatch[3].rm_so);
441      if (r == s + len) {        tm->tm_mon = month(s + pmatch[2].rm_so);
442          tm->tm_year = atoi(s + pmatch[7].rm_so) - 1900;
443          tm->tm_hour = atoi(s + pmatch[4].rm_so);
444          tm->tm_min = atoi(s + pmatch[5].rm_so);
445          tm->tm_sec = atoi(s + pmatch[6].rm_so);
446        lookup("asctime");        lookup("asctime");
447        return true;        return true;
448      }      }
449    
450    } else {    } else {
451      /* RFC 1036 */      /* RFC 1036 */
452      r = strptime(s, "%a, %d-%b-%y %H:%M:%S GMT", tm);      r = regexec(&re_rfc1036, s, 20, pmatch, 0);
453      if (r == s + len) {      if (r == 0) {
454          tm->tm_mday = atoi(s + pmatch[2].rm_so);
455          tm->tm_mon = month(s + pmatch[3].rm_so);
456          tm->tm_year = 100 + atoi(s + pmatch[4].rm_so);
457          tm->tm_hour = atoi(s + pmatch[5].rm_so);
458          tm->tm_min = atoi(s + pmatch[6].rm_so);
459          tm->tm_sec = atoi(s + pmatch[7].rm_so);
460        lookup("rfc1036");        lookup("rfc1036");
461        return true;        return true;
462      }      }
# Line 427  bool parse_date(const char *s, struct tm Line 468  bool parse_date(const char *s, struct tm
468  }  }
469    
470    
471    /**
472     * Convert a month name to the month number.
473     */
474    int month(const char *s)
475    {
476      switch (s[0]) {
477        case 'J':
478          switch (s[1]) {
479            case 'a':
480              return 0;
481            case 'u':
482              return s[2] == 'n' ? 5 : 6;
483          }
484        case 'F':
485          return 1;
486        case 'M':
487          return s[2] == 'r' ? 2 : 4;
488        case 'A':
489          return s[1] == 'p' ? 3 : 7;
490        case 'S':
491          return 8;
492        case 'O':
493          return 9;
494        case 'N':
495          return 10;
496        case 'D':
497          return 11;
498      }
499      return 0;
500    }
501    
502    
503  /**  /**
504   * Skip optional LWS (linear white space) [2.2]   * Skip optional LWS (linear white space) [2.2]
505   */   */

Legend:
Removed from v.40  
changed lines
  Added in v.41

  ViewVC Help
Powered by ViewVC 1.1.26