[Boost-bugs] [Boost C++ Libraries] #11633: chrono IO may throw bad_cast

Subject: [Boost-bugs] [Boost C++ Libraries] #11633: chrono IO may throw bad_cast
From: Boost C++ Libraries (noreply_at_[hidden])
Date: 2015-09-09 14:59:45


#11633: chrono IO may throw bad_cast
-------------------------------------------------+-------------------------
 Reporter: Sébastien Barthélémy <barthelemy@…> | Type: Bugs
   Status: new | Milestone: To Be
Component: None | Determined
 Severity: Problem | Version: Boost
                                                 | 1.58.0
                                                 | Keywords:
-------------------------------------------------+-------------------------
 I had occurences of chrono io throwing bad_cast exceptions, which lead to
 backtraces like this one:


 {{{
     #0 0x00007ffff54fda30 in __cxa_throw () from /usr/lib/x86_64-linux-
 gnu/libstdc++.so.6
     #1 0x00007ffff554f2a2 in std::__throw_bad_cast() () from
 /usr/lib/x86_64-linux-gnu/libstdc++.so.6
     #2 0x00007ffff2289bab in
 std::use_facet<boost::chrono::duration_punct<char> > (__loc=...) at
 /usr/include/c++/4.8/bits/locale_classes.tcc:137
     #3 0x00007ffff2288c61 in boost::chrono::operator<< <char,
 std::char_traits<char>, boost::rational<int>, boost::ratio<1l, 1l> >
 (os=..., d=...) at
 /home/sbarthelemy/.local/share/qi/toolchains/linux64/boost/include/boost/chrono/io_v1/chrono_io.hpp:210
 }}}

 I think the attached minimal example reproduces the issue.

 Here the compile & run log using boost 1.58
 {{{
 $ make clean && make test
 rm -f src/*.o src/chrono_io
 clang++ -std=c++11 -c -g -fPIC -Iinclude -I/usr/include -o src/chrono_io.o
 src/chrono_io.cc
 clang++ -std=c++11 -rdynamic -Lsrc -o src/chrono_io src/chrono_io.o
 -lboost_chrono -lboost_system -lpthread -L/usr/lib/x86_64-linux-gnu
 LD_LIBRARY_PATH=/usr/lib/x86_64-linux-gnu ./src/chrono_io
 terminate called after throwing an instance of 'std::bad_cast'
   what(): std::bad_cast
 Aborted (core dumped)
 Makefile:13: recipe for target 'test' failed
 make: *** [test] Error 13
 }}}


 Here is the code around boost/include/boost/chrono/io_v1/chrono_io.hpp:210
 {{{
 template <class CharT, class Traits, class Rep, class Period>
 std::basic_ostream<CharT, Traits>&
 operator<<(std::basic_ostream<CharT, Traits>& os, const duration<Rep,
 Period>& d)
 {
     typedef duration_punct<CharT> Facet;
     std::locale loc = os.getloc();
     if (!std::has_facet<Facet>(loc))
         os.imbue(std::locale(loc, new Facet));
     const Facet& f = std::use_facet<Facet>(os.getloc()); //<<<<<<<
 line210, throw here
     return os << d.count() << ' ' << f.template name<Period>(d.count());
 }
 }}}

 maybe we could avoid calling os.getloc() again at line 210 to avoid the
 race?

-- 
Ticket URL: <https://svn.boost.org/trac/boost/ticket/11633>
Boost C++ Libraries <http://www.boost.org/>
Boost provides free peer-reviewed portable C++ source libraries.

This archive was generated by hypermail 2.1.7 : 2017-02-16 18:50:19 UTC