gh-122272: Guarantee specifiers %F and %C for datetime.strftime to be 0-padded (GH-122436)

This commit is contained in:
blhsing 2024-08-23 23:45:03 +08:00 committed by GitHub
parent 7cd3aa42f0
commit 126910edba
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 145 additions and 14 deletions

View file

@ -1853,7 +1853,12 @@ wrap_strftime(PyObject *object, PyObject *format, PyObject *timetuple,
#ifdef Py_NORMALIZE_CENTURY
/* Buffer of maximum size of formatted year permitted by long. */
char buf[SIZEOF_LONG*5/2+2];
char buf[SIZEOF_LONG * 5 / 2 + 2
#ifdef Py_STRFTIME_C99_SUPPORT
/* Need 6 more to accomodate dashes, 2-digit month and day for %F. */
+ 6
#endif
];
#endif
assert(object && format && timetuple);
@ -1950,11 +1955,18 @@ wrap_strftime(PyObject *object, PyObject *format, PyObject *timetuple,
ntoappend = PyBytes_GET_SIZE(freplacement);
}
#ifdef Py_NORMALIZE_CENTURY
else if (ch == 'Y' || ch == 'G') {
else if (ch == 'Y' || ch == 'G'
#ifdef Py_STRFTIME_C99_SUPPORT
|| ch == 'F' || ch == 'C'
#endif
) {
/* 0-pad year with century as necessary */
PyObject *item = PyTuple_GET_ITEM(timetuple, 0);
PyObject *item = PySequence_GetItem(timetuple, 0);
if (item == NULL) {
goto Done;
}
long year_long = PyLong_AsLong(item);
Py_DECREF(item);
if (year_long == -1 && PyErr_Occurred()) {
goto Done;
}
@ -1980,8 +1992,16 @@ wrap_strftime(PyObject *object, PyObject *format, PyObject *timetuple,
goto Done;
}
}
ntoappend = PyOS_snprintf(buf, sizeof(buf), "%04ld", year_long);
ntoappend = PyOS_snprintf(buf, sizeof(buf),
#ifdef Py_STRFTIME_C99_SUPPORT
ch == 'F' ? "%04ld-%%m-%%d" :
#endif
"%04ld", year_long);
#ifdef Py_STRFTIME_C99_SUPPORT
if (ch == 'C') {
ntoappend -= 2;
}
#endif
ptoappend = buf;
}
#endif