]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
re PR rtl-optimization/7291 (off-by-one in generated inline bzero code for i386 ...
authorJakub Jelinek <jakub@gcc.gnu.org>
Fri, 26 Jul 2002 23:23:45 +0000 (01:23 +0200)
committerJakub Jelinek <jakub@gcc.gnu.org>
Fri, 26 Jul 2002 23:23:45 +0000 (01:23 +0200)
gcc/ChangeLog

2002-07-24  Frank van der Linden  <fvdl@wasabisystems.com>

PR optimization/7291
* config/i386/i386.c (ix86_expand_clrstr): Fix bzero alignment
problem on x86_64.

2002-05-16  Jason Merrill  <jason@redhat.com>

* config/mips/mips.c (mips_output_external): Don't do sdata
optimization for a variable with DECL_COMDAT set.

2002-01-03  Jakub Jelinek  <jakub@redhat.com>

* c-decl.c (build_compound_literal): Set decl TREE_READONLY from TYPE.

* c-decl.c (build_compound_literal): Defer compound literal decls
until until file end to emit them only if they are actually used.

gcc/cp/ChangeLog

2002-07-17  Scott Snyder <snyder@fnal.gov>

PR c++/7320
* rtti.c (get_tinfo_decl): Set DECL_COMDAT.

2002-07-05  Nathan Sidwell  <nathan@codesourcery.com>

Repair damage on weak-impared targets caused by my previous patch.
* cp-tree.h (import_export_tinfo): Add parameter.
* decl2.c (import_export_tinfo): Add parameter, post adjust
DECL_COMDAT.
* rtti.c (emit_tinfo_decl): DECL_COMDAT is (nearly) always setup by
import_export_tinfo.

2002-06-30  Nathan Sidwell  <nathan@codesourcery.com>

* cp-tree.h (CPTI_TINFO_DECL_TYPE): Replace with ...
(CPTI_TYPE_INFO_PTR_TYPE): ... this.
(tinfo_decl_type): Replace with ...
(type_info_ptr_type): ... this.
(import_export_tinfo): Declare.
(tinfo_decl_p): Rename to ...
(unemitted_tinfo_decl_p): ... this.
* decl2.c (import_export_decl): Break out tinfo handling into ...
(import_export_tinfo): ... here. New function.
(finish_file): Adjust.
* rtti.c (TINFO_REAL_NAME): New macro.
(init_rtti_processing): Create the tinfo types.
(get_tinfo_decl_dynamic): Use type_info_ptr_type, get_tinfo_ptr.
(get_tinfo_decl): Adjust.
(get_tinfo_ptr): New function.
(get_type_id): Use it.
(tinfo_base_init): Create vtable decl here, if it doesn't exist.
(ptr_initializer): Use get_tinfo_ptr.
(ptm_initializer): Likewise.
(synthesize_tinfo_var): Break into ...
(get_pseudo_ti_init): ... this. Just create the initializer.
(get_pseudo_ti_desc): .. and this.
(create_real_tinfo_var): Remove.
(create_pseudo_type_info): Don't create the vtable decl here.
(get_vmi_pseudo_type_info): Remove.
(create_tinfo_types): Adjust.
(tinfo_decl_p): Rename to ...
(unemitted_tinfo_decl_p): ... here. Adjust.
(emit_tinfo_decl): Adjust. Create the initializer.

2002-06-14  Jason Merrill  <jason@redhat.com>

C++ ABI changes.
* class.c (build_base_field): Set DECL_PACKED.
(layout_class_type): Don't use tail padding of PODs.
* mangle.c (write_unqualified_name): Fix template conversion op
mangling.

2002-05-18  Jason Merrill  <jason@redhat.com>

PR c++/6611
* decl2.c (import_export_decl): If we clear
DECL_NOT_REALLY_EXTERN, make sure DECL_EXTERNAL is set.

2002-05-14  Jason Merrill  <jason@redhat.com>

* rtti.c (get_tinfo_decl): Don't call comdat_linkage.
Do set DECL_COMDAT.
(synthesize_tinfo_var): Take the public decl.
(create_real_tinfo_var): Likewise.  Check DECL_COMDAT.
(emit_tinfo_decl): Adjust.  Call import_export_decl.
* decl2.c (import_export_decl): Simplify tinfo decl handling.

gcc/testsuite/ChangeLog

2002-07-24  Roger Sayle  <roger@eyesopen.com>

* gcc.c-torture/execute/memset-3.c: New testcase.

2002-06-14  Jason Merrill  <jason@redhat.com>

* g++.dg/abi/layout1.C: New test.
* g++.dg/abi/layout2.C: New test.
* g++.dg/abi/mangle8.C: New test.

2002-05-14  Jason Merrill  <jason@redhat.com>

* g++.dg/abi/rtti1.C: New test.

2002-01-03  Jakub Jelinek  <jakub@redhat.com>

* gcc.dg/gnu89-init-2.c: New test.

libstdc++-v3/ChangeLog

2002-07-26  Phil Edwards  <pme@gcc.gnu.org>

* libsupc++/new (placement delete):  Remove unused paramater names.

2002-07-25  Benjamin Kosnik  <bkoz@redhat.com>

PR libstdc++/7216
* include/std/std_istream.h (basic_iostream): Add typedefs for
char_type, int_type, pos_type, off_type, and traits_type.
* testsuite/27_io/iostream.cc (test01): Add typedef tests.
* testsuite/27_io/istream.cc: Same.
* testsuite/27_io/ostream.cc: Same.
* testsuite/27_io/filebuf.cc: Same.
* testsuite/27_io/stringbuf.cc: Replace content, move to...
* testsuite/27_io/stringbuf_members.cc: ...here.
* testsuite/27_io/streambuf.cc: Replace content, move to...
* testsuite/27_io/streambuf_members.cc: ...here.
* testsuite/27_io/stringstream.cc: Replace content, move to...
* testsuite/27_io/stringstream_members.cc: ...here.
* testsuite/27_io/ios.cc: New file.
* testsuite/27_io/fstream.cc: New file.
* testsuite/27_io/ifstream.cc: New file.
* testsuite/27_io/ofstream.cc: New file.
* testsuite/27_io/istringstream.cc: New file.
* testsuite/27_io/ostringstream.cc: New file.

2002-07-25  Benjamin Kosnik  <bkoz@redhat.com>

PR libstdc++/7220
* include/bits/istream.tcc (istream::ignore): Don't extract on
zero.
* testsuite/27_io/istream_unformatted.cc (test10): Add.

2002-07-24  Benjamin Kosnik  <bkoz@redhat.com>

PR libstdc++/7222
* src/locale.cc (locale::locale(const char*)): Use setlocale NULL.
* testsuite/22_locale/ctor_copy_dtor.cc (test02): New.

2002-07-24  Benjamin Kosnik  <bkoz@redhat.com>

PR libstdc++/7286
* libsupc++/new: Add placement delete.
* testsuite/18_support/new_delete_placement.cc: New.

2002-07-07  Paolo Carlini  <pcarlini@unitus.it>

PR libstdc++/7186
* include/bits/stl_deque.h (_Deque_iterator::operator-):
Make non-member, as already happens for the comparison
operators in accord with DR179 (Ready).
* testsuite/23_containers/deque_operators.cc: Add test02.

2002-07-04  Benjamin Kosnik  <bkoz@redhat.com>
    Jack Reeves  <jackw_reeves@hotmail.com>

* include/std/std_streambuf.h (basic_streambuf::_M_buf): Change to
size_t, from int_type.
  (basic_streambuf::_M_buf_size_opt): Same.
  (basic_streambuf::_S_pback_sizex): Same.
* include/bits/streambuf.tcc: Same.
* include/std/std_streambuf.h (basic_streambuf::snextc): Use
eq_int_type.
(basic_streambuf::uflow): Same.
* include/bits/sstream.tcc (basic_stringbuf::overflow): Use
to_char_type.
* include/bits/basic_ios.tcc (basic_ios::init): Use _CharT().
* include/bits/streambuf.tcc (basic_streambuf::xsgetn): Use
eq_int_type.
(basic_streambuf::xsputn): Same.
(__copy_streambufs): Same.

2002-07-02  Paolo Carlini  <pcarlini@unitus.it>

PR libstdc++/6642
* include/bits/stl_iterator.h
(__normal_iterator::operator-(const __normal_iterator&)):
Make non-member, as already happens for the comparison
operators in accord with DR179 (Ready).
* testsuite/24_iterators/iterator.cc: Add test from the PR.

2002-07-02  Benjamin Kosnik  <bkoz@redhat.com>

PR libstdc++/6410
* include/bits/locale_facets.h (moneypunct::moneypunct): Add const
char* name parameter.
* config/locale/gnu/monetary_members.cc: Use it.
* config/locale/generic/monetary_members.cc: Same.
* src/localename.cc (_Impl::_Impl(const char*, size_t)): Use it.

2002-07-01  Benjamin Kosnik  <bkoz@redhat.com>

* configure.in (libtool_VERSION): Bump to 5:0:0.
* configure: Regenerate.

2002-05-19  Paolo Carlini  <pcarlini@unitus.it>

* testsuite/23_containers/deque_operators.cc (test01):
Fix minor typo in last commit.

2002-05-18  Paolo Carlini  <pcarlini@unitus.it>

PR libstdc++/6503
* include/bits/stl_deque.h (_Deque_iterator::operator==,
operator!=, operator<, operator>, operator>=, operator<=):
Make non-member functions, to allow comparing const and
non-const iterators in any order.
* testsuite/23_containers/deque_operators.cc: New testfile.

From-SVN: r55786

40 files changed:
gcc/ChangeLog
gcc/c-decl.c
gcc/config/i386/i386.c
gcc/config/mips/mips.c
gcc/cp/ChangeLog
gcc/cp/class.c
gcc/cp/cp-tree.h
gcc/cp/decl2.c
gcc/cp/mangle.c
gcc/cp/rtti.c
gcc/testsuite/ChangeLog
libstdc++-v3/ChangeLog
libstdc++-v3/config/locale/generic/monetary_members.cc
libstdc++-v3/config/locale/gnu/monetary_members.cc
libstdc++-v3/configure
libstdc++-v3/configure.in
libstdc++-v3/include/bits/basic_ios.tcc
libstdc++-v3/include/bits/istream.tcc
libstdc++-v3/include/bits/locale_facets.h
libstdc++-v3/include/bits/sstream.tcc
libstdc++-v3/include/bits/stl_deque.h
libstdc++-v3/include/bits/stl_iterator.h
libstdc++-v3/include/bits/streambuf.tcc
libstdc++-v3/include/std/std_istream.h
libstdc++-v3/include/std/std_streambuf.h
libstdc++-v3/libsupc++/new
libstdc++-v3/src/locale.cc
libstdc++-v3/src/localename.cc
libstdc++-v3/testsuite/22_locale/ctor_copy_dtor.cc
libstdc++-v3/testsuite/24_iterators/iterator.cc
libstdc++-v3/testsuite/27_io/filebuf.cc
libstdc++-v3/testsuite/27_io/iostream.cc
libstdc++-v3/testsuite/27_io/istream.cc
libstdc++-v3/testsuite/27_io/istream_unformatted.cc
libstdc++-v3/testsuite/27_io/ostream.cc
libstdc++-v3/testsuite/27_io/ostringstream_members.cc
libstdc++-v3/testsuite/27_io/streambuf.cc
libstdc++-v3/testsuite/27_io/stringbuf.cc
libstdc++-v3/testsuite/27_io/stringstream.cc
libstdc++-v3/testsuite/27_io/stringstream_members.cc

index d083356e321d9c395c31497b877b024b81d0270d..97bd68527f51c26c92b9c897c27e7cc489e69c7a 100644 (file)
@@ -1,3 +1,21 @@
+2002-07-24  Frank van der Linden  <fvdl@wasabisystems.com>
+
+       PR optimization/7291
+       * config/i386/i386.c (ix86_expand_clrstr): Fix bzero alignment
+       problem on x86_64.
+
+2002-05-16  Jason Merrill  <jason@redhat.com>
+
+       * config/mips/mips.c (mips_output_external): Don't do sdata
+       optimization for a variable with DECL_COMDAT set.
+
+2002-01-03  Jakub Jelinek  <jakub@redhat.com>
+
+       * c-decl.c (build_compound_literal): Set decl TREE_READONLY from TYPE.
+
+       * c-decl.c (build_compound_literal): Defer compound literal decls
+       until until file end to emit them only if they are actually used.
+
 2002-07-25  Release Manager
 
        * GCC 3.1.1 Released.
index a851ed99360080e9c6a0bd4193db147b27b3d0d9..a6e010bafe0fb19f8a84e81df74e088f86ad8182 100644 (file)
@@ -3911,6 +3911,7 @@ build_compound_literal (type, init)
   DECL_CONTEXT (decl) = current_function_decl;
   TREE_USED (decl) = 1;
   TREE_TYPE (decl) = type;
+  TREE_READONLY (decl) = TREE_READONLY (type);
   store_init_value (decl, init);
 
   if (TREE_CODE (type) == ARRAY_TYPE && !COMPLETE_TYPE_P (type))
@@ -3933,12 +3934,18 @@ build_compound_literal (type, init)
   if (TREE_STATIC (decl))
     {
       /* This decl needs a name for the assembler output.  We also need
-        a unique suffix to be added to the name, for which DECL_CONTEXT
-        must be set.  */
-      DECL_NAME (decl) = get_identifier ("__compound_literal");
-      DECL_CONTEXT (decl) = complit;
+        a unique suffix to be added to the name.  */
+      char *name;
+      extern int var_labelno;
+
+      ASM_FORMAT_PRIVATE_NAME (name, "__compound_literal", var_labelno);
+      var_labelno++;
+      DECL_NAME (decl) = get_identifier (name);
+      DECL_DEFER_OUTPUT (decl) = 1;
+      DECL_COMDAT (decl) = 1;
+      DECL_ARTIFICIAL (decl) = 1;
+      pushdecl (decl);
       rest_of_decl_compilation (decl, NULL, 1, 0);
-      DECL_CONTEXT (decl) = NULL_TREE;
     }
 
   return complit;
index a34831ed4c74f0a6ab9df2fbc8698aec448eb6c0..274c9a0632a9a8931277e560e4ab2080b3506785 100644 (file)
@@ -9505,7 +9505,7 @@ ix86_expand_clrstr (src, count_exp, align_exp)
                                 gen_rtx_SUBREG (SImode, zeroreg, 0)));
       if (TARGET_64BIT && (align <= 4 || count == 0))
        {
-         rtx label = ix86_expand_aligntest (countreg, 2);
+         rtx label = ix86_expand_aligntest (countreg, 4);
          emit_insn (gen_strsetsi (destreg,
                                   gen_rtx_SUBREG (SImode, zeroreg, 0)));
          emit_label (label);
index a230c9e32d166ae7e1554018ae217f265291a903..4c8bfb916e7975192d398802e13b3ddbe9deea3e 100644 (file)
@@ -5854,6 +5854,7 @@ mips_output_external (file, decl, name)
 
   if (TARGET_GP_OPT
       && TREE_CODE (decl) != FUNCTION_DECL
+      && !DECL_COMDAT (decl)
       && (len = int_size_in_bytes (TREE_TYPE (decl))) > 0
       && ((section_name = DECL_SECTION_NAME (decl)) == NULL
          || strcmp (TREE_STRING_POINTER (section_name), ".sbss") == 0
index d45bb09540d21473b7b9b57a944ae2b5e5e0b493..a226d36d01fbd26447abd4246527ab974563cfc2 100644 (file)
@@ -1,3 +1,72 @@
+2002-07-17  Scott Snyder <snyder@fnal.gov>
+
+       PR c++/7320
+       * rtti.c (get_tinfo_decl): Set DECL_COMDAT.
+
+2002-07-05  Nathan Sidwell  <nathan@codesourcery.com>
+
+       Repair damage on weak-impared targets caused by my previous patch.
+       * cp-tree.h (import_export_tinfo): Add parameter.
+       * decl2.c (import_export_tinfo): Add parameter, post adjust
+       DECL_COMDAT.
+       * rtti.c (emit_tinfo_decl): DECL_COMDAT is (nearly) always setup by
+       import_export_tinfo.
+
+2002-06-30  Nathan Sidwell  <nathan@codesourcery.com>
+
+       * cp-tree.h (CPTI_TINFO_DECL_TYPE): Replace with ...
+       (CPTI_TYPE_INFO_PTR_TYPE): ... this.
+       (tinfo_decl_type): Replace with ...
+       (type_info_ptr_type): ... this.
+       (import_export_tinfo): Declare.
+       (tinfo_decl_p): Rename to ...
+       (unemitted_tinfo_decl_p): ... this.
+       * decl2.c (import_export_decl): Break out tinfo handling into ...
+       (import_export_tinfo): ... here. New function.
+       (finish_file): Adjust.
+       * rtti.c (TINFO_REAL_NAME): New macro.
+       (init_rtti_processing): Create the tinfo types.
+       (get_tinfo_decl_dynamic): Use type_info_ptr_type, get_tinfo_ptr.
+       (get_tinfo_decl): Adjust.
+       (get_tinfo_ptr): New function.
+       (get_type_id): Use it.
+       (tinfo_base_init): Create vtable decl here, if it doesn't exist.
+       (ptr_initializer): Use get_tinfo_ptr.
+       (ptm_initializer): Likewise.
+       (synthesize_tinfo_var): Break into ...
+       (get_pseudo_ti_init): ... this. Just create the initializer.
+       (get_pseudo_ti_desc): .. and this.
+       (create_real_tinfo_var): Remove.
+       (create_pseudo_type_info): Don't create the vtable decl here.
+       (get_vmi_pseudo_type_info): Remove.
+       (create_tinfo_types): Adjust.
+       (tinfo_decl_p): Rename to ...
+       (unemitted_tinfo_decl_p): ... here. Adjust.
+       (emit_tinfo_decl): Adjust. Create the initializer.
+
+2002-06-14  Jason Merrill  <jason@redhat.com>
+
+       C++ ABI changes.
+       * class.c (build_base_field): Set DECL_PACKED.
+       (layout_class_type): Don't use tail padding of PODs.
+       * mangle.c (write_unqualified_name): Fix template conversion op
+       mangling.
+
+2002-05-18  Jason Merrill  <jason@redhat.com>
+
+       PR c++/6611
+       * decl2.c (import_export_decl): If we clear
+       DECL_NOT_REALLY_EXTERN, make sure DECL_EXTERNAL is set.
+
+2002-05-14  Jason Merrill  <jason@redhat.com>
+
+       * rtti.c (get_tinfo_decl): Don't call comdat_linkage.
+       Do set DECL_COMDAT.
+       (synthesize_tinfo_var): Take the public decl.
+       (create_real_tinfo_var): Likewise.  Check DECL_COMDAT.
+       (emit_tinfo_decl): Adjust.  Call import_export_decl.
+       * decl2.c (import_export_decl): Simplify tinfo decl handling.
+
 2002-07-25  Release Manager
 
        * GCC 3.1.1 Released.
index 998eec04a7c5d72821e5c6a62f2d482ca56da1cf..036d7f72178bd4fe1b36e92c56cdf2dc475a6841 100644 (file)
@@ -3830,6 +3830,8 @@ build_base_field (rli, binfo, empty_p, offsets, t)
   DECL_SIZE_UNIT (decl) = CLASSTYPE_SIZE_UNIT (basetype);
   DECL_ALIGN (decl) = CLASSTYPE_ALIGN (basetype);
   DECL_USER_ALIGN (decl) = CLASSTYPE_USER_ALIGN (basetype);
+  /* Tell the backend not to round up to TYPE_ALIGN.  */
+  DECL_PACKED (decl) = 1;
   
   if (!integer_zerop (DECL_SIZE (decl)))
     {
@@ -4971,6 +4973,12 @@ layout_class_type (t, empty_p, vfuns_p,
       CLASSTYPE_SIZE (t) = bitsize_zero_node;
       CLASSTYPE_SIZE_UNIT (t) = size_zero_node;
     }
+  /* If this is a POD, we can't reuse its tail padding.  */
+  else if (!CLASSTYPE_NON_POD_P (t))
+    {
+      CLASSTYPE_SIZE (t) = TYPE_SIZE (t);
+      CLASSTYPE_SIZE_UNIT (t) = TYPE_SIZE_UNIT (t);
+    }
   else
     {
       CLASSTYPE_SIZE (t) = TYPE_BINFO_SIZE (t);
index bfc6e339bce041ddbc2b0161f334723c2e41bf84..6fe5875ada74dcdb40e0dccab5d76395a0628bf6 100644 (file)
@@ -539,7 +539,7 @@ enum cp_tree_index
     CPTI_STD,
     CPTI_ABI,
     CPTI_TYPE_INFO_TYPE,
-    CPTI_TINFO_DECL_TYPE,
+    CPTI_TYPE_INFO_PTR_TYPE,
     CPTI_ABORT_FNDECL,
     CPTI_GLOBAL_DELETE_FNDECL,
     CPTI_AGGR_TAG,
@@ -626,7 +626,7 @@ extern tree cp_global_trees[CPTI_MAX];
 #define std_node                       cp_global_trees[CPTI_STD]
 #define abi_node                        cp_global_trees[CPTI_ABI]
 #define type_info_type_node            cp_global_trees[CPTI_TYPE_INFO_TYPE]
-#define tinfo_decl_type                        cp_global_trees[CPTI_TINFO_DECL_TYPE]
+#define type_info_ptr_type             cp_global_trees[CPTI_TYPE_INFO_PTR_TYPE]
 #define abort_fndecl                   cp_global_trees[CPTI_ABORT_FNDECL]
 #define global_delete_fndecl           cp_global_trees[CPTI_GLOBAL_DELETE_FNDECL]
 #define current_aggr                   cp_global_trees[CPTI_AGGR_TAG]
@@ -3819,6 +3819,7 @@ extern tree coerce_delete_type                    PARAMS ((tree));
 extern void comdat_linkage                     PARAMS ((tree));
 extern void import_export_vtable               PARAMS ((tree, tree, int));
 extern void import_export_decl                 PARAMS ((tree));
+extern void import_export_tinfo                        PARAMS ((tree, tree, int));
 extern tree build_cleanup                      PARAMS ((tree));
 extern void finish_file                                PARAMS ((void));
 extern tree reparse_absdcl_as_expr             PARAMS ((tree, tree));
@@ -4051,7 +4052,7 @@ extern tree get_tinfo_decl                      PARAMS((tree));
 extern tree get_typeid                         PARAMS((tree));
 extern tree build_dynamic_cast                 PARAMS((tree, tree));
 extern void emit_support_tinfos                 PARAMS((void));
-extern int tinfo_decl_p                         PARAMS((tree, void *));
+extern int unemitted_tinfo_decl_p              PARAMS((tree, void *));
 extern int emit_tinfo_decl                      PARAMS((tree *, void *));
 
 /* in search.c */
index c5ed336b6250d1b6413d18fd2c94650adcbad567..499ff73b9f594fbb54331fd7b5e78e239b620058 100644 (file)
@@ -2529,48 +2529,53 @@ import_export_decl (decl)
       else
        comdat_linkage (decl);
     }
-  else if (tinfo_decl_p (decl, 0))
-    {
-      tree ctype = TREE_TYPE (DECL_NAME (decl));
-
-      if (IS_AGGR_TYPE (ctype))
-       import_export_class (ctype);
-
-      if (IS_AGGR_TYPE (ctype) && CLASSTYPE_INTERFACE_KNOWN (ctype)
-         && TYPE_POLYMORPHIC_P (ctype)
-         /* If -fno-rtti, we're not necessarily emitting this stuff with
-            the class, so go ahead and emit it now.  This can happen
-            when a class is used in exception handling.  */
-         && flag_rtti
-         /* If the type is a cv-qualified variant of a type, then we
-            must emit the tinfo function in this translation unit
-            since it will not be emitted when the vtable for the type
-            is output (which is when the unqualified version is
-            generated).  */
-         && same_type_p (ctype, TYPE_MAIN_VARIANT (ctype)))
-       {
-         DECL_NOT_REALLY_EXTERN (decl)
-           = ! (CLASSTYPE_INTERFACE_ONLY (ctype)
-                || (DECL_DECLARED_INLINE_P (decl) 
-                    && ! flag_implement_inlines
-                    && !DECL_VINDEX (decl)));
-
-         /* Always make artificials weak.  */
-         if (flag_weak)
-           comdat_linkage (decl);
-       }
-      else if (TYPE_BUILT_IN (ctype) 
-              && same_type_p (ctype, TYPE_MAIN_VARIANT (ctype)))
-       DECL_NOT_REALLY_EXTERN (decl) = 0;
-      else
-       comdat_linkage (decl);
-    } 
   else
     comdat_linkage (decl);
 
   DECL_INTERFACE_KNOWN (decl) = 1;
 }
 
+/* Here, we only decide whether or not the tinfo node should be
+   emitted with the vtable.  IS_IN_LIBRARY is non-zero iff the
+   typeinfo for TYPE should be in the runtime library.  */
+
+void
+import_export_tinfo (decl, type, is_in_library)
+     tree decl;
+     tree type;
+     int is_in_library;
+{
+  if (DECL_INTERFACE_KNOWN (decl))
+    return;
+  
+  if (IS_AGGR_TYPE (type))
+    import_export_class (type);
+      
+  if (IS_AGGR_TYPE (type) && CLASSTYPE_INTERFACE_KNOWN (type)
+      && TYPE_POLYMORPHIC_P (type)
+      /* If -fno-rtti, we're not necessarily emitting this stuff with
+        the class, so go ahead and emit it now.  This can happen when
+        a class is used in exception handling.  */
+      && flag_rtti)
+    {
+      DECL_NOT_REALLY_EXTERN (decl) = !CLASSTYPE_INTERFACE_ONLY (type);
+      DECL_COMDAT (decl) = 0;
+    }
+  else
+    {
+      DECL_NOT_REALLY_EXTERN (decl) = 1;
+      DECL_COMDAT (decl) = 1;
+    }
+
+  /* Now override some cases. */
+  if (flag_weak)
+    DECL_COMDAT (decl) = 1;
+  else if (is_in_library)
+    DECL_COMDAT (decl) = 0;
+  
+  DECL_INTERFACE_KNOWN (decl) = 1;
+}
+
 tree
 build_cleanup (decl)
      tree decl;
@@ -3364,7 +3369,7 @@ finish_file ()
       
       /* Write out needed type info variables. Writing out one variable
          might cause others to be needed.  */
-      if (walk_globals (tinfo_decl_p, emit_tinfo_decl, /*data=*/0))
+      if (walk_globals (unemitted_tinfo_decl_p, emit_tinfo_decl, /*data=*/0))
        reconsider = 1;
 
       /* The list of objects with static storage duration is built up
index 7bfbb4bc46050763b49b3b4d664446c4a15ed1cf..ba312b70995310ec7e5f76107381e36e042d7ad4 100644 (file)
@@ -982,8 +982,17 @@ write_unqualified_name (decl)
     {
       /* Conversion operator. Handle it right here.  
            <operator> ::= cv <type>  */
+      tree type;
+      if (decl_is_template_id (decl, NULL))
+       {
+         tree fn_type = get_mostly_instantiated_function_type (decl, NULL,
+                                                               NULL);
+         type = TREE_TYPE (fn_type);
+       }
+      else
+       type = TREE_TYPE (DECL_NAME (decl));
       write_string ("cv");
-      write_type (TREE_TYPE (DECL_NAME (decl)));
+      write_type (type);
     }
   else if (DECL_OVERLOADED_OPERATOR_P (decl))
     {
index 8c9b1c14f7fd40f48cf5423e6b7ebeba7479b690..ae23234ee66b7775bdc56fa0baf41ea6d6479f7d 100644 (file)
@@ -1,5 +1,5 @@
 /* RunTime Type Identification
-   Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2001
+   Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002
    Free Software Foundation, Inc.
    Mostly written by Jason Merrill (jason@cygnus.com).
 
@@ -30,16 +30,46 @@ Boston, MA 02111-1307, USA.  */
 #include "assert.h"
 #include "toplev.h"
 
+/* C++ returns type information to the user in struct type_info
+   objects. We also use type information to implement dynamic_cast and
+   exception handlers. Type information for a particular type is
+   indicated with an ABI defined structure derived from type_info.
+   This would all be very straight forward, but for the fact that the
+   runtime library provides the definitions of the type_info structure
+   and the ABI defined derived classes. We cannot build declarations
+   of them directly in the compiler, but we need to layout objects of
+   their type.  Somewhere we have to lie.
+
+   We define layout compatible POD-structs with compiler-defined names
+   and generate the appropriate initializations for them (complete
+   with explicit mention of their vtable). When we have to provide a
+   type_info to the user we reinterpret_cast the internal compiler
+   type to type_info.  A well formed program can only explicitly refer
+   to the type_infos of complete types (& cv void).  However, we chain
+   pointer type_infos to the pointed-to-type, and that can be
+   incomplete.  We only need the addresses of such incomplete
+   type_info objects for static initialization.
+
+   The type information VAR_DECL of a type is held on the
+   IDENTIFIER_GLOBAL_VALUE of the type's mangled name. That VAR_DECL
+   will be the internal type.  It will usually have the correct
+   internal type reflecting the kind of type it represents (pointer,
+   array, function, class, inherited class, etc).  When the type it
+   represents is incomplete, it will have the internal type
+   corresponding to type_info.  That will only happen at the end of
+   translation, when we are emitting the type info objects.  */
+
 /* Accessors for the type_info objects. We need to remember several things
    about each of the type_info types. The global tree nodes such as
    bltn_desc_type_node are TREE_LISTs, and these macros are used to access
    the required information. */
 /* The RECORD_TYPE of a type_info derived class. */
 #define TINFO_PSEUDO_TYPE(NODE) TREE_TYPE (NODE)
-/* The VAR_DECL of the vtable for the type_info derived class. */
+/* The VAR_DECL of the vtable for the type_info derived class.
+   This is only filled in at the end of the translation. */
 #define TINFO_VTABLE_DECL(NODE) TREE_VALUE (NODE)
-
-extern struct obstack permanent_obstack;
+/* The IDENTIFIER_NODE naming the real class. */
+#define TINFO_REAL_NAME(NODE) TREE_PURPOSE (NODE)
 
 static tree build_headof PARAMS((tree));
 static tree ifnonnull PARAMS((tree, tree));
@@ -48,7 +78,8 @@ static tree build_dynamic_cast_1 PARAMS((tree, tree));
 static tree throw_bad_cast PARAMS((void));
 static tree throw_bad_typeid PARAMS((void));
 static tree get_tinfo_decl_dynamic PARAMS((tree));
-static bool typeid_ok_p PARAMS ((void));
+static tree get_tinfo_ptr PARAMS((tree));
+static bool typeid_ok_p PARAMS((void));
 static int qualifier_flags PARAMS((tree));
 static int target_incomplete_p PARAMS((tree));
 static tree tinfo_base_init PARAMS((tree, tree));
@@ -59,15 +90,21 @@ static tree dfs_class_hint_mark PARAMS ((tree, void *));
 static tree dfs_class_hint_unmark PARAMS ((tree, void *));
 static int class_hint_flags PARAMS((tree));
 static tree class_initializer PARAMS((tree, tree, tree));
-static tree synthesize_tinfo_var PARAMS((tree, tree));
-static tree create_real_tinfo_var PARAMS((tree, tree, tree, tree, int));
 static tree create_pseudo_type_info PARAMS((const char *, int, ...));
-static tree get_vmi_pseudo_type_info PARAMS((int));
+static tree get_pseudo_ti_init PARAMS ((tree, tree, int *));
+static tree get_pseudo_ti_desc PARAMS((tree));
 static void create_tinfo_types PARAMS((void));
 static int typeinfo_in_lib_p PARAMS((tree));
 
 static int doing_runtime = 0;
 \f
+
+/* Declare language defined type_info type and a pointer to const
+   type_info.  This is incomplete here, and will be completed when
+   the user #includes <typeinfo>.  There are language defined
+   restrictions on what can be done until that is included.  Create
+   the internal versions of the ABI types.  */
+
 void
 init_rtti_processing ()
 {
@@ -75,8 +112,11 @@ init_rtti_processing ()
   type_info_type_node = xref_tag
     (class_type_node, get_identifier ("type_info"), 1);
   pop_namespace ();
-  tinfo_decl_type = 
-    build_qualified_type (type_info_type_node, TYPE_QUAL_CONST);
+  type_info_ptr_type = 
+    build_pointer_type
+     (build_qualified_type (type_info_type_node, TYPE_QUAL_CONST));
+
+  create_tinfo_types ();
 }
 
 /* Given the expression EXP of type `class *', return the head of the
@@ -183,13 +223,12 @@ get_tinfo_decl_dynamic (exp)
       /* The RTTI information is at index -1.  */
       index = integer_minus_one_node;
       t = build_vtbl_ref (exp, index);
-      TREE_TYPE (t) = build_pointer_type (tinfo_decl_type);
+      TREE_TYPE (t) = type_info_ptr_type;
       return t;
     }
 
-  /* otherwise return the type_info for the static type of the expr.  */
-  exp = get_tinfo_decl (TYPE_MAIN_VARIANT (type));
-  return build_unary_op (ADDR_EXPR, exp, 0);
+  /* Otherwise return the type_info for the static type of the expr.  */
+  return get_tinfo_ptr (TYPE_MAIN_VARIANT (type));
 }
 
 static bool
@@ -263,9 +302,9 @@ tinfo_name (type)
   return name_string;
 }
 
-/* Returns a decl for the type_info variable for TYPE.  You must
-   arrange that the decl is mark_used, if actually use it --- decls in
-   vtables are only used if the vtable is output.  */ 
+/* Return a VAR_DECL for the internal ABI defined type_info object for
+   TYPE. You must arrange that the decl is mark_used, if actually use
+   it --- decls in vtables are only used if the vtable is output.  */ 
 
 tree
 get_tinfo_decl (type)
@@ -278,7 +317,7 @@ get_tinfo_decl (type)
       && TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
     {
       error ("cannot create type information for type `%T' because its size is variable", 
-               type);
+            type);
       return error_mark_node;
     }
 
@@ -291,37 +330,45 @@ get_tinfo_decl (type)
   name = mangle_typeinfo_for_type (type);
 
   d = IDENTIFIER_GLOBAL_VALUE (name);
-  if (d)
-    /* OK */;
-  else
+  if (!d)
     {
-      /* The tinfo decl is the type_info object itself.  We make all
-         tinfo objects look as type_info, even though they will end up
-         being a subclass of that when emitted.  This means that we'll
-         erroneously think we know the dynamic type -- be careful in the
-         runtime.  */
-      d = build_lang_decl (VAR_DECL, name, tinfo_decl_type);
+      tree var_desc = get_pseudo_ti_desc (type);
+
+      d = build_lang_decl (VAR_DECL, name, TINFO_PSEUDO_TYPE (var_desc));
       
       DECL_ARTIFICIAL (d) = 1;
-      DECL_ALIGN (d) = TYPE_ALIGN (ptr_type_node);
-      DECL_USER_ALIGN (d) = 0;
       TREE_READONLY (d) = 1;
       TREE_STATIC (d) = 1;
       DECL_EXTERNAL (d) = 1;
-      TREE_PUBLIC (d) = 1;
-      if (flag_weak || !typeinfo_in_lib_p (type))
-       comdat_linkage (d);
       SET_DECL_ASSEMBLER_NAME (d, name);
+      DECL_COMDAT (d) = 1;
       cp_finish_decl (d, NULL_TREE, NULL_TREE, 0);
 
       pushdecl_top_level (d);
+
       /* Remember the type it is for.  */
       TREE_TYPE (name) = type;
-      TREE_USED (name) = 1;
     }
+
   return d;
 }
 
+/* Return a pointer to a type_info object describing TYPE, suitably
+   cast to the language defined type.  */
+
+static tree
+get_tinfo_ptr (type)
+     tree type;
+{
+  tree exp = get_tinfo_decl (type);
+  
+   /* Convert to type_info type.  */
+  exp = build_unary_op (ADDR_EXPR, exp, 0);
+  exp = ocp_convert (type_info_ptr_type, exp, CONV_REINTERPRET, 0);
+
+  return exp;
+}
+
 /* Return the type_info object for TYPE.  */
 
 tree
@@ -350,7 +397,7 @@ get_typeid (type)
   if (!type)
     return error_mark_node;
 
-  return get_tinfo_decl (type);
+  return build_indirect_ref (get_tinfo_ptr (type), NULL);
 }
 
 /* Check whether TEST is null before returning RESULT.  If TEST is used in
@@ -683,6 +730,7 @@ tinfo_base_init (desc, target)
 {
   tree init = NULL_TREE;
   tree name_decl;
+  tree vtable_ptr;
   
   {
     tree name_name;
@@ -710,12 +758,40 @@ tinfo_base_init (desc, target)
     cp_finish_decl (name_decl, name_string, NULL_TREE, 0);
     pushdecl_top_level (name_decl);
   }
-  
-  if (TINFO_VTABLE_DECL (desc))
+
+  vtable_ptr = TINFO_VTABLE_DECL (desc);
+  if (!vtable_ptr)
     {
-      tree vtbl_ptr = TINFO_VTABLE_DECL (desc);
-      init = tree_cons (NULL_TREE, vtbl_ptr, init);
+      tree real_type;
+  
+      push_nested_namespace (abi_node);
+      real_type = xref_tag (class_type_node, TINFO_REAL_NAME (desc), 1);
+      pop_nested_namespace (abi_node);
+
+      if (!COMPLETE_TYPE_P (real_type))
+       {
+          /* We never saw a definition of this type, so we need to
+            tell the compiler that this is an exported class, as
+            indeed all of the __*_type_info classes are.  */
+         SET_CLASSTYPE_INTERFACE_KNOWN (real_type);
+         CLASSTYPE_INTERFACE_ONLY (real_type) = 1;
+       }
+
+      vtable_ptr = get_vtable_decl (real_type, /*complete=*/1);
+      vtable_ptr = build_unary_op (ADDR_EXPR, vtable_ptr, 0);
+
+      /* We need to point into the middle of the vtable.  */
+      vtable_ptr = build
+       (PLUS_EXPR, TREE_TYPE (vtable_ptr), vtable_ptr,
+        size_binop (MULT_EXPR,
+                    size_int (2),
+                    TYPE_SIZE_UNIT (vtable_entry_type)));
+      TREE_CONSTANT (vtable_ptr) = 1;
+
+      TINFO_VTABLE_DECL (desc) = vtable_ptr;
     }
+
+  init = tree_cons (NULL_TREE, vtable_ptr, init);
   
   init = tree_cons (NULL_TREE, decay_conversion (name_decl), init);
   
@@ -764,8 +840,7 @@ ptr_initializer (desc, target, non_public_ptr)
     }
   init = tree_cons (NULL_TREE, build_int_2 (flags, 0), init);
   init = tree_cons (NULL_TREE,
-                    build_unary_op (ADDR_EXPR,
-                                    get_tinfo_decl (TYPE_MAIN_VARIANT (to)), 0),
+                    get_tinfo_ptr (TYPE_MAIN_VARIANT (to)),
                     init);
   
   init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, nreverse (init));
@@ -802,12 +877,11 @@ ptm_initializer (desc, target, non_public_ptr)
     }
   init = tree_cons (NULL_TREE, build_int_2 (flags, 0), init);
   init = tree_cons (NULL_TREE,
-                    build_unary_op (ADDR_EXPR,
-                                    get_tinfo_decl (TYPE_MAIN_VARIANT (to)), 0),
+                   get_tinfo_ptr (TYPE_MAIN_VARIANT (to)),
                     init);
   init = tree_cons (NULL_TREE,
-                    build_unary_op (ADDR_EXPR, get_tinfo_decl (klass), 0),
-                    init);  
+                   get_tinfo_ptr (klass),
+                   init);  
   
   init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, nreverse (init));
   TREE_HAS_CONSTRUCTOR (init) = TREE_CONSTANT (init) = TREE_STATIC (init) = 1;
@@ -928,77 +1002,63 @@ typeinfo_in_lib_p (type)
     }
 }
 
-/* Generate a pseudo_type_info VAR_DECL suitable for the supplied
-   TARGET_TYPE and given the REAL_NAME. This is the structure expected by
-   the runtime, and therefore has additional fields.  If we need not emit a
-   definition (because the runtime must contain it), return NULL_TREE,
-   otherwise return the VAR_DECL.  */
+/* Generate the initializer for the type info describing
+   TYPE. VAR_DESC is a . NON_PUBLIC_P is set non-zero, if the VAR_DECL
+   should not be exported from this object file.  This should only be
+   called at the end of translation, when we know that no further
+   types will be completed.  */
 
 static tree
-synthesize_tinfo_var (target_type, real_name)
-     tree target_type;
-     tree real_name;
+get_pseudo_ti_init (type, var_desc, non_public_p)
+     tree type;
+     tree var_desc;
+     int *non_public_p;
 {
-  tree var_init = NULL_TREE;
-  tree var_type = NULL_TREE;
-  int non_public = 0;
-  
-  switch (TREE_CODE (target_type))
+  my_friendly_assert (at_eof, 20021120);
+  switch (TREE_CODE (type))
     {
     case POINTER_TYPE:
-      if (TYPE_PTRMEM_P (target_type))
-        {
-          var_type = ptm_desc_type_node;
-          var_init = ptm_initializer (var_type, target_type, &non_public);
-        }
+      if (TYPE_PTRMEM_P (type))
+       return ptm_initializer (var_desc, type, non_public_p);
       else
-        {
-          if (typeinfo_in_lib_p (target_type) && !doing_runtime)
-            /* These are in the runtime.  */
-            return NULL_TREE;
-          var_type = ptr_desc_type_node;
-          var_init = ptr_initializer (var_type, target_type, &non_public);
-        }
+       return ptr_initializer (var_desc, type, non_public_p);
       break;
     case ENUMERAL_TYPE:
-      var_type = enum_desc_type_node;
-      var_init = generic_initializer (var_type, target_type);
+      return generic_initializer (var_desc, type);
       break;
     case FUNCTION_TYPE:
-      var_type = func_desc_type_node;
-      var_init = generic_initializer (var_type, target_type);
+      return generic_initializer (var_desc, type);
       break;
     case ARRAY_TYPE:
-      var_type = ary_desc_type_node;
-      var_init = generic_initializer (var_type, target_type);
+      return generic_initializer (var_desc, type);
       break;
     case UNION_TYPE:
     case RECORD_TYPE:
-      if (TYPE_PTRMEMFUNC_P (target_type))
-        {
-          var_type = ptm_desc_type_node;
-          var_init = ptm_initializer (var_type, target_type, &non_public);
-        }
-      else if (!COMPLETE_TYPE_P (target_type))
-        {
-          /* Emit a non-public class_type_info.  */
-          non_public = 1;
-          var_type = class_desc_type_node;
-          var_init = class_initializer (var_type, target_type, NULL_TREE);
-        }
-      else if (!CLASSTYPE_N_BASECLASSES (target_type))
+      if (TYPE_PTRMEMFUNC_P (type))
+       return ptm_initializer (var_desc, type, non_public_p);
+      else if (var_desc == class_desc_type_node)
         {
-          var_type = class_desc_type_node;
-          var_init = class_initializer (var_type, target_type, NULL_TREE);
+         if (!COMPLETE_TYPE_P (type))
+           /* Emit a non-public class_type_info.  */
+           *non_public_p = 1;
+         return class_initializer (var_desc, type, NULL_TREE);
         }
+      else if (var_desc == si_class_desc_type_node)
+       {
+          tree base_binfos = BINFO_BASETYPES (TYPE_BINFO (type));
+         tree base_binfo = TREE_VEC_ELT (base_binfos, 0);
+         tree tinfo = get_tinfo_ptr (BINFO_TYPE (base_binfo));
+         tree base_inits = tree_cons (NULL_TREE, tinfo, NULL_TREE);
+         
+         return class_initializer (var_desc, type, base_inits);
+       }
       else
         {
-          /* if this has a single public non-virtual base, it's easier */
-          tree binfo = TYPE_BINFO (target_type);
+         int hint = class_hint_flags (type);
+         tree binfo = TYPE_BINFO (type);
           int nbases = BINFO_N_BASETYPES (binfo);
           tree base_binfos = BINFO_BASETYPES (binfo);
           tree base_inits = NULL_TREE;
-          int is_simple = nbases == 1;
           int ix;
           
           /* Generate the base information initializer.  */
@@ -1012,28 +1072,19 @@ synthesize_tinfo_var (target_type, real_name)
               
               if (TREE_PUBLIC (base_binfo))
                 flags |= 2;
-              tinfo = get_tinfo_decl (BINFO_TYPE (base_binfo));
-              tinfo = build_unary_op (ADDR_EXPR, tinfo, 0);
+              tinfo = get_tinfo_ptr (BINFO_TYPE (base_binfo));
              if (TREE_VIA_VIRTUAL (base_binfo))
                {
                   /* We store the vtable offset at which the virtual
                              base offset can be found.  */
-                 offset = BINFO_VPTR_FIELD (binfo_for_vbase (BINFO_TYPE (base_binfo),
-                                                             target_type));
+                 offset = BINFO_VPTR_FIELD
+                   (binfo_for_vbase (BINFO_TYPE (base_binfo), type));
                  offset = convert (sizetype, offset);
                  flags |= 1;
                }
              else
                offset = BINFO_OFFSET (base_binfo);
               
-              /* is it a single public inheritance? */
-              if (is_simple && flags == 2 && integer_zerop (offset))
-                {
-                  base_inits = tree_cons (NULL_TREE, tinfo, NULL_TREE);
-                  break;
-                }
-              is_simple = 0;
-              
               /* combine offset and flags into one field */
               offset = cp_build_binary_op (LSHIFT_EXPR, offset,
                                           build_int_2 (8, 0));
@@ -1044,86 +1095,23 @@ synthesize_tinfo_var (target_type, real_name)
               base_init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, base_init);
               base_inits = tree_cons (NULL_TREE, base_init, base_inits);
             }
-          
-          if (is_simple)
-            var_type = si_class_desc_type_node;
-          else
-            {
-              int hint = class_hint_flags (target_type);
-              
-              base_inits = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, base_inits);
-              base_inits = tree_cons (NULL_TREE, base_inits, NULL_TREE);
-              /* Prepend the number of bases.  */
-              base_inits = tree_cons (NULL_TREE,
-                                      build_int_2 (nbases, 0), base_inits);
-              /* Prepend the hint flags. */
-              base_inits = tree_cons (NULL_TREE,
-                                      build_int_2 (hint, 0), base_inits);
-              var_type = get_vmi_pseudo_type_info (nbases);
-            }
-          var_init = class_initializer (var_type, target_type, base_inits);
+         base_inits = build (CONSTRUCTOR,
+                             NULL_TREE, NULL_TREE, base_inits);
+         base_inits = tree_cons (NULL_TREE, base_inits, NULL_TREE);
+         /* Prepend the number of bases.  */
+         base_inits = tree_cons (NULL_TREE,
+                                 build_int_2 (nbases, 0), base_inits);
+         /* Prepend the hint flags. */
+         base_inits = tree_cons (NULL_TREE,
+                                 build_int_2 (hint, 0), base_inits);
+
+          return class_initializer (var_desc, type, base_inits);
         }
       break;
 
     default:
-      if (typeinfo_in_lib_p (target_type))
-       {
-         if (!doing_runtime)
-           /* These are guaranteed to be in the runtime.  */
-           return NULL_TREE;
-         var_type = bltn_desc_type_node;
-         var_init = generic_initializer (var_type, target_type);
-         break;
-       }
-      abort ();
+      return generic_initializer (var_desc, type);
     }
-  
-  return create_real_tinfo_var (target_type,
-                               real_name, TINFO_PSEUDO_TYPE (var_type),
-                                var_init, non_public);
-}
-
-/* Create the real typeinfo variable.  NON_PUBLIC indicates that we cannot
-   make this variable public (comdat). */
-
-static tree
-create_real_tinfo_var (target_type, name, type, init, non_public)
-     tree target_type;
-     tree name;
-     tree type;
-     tree init;
-     int non_public;
-{
-  static int count = 0;
-  tree decl;
-  tree hidden_name;
-  char hidden[30];
-
-  /* We cannot give this the name NAME, as that already is globally
-     bound to the tinfo_decl we originally created for this type in
-     get_tinfo_decl. */
-  sprintf (hidden, "__ti_%d", count++);
-  hidden_name = get_identifier (hidden);
-  
-  decl = build_lang_decl (VAR_DECL, hidden_name,
-                          build_qualified_type (type, TYPE_QUAL_CONST));
-  DECL_ARTIFICIAL (decl) = 1;
-  TREE_READONLY (decl) = 1;
-  TREE_STATIC (decl) = 1;
-  DECL_EXTERNAL (decl) = 0;
-  
-  if (!non_public)
-    {
-      TREE_PUBLIC (decl) = 1;
-      if (flag_weak || !typeinfo_in_lib_p (target_type))
-       comdat_linkage (decl);
-    }
-  SET_DECL_ASSEMBLER_NAME (decl, name);
-  DECL_INITIAL (decl) = init;
-  cp_finish_decl (decl, init, NULL_TREE, 0);
-  pushdecl_top_level (decl);
-  TREE_USED (decl) = 1;
-  return decl;
 }
 
 /* Generate the RECORD_TYPE containing the data layout of a type_info
@@ -1132,7 +1120,10 @@ create_real_tinfo_var (target_type, name, type, init, non_public)
    type's vtable. We explicitly manage the vtable member, and name it for
    real type as used in the runtime. The RECORD type has a different name,
    to avoid collisions.  Return a TREE_LIST who's TINFO_PSEUDO_TYPE
-   is the generated type and TINFO_VTABLE_DECL is the vtable decl.
+   is the generated type and TINFO_VTABLE_NAME is the name of the
+   vtable.  We have to delay generating the VAR_DECL of the vtable
+   until the end of the translation, when we'll have seen the library
+   definition, if there was one.
    
    REAL_NAME is the runtime's name of the type. Trailing arguments are
    additional FIELD_DECL's for the structure. The final argument must be
@@ -1141,9 +1132,8 @@ create_real_tinfo_var (target_type, name, type, init, non_public)
 static tree
 create_pseudo_type_info VPARAMS((const char *real_name, int ident, ...))
 {
-  tree real_type, pseudo_type;
+  tree pseudo_type;
   char *pseudo_name;
-  tree vtable_decl;
   int ix;
   tree fields[10];
   tree field_decl;
@@ -1160,29 +1150,6 @@ create_pseudo_type_info VPARAMS((const char *real_name, int ident, ...))
   if (ident)
     sprintf (pseudo_name + strlen (pseudo_name), "%d", ident);
   
-  /* Get the vtable decl. */
-  real_type = xref_tag (class_type_node, get_identifier (real_name), 1);
-  if (! TYPE_SIZE (real_type))
-    {
-      /* We never saw a definition of this type, so we need to tell the
-        compiler that this is an exported class, as indeed all of the
-        __*_type_info classes are.  */
-      SET_CLASSTYPE_INTERFACE_KNOWN (real_type);
-      CLASSTYPE_INTERFACE_ONLY (real_type) = 1;
-    }
-
-  vtable_decl = get_vtable_decl (real_type, /*complete=*/1);
-  vtable_decl = build_unary_op (ADDR_EXPR, vtable_decl, 0);
-
-  /* We need to point into the middle of the vtable.  */
-  vtable_decl = build (PLUS_EXPR,
-                      TREE_TYPE (vtable_decl),
-                      vtable_decl,
-                      size_binop (MULT_EXPR,
-                                  size_int (2),
-                                  TYPE_SIZE_UNIT (vtable_entry_type)));
-  TREE_CONSTANT (vtable_decl) = 1;
-
   /* First field is the pseudo type_info base class. */
   fields[0] = build_decl (FIELD_DECL, NULL_TREE, ti_desc_type_node);
   
@@ -1196,53 +1163,96 @@ create_pseudo_type_info VPARAMS((const char *real_name, int ident, ...))
   TYPE_HAS_CONSTRUCTOR (pseudo_type) = 1;
 
   result = tree_cons (NULL_TREE, NULL_TREE, NULL_TREE);
-  TINFO_VTABLE_DECL (result) = vtable_decl;
-  TINFO_PSEUDO_TYPE (result) = pseudo_type;
+  TINFO_REAL_NAME (result) = get_identifier (real_name);
+  TINFO_PSEUDO_TYPE (result) =
+    cp_build_qualified_type (pseudo_type, TYPE_QUAL_CONST);
   
   VA_CLOSE (ap);
   return result;
 }
 
-/* Return a descriptor for a vmi type with NUM_BASES bases.  */
+/* Return a pseudo type info type node used to describe TYPE.  TYPE
+   must be a complete type (or cv void), except at the end of the
+   translation unit.  */
 
 static tree
-get_vmi_pseudo_type_info (num_bases)
-     int num_bases;
+get_pseudo_ti_desc (type)
+     tree type;
 {
-  tree desc;
-  tree array_domain, base_array;
-  
-  if (TREE_VEC_LENGTH (vmi_class_desc_type_node) <= num_bases)
+  switch (TREE_CODE (type))
     {
-      int ix;
-      tree extend = make_tree_vec (num_bases + 5);
-      
-      for (ix = TREE_VEC_LENGTH (vmi_class_desc_type_node); ix--;)
-        TREE_VEC_ELT (extend, ix) = TREE_VEC_ELT (vmi_class_desc_type_node, ix);
-      vmi_class_desc_type_node = extend;
-    }
-  desc = TREE_VEC_ELT (vmi_class_desc_type_node, num_bases);
-  
-  if (desc)
-    return desc;
+    case POINTER_TYPE:
+      return TYPE_PTRMEM_P (type) ? ptm_desc_type_node : ptr_desc_type_node;
+    case ENUMERAL_TYPE:
+      return enum_desc_type_node;
+    case FUNCTION_TYPE:
+      return func_desc_type_node;
+    case ARRAY_TYPE:
+      return ary_desc_type_node;
+    case UNION_TYPE:
+    case RECORD_TYPE:
+      if (TYPE_PTRMEMFUNC_P (type))
+       return ptm_desc_type_node;
+      else if (!COMPLETE_TYPE_P (type))
+       {
+         my_friendly_assert (at_eof, 20020609);
+         return class_desc_type_node;
+       }
+      else if (!CLASSTYPE_N_BASECLASSES (type))
+       return class_desc_type_node;
+      else
+       {
+         tree base_binfo =
+           TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO (type)), 0);
+         int num_bases = BINFO_N_BASETYPES (TYPE_BINFO (type));
+         
+         if (num_bases == 1
+             && TREE_PUBLIC (base_binfo)
+             && !TREE_VIA_VIRTUAL (base_binfo)
+             && integer_zerop (BINFO_OFFSET (base_binfo)))
+           /* single non-virtual public. */
+           return si_class_desc_type_node;
+         else
+           {
+             tree var_desc;
+             tree array_domain, base_array;
+             
+             if (TREE_VEC_LENGTH (vmi_class_desc_type_node) <= num_bases)
+               {
+                 int ix;
+                 tree extend = make_tree_vec (num_bases + 5);
+                 
+                 for (ix = TREE_VEC_LENGTH (vmi_class_desc_type_node); ix--;)
+                   TREE_VEC_ELT (extend, ix)
+                     = TREE_VEC_ELT (vmi_class_desc_type_node, ix);
+                 vmi_class_desc_type_node = extend;
+               }
+             var_desc = TREE_VEC_ELT (vmi_class_desc_type_node, num_bases);
+             if (var_desc)
+               return var_desc;
   
-  /* Add number of bases and trailing array of base_class_type_info.  */
-  array_domain = build_index_type (size_int (num_bases));
-  base_array = build_array_type (base_desc_type_node, array_domain);
-
-  push_nested_namespace (abi_node);
-
-  desc = create_pseudo_type_info
-            ("__vmi_class_type_info", num_bases,
-             build_decl (FIELD_DECL, NULL_TREE, integer_type_node),
-             build_decl (FIELD_DECL, NULL_TREE, integer_type_node),
-             build_decl (FIELD_DECL, NULL_TREE, base_array),
-             NULL);
-
-  pop_nested_namespace (abi_node);
-
-  TREE_VEC_ELT (vmi_class_desc_type_node, num_bases) = desc;
-  return desc;
+             /* Add number of bases and trailing array of
+                base_class_type_info.  */
+             array_domain = build_index_type (size_int (num_bases));
+             base_array =
+               build_array_type (base_desc_type_node, array_domain);
+
+             push_nested_namespace (abi_node);
+             var_desc = create_pseudo_type_info
+               ("__vmi_class_type_info", num_bases,
+                build_decl (FIELD_DECL, NULL_TREE, integer_type_node),
+                build_decl (FIELD_DECL, NULL_TREE, integer_type_node),
+                build_decl (FIELD_DECL, NULL_TREE, base_array),
+                NULL);
+             pop_nested_namespace (abi_node);
+
+             TREE_VEC_ELT (vmi_class_desc_type_node, num_bases) = var_desc;
+             return var_desc;
+           }
+       }
+    default:
+      return bltn_desc_type_node;
+    }
 }
 
 /* Make sure the required builtin types exist for generating the type_info
@@ -1251,15 +1261,9 @@ get_vmi_pseudo_type_info (num_bases)
 static void
 create_tinfo_types ()
 {
-  tree ptr_type_info;
-  
-  if (bltn_desc_type_node)
-    return;
-  push_nested_namespace (abi_node);
+  my_friendly_assert (!ti_desc_type_node, 20020609);
 
-  ptr_type_info = build_pointer_type
-                    (build_qualified_type
-                      (type_info_type_node, TYPE_QUAL_CONST));
+  push_nested_namespace (abi_node);
   
   /* Create the internal type_info structure. This is used as a base for
      the other structures.  */
@@ -1299,7 +1303,7 @@ create_tinfo_types ()
      This is really a descendant of __class_type_info.  */
   si_class_desc_type_node = create_pseudo_type_info
            ("__si_class_type_info", 0,
-            build_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
+            build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type),
             NULL);
   
   /* Base class internal helper. Pointer to base type, offset to base,
@@ -1307,7 +1311,7 @@ create_tinfo_types ()
   {
     tree fields[2];
     
-    fields[0] = build_decl (FIELD_DECL, NULL_TREE, ptr_type_info);
+    fields[0] = build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type);
     fields[1] = build_decl (FIELD_DECL, NULL_TREE, integer_types[itk_long]);
     base_desc_type_node = make_aggr_type (RECORD_TYPE);
     finish_builtin_type (base_desc_type_node, "__base_class_type_info_pseudo",
@@ -1324,7 +1328,7 @@ create_tinfo_types ()
   ptr_desc_type_node = create_pseudo_type_info
       ("__pointer_type_info", 0,
        build_decl (FIELD_DECL, NULL_TREE, integer_type_node),
-       build_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
+       build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type),
        NULL);
 
   /* Pointer to member data type_info.  Add qualifications flags,
@@ -1333,8 +1337,8 @@ create_tinfo_types ()
   ptm_desc_type_node = create_pseudo_type_info
        ("__pointer_to_member_type_info", 0,
         build_decl (FIELD_DECL, NULL_TREE, integer_type_node),
-        build_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
-        build_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
+        build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type),
+        build_decl (FIELD_DECL, NULL_TREE, type_info_ptr_type),
         NULL);
 
   pop_nested_namespace (abi_node);
@@ -1401,75 +1405,61 @@ emit_support_tinfos ()
    definition emitted for it.  */
 
 int
-tinfo_decl_p (t, data)
+unemitted_tinfo_decl_p (t, data)
      tree t;
      void *data ATTRIBUTE_UNUSED;
 {
-  return TREE_CODE (t) == VAR_DECL
-         && IDENTIFIER_GLOBAL_VALUE (DECL_NAME (t)) == (t)
-         && TREE_TYPE (t) == tinfo_decl_type
-         && TREE_TYPE (DECL_NAME (t));
+  if (/* It's a var decl */
+      TREE_CODE (t) == VAR_DECL
+      /* whos name points back to itself */
+      && IDENTIFIER_GLOBAL_VALUE (DECL_NAME (t)) == t
+      /* whos name's type is non-null */
+      && TREE_TYPE (DECL_NAME (t))
+      /* and whos type is a struct */
+      && TREE_CODE (TREE_TYPE (t)) == RECORD_TYPE
+      /* with a first field of our pseudo type info */
+      && TREE_TYPE (TYPE_FIELDS (TREE_TYPE (t))) == ti_desc_type_node)
+    return 1;
+  return 0;
 }
 
-/* Emit a suitable type_info definition for the type_info decl pointed to by
-   DECL_PTR. We emit a completely new variable, of the correct type for the
-   actual type this is describing. The DECL_ASSEMBLER_NAME of the generated
-   definition is set to that of the supplied decl, so that they can be tied
-   up. Mark the supplied decl as having been dealt with. Emitting one
-   definition might cause other definitions to be required.
-   
-   We need to do things this way, because we're trying to do something like
-   
-      struct B : A {
-        ...
-      };
-   
-      extern const A tinfo_var;
-   
-      const B tinfo_var = {...};
-   
-   which is not permitted. Also, we've not necessarily seen the definition of B.
-   So we do something like the following,
-   
-      extern const A tinfo_var;
-   
-      struct pseudo_A {
-        const void *vtable_ptr;
-        const char *name;
-      };
-      struct pseudo_B {
-        pseudo_A base;
-        ...
-      };
-      
-      const pseudo_B proxy_tinfo_var attribute((assembler_name="tinfo_var")) =
-      {
-        {&B::vtable, "..."},
-        ...
-      };
-   
-   pseudo_A and pseudo_B must be layout equivalent to the real definitions in
-   the runtime.  */
+/* Finish a type info decl. DECL_PTR is a pointer to an unemitted
+   tinfo decl.  Determine whether it needs emitting, and if so
+   generate the initializer.  */
 
 int
 emit_tinfo_decl (decl_ptr, data)
      tree *decl_ptr;
      void *data ATTRIBUTE_UNUSED;
 {
-  tree tinfo_decl = *decl_ptr;
-  tree tinfo_type, decl;
-  
-  my_friendly_assert (TREE_TYPE (tinfo_decl) == tinfo_decl_type, 20000121);
-  tinfo_type = TREE_TYPE (DECL_NAME (tinfo_decl));
-  my_friendly_assert (tinfo_type != NULL_TREE, 20000120);
+  tree decl = *decl_ptr;
+  tree type = TREE_TYPE (DECL_NAME (decl));
+  int non_public;
+  int in_library = typeinfo_in_lib_p (type);
+  tree var_desc, var_init;
   
-  if (!DECL_NEEDED_P (tinfo_decl))
+  import_export_tinfo (decl, type, in_library);
+  if (DECL_REALLY_EXTERN (decl) || !DECL_NEEDED_P (decl))
     return 0;
-  /* Say we've dealt with it.  */
-  TREE_TYPE (DECL_NAME (tinfo_decl)) = NULL_TREE;
+
+  if (!doing_runtime && in_library)
+    return 0;
+
+  non_public = 0;
+  var_desc = get_pseudo_ti_desc (type);
+  var_init = get_pseudo_ti_init (type, var_desc, &non_public);
   
-  create_tinfo_types ();
-  decl = synthesize_tinfo_var (tinfo_type, DECL_ASSEMBLER_NAME (tinfo_decl));
+  DECL_EXTERNAL (decl) = 0;
+  TREE_PUBLIC (decl) = !non_public;
+  if (non_public)
+    DECL_COMDAT (decl) = 0;
+
+  DECL_INITIAL (decl) = var_init;
+  cp_finish_decl (decl, var_init, NULL_TREE, 0);
+  /* cp_finish_decl will have dealt with linkage. */
   
-  return decl != 0;
+  /* Say we've dealt with it.  */
+  TREE_TYPE (DECL_NAME (decl)) = NULL_TREE;
+
+  return 1;
 }
index 7ba9393db7871594a9ecc4fe6bad2bb442d9aaa9..1ad507e6b87fb5e9b0967b1508e3cb76bc95b4b8 100644 (file)
@@ -1,3 +1,21 @@
+2002-07-24  Roger Sayle  <roger@eyesopen.com>
+
+       * gcc.c-torture/execute/memset-3.c: New testcase.
+
+2002-06-14  Jason Merrill  <jason@redhat.com>
+
+       * g++.dg/abi/layout1.C: New test.
+       * g++.dg/abi/layout2.C: New test.
+       * g++.dg/abi/mangle8.C: New test.
+
+2002-05-14  Jason Merrill  <jason@redhat.com>
+
+       * g++.dg/abi/rtti1.C: New test.
+
+2002-01-03  Jakub Jelinek  <jakub@redhat.com>
+
+       * gcc.dg/gnu89-init-2.c: New test.
+
 2002-07-25  Release Manager
 
        * GCC 3.1.1 Released.
index 45bea70fcdbe10625324ff6df5c8fa2ee159ddf3..f1ac5ece41cffc0914bc7444df38dd3d8dbeed1e 100644 (file)
@@ -1,3 +1,112 @@
+2002-07-26  Phil Edwards  <pme@gcc.gnu.org>
+
+       * libsupc++/new (placement delete):  Remove unused paramater names.
+
+2002-07-25  Benjamin Kosnik  <bkoz@redhat.com>
+
+       PR libstdc++/7216
+       * include/std/std_istream.h (basic_iostream): Add typedefs for
+       char_type, int_type, pos_type, off_type, and traits_type.
+       * testsuite/27_io/iostream.cc (test01): Add typedef tests.
+       * testsuite/27_io/istream.cc: Same.
+       * testsuite/27_io/ostream.cc: Same.
+       * testsuite/27_io/filebuf.cc: Same.
+       * testsuite/27_io/stringbuf.cc: Replace content, move to...
+       * testsuite/27_io/stringbuf_members.cc: ...here.        
+       * testsuite/27_io/streambuf.cc: Replace content, move to...
+       * testsuite/27_io/streambuf_members.cc: ...here.        
+       * testsuite/27_io/stringstream.cc: Replace content, move to...
+       * testsuite/27_io/stringstream_members.cc: ...here.
+       * testsuite/27_io/ios.cc: New file.
+       * testsuite/27_io/fstream.cc: New file.
+       * testsuite/27_io/ifstream.cc: New file.        
+       * testsuite/27_io/ofstream.cc: New file.                
+       * testsuite/27_io/istringstream.cc: New file.   
+       * testsuite/27_io/ostringstream.cc: New file.   
+       
+2002-07-25  Benjamin Kosnik  <bkoz@redhat.com>
+
+       PR libstdc++/7220
+       * include/bits/istream.tcc (istream::ignore): Don't extract on
+       zero.
+       * testsuite/27_io/istream_unformatted.cc (test10): Add.
+
+2002-07-24  Benjamin Kosnik  <bkoz@redhat.com>
+
+       PR libstdc++/7222
+       * src/locale.cc (locale::locale(const char*)): Use setlocale NULL.
+       * testsuite/22_locale/ctor_copy_dtor.cc (test02): New.
+       
+2002-07-24  Benjamin Kosnik  <bkoz@redhat.com>
+
+       PR libstdc++/7286
+       * libsupc++/new: Add placement delete.
+       * testsuite/18_support/new_delete_placement.cc: New.
+       
+2002-07-07  Paolo Carlini  <pcarlini@unitus.it>
+
+       PR libstdc++/7186
+       * include/bits/stl_deque.h (_Deque_iterator::operator-):
+       Make non-member, as already happens for the comparison
+       operators in accord with DR179 (Ready).
+       * testsuite/23_containers/deque_operators.cc: Add test02.
+
+2002-07-04  Benjamin Kosnik  <bkoz@redhat.com>
+           Jack Reeves  <jackw_reeves@hotmail.com>
+
+       * include/std/std_streambuf.h (basic_streambuf::_M_buf): Change to
+       size_t, from int_type.
+       (basic_streambuf::_M_buf_size_opt): Same.
+       (basic_streambuf::_S_pback_sizex): Same.        
+       * include/bits/streambuf.tcc: Same.
+       * include/std/std_streambuf.h (basic_streambuf::snextc): Use
+       eq_int_type.
+       (basic_streambuf::uflow): Same.
+       * include/bits/sstream.tcc (basic_stringbuf::overflow): Use
+       to_char_type.
+       * include/bits/basic_ios.tcc (basic_ios::init): Use _CharT().
+       * include/bits/streambuf.tcc (basic_streambuf::xsgetn): Use
+       eq_int_type.
+       (basic_streambuf::xsputn): Same.
+       (__copy_streambufs): Same.
+
+2002-07-02  Paolo Carlini  <pcarlini@unitus.it>
+
+       PR libstdc++/6642
+       * include/bits/stl_iterator.h
+       (__normal_iterator::operator-(const __normal_iterator&)):
+       Make non-member, as already happens for the comparison
+       operators in accord with DR179 (Ready).
+       * testsuite/24_iterators/iterator.cc: Add test from the PR.
+
+2002-07-02  Benjamin Kosnik  <bkoz@redhat.com>
+
+       PR libstdc++/6410
+       * include/bits/locale_facets.h (moneypunct::moneypunct): Add const
+       char* name parameter.
+       * config/locale/gnu/monetary_members.cc: Use it.
+       * config/locale/generic/monetary_members.cc: Same.
+       * src/localename.cc (_Impl::_Impl(const char*, size_t)): Use it.
+
+2002-07-01  Benjamin Kosnik  <bkoz@redhat.com>
+
+       * configure.in (libtool_VERSION): Bump to 5:0:0.
+       * configure: Regenerate.
+
+2002-05-19  Paolo Carlini  <pcarlini@unitus.it>
+
+       * testsuite/23_containers/deque_operators.cc (test01):
+       Fix minor typo in last commit.
+
+2002-05-18  Paolo Carlini  <pcarlini@unitus.it>
+
+       PR libstdc++/6503
+       * include/bits/stl_deque.h (_Deque_iterator::operator==,
+       operator!=, operator<, operator>, operator>=, operator<=):
+       Make non-member functions, to allow comparing const and
+       non-const iterators in any order.
+       * testsuite/23_containers/deque_operators.cc: New testfile.
+
 2002-07-25  Release Manager
 
        * GCC 3.1.1 Released.
index 7c2e13b62df939d2bba3664d74d92169f635212e..1921f46e98cfd09cf4fd4e644710ef51573a0c9c 100644 (file)
@@ -45,7 +45,7 @@ namespace std
 
   template<> 
     void
-    moneypunct<char, true>::_M_initialize_moneypunct(__c_locale)
+    moneypunct<char, true>::_M_initialize_moneypunct(__c_locale, const char*)
     {
       // "C" locale
       _M_decimal_point = '.';
@@ -61,7 +61,7 @@ namespace std
 
   template<> 
     void
-    moneypunct<char, false>::_M_initialize_moneypunct(__c_locale)
+    moneypunct<char, false>::_M_initialize_moneypunct(__c_locale, const char*)
     {
       // "C" locale
       _M_decimal_point = '.';
@@ -86,7 +86,8 @@ namespace std
 #ifdef _GLIBCPP_USE_WCHAR_T
   template<> 
     void
-    moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale)
+    moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale, 
+                                                       const char*)
     {
       // "C" locale
       _M_decimal_point = L'.';
@@ -102,7 +103,8 @@ namespace std
 
   template<> 
     void
-    moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale)
+    moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale, 
+                                                        const char*)
     {
       // "C" locale
       _M_decimal_point = L'.';
index bf9b50cbb951e8021edbb0b05bbd8a460a56da06..6a797ffbc25fa82ba7e0abb7c8c5ac5beac3ee9e 100644 (file)
@@ -216,7 +216,8 @@ namespace std
 
   template<> 
     void
-    moneypunct<char, true>::_M_initialize_moneypunct(__c_locale __cloc)
+    moneypunct<char, true>::_M_initialize_moneypunct(__c_locale __cloc, 
+                                                    const char*)
     {
       if (__cloc == _S_c_locale)
        {
@@ -260,7 +261,8 @@ namespace std
 
   template<> 
     void
-    moneypunct<char, false>::_M_initialize_moneypunct(__c_locale __cloc)
+    moneypunct<char, false>::_M_initialize_moneypunct(__c_locale __cloc, 
+                                                     const char*)
     {
       if (__cloc == _S_c_locale)
        {
@@ -313,7 +315,8 @@ namespace std
 #ifdef _GLIBCPP_USE_WCHAR_T
   template<> 
     void
-    moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale __cloc)
+    moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale __cloc, 
+                                                       const char* __name)
     {
       if (__cloc == _S_c_locale)
        {
@@ -331,6 +334,10 @@ namespace std
       else
        {
          // Named locale.
+         // XXX Fix me. Switch to named locale so that mbsrtowcs will work.
+         char* __old = strdup(setlocale(LC_ALL, NULL));
+         setlocale(LC_ALL, __name);
+
          _M_decimal_point = static_cast<wchar_t>(((union { const char *__s; unsigned int __w; }){ __s: __nl_langinfo_l(_NL_NUMERIC_DECIMAL_POINT_WC, __cloc)}).__w);
 
          _M_thousands_sep = static_cast<wchar_t>(((union { const char *__s; unsigned int __w; }){ __s: __nl_langinfo_l(_NL_NUMERIC_THOUSANDS_SEP_WC, __cloc)}).__w);
@@ -391,12 +398,17 @@ namespace std
          char __nprecedes = *(__nl_langinfo_l(__INT_N_CS_PRECEDES, __cloc));
          char __nspace = *(__nl_langinfo_l(__INT_N_SEP_BY_SPACE, __cloc));
          _M_neg_format = _S_construct_pattern(__nprecedes, __nspace, __nposn);
+
+         // XXX
+         setlocale(LC_ALL, __old);
+         free(__old);
        }
     }
 
   template<> 
     void
-    moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale __cloc)
+    moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale __cloc, 
+                                                        const char* __name)
     {
       if (__cloc == _S_c_locale)
        {
@@ -414,6 +426,10 @@ namespace std
       else
        {
          // Named locale.
+         // XXX Fix me. Switch to named locale so that mbsrtowcs will work.
+         char* __old = strdup(setlocale(LC_ALL, NULL));
+         setlocale(LC_ALL, __name);
+
          _M_decimal_point = static_cast<wchar_t>(((union { const char *__s; unsigned int __w; }){ __s: __nl_langinfo_l(_NL_NUMERIC_DECIMAL_POINT_WC, __cloc)}).__w);
          _M_thousands_sep = static_cast<wchar_t>(((union { const char *__s; unsigned int __w; }){ __s: __nl_langinfo_l(_NL_NUMERIC_THOUSANDS_SEP_WC, __cloc)}).__w);
          _M_grouping = __nl_langinfo_l(GROUPING, __cloc);
@@ -473,6 +489,10 @@ namespace std
          char __nprecedes = *(__nl_langinfo_l(__N_CS_PRECEDES, __cloc));
          char __nspace = *(__nl_langinfo_l(__N_SEP_BY_SPACE, __cloc));
          _M_neg_format = _S_construct_pattern(__nprecedes, __nspace, __nposn);
+
+         // XXX
+         setlocale(LC_ALL, __old);
+         free(__old);
        }
     }
 
index 553f21b6f5dbf006d46228d6b8365c0dd6132d31..d2f0ca3164d707ec3a99dbd69e86dac3785c7bd6 100755 (executable)
@@ -599,7 +599,7 @@ ORIGINAL_LD_FOR_MULTILIBS=$LD
 PACKAGE=libstdc++
 
 # For libtool versioning info, format is CURRENT:REVISION:AGE
-libtool_VERSION=4:1:0
+libtool_VERSION=5:0:0
 
 
 
index eaa09cddaf1187473ae85eefa597c17fe4ddad8c..9dbdf6e792c9971c35f55fa6e9905184c1a68e72 100644 (file)
@@ -13,7 +13,7 @@ ORIGINAL_LD_FOR_MULTILIBS=$LD
 PACKAGE=libstdc++
 AC_SUBST(PACKAGE)
 # For libtool versioning info, format is CURRENT:REVISION:AGE
-libtool_VERSION=4:1:0
+libtool_VERSION=5:0:0
 AC_SUBST(libtool_VERSION)
 
 GLIBCPP_TOPREL_CONFIGURE
index 1e345dc2117205d9394cf744a348547c05f08abd..a38a95b58a0ff43834ad0635ca44bb6298a155ef 100644 (file)
@@ -156,7 +156,7 @@ namespace std
       // unformatted input and output with non-required basic_ios
       // instantiations is possible even without imbuing the expected
       // ctype<char_type> facet.
-      _M_fill = 0;
+      _M_fill = _CharT();
       _M_fill_init = false;
 
       _M_exception = goodbit;
index 2658866ec5784c94d993b4d9b2182314d1980b0e..fc0adea69e37c60550bcd4cc8c72d275562b595a 100644 (file)
@@ -708,7 +708,7 @@ namespace std
     {
       _M_gcount = 0;
       sentry __cerb(*this, true);
-      if (__cerb) 
+      if (__cerb && __n > 0
        {
          try 
            {
index d63eb5dd2d5f8d1f5d310b51f7b79704b3ce6caa..241c4655dc2856af73a44e1a5c614e3606eb90f0 100644 (file)
@@ -1357,8 +1357,9 @@ namespace std
       { _M_initialize_moneypunct(); }
 
       explicit 
-      moneypunct(__c_locale __cloc, size_t __refs = 0) : locale::facet(__refs)
-      { _M_initialize_moneypunct(__cloc); }
+      moneypunct(__c_locale __cloc, const char* __s, size_t __refs = 0) 
+      : locale::facet(__refs)
+      { _M_initialize_moneypunct(__cloc, __s); }
 
       char_type
       decimal_point() const
@@ -1438,7 +1439,8 @@ namespace std
 
       // For use at construction time only.
        void 
-       _M_initialize_moneypunct(__c_locale __cloc = _S_c_locale);
+       _M_initialize_moneypunct(__c_locale __cloc = _S_c_locale, 
+                               const char* __name = NULL);
     };
 
   template<typename _CharT, bool _Intl>
@@ -1455,11 +1457,11 @@ namespace std
 
   template<> 
     void
-    moneypunct<char, true>::_M_initialize_moneypunct(__c_locale __cloc);
+    moneypunct<char, true>::_M_initialize_moneypunct(__c_locale, const char*);
 
   template<> 
     void
-    moneypunct<char, false>::_M_initialize_moneypunct(__c_locale __cloc);
+    moneypunct<char, false>::_M_initialize_moneypunct(__c_locale, const char*);
 
 #ifdef _GLIBCPP_USE_WCHAR_T
   template<>
@@ -1470,11 +1472,13 @@ namespace std
 
   template<> 
     void
-    moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale __cloc);
+    moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale, 
+                                                       const char*);
 
   template<> 
     void
-    moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale __cloc);
+    moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale, 
+                                                        const char*);
 #endif
 
   template<typename _CharT, bool _Intl>
index e7419504d3e548069b9d3b81de3ba5feb36d251c..fd56347a7a4afa9f21c42d2ad81cfc92d57b66c0 100644 (file)
@@ -95,13 +95,13 @@ namespace std
              __len *= 2;
 
              if (__testwrite)
-               __ret = this->sputc(__c);
+               __ret = this->sputc(traits_type::to_char_type(__c));
              else if (__len <= _M_string.max_size())
                {
                  // Force-allocate, re-sync.
                  _M_string = this->str();
                  _M_string.reserve(__len);
-                 _M_buf_size = static_cast<int_type>(__len);
+                 _M_buf_size = __len;
                  _M_really_sync(_M_in_cur - _M_in_beg, 
                                 _M_out_cur - _M_out_beg);
                  *_M_out_cur = traits_type::to_char_type(__c);
index 5fa8d125e75612525b88637bd34f556418f40c8a..ce6be7e4ce2f52bda41940c748abfb6076c36dfd 100644 (file)
@@ -130,11 +130,6 @@ struct _Deque_iterator
   reference operator*() const { return *_M_cur; }
   pointer operator->() const { return _M_cur; }
 
-  difference_type operator-(const _Self& __x) const {
-    return difference_type(_S_buffer_size()) * (_M_node - __x._M_node - 1) +
-      (_M_cur - _M_first) + (__x._M_last - __x._M_cur);
-  }
-
   _Self& operator++() {
     ++_M_cur;
     if (_M_cur == _M_last) {
@@ -194,16 +189,6 @@ struct _Deque_iterator
 
   reference operator[](difference_type __n) const { return *(*this + __n); }
 
-  bool operator==(const _Self& __x) const { return _M_cur == __x._M_cur; }
-  bool operator!=(const _Self& __x) const { return !(*this == __x); }
-  bool operator<(const _Self& __x) const {
-    return (_M_node == __x._M_node) ? 
-      (_M_cur < __x._M_cur) : (_M_node < __x._M_node);
-  }
-  bool operator>(const _Self& __x) const  { return __x < *this; }
-  bool operator<=(const _Self& __x) const { return !(__x < *this); }
-  bool operator>=(const _Self& __x) const { return !(*this < __x); }
-
   /** @if maint
    *  Prepares to traverse new_node.  Sets everything except _M_cur, which
    *  should therefore be set by the caller immediately afterwards, based on
@@ -217,6 +202,123 @@ struct _Deque_iterator
   }
 };
 
+// Note: we also provide overloads whose operands are of the same type in
+// order to avoid ambiguos overload resolution when std::rel_ops operators
+// are in scope (for additional details, see libstdc++/3628)
+template <class _Tp, class _Ref, class _Ptr>
+inline bool
+operator==(const _Deque_iterator<_Tp, _Ref, _Ptr>& __x,
+          const _Deque_iterator<_Tp, _Ref, _Ptr>& __y)
+{
+  return __x._M_cur == __y._M_cur;
+}
+
+template <class _Tp, class _RefL, class _PtrL, class _RefR, class _PtrR>
+inline bool
+operator==(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+          const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return __x._M_cur == __y._M_cur;
+}
+
+template <class _Tp, class _Ref, class _Ptr>
+inline bool
+operator!=(const _Deque_iterator<_Tp, _Ref, _Ptr>& __x,
+          const _Deque_iterator<_Tp, _Ref, _Ptr>& __y)
+{
+  return !(__x == __y);
+}
+
+template <class _Tp, class _RefL, class _PtrL, class _RefR, class _PtrR>
+inline bool
+operator!=(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+          const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return !(__x == __y);
+}
+
+template <class _Tp, class _Ref, class _Ptr>
+inline bool
+operator<(const _Deque_iterator<_Tp, _Ref, _Ptr>& __x,
+          const _Deque_iterator<_Tp, _Ref, _Ptr>& __y)
+{
+  return (__x._M_node == __y._M_node) ? 
+    (__x._M_cur < __y._M_cur) : (__x._M_node < __y._M_node);
+}
+
+template <class _Tp, class _RefL, class _PtrL, class _RefR, class _PtrR>
+inline bool
+operator<(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+          const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return (__x._M_node == __y._M_node) ? 
+    (__x._M_cur < __y._M_cur) : (__x._M_node < __y._M_node);
+}
+
+template <class _Tp, class _Ref, class _Ptr>
+inline bool
+operator>(const _Deque_iterator<_Tp, _Ref, _Ptr>& __x,
+          const _Deque_iterator<_Tp, _Ref, _Ptr>& __y)
+{
+  return __y < __x;
+}
+
+template <class _Tp, class _RefL, class _PtrL, class _RefR, class _PtrR>
+inline bool
+operator>(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+          const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return __y < __x;
+}
+
+template <class _Tp, class _Ref, class _Ptr>
+inline bool
+operator<=(const _Deque_iterator<_Tp, _Ref, _Ptr>& __x,
+          const _Deque_iterator<_Tp, _Ref, _Ptr>& __y)
+{
+  return !(__y < __x);
+}
+
+template <class _Tp, class _RefL, class _PtrL, class _RefR, class _PtrR>
+inline bool
+operator<=(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+          const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return !(__y < __x);
+}
+
+template <class _Tp, class _Ref, class _Ptr>
+inline bool
+operator>=(const _Deque_iterator<_Tp, _Ref, _Ptr>& __x,
+          const _Deque_iterator<_Tp, _Ref, _Ptr>& __y)
+{
+  return !(__x < __y);
+}
+
+template <class _Tp, class _RefL, class _PtrL, class _RefR, class _PtrR>
+inline bool
+operator>=(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+          const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return !(__x < __y);
+}
+
+// _GLIBCPP_RESOLVE_LIB_DEFECTS
+// According to the resolution of DR179 not only the various comparison
+// operators but also operator- must accept mixed iterator/const_iterator
+// parameters.
+template <typename _Tp, typename _RefL, typename _PtrL,
+                        typename _RefR, typename _PtrR>
+inline typename _Deque_iterator<_Tp, _RefL, _PtrL>::difference_type
+operator-(const _Deque_iterator<_Tp, _RefL, _PtrL>& __x,
+         const _Deque_iterator<_Tp, _RefR, _PtrR>& __y)
+{
+  return _Deque_iterator<_Tp, _RefL, _PtrL>::difference_type
+    (_Deque_iterator<_Tp, _RefL, _PtrL>::_S_buffer_size()) *
+    (__x._M_node - __y._M_node - 1) + (__x._M_cur - __x._M_first) +
+    (__y._M_last - __y._M_cur);
+}
+
 template <class _Tp, class _Ref, class _Ptr>
 inline _Deque_iterator<_Tp, _Ref, _Ptr>
 operator+(ptrdiff_t __n, const _Deque_iterator<_Tp, _Ref, _Ptr>& __x)
index d8a6d8ca374ae5b5b91b4973ab7628b3b699e9b8..6fb0d81339f04a09c16d087b2e81a9dac1ccf4f2 100644 (file)
@@ -629,10 +629,6 @@ namespace __gnu_cxx
       operator-(const difference_type& __n) const
       { return __normal_iterator(_M_current - __n); }
       
-      difference_type
-      operator-(const __normal_iterator& __i) const
-      { return _M_current - __i._M_current; }
-      
       const _Iterator& 
       base() const { return _M_current; }
     };
@@ -719,6 +715,16 @@ namespace __gnu_cxx
             const __normal_iterator<_Iterator, _Container>& __rhs)
   { return __lhs.base() >= __rhs.base(); }
 
+  // _GLIBCPP_RESOLVE_LIB_DEFECTS
+  // According to the resolution of DR179 not only the various comparison
+  // operators but also operator- must accept mixed iterator/const_iterator
+  // parameters.
+  template<typename _IteratorL, typename _IteratorR, typename _Container>
+  inline typename __normal_iterator<_IteratorL, _Container>::difference_type
+  operator-(const __normal_iterator<_IteratorL, _Container>& __lhs,
+            const __normal_iterator<_IteratorR, _Container>& __rhs)
+  { return __lhs.base() - __rhs.base(); }
+
   template<typename _Iterator, typename _Container>
   inline __normal_iterator<_Iterator, _Container>
   operator+(typename __normal_iterator<_Iterator, _Container>::difference_type __n,
index 292999cfba3183cc898ce08edbf08779bd769181..2f790e902cb7c9f0e5d2bcd76149790733d5404d 100644 (file)
@@ -40,7 +40,7 @@
 namespace std 
 {
   template<typename _CharT, typename _Traits>
-    const typename basic_streambuf<_CharT, _Traits>::int_type
+    const size_t
     basic_streambuf<_CharT, _Traits>::_S_pback_size;
 
   template<typename _CharT, typename _Traits>
@@ -138,7 +138,7 @@ namespace std
          if (__ret < __n)
            {
              int_type __c = this->uflow();  
-             if (__c != traits_type::eof())
+             if (!traits_type::eq_int_type(__c, traits_type::eof()))
                {
                  traits_type::assign(*__s++, traits_type::to_char_type(__c));
                  ++__ret;
@@ -177,7 +177,7 @@ namespace std
          if (__ret < __n)
            {
              int_type __c = this->overflow(traits_type::to_int_type(*__s));
-             if (__c != traits_type::eof())
+             if (!traits_type::eq_int_type(__c, traits_type::eof()))
                {
                  ++__ret;
                  ++__s;
@@ -214,7 +214,7 @@ namespace std
              __sbin->_M_in_cur_move(__xtrct);
              if (__xtrct == __bufsize)
                {
-                 if (__sbin->sgetc() == _Traits::eof())
+                 if (_Traits::eq_int_type(__sbin->sgetc(), _Traits::eof()))
                    break;
                  __bufsize = __sbin->in_avail();
                }
index 40f4b67fb9f75dee50024b244add9088a2ac7ed2..8aa9123ed5c5683ca003dafb5b15c12b5cc3b773 100644 (file)
@@ -261,6 +261,16 @@ namespace std
       public basic_ostream<_CharT, _Traits>
     {
     public:
+#ifdef _GLIBCPP_RESOLVE_LIB_DEFECTS
+// 271. basic_iostream missing typedefs
+      // Types (inherited):
+      typedef _CharT                                   char_type;
+      typedef typename _Traits::int_type               int_type;
+      typedef typename _Traits::pos_type               pos_type;
+      typedef typename _Traits::off_type               off_type;
+      typedef _Traits                                  traits_type;
+#endif
+
       // Non-standard Types:
       typedef basic_istream<_CharT, _Traits>           __istream_type;
       typedef basic_ostream<_CharT, _Traits>           __ostream_type;
index 012bf4e6cf6bfe1e2f35e78f93d439c6e3b1bfcc..0270c181c126c988519e1fdd7f79f4792afe8e06 100644 (file)
@@ -91,10 +91,10 @@ namespace std
       char_type*               _M_buf;         
 
       // Actual size of allocated internal buffer, in bytes.
-      int_type                 _M_buf_size;
+      size_t                   _M_buf_size;
 
       // Optimal or preferred size of internal buffer, in bytes.
-      int_type                 _M_buf_size_opt;
+      size_t                   _M_buf_size_opt;
 
       // True iff _M_in_* and _M_out_* buffers should always point to
       // the same place.  True for fstreams, false for sstreams.
@@ -126,7 +126,7 @@ namespace std
       // requirements. The only basic_streambuf member function that
       // needs access to these data members is in_avail...
       // NB: pbacks of over one character are not currently supported.
-      static const int_type            _S_pback_size = 1; 
+      static const size_t      _S_pback_size = 1; 
       char_type                        _M_pback[_S_pback_size]; 
       char_type*               _M_pback_cur_save;
       char_type*               _M_pback_end_save;
@@ -140,8 +140,8 @@ namespace std
       {
        if (!_M_pback_init)
          {
-           int_type __dist = _M_in_end - _M_in_cur;
-           int_type __len = min(_S_pback_size, __dist);
+           size_t __dist = _M_in_end - _M_in_cur;
+           size_t __len = min(_S_pback_size, __dist);
            traits_type::copy(_M_pback, _M_in_cur, __len);
            _M_pback_cur_save = _M_in_cur;
            _M_pback_end_save = _M_in_end;
@@ -159,12 +159,12 @@ namespace std
        if (_M_pback_init)
          {
            // Length _M_in_cur moved in the pback buffer.
-           int_type __off_cur = _M_in_cur - _M_pback;
+           size_t __off_cur = _M_in_cur - _M_pback;
            
            // For in | out buffers, the end can be pushed back...
-           int_type __off_end = 0;
-           int_type __pback_len = _M_in_end - _M_pback;
-           int_type __save_len = _M_pback_end_save - _M_buf;
+           size_t __off_end = 0;
+           size_t __pback_len = _M_in_end - _M_pback;
+           size_t __save_len = _M_pback_end_save - _M_buf;
            if (__pback_len > __save_len)
              __off_end = __pback_len - __save_len;
 
@@ -288,8 +288,8 @@ namespace std
          {
            if (_M_pback_init)
              {
-               int_type __save_len =  _M_pback_end_save - _M_pback_cur_save;
-               int_type __pback_len = _M_in_cur - _M_pback;
+               size_t __save_len =  _M_pback_end_save - _M_pback_cur_save;
+               size_t __pback_len = _M_in_cur - _M_pback;
                __ret = __save_len - __pback_len;
              }
            else
@@ -304,7 +304,8 @@ namespace std
       snextc()
       {
        int_type __eof = traits_type::eof();
-       return (this->sbumpc() == __eof ? __eof : this->sgetc()); 
+       return (traits_type::eq_int_type(this->sbumpc(), __eof) 
+               ? __eof : this->sgetc());
       }
 
       int_type 
@@ -342,10 +343,10 @@ namespace std
 
     protected:
       basic_streambuf()
-      : _M_buf(NULL), _M_buf_size(0), 
-      _M_buf_size_opt(static_cast<int_type>(BUFSIZ)), _M_buf_unified(false), 
-      _M_in_beg(0), _M_in_cur(0), _M_in_end(0), _M_out_beg(0), _M_out_cur(0), 
-      _M_out_end(0), _M_mode(ios_base::openmode(0)), _M_buf_locale(locale()), 
+      : _M_buf(NULL), _M_buf_size(0), _M_buf_size_opt(BUFSIZ), 
+      _M_buf_unified(false), _M_in_beg(0), _M_in_cur(0), _M_in_end(0), 
+      _M_out_beg(0), _M_out_cur(0), _M_out_end(0), 
+      _M_mode(ios_base::openmode(0)), _M_buf_locale(locale()), 
       _M_buf_locale_init(false), _M_pback_cur_save(0), _M_pback_end_save(0), 
       _M_pback_init(false)
       { }
@@ -438,7 +439,7 @@ namespace std
       uflow() 
       {
        int_type __ret = traits_type::eof();
-       bool __testeof = this->underflow() == __ret;
+       bool __testeof = traits_type::eq_int_type(this->underflow(), __ret);
        bool __testpending = _M_in_cur && _M_in_cur < _M_in_end;
        if (!__testeof && __testpending)
          {
index 74f14b5a4a25c67987cc803cc2176d9e44e53b71..475083be3fc15a386992c74e36326fb8536046fc 100644 (file)
@@ -88,6 +88,10 @@ void operator delete[](void*, const std::nothrow_t&) throw();
 // Default placement versions of operator new.
 inline void* operator new(std::size_t, void* __p) throw() { return __p; }
 inline void* operator new[](std::size_t, void* __p) throw() { return __p; }
+
+// Default placement versions of operator delete.
+inline void  operator delete  (void*, void*) throw() { };
+inline void  operator delete[](void*, void*) throw() { };
 //@}
 } // extern "C++"
 
index 26c2834eb7d6afdf0f6bd9070ed44e25c492bd57..3cb9d1b4cbfd1f569b700add610f38263c66b364 100644 (file)
@@ -202,7 +202,7 @@ namespace std
        if (strcmp(__s, "C") == 0 || strcmp(__s, "POSIX") == 0)
          (_M_impl = _S_classic)->_M_add_reference();
        else if (strcmp(__s, "") == 0)
-         _M_impl = new _Impl(setlocale(LC_ALL, __s), 1);
+         _M_impl = new _Impl(setlocale(LC_ALL, NULL), 1);
        else
          _M_impl = new _Impl(__s, 1);
       }
index 824d9790cef9f5e8b81248a626e2de96e6854a53..8fa911891705aad7dfab3ff7627c02f5731def3c 100644 (file)
@@ -132,8 +132,8 @@ namespace std
     _M_init_facet(new num_get<char>);
     _M_init_facet(new num_put<char>);
     _M_init_facet(new std::collate<char>(__cloc));
-    _M_init_facet(new moneypunct<char, false>(__cloc));
-    _M_init_facet(new moneypunct<char, true>(__cloc));
+    _M_init_facet(new moneypunct<char, false>(__cloc, __s));
+    _M_init_facet(new moneypunct<char, true>(__cloc, __s));
     _M_init_facet(new money_get<char>);
     _M_init_facet(new money_put<char>);
     _M_init_facet(new __timepunct<char>(__cloc, __s));
@@ -148,8 +148,8 @@ namespace std
     _M_init_facet(new num_get<wchar_t>);
     _M_init_facet(new num_put<wchar_t>);
     _M_init_facet(new std::collate<wchar_t>(__cloc));
-    _M_init_facet(new moneypunct<wchar_t, false>(__cloc));
-    _M_init_facet(new moneypunct<wchar_t, true>(__cloc));
+    _M_init_facet(new moneypunct<wchar_t, false>(__cloc, __s));
+    _M_init_facet(new moneypunct<wchar_t, true>(__cloc, __s));
     _M_init_facet(new money_get<wchar_t>);
     _M_init_facet(new money_put<wchar_t>);
     _M_init_facet(new __timepunct<wchar_t>(__cloc, __s));
index 8735799c7a8340bf79f7bce39b55a2311a72c0fe..732ec1714aa23b6ae6dc638ce4f1a775b1835ffe 100644 (file)
@@ -25,7 +25,6 @@
 #include <stdexcept>
 #include <testsuite_hooks.h>
 
-
 void test00()
 {
   // Should be able to do this as the first thing that happens in a
@@ -238,7 +237,21 @@ void test01()
 }
 #endif // _GLIBCPP_USE___ENC_TRAITS
 
-int main ()
+// libstdc++/7222
+void test02()
+{
+  bool test = true;
+  std::locale loc_c1("C");
+  std::locale loc_c2 ("C");
+  
+  std::locale loc_1("");
+  std::locale loc_2("");
+
+  VERIFY( loc_c1 == loc_c2 );
+  VERIFY( loc_1 == loc_2 );
+}
+
+int main()
 {
   test00();
 
@@ -246,5 +259,7 @@ int main ()
   test01();
 #endif 
 
+  test02();
+
   return 0;
 }
index 98aa8c0b2589fa250fdf2db045d97396eaf3793e..7acd1ec26e1a581adcee085798731266ad7772d0 100644 (file)
@@ -577,6 +577,17 @@ wrong_stuff()
    return failures;
 }
 
+// libstdc++/6642
+int
+test6642()
+{
+   std::string s;
+   std::string::iterator it = s.begin();
+   std::string::const_iterator cit = s.begin();
+
+   return it - cit;
+}
+
 int
 main(int argc, char **argv)
 {
@@ -590,6 +601,8 @@ main(int argc, char **argv)
 
    failures += wrong_stuff();
 
+   failures += test6642();
+
 #ifdef DEBUG_ASSERT
    assert (failures == 0);
 #endif
index 558d196f9fb359de9dc8a8522b397a55cb102f62..9919365a552b3d3f37cedf00d3fdde6a068811aa 100644 (file)
 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
 // USA.
 
-// NB: this test assumes that _M_buf_size == 40, and not the usual
-// buffer_size length of BUFSIZ (8192), so that overflow/underflow can be
-// simulated a bit more readily.
+// 27.8.1.1 - Template class basic_filebuf 
+// NB: This file is for testing basic_filebuf with NO OTHER INCLUDES.
 
 #include <fstream>
 #include <testsuite_hooks.h>
 
 // { dg-do compile }
 
+// libstdc++/7216
+void test01()
+{
+  // Check for required typedefs
+  typedef std::filebuf test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
+}
+
 // test05
 // libstdc++/1886
 // should be able to instantiate basic_filebuf for non-standard types.
@@ -35,6 +46,7 @@ template class std::basic_filebuf<short, std::char_traits<short> >;
 
 int main() 
 {
+  test01();
   return 0;
 }
 
index 26849ac0fd2f318bd7ffb0bf29c50c8c01142043..943819bf82fd572b0f16dda98c089b4fcbc77223 100644 (file)
 
 #include <istream>
 
+// libstdc++/7216
+void test01()
+{
+  // Check for required typedefs
+  typedef std::iostream test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
+}
+
 namespace test 
 {
   using namespace std;
@@ -43,5 +55,6 @@ namespace test
 
 int main() 
 {
+  test01();
   return 0;
 }
index ef88a39f727e00004799d1f9ffb5f0b5ea988af1..05db50ed461f627ebc366b4a03b671e492a9235b 100644 (file)
 
 // { dg-do compile }
 
+// libstdc++/7216
+void test01()
+{
+  // Check for required typedefs
+  typedef std::istream test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
+}
+
 namespace test 
 {
   using namespace std;
@@ -43,5 +55,6 @@ namespace test
 
 int main() 
 {
+  test01();
   return 0;
 }
index da2cdeb739ed12c5c2685f67975ae2c4faf74f11..0e98dced1082028b08cc92cd1fc758fedfd001e3 100644 (file)
@@ -514,6 +514,43 @@ test09()
   VERIFY( test );
 }
 
+// libstdc++/70220
+void
+test10()
+{
+  using namespace std;
+  bool test = true;
+  typedef string string_type;
+  typedef stringbuf stringbuf_type;
+  typedef istream istream_type;
+
+  int res = 0;
+  streamsize n;
+  string_type  input("abcdefg\n");
+  stringbuf_type sbuf(input);
+  istream_type  istr(&sbuf);
+  
+  istr.ignore(0);
+  if (istr.gcount() != 0) 
+    test = false;
+  VERIFY( test );
+  
+  istr.ignore(0, 'b');
+  if (istr.gcount() != 0) 
+    test = false;
+  VERIFY( test );
+  
+  istr.ignore();       // Advance to next position.
+  istr.ignore(0, 'b');
+  if ((n=istr.gcount()) != 0) 
+    test = false;
+  VERIFY( test );
+  
+  if (istr.peek() != 'b')
+    test = false;
+  VERIFY( test );
+}
+
 int 
 main()
 {
@@ -526,6 +563,7 @@ main()
   test07();
   test08();
   test09();
+  test10();
 
   return 0;
 }
index cbc4a6739c2b8f47f43bef8be605ec9df17f27d2..ae524ec61f29eb32efcaee96806ef569f75b2758 100644 (file)
 
 // { dg-do compile }
 
+// libstdc++/7216
+void test01()
+{
+  // Check for required typedefs
+  typedef std::ostream test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
+}
+
 namespace test 
 {
   using namespace std;
@@ -43,5 +55,6 @@ namespace test
 
 int main() 
 {
+  test01();
   return 0;
 }
index 4e7f861b516f8990886dcbc10da65eef6144604a..bf823697c830811400126d5b26466d8fc34ced79 100644 (file)
@@ -1,6 +1,6 @@
 // 2001-05-23 Benjamin Kosnik  <bkoz@redhat.com>
 
-// Copyright (C) 2001 Free Software Foundation, Inc.
+// Copyright (C) 2001, 2002 Free Software Foundation, Inc.
 //
 // This file is part of the GNU ISO C++ Library.  This library is free
 // software; you can redistribute it and/or modify it under the
@@ -97,9 +97,61 @@ void test02()
   // These semantics are a joke, a serious defect, and incredibly lame.
 }
 
+// 03: sanity checks for strings, stringbufs
+void
+test03()
+{
+  bool test = false;
+
+  // Empty string sanity check.
+  std::string str01;
+  std::string::iterator __i_start = str01.begin();
+  std::string::iterator __i_end = str01.end();
+  std::string::size_type len = str01.size();
+  test = __i_start == __i_end;
+  VERIFY( len == 0 );
+
+  // Full string sanity check.
+  std::string str02("these golden days, i spend waiting for you:\n"
+                   "Betty Carter on Verve with I'm Yours and You're Mine.");
+  __i_start = str02.begin();
+  __i_end = str02.end();
+  len = str02.size();
+  VERIFY( __i_start != __i_end );
+  VERIFY( len != 0 );
+  // Test an empty ostringstream for sanity.
+  std::ostringstream ostrstream0;
+  std::string str03 = ostrstream0.str();
+  __i_start = str03.begin();
+  __i_end = str03.end();
+  len = str03.size();
+  VERIFY( __i_start == __i_end );
+  VERIFY( len == 0 );
+  VERIFY( str01 == str03 );
+}
+
+// user-reported error
+class derived_oss: public std::ostringstream 
+{
+public:
+  derived_oss() : std::ostringstream() { }
+};
+
+void
+test04()
+{
+  bool test = true;
+  derived_oss yy;
+  yy << "buena vista social club\n";
+  VERIFY( yy.str() == std::string("buena vista social club\n") );
+}
+
 int main()
 {
   test01();
   test02();
+  test03();
+  test04();
   return 0;
 }
index 3f9a3192b7e0174c1ccb6aa843a185d585210f6f..905dee089de81cac8c2892af5d7c2d2fd81791a9 100644 (file)
@@ -1,6 +1,6 @@
-// 1999-10-11 bkoz
+// 2002-07-25 Benjamin Kosnik <bkoz@redhat.com>
 
-// Copyright (C) 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
+// Copyright (C) 2002 Free Software Foundation, Inc.
 //
 // This file is part of the GNU ISO C++ Library.  This library is free
 // software; you can redistribute it and/or modify it under the
 // invalidate any other reasons why the executable file might be covered by
 // the GNU General Public License.
 
-// 27.5.2 template class basic_streambuf
+// 27.5.2 - Template class basic_streambuf
+// NB: This file is for testing basic_streambuf with NO OTHER INCLUDES.
 
-#include <cstring> // for memset, memcmp
 #include <streambuf>
-#include <string>
-#include <ostream>
-#include <testsuite_hooks.h>
 
-class testbuf : public std::streambuf
-{
-public:
-
-  // Typedefs:
-  typedef std::streambuf::traits_type traits_type;
-  typedef std::streambuf::char_type char_type;
-
-  testbuf(): std::streambuf() 
-  { _M_mode = (std::ios_base::in | std::ios_base::out); }
-
-  bool
-  check_pointers()
-  { 
-    bool test = true;
-    VERIFY( this->eback() == NULL );
-    VERIFY( this->gptr() == NULL );
-    VERIFY( this->egptr() == NULL );
-    VERIFY( this->pbase() == NULL );
-    VERIFY( this->pptr() == NULL );
-    VERIFY( this->epptr() == NULL );
-    return test;
-  }
-
-  int_type 
-  pub_uflow() 
-  { return (this->uflow()); }
-
-  int_type 
-  pub_overflow(int_type __c = traits_type::eof()) 
-  { return (this->overflow(__c)); }
-
-  int_type 
-  pub_pbackfail(int_type __c) 
-  { return (this->pbackfail(__c)); }
-
-  void 
-  pub_setg(char* beg, char* cur, char *end) 
-  { this->setg(beg, cur, end); }
-
-  void 
-  pub_setp(char* beg, char* end) 
-  { this->setp(beg, end); }
-
-protected:
-  int_type 
-  underflow() 
-  { 
-    int_type __retval = traits_type::eof();
-    if (this->gptr() < this->egptr())
-      __retval = traits_type::not_eof(0); 
-    return __retval;
-  }
-};
+// { dg-do compile }
 
+// libstdc++/7216
 void test01()
 {
-  typedef testbuf::traits_type traits_type;
-  typedef testbuf::int_type int_type;
-
-  bool test = true;
-  char* lit01 = "chicago underground trio/possible cube on delmark";
-  testbuf buf01;
-
-  // 27.5.2.1 basic_streambuf ctors
-  // default ctor initializes 
-  // - all pointer members to null pointers
-  // - locale to current global locale
-  VERIFY( buf01.check_pointers() );
-  VERIFY( buf01.getloc() == std::locale() );
-
-  // 27.5.2.3.1 get area
-  // 27.5.2.2.3 get area
-  // 27.5.2.4.3 get area
-  int i01 = 3;
-  buf01.pub_setg(lit01, lit01, (lit01 + i01));
-  VERIFY( i01 == buf01.in_avail() );
-
-  VERIFY( buf01.pub_uflow() == lit01[0] );
-  VERIFY( buf01.sgetc() == traits_type::to_int_type(lit01[1]) );
-  VERIFY( buf01.pub_uflow() == lit01[1] );
-  VERIFY( buf01.sgetc() == traits_type::to_int_type(lit01[2]) );
-  VERIFY( buf01.pub_uflow() == lit01[2] );
-  VERIFY( buf01.sgetc() == traits_type::eof() );
-
-  // pbackfail
-  buf01.pub_setg(lit01, lit01, (lit01 + i01));
-  VERIFY( i01 == buf01.in_avail() );
-  int_type intt01 = traits_type::to_int_type('b');
-  VERIFY( traits_type::eof() == buf01.pub_pbackfail(intt01) );
-
-  // overflow
-  VERIFY( traits_type::eof() == buf01.pub_overflow(intt01) );
-  VERIFY( traits_type::eof() == buf01.pub_overflow() );
-  VERIFY( buf01.sgetc() == traits_type::to_int_type(lit01[0]) );
-
-  // sputn/xsputn
-  char* lit02 = "isotope 217: the unstable molecule on thrill jockey";
-  int i02 = std::strlen(lit02);
-  char carray[i02 + 1];
-  std::memset(carray, 0, i02 + 1);
-
-  buf01.pub_setp(carray, (carray + i02));
-  buf01.sputn(lit02, 0);
-  VERIFY( carray[0] == 0 );
-  VERIFY( lit02[0] == 'i' );
-  buf01.sputn(lit02, 1);
-  VERIFY( lit02[0] == carray[0] );
-  VERIFY( lit02[1] == 's' );
-  VERIFY( carray[1] == 0 );
-  buf01.sputn(lit02 + 1, 10);
-  VERIFY( std::memcmp(lit02, carray, 10) == 0 );
-  buf01.sputn(lit02 + 11, 20);
-  VERIFY( std::memcmp(lit02, carray, 30) == 0 );
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
-}
-
-void test02()
-{
-  typedef testbuf::traits_type traits_type;
-  typedef testbuf::int_type int_type;
-
-  bool test = true;
-  char* lit01 = "chicago underground trio/possible cube on delmark";
-  testbuf buf01;
-
-  // 27.5.2.1 basic_streambuf ctors
-  // default ctor initializes 
-  // - all pointer members to null pointers
-  // - locale to current global locale
-  VERIFY( buf01.check_pointers() );
-  VERIFY( buf01.getloc() == std::locale() );
-
-  // 27.5.2.2.5 Put area
-  size_t i01 = traits_type::length(lit01);
-  char carray01[i01];
-  std::memset(carray01, 0, i01);
-  
-  buf01.pub_setg(lit01, lit01, lit01 + i01);
-  buf01.sgetn(carray01, 0);
-  VERIFY( carray01[0] == 0 );
-  buf01.sgetn(carray01, 1);
-  VERIFY( carray01[0] == 'c' );
-  buf01.sgetn(carray01 + 1, i01 - 1);
-  VERIFY( carray01[0] == 'c' );
-  VERIFY( carray01[1] == 'h' );
-  VERIFY( carray01[i01 - 1] == 'k' );
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
+  // Check for required typedefs
+  typedef std::streambuf test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
 }
-// test03
-// http://gcc.gnu.org/ml/libstdc++/2000-q1/msg00151.html
-template<typename charT, typename traits = std::char_traits<charT> >
-  class basic_nullbuf : public std::basic_streambuf<charT, traits>
-  {
-  protected:
-    typedef typename
-      std::basic_streambuf<charT, traits>::int_type int_type;
-    virtual int_type 
-    overflow(int_type c) 
-    {  return traits::not_eof(c); }
-  };
-
-typedef basic_nullbuf<char> nullbuf;
-typedef basic_nullbuf<wchar_t> wnullbuf;
-
-template<typename T>
-  char
-  print(const T& x) 
-  {
-   nullbuf ob;
-   std::ostream out(&ob); 
-   out << x << std::endl;
-   return (!out ? '0' : '1');
- }
 
-void test03() 
+namespace test 
 {
-  bool test = true;
-  const std::string control01("11111");
-  std::string test01;
-
-  test01 += print(true);
-  test01 += print(3.14159);
-  test01 += print(10);
-  test01 += print('x');
-  test01 += print("pipo");
-
-  VERIFY( test01 == control01 );
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
-}
-
-class setpbuf : public std::streambuf
-{
-  char                 buffer[4];
-  std::string  result;
-
-public:
-
-  std::string&
-  get_result()
-  { return result; }
-
-  setpbuf()
-  {
-    char foo [32];
-    setp(foo, foo + 32);
-    setp(buffer, buffer + 4);
-  }
-
-  ~setpbuf()
-  { sync(); }
-
-  virtual int_type 
-  overflow(int_type n)
-  {
-    if (sync() != 0)
-      return traits_type::eof();
-    
-    result += traits_type::to_char_type(n);
-    
-    return n;
-  }
-  
-  virtual int 
-  sync()
-  {
-    result.append(pbase(), pptr());
-    setp(buffer, buffer + 4);
-    return 0;
-  }
-};
-
-// libstdc++/1057
-void test04()
-{
-  bool test = true;
-  std::string text = "abcdefghijklmn";
-  
-  // 01
-  setpbuf sp1;
-  // Here xsputn writes over sp1.result
-  sp1.sputn(text.c_str(), text.length());
-
-  // This crashes when result is accessed
-  sp1.pubsync();
-  VERIFY( sp1.get_result() == text );
-  
-
-  // 02
-  setpbuf sp2;
-  for (std::string::size_type i = 0; i < text.length(); ++i)
-    {
-      // sputc also writes over result
-      sp2.sputc(text[i]);
-    }
-  
-  // Crash here
-  sp2.pubsync();
-  VERIFY( sp2.get_result() == text );
-}
-
-class nullsetpbuf : public std::streambuf
-{
-  char foo[64];
-public:
-  nullsetpbuf()
-  {
-    setp(foo, foo + 64);
-    setp(NULL, NULL);
-  }
-};
-
-// libstdc++/1057
-void test05()
-{
-    std::string text1 = "abcdefghijklmn";
-
-    nullsetpbuf nsp;
-    // Immediate crash as xsputn writes to null pointer
-    nsp.sputn(text1.c_str(), text1.length());
-    // ditto
-    nsp.sputc('a');
-}
-
-// test06
-namespace gnu 
-{
-  class something_derived;
-}
-
-class gnu::something_derived : std::streambuf { };
-
-// libstdc++/3599
-class testbuf2 : public std::streambuf
-{
-public:
-  typedef std::streambuf::traits_type traits_type;
-
-  testbuf2() : std::streambuf() { }
-protected:
-  int_type 
-  overflow(int_type c = traits_type::eof()) 
-  { return traits_type::not_eof(0); }
-};
-
-void
-test07()
-{
-  bool test = true;
-  testbuf2 ob;
-  std::ostream out(&ob); 
-
-  out << "gasp";
-  VERIFY(out.good());
-
-  out << std::endl;
-  VERIFY(out.good());
-}
+  using namespace std;
+  typedef short type_t;
+  template class basic_streambuf<type_t, char_traits<type_t> >;
+} // test
 
 int main() 
 {
   test01();
-  test02();
-  test03();
-
-  test04();
-  test05();
-
-  test07();
   return 0;
 }
index bc0bbb4dd8e1365e5ffe2135e991ba0ce7da342d..00825b6b69c7130b20babc83ea34895f4a958ec5 100644 (file)
@@ -1,7 +1,6 @@
-// 981208 bkoz test functionality of basic_stringbuf for char_type == char
+// 2002-07-25 Benjamin Kosnik <bkoz@redhat.com>
 
-// Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002
-// Free Software Foundation, Inc.
+// Copyright (C) 2002 Free Software Foundation, Inc.
 //
 // This file is part of the GNU ISO C++ Library.  This library is free
 // software; you can redistribute it and/or modify it under the
 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
 // USA.
 
-#include <sstream>
-#include <testsuite_hooks.h>
-
-std::string str_01("mykonos. . . or what?");
-std::string str_02("paris, or sainte-maxime?");
-std::string str_03;
-std::stringbuf strb_01(str_01);
-std::stringbuf strb_02(str_02, std::ios_base::in);
-std::stringbuf strb_03(str_03, std::ios_base::out);
-
-
-// test the underlying allocator
-bool test01() {
-  bool test = false;
-  std::allocator<char> alloc_01;
-  std::allocator<char>::size_type size_01 = alloc_01.max_size();
-  std::allocator<char>::pointer p_01 = alloc_01.allocate(32);
-
-  return true;
-}
-
-
-// test the streambuf/stringbuf locale settings
-bool test02() {
-  std::locale loc_tmp;
-  loc_tmp = strb_01.getloc();
-  strb_01.pubimbue(loc_tmp); //This should initialize _M_init to true
-  strb_01.getloc(); //This should just return _M_locale
-
-  return true;
-}
-
-
-// test member functions
-bool test03() {
-  bool test = true;
-
-  //stringbuf::str()
-  VERIFY( strb_01.str() == str_01 );
-  VERIFY( strb_02.str() == str_02 );
-  VERIFY( strb_03.str() == str_03 );
-  //stringbuf::str(string&)
-  strb_03.str("none of the above, go to the oberoi in cairo, egypt.");
-  strb_03.str(str_01);
-  std::streamsize d1 = strb_01.in_avail();
-  std::streamsize d2 = strb_03.in_avail();
-  VERIFY( d1 ); // non-zero
-  VERIFY( !d2 ); // zero, cuz ios_base::out
-  VERIFY( d1 != d2 ); //these should be the same
-  VERIFY( str_01.length() == d1 );  
-  VERIFY( strb_01.str() == strb_03.str() ); //ditto
-
-  // stringbuf::str(string&) and stringbuf::stringbuf(string&), where the
-  // string in question contains embedded NUL characters.  Note that in this
-  // embedded-NUL situation, the size must be passed to the string ctor.
-  std::string str_nulls ("eschew \0 obfuscation", 20);  // tested in 21_strings
-  std::stringbuf strb_normal (str_01);
-  std::stringbuf strb_nulls (str_nulls);
-  strb_normal.str(str_nulls);  // tried using 'strb_01' rather than declaring
-                               // another variable, but then test04 broke!
-  VERIFY( strb_nulls.in_avail() == str_nulls.size()  );
-  VERIFY( strb_nulls.str().size() == 20              );
-  VERIFY( strb_normal.in_avail() == str_nulls.size() );
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
-  return test;
-}
-
-
-// test overloaded virtual functions
-bool test04() {
-  bool                         test = true;
-  std::string          str_tmp;
-  std::stringbuf               strb_tmp;
-  std::streamsize              strmsz_1, strmsz_2;
-  std::streamoff               strmof_1(-1), strmof_2;
-  typedef std::stringbuf::int_type int_type;
-  typedef std::stringbuf::traits_type traits_type;
-  typedef std::stringbuf::pos_type pos_type;
-  typedef std::stringbuf::off_type off_type;
-
-  // GET
-  // int in_avail()
-  strmof_1 = strb_01.in_avail();
-  strmof_2 = strb_02.in_avail();
-  VERIFY( strmof_1 != strmof_2 );
-  VERIFY( strmof_1 == str_01.length() );
-  VERIFY( strmof_2 == str_02.length() );
-  strmof_1 = strb_03.in_avail(); 
-  VERIFY( strmof_1 == 0 ); // zero cuz write-only, or eof()? zero, from showmany
-
-  // int_type sbumpc()
-  // if read_cur not avail, return uflow(), else return *read_cur & increment
-  int_type c1 = strb_01.sbumpc();
-  int_type c2 = strb_02.sbumpc();
-  VERIFY( c1 != c2 );
-  VERIFY( c1 == str_01[0] );
-  VERIFY( c2 == str_02[0] ); //should equal first letter at this point
-  int_type c3 = strb_01.sbumpc();
-  int_type c4 = strb_02.sbumpc();
-  VERIFY( c1 != c2 );
-  VERIFY( c1 != c3 );
-  VERIFY( c2 != c4 );
-  int_type c5 = strb_03.sbumpc();
-  VERIFY( c5 == traits_type::eof() );
-
-  // int_type sgetc()
-  // if read_cur not avail, return uflow(), else return *read_cur  
-  int_type c6 = strb_01.sgetc();
-  int_type c7 = strb_02.sgetc();
-  VERIFY( c6 != c3 );
-  VERIFY( c7 != c4 );
-  int_type c8 = strb_01.sgetc();
-  int_type c9 = strb_02.sgetc();
-  VERIFY( c6 == c8 );
-  VERIFY( c7 == c9 );
-  c5 = strb_03.sgetc();
-  VERIFY( c5 == traits_type::eof() );
-
-  // int_type snextc()
-  // calls sbumpc and if sbumpc != eof, return sgetc
-  c6 = strb_01.snextc();
-  c7 = strb_02.snextc();
-  VERIFY( c6 != c8 );
-  VERIFY( c7 != c9 );
-  VERIFY( c6 == str_01[3] );
-  VERIFY( c7 == str_02[3] ); //should equal fourth letter at this point
-  c5 = strb_03.snextc();
-  VERIFY( c5 == traits_type::eof() );
-
-  // int showmanyc
-  // streamsize sgetn(char_type *s, streamsize n)
-  // streamsize xsgetn(char_type *s, streamsize n)
-  // assign up to n chars to s from input sequence, indexing in_cur as
-  // approp and returning the number of chars assigned
-  strmsz_1 = strb_01.in_avail();
-  strmsz_2 = strb_02.in_avail();
-  test = strmsz_1 != strmsz_2;
-  VERIFY( strmsz_1 != str_01.length() );
-  VERIFY( strmsz_2 != str_02.length() ); //because now we've moved into string
-  char carray1[11] = "";
-  strmsz_1 = strb_01.sgetn(carray1, 10);
-  char carray2[20] = "";
-  strmsz_2 = strb_02.sgetn(carray2, 10);
-  VERIFY( strmsz_1 == strmsz_2 );
-  VERIFY( strmsz_1 == 10 );
-  c1 = strb_01.sgetc();
-  c2 = strb_02.sgetc();
-  VERIFY( c6 == c1 ); //just by co-incidence both o's
-  VERIFY( c7 != c2 ); // n != i
-  VERIFY( c1 == str_01[13] );
-  VERIFY( c2 == str_02[13] ); //should equal fourteenth letter at this point
-  strmsz_1 = strb_03.sgetn(carray1, 10);
-  VERIFY( !strmsz_1 ); //zero
-  strmsz_1 = strb_02.in_avail();
-  strmsz_2 = strb_02.sgetn(carray2, strmsz_1 + 5);
-  VERIFY( strmsz_1 == strmsz_2 ); //write off the end
-  c4 = strb_02.sgetc(); // should be EOF
-  VERIFY( c4 == traits_type::eof() );
-
-  // PUT
-  // int_type sputc(char_type c)
-  // if out_cur not avail, return overflow. Else, stores c at out_cur,
-  // increments out_cur, and returns c as int_type
-  strb_03.str(str_01); //reset
-  std::string::size_type sz1 = strb_03.str().length();
-  c1 = strb_03.sputc('a'); 
-  std::string::size_type sz2 = strb_03.str().length();
-  VERIFY( sz1 == sz2 ); //cuz inserting at out_cur, which is at beg to start
-  c2 = strb_03.sputc('b'); 
-  VERIFY( c1 != c2 );
-  VERIFY( strb_03.str() != str_01 );
-  c3 = strb_02.sputc('a'); // should be EOF because this is read-only
-  VERIFY( c3 == traits_type::eof() );
-  
-  // streamsize sputn(const char_typs* s, streamsize n)
-  // write up to n chars to out_cur from s, returning number assigned
-  // NB *sputn will happily put '\0' into your stream if you give it a chance*
-  str_tmp = strb_03.str();
-  sz1 = str_tmp.length();
-  strmsz_1 = strb_03.sputn("racadabras", 10);//"abracadabras or what?"
-  sz2 = strb_03.str().length();
-  VERIFY( sz1 == sz2 ); //shouldn't have changed length
-  VERIFY( strmsz_1 == 10 );
-  VERIFY( str_tmp != strb_03.str() );
-  strmsz_2 = strb_03.sputn(", i wanna reach out and", 10);
-  VERIFY( strmsz_1 == strmsz_2 ); // should re-allocate, copy 10 chars.
-  VERIFY( strmsz_1 == 10 );
-  VERIFY( strmsz_2 == 10 );
-  sz2 = strb_03.str().length();
-  VERIFY( sz1 != sz2 ); // need to change length
-  VERIFY( str_tmp != strb_03.str() );
-  str_tmp = strb_02.str();
-  strmsz_1 = strb_02.sputn("racadabra", 10);
-  VERIFY( strmsz_1 == 0 );  
-  VERIFY( str_tmp == strb_02.str() );
-
-  // PUTBACK
-  // int_type pbfail(int_type c)
-  // called when gptr() null, gptr() == eback(), or traits::eq(*gptr, c) false
-  // "pending sequence" is:
-  //   1) everything as defined in underflow
-  //   2) + if (traits::eq_int_type(c, traits::eof()), then input
-  //   sequence is backed up one char before the pending sequence is
-  //   determined.
-  //   3) + if (not 2) then c is prepended. Left unspecified is
-  //   whether the input sequence is backedup or modified in any way
-  // returns traits::eof() for failure, unspecified other value for success
+// As a special exception, you may use this file as part of a free software
+// library without restriction.  Specifically, if other files instantiate
+// templates or use macros or inline functions from this file, or you compile
+// this file and link it with other files to produce an executable, this
+// file does not by itself cause the resulting executable to be covered by
+// the GNU General Public License.  This exception does not however
+// invalidate any other reasons why the executable file might be covered by
+// the GNU General Public License.
 
-  // int_type sputbackc(char_type c)
-  // if in_cur not avail || ! traits::eq(c, gptr() [-1]), return pbfail
-  // otherwise decrements in_cur and returns *gptr()
-  strmsz_1 = strb_01.in_avail();
-  str_tmp = strb_01.str();
-  c1 = strb_01.sgetc(); //"mykonos. . . 'o'r what?"
-  c2 = strb_01.sputbackc('z');//"mykonos. . .zor what?"
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( c3 == c2 );
-  VERIFY( strb_01.str() == std::string("mykonos. . .zor what?") );
-  VERIFY( str_tmp.size() == strb_01.str().size() );
-  //test for _in_cur == _in_beg
-  strb_01.str(str_tmp);
-  strmsz_1 = strb_01.in_avail();
-  c1 = strb_01.sgetc(); //"'m'ykonos. . . or what?"
-  c2 = strb_01.sputbackc('z');//"mykonos. . . or what?"
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( c3 != c2 );
-  VERIFY( c1 == c3 );
-  VERIFY( c2 == traits_type::eof() );
-  VERIFY( strb_01.str() == str_tmp );
-  VERIFY( str_tmp.size() == strb_01.str().size() );
-  // test for replacing char with identical one
-  strb_01.str(str_01); //reset
-  strmsz_1 = strb_01.in_avail();
-  strb_01.sbumpc();
-  strb_01.sbumpc();
-  c1 = strb_01.sgetc(); //"my'k'onos. . . or what?"
-  c2 = strb_01.sputbackc('y');//"mykonos. . . or what?"
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( c3 == c2 );
-  VERIFY( c1 != c3 );
-  VERIFY( strb_01.str() == str_01 );
-  VERIFY( str_01.size() == strb_01.str().size() );
-  //test for ios_base::out
-  strmsz_2 = strb_03.in_avail();
-  c4 = strb_03.sputbackc('x');
-  VERIFY( c4 == traits_type::eof() );
+// 27.7.1 - Template class basic_stringbuf
+// NB: This file is for testing basic_stringbuf with NO OTHER INCLUDES.
 
-  // int_type sungetc()
-  // if in_cur not avail, return pbackfail(), else decrement and
-  // return to_int_type(*gptr())
-  for (int i = 0; i<12; ++i)
-    strb_01.sbumpc();
-  strmsz_1 = strb_01.in_avail();
-  str_tmp = strb_01.str();
-  c1 = strb_01.sgetc(); //"mykonos. . . 'o'r what?"
-  c2 = strb_01.sungetc();//"mykonos. . . or what?"
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( c3 == c2 );
-  VERIFY( c1 != c3 );
-  VERIFY( c2 == ' ' );
-  VERIFY( strb_01.str() == str_01 );
-  VERIFY( str_01.size() == strb_01.str().size() );
-  //test for _in_cur == _in_beg
-  strb_01.str(str_tmp);
-  strmsz_1 = strb_01.in_avail();
-  c1 = strb_01.sgetc(); //"'m'ykonos. . . or what?"
-  c2 = strb_01.sungetc();//"mykonos. . . or what?"
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( c3 != c2 );
-  VERIFY( c1 == c3 );
-  VERIFY( c2 == traits_type::eof() );
-  VERIFY( strb_01.str() == str_01 );
-  VERIFY( str_01.size() == strb_01.str().size() );
-  // test for replacing char with identical one
-  strb_01.str(str_01); //reset
-  strmsz_1 = strb_01.in_avail();
-  strb_01.sbumpc();
-  strb_01.sbumpc();
-  c1 = strb_01.sgetc(); //"my'k'onos. . . or what?"
-  c2 = strb_01.sungetc();//"mykonos. . . or what?"
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( c3 == c2 );
-  VERIFY( c1 != c3 );
-  VERIFY( strb_01.str() == str_01 );
-  VERIFY( str_01.size() == strb_01.str().size() );
-  //test for ios_base::out
-  strmsz_2 = strb_03.in_avail();
-  c4 = strb_03.sungetc();
-  VERIFY( c4 == traits_type::eof() );
-
-  // BUFFER MANAGEMENT & POSITIONING
-  // sync
-  // pubsync
-  strb_01.pubsync();
-  strb_02.pubsync();
-  strb_03.pubsync();
-
-  // setbuf
-  // pubsetbuf(char_type* s, streamsize n)
-  str_tmp = std::string("naaaah, go to cebu");
-  strb_01.pubsetbuf(const_cast<char*> (str_tmp.c_str()), str_tmp.size());
-  VERIFY( strb_01.str() == str_tmp );
-  strb_01.pubsetbuf(0,0);
-  VERIFY( strb_01.str() == str_tmp );
-
-  // seekoff
-  // pubseekoff(off_type off, ios_base::seekdir way, ios_base::openmode which)
-  // alters the stream position to off
-  pos_type pt_1(off_type(-1));
-  pos_type pt_2(off_type(0));
-  off_type off_1 = 0;
-  off_type off_2 = 0;
-  strb_01.str(str_01); //in|out ("mykonos. . . or what?");
-  strb_02.str(str_02); //in ("paris, or sainte-maxime?");
-  strb_03.str(str_03); //out ("")
-  //IN|OUT
-  //beg
-  pt_1 = strb_01.pubseekoff(2, std::ios_base::beg);
-  off_1 = pt_1;
-  VERIFY( off_1 >= 0 );
-  c1 = strb_01.snextc(); //current in pointer +1
-  VERIFY( c1 == 'o' );
-  c2 = strb_01.sputc('x');  //test current out pointer
-  str_tmp = std::string("myxonos. . . or what?");
-  VERIFY( strb_01.str() == str_tmp );
-  //cur
-  pt_1 = strb_01.pubseekoff(2, std::ios_base::cur);
-  off_1 = pt_1;
-  VERIFY( off_1 == -1 ); // can't seekoff for in and out + cur in sstreams
-  pt_1 = strb_01.pubseekoff(2, std::ios_base::cur, std::ios_base::in);
-  off_1 = pt_1;
-  pt_2 = strb_01.pubseekoff(2, std::ios_base::cur, std::ios_base::in);
-  off_2 = pt_2;
-  VERIFY( off_2 == off_1 + 2 );
-  c1 = strb_01.snextc(); //current in pointer + 1
-  VERIFY( c1 == ' ' );
-  c2 = strb_01.sputc('x');  //test current out pointer
-  str_tmp = std::string("myxxnos. . . or what?");
-  VERIFY( strb_01.str() == str_tmp );
-  //end
-  pt_2 = strb_01.pubseekoff(2, std::ios_base::end);
-  off_1 = pt_2;
-  VERIFY( off_1 == -1 ); // not a valid position
-  VERIFY( strb_01.str() == str_tmp );
-  // end part two (from the filebuf tests)
-  strb_01.pubseekoff(0, std::ios_base::end);
-  strmsz_1 = strb_01.in_avail(); // 0 cuz at the end
-  c1 = strb_01.sgetc(); 
-  c2 = strb_01.sungetc();
-  strmsz_2 = strb_01.in_avail(); // 1
-  c3 = strb_01.sgetc();
-  VERIFY( c1 != c2 );
-  VERIFY( strmsz_2 != strmsz_1 );
-  VERIFY( strmsz_2 == 1 );
-  // end part three
-  strmsz_1 = strb_01.str().size();
-  strmsz_2 = strb_01.sputn(" ravi shankar meets carlos santana in LoHa", 90);
-  strb_01.pubseekoff(0, std::ios_base::end);
-  strb_01.sputc('<');
-  str_tmp = strb_01.str();
-  VERIFY( str_tmp.size() == strmsz_1 + strmsz_2 + 1 );
-  // IN
-  // OUT
-
-  // seekpos
-  // pubseekpos(pos_type sp, ios_base::openmode)
-  // alters the stream position to sp
-  strb_01.str(str_01); //in|out ("mykonos. . . or what?");
-  strb_02.str(str_02); //in ("paris, or sainte-maxime?");
-  strb_03.str(str_03); //out ("")
-  //IN|OUT
-  //beg
-  pt_1 = strb_01.pubseekoff(2, std::ios_base::beg);
-  off_1 = pt_1;
-  VERIFY( off_1 >= 0 );
-  pt_1 = strb_01.pubseekoff(0, std::ios_base::cur, std::ios_base::out);
-  off_1 = pt_1;
-  c1 = strb_01.snextc(); //current in pointer +1
-  VERIFY( c1 == 'o' );
-  c2 = strb_01.sputc('x');  //test current out pointer
-  str_tmp = std::string("myxonos. . . or what?");
-  VERIFY( strb_01.str() == str_tmp );
-  strb_01.pubsync(); //resets pointers
-  pt_2 = strb_01.pubseekpos(pt_1, std::ios_base::in|std::ios_base::out);
-  off_2 = pt_2;
-  VERIFY( off_1 == off_2 );
-  c3 = strb_01.snextc(); //current in pointer +1
-  VERIFY( c1 == c3 );
-  c2 = strb_01.sputc('x');  //test current out pointer
-  str_tmp = std::string("myxonos. . . or what?");
-  VERIFY( strb_01.str() == str_tmp );
-
-  // VIRTUALS (indirectly tested)
-  // underflow
-  // if read position avail, returns *gptr()
-
-  // pbackfail(int_type c)
-  // put c back into input sequence
-
-  // overflow
-  // appends c to output seq
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
-
-  return test;
-}
+#include <sstream>
 
+// { dg-do compile }
 
-// libstdc++/3955 -- ios_base::app overwrites from the beginning
-bool test05()
+// libstdc++/7216
+void test01()
 {
-  bool test = true;
-
-  std::ostringstream os ("foo");
-  os << "bar";
-
-  test = os.str() == "bar";
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
-
-  return test;
+  // Check for required typedefs
+  typedef std::stringbuf test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
 }
 
-bool test06()
+namespace test 
 {
-  bool test = true;
-
-  std::ostringstream os ("foo", std::ios_base::app);
-  os << "bar";
-
-  test = os.str() == "foobar";
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
+  using namespace std;
+  typedef short type_t;
+  template class basic_stringbuf<type_t, char_traits<type_t> >;
+} // test
 
-  return test;
-}
-
-int main()
+int main() 
 {
   test01();
-  test02();
-  test03();
-  test04();
-  test05();
-  test06();
-
   return 0;
 }
-
-
-
-// more candy!!!
index 45ca438a59031cbd3ac68372c7d0d2615fa694db..1a1b017807418e67330de5663ffa57a7e03b0b67 100644 (file)
@@ -1,7 +1,6 @@
-// 981015 bkoz
-// i,o,stringstream usage
+// 2002-07-25 Benjamin Kosnik <bkoz@redhat.com>
 
-// Copyright (C) 1997, 1998, 1999 Free Software Foundation, Inc.
+// Copyright (C) 2002 Free Software Foundation, Inc.
 //
 // This file is part of the GNU ISO C++ Library.  This library is free
 // software; you can redistribute it and/or modify it under the
 // invalidate any other reasons why the executable file might be covered by
 // the GNU General Public License.
 
-#include <vector>
-#include <string>
-#include <sstream>
-#include <testsuite_hooks.h>
-
-// 01: sanity checks for strings, stringbufs
-std::string 
-test01()
-{
-  bool test = false;
-
-  // Empty string sanity check.
-  std::string str01;
-  std::string::iterator __i_start = str01.begin();
-  std::string::iterator __i_end = str01.end();
-  std::string::size_type len = str01.size();
-  test = __i_start == __i_end;
-  VERIFY( len == 0 );
-
-  // Full string sanity check.
-  std::string str02("these golden days, i spend waiting for you:\n"
-                   "Betty Carter on Verve with I'm Yours and You're Mine.");
-  __i_start = str02.begin();
-  __i_end = str02.end();
-  len = str02.size();
-  VERIFY( __i_start != __i_end );
-  VERIFY( len != 0 );
-  // Test an empty ostring stream for sanity.
-  std::ostringstream ostrstream0;
-  std::string str03 = ostrstream0.str();
-  __i_start = str03.begin();
-  __i_end = str03.end();
-  len = str03.size();
-  VERIFY( __i_start == __i_end );
-  VERIFY( len == 0 );
-  VERIFY( str01 == str03 );
+// 27.7.4 - Template class basic_stringstream
+// NB: This file is for testing basic_stringstream with NO OTHER INCLUDES.
 
-  return str02;
-}
+#include <sstream>
 
+// { dg-do compile }
 
-int
-test02()
+// libstdc++/7216
+void test01()
 {
-  bool test = true;
-
-  //
-  // 1: Automatic formatting of a compound string
-  //
-  int i = 1024;
-  int *pi = &i;
-  double d = 3.14159;
-  double *pd = &d;
-  std::string blank;
-  std::ostringstream ostrst01; 
-  std::ostringstream ostrst02(blank); 
-  
-  // No buffer,so should be created.
-  ostrst01 << "i: " << i << " i's address:  " << pi << "\n"
-            << "d: " << d << " d's address: " << pd << std::endl;
-  // Buffer, so existing buffer should be overwritten.
-  ostrst02 << "i: " << i << " i's address:  " << pi << "\n"
-            << "d: " << d << " d's address: " << pd << std::endl;
-
-  std::string msg01 = ostrst01.str();
-  std::string msg02 = ostrst02.str();
-  VERIFY( msg01 == msg02 );
-  VERIFY( msg02 != blank );
-
-  //
-  // 2: istringstream
-  //
-  // extracts the stored ascii values, placing them in turn in the four vars
-#if 0
-  int i2 = 0;
-  int *pi2 = &i2;
-  double d2 = 0.0;
-  double *pd2 = &d2;
-  std::istringstream istrst01(ostrst02.str());
-
-  istrst01 >> i2 >> pi2 >> d2 >> pd2;
-  //istrst01 >> i2;
-  //istrst01 >> pi2;
-  VERIFY( i2 == i );
-  VERIFY( d2 == d );
-  VERIFY( pd2 == pd );
-  VERIFY( pi2 == pi );
-#endif
-
-  // stringstream
-  std::string str1("");
-  std::string str3("this is a somewhat  string");
-  std::stringstream ss1(str1, std::ios_base::in|std::ios_base::out);
-  std::stringstream ss2(str3, std::ios_base::in|std::ios_base::out);
-
-  return 0;
+  // Check for required typedefs
+  typedef std::stringstream test_type;
+  typedef test_type::char_type char_type;
+  typedef test_type::traits_type traits_type;
+  typedef test_type::int_type int_type;
+  typedef test_type::pos_type pos_type;
+  typedef test_type::off_type off_type;
 }
 
-// user-reported error
-class derived_oss: public std::ostringstream 
-{
-public:
-  derived_oss() : std::ostringstream() {}
-};
-
-int
-test03()
+namespace test 
 {
-  bool test = true;
-  derived_oss yy;
-  yy << "buena vista social club\n";
-  VERIFY( yy.str() == std::string("buena vista social club\n") );
-
-#ifdef DEBUG_ASSERT
-  assert(test);
-#endif
-
-  return 0;
-}
+  using namespace std;
+  typedef short type_t;
+  template class basic_stringstream<type_t, char_traits<type_t> >;
+} // test
 
-int 
-main() 
+int main() 
 {
   test01();
-  test02();
-  test03();
-  
   return 0;
 }
index 4de7b8c52411f101c138dfe26c654b191914ac8e..91ee79bcf40b6e06f18faf4ccd2971be907a05da 100644 (file)
@@ -1,6 +1,6 @@
 // 2001-05-24 Benjamin Kosnik  <bkoz@redhat.com>
 
-// Copyright (C) 2001 Free Software Foundation, Inc.
+// Copyright (C) 2001, 2002 Free Software Foundation, Inc.
 //
 // This file is part of the GNU ISO C++ Library.  This library is free
 // software; you can redistribute it and/or modify it under the
@@ -120,12 +120,67 @@ void test02()
   // These semantics are a joke, a serious defect, and incredibly lame.
 }
 
+void
+test03()
+{
+  bool test = true;
+
+  //
+  // 1: Automatic formatting of a compound string
+  //
+  int i = 1024;
+  int *pi = &i;
+  double d = 3.14159;
+  double *pd = &d;
+  std::string blank;
+  std::ostringstream ostrst01; 
+  std::ostringstream ostrst02(blank); 
+  
+  // No buffer, so should be created.
+  ostrst01 << "i: " << i << " i's address:  " << pi << "\n"
+            << "d: " << d << " d's address: " << pd << std::endl;
+  // Buffer, so existing buffer should be overwritten.
+  ostrst02 << "i: " << i << " i's address:  " << pi << "\n"
+            << "d: " << d << " d's address: " << pd << std::endl;
+
+  std::string msg01 = ostrst01.str();
+  std::string msg02 = ostrst02.str();
+  VERIFY( msg01 == msg02 );
+  VERIFY( msg02 != blank );
+
+  //
+  // 2: istringstream
+  //
+  // extracts the stored ascii values, placing them in turn in the four vars
+#if 0
+  int i2 = 0;
+  //int* pi2 = &i2;
+  void* pi2 = &i2;
+  double d2 = 0.0;
+  //  double* pd2 = &d2;
+  void* pd2 = &d2;
+  std::istringstream istrst01(ostrst02.str());
+
+  istrst01 >> i2 >> pi2 >> d2 >> pd2;
+  //istrst01 >> i2;
+  //istrst01 >> pi2;
+  VERIFY( i2 == i );
+  VERIFY( d2 == d );
+  VERIFY( pd2 == pd );
+  VERIFY( pi2 == pi );
+#endif
+
+  // stringstream
+  std::string str1("");
+  std::string str3("this is a somewhat  string");
+  std::stringstream ss1(str1, std::ios_base::in|std::ios_base::out);
+  std::stringstream ss2(str3, std::ios_base::in|std::ios_base::out);
+}
+
 int main()
 {
   test01();
   test02();
+  test03();
   return 0;
 }
-
-
-