Boost C++ Libraries: Ticket #3650: Text Serialization crashes when istream close unexpectedly https://svn.boost.org/trac10/ticket/3650 <p> I am using <a class="missing wiki">TextSerialization</a> over a tcp::iostream. I am retrieving object pointers through the serialization mecanisms. </p> <p> boost::archive::text_iarchive ia(*_stream); while(!_stream-&gt;eof()) { </p> <blockquote> <p> boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; ... </p> </blockquote> <p> } </p> <p> If the socket stream close unexpectedly, then the program goes to fault. </p> <p> It seems that moving the check for stream failure after the data reads in the basic_text_iprimitive.hpp file fixes the problem. </p> <p> Thanks </p> en-us Boost C++ Libraries /htdocs/site/boost.png https://svn.boost.org/trac10/ticket/3650 Trac 1.4.3 Steven Watanabe Fri, 20 Nov 2009 20:37:59 GMT component changed; owner set https://svn.boost.org/trac10/ticket/3650#comment:1 https://svn.boost.org/trac10/ticket/3650#comment:1 <ul> <li><strong>owner</strong> set to <span class="trac-author">Robert Ramey</span> </li> <li><strong>component</strong> <span class="trac-field-old">None</span> → <span class="trac-field-new">serialization</span> </li> </ul> Ticket Robert Ramey Sat, 28 Nov 2009 18:55:03 GMT <link>https://svn.boost.org/trac10/ticket/3650#comment:2 </link> <guid isPermaLink="false">https://svn.boost.org/trac10/ticket/3650#comment:2</guid> <description> <p> Hmmm - I'm not sure that is the correct fix. </p> <p> wouldn't it be better to use something like: </p> <p> boost::archive::text_iarchive ia(*_stream); while(! _stream-&gt;eof() &amp;&amp; ! _stream-&gt;fail() ) { </p> <blockquote> <p> boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; ... </p> </blockquote> <p> } </p> <p> I'm reluctant to add "too much" code in the depths of the library. </p> <p> Robert Ramey </p> </description> <category>Ticket</category> </item> <item> <dc:creator>Doug Wallas</dc:creator> <pubDate>Mon, 30 Nov 2009 11:28:10 GMT</pubDate> <title/> <link>https://svn.boost.org/trac10/ticket/3650#comment:3 </link> <guid isPermaLink="false">https://svn.boost.org/trac10/ticket/3650#comment:3</guid> <description> <p> The problem seems to be on the &gt;&gt; operator. The library do read from the stream, but does not check after reading that the stream had not encoutered an error while reading. The &gt;&gt; operator then starts creating a new object from what he just read and sigfaults :( </p> <p> I may be wrong, but i think the fail() is updated after a read, so the check on _stream-&gt;fail() would be ok (the library already does one in internal) and the crash would still occur. </p> </description> <category>Ticket</category> </item> <item> <dc:creator>Robert Ramey</dc:creator> <pubDate>Mon, 30 Nov 2009 17:27:03 GMT</pubDate> <title>status, type changed; resolution set https://svn.boost.org/trac10/ticket/3650#comment:4 https://svn.boost.org/trac10/ticket/3650#comment:4 <ul> <li><strong>status</strong> <span class="trac-field-old">new</span> → <span class="trac-field-new">closed</span> </li> <li><strong>type</strong> <span class="trac-field-old">Bugs</span> → <span class="trac-field-new">Feature Requests</span> </li> <li><strong>resolution</strong> → <span class="trac-field-new">wontfix</span> </li> </ul> <p> The reason that I did it the way I did was to permit the user code to handle the fail case. If I throw an exception after each operation, then the user can't make code like </p> <pre class="wiki">boost::archive::text_iarchive ia(*_stream); do{ boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; ... }while(! _stream-&gt;eof() &amp;&amp; ! _stream-&gt;fail() ) { </pre><p> But would be obligated to write exception handling code. If you really want things to operate this way, you can write </p> <pre class="wiki">boost::archive::text_iarchive ia(*_stream); do{ boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; ... if(_stream-&gt;fail()) throw ... }while(! _stream-&gt;eof()) { </pre><p> So the current situation leaves more flexibility to the user. </p> <p> Robert Ramey </p> Ticket anonymous Tue, 01 Dec 2009 14:25:59 GMT <link>https://svn.boost.org/trac10/ticket/3650#comment:5 </link> <guid isPermaLink="false">https://svn.boost.org/trac10/ticket/3650#comment:5</guid> <description> <p> Hello, I understand your point but the library sigfaults on the &gt;&gt; operator... So i think it's not possible for the user code to handle it :( </p> <pre class="wiki"> boost::archive::text_iarchive ia(*_stream); do{ boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; // sigfaults if(_stream-&gt;fail()) // Wont be called throw ... }while(! _stream-&gt;eof()) { </pre><p> Thanks for your time looking at the problem. </p> <p> Replying to <a class="ticket" href="https://svn.boost.org/trac10/ticket/3650#comment:4" title="Comment 4">ramey</a>: </p> <blockquote class="citation"> <p> The reason that I did it the way I did was to permit the user code to handle the fail case. If I throw an exception after each operation, then the user can't make code like </p> <pre class="wiki">boost::archive::text_iarchive ia(*_stream); do{ boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; ... }while(! _stream-&gt;eof() &amp;&amp; ! _stream-&gt;fail() ) { </pre><p> But would be obligated to write exception handling code. If you really want things to operate this way, you can write </p> <pre class="wiki">boost::archive::text_iarchive ia(*_stream); do{ boost::shared_ptr&lt;Message&gt; msg; ia &gt;&gt; msg; ... if(_stream-&gt;fail()) throw ... }while(! _stream-&gt;eof()) { </pre><p> So the current situation leaves more flexibility to the user. </p> <p> Robert Ramey </p> </blockquote> </description> <category>Ticket</category> </item> <item> <dc:creator>anonymous</dc:creator> <pubDate>Fri, 04 Dec 2009 06:46:33 GMT</pubDate> <title>status, type changed; resolution deleted https://svn.boost.org/trac10/ticket/3650#comment:6 https://svn.boost.org/trac10/ticket/3650#comment:6 <ul> <li><strong>status</strong> <span class="trac-field-old">closed</span> → <span class="trac-field-new">reopened</span> </li> <li><strong>type</strong> <span class="trac-field-old">Feature Requests</span> → <span class="trac-field-new">Bugs</span> </li> <li><strong>resolution</strong> <span class="trac-field-deleted">wontfix</span> </li> </ul> <p> I just seen that the type was changed to feature request... The serialization library just crashes i dont think it can be considered as a feature request... </p> Ticket Robert Ramey Sun, 06 Dec 2009 22:12:33 GMT status changed; resolution set https://svn.boost.org/trac10/ticket/3650#comment:7 https://svn.boost.org/trac10/ticket/3650#comment:7 <ul> <li><strong>status</strong> <span class="trac-field-old">reopened</span> → <span class="trac-field-new">closed</span> </li> <li><strong>resolution</strong> → <span class="trac-field-new">wontfix</span> </li> </ul> <pre class="wiki"> boost::archive::text_iarchive ia(*_stream); do{ boost::shared_ptr&lt;Message&gt; msg; // check here that the stream is OK. That is, if the stream // has been unexpected closed - deal with it here! if(_stream-&gt;eof() or stream-&gt; ?) break; ia &gt;&gt; msg; // sigfaults if(_stream-&gt;fail()) // Wont be called throw ... }while(! _stream-&gt;eof()) { </pre> Ticket anonymous Mon, 07 Dec 2009 13:14:02 GMT status changed; resolution deleted https://svn.boost.org/trac10/ticket/3650#comment:8 https://svn.boost.org/trac10/ticket/3650#comment:8 <ul> <li><strong>status</strong> <span class="trac-field-old">closed</span> → <span class="trac-field-new">reopened</span> </li> <li><strong>resolution</strong> <span class="trac-field-deleted">wontfix</span> </li> </ul> <p> It wouldnt work since "&gt;&gt;" is blocking so your checks could be OK, but it would still sigfaults on the "&gt;&gt;" operand as i mentioned before. </p> <p> If the stream is closed while waiting on the &gt;&gt; operand, a modification of the library is necessary or there's no other way (i could think of) to catch that kind of error. </p> Ticket Robert Ramey Wed, 30 Dec 2009 18:11:14 GMT status, type changed; resolution set https://svn.boost.org/trac10/ticket/3650#comment:9 https://svn.boost.org/trac10/ticket/3650#comment:9 <ul> <li><strong>status</strong> <span class="trac-field-old">reopened</span> → <span class="trac-field-new">closed</span> </li> <li><strong>type</strong> <span class="trac-field-old">Bugs</span> → <span class="trac-field-new">Feature Requests</span> </li> <li><strong>resolution</strong> → <span class="trac-field-new">wontfix</span> </li> </ul> <p> The library has to assume that the stream remains open while an archive is being saved. This is not an unreasonable expectation. </p> <p> basically the best way to handle this would be to trap the situation where the stream closes and not make any serialization library calls when this is detected. </p> <p> In any case, the library won't be changing. </p> <p> Robert Ramey </p> Ticket Vladimir Prus Thu, 31 Dec 2009 08:44:13 GMT status changed; resolution deleted https://svn.boost.org/trac10/ticket/3650#comment:10 https://svn.boost.org/trac10/ticket/3650#comment:10 <ul> <li><strong>status</strong> <span class="trac-field-old">closed</span> → <span class="trac-field-new">reopened</span> </li> <li><strong>resolution</strong> <span class="trac-field-deleted">wontfix</span> </li> </ul> <p> Robert, I don't understand your position here. The stream can unexpectedly fail at any moment, and stream do fail in properly written programs. Even if the user checks that stream is OK right before calling operator&lt;&lt;, you can get a stream error -- e.g. a network connection can close immediately after user's check is executed. It does not seem that crashing in face of a natural situation is desirable. Could you clarify further? </p> <p> Thanks, Volodya </p> Ticket Francois Valette Thu, 21 Jan 2010 07:46:33 GMT <link>https://svn.boost.org/trac10/ticket/3650#comment:11 </link> <guid isPermaLink="false">https://svn.boost.org/trac10/ticket/3650#comment:11</guid> <description> <p> Hello, We encounter the same problem sometimes when our stream failed unexpectedly. The occurence is pretty rare so it was hard to find the cause... Thx for pointing out the fix Doug. </p> </description> <category>Ticket</category> </item> </channel> </rss>