Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

<iomanip>: Case sensitivity when parsing months #1126

Closed
fsb4000 opened this issue Aug 1, 2020 · 2 comments · Fixed by #1168
Closed

<iomanip>: Case sensitivity when parsing months #1126

fsb4000 opened this issue Aug 1, 2020 · 2 comments · Fixed by #1168
Labels
bug Something isn't working fixed Something works now, yay!

Comments

@fsb4000
Copy link
Contributor

fsb4000 commented Aug 1, 2020

Describe the bug
According to the C++ standard, month and day string parsing is meant to be case insensitive.

From https://isocpp.org/files/papers/N4860.pdf (c++ 20 draft):
or from http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf (c++11 draft)

The next element of fmt is equal to’%’, optionally followed by a modifier character, followed by a conversion specifier character, format, together forming a conversion specification valid for the ISO/IEC 9945 function strptime

From https://pubs.opengroup.org/onlinepubs/9699919799/functions/strptime.html

Case is ignored when matching items in buf such as month or weekday names.

Clang with libc++ also parses fine: https://gcc.godbolt.org/z/ceb98o

Command-line test case

C:\Temp>type main.cpp
#include <iostream>
#include <sstream>
#include <iomanip>

int main()
{
    std::tm t = {};
    std::istringstream ss("2011-FEB-18");
    ss >> std::get_time(&t, "%Y-%b-%d");
    if (ss.fail()) {
        std::cout << "Parse failed\n";
    }
    else {
        std::cout << std::put_time(&t, "%c") << '\n';
    }
}

C:\Temp>cl /EHsc /W4 /WX main.cpp
Оптимизирующий компилятор Microsoft (R) C/C++ версии 19.27.29109 для x64
(C) Корпорация Майкрософт (Microsoft Corporation).  Все права защищены.

main.cpp
Microsoft (R) Incremental Linker Version 14.27.29109.0
Copyright (C) Microsoft Corporation.  All rights reserved.

/out:main.exe
main.obj

C:\Temp>main.exe
Parse failed

Expected behavior
Expected output:

Sun Feb 18 00:00:00 2011

STL version
Microsoft Visual Studio Community 2019 Preview Version 16.7.0 Preview 6.0

Additional context
VSO-596742 / AB#596742 | DevCom-229445

@fsb4000 fsb4000 mentioned this issue Aug 1, 2020
58 tasks
@Arzaghi
Copy link
Contributor

Arzaghi commented Aug 6, 2020

I'm trying to fix the issue and encountered another case that doesn't make sense.

#include <iostream>
#include <sstream>
#include <iomanip>

int main()
{
    std::tm t = {};
    std::istringstream ss("2011-D-18");
    ss >> std::get_time(&t, "%Y-%b-%d");
    if (ss.fail()) {
        std::cout << "Parse failed\n";
    }
    else {
        std::cout << std::put_time(&t, "%c") << '\n';
    }
}

MSVC output: 01/18/11 00:00:00
GCC output: parse failed

what should be the expected output for this code according to the Standard definitions?

@fsb4000
Copy link
Contributor Author

fsb4000 commented Aug 6, 2020

gcc output is correct.

for "C" locale it should parse only:

Jan
January
Feb
February
Mar
March
Apr
April
May
May
Jun
June
Jul
July
Aug
August
Sep
September
Oct
October
Nov
November
Dec
December

plus case insensitive: dEc, DEC, etc...

Current implementation of std::get_time is buggy :(

@StephanTLavavej StephanTLavavej added the bug Something isn't working label Aug 8, 2020
StephanTLavavej added a commit that referenced this issue Aug 26, 2020
Fixes #1126.

Co-authored-by: Stephan T. Lavavej <stl@microsoft.com>
@StephanTLavavej StephanTLavavej added the fixed Something works now, yay! label Aug 26, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working fixed Something works now, yay!
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants