[Boost-bugs] [Boost C++ Libraries] #4807: Sink devices "leacks" exception out of the stream

Subject: [Boost-bugs] [Boost C++ Libraries] #4807: Sink devices "leacks" exception out of the stream
From: Boost C++ Libraries (noreply_at_[hidden])
Date: 2010-11-02 08:07:11


#4807: Sink devices "leacks" exception out of the stream
---------------------------------+------------------------------------------
 Reporter: artyomtnk@… | Owner: turkanis
     Type: Bugs | Status: new
Milestone: To Be Determined | Component: iostreams
  Version: Boost 1.44.0 | Severity: Problem
 Keywords: |
---------------------------------+------------------------------------------
 I implement the sink device that sometimes may fail on writes.
 When Sink is implemented it should throw an exception on fault
 to notify the stream on error.

 However it is not always works this way.
 I've got the exception to "leak" to the
 main program when I combine in the
 filter gzip_comressor() filter that writes
 to output device that its Sink is full.
 When I call reset on the filter
 the exception in leaking to the
 program instead of being caught.

 On the other hand, if I don't throw but rather return 0,
 I get into infinite loop
 in the boost::iostreams::non_blocking_adapter::write
 when I call filter.reset().

 In following example the exception is caught
 when filter.reset() is called, when it shouldn't.


 {{{
     #include <boost/iostreams/stream.hpp>
     #include <boost/iostreams/filtering_stream.hpp>
     #include <boost/iostreams/filter/gzip.hpp>
     #include <boost/iostreams/tee.hpp>
     #include <iostream>

     class my_small_device : public boost::iostreams::sink
     {
         int count;
     public:
         my_small_device() : count(1000) {}
         std::streamsize write(char const *d,std::streamsize n)
         {
             if(count < n)
                 throw std::runtime_error("Device is full");
             count-=n;
             return n;
         }
     };

     int main()
     {
         try {
             using namespace boost::iostreams;
             boost::iostreams::stream<my_small_device>
 output(my_small_device(),10);
             {
                 boost::iostreams::filtering_ostream filter;
                 filter.push(gzip_compressor());
                 filter.push(output);
                 for(int i=0;i<10000000;i++) {
                     if(!(filter << i << '\n')) {
                         std::cerr << "Fail!" << std::endl;
                         break;
                     }
                 }
                 std::cout << "Closing filter" << std::endl;
                 filter.reset();
             }

             std::cout << "ok" << std::endl;
             return 0;
         }catch(std::exception const &e) {
             std::cerr << "Catched " << e.what() << std::endl;
             return 1;
         }
     }
 }}}

-- 
Ticket URL: <https://svn.boost.org/trac/boost/ticket/4807>
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:04 UTC