+static int match_multi_number(unsigned long num, char c, const char *date, char *end, struct tm *tm)
+{
+ long num2, num3;
+
+ num2 = strtol(end+1, &end, 10);
+ num3 = -1;
+ if (*end == c && isdigit(end[1]))
+ num3 = strtol(end+1, &end, 10);
+
+ /* Time? Date? */
+ switch (c) {
+ case ':':
+ if (num3 < 0)
+ num3 = 0;
+ if (num < 25 && num2 >= 0 && num2 < 60 && num3 >= 0 && num3 <= 60) {
+ tm->tm_hour = num;
+ tm->tm_min = num2;
+ tm->tm_sec = num3;
+ break;
+ }
+ return 0;
+
+ case '-':
+ case '/':
+ if (num > 70) {
+ /* yyyy-mm-dd? */
+ if (is_date(num, num2, num3, tm))
+ break;
+ /* yyyy-dd-mm? */
+ if (is_date(num, num3, num2, tm))
+ break;
+ }
+ /* mm/dd/yy ? */
+ if (is_date(num3, num2, num, tm))
+ break;
+ /* dd/mm/yy ? */
+ if (is_date(num3, num, num2, tm))
+ break;
+ return 0;
+ }
+ return end - date;
+}
+
+/*
+ * We've seen a digit. Time? Year? Date?
+ */
+static int match_digit(const char *date, struct tm *tm, int *offset, int *tm_gmt)