Bug 1402151, part 1 - Improve handling of two digit years. r=michal
The tm_year field of PRExplodedTime is an absolute year, not years
since 1900, so fix a few places that try to do the latter.
I also made the conversion of 2 digit years more consistent.
MozReview-Commit-ID: GetS2wmXHhA
--- a/netwerk/streamconv/converters/ParseFTPList.cpp
+++ b/netwerk/streamconv/converters/ParseFTPList.cpp
@@ -20,16 +20,29 @@ using mozilla::CheckedInt;
static inline int ParsingFailed(struct list_state *state)
{
if (state->parsed_one || state->lstyle) /* junk if we fail to parse */
return '?'; /* this time but had previously parsed successfully */
return '"'; /* its part of a comment or error message */
}
+void
+FixupYear(PRExplodedTime* aTime)
+{
+ /* if year has only two digits then assume that
+ 00-79 is 2000-2079
+ 80-99 is 1980-1999 */
+ if (aTime->tm_year < 80) {
+ aTime->tm_year += 2000;
+ } else if (aTime->tm_year < 100) {
+ aTime->tm_year += 1900;
+ }
+}
+
int ParseFTPList(const char *line, struct list_state *state,
struct list_result *result )
{
unsigned int carry_buf_len; /* copy of state->carry_buf_len */
unsigned int pos;
const char *p;
if (!line || !state || !result)
@@ -650,28 +663,27 @@ int ParseFTPList(const char *line, struc
if (lstyle == 'C')
{
state->parsed_one = 1;
state->lstyle = lstyle;
p = tokens[tokmarker+4];
if (toklen[tokmarker+4] == 10) /* newstyle: YYYY-MM-DD format */
{
- result->fe_time.tm_year = atoi(p+0) - 1900;
+ result->fe_time.tm_year = atoi(p+0);
result->fe_time.tm_month = atoi(p+5) - 1;
result->fe_time.tm_mday = atoi(p+8);
}
else /* oldstyle: [M]M/DD/YY format */
{
pos = toklen[tokmarker+4];
result->fe_time.tm_month = atoi(p) - 1;
result->fe_time.tm_mday = atoi((p+pos)-5);
result->fe_time.tm_year = atoi((p+pos)-2);
- if (result->fe_time.tm_year < 70)
- result->fe_time.tm_year += 100;
+ FixupYear(&result->fe_time);
}
p = tokens[tokmarker+5];
pos = toklen[tokmarker+5];
result->fe_time.tm_hour = atoi(p);
result->fe_time.tm_min = atoi((p+pos)-5);
result->fe_time.tm_sec = atoi((p+pos)-2);
@@ -824,23 +836,17 @@ int ParseFTPList(const char *line, struc
}
result->fe_time.tm_month = atoi(tokens[0]+0);
if (result->fe_time.tm_month != 0)
{
result->fe_time.tm_month--;
result->fe_time.tm_mday = atoi(tokens[0]+3);
result->fe_time.tm_year = atoi(tokens[0]+6);
- /* if year has only two digits then assume that
- 00-79 is 2000-2079
- 80-99 is 1980-1999 */
- if (result->fe_time.tm_year < 80)
- result->fe_time.tm_year += 2000;
- else if (result->fe_time.tm_year < 100)
- result->fe_time.tm_year += 1900;
+ FixupYear(&result->fe_time);
}
result->fe_time.tm_hour = atoi(tokens[1]+0);
result->fe_time.tm_min = atoi(tokens[1]+3);
if (toklen[1] == 7)
{
if ((tokens[1][5]) == 'P' && result->fe_time.tm_hour < 12)
result->fe_time.tm_hour += 12;
@@ -942,18 +948,17 @@ int ParseFTPList(const char *line, struc
pos = (sizeof(result->fe_size)-1);
memcpy( result->fe_size, tokens[0], pos );
result->fe_size[pos] = '\0';
}
result->fe_time.tm_month = atoi(&p[35-18]) - 1;
result->fe_time.tm_mday = atoi(&p[38-18]);
result->fe_time.tm_year = atoi(&p[41-18]);
- if (result->fe_time.tm_year < 80)
- result->fe_time.tm_year += 100;
+ FixupYear(&result->fe_time);
result->fe_time.tm_hour = atoi(&p[46-18]);
result->fe_time.tm_min = atoi(&p[49-18]);
/* the caller should do this (if dropping "." and ".." is desired)
if (result->fe_type == 'd' && result->fe_fname[0] == '.' &&
(result->fe_fnlen == 1 || (result->fe_fnlen == 2 &&
result->fe_fname[1] == '.')))
return '?';
@@ -1369,29 +1374,28 @@ int ParseFTPList(const char *line, struc
for (pos = 0; pos < (12*3); pos+=3)
{
if (tbuf[0] == month_names[pos+0] &&
tbuf[1] == month_names[pos+1] &&
tbuf[2] == month_names[pos+2])
{
result->fe_time.tm_month = pos/3;
result->fe_time.tm_mday = atoi(tokens[3]);
- result->fe_time.tm_year = atoi(tokens[4]) - 1900;
+ result->fe_time.tm_year = atoi(tokens[4]);
break;
}
}
pos = 5; /* Chameleon toknum of date field */
}
else
{
result->fe_time.tm_month = atoi(p+0)-1;
result->fe_time.tm_mday = atoi(p+3);
result->fe_time.tm_year = atoi(p+6);
- if (result->fe_time.tm_year < 80) /* SuperTCP */
- result->fe_time.tm_year += 100;
+ FixupYear(&result->fe_time); /* SuperTCP */
pos = 3; /* SuperTCP toknum of date field */
}
result->fe_time.tm_hour = atoi(tokens[pos]);
result->fe_time.tm_min = atoi(&(tokens[pos][toklen[pos]-2]));
/* the caller should do this (if dropping "." and ".." is desired)
@@ -1626,17 +1630,17 @@ int ParseFTPList(const char *line, struc
}
if (result->fe_time.tm_mday)
{
tokmarker += 3; /* skip mday/mon/yrtime (to find " -> ") */
p = tokens[tokmarker];
pos = atoi(p);
if (pos > 24)
- result->fe_time.tm_year = pos-1900;
+ result->fe_time.tm_year = pos;
else
{
if (p[1] == ':')
p--;
result->fe_time.tm_hour = pos;
result->fe_time.tm_min = atoi(p+3);
if (!state->now_time)
{