44#define OpPlusEq(sig) StringIds::op_plus_eq_ ## sig
46static const char*
const exceptions[] = {
47 "unknown exception",
"out_of_range",
"length_error",
48 "bad_alloc",
"exception"
59#define TEST(str, src, res, bthrow) \
60 { __LINE__, -1, -1, -1, -1, -1, str, sizeof str - 1, src, \
61 sizeof src - 1, res, sizeof res - 1, bthrow }
72 TEST (
"ab",
"c",
"abc", 0),
75 TEST (
"",
"<U0>",
"", 0),
76 TEST (
"",
"abc",
"abc", 0),
78 TEST (
"<U0>",
"",
"<U0>", 0),
79 TEST (
"<U0>",
"a",
"<U0>a", 0),
80 TEST (
"<U0>",
"<U0>@2",
"<U0>", 0),
82 TEST (
"ab",
"cd",
"abcd", 0),
83 TEST (
"bcd",
"a",
"bcda", 0),
84 TEST (
"cde",
"ab",
"cdeab", 0),
85 TEST (
"abc",
"",
"abc", 0),
86 TEST (
"ab",
"c<U0>e",
"abc", 0),
88 TEST (
"<U0>@2ab",
"cdefghij",
"<U0>@2abcdefghij", 0),
89 TEST (
"a<U0>@2b",
"cdefghij",
"a<U0>@2bcdefghij", 0),
90 TEST (
"ab<U0>@2",
"cdefghij",
"ab<U0>@2cdefghij", 0),
91 TEST (
"a<U0>b<U0>@2c",
"e<U0>",
"a<U0>b<U0>@2ce", 0),
92 TEST (
"<U0>ab<U0>@2c",
"e<U0>",
"<U0>ab<U0>@2ce", 0),
93 TEST (
"abcdefghij",
"abcdefghij",
"abcdefghijabcdefghij", 0),
95 TEST (
"",
"x@4096",
"x@4096", 0),
96 TEST (
"x@4096",
"",
"x@4096", 0),
97 TEST (
"x@2048",
"y@2048",
"x@2048y@2048", 0),
99 TEST (
"x@10",
"x@118",
"x@128", 0),
100 TEST (
"x@128",
"x@79",
"x@207", 0),
101 TEST (
"x@207",
"x@127",
"x@334", 0),
102 TEST (
"x@334",
"x@206",
"x@540", 0),
103 TEST (
"x@540",
"x@333",
"x@873", 0),
104 TEST (
"x@539",
"x@873",
"x@1412", 0),
105 TEST (
"x@872",
"x@1412",
"x@2284", 0),
106 TEST (
"x@1411",
"x@2284",
"x@3695", 0),
107 TEST (
"x@1412",
"x@2284",
"x@3696", 0),
110 TEST (
"abc", 0,
"abcabc", 0),
111 TEST (
"a<U0>@2bc", 0,
"a<U0>@2bca", 0),
112 TEST (
"<U0>@2abc", 0,
"<U0>@2abc", 0),
113 TEST (
"abc<U0>@2", 0,
"abc<U0>@2abc", 0),
114 TEST (
"x@2048", 0,
"x@4096", 0),
116 TEST (
"last",
"test",
"lasttest", 0)
124cstr_test_cases [] = {
127#define TEST(str, src, res, bthrow) \
128 { __LINE__, -1, -1, -1, -1, -1, str, sizeof str - 1, src, \
129 sizeof src - 1, res, sizeof res - 1, bthrow }
140 TEST (
"ab",
"c",
"abc", 0),
142 TEST (
"",
"",
"", 0),
143 TEST (
"",
"<U0>",
"<U0>", 0),
144 TEST (
"",
"abc",
"abc", 0),
146 TEST (
"<U0>",
"",
"<U0>", 0),
147 TEST (
"<U0>",
"a",
"<U0>a", 0),
148 TEST (
"<U0>",
"<U0>@2",
"<U0>@3", 0),
150 TEST (
"ab",
"cd",
"abcd", 0),
151 TEST (
"bcd",
"a",
"bcda", 0),
152 TEST (
"cde",
"ab",
"cdeab", 0),
153 TEST (
"abc",
"",
"abc", 0),
154 TEST (
"ab",
"c<U0>e",
"abc<U0>e", 0),
156 TEST (
"<U0>@2ab",
"cdefghij",
"<U0>@2abcdefghij", 0),
157 TEST (
"a<U0>@2b",
"cdefghij",
"a<U0>@2bcdefghij", 0),
158 TEST (
"ab<U0>@2",
"cdefghij",
"ab<U0>@2cdefghij", 0),
159 TEST (
"a<U0>b<U0>@2c",
"e<U0>",
"a<U0>b<U0>@2ce<U0>", 0),
160 TEST (
"<U0>ab<U0>@2c",
"e<U0>",
"<U0>ab<U0>@2ce<U0>", 0),
161 TEST (
"ab<U0>@2c<U0>",
"<U0>e",
"ab<U0>@2c<U0>@2e", 0),
162 TEST (
"abcdefghij",
"abcdefghij",
"abcdefghijabcdefghij", 0),
164 TEST (
"",
"x@4096",
"x@4096", 0),
165 TEST (
"x@4096",
"",
"x@4096", 0),
166 TEST (
"x@2048",
"y@2048",
"x@2048y@2048", 0),
168 TEST (
"x@10",
"x@118",
"x@128", 0),
169 TEST (
"x@128",
"x@79",
"x@207", 0),
170 TEST (
"x@207",
"x@127",
"x@334", 0),
171 TEST (
"x@334",
"x@206",
"x@540", 0),
172 TEST (
"x@540",
"x@333",
"x@873", 0),
173 TEST (
"x@539",
"x@873",
"x@1412", 0),
174 TEST (
"x@872",
"x@1412",
"x@2284", 0),
175 TEST (
"x@1411",
"x@2284",
"x@3695", 0),
176 TEST (
"x@1412",
"x@2284",
"x@3696", 0),
179 TEST (
"abc", 0,
"abcabc", 0),
180 TEST (
"a<U0>@2bc", 0,
"a<U0>@2bca<U0>@2bc", 0),
181 TEST (
"<U0>@2abc", 0,
"<U0>@2abc<U0>@2abc", 0),
182 TEST (
"abc<U0>@2", 0,
"abc<U0>@2abc<U0>@2", 0),
183 TEST (
"x@2048", 0,
"x@4096", 0),
185 TEST (
"last",
"test",
"lasttest", 0)
196#define TEST(str, val, res, bthrow) \
197 { __LINE__, -1, -1, -1, -1, val, str, sizeof str - 1, 0, 0, \
198 res, sizeof res - 1, bthrow }
209 TEST (
"ab",
'c',
"abc", 0),
211 TEST (
"",
'a',
"a", 0),
212 TEST (
"",
'\0',
"<U0>", 0),
214 TEST (
"<U0>",
'a',
"<U0>a", 0),
215 TEST (
"<U0>",
'\0',
"<U0>@2", 0),
217 TEST (
"cde",
'a',
"cdea", 0),
218 TEST (
"abc",
'\0',
"abc<U0>", 0),
220 TEST (
"a<U0>b<U0>@2c",
'\0',
"a<U0>b<U0>@2c<U0>", 0),
221 TEST (
"<U0>ab<U0>@2c",
'\0',
"<U0>ab<U0>@2c<U0>", 0),
222 TEST (
"a<U0>bc<U0>@2",
'a',
"a<U0>bc<U0>@2a", 0),
224 TEST (
"x@127",
'x',
"x@128", 0),
225 TEST (
"x@206",
'x',
"x@207", 0),
226 TEST (
"x@333",
'x',
"x@334", 0),
227 TEST (
"x@539",
'x',
"x@540", 0),
228 TEST (
"x@1411",
'x',
"x@1412", 0),
229 TEST (
"x@2283",
'x',
"x@2284", 0),
230 TEST (
"x@3694",
'x',
"x@3695", 0),
231 TEST (
"x@540",
'x',
"x@541", 0),
233 TEST (
"last",
't',
"lastt", 0)
238template <
class charT,
class Traits,
class Allocator>
243 typedef std::basic_string <charT, Traits, Allocator>
String;
244 typedef typename String::iterator StringIter;
247 static const std::size_t BUFSIZE = 256;
249 static charT wstr_buf [BUFSIZE];
250 static charT warg_buf [BUFSIZE];
252 std::size_t str_len =
sizeof wstr_buf /
sizeof *wstr_buf;
253 std::size_t arg_len =
sizeof warg_buf /
sizeof *warg_buf;
258 static charT wres_buf [BUFSIZE];
259 std::size_t res_len =
sizeof wres_buf /
sizeof *wres_buf;
267 if (wstr != wstr_buf)
270 if (warg != warg_buf)
281 const charT*
const arg_ptr = tcase.
arg ?
arg.c_str () :
str.c_str ();
285 std::size_t total_length_calls = 0;
286 std::size_t n_length_calls = 0;
290 total_length_calls = rg_calls [UTMemFun::length];
298 std::size_t throw_count;
299 for (throw_count = 0; ; ++throw_count) {
302 const char* expected = 0;
305#ifndef _RWSTD_NO_EXCEPTIONS
308 expected = exceptions [2];
309 else if (0 == tcase.
bthrow) {
313 expected = exceptions [3];
325 if (wres != wres_buf)
339 const String* ret_ptr = 0;
341 switch (
func.which_) {
344 ret_ptr = &
str.operator+= (arg_ptr);
346 n_length_calls = rg_calls [UTMemFun::length];
350 ret_ptr = &
str.operator+= (arg_str);
354 ret_ptr = &
str.operator+= (arg_val);
358 RW_ASSERT (
"test logic error: unknown operator += overload");
365 const std::ptrdiff_t ret_off = ret_ptr - &
str;
369 "line %d. %{$FUNCALL} returned invalid reference, "
370 "offset is %td", __LINE__, ret_off);
374 "line %d. %{$FUNCALL} expected %{#*s} "
375 "with length %zu, got %{/*.*Gs} with length %zu",
376 __LINE__, int (tcase.
nres), tcase.
res, res_len,
377 int (
sizeof (
charT)),
int (
str.size ()),
378 str.c_str (),
str.size ());
380 if (res_len ==
str.size ()) {
384 const std::size_t match =
388 "line %d. %{$FUNCALL} expected %{#*s}, "
389 "got %{/*.*Gs}, difference at offset %zu",
390 __LINE__, int (tcase.
nres), tcase.
res,
391 int (
sizeof (
charT)),
int (
str.size ()),
392 str.c_str (), match);
397 rw_assert (n_length_calls - total_length_calls > 0,
398 0, tcase.
line,
"line %d. %{$FUNCALL} doesn't "
399 "use traits::length()", __LINE__);
403#ifndef _RWSTD_NO_EXCEPTIONS
405 catch (
const std::length_error &ex) {
408 "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
409 "unexpectedly%{;} caught std::%s(%#s)",
410 __LINE__, 0 != expected, expected,
caught, ex.what ());
415 "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
416 "unexpectedly%{;} caught std::%s(%#s)",
417 __LINE__, 0 != expected, expected,
caught, ex.what ());
422 "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
423 "unexpectedly%{;} caught std::%s(%#s)",
424 __LINE__, 0 != expected, expected,
caught, ex.what ());
429 "line %d. %{$FUNCALL} %{?}expected %s,%{:}"
430 "unexpectedly%{;} caught %s",
431 __LINE__, 0 != expected, expected,
caught);
439 std::size_t (-1), std::size_t (-1));
454 else if (0 < tcase.
bthrow) {
456 "line %d. %{$FUNCALL} %{?}expected %s, caught %s"
457 "%{:}unexpectedly caught %s%{;}",
464#ifndef _RWSTD_NO_REPLACEABLE_NEW_DELETE
468 const std::size_t expect_throws = str_state.
capacity_ <
str.capacity ();
472 const std::size_t expect_throws =
479 "line %d: %{$FUNCALL}: expected exactly 1 %s exception "
480 "while changing capacity from %zu to %zu, got %zu",
481 __LINE__, exceptions [3],
488 if (wres != wres_buf)
496int main (
int argc,
char** argv)
503 OpPlusEq (sig), sig ## _test_cases, \
504 sizeof sig ## _test_cases / sizeof *sig ## _test_cases \
512 const std::size_t test_count =
sizeof tests /
sizeof *tests;
void test_op_plus_eq(charT, Traits *, Allocator *, const StringFunc &func, const StringTestCase &tcase)
#define TEST(str, src, res, bthrow)
std::char_traits< S > Traits
_TEST_EXPORT void rw_check_leaks(const SharedAlloc *=0, int=0, _RWSTD_SIZE_T=0, _RWSTD_SIZE_T=_RWSTD_SIZE_MAX)
UserChar make_char(char c, UserChar *)
_TEST_EXPORT char * rw_expand(char *, const char *, _RWSTD_SIZE_T=_RWSTD_SIZE_MAX, _RWSTD_SIZE_T *=0)
_RWSTD_SIZE_T * rw_get_call_counters(std::char_traits< charT > *, charT *)
_TEST_EXPORT _RWSTD_SIZE_T rw_match(const char *, const char *, _RWSTD_SIZE_T=_RWSTD_SIZE_MAX)
_TEST_EXPORT int rw_assert(int, const char *, int, const char *,...)
_TEST_EXPORT rwt_free_store * rwt_get_free_store(rwt_free_store *)
StringState rw_get_string_state(const String &str)
#define DEFINE_STRING_TEST_DISPATCH(fname)
_TEST_EXPORT int rw_run_string_test(int, char **, const char *, const char *, StringTestFunc *, const StringTest *, _RWSTD_SIZE_T)
static SharedAlloc * instance(SharedAlloc *=0)
_RWSTD_SIZE_T throw_at_calls_[n_funs]
int assert_equal(const StringState &, int, int, const char *) const
_RWSTD_SIZE_T * throw_at_calls_[2]
_RWSTD_SIZE_T new_calls_[2]