aboutsummaryrefslogtreecommitdiff
path: root/libstdc++-v3/testsuite
diff options
context:
space:
mode:
authorJonathan Wakely <jwakely@redhat.com>2017-10-27 00:50:40 +0100
committerJonathan Wakely <redi@gcc.gnu.org>2017-10-27 00:50:40 +0100
commitd67be4437a94b3f261ee22515b9508da59c691ef (patch)
tree102e630a448b23221458eabdc5ea069db19503fc /libstdc++-v3/testsuite
parente1b76fde8ffaa74dffc895c2e2e625e30428b435 (diff)
downloadgcc-d67be4437a94b3f261ee22515b9508da59c691ef.zip
gcc-d67be4437a94b3f261ee22515b9508da59c691ef.tar.gz
gcc-d67be4437a94b3f261ee22515b9508da59c691ef.tar.bz2
Protect more algorithms from overloaded comma operators
* include/bits/stl_algo.h (__find_if_not_n, generate_n): Cast to void to ensure overloaded comma not used. * include/bits/stl_algobase.h (__fill_n_a, equal): Likewise. * include/bits/stl_uninitialized.h (__uninitialized_fill_n) (__uninitialized_fill_n_a, __uninitialized_default_n_1) (__uninitialized_default_n_a, __uninitialized_copy_n) (__uninitialized_copy_n_pair): Likewise * testsuite/20_util/specialized_algorithms/memory_management_tools/1.cc: Use test iterator wrappers with overloaded comma operator. * testsuite/25_algorithms/fill_n/1.cc: Likewise. * testsuite/25_algorithms/generate_n/1.cc: New test. * testsuite/25_algorithms/stable_partition/1.cc: New test. * testsuite/util/testsuite_iterators.h (operator,): Add deleted non-member comma operator with iterator wrappers as right operand. From-SVN: r254128
Diffstat (limited to 'libstdc++-v3/testsuite')
-rw-r--r--libstdc++-v3/testsuite/20_util/specialized_algorithms/memory_management_tools/1.cc82
-rw-r--r--libstdc++-v3/testsuite/25_algorithms/fill_n/1.cc19
-rw-r--r--libstdc++-v3/testsuite/25_algorithms/generate_n/1.cc47
-rw-r--r--libstdc++-v3/testsuite/25_algorithms/stable_partition/1.cc8
-rw-r--r--libstdc++-v3/testsuite/util/testsuite_iterators.h9
5 files changed, 130 insertions, 35 deletions
diff --git a/libstdc++-v3/testsuite/20_util/specialized_algorithms/memory_management_tools/1.cc b/libstdc++-v3/testsuite/20_util/specialized_algorithms/memory_management_tools/1.cc
index 39d3e76..d118dd1 100644
--- a/libstdc++-v3/testsuite/20_util/specialized_algorithms/memory_management_tools/1.cc
+++ b/libstdc++-v3/testsuite/20_util/specialized_algorithms/memory_management_tools/1.cc
@@ -19,8 +19,8 @@
#include <memory>
#include <testsuite_hooks.h>
+#include <testsuite_iterators.h>
#include <string>
-#include <array>
#include <vector>
#include <sstream>
@@ -56,36 +56,42 @@ struct ThrowAfterN
DelCount dc;
};
+template<typename T>
+ using FwdIteratorRange
+ = __gnu_test::test_container<T, __gnu_test::forward_iterator_wrapper>;
+
void test01()
{
char test_data[] = "123456";
- std::uninitialized_default_construct(std::begin(test_data),
- std::end(test_data));
+ FwdIteratorRange<char> r(test_data);
+ std::uninitialized_default_construct(std::begin(r), std::end(r));
VERIFY(std::string(test_data) == "123456");
}
void test02()
{
char test_data[] = "123456";
- std::uninitialized_value_construct(std::begin(test_data),
- std::end(test_data));
+ FwdIteratorRange<char> r(test_data);
+ std::uninitialized_value_construct(std::begin(r), std::end(r));
VERIFY(std::string(test_data, 6) == std::string("\0\0\0\0\0\0", 6));
}
void test03()
{
char test_data[] = "123456";
- auto end = std::uninitialized_default_construct_n(std::begin(test_data), 6);
+ FwdIteratorRange<char> r(test_data);
+ auto end = std::uninitialized_default_construct_n(std::begin(r), 6);
VERIFY(std::string(test_data) == "123456");
- VERIFY( end == test_data + 6 );
+ VERIFY( end == std::next(r.begin(), 6) );
}
void test04()
{
char test_data[] = "123456";
- auto end = std::uninitialized_value_construct_n(std::begin(test_data), 5);
+ FwdIteratorRange<char> r(test_data);
+ auto end = std::uninitialized_value_construct_n(std::begin(r), 5);
VERIFY(std::string(test_data, 6) == std::string("\0\0\0\0\0" "6", 6));
- VERIFY( end == test_data + 5 );
+ VERIFY( end == std::next(r.begin(), 5) );
}
void test05()
@@ -122,33 +128,43 @@ void test07()
free(x);
}
+struct MoveOnly
+{
+ MoveOnly() : val(-1) { }
+ MoveOnly(MoveOnly&& m) : val(m.val) { m.val = -1; }
+ int val;
+};
+
void test08()
{
- std::vector<std::unique_ptr<int>> source;
- for (int i = 0; i < 10; ++i) source.push_back(std::make_unique<int>(i));
- std::unique_ptr<int>* target =
- (std::unique_ptr<int>*)malloc(sizeof(std::unique_ptr<int>)*10);
- std::uninitialized_move(source.begin(), source.end(), target);
- for (const auto& x : source) VERIFY(!x);
- for (int i = 0; i < 10; ++i) VERIFY(bool(*(target+i)));
- auto end = std::destroy_n(target, 10);
- VERIFY( end == target + 10 );
+ MoveOnly source[10];
+ for (int i = 0; i < 10; ++i) source[i].val = i;
+ FwdIteratorRange<MoveOnly> src(source);
+ MoveOnly* target = (MoveOnly*)malloc(sizeof(MoveOnly)*10);
+ FwdIteratorRange<MoveOnly> tgt(target, target+10);
+ auto end = std::uninitialized_move(src.begin(), src.end(), tgt.begin());
+ VERIFY( end == std::next(tgt.begin(), 10) );
+ for (const auto& x : source) VERIFY( x.val == -1 );
+ for (int i = 0; i < 10; ++i) VERIFY( target[i].val == i );
+ auto end2 = std::destroy_n(tgt.begin(), 10);
+ VERIFY( end2 == std::next(tgt.begin(), 10) );
free(target);
}
void test09()
{
- std::vector<std::unique_ptr<int>> source;
- for (int i = 0; i < 10; ++i) source.push_back(std::make_unique<int>(i));
- std::unique_ptr<int>* target =
- (std::unique_ptr<int>*)malloc(sizeof(std::unique_ptr<int>)*10);
- auto end = std::uninitialized_move_n(source.begin(), 10, target);
- VERIFY( end.first == source.begin() + 10 );
- VERIFY( end.second == target + 10 );
- for (const auto& x : source) VERIFY(!x);
- for (int i = 0; i < 10; ++i) VERIFY(bool(*(target+i)));
- auto end2 = std::destroy_n(target, 10);
- VERIFY( end2 == target + 10 );
+ MoveOnly source[10];
+ for (int i = 0; i < 10; ++i) source[i].val = i;
+ FwdIteratorRange<MoveOnly> src(source);
+ MoveOnly* target = (MoveOnly*)malloc(sizeof(MoveOnly)*10);
+ FwdIteratorRange<MoveOnly> tgt(target, target+10);
+ auto end = std::uninitialized_move_n(src.begin(), 10, tgt.begin());
+ VERIFY( end.first == std::next(src.begin(), 10) );
+ VERIFY( end.second == std::next(tgt.begin(), 10) );
+ for (const auto& x : source) VERIFY( x.val == -1 );
+ for (int i = 0; i < 10; ++i) VERIFY( target[i].val == i );
+ auto end2 = std::destroy_n(tgt.begin(), 10);
+ VERIFY( end2 == std::next(tgt.begin(), 10) );
free(target);
}
@@ -156,7 +172,8 @@ void test10()
{
char* x = (char*)malloc(sizeof(char)*10);
for (int i = 0; i < 10; ++i) new (x+i) char;
- std::destroy(x, x+10);
+ FwdIteratorRange<char> r(x, x+10);
+ std::destroy(r.begin(), r.end());
free(x);
}
@@ -164,8 +181,9 @@ void test11()
{
char* x = (char*)malloc(sizeof(char)*10);
for (int i = 0; i < 10; ++i) new (x+i) char;
- auto end = std::destroy_n(x, 10);
- VERIFY( end == x + 10 );
+ FwdIteratorRange<char> r(x, x+10);
+ auto end = std::destroy_n(r.begin(), 10);
+ VERIFY( end == std::next(r.begin(), 10) );
free(x);
}
diff --git a/libstdc++-v3/testsuite/25_algorithms/fill_n/1.cc b/libstdc++-v3/testsuite/25_algorithms/fill_n/1.cc
index d446e7a..4d27f0b 100644
--- a/libstdc++-v3/testsuite/25_algorithms/fill_n/1.cc
+++ b/libstdc++-v3/testsuite/25_algorithms/fill_n/1.cc
@@ -22,21 +22,36 @@
#include <algorithm>
#include <vector>
#include <testsuite_hooks.h>
+#include <testsuite_iterators.h>
+
+// Non-scalar type to exercise partial specialization of fill_n implementation.
+struct Value
+{
+ Value(int n) : n(n) { }
+
+ operator int() const { return n; }
+
+private:
+ int n;
+};
void
test01()
{
using namespace std;
+ using __gnu_test::test_container;
+ using __gnu_test::output_iterator_wrapper;
const int A1[] = {3, 3, 3, 3, 3, 3, 3, 3, 3, 3};
const int N1 = sizeof(A1) / sizeof(int);
int i1[N1];
- fill_n(i1, N1, 3);
+ test_container<int, output_iterator_wrapper> c1(i1, i1 + N1);
+ fill_n(c1.begin(), N1, 3);
VERIFY( equal(i1, i1 + N1, A1) );
vector<int> v1(N1);
- fill_n(v1.begin(), N1, 3);
+ fill_n(v1.begin(), N1, Value(3));
VERIFY( equal(v1.begin(), v1.end(), A1) );
const char A2[] = {'\3', '\3', '\3', '\3', '\3',
diff --git a/libstdc++-v3/testsuite/25_algorithms/generate_n/1.cc b/libstdc++-v3/testsuite/25_algorithms/generate_n/1.cc
new file mode 100644
index 0000000..dc3cb9f
--- /dev/null
+++ b/libstdc++-v3/testsuite/25_algorithms/generate_n/1.cc
@@ -0,0 +1,47 @@
+// Copyright (C) 2017 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
+// terms of the GNU General Public License as published by the
+// Free Software Foundation; either version 3, or (at your option)
+// any later version.
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+// GNU General Public License for more details.
+
+// You should have received a copy of the GNU General Public License along
+// with this library; see the file COPYING3. If not see
+// <http://www.gnu.org/licenses/>.
+
+#include <algorithm>
+#include <testsuite_hooks.h>
+#include <testsuite_iterators.h>
+
+struct Inc
+{
+ int operator()() { return ++i; }
+
+ int i;
+};
+
+void
+test01()
+{
+ const int N = 3;
+ int array[N];
+
+ using __gnu_test::test_container;
+ using __gnu_test::output_iterator_wrapper;
+ test_container<int, output_iterator_wrapper> c(array, array + N);
+ std::generate_n(c.begin(), N, Inc());
+ VERIFY(array[0] == 1);
+ VERIFY(array[1] == 2);
+ VERIFY(array[2] == 3);
+}
+
+int main()
+{
+ test01();
+}
diff --git a/libstdc++-v3/testsuite/25_algorithms/stable_partition/1.cc b/libstdc++-v3/testsuite/25_algorithms/stable_partition/1.cc
index 7585157..f29d817 100644
--- a/libstdc++-v3/testsuite/25_algorithms/stable_partition/1.cc
+++ b/libstdc++-v3/testsuite/25_algorithms/stable_partition/1.cc
@@ -21,6 +21,7 @@
#include <functional>
#include <testsuite_new_operators.h>
#include <testsuite_hooks.h>
+#include <testsuite_iterators.h>
const int A[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17};
const int B[] = {2, 4, 6, 8, 10, 12, 14, 16, 1, 3, 5, 7, 9, 11, 13, 15, 17};
@@ -41,11 +42,16 @@ void
test01()
{
using std::stable_partition;
+ using __gnu_test::test_container;
+ using __gnu_test::forward_iterator_wrapper;
int s1[N];
std::copy(A, A + N, s1);
- VERIFY( stable_partition(s1, s1 + N, Pred()) == s1 + M );
+ test_container<int, forward_iterator_wrapper> c(s1, s1+N);
+ forward_iterator_wrapper<int> expected = c.begin();
+ std::advance(expected, M);
+ VERIFY( stable_partition(c.begin(), c.end(), Pred()) == expected);
VERIFY( std::equal(s1, s1 + N, B) );
}
diff --git a/libstdc++-v3/testsuite/util/testsuite_iterators.h b/libstdc++-v3/testsuite/util/testsuite_iterators.h
index d61b216..d6b550d 100644
--- a/libstdc++-v3/testsuite/util/testsuite_iterators.h
+++ b/libstdc++-v3/testsuite/util/testsuite_iterators.h
@@ -180,6 +180,11 @@ namespace __gnu_test
#endif
};
+#if __cplusplus >= 201103L
+ template<typename T, typename U>
+ void operator,(const T&, const output_iterator_wrapper<U>&) = delete;
+#endif
+
/**
* @brief input_iterator wrapper for pointer
*
@@ -270,6 +275,10 @@ namespace __gnu_test
#endif
};
+#if __cplusplus >= 201103L
+ template<typename T, typename U>
+ void operator,(const T&, const input_iterator_wrapper<U>&) = delete;
+#endif
/**
* @brief forward_iterator wrapper for pointer