// scans all digits (but no more than len) and returns the resulting number
bool GetNumericToken(size_t len,
wxString::const_iterator& p,
+ const wxString::const_iterator& end,
unsigned long *number)
{
size_t n = 1;
wxString s;
- while ( wxIsdigit(*p) )
+ while ( p != end && wxIsdigit(*p) )
{
s += *p++;
}
// scans all alphabetic characters and returns the resulting string
-wxString GetAlphaToken(wxString::const_iterator& p)
+wxString
+GetAlphaToken(wxString::const_iterator& p,
+ const wxString::const_iterator& end)
{
wxString s;
- while ( wxIsalpha(*p) )
+ while ( p != end && wxIsalpha(*p) )
{
s += *p++;
}
wxDateTime::ParseFormat(const wxString& date,
const wxString& format,
const wxDateTime& dateDef,
- wxString::const_iterator *end)
+ wxString::const_iterator *endParse)
{
wxCHECK_MSG( !format.empty(), false, "format can't be empty" );
- wxCHECK_MSG( end, false, "end iterator pointer must be specified" );
+ wxCHECK_MSG( endParse, false, "end iterator pointer must be specified" );
wxString str;
unsigned long num;
int year = 0;
wxString::const_iterator input = date.begin();
+ const wxString::const_iterator end = date.end();
for ( wxString::const_iterator fmt = format.begin(); fmt != format.end(); ++fmt )
{
if ( *fmt != _T('%') )
{
wday = GetWeekDayFromName
(
- GetAlphaToken(input),
+ GetAlphaToken(input, end),
*fmt == 'a' ? Name_Abbr : Name_Full,
DateLang_Local
);
{
mon = GetMonthFromName
(
- GetAlphaToken(input),
+ GetAlphaToken(input, end),
*fmt == 'b' ? Name_Abbr : Name_Full,
DateLang_Local
);
const wxDateTime dt = ParseFormatAt
(
input,
- date.end(),
+ end,
wxS("%a %b %d %H:%M:%S %Y"),
wxS("%x %X"),
wxS("%X %x")
break;
case _T('d'): // day of a month (01-31)
- if ( !GetNumericToken(width, input, &num) ||
+ if ( !GetNumericToken(width, input, end, &num) ||
(num > 31) || (num < 1) )
{
// no match
break;
case _T('H'): // hour in 24h format (00-23)
- if ( !GetNumericToken(width, input, &num) || (num > 23) )
+ if ( !GetNumericToken(width, input, end, &num) || (num > 23) )
{
// no match
return false;
break;
case _T('I'): // hour in 12h format (01-12)
- if ( !GetNumericToken(width, input, &num) || !num || (num > 12) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ !num || (num > 12) )
{
// no match
return false;
break;
case _T('j'): // day of the year
- if ( !GetNumericToken(width, input, &num) || !num || (num > 366) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ !num || (num > 366) )
{
// no match
return false;
break;
case _T('l'): // milliseconds (0-999)
- if ( !GetNumericToken(width, input, &num) )
+ if ( !GetNumericToken(width, input, end, &num) )
return false;
haveMsec = true;
break;
case _T('m'): // month as a number (01-12)
- if ( !GetNumericToken(width, input, &num) || !num || (num > 12) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ !num || (num > 12) )
{
// no match
return false;
break;
case _T('M'): // minute as a decimal number (00-59)
- if ( !GetNumericToken(width, input, &num) || (num > 59) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ (num > 59) )
{
// no match
return false;
case _T('p'): // AM or PM string
{
- wxString am, pm, token = GetAlphaToken(input);
+ wxString am, pm, token = GetAlphaToken(input, end);
// some locales have empty AM/PM tokens and thus when formatting
// dates with the %p specifier nothing is generated; when trying to
case _T('r'): // time as %I:%M:%S %p
{
wxDateTime dt;
- if ( !dt.ParseFormat(wxString(input, date.end()),
+ if ( !dt.ParseFormat(wxString(input, end),
wxS("%I:%M:%S %p"), &input) )
return false;
case _T('R'): // time as %H:%M
{
const wxDateTime
- dt = ParseFormatAt(input, date.end(), wxS("%H:%M"));
+ dt = ParseFormatAt(input, end, wxS("%H:%M"));
if ( !dt.IsValid() )
return false;
break;
case _T('S'): // second as a decimal number (00-61)
- if ( !GetNumericToken(width, input, &num) || (num > 61) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ (num > 61) )
{
// no match
return false;
case _T('T'): // time as %H:%M:%S
{
const wxDateTime
- dt = ParseFormatAt(input, date.end(), wxS("%H:%M:%S"));
+ dt = ParseFormatAt(input, end, wxS("%H:%M:%S"));
if ( !dt.IsValid() )
return false;
break;
case _T('w'): // weekday as a number (0-6), Sunday = 0
- if ( !GetNumericToken(width, input, &num) || (wday > 6) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ (wday > 6) )
{
// no match
return false;
}
const wxDateTime
- dt = ParseFormatAt(input, date.end(),
+ dt = ParseFormatAt(input, end,
fmtDate, fmtDateAlt);
if ( !dt.IsValid() )
return false;
// fails, as "%I:%M:%S %p" - this should catch the most
// common cases
const wxDateTime
- dt = ParseFormatAt(input, date.end(), "%T", "%r");
+ dt = ParseFormatAt(input, end, "%T", "%r");
if ( !dt.IsValid() )
return false;
break;
case _T('y'): // year without century (00-99)
- if ( !GetNumericToken(width, input, &num) || (num > 99) )
+ if ( !GetNumericToken(width, input, end, &num) ||
+ (num > 99) )
{
// no match
return false;
break;
case _T('Y'): // year with century
- if ( !GetNumericToken(width, input, &num) )
+ if ( !GetNumericToken(width, input, end, &num) )
{
// no match
return false;
if ( haveWDay && GetWeekDay() != wday )
return false;
- *end = input;
+ *endParse = input;
return true;
}
{ wxTRANSLATE("tomorrow"), 1 },
};
+ const size_t lenRest = date.end() - p;
for ( size_t n = 0; n < WXSIZEOF(literalDates); n++ )
{
const wxString dateStr = wxGetTranslation(literalDates[n].str);
size_t len = dateStr.length();
+ if ( len > lenRest )
+ continue;
+
const wxString::const_iterator pEnd = p + len;
if ( wxString(p, pEnd).CmpNoCase(dateStr) == 0 )
{