3 <title>Libstdc++-porting-howto</title>
4 <meta content="DocBook XSL Stylesheets V1.16" name="generator">
6 <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
7 <div class="article" id="libstdporting">
8 <div class="titlepage">
10 <a name="libstdporting">Libstdc++-porting-howto</a>
12 <h3 class="author">Felix Natter</h3>
14 This document can be distributed under the FDL
15 (<a href="http://www.gnu.org">www.gnu.org</a>)
17 <p class="pubdate">what kind of a date ? I don't drink !</p>
18 <div class="revhistory">
19 <table width="100%" border="1">
21 <th colspan="3" valign="top" align="left"><b>Revision History</b></th>
24 <td align="left">Revision 0.5</td><td align="left">Thu Jun 1 13:06:50 2000</td><td align="left">fnatter</td>
27 <td colspan="3" align="left">First docbook-version.</td>
30 <td align="left">Revision 0.8</td><td align="left">Sun Jul 30 20:28:40 2000</td><td align="left">fnatter</td>
33 <td colspan="3" align="left">First released version using docbook-xml
34 + second upload to libstdc++-page.
38 <td align="left">Revision 0.9</td><td align="left">Wed Sep 6 02:59:32 2000</td><td align="left">fnatter</td>
41 <td colspan="3" align="left">5 new sections.</td>
45 <div class="abstract">
47 <a name="N2688"></a><b>Abstract</b>
50 Some notes on porting applications from libstdc++-2.90 (or earlier
51 versions) to libstdc++-v3. Not speaking in terms of the GNU libstdc++
52 implementations, this means porting from earlier versions of the
53 C++-Standard to ISO 14882.
60 <b>Table of Contents</b>
63 <dt>1. <a href="#sec-nsstd">Namespace std::</a>
67 <dt>1.1.1. <a href="#sec-gtkmm-hack">Using <i>namespace
68 composition</i> if the project uses a separate
71 <dt>1.1.2. <a href="#sec-emptyns">Defining an empty namespace std</a>
73 <dt>1.1.3. <a href="#sec-avoidfqn">Avoid to use fully qualified names
74 (i.e. std::string)</a>
76 <dt>1.1.4. <a href="#sec-osprojects">How some open-source-projects deal
81 <dt>2. <a href="#sec-nocreate">there is no ios::nocreate/ios::noreplace
84 <dt>3. <a href="#sec-stream::attach"><b>stream::attach(int
85 fd)</b> is not in the standard any more</a>
87 <dt>4. <a href="#sec-headers">The new headers</a>
91 <dt>4.4.1. <a href="#sec-cheaders">New headers replacing C-headers</a>
93 <dt>4.4.2. <a href="#sec-fstream-header">
94 <tt><fstream></tt> does
95 not define <b>std::cout</b>,
96 <b>std::cin</b> etc.</a>
100 <dt>5. <a href="#sec-iterators">Iterators</a>
102 <dt>6. <a href="#sec-macros">
103 Libc-macros (i.e. <b>isspace</b> from
104 <tt><cctype></tt>)</a>
106 <dt>7. <a href="#sec-stream-state">
110 <dt>8. <a href="#sec-vector-at">vector::at is missing (i.e. gcc 2.95.2)</a>
112 <dt>9. <a href="#sec-eof">Using std::char_traits<char>::eof()</a>
114 <dt>10. <a href="#sec-string-clear">Using string::clear()/string::erase()</a>
116 <dt>11. <a href="#sec-stringstream">Using stringstream's</a>
118 <dt>12. <a href="#sec-about">About...</a>
123 In the following, when I say portable, I will refer to "portable among ISO
124 14882-implementations". On the other hand, if I say "backportable" or
125 "conservative", I am talking about "compiles with older
126 libstdc++-implementations".
128 <div class="section" id="sec-nsstd">
129 <h2 class="title" style="clear: all">
130 <a name="sec-nsstd"><b>1. Namespace std::</b></a>
133 The latest C++-standard (ISO-14882) requires that the standard
134 C++-library is defined in namespace std::. Thus, in order to use
135 classes from the standard C++-library, you can do one of three
137 <div class="itemizedlist">
141 <p>wrap your code in <b>namespace std {
142 ... }</b> => This is not an option because only symbols
143 from the standard c++-library are defined in namespace std::.
149 <i>using-declaration</i> in your source (either
150 <b>using namespace std;</b> or i.e. <b>using
151 std::string;</b>) => works well for source-files, but
152 cannot be used in header-files.
157 <p>use a <i>fully qualified name</i> for
158 each libstdc++-symbol (i.e. <b>std::string</b>,
159 <b>std::cout</b>) => can always be used
166 Because there are many compilers which still use an implementation
167 that does not have the standard C++-library in namespace
168 <b>std::</b>, some care is required to support these as
172 Namespace back-portability-issues are generally not a problem with
173 g++, because versions of g++ that do not have libstdc++ in
174 <b>std::</b> use <b>-fno-honor-std</b>
175 (ignore <b>std::</b>, <b>:: = std::</b>) by
176 default. That is, the responsibility for enabling or disabling
177 <b>std::</b> is on the user; the maintainer does not have
178 to care about it. This probably applies to some other compilers as
182 The following sections list some possible solutions to support compilers
183 that cannot ignore std::.
185 <div class="section" id="sec-gtkmm-hack">
187 <a name="sec-gtkmm-hack"><b>1.1.1. Using <i>namespace
188 composition</i> if the project uses a separate
192 <a href="http://gtkmm.sourceforge.net">Gtk--</a> defines
193 most of its classes in namespace Gtk::. Thus, it was possible to
194 adapt Gtk-- to namespace std:: by using a C++-feature called
195 <i>namespace composition</i>. This is what happens if
196 you put a <i>using</i>-declaration into a
197 namespace-definition: the imported symbol(s) gets imported into the
198 currently active namespace(s). For example:
199 <pre class="programlisting">
205 In this example, <b>std::string</b> gets imported into
206 namespace Gtk::. The result is that you don't have to use
207 <b>std::string</b> in this header, but still
208 <b>std::string</b> does not get imported into
209 user-space (the global namespace ::) unless the user does
210 <b>using namespace Gtk;</b> (which is not recommended
211 practice for Gtk--, so it is not a problem). Additionally, the
212 <b>using</b>-declarations are wrapped in macros that
213 are set based on autoconf-tests to either "" or i.e. <b>using
214 std::string;</b> (depending on whether the system has
215 libstdc++ in <b>std::</b> or not). (ideas from
216 <tt><<a href="mailto:llewelly@dbritsch.dsl.xmission.com">llewelly@dbritsch.dsl.xmission.com</a>></tt>, Karl Nelson
217 <tt><<a href="mailto:kenelson@ece.ucdavis.edu">kenelson@ece.ucdavis.edu</a>></tt>)
220 <div class="section" id="sec-emptyns">
222 <a name="sec-emptyns"><b>1.1.2. Defining an empty namespace std</b></a>
225 By defining an (empty) namespace <b>std::</b> before
226 using it, you avoid getting errors on systems where no part of the
227 library is in namespace std:
228 <pre class="programlisting">
234 <div class="section" id="sec-avoidfqn">
236 <a name="sec-avoidfqn"><b>1.1.3. Avoid to use fully qualified names
237 (i.e. std::string)</b></a>
240 If some compilers complain about <b>using
241 std::string;</b>, and if the "hack" for gtk-- mentioned above
242 does not work, then it might be a good idea to define a macro
243 NS_STD, which is defined to either "" or "std"
244 based on an autoconf-test. Then you should be able to use
245 <b>NS_STD::string</b>, which will evaluate to
246 <b>::string</b> ("string in the global namespace") on
247 systems that do not put string in std::. (This is untested)
250 <div class="section" id="sec-osprojects">
252 <a name="sec-osprojects"><b>1.1.4. How some open-source-projects deal
256 This information was gathered around May 2000. It may not be correct
257 by the time you read this.
261 <a name="N2901"></a><b>Table 1. Namespace std:: in Open-Source programs</b>
270 <td><a href="http://www.clanlib.org">clanlib</a></td><td>usual</td>
273 <td><a href="http://pingus.seul.org">pingus</a></td><td>usual</td>
276 <td><a href="http://www.mozilla.org">mozilla</a></td><td>usual</td>
279 <td><a href="http://www.mnemonic.org">mnemonic</a></td><td>none</td>
282 <td><a href="http://libsigc.sourceforge.net">
283 libsigc++</a></td><td>conservative-impl</td>
290 <a name="N2978"></a><b>Table 2. Notations for categories</b>
299 <td>usual</td><td>mostly fully qualified names and some
300 using-declarations (but not in headers)</td>
303 <td>none</td><td>no namespace std at all</td>
306 <td>conservative-impl</td><td>wrap all
307 namespace-handling in macros to support compilers without
308 namespace-support (no libstdc++ used in headers)</td>
314 As you can see, this currently lacks an example of a project which
315 uses libstdc++-symbols in headers in a back-portable way (except
316 for Gtk--: see the <a href="#"></a>).
320 <div class="section" id="sec-nocreate">
321 <h2 class="title" style="clear: all">
322 <a name="sec-nocreate"><b>2. there is no ios::nocreate/ios::noreplace
326 I have seen <b>ios::nocreate</b> being used for input-streams,
327 most probably because the authors thought it would be more correct
328 to specify nocreate "explicitly". So you can simply leave it out
332 For output streams, "nocreate" is probably the default, unless you
333 specify <b>std::ios::trunc</b> ? To be safe, you can open
334 the file for reading, check if it has been opened, and then decide
335 whether you want to create/replace or not. To my knowledge, even
336 older implementations support <b>app</b>,
337 <b>ate</b> and <b>trunc</b> (except for
341 <div class="section" id="sec-stream::attach">
342 <h2 class="title" style="clear: all">
343 <a name="sec-stream::attach"><b>3. <b>stream::attach(int
344 fd)</b> is not in the standard any more</b></a>
347 When using libstdc++-v3, you can use
348 <div id="N3082" class="funcsynopsis">
352 <pre class="funcsynopsisinfo">
353 #include <fstream>
356 <code><code class="funcdef">int <b class="fsfunc">basic_filebuf</b></code>(<var class="pdparam">__fd</var>, <var class="pdparam">__name</var>, <var class="pdparam">__mode</var>);<br>int <var class="pdparam">__fd</var>;<br>const char* <var class="pdparam">__name</var>;<br>ios_base::openmode <var class="pdparam">__mode</var>;</code>
361 For a portable solution (if there is one), you need to implement a
362 subclass of <b>streambuf</b> which opens a file given a
363 descriptor, and then pass an instance of this to the
364 stream-constructor (from the Josuttis-book).
367 <div class="section" id="sec-headers">
368 <h2 class="title" style="clear: all">
369 <a name="sec-headers"><b>4. The new headers</b></a>
372 All new headers can be seen in this <a href="../../testsuite/17_intro/headers.cc">source-code</a>.
375 I think it is a problem for libstdc++-v3 to add links or wrappers
376 for the old headers, because the implementation has changed, and
377 the header name-changes indicate this. It might be preferable to
378 use the new headers and tell users of old compilers that they
379 should create links (which is what they will have to do sometime
382 <div class="section" id="sec-cheaders">
384 <a name="sec-cheaders"><b>4.4.1. New headers replacing C-headers</b></a>
387 You should not use the C-headers (except for system-level headers)
388 from C++ programs. Instead, you should use a set of headers that
389 are named by prepending 'c' and, as usual, ommiting the extension
390 (.h). For example, instead of using <tt><math.h></tt>, you should use <tt><cmath></tt>. The standard
391 specifies that if you include the C-style header (<tt><math.h></tt> in this case), the symbols
392 will be available both in the global namespace and in namespace
393 <b>std::</b> (libstdc++-v3, version 2.90.8 currently
394 puts them in <b>std::</b> only) On the other hand, if
395 you include only the new header (i.e. <tt><pcmath></tt>), the symbols will only be
396 defined in namespace <b>std::</b> (and macros will be
397 converted to inline-functions).
400 For more information on this, and for information on how the GNU
401 C++ implementation reuses ("shadows") the C library-functions, have
402 a look at <a href="http://www.cantrip.org/cheaders.html">
406 <div class="section" id="sec-fstream-header">
408 <a name="sec-fstream-header"><b>4.4.2.
409 <tt><fstream></tt> does
410 not define <b>std::cout</b>,
411 <b>std::cin</b> etc.</b></a>
414 In previous versions of the standard, <tt><fstream.h></tt>, <tt><ostream.h></tt> and <tt><istream.h></tt> used to define
415 <b>cout</b>, <b>cin</b> and so on. Because
416 of the templatized iostreams in libstdc++-v3, you need to include
417 <tt><iostream></tt>
418 explicitly to define these.
422 <div class="section" id="sec-iterators">
423 <h2 class="title" style="clear: all">
424 <a name="sec-iterators"><b>5. Iterators</b></a>
427 The following are not proper uses of iterators, but may be working
428 fixes for existing uses of iterators.
429 <div class="itemizedlist">
434 <b>ostream::operator<<(iterator)</b> to
435 print the address of the iterator => use
436 <b>operator<< &*iterator</b> instead ?
441 <p>you cannot clear an iterator's reference
442 (<b>iterator = 0</b>) => use
443 <b>iterator = iterator_type();</b> ?
449 <b>if (iterator)</b> won't work any
450 more => use <b>if (iterator != iterator_type())</b>
457 <div class="section" id="sec-macros">
458 <h2 class="title" style="clear: all">
459 <a name="sec-macros"><b>6.
460 Libc-macros (i.e. <b>isspace</b> from
461 <tt><cctype></tt>)</b></a>
464 Glibc 2.0.x and 2.1.x define the <tt><ctype.h></tt> -functionality as
465 macros (isspace, isalpha etc.). Libstdc++-v3 "shadows" these macros
466 as described in the <a href="#"></a>.
469 Older implementations of libstdc++ (g++-2 for egcs 1.x and g++-3
470 for gcc 2.95.2), however, keep these functions as macros, and so it
471 is not back-portable to use fully qualified names. For example:
472 <pre class="programlisting">
473 #include <cctype>
474 int main() { std::isspace('X'); }
476 will result in something like this (unless using g++-v3):
477 <pre class="programlisting">
478 std:: (__ctype_b[(int) ( ( 'X' ) )] & (unsigned short int)
483 One solution I can think of is to test for -v3 using
484 autoconf-macros, and define macros for each of the C-functions
485 (maybe that is possible with one "wrapper" macro as well ?).
488 Another solution which would fix g++ is to tell the user to modify a
489 header-file so that g++-2 (egcs 1.x) and g++-3 (gcc 2.95.2) define a
490 macro which tells <tt><ctype.h></tt> to define functions
492 <pre class="programlisting">
493 // This keeps isalnum, et al from being propagated as macros.
498 [ now include <ctype.h> ]
502 Another problem arises if you put a <b>using namespace
503 std;</b> declaration at the top, and include <tt><ctype.h></tt>. This will result in
504 ambiguities between the definitions in the global namespace
505 (<tt><ctype.h></tt>) and the
506 definitions in namespace <b>std::</b>
507 (<b><cctype></b>).
510 The solution to this problem was posted to the libstdc++-v3
512 Benjamin Kosnik <tt><<a href="mailto:bkoz@redhat.com">bkoz@redhat.com</a>></tt> writes:
514 --enable-cshadow-headers is currently broken. As a result, shadow
515 headers are not being searched....
519 <div class="section" id="sec-stream-state">
520 <h2 class="title" style="clear: all">
521 <a name="sec-stream-state"><b>7.
526 At least some older implementations don't have
527 <b>std::ios_base</b>, so you should use
528 <b>std::ios::badbit</b>, <b>std::ios::failbit</b>
529 and <b>std::ios::eofbit</b> and
530 <b>std::ios::goodbit</b>.
533 <div class="section" id="sec-vector-at">
534 <h2 class="title" style="clear: all">
535 <a name="sec-vector-at"><b>8. vector::at is missing (i.e. gcc 2.95.2)</b></a>
538 For my use, I added it to
539 <tt>prefix/include/g++-3/stl_vector.h</tt>:
540 <pre class="programlisting">
541 reference operator[](size_type __n) { return *(begin() + __n); }
542 reference at(size_type __n) {
543 if (begin() + __n >= end())
544 throw out_of_range("vector::at");
545 return *(begin() + __n);
547 const_reference operator[](size_type __n) const { return *(begin() + __n); }
548 const_reference at(size_type __n) const {
549 if (begin() + __n >= end())
550 throw out_of_range("vector::at");
551 return *(begin() + __n);
556 <div class="section" id="sec-eof">
557 <h2 class="title" style="clear: all">
558 <a name="sec-eof"><b>9. Using std::char_traits<char>::eof()</b></a>
561 <pre class="programlisting">
562 #ifdef HAVE_CHAR_TRAITS
563 #define CPP_EOF std::char_traits<char>::eof()
570 <div class="section" id="sec-string-clear">
571 <h2 class="title" style="clear: all">
572 <a name="sec-string-clear"><b>10. Using string::clear()/string::erase()</b></a>
575 There are two functions for deleting the contents of a string:
576 <b>clear</b> and <b>erase</b> (the latter
578 <pre class="programlisting">
580 clear() { _M_mutate(0, this->size(), 0); }
582 <pre class="programlisting">
584 erase(size_type __pos = 0, size_type __n = npos)
586 return this->replace(_M_check(__pos), _M_fold(__pos, __n),
587 _M_data(), _M_data());
590 The implementation of <b>erase</b> seems to be more
591 complicated (from libstdc++-v3), but <b>clear</b> is not
592 implemented in gcc 2.95.2's libstdc++, so you should use
593 <b>erase</b> (which is probably faster than
594 <b>operator=(charT*)</b>).
597 <div class="section" id="sec-stringstream">
598 <h2 class="title" style="clear: all">
599 <a name="sec-stringstream"><b>11. Using stringstream's</b></a>
602 Libstdc++-v3 includes the new
603 <b>i/ostringstream</b>-classes, (<tt><sstream></tt>), but with older
604 implementations you still have to use <b>i/ostrstream</b>
605 (<tt><strstream></tt>):
606 <pre class="programlisting">
608 #include <sstream>
610 #include <strstream>
613 <div class="itemizedlist">
617 <p> <b>strstream</b> is considered to be
623 <p> <b>strstream</b> is limited to
629 <p> with <b>ostringstream</b> you don't
630 have to take care of terminating the string or freeing its
636 <p> <b>istringstream</b> can be re-filled
637 (clear(); str(input);)
644 You can then use output-stringstreams like this:
645 <pre class="programlisting">
647 std::ostringstream oss;
651 oss << "Name=" << m_name << ", number=" << m_number << std::endl;
654 oss << std::ends; // terminate the char*-string
656 // str() returns char* for ostrstream and a string for ostringstream
657 // this also causes ostrstream to think that the buffer's memory
659 m_label.set_text(oss.str());
661 // let the ostrstream take care of freeing the memory
667 Input-stringstreams can be used similarly:
668 <pre class="programlisting">
672 std::istringstream iss(input);
674 std::istrstream iss(input.c_str());
679 One (the only?) restriction is that an istrstream cannot be re-filled:
680 <pre class="programlisting">
681 std::istringstream iss(numerator);
683 // this is not possible with istrstream
685 iss.str(denominator);
688 If you don't care about speed, you can put these conversions in
690 <pre class="programlisting">
691 template <class X>
692 void fromString(const string& input, X& any)
695 std::istringstream iss(input);
697 std::istrstream iss(input.c_str());
702 throw runtime_error(..)
708 I have read the Josuttis book on Standard C++, so some information
709 comes from there. Additionally, there is information in
710 "info iostream", which covers the old implementation that gcc 2.95.2
714 <div class="section" id="sec-about">
715 <h2 class="title" style="clear: all">
716 <a name="sec-about"><b>12. About...</b></a>
719 Please send any experience, additions, corrections or questions to
720 <a href="mailto:fnatter@gmx.net">fnatter@gmx.net</a> or for
721 discussion to the libstdc++-v3-mailing-list.