stdcxx-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From far...@apache.org
Subject svn commit: r522951 [2/2] - in /incubator/stdcxx/trunk/tests/containers: 23.list.assign.cpp 23.list.capacity.cpp 23.list.cons.cpp 23.list.erase.cpp 23.list.insert.cpp 23.list.iterators.cpp 23.list.special.cpp
Date Tue, 27 Mar 2007 15:16:25 GMT
Added: incubator/stdcxx/trunk/tests/containers/23.list.erase.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/containers/23.list.erase.cpp?view=auto&rev=522951
==============================================================================
--- incubator/stdcxx/trunk/tests/containers/23.list.erase.cpp (added)
+++ incubator/stdcxx/trunk/tests/containers/23.list.erase.cpp Tue Mar 27 08:16:23 2007
@@ -0,0 +1,492 @@
+/***************************************************************************
+ *
+ * 23.list.erase.cpp - test exercising [lib.list::erase]
+ *
+ * $Id$
+ *
+ ***************************************************************************
+ *
+ * Licensed to the Apache Software  Foundation (ASF) under one or more
+ * contributor  license agreements.  See  the NOTICE  file distributed
+ * with  this  work  for  additional information  regarding  copyright
+ * ownership.   The ASF  licenses this  file to  you under  the Apache
+ * License, Version  2.0 (the  "License"); you may  not use  this file
+ * except in  compliance with the License.   You may obtain  a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the  License is distributed on an  "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY  KIND, either  express or
+ * implied.   See  the License  for  the  specific language  governing
+ * permissions and limitations under the License.
+ *
+ **************************************************************************/
+
+#include <list>             // for list
+#include <cstddef>          // for ptrdiff_t, size_t
+#include <stdexcept>        // for out_of_range
+
+#include <23.list.h>        // for ListMembers
+#include <driver.h>         // for rw_test()
+#include <rw_allocator.h>   // for UserAlloc
+#include <rw_char.h>        // for rw_expand()
+#include <rw_new.h>         // for bad_alloc, replacement operator new
+
+/**************************************************************************/
+
+// for convenience and brevity
+#define Erase(sig)                ListIds::erase_ ## sig
+
+static const char* const exceptions[] = {
+    "unknown exception", "exception"
+};
+
+/**************************************************************************/
+
+// used to exercise
+// erase (iterator, iterator)
+static const ContainerTestCase
+iter_iter_test_cases [] = {
+
+#undef TEST
+#define TEST(str, off, size, res) {                                        \
+        __LINE__, off, size, -1, -1, -1, str, sizeof str - 1,              \
+        0, 0, res, sizeof res - 1, 0 }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                   +--------------------- erase() pos argument
+    //    |                   |         +----------- erase() n argument
+    //    |                   |         |   +------- expected result sequence
+    //    |                   |         |   |
+    //    |                   |         |   |
+    //    |                   |         |   |
+    //    |                   |         |   |
+    //    |                   |         |   |
+    //    V                   V         V   V
+    TEST ("",                 0,        0,  ""              ),
+    TEST ("<U0>",             0,        1,  ""              ),
+    TEST ("<U0>",             0,        0,  "<U0>"          ),
+    TEST ("<U0>",             1,        1,  "<U0>"          ),
+    TEST ("<U0>@2",           1,        1,  "<U0>"          ),
+    TEST ("<U0>@2",           0,        1,  "<U0>"          ),
+
+    TEST ("a",                0,        1,  ""              ),
+    TEST ("a",                0,        0,  "a"             ),
+    TEST ("a",                1,        1,  "a"             ),
+
+    TEST ("abc",              0,        3,  ""              ),
+    TEST ("abc",              0,        2,  "c"             ),
+    TEST ("abc",              1,        2,  "a"             ),
+    TEST ("abc",              1,        1,  "ac"            ),
+    TEST ("abc",              2,        1,  "ab"            ),
+    TEST ("abc",              3,        0,  "abc"           ),
+
+    TEST ("t<U0> s",          0,        3,  "s"             ),
+    TEST ("t<U0> s",          0,        4,  ""              ),
+    TEST ("t<U0> s",          0,        1,  "<U0> s"        ),
+    TEST ("t<U0> s",          1,        3,  "t"             ),
+    TEST ("t<U0> s",          1,        2,  "ts"            ),
+    TEST ("t<U0> s",          2,        2,  "t<U0>"         ),
+    TEST ("t<U0> s",          2,        1,  "t<U0>s"        ),
+    TEST ("t<U0> s",          3,        2,  "t<U0> "        ),
+    TEST ("t<U0> s",          4,        0,  "t<U0> s"       ),
+
+    TEST ("a<U0>@3b",         2,        0,  "a<U0>@3b"      ),
+    TEST ("a<U0>@3b",         2,        3,  "a<U0>"         ),
+    TEST ("a<U0>@3b",         2,        2,  "a<U0>b"        ),
+    TEST ("a<U0>@3b",         1,        4,  "a"             ),
+    TEST ("a<U0>@3b",         0,        5,  ""              ),
+    TEST ("a<U0>@3b",         0,        2,  "<U0>@2b"       ),
+    TEST ("a<U0>b<U0>@2c",    0,        6,  ""              ),
+    TEST ("a<U0>b<U0>@2c",    4,        2,  "a<U0>b<U0>"    ),
+    TEST ("a<U0>b<U0>@2c",    4,        1,  "a<U0>b<U0>c"   ),
+    TEST ("<U0>ab<U0>@2c",    2,        5,  "<U0>a"         ),
+    TEST ("<U0>ab<U0>@2c",    0,        4,  "<U0>c"         ),
+    TEST ("ab<U0>c<U0>@2",    5,        1,  "ab<U0>c<U0>"   ),
+    TEST ("a",                0,        3,  ""              ),
+    TEST ("t<U0> s",          0,        9,  ""              ),
+    TEST ("ab<U0>c<U0>@2",    0,       10,  ""              ),
+    TEST ("x@4096",           0,     4105,  ""              ),
+    TEST ("a",                3,        1,  "a"             ),
+    TEST ("t<U0> s",          5,        1,  "t<U0> s"       ),
+    TEST ("ab<U0>c<U0>@2",   10,        1,  "ab<U0>c<U0>@2" ),
+    TEST ("x@4096",        4106,        1,  "x@4096"        ),
+    TEST ("x@4096",           0,     4096,  ""              ),
+    TEST ("x@4096",           1,     4095,  "x"             ),
+    TEST ("x@4096",           4,     4092,  "xxxx"          ),
+    TEST ("x@4096",           4,     4090,  "xxxxxx"        ),
+    TEST ("x@4096",        4096,     4096,  "x@4096"        ),
+    TEST ("x@2048y@2048",     1,     4094,  "xy"            ),
+
+    TEST ("last test",        4,        1,  "lasttest"      )
+};
+
+
+/**************************************************************************/
+
+// used to exercise
+// erase (iterator)
+static const ContainerTestCase
+iter_test_cases [] = {
+
+#undef TEST
+#define TEST(str, off, res) {                                      \
+        __LINE__, off, -1, -1, -1, -1, str, sizeof str - 1,        \
+        0, 0, res, sizeof res - 1, 0 }
+
+    //    +-------------------------------------- controlled sequence
+    //    |                   +------------------ iterator offset
+    //    |                   |    +------------- expected result sequence
+    //    |                   |    |
+    //    V                   V    V
+    TEST ("a",                0,   ""),
+
+    TEST ("<U0>",             0,   ""),
+    TEST ("<U0>@2",           0,   "<U0>"),
+    TEST ("<U0>@2",           1,   "<U0>"),
+
+    TEST ("abc",              0,   "bc"),
+    TEST ("abc",              1,   "ac"),
+    TEST ("abc",              2,   "ab"),
+
+    TEST ("t<U0> s",          0,   "<U0> s"),
+    TEST ("t<U0> s",          1,   "t s"),
+    TEST ("t<U0> s",          2,   "t<U0>s"),
+    TEST ("t<U0> s",          3,   "t<U0> "),
+
+    TEST ("a<U0>@3b",         4,   "a<U0>@3"),
+    TEST ("a<U0>@3b",         2,   "a<U0>@2b"),
+    TEST ("a<U0>@3b",         1,   "a<U0>@2b"),
+    TEST ("a<U0>@3b",         0,   "<U0>@3b"),
+    TEST ("a<U0>b<U0>@2c",    4,   "a<U0>b<U0>c"),
+    TEST ("<U0>ab<U0>@2c",    0,   "ab<U0>@2c"),
+    TEST ("<U0>ab<U0>@2c",    2,   "<U0>a<U0>@2c"),
+    TEST ("ab<U0>c<U0>@2",    5,   "ab<U0>c<U0>"),
+
+    TEST ("x@4096y",       4096,   "x@4096"),
+    TEST ("x@4096",        4088,   "x@4095"),
+    TEST ("ax@4096",          0,   "x@4096"),
+    TEST ("x@4096",           9,   "x@4095"),
+
+    TEST ("last test",        4,   "lasttest")
+};
+
+/**************************************************************************/
+
+// used to exercise
+// pop_front ()
+static const ContainerTestCase
+pop_front_test_cases [] = {
+
+#undef TEST
+#define TEST(str, res) {                                            \
+    __LINE__, -1, -1, -1, -1, -1, str, sizeof str - 1,              \
+    0, 0, res, sizeof res - 1, 0 }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                +------------------------ expected result sequence
+    //    |                |
+    //    |                |
+    //    |                |
+    //    |                |
+    //    |                |
+    //    V                V
+    TEST ("<U0>",          ""              ),
+    TEST ("<U0>@2",        "<U0>"          ),
+    TEST ("a",             ""              ),
+    TEST ("abc",           "bc"            ),
+    TEST ("t<U0> s",       "<U0> s"        ),
+    TEST ("a<U0>@3b",      "<U0>@3b"       ),
+    TEST ("a<U0>b<U0>@2c", "<U0>b<U0>@2c"  ),
+    TEST ("<U0>ab<U0>@2c", "ab<U0>@2c"     ),
+    TEST ("ab<U0>c<U0>@2", "b<U0>c<U0>@2"  ),
+    TEST ("x@4096",        "x@4095"        ),
+
+    TEST (" last test",    "last test"     )
+};
+
+/**************************************************************************/
+
+// used to exercise
+// pop_back ()
+static const ContainerTestCase
+pop_back_test_cases [] = {
+
+#undef TEST
+#define TEST(str, res) {                                            \
+    __LINE__, -1, -1, -1, -1, -1, str, sizeof str - 1,              \
+    0, 0, res, sizeof res - 1, 0 }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                +------------------------ expected result sequence
+    //    |                |
+    //    |                |
+    //    |                |
+    //    |                |
+    //    |                |
+    //    V                V
+    TEST ("<U0>",          ""              ),
+    TEST ("<U0>@2",        "<U0>"          ),
+    TEST ("a",             ""              ),
+    TEST ("abc",           "ab"            ),
+    TEST ("t<U0> s",       "t<U0> "        ),
+    TEST ("a<U0>@3b",      "a<U0>@3"       ),
+    TEST ("a<U0>b<U0>@2c", "a<U0>b<U0>@2"  ),
+    TEST ("<U0>ab<U0>@2c", "<U0>ab<U0>@2"  ),
+    TEST ("ab<U0>c<U0>@2", "ab<U0>c<U0>"   ),
+    TEST ("x@4096",        "x@4095"        ),
+
+    TEST ("last test ",    "last test"     )
+};
+
+/**************************************************************************/
+
+template <class InputIterator, class Distance>
+static inline void
+_rw_advance (InputIterator& it, Distance dist) {
+
+    while (0 < dist) {
+        --dist;
+        ++it;
+    }
+}
+
+template<class InputIterator>
+static inline size_t
+_rw_distance(InputIterator first, InputIterator last)
+{
+    size_t dist = 0;
+
+    for (; first != last; ++first)
+        ++dist;
+
+    return dist;
+}
+
+template <class T, class Allocator>
+void test_erase (T*, Allocator*,
+                 const ContainerTestCaseData<T> &tdata)
+{
+    typedef std::list <T, Allocator>      List;
+    typedef typename List::iterator       ListIter;
+    typedef typename List::const_iterator ListCIter;
+    typedef ListState<List>               ListState;
+
+    const ContainerFunc     &func  = tdata.func_;
+    const ContainerTestCase &tcase = tdata.tcase_;
+
+    // construct the list object to be modified
+    List lst (tdata.str_, tdata.str_ + tdata.strlen_);
+
+    // compute the offset and the extent (the number of elements)
+    // of the first range into the list object being modified
+    const std::size_t size1 = tdata.strlen_;
+    const std::size_t off1 =
+        std::size_t (tcase.off) < size1 ? std::size_t (tcase.off) : size1;
+    const std::size_t ext1 =
+        off1 + tcase.size < size1 ? tcase.size : size1 - off1;
+
+    // create a pair of iterators into the list object being modified
+    ListIter it_first (lst.begin ());
+    _rw_advance (it_first, off1);
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+    // is some exception expected ?
+    const char* expected = 0;
+    const char* caught = 0;
+
+#else   // if defined (_RWSTD_NO_EXCEPTIONS)
+
+    if (tcase.bthrow)
+        return;
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+    // start checking for memory leaks
+    rwt_check_leaks (0, 0);
+
+    ListIter res_iter;
+
+    const bool is_class = ListIds::UserClass == func.elem_id_;
+
+    const size_t x_count_save = UserClass::count_;
+
+    try {
+        // reset function call counters
+        if (is_class)
+            UserClass::reset_totals ();
+
+        std::size_t delcnt = 0;
+
+        switch (func.which_) {
+
+        case Erase (iter):
+            res_iter = lst.erase (it_first);
+            delcnt = 1;
+            break;
+
+        case Erase (iter_iter): {
+            ListIter it_last (it_first);
+            _rw_advance (it_last, ext1);
+            res_iter = lst.erase (it_first, it_last);
+            delcnt = ext1;
+            break;
+        }
+
+        case ListIds::pop_front_void:
+            lst.pop_front ();
+            delcnt = 1;
+            break;
+
+        case ListIds::pop_back_void:
+            lst.pop_back ();
+            delcnt = 1;
+            break;
+
+        default:
+            RW_ASSERT (!"test logic error: unknown erase overload");
+            return;
+        }
+
+        if (is_class) {
+            // verify that the erase method calls only dtor
+            // of UserClass and only the given number of times each
+            bool success = UserClass::is_total (x_count_save - delcnt,
+                                                0, 0, 0, 0, 0)
+                        && UserClass::n_total_dtor_ == delcnt;
+
+            rw_assert (success, 0, tcase.line,
+                       "line %d. %{$FUNCALL} called default/copy ctor, "
+                       "operator=() and dtor %zu, %zu, %zu, and %zu times, "
+                       "respectively, 0, 0, 0, %zu expected",
+                       __LINE__,
+                       UserClass::n_total_def_ctor_,
+                       UserClass::n_total_copy_ctor_,
+                       UserClass::n_total_op_assign_,
+                       UserClass::n_total_dtor_, delcnt);
+        }
+
+        if (ListIds::pop_front_void != func.which_
+         && ListIds::pop_back_void != func.which_) {
+             // verify the returned value
+             size_t dist = _rw_distance (lst.begin (), res_iter);
+             rw_assert (dist <= lst.size(), 0, tcase.line,
+                 "line %d. %{$FUNCALL} returned invalid iterator, "
+                 "difference with begin is %zu",
+                 __LINE__, dist);
+
+             if (std::size_t (tcase.off) >= tdata.reslen_) {
+                 rw_assert (res_iter == lst.end (), 0, tcase.line,
+                     "line %d. %{$FUNCALL} != end()", __LINE__);
+             }
+             else {
+                 bool success =
+                     tdata.res_ [tcase.off].data_.val_ == res_iter->data_.val_;
+
+                 rw_assert (success, 0, tcase.line,
+                     "line %d. %{$FUNCALL} == %{#c}, got %{#c}",
+                     __LINE__, char (tdata.res_ [tcase.off].data_.val_),
+                     char (res_iter->data_.val_));
+             }
+        }
+
+        // for convenience
+        static const int cwidth = sizeof (T);
+
+        const size_t got_size = lst.size ();
+        char* const got = new char [got_size + 1];
+ 
+        size_t index = 0;
+        for (ListCIter it = lst.begin (),
+            end = lst.end (); it != end; ++it) {
+            got [index++] = char (it->data_.val_);
+        }
+
+        got [got_size] = '\0';
+
+        // verify that strings length are equal
+        rw_assert (tdata.reslen_ == got_size, 0, tcase.line,
+                   "line %d. %{$FUNCALL} expected \"%{X=*}\" with length "
+                   "%zu, got %{/*.*Gs} with length %zu",
+                   __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+                   tdata.reslen_, 1, int (got_size), got, got_size);
+
+        if (tdata.reslen_ == got_size) {
+            // if the result length matches the expected length
+            // (and only then), also verify that the modified
+            // list matches the expected result
+            const T* pmatch = T::mismatch (tdata.res_, got, got_size);
+
+            rw_assert (0 == pmatch, 0, tcase.line,
+                       "line %d. %{$FUNCALL} expected \"%{X=*}\", "
+                       "got %{/*.*Gs}, difference at offset %zu",
+                       __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+                       1, int (got_size), got, pmatch - tdata.res_);
+        }
+
+        delete [] got;
+    }
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+    catch (const std::exception &ex) {
+        caught = exceptions [1];
+        rw_assert (0, 0, tcase.line,
+                   "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                   "unexpectedly%{;} caught std::%s(%#s)",
+                   __LINE__, 0 != expected, expected, caught, ex.what ());
+    }
+    catch (...) {
+        caught = exceptions [0];
+        rw_assert (0, 0, tcase.line,
+                   "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                   "unexpectedly%{;} caught %s",
+                   __LINE__, 0 != expected, expected, caught);
+    }
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+    // FIXME: verify the number of blocks the function call
+    // is expected to allocate and detect any memory leaks
+    rw_check_leaks (lst.get_allocator (), tcase.line,
+        std::size_t (-1), std::size_t (-1));
+}
+
+/**************************************************************************/
+
+DEFINE_CONTAINER_TEST_FUNCTIONS (test_erase);
+
+int main (int argc, char** argv)
+{
+    static const ContainerTest
+    tests [] = {
+
+#undef TEST
+#define TEST(sig) {                                             \
+        Erase (sig), sig ## _test_cases,                        \
+        sizeof sig ## _test_cases / sizeof *sig ## _test_cases  \
+    }
+
+        TEST (iter),
+        TEST (iter_iter),
+
+#undef TEST
+#define TEST(sig) {                                             \
+        ListIds::sig ## _void, sig ## _test_cases,              \
+        sizeof sig ## _test_cases / sizeof *sig ## _test_cases  \
+    }
+
+        TEST (pop_front),
+        TEST (pop_back)
+    };
+
+    const std::size_t test_count = sizeof tests / sizeof *tests;
+
+    return rw_run_cont_test (argc, argv, __FILE__,
+                             "lib.list.erase",
+                             ContainerIds::List,
+                             test_erase_func_array, tests, test_count);
+}

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.erase.cpp
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.erase.cpp
------------------------------------------------------------------------------
    svn:keywords = Id

Added: incubator/stdcxx/trunk/tests/containers/23.list.insert.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/containers/23.list.insert.cpp?view=auto&rev=522951
==============================================================================
--- incubator/stdcxx/trunk/tests/containers/23.list.insert.cpp (added)
+++ incubator/stdcxx/trunk/tests/containers/23.list.insert.cpp Tue Mar 27 08:16:23 2007
@@ -0,0 +1,837 @@
+/***************************************************************************
+ *
+ * 23.list.insert.cpp - test exercising [lib.list.insert]
+ *
+ * $Id$
+ *
+ ***************************************************************************
+ *
+ * Licensed to the Apache Software  Foundation (ASF) under one or more
+ * contributor  license agreements.  See  the NOTICE  file distributed
+ * with  this  work  for  additional information  regarding  copyright
+ * ownership.   The ASF  licenses this  file to  you under  the Apache
+ * License, Version  2.0 (the  "License"); you may  not use  this file
+ * except in  compliance with the License.   You may obtain  a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the  License is distributed on an  "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY  KIND, either  express or
+ * implied.   See  the License  for  the  specific language  governing
+ * permissions and limitations under the License.
+ *
+ **************************************************************************/
+
+#include <list>           // for list
+#include <stdexcept>      // for out_of_range, length_error
+#include <cstddef>        // for size_t
+
+#include <23.list.h>      // for ListMembers
+#include <alg_test.h>     // for InputIter
+#include <driver.h>       // for rw_test()
+#include <rw_allocator.h> // for UserAlloc
+#include <rw_new.h>       // for bad_alloc, replacement operator new
+
+/**************************************************************************/
+
+// for convenience and brevity
+#define Insert(sig)   ListIds::insert_ ## sig
+
+static const char* const exceptions[] = {
+    "unknown exception", "bad_alloc", "exception"
+};
+
+/**************************************************************************/
+
+// exercises
+// insert (iterator, InputIterator, InputIterator)
+static const ContainerTestCase
+iter_range_test_cases [] = {
+
+#undef TEST
+#define TEST(lst, off, arg, off2, size2, res, bthrow) {                 \
+        __LINE__, off, -1, off2, size2, -1, lst, sizeof lst - 1,        \
+        arg, sizeof arg - 1, res, sizeof res - 1, bthrow                \
+    }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                +------------------------ insert() pos argument
+    //    |                |  +--------------------- sequence to be inserted
+    //    |                |  |            +-------- insert() off2 argument
+    //    |                |  |            |  +----- insert() num argument
+    //    |                |  |            |  |  +-- expected result sequence
+    //    |                |  |            |  |  |  +--- exception info
+    //    |                |  |            |  |  |  |       0 - no exception
+    //    |                |  |            |  |  |  |       1 - out_of_range
+    //    |                |  |            |  |  |  |       2 - length_error
+    //    |                |  |            |  |  |  |      -1 - exc. safety
+    //    |                |  |            |  |  |  |
+    //    |                |  |            |  |  |  +----------------+
+    //    V                V  V            V  V  V                   V
+    TEST ("ab",            0, "c",         0, 1, "cab",              0),
+
+    TEST ("",              0, "",          0, 0,  "",                0),
+    TEST ("",              0, "abc",       1, 1,  "b",               0),
+    TEST ("",              0, "<U0>",      0, 1,  "<U0>",            0),
+
+    TEST ("<U0>",          0, "",          0, 0,  "<U0>",            0),
+    TEST ("<U0>",          1, "",          0, 0,  "<U0>",            0),
+
+    TEST ("abc",           0, "",          0, 0,  "abc",             0),
+    TEST ("abc",           1, "",          0, 0,  "abc",             0),
+    TEST ("abc",           3, "",          0, 0,  "abc",             0),
+
+    TEST ("<U0>",          0, "a",         0, 1,  "a<U0>",           0),
+    TEST ("<U0>",          1, "a",         0, 1,  "<U0>a",           0),
+    TEST ("<U0>",          0, "<U0>@2",    1, 1,  "<U0>@2",          0),
+    TEST ("<U0>",          1, "<U0>@2",    0, 2,  "<U0>@3",          0),
+
+    TEST ("cde",           0, "ab",        0, 2,  "abcde",           0),
+    TEST ("cde",           1, "ab",        0, 1,  "cade",            0),
+    TEST ("cde",           3, "ab",        1, 1,  "cdeb",            0),
+
+    TEST ("ab",            0, "c<U0>e",    0, 3,  "c<U0>eab",        0),
+    TEST ("ab",            1, "c<U0>e",    1, 2,  "a<U0>eb",         0),
+    TEST ("ab",            2, "c<U0>e",    0, 2,  "abc<U0>",         0),
+
+    TEST ("<U0>e<U0>",     1, "<U0>ab<U0>@2c", 0, 6, "<U0>@2ab<U0>@2ce<U0>",0),
+    TEST ("<U0>e<U0>",     1, "<U0>ab<U0>@2c", 0, 3, "<U0>@2abe<U0>",       0),
+    TEST ("a<U0>b<U0>@2c", 3, "<U0>e<U0>",     0, 3, "a<U0>b<U0>e<U0>@3c",  0),
+    TEST ("a<U0>b<U0>@2c", 2, "<U0>@2e<U0>",   0, 2, "a<U0>@3b<U0>@2c",     0),
+    TEST ("<U0>ab<U0>@2c", 0, "<U0>e<U0>",     2, 1, "<U0>@2ab<U0>@2c",     0),
+    TEST ("a<U0>bc<U0>@2", 6, "<U0>e",         0, 2, "a<U0>bc<U0>@3e",      0),
+
+    TEST ("",              0, "x@4096",    0, 4096, "x@4096",        0),
+    TEST ("x@4096",        0, "",          0,    0, "x@4096",        0),
+    TEST ("a@1000",        0, "b@1000",    0,  999, "b@999a@1000",   0),
+    TEST ("a@1000",        1, "b@1001",    0, 1000, "ab@1000a@999",  0),
+    TEST ("a@1000",        2, "b@1002",    0, 1001, "aab@1001a@998", 0),
+    TEST ("a@1000",      998, "b@1000",    1,  999, "a@998b@999aa",  0),
+    TEST ("a@1000",      999, "b@1001",    2,  999, "a@999b@999a",   0),
+    TEST ("a@1000",        2, "b@1002",  999,    3, "aabbba@998",    0),
+
+    TEST ("x@10",          1, "x@118",     0,  118, "x@128",         0),
+    TEST ("x@128",         0, "x@129",    50,   79, "x@207",         0),
+    TEST ("x@207",       207, "x@127",     0,  127, "x@334",         0),
+    TEST ("x@207",       128, "x@207",    10,  127, "x@334",         0),
+    TEST ("x@334",       334, "x@208",     2,  206, "x@540",         0),
+    TEST ("x@540",         0, "x@336",     3,  333, "x@873",         0),
+    TEST ("x@539",       538, "x@873",     0,  873, "x@1412",        0),
+    TEST ("x@873",       540, "x@540",     1,  539, "x@1412",        0),
+    TEST ("x@872",         0, "x@1412",    0, 1412, "x@2284",        0),
+    TEST ("x@1411",     1411, "x@2288",    4, 2284, "x@3695",        0),
+    TEST ("x@1411",      872, "x@3695",  128, 2284, "x@3695",        0),
+    TEST ("x@1412",        0, "x@2284",    0, 2284, "x@3696",        0),
+
+    TEST ("<U0>",          2, "",          0,    0,  "<U0>",         1),
+    TEST ("",              0, "<U0>",      2,    0,  "",             2),
+
+    TEST ("a",             2, "",          0,    0,  "a",            1),
+    TEST ("",              0, "a",         2,    0,  "",             2),
+
+    TEST ("x@4096",     4106, "",          0,    0,  "x@4096",       1),
+    TEST ("",              0, "x@4096", 4106,    0,  "",             2),
+
+    TEST ("last",          4, "test",      0,    4,  "lasttest",     0)
+};
+
+/**************************************************************************/
+
+// exercises
+// insert (iterator, size_type, const value_type&)
+static const ContainerTestCase
+iter_size_cref_test_cases [] = {
+
+#undef TEST
+#define TEST(lst, off, size, val, res, bthrow) {               \
+        __LINE__, off, size, -1, -1, val, lst, sizeof lst - 1, \
+        0, 0, res, sizeof res - 1, bthrow                      \
+    }
+
+    //    +---------------------------------------- controlled sequence
+    //    |                +----------------------- insert() pos argument
+    //    |                |  +-------------------- insert() size argument
+    //    |                |  |      +------------- character to be inserted
+    //    |                |  |      |   +--------- expected result sequence
+    //    |                |  |      |   |       +- exception info
+    //    |                |  |      |   |       |      0 - no exception
+    //    |                |  |      |   |       |      1 - out_of_range
+    //    |                |  |      |   |       |      2 - length_error
+    //    |                |  |      |   |       |     -1 - exc. safety
+    //    |                |  |      |   |       |
+    //    |                |  |      |   |       +---------+
+    //    V                V  V      V   V                 V
+    TEST ("ab",            0, 1,    'c', "cab",            0),
+
+    TEST ("",              0, 0,    ' ',  "",              0),
+    TEST ("",              0, 1,    'b',  "b",             0),
+
+    TEST ("<U0>",          0, 0,    ' ',  "<U0>",          0),
+    TEST ("<U0>",          1, 0,    ' ',  "<U0>",          0),
+    TEST ("",              0, 2,    '\0', "<U0>@2",        0),
+
+    TEST ("<U0>",          0, 1,    'a',  "a<U0>",         0),
+    TEST ("<U0>",          1, 1,    'a',  "<U0>a",         0),
+    TEST ("<U0>",          0, 1,    '\0', "<U0>@2",        0),
+    TEST ("<U0>",          1, 2,    '\0', "<U0>@3",        0),
+    TEST ("<U0>",          1, 0,    '\0', "<U0>",          0),
+
+    TEST ("cde",           0, 2,    'a',  "aacde",         0),
+    TEST ("cde",           1, 1,    'a',  "cade",          0),
+    TEST ("cde",           3, 3,    'a',  "cdeaaa",        0),
+    TEST ("cde",           2, 3,    'a',  "cdaaae",        0),
+
+    TEST ("ab",            0, 2,    '\0', "<U0>@2ab",      0),
+    TEST ("ab",            1, 1,    '\0', "a<U0>b",        0),
+    TEST ("ab",            2, 2,    '\0', "ab<U0>@2",      0),
+
+    TEST ("a<U0>b<U0>@2c", 3, 2,    '\0', "a<U0>b<U0>@3<U0>c",   0),
+    TEST ("a<U0>b<U0>@2c", 2, 1,    '\0', "a<U0>@2b<U0>@2c",     0),
+    TEST ("<U0>ab<U0>@2c", 0, 3,    '\0', "<U0>@3<U0>ab<U0>@2c", 0),
+    TEST ("a<U0>bc<U0>@2", 6, 2,    'a',  "a<U0>bc<U0>@2aa",     0),
+
+    TEST ("",              0, 4106, 'x',  "x@4106",        0),
+    TEST ("x@4096",        0, 2,    'a',  "aax@4096",      0),
+
+    TEST ("x@4096",        0, 2,    'a',  "aax@4096",      0),
+    TEST ("x@4096",        1, 2,    'a',  "xaax@4095",     0),
+    TEST ("x@4096",        1, 1,    '\0', "x<U0>x@4095",   0),
+
+    TEST ("x@127",         0, 1,    'x',  "x@128",         0),
+    TEST ("x@200",       128, 7,    'x',  "x@207",         0),
+    TEST ("x@331",       331, 3,    'x',  "x@334",         0),
+    TEST ("x@539",         0, 1,    'x',  "x@540",         0),
+    TEST ("x@539",         0, 873,  'x',  "x@1412",        0),
+    TEST ("x@873",       873, 1411, 'x',  "x@2284",        0),
+    TEST ("x@3694",      128, 1,    'x',  "x@3695",        0),
+    TEST ("x@540",         0, 1,    'x',  "x@541",         0),
+    TEST ("",              0, 3695, 'x',  "x@3695",        0),
+
+    TEST ("a",             0, 4095, 'x',  "x@4095a",       0),
+    TEST ("x@4096",        0, 2047, 'b',  "b@2047x@4096",  0),
+    TEST ("x@4096",     2047, 2048, 'x',  "x@6144",        0),
+
+    TEST ("last",          4, 4,    't',  "lasttttt",      0)
+};
+
+/**************************************************************************/
+
+// used to exercise
+// insert (iterator, const value_type&)
+static const ContainerTestCase
+iter_cref_test_cases [] = {
+
+#undef TEST
+#define TEST(lst, off, val, res, bthrow)                                \
+    { __LINE__, off, -1, -1, -1, val, lst, sizeof lst - 1, 0,           \
+      0, res, sizeof res - 1, bthrow }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                +------------------------ insert() pos argument
+    //    |                |    +------------------- character to be inserted
+    //    |                |    |   +--------------- expected result sequence
+    //    |                |    |   |               +--- exception info
+    //    |                |    |   |               |       0 - no exception
+    //    |                |    |   |               |       1 - out_of_range
+    //    |                |    |   |               |       2 - length_error
+    //    |                |    |   |               |      -1 - exc. safety
+    //    |                |    |   |               |
+    //    |                |    |   |               |
+    //    V                V    V   V               V
+    TEST ("ab",            0,  'c', "cab",          0),
+
+    TEST ("",              0,  'b', "b",            0),
+    TEST ("",              0, '\0', "<U0>",         0),
+
+    TEST ("<U0>",          0,  'a', "a<U0>",        0),
+    TEST ("<U0>",          1,  'a', "<U0>a",        0),
+    TEST ("<U0>",          0, '\0', "<U0>@2",       0),
+    TEST ("<U0>",          1, '\0', "<U0>@2",       0),
+
+    TEST ("cde",           0,  'a', "acde",         0),
+    TEST ("cde",           1,  'a', "cade",         0),
+    TEST ("cde",           2,  'a', "cdae",         0),
+    TEST ("cde",           3,  'a', "cdea",         0),
+
+    TEST ("a<U0>b<U0>@2c", 3, '\0', "a<U0>b<U0>@3c",    0),
+    TEST ("<U0>ab<U0>@2c", 0, '\0', "<U0>@2ab<U0>@2c",  0),
+    TEST ("a<U0>bc<U0>@2", 6,  'a', "a<U0>bc<U0>@2a",   0),
+
+    TEST ("x@4096",        0,  'a', "ax@4096",      0),
+    TEST ("x@4096",        1,  'a', "xax@4095",     0),
+    TEST ("x@4096",        1, '\0', "x<U0>x@4095",  0),
+
+    TEST ("x@127",         0, 'x',  "x@128",        0),
+    TEST ("x@206",         1, 'x',  "x@207",        0),
+    TEST ("x@333",       333, 'x',  "x@334",        0),
+    TEST ("x@539",       128, 'x',  "x@540",        0),
+    TEST ("x@1411",        0, 'x',  "x@1412",       0),
+    TEST ("x@2283",       10, 'x',  "x@2284",       0),
+    TEST ("x@3694",     3694, 'x',  "x@3695",       0),
+    TEST ("x@540",       538, 'x',  "x@541",        0),
+
+    TEST ("last",          4,  't', "lastt",        0)
+};
+
+/**************************************************************************/
+
+// used to exercise
+// push_front (const value_type&)
+static const ContainerTestCase
+push_front_test_cases [] = {
+
+#undef TEST
+#define TEST(str, val, res) {                                       \
+    __LINE__, -1, -1, -1, -1, val, str, sizeof str - 1,             \
+    0, 0, res, sizeof res - 1, 0 }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                +------------------------ character to be inserted
+    //    |                |     +------------------ expected result sequence
+    //    |                |     |
+    //    |                |     |
+    //    |                |     |
+    //    |                |     |
+    //    |                |     |
+    //    V                V     V
+    TEST ("",              'x',  "x"              ),
+    TEST ("<U0>",          '\0', "<U0>@2"         ),
+    TEST ("",              'a',  "a"              ),
+    TEST ("bc",            'a',  "abc"            ),
+    TEST ("<U0> s",        't',  "t<U0> s"        ),
+    TEST ("<U0>@3b",       'a',  "a<U0>@3b"       ),
+    TEST ("<U0>b<U0>@2c",  'a',  "a<U0>b<U0>@2c"  ),
+    TEST ("ab<U0>@2c",     '\0', "<U0>ab<U0>@2c"  ),
+    TEST ("b<U0>c<U0>@2",  'a',  "ab<U0>c<U0>@2"  ),
+    TEST ("x@4095",        'x',  "x@4096"         ),
+                          
+    TEST ("ast test",      'l',  "last test"      )
+};
+
+/**************************************************************************/
+
+// used to exercise
+// push_back (const value_type&)
+static const ContainerTestCase
+push_back_test_cases [] = {
+
+#undef TEST
+#define TEST(str, val, res) {                                       \
+    __LINE__, -1, -1, -1, -1, val, str, sizeof str - 1,             \
+    0, 0, res, sizeof res - 1, 0 }
+
+    //    +----------------------------------------- controlled sequence
+    //    |                +------------------------ character to be inserted
+    //    |                |     +------------------ expected result sequence
+    //    |                |     |
+    //    |                |     |
+    //    |                |     |
+    //    |                |     |
+    //    |                |     |
+    //    V                V     V
+    TEST ("",              'x',  "x"              ),
+    TEST ("<U0>",          '\0', "<U0>@2"         ),
+    TEST ("",              'a',  "a"              ),
+    TEST ("ab",            'c',  "abc"            ),
+    TEST ("t<U0> ",        's',  "t<U0> s"        ),
+    TEST ("a<U0>@3",       'b',  "a<U0>@3b"       ),
+    TEST ("a<U0>b<U0>@2",  'c',  "a<U0>b<U0>@2c"  ),
+    TEST ("<U0>ab<U0>@2",  'c',  "<U0>ab<U0>@2c"  ),
+    TEST ("ab<U0>c<U0>",   '\0', "ab<U0>c<U0>@2"  ),
+    TEST ("x@4095",        'x',  "x@4096"         ),
+
+    TEST ("last tes",      't',  "last test"      )
+};
+
+/**************************************************************************/
+
+template <class InputIterator, class Distance>
+static inline void
+_rw_advance (InputIterator& it, Distance dist) {
+
+    while (0 < dist) {
+        --dist;
+        ++it;
+    }
+}
+
+template<class InputIterator>
+static inline size_t
+_rw_distance(InputIterator first, InputIterator last)
+{
+    size_t dist = 0;
+
+    for (; first != last; ++first)
+        ++dist;
+
+    return dist;
+}
+
+// invokes specializations of the member function template
+// on the required iterator categories
+template <class List, class Iterator>
+struct InsertRange: ContRangeBase<List> {
+
+    typedef typename List::iterator       ListIter;
+    typedef typename List::value_type     ListVal;
+
+    InsertRange () { }
+
+    virtual List&
+    operator() (List &lst, 
+                const ContainerTestCaseData<ListVal>& tdata) const {
+
+        const ContainerTestCase &tcase = tdata.tcase_;
+
+        // create a pair of iterators into the list object being modified
+        ListIter first1 (lst.begin ());
+        _rw_advance (first1, tdata.off1_);
+
+        const ListVal* const beg = tdata.arg_ + tdata.off2_;
+        const ListVal* const end = beg + tdata.ext2_;
+
+        const Iterator first2 (beg, beg, end);
+        const Iterator last2  (end, beg, end);
+
+        lst.insert (first1, first2, last2);
+        return lst;
+    }
+};
+
+
+// invokes possible overloads of the member function template
+// on common RandomAccessIterator types
+template <class List, class Iterator>
+struct InsertRangeOverload: ContRangeBase<List>
+{
+    typedef typename List::iterator       ListIter;
+    typedef typename List::value_type     ListVal;
+
+    InsertRangeOverload () { }
+
+    virtual List&
+    operator() (List &lst, 
+                const ContainerTestCaseData<ListVal>& tdata) const {
+
+        const ContainerTestCase &tcase = tdata.tcase_;
+
+        // create a pair of iterators into the list object being modified
+        ListIter first1 (lst.begin ());
+        _rw_advance (first1, tdata.off1_);
+
+        bool reverse_iter = ListIds::ReverseIterator == tdata.func_.iter_id_
+            || ListIds::ConstReverseIterator == tdata.func_.iter_id_;
+
+        const std::size_t srclen_ = tdata.arglen_;
+
+        const std::size_t off = 
+            reverse_iter ? srclen_ - tdata.off2_ - tdata.ext2_ : tdata.off2_;
+        const std::size_t ext = tdata.ext2_;
+
+        List str_arg (tdata.arg_, tdata.arg_ + tdata.arglen_);
+
+        Iterator first2 (this->begin (str_arg, (Iterator*)0));
+        _rw_advance (first2, off);
+
+        Iterator last2 (first2);
+        _rw_advance (last2, ext);
+
+        if (ListIds::UserClass == tdata.func_.elem_id_)
+            UserClass::reset_totals ();
+
+        lst.insert (first1, first2, last2);
+        return lst;
+    }
+};
+
+// invokes specializations of the member function template
+// on the required iterator categories
+template <class List, class Iterator>
+struct InsertRangePtrOverload: ContRangeBase<List> {
+
+    typedef typename List::iterator       ListIter;
+    typedef typename List::value_type     ListVal;
+
+    InsertRangePtrOverload () { }
+
+    virtual List&
+    operator() (List& lst,
+                const ContainerTestCaseData<ListVal>& tdata) const {
+
+        const ContainerTestCase &tcase = tdata.tcase_;
+
+        ListIter first1 (lst.begin ());
+        _rw_advance (first1, tdata.off1_);
+
+        const ListVal* const beg = tdata.arg_ + tdata.off2_;
+        const ListVal* const end = beg + tdata.ext2_;
+
+        const Iterator first2 = _RWSTD_CONST_CAST (const Iterator, beg);
+        const Iterator last2  = _RWSTD_CONST_CAST (const Iterator, end);
+
+        lst.insert (first1, first2, last2);
+        return lst;
+    }
+};
+
+/**************************************************************************/
+
+template <class T, class Allocator>
+void test_insert (T*, Allocator*,
+                  const ContRangeBase< std::list <T, Allocator> > &rng,
+                  const ContainerTestCaseData<T>                  &tdata)
+{
+    typedef std::list <T, Allocator>      List;
+    typedef typename List::iterator       ListIter;
+    typedef typename List::const_iterator ListCIter;
+    typedef ListState<List>               ListState;
+
+    const ContainerFunc     &func  = tdata.func_;
+    const ContainerTestCase &tcase = tdata.tcase_;
+
+    // construct the list object to be modified
+    List lst (tdata.str_, tdata.str_ + tdata.strlen_);
+
+    // save the state of the list object before the call
+    // to detect exception safety violations (changes to
+    // the state of the object after an exception)
+    const ListState lst_state (lst);
+
+    std::ptrdiff_t exp_off = Insert (iter_cref) == func.which_ ? tcase.off : 0;
+
+    // compute the offset and the extent (the number of elements)
+    // of the first range into the list object being modified
+    const std::size_t size1 = tdata.strlen_;
+    const std::size_t off1 =
+        std::size_t (tcase.off) < size1 ? std::size_t (tcase.off) : size1;
+
+    const T arg_val = T::from_char (char (tcase.val));
+
+    rwt_free_store* const pst = rwt_get_free_store (0);
+    SharedAlloc*    const pal = SharedAlloc::instance ();
+
+    // iterate for`throw_after' starting at the next call to operator new,
+    // forcing each call to throw an exception, until the function finally
+    // succeeds (i.e, no exception is thrown)
+    std::size_t throw_count;
+    for (throw_count = 0; ; ++throw_count) {
+
+        // (name of) expected and caught exception
+        const char* expected = 0;
+        const char* caught   = 0;
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+        if (0 == tcase.bthrow) {
+            // by default exercise the exception safety of the function
+            // by iteratively inducing an exception at each call to operator
+            // new or Allocator::allocate() until the call succeeds
+            expected = exceptions [1];      // bad_alloc
+            *pst->throw_at_calls_ [0] = pst->new_calls_ [0] + throw_count + 1;
+            pal->throw_at_calls_ [pal->m_allocate] =
+                pal->throw_at_calls_ [pal->m_allocate] + throw_count + 1;
+        }
+        else {
+            // exceptions disabled for this test case
+        }
+
+#else   // if defined (_RWSTD_NO_EXCEPTIONS)
+
+        if (tcase.bthrow) 
+            return;
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+        // pointer to the returned reference
+        const List* ret_ptr = 0;
+
+        // start checking for memory leaks
+        rw_check_leaks (lst.get_allocator ());
+
+        const bool is_class = ListIds::UserClass == func.elem_id_;
+
+        const size_t x_count_save = UserClass::count_;
+
+        try {
+            // reset function call counters
+            if (is_class)
+                UserClass::reset_totals ();
+
+            std::size_t newcnt = 0;
+
+            switch (func.which_) {
+
+            case Insert (iter_size_cref): {
+                ListIter it (lst.begin ());
+                _rw_advance (it, off1);
+                lst.insert (it, tcase.size, arg_val);
+                ret_ptr = &lst;   // function returns void
+                newcnt = tcase.size;
+                break;
+            }
+
+            case Insert (iter_cref): {
+                ListIter it (lst.begin ());
+                _rw_advance (it, off1);
+                it = lst.insert (it, arg_val);
+                ret_ptr = &lst + _rw_distance (lst.begin (), it);
+                newcnt = 1;
+                break;
+            }
+
+            case Insert (iter_range): {
+                ret_ptr = &rng (lst, tdata);  // function returns void
+                newcnt = tcase.size2;
+                break;
+            }
+
+            case ListIds::push_front_cref:
+                lst.push_front (arg_val);
+                ret_ptr = &lst;   // function returns void
+                newcnt = 1;
+                break;
+
+            case ListIds::push_back_cref:
+                lst.push_back (arg_val);
+                ret_ptr = &lst;   // function returns void
+                newcnt = 1;
+                break;
+
+            default:
+                RW_ASSERT (!"logic error: unknown insert overload");
+                return;
+            }
+
+            if (is_class) {
+                // verify that the erase method calls only dtor
+                // of UserClass and only the given number of times each
+                bool success = UserClass::is_total (x_count_save + newcnt,
+                                                    0, newcnt, 0, 0, 0);
+
+                rw_assert (success, 0, tcase.line,
+                           "line %d. %{$FUNCALL} called default/copy ctor "
+                           "and operator=() %zu, %zu and %zu times, "
+                           "respectively, 0, %zu, 0, expected",
+                           __LINE__,
+                           UserClass::n_total_def_ctor_,
+                           UserClass::n_total_copy_ctor_,
+                           UserClass::n_total_op_assign_,
+                           newcnt);
+            }
+
+            // verify that the reference returned from the function
+            // refers to the modified list object (i.e., *this
+            // within the function)
+            const std::ptrdiff_t ret_off = ret_ptr - &lst;
+
+            // verify the returned value
+            rw_assert (exp_off == ret_off, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}== begin() + %td, got %td%{;}"
+                       "%{?}returned invalid reference, offset is %td%{;}",
+                       __LINE__, Insert (iter_cref) == func.which_,
+                       exp_off, ret_off,
+                       Insert (iter_cref) != func.which_, ret_off);
+
+            // for convenience
+            static const int cwidth = sizeof (T);
+
+            const size_t got_size = lst.size ();
+            char* const got = new char [got_size + 1];
+
+            size_t index = 0;
+            for (ListCIter it = lst.begin (),
+                end = lst.end (); it != end; ++it) {
+                got [index++] = char (it->data_.val_);
+            }
+
+            got [got_size] = '\0';
+
+            // verify that strings length are equal
+            rw_assert (tdata.reslen_ == got_size, 0, tcase.line,
+                       "line %d. %{$FUNCALL} expected \"%{X=*}\" with length "
+                       "%zu, got %{/*.*Gs} with length %zu", __LINE__, 
+                       cwidth, int (tdata.reslen_), tdata.res_, tdata.reslen_, 
+                       1, int (got_size), got, got_size);
+
+            if (tdata.reslen_ == got_size) {
+                // if the result length matches the expected length
+                // (and only then), also verify that the modified
+                // list matches the expected result
+                const T* pmatch = T::mismatch (tdata.res_, got, got_size);
+
+                rw_assert (0 == pmatch, 0, tcase.line,
+                           "line %d. %{$FUNCALL} expected \"%{X=*}\", "
+                           "got %{/*.*Gs}, difference at offset %zu",
+                           __LINE__, cwidth, int (tdata.reslen_), tdata.res_,
+                           1, int (got_size), got, pmatch - tdata.res_);
+            }
+
+            delete [] got;
+        }
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+        catch (const std::bad_alloc &ex) {
+            caught = exceptions [1];
+            rw_assert (0 == tcase.bthrow, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                       "unexpectedly%{;} caught std::%s(%#s)",
+                       __LINE__, 0 != expected, expected, caught, ex.what ());
+        }
+        catch (const std::exception &ex) {
+            caught = exceptions [2];
+            rw_assert (0, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                       "unexpectedly%{;} caught std::%s(%#s)",
+                       __LINE__, 0 != expected, expected, caught, ex.what ());
+        }
+        catch (...) {
+            caught = exceptions [0];
+            rw_assert (0, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                       "unexpectedly%{;} caught %s",
+                       __LINE__, 0 != expected, expected, caught);
+        }
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+        // FIXME: verify the number of blocks the function call
+        // is expected to allocate and detect any memory leaks
+        rw_check_leaks (lst.get_allocator (), tcase.line,
+                        std::size_t (-1), std::size_t (-1));
+
+        if (caught) {
+            // verify that an exception thrown during allocation
+            // didn't cause a change in the state of the object
+            lst_state.assert_equal (ListState (lst),
+                                    __LINE__, tcase.line, caught);
+
+            if (0 == tcase.bthrow) {
+                // allow this call to operator new to succeed and try
+                // to make the next one to fail during the next call
+                // to the same function again
+                continue;
+            }
+        }
+        else if (0 < tcase.bthrow) {
+            rw_assert (caught == expected, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s, caught %s"
+                       "%{:}unexpectedly caught %s%{;}",
+                       __LINE__, 0 != expected, expected, caught, caught);
+        }
+
+        break;
+    }
+
+    // disable bad_alloc exceptions
+    *pst->throw_at_calls_ [0] = 0;
+    pal->throw_at_calls_ [pal->m_allocate] = 0;
+}
+
+/**************************************************************************/
+
+template <class T, class Allocator>
+void test_insert (T*, Allocator*,
+                  const ContainerTestCaseData<T> &tdata)
+{
+    typedef std::list<T, Allocator> List;
+
+    if (tdata.func_.which_ == Insert (iter_range)) {
+
+        switch (tdata.func_.iter_id_) {
+
+        // exercise possible overloads of the member function template
+        // on common RandomAccessIterator types
+#undef TEST
+#define TEST(Iterator) do {                                                 \
+        typedef typename List::Iterator Iter;                               \
+        static const                                                        \
+        InsertRangePtrOverload<List, Iter> rng;                             \
+        test_insert ((T*)0, (Allocator*)0, rng, tdata);                     \
+    } while (0)
+
+        case ListIds::Pointer: TEST (pointer); break;
+        case ListIds::ConstPointer: TEST (const_pointer); break;
+
+#undef TEST
+#define TEST(Iterator) do {                                                 \
+        typedef typename List::Iterator Iter;                               \
+        static const                                                        \
+        InsertRangeOverload<List, Iter> rng;                                \
+        test_insert ((T*)0, (Allocator*)0, rng, tdata);                     \
+    } while (0)
+
+        case ListIds::Iterator: TEST (iterator); break;
+        case ListIds::ConstIterator: TEST (const_iterator); break;
+
+        case ListIds::ReverseIterator: TEST (reverse_iterator); break;
+        case ListIds::ConstReverseIterator: TEST (const_reverse_iterator);
+            break;
+
+        // exercise specializations of the member function template
+        // on the required iterator categories
+#undef TEST
+#define TEST(Iterator) do {                                                 \
+        typedef Iterator<T> Iter;                                           \
+        static const                                                        \
+        InsertRange<List, Iter> rng;                                        \
+        test_insert ((T*)0, (Allocator*)0, rng, tdata);                     \
+    } while (0)
+
+        case ListIds::Input: TEST (InputIter); break;
+        case ListIds::Forward: TEST (ConstFwdIter); break;
+        case ListIds::Bidir: TEST (ConstBidirIter); break;
+        case ListIds::Random: TEST (ConstRandomAccessIter); break;
+
+        default:
+            rw_error (0, 0, __LINE__, "bad iterator id");
+        }
+    }
+    else {
+        // exercise ordinary overloads of the member function
+        static const ContRangeBase<List> rng;
+        test_insert ((T*)0, (Allocator*)0, rng, tdata);
+    }
+}
+
+/**************************************************************************/
+
+DEFINE_CONTAINER_TEST_FUNCTIONS (test_insert);
+
+int main (int argc, char** argv)
+{
+    static const ContainerTest
+    tests [] = {
+
+#undef TEST
+#define TEST(sig) {                                             \
+        Insert (sig), sig ## _test_cases,                       \
+        sizeof sig ## _test_cases / sizeof *sig ## _test_cases  \
+    }
+
+        TEST (iter_cref),
+        TEST (iter_size_cref),
+        TEST (iter_range),
+
+#undef TEST
+#define TEST(sig) {                                             \
+        ListIds::sig ## _cref, sig ## _test_cases,              \
+        sizeof sig ## _test_cases / sizeof *sig ## _test_cases  \
+    }
+
+        TEST (push_front),
+        TEST (push_back)
+    };
+
+    const std::size_t test_count = sizeof tests / sizeof *tests;
+
+    const int status =
+        rw_run_cont_test (argc, argv, __FILE__,
+                          "lib.list.insert",
+                          ContainerIds::List,
+                          test_insert_func_array, tests, test_count);
+
+    return status;
+}

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.insert.cpp
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.insert.cpp
------------------------------------------------------------------------------
    svn:keywords = Id

Added: incubator/stdcxx/trunk/tests/containers/23.list.iterators.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/containers/23.list.iterators.cpp?view=auto&rev=522951
==============================================================================
--- incubator/stdcxx/trunk/tests/containers/23.list.iterators.cpp (added)
+++ incubator/stdcxx/trunk/tests/containers/23.list.iterators.cpp Tue Mar 27 08:16:23 2007
@@ -0,0 +1,426 @@
+/***************************************************************************
+ *
+ * 23.list.iterators.cpp - test exercising [lib.list.iterators]
+ *
+ * $Id$
+ *
+ ***************************************************************************
+ *
+ * Licensed to the Apache Software  Foundation (ASF) under one or more
+ * contributor  license agreements.  See  the NOTICE  file distributed
+ * with  this  work  for  additional information  regarding  copyright
+ * ownership.   The ASF  licenses this  file to  you under  the Apache
+ * License, Version  2.0 (the  "License"); you may  not use  this file
+ * except in  compliance with the License.   You may obtain  a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the  License is distributed on an  "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY  KIND, either  express or
+ * implied.   See  the License  for  the  specific language  governing
+ * permissions and limitations under the License.
+ *
+ **************************************************************************/
+
+#include <list>             // for list
+#include <stdexcept>        // for out_of_range, length_error
+#include <cstddef>          // for size_t
+
+#include <23.list.h>        // for ListMembers
+#include <driver.h>         // for rw_test()
+#include <rw_allocator.h>   // for UserAlloc
+#include <rw_new.h>         // for bad_alloc, replacement operator new
+
+/**************************************************************************/
+
+static const char* const exceptions[] = {
+    "unknown exception", "bad_alloc", "exception"
+};
+
+/**************************************************************************/
+
+// used to exercise
+// begin () and rend () and front ()
+static const ContainerTestCase 
+begin_void_test_cases [] = {
+
+#undef TEST
+#define TEST(lst, res) {                    \
+    __LINE__, -1, -1, -1, -1, -1,           \
+    lst, sizeof (lst) - 1,                  \
+    0, 0, 0, res, 0                         \
+}
+
+    //    +--------------------------------- controlled sequence
+    //    |                +---------------- expected result 
+    //    |                |     
+    //    V                V     
+    TEST ("",              _RWSTD_SIZE_MAX), 
+    TEST ("a",             'a' ), 
+    TEST ("<U0>",          '\0'),
+    TEST ("abc",           'a' ),  
+    TEST ("<U0>ab<U0>@2c", '\0'), 
+    TEST ("a<U0>b<U0>@2c", 'a' ),  
+    TEST ("a<U0>bc<U0>@2", 'a' ), 
+    TEST ("x@4096",        'x' ),  
+    TEST ("last",          'l' )  
+};
+
+/**************************************************************************/
+
+// used to exercise
+// end () and rbegin () and back ()
+static const ContainerTestCase 
+end_void_test_cases [] = {
+
+#undef TEST
+#define TEST(lst, res) {                    \
+    __LINE__, -1, -1, -1, -1, -1,           \
+    lst, sizeof (lst) - 1,                  \
+    0, 0, 0, res, 0                         \
+}
+
+    //    +--------------------------------- controlled sequence
+    //    |                +---------------- expected result 
+    //    |                |     
+    //    V                V     
+    TEST ("",              _RWSTD_SIZE_MAX), 
+    TEST ("a",             'a' ), 
+    TEST ("<U0>",          '\0'),
+    TEST ("abc",           'c' ),  
+    TEST ("<U0>ab<U0>@2c", 'c' ), 
+    TEST ("a<U0>b<U0>@2c", 'c' ),  
+    TEST ("a<U0>bc<U0>@2", '\0'), 
+    TEST ("x@4096",        'x' ),  
+    TEST ("last",          't' )  
+};
+
+/**************************************************************************/
+
+// exercises:
+// get_allocator ()
+static const ContainerTestCase
+get_allocator_void_test_cases [] = {
+
+#undef TEST
+#define TEST(lst) {                   \
+    __LINE__, -1, -1, -1, -1, -1,     \
+    lst, sizeof (lst) - 1,            \
+    0, 0, 0, 0, 0                     \
+}
+
+    //    +------------------------------------------ controlled sequence
+    //    | 
+    //    | 
+    //    |    
+    //    |    
+    //    | 
+    //    | 
+    //    | 
+    //    V 
+    TEST (""              ),
+    TEST ("ab"            ),
+    TEST ("<U0>"          ),
+    TEST ("x@4096"        ),
+    TEST ("a<U0>b"        ),
+    TEST ("a@2048cb@2047" ),
+    TEST ("last"          )
+};
+
+
+/**************************************************************************/
+
+template <class T, class Allocator>
+void test_iterators (T*, Allocator*,
+                     const ContainerTestCaseData<T> &tdata)
+{
+    typedef std::list <T, Allocator>                   List;
+    typedef typename List::iterator                    ListIter;
+    typedef typename List::const_iterator              ListCIter;
+    typedef typename List::reverse_iterator            ListRIter;
+    typedef typename List::const_reverse_iterator      ListCRIter;
+    typedef ListState<List>                            ListState;
+
+    const ContainerFunc     &func  = tdata.func_;
+    const ContainerTestCase &tcase = tdata.tcase_;
+
+    const bool test_iters =
+           func.which_ == ListIds::begin_void 
+        || func.which_ == ListIds::begin_const_void 
+        || func.which_ == ListIds::end_void
+        || func.which_ == ListIds::end_const_void
+        || func.which_ == ListIds::rbegin_void
+        || func.which_ == ListIds::rbegin_const_void
+        || func.which_ == ListIds::rend_void
+        || func.which_ == ListIds::rend_const_void
+        || func.which_ == ListIds::front_void
+        || func.which_ == ListIds::front_const_void
+        || func.which_ == ListIds::back_void
+        || func.which_ == ListIds::back_const_void;
+
+    const bool test_const_list =
+           func.which_ == ListIds::begin_const_void 
+        || func.which_ == ListIds::end_const_void
+        || func.which_ == ListIds::rbegin_const_void
+        || func.which_ == ListIds::rend_const_void
+        || func.which_ == ListIds::front_const_void
+        || func.which_ == ListIds::back_const_void;
+
+    const bool test_end_iters =
+           func.which_ == ListIds::end_void 
+        || func.which_ == ListIds::end_const_void
+        || func.which_ == ListIds::rend_void
+        || func.which_ == ListIds::rend_const_void;
+
+    // allocator object for test get_allocator
+    Allocator alloc;
+
+    // construct the list object 
+    List lst (tdata.str_, tdata.str_ + tdata.strlen_, alloc);
+    // construct the constant list object
+    const List clst (tdata.str_, tdata.str_ + tdata.strlen_, alloc);
+
+    const size_t s_size = test_const_list ? clst.size () : lst.size ();
+
+    // save the state of the list object before the call
+    // to detect exception safety violations (changes to
+    // the state of the object after an exception)
+    const ListState lst_state (lst);
+
+    // start checking for memory leaks
+    rw_check_leaks (lst.get_allocator ());
+
+    try {
+
+        // methods result
+        const T* res_ptr = 0;
+
+        // for begin () and end ()
+        ListIter it;
+        // for begin () const and end () const
+        ListCIter cit;
+        // for rbegin () and rend ()
+        ListRIter rit;
+        // for rbegin () const and rend () const
+        ListCRIter crit;
+
+        // for get_allocator ()
+        Allocator resalloc;
+
+        bool it_relations = true;
+
+        switch (func.which_) {
+
+        case ListIds::begin_void:
+            it = lst.begin();
+            it_relations = it == lst.rend ().base ();
+            if (s_size) res_ptr = &*it;
+            break;
+
+        case ListIds::begin_const_void:
+            cit = clst.begin();
+            it_relations = cit == clst.rend ().base ();
+            if (s_size) res_ptr = &*cit;
+            break;
+
+        case ListIds::end_void:
+            it = lst.end();
+            it_relations = it == lst.rbegin ().base ();
+            if (s_size) res_ptr = &*--it;
+            break;
+
+        case ListIds::end_const_void:
+            cit = clst.end();
+            it_relations = cit == clst.rbegin ().base ();
+            if (s_size) res_ptr = &*--cit;
+            break;
+
+        case ListIds::rbegin_void:
+            rit = lst.rbegin();
+            it_relations = rit.base () == lst.end ();
+            if (s_size) res_ptr = &*rit;
+            break;
+
+        case ListIds::rbegin_const_void:
+            crit = clst.rbegin();
+            it_relations = crit.base () == clst.end ();
+            if (s_size) res_ptr = &*crit;
+            break;
+
+        case ListIds::rend_void:
+            rit = lst.rend();
+            it_relations = rit.base () == lst.begin ();
+            if (s_size) res_ptr = &*--rit;
+            break;
+
+        case ListIds::rend_const_void:
+            crit = clst.rend();
+            it_relations = crit.base () == clst.begin ();
+            if (s_size) res_ptr = &*--crit;
+            break;
+
+        case ListIds::front_void:
+            if (s_size) {
+                res_ptr = &lst.front ();
+                it_relations = res_ptr == &*lst.begin ();
+            }
+            break;
+
+        case ListIds::front_const_void:
+            if (s_size) {
+                res_ptr = &clst.front ();
+                it_relations = res_ptr == &*clst.begin ();
+            }
+            break;
+
+        case ListIds::back_void:
+            if (s_size) {
+                res_ptr = &lst.back ();
+                it_relations = res_ptr == &*--lst.end ();
+            }
+            break;
+
+        case ListIds::back_const_void:
+            if (s_size) {
+                res_ptr = &clst.back ();
+                it_relations = res_ptr == &*--clst.end ();
+            }
+            break;
+
+        case ListIds::get_allocator_void:
+            resalloc = clst.get_allocator ();
+            break;
+
+        default:
+            RW_ASSERT (!"test logic error: unknown iterators overload");
+            return;
+        }
+
+        if (res_ptr) {
+
+            const char exp_res = 
+                (_RWSTD_SIZE_MAX != tcase.nres ? char (tcase.nres) : char ());
+
+            const bool success = 0 == T::mismatch (res_ptr, &exp_res, 1);
+
+            rw_assert (success, 0, tcase.line,
+                       "line %d. %{$FUNCALL}%{?} - 1%{;} expected "
+                       "%{#c}, got %{#c}", __LINE__, 
+                       test_end_iters, exp_res, char (res_ptr->data_.val_));
+        }
+
+        if (test_iters) {
+
+            if (0 == s_size) {
+
+                bool success = true;
+
+                if (   func.which_ == ListIds::begin_void 
+                    || func.which_ == ListIds::end_void) 
+                    success = it == lst.begin () && it == lst.end ();
+
+                if (   func.which_ == ListIds::begin_const_void 
+                    || func.which_ == ListIds::end_const_void) 
+                    success = cit == clst.begin () && cit == clst.end ();
+
+                if (   func.which_ == ListIds::rbegin_void 
+                    || func.which_ == ListIds::rend_void) 
+                    success = rit == lst.rbegin () && rit == lst.rend ();
+
+                if (   func.which_ == ListIds::rbegin_const_void 
+                    || func.which_ == ListIds::rend_const_void) 
+                    success = crit == clst.rbegin () && crit == clst.rend ();
+
+                // check the begin () == end (), rbegin () == rend ()
+                rw_assert(success, 0, tcase.line,
+                          "line %d. %{$FUNCALL} returned iterator is not "
+                          "equal to begin and end for an empty list", 
+                          __LINE__);
+            }
+
+            // check the iterators relationship
+            rw_assert(it_relations, 0, tcase.line,
+                      "line %d. %{$FUNCALL} iterators "
+                      "relationship is broken", __LINE__);
+        } 
+
+        if (func.which_ == ListIds::get_allocator_void) {
+
+            // verify that the allocator returned from the function
+            // equal to allocator passed to the ctor
+            const bool success = (alloc == resalloc);
+
+            rw_assert(success, 0, tcase.line,
+                      "line %d. %{$FUNCALL} expected equal to allocator "
+                      "passed to the ctor", __LINE__);
+        }
+    }
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+    catch (const std::bad_alloc &ex) {
+        rw_assert (0, 0, tcase.line,
+                   "line %d. %{$FUNCALL} unexpectedly caught std::%s(%#s)",
+                   __LINE__, exceptions [1], ex.what ());
+    }
+    catch (const std::exception &ex) {
+        rw_assert (0, 0, tcase.line,
+                   "line %d. %{$FUNCALL} unexpectedly caught std::%s(%#s)",
+                   __LINE__, exceptions [2], ex.what ());
+    }
+    catch (...) {
+        rw_assert (0, 0, tcase.line,
+                   "line %d. %{$FUNCALL} unexpectedly caught %s",
+                   __LINE__, exceptions [0]);
+    }
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+    // FIXME: verify the number of blocks the function call
+    // is expected to allocate and detect any memory leaks
+    rw_check_leaks (lst.get_allocator (), tcase.line,
+        size_t (-1), size_t (-1));
+
+    // verify that state of the object didn't changed
+    lst_state.assert_equal (ListState (lst),
+        __LINE__, tcase.line, "call");
+}
+
+/**************************************************************************/
+
+DEFINE_CONTAINER_TEST_FUNCTIONS (test_iterators);
+
+int main (int argc, char** argv)
+{
+    static const ContainerTest
+    tests [] = {
+
+#undef TEST
+#define TEST(gsig, sig) {                                       \
+    gsig, sig ## _test_cases,                                   \
+    sizeof sig ## _test_cases / sizeof *sig ## _test_cases      \
+}
+
+        TEST (ListIds::begin_void, begin_void),
+        TEST (ListIds::begin_const_void, begin_void),
+        TEST (ListIds::end_void, end_void),
+        TEST (ListIds::end_const_void, end_void),
+        TEST (ListIds::rbegin_void, end_void),
+        TEST (ListIds::rbegin_const_void, end_void),
+        TEST (ListIds::rend_void, begin_void),
+        TEST (ListIds::rend_const_void, begin_void),
+        TEST (ListIds::front_void, begin_void),
+        TEST (ListIds::front_const_void, begin_void),
+        TEST (ListIds::back_void, end_void),
+        TEST (ListIds::back_const_void, end_void),
+        TEST (ListIds::get_allocator_void, get_allocator_void)
+    };
+
+    const size_t test_count = sizeof tests / sizeof *tests;
+
+    return rw_run_cont_test (argc, argv, __FILE__,
+                             "lib.list.iterators", ContainerIds::List,
+                             test_iterators_func_array, tests, test_count);
+}

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.iterators.cpp
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.iterators.cpp
------------------------------------------------------------------------------
    svn:keywords = Id

Added: incubator/stdcxx/trunk/tests/containers/23.list.special.cpp
URL: http://svn.apache.org/viewvc/incubator/stdcxx/trunk/tests/containers/23.list.special.cpp?view=auto&rev=522951
==============================================================================
--- incubator/stdcxx/trunk/tests/containers/23.list.special.cpp (added)
+++ incubator/stdcxx/trunk/tests/containers/23.list.special.cpp Tue Mar 27 08:16:23 2007
@@ -0,0 +1,421 @@
+/***************************************************************************
+ *
+ * 23.list.special.cpp - test exercising [lib.list.special]
+ *
+ * $Id$
+ *
+ ***************************************************************************
+ *
+ * Licensed to the Apache Software  Foundation (ASF) under one or more
+ * contributor  license agreements.  See  the NOTICE  file distributed
+ * with  this  work  for  additional information  regarding  copyright
+ * ownership.   The ASF  licenses this  file to  you under  the Apache
+ * License, Version  2.0 (the  "License"); you may  not use  this file
+ * except in  compliance with the License.   You may obtain  a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the  License is distributed on an  "AS IS" BASIS,
+ * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY  KIND, either  express or
+ * implied.   See  the License  for  the  specific language  governing
+ * permissions and limitations under the License.
+ * 
+ **************************************************************************/
+
+#include <list>             // for list
+#include <cstddef>          // size_t
+
+#include <23.list.h>        // for ListMembers
+#include <driver.h>         // for rw_assert()
+#include <rw_allocator.h>   // for UserAlloc
+#include <rw_new.h>         // for bad_alloc, replacement operator new
+
+/**************************************************************************/
+
+// for convenience and brevity
+#define Swap(sig)   ListIds::swap_ ## sig
+
+static const char* const exceptions[] = {
+    "unknown exception", "bad_alloc", "exception"
+};
+
+/**************************************************************************/
+
+// exercises:
+// swap (list&)
+static const ContainerTestCase
+cont_cont_test_cases [] = {
+
+#undef TEST
+#define TEST(str, arg)                                \
+    { __LINE__, -1, -1, -1, -1, -1,                   \
+    str, sizeof str - 1, arg, sizeof arg - 1,         \
+    0, 0, 0                                           \
+    }
+
+    //    +------------------------- controlled "destination" sequence
+    //    |                +-------- controlled "source" sequence
+    //    |                |
+    //    V                V
+    TEST ("",              ""),
+};
+
+// exercises:
+// swap (list&)
+static const ContainerTestCase
+cont_test_cases [] = {
+
+    //    +------------------------- controlled "destination" sequence
+    //    |                +-------- controlled "source" sequence
+    //    |                |
+    //    V                V
+    TEST ("",              ""),
+    TEST ("",              "a"),
+    TEST ("a",             ""),
+    TEST ("",              "<U0>"),
+    TEST ("<U0>",          ""),
+
+    TEST ("a",             "b"),
+    TEST ("a",             "bc"),
+    TEST ("ab",            "c"),
+
+    TEST ("a<U0>b<U0>@2c", "<U0>b<U0>@2c"),
+    TEST ("<U0>b<U0>@2c",  "a<U0>b<U0>@2c"),
+
+    TEST ("a<U0>b<U0>@2c", "<U0>@2"),
+    TEST ("<U0>@2",        "a<U0>b<U0>@2c"),
+
+    TEST ("x@4096",        ""),
+    TEST ("",              "x@4096"),
+    TEST ("x@4096",        "<U0>@3"),
+    TEST ("<U0>@3",        "x@4096"),
+    TEST ("x@4096",        "x@4096"),
+
+    TEST ("",              "x@128"),
+    TEST ("x@207",         "x@128"),
+    TEST ("x@128",         "x@334"),
+    TEST ("x@873",         "x@334"),
+    TEST ("x@1412",        "x@540"),
+    TEST ("x@540",         "x@2284"),
+    TEST ("x@3695",        "x@2284"),
+    TEST ("x@3695",        "x@128"),
+
+    TEST ("",              0),
+    TEST ("<U0>",          0),
+    TEST ("abc",           0),
+    TEST ("a<U0>b<U0>@2c", 0),
+    TEST ("x@4096",        0),
+
+    TEST (0,               ""),
+    TEST (0,               "<U0>"),       
+    TEST (0,               "abc@1024"),       
+    TEST (0,               "a<U0>b<U0>@2c"), 
+    TEST (0,               "x@4096"),   
+ 
+    TEST ("last",          "test")
+};
+
+
+/**************************************************************************/
+
+struct ListValueType { };
+
+typedef std::allocator<ListValueType>           ListAllocator;
+typedef std::list<ListValueType, ListAllocator> ListType;
+
+static int list_swap_called;
+
+_RWSTD_NAMESPACE (std) {
+
+    // define an explicit specialization of the list::swap() member
+    // to verify tha the non-member swap function calls the member
+
+_RWSTD_SPECIALIZED_FUNCTION
+void ListType::swap (ListType&)
+{
+    ++list_swap_called;
+}
+
+}   // namespace std
+
+/**************************************************************************/
+
+void test_std_swap ()
+{
+    static bool tested = false;
+
+    if (tested)
+        return;
+
+    tested = true;
+
+    rw_info (0, 0, 0, 
+             "Testing std::swap (std::list&, std::list&) "
+             "calls std::list::swap");
+
+    // verify the signature of the function specialization
+    void (*pswap)(ListType&, ListType&) =
+        &std::swap<ListValueType, ListAllocator>;
+
+    _RWSTD_UNUSED (pswap);
+
+    // verify that std::swap() calls std::list::swap()
+    ListType lst;
+
+    std::swap (lst, lst);
+
+    rw_assert (1 == list_swap_called, 0, __LINE__,
+               "std::swap (std::list<T, A>&, std::list<T, A>&) called "
+               "std::list<T, A>::swap (std::list<T, A>&) exactly once; "
+               "got %d times", list_swap_called);
+}
+
+/**************************************************************************/
+
+template <class T, class Allocator>
+void test_swap (T*,
+                Allocator                      &a1,
+                Allocator                      &a2,
+                const ContainerTestCaseData<T> &tdata)
+{
+    typedef std::list <T, Allocator> List;
+    typedef ListState<List>          ListState;
+
+    const ContainerTestCase &tcase = tdata.tcase_;
+    const ContainerFunc     &func  = tdata.func_;
+
+    // construct the list object to be modified
+    // and the argument list
+    List src_list (tdata.str_, tdata.str_ + tdata.strlen_, a1);
+    List dst_list (tdata.arg_, tdata.arg_ + tdata.arglen_, a2);
+
+    List& arg_list            = tcase.arg ? dst_list : src_list;
+
+    // save the state of the list object before the call
+    // to detect exception safety violations (changes to
+    // the state of the object after an exception)
+    const ListState src_state (src_list);
+    const ListState arg_state (arg_list);
+
+    rwt_free_store* const pst = rwt_get_free_store (0);
+    SharedAlloc*    const pal = SharedAlloc::instance ();
+
+    // iterate for`throw_count' starting at the next call to operator new,
+    // forcing each call to throw an exception, until the function finally
+    // succeeds (i.e, no exception is thrown)
+    std::size_t throw_count;
+    for (throw_count = 0; ; ++throw_count) {
+
+        const char* expected = 0;
+        const char* caught = 0;
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+        // no exceptions expected
+        if (0 == tcase.bthrow && a1 == a2) {
+            // by default exercise the exception safety of the function
+            // by iteratively inducing an exception at each call to operator
+            // new or Allocator::allocate() until the call succeeds
+            expected = exceptions [1];      // bad_alloc
+            *pst->throw_at_calls_ [0] = pst->new_calls_ [0] + throw_count + 1;
+            pal->throw_at_calls_ [pal->m_allocate] =
+                pal->throw_at_calls_ [pal->m_allocate] + throw_count + 1;
+        }
+
+#else   // if defined (_RWSTD_NO_EXCEPTIONS)
+
+        if (tcase.bthrow)
+            return;
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+        // start checking for memory leaks
+        rw_check_leaks (src_list.get_allocator ());
+        rw_check_leaks (arg_list.get_allocator ());
+
+        try {
+            const bool is_class = ListIds::UserClass == func.elem_id_;
+
+            // reset function call counters
+            if (is_class)
+                UserClass::reset_totals ();
+
+            src_list.swap (arg_list);
+
+            if (is_class && a1 == a2) {
+
+                bool success =  0 == (UserClass::n_total_def_ctor_
+                                    | UserClass::n_total_copy_ctor_
+                                    | UserClass::n_total_op_assign_);
+
+                rw_assert (success, 0, tcase.line, 
+                           "line %d. %{$FUNCALL}: complexity: %zu def ctors, "
+                           "%zu copy ctors, %zu assigns", __LINE__,
+                           UserClass::n_total_def_ctor_,
+                           UserClass::n_total_copy_ctor_,
+                           UserClass::n_total_op_assign_);
+            }
+
+            if (0 == tcase.str) {
+
+                rw_assert (0 == arg_list.size (), 0, tcase.line, 
+                           "line %d. %{$FUNCALL}: expected 0 size, "
+                           "got %zu",  __LINE__, arg_list.size ());
+            }
+
+            if (a1 == a2) {
+
+                src_state.assert_equal (ListState (arg_list),
+                    __LINE__, tcase.line, "swap");
+
+                arg_state.assert_equal (ListState (src_list),
+                    __LINE__, tcase.line, "swap");
+            }
+        }
+
+#ifndef _RWSTD_NO_EXCEPTIONS
+
+        catch (const std::bad_alloc &ex) {
+            caught = exceptions [1];
+            rw_assert (0 == tcase.bthrow, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                       "unexpectedly%{;} caught std::%s(%#s)",
+                       __LINE__, 0 != expected, expected, caught, ex.what ());
+        }
+        catch (const std::exception &ex) {
+            caught = exceptions [2];
+            rw_assert (0, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                       "unexpectedly%{;} caught std::%s(%#s)",
+                       __LINE__, 0 != expected, expected, caught, ex.what ());
+        }
+        catch (...) {
+            caught = exceptions [0];
+            rw_assert (0, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
+                       "unexpectedly%{;} caught %s",
+                       __LINE__, 0 != expected, expected, caught);
+        }
+
+#endif   // _RWSTD_NO_EXCEPTIONS
+
+        // FIXME: verify the number of blocks the function call
+        // is expected to allocate and detect any memory leaks
+        rw_check_leaks (src_list.get_allocator (), tcase.line,
+                        std::size_t (-1), std::size_t (-1));
+
+        rw_check_leaks (arg_list.get_allocator (), tcase.line,
+                        std::size_t (-1), std::size_t (-1));
+
+        if (caught) {
+            // verify that an exception thrown during allocation
+            // didn't cause a change in the state of the object
+            src_state.assert_equal (ListState (src_list),
+                                    __LINE__, tcase.line, caught);
+
+            arg_state.assert_equal (ListState (arg_list),
+                                    __LINE__, tcase.line, caught);
+
+            if (0 == tcase.bthrow) {
+                // allow this call to operator new to succeed and try
+                // to make the next one to fail during the next call
+                // to the same function again
+                continue;
+            }
+        }
+        else if (0 < tcase.bthrow) {
+            rw_assert (caught == expected, 0, tcase.line,
+                       "line %d. %{$FUNCALL} %{?}expected %s, caught %s"
+                       "%{:}unexpectedly caught %s%{;}",
+                       __LINE__, 0 != expected, expected, caught, caught);
+        }
+
+        break;
+    }
+
+    // no exception expected
+    const std::size_t expect_throws = 0;
+
+    rw_assert (expect_throws == throw_count, 0, tcase.line,
+               "line %d: %{$FUNCALL}: expected exactly 0 %s exception "
+               "while the swap, got %zu",
+               __LINE__, exceptions [1], throw_count);
+
+    // disable bad_alloc exceptions
+    *pst->throw_at_calls_ [0] = 0;
+    pal->throw_at_calls_ [pal->m_allocate] = 0;
+}
+
+/**************************************************************************/
+
+template <class T>
+std::allocator<T>
+make_alloc (SharedAlloc&, std::allocator<T>*) {
+    return std::allocator<T>();
+}
+
+template <class T, class Types>
+UserAlloc<T, Types>
+make_alloc (SharedAlloc &shal, UserAlloc<T, Types>*) {
+    return UserAlloc<T, Types>(&shal);
+}
+
+/**************************************************************************/
+
+template <class T, class Allocator>
+void test_swap (T*, Allocator*,
+                const ContainerTestCaseData<T> &tdata)
+{
+    if (Swap (cont_cont) == tdata.func_.which_) {
+
+        test_std_swap ();
+
+        return;
+    }
+
+    SharedAlloc sa1;
+    Allocator a1 = make_alloc(sa1, (Allocator*)0);
+
+    // test swap using the same allocator objects
+    test_swap ((T*)0, a1, a1, tdata);
+
+    SharedAlloc sa2;
+    Allocator a2 = make_alloc(sa2, (Allocator*)0);
+
+    if (a1 != a2) {
+        // test swap using different allocator objects
+        test_swap ((T*)0, a1, a2, tdata);
+    }
+}
+
+/**************************************************************************/
+
+DEFINE_CONTAINER_TEST_FUNCTIONS (test_swap);
+
+int main (int argc, char** argv)
+{
+    static const ContainerTest
+    tests [] = {
+
+#undef TEST
+#define TEST(sig) {                                             \
+        Swap (sig), sig ## _test_cases,                         \
+        sizeof sig ## _test_cases / sizeof *sig ## _test_cases, \
+    }
+
+        TEST (cont),
+        TEST (cont_cont)
+    };
+
+    const std::size_t test_count = sizeof tests / sizeof *tests;
+
+    const int status =
+        rw_run_cont_test (argc, argv, __FILE__,
+                          "lib.list.special",
+                          ContainerIds::List,
+                          test_swap_func_array, tests, test_count);
+
+    return status;
+}

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.special.cpp
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: incubator/stdcxx/trunk/tests/containers/23.list.special.cpp
------------------------------------------------------------------------------
    svn:keywords = Id



Mime
View raw message