1 /* 2 * Copyright (C) 2012 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #include <gtest/gtest.h> 18 19 #include <errno.h> 20 #include <math.h> 21 #include <string.h> 22 23 #define KB 1024 24 #define SMALL 1*KB 25 #define LARGE 64*KB 26 27 static int signum(int i) { 28 if (i < 0) { 29 return -1; 30 } else if (i > 0) { 31 return 1; 32 } 33 return 0; 34 } 35 36 TEST(string, strerror) { 37 // Valid. 38 ASSERT_STREQ("Success", strerror(0)); 39 ASSERT_STREQ("Operation not permitted", strerror(1)); 40 41 // Invalid. 42 ASSERT_STREQ("Unknown error -1", strerror(-1)); 43 ASSERT_STREQ("Unknown error 1234", strerror(1234)); 44 } 45 46 #if __BIONIC__ // glibc's strerror isn't thread safe, only its strsignal. 47 48 static void* ConcurrentStrErrorFn(void*) { 49 bool equal = (strcmp("Unknown error 2002", strerror(2002)) == 0); 50 return reinterpret_cast<void*>(equal); 51 } 52 53 TEST(string, strerror_concurrent) { 54 const char* strerror1001 = strerror(1001); 55 ASSERT_STREQ("Unknown error 1001", strerror1001); 56 57 pthread_t t; 58 ASSERT_EQ(0, pthread_create(&t, NULL, ConcurrentStrErrorFn, NULL)); 59 void* result; 60 ASSERT_EQ(0, pthread_join(t, &result)); 61 ASSERT_TRUE(static_cast<bool>(result)); 62 63 ASSERT_STREQ("Unknown error 1001", strerror1001); 64 } 65 66 #endif 67 68 #if __BIONIC__ // glibc's strerror_r doesn't even have the same signature as the POSIX one. 69 TEST(string, strerror_r) { 70 char buf[256]; 71 72 // Valid. 73 ASSERT_EQ(0, strerror_r(0, buf, sizeof(buf))); 74 ASSERT_STREQ("Success", buf); 75 ASSERT_EQ(0, strerror_r(1, buf, sizeof(buf))); 76 ASSERT_STREQ("Operation not permitted", buf); 77 78 // Invalid. 79 ASSERT_EQ(0, strerror_r(-1, buf, sizeof(buf))); 80 ASSERT_STREQ("Unknown error -1", buf); 81 ASSERT_EQ(0, strerror_r(1234, buf, sizeof(buf))); 82 ASSERT_STREQ("Unknown error 1234", buf); 83 84 // Buffer too small. 85 ASSERT_EQ(-1, strerror_r(0, buf, 2)); 86 ASSERT_EQ(ERANGE, errno); 87 } 88 #endif 89 90 TEST(string, strsignal) { 91 // A regular signal. 92 ASSERT_STREQ("Hangup", strsignal(1)); 93 94 // A real-time signal. 95 #ifdef __GLIBC__ // glibc reserves real-time signals for internal use, and doesn't count those. 96 ASSERT_STREQ("Real-time signal 14", strsignal(48)); 97 #else 98 ASSERT_STREQ("Real-time signal 16", strsignal(48)); 99 #endif 100 101 // Errors. 102 ASSERT_STREQ("Unknown signal -1", strsignal(-1)); // Too small. 103 ASSERT_STREQ("Unknown signal 0", strsignal(0)); // Still too small. 104 ASSERT_STREQ("Unknown signal 1234", strsignal(1234)); // Too large. 105 } 106 107 static void* ConcurrentStrSignalFn(void*) { 108 bool equal = (strcmp("Unknown signal 2002", strsignal(2002)) == 0); 109 return reinterpret_cast<void*>(equal); 110 } 111 112 TEST(string, strsignal_concurrent) { 113 const char* strsignal1001 = strsignal(1001); 114 ASSERT_STREQ("Unknown signal 1001", strsignal1001); 115 116 pthread_t t; 117 ASSERT_EQ(0, pthread_create(&t, NULL, ConcurrentStrSignalFn, NULL)); 118 void* result; 119 ASSERT_EQ(0, pthread_join(t, &result)); 120 ASSERT_TRUE(static_cast<bool>(result)); 121 122 ASSERT_STREQ("Unknown signal 1001", strsignal1001); 123 } 124 125 // TODO: where did these numbers come from? 126 #define POS_ITER 10 127 #define ITER 500 128 129 // For every length we want to test, vary and change alignment 130 // of allocated memory, fill it with some values, calculate 131 // expected result and then run function and compare what we got. 132 // These tests contributed by Intel Corporation. 133 // TODO: make these tests more intention-revealing and less random. 134 template<class Character> 135 struct StringTestState { 136 StringTestState(size_t MAX_LEN) : MAX_LEN(MAX_LEN) { 137 int max_alignment = 64; 138 139 // TODO: fix the tests to not sometimes use twice their specified "MAX_LEN". 140 glob_ptr = reinterpret_cast<Character*>(valloc(2 * sizeof(Character) * MAX_LEN + max_alignment)); 141 glob_ptr1 = reinterpret_cast<Character*>(valloc(2 * sizeof(Character) * MAX_LEN + max_alignment)); 142 glob_ptr2 = reinterpret_cast<Character*>(valloc(2 * sizeof(Character) * MAX_LEN + max_alignment)); 143 144 InitLenArray(); 145 146 srandom(1234); 147 } 148 149 ~StringTestState() { 150 free(glob_ptr); 151 free(glob_ptr1); 152 free(glob_ptr2); 153 } 154 155 void NewIteration() { 156 int alignments[] = { 24, 32, 16, 48, 1, 2, 3, 0, 5, 11 }; 157 int usable_alignments = 10; 158 int align1 = alignments[random() % (usable_alignments - 1)]; 159 int align2 = alignments[random() % (usable_alignments - 1)]; 160 161 ptr = glob_ptr + align1; 162 ptr1 = glob_ptr1 + align1; 163 ptr2 = glob_ptr2 + align2; 164 } 165 166 const size_t MAX_LEN; 167 Character *ptr, *ptr1, *ptr2; 168 size_t n; 169 int len[ITER + 1]; 170 171 private: 172 Character *glob_ptr, *glob_ptr1, *glob_ptr2; 173 174 // Calculate input lengths and fill state.len with them. 175 // Test small lengths with more density than big ones. Manually push 176 // smallest (0) and biggest (MAX_LEN) lengths. Avoid repeats. 177 // Return number of lengths to test. 178 void InitLenArray() { 179 n = 0; 180 len[n++] = 0; 181 for (size_t i = 1; i < ITER; ++i) { 182 int l = (int) exp(log((double) MAX_LEN) * i / ITER); 183 if (l != len[n - 1]) { 184 len[n++] = l; 185 } 186 } 187 len[n++] = MAX_LEN; 188 } 189 }; 190 191 TEST(string, strcat) { 192 StringTestState<char> state(SMALL); 193 for (size_t i = 1; i < state.n; i++) { 194 for (size_t j = 0; j < POS_ITER; j++) { 195 state.NewIteration(); 196 197 memset(state.ptr2, '\2', state.MAX_LEN); 198 state.ptr2[state.MAX_LEN - 1] = '\0'; 199 memcpy(state.ptr, state.ptr2, 2 * state.MAX_LEN); 200 201 memset(state.ptr1, random() & 255, state.len[i]); 202 state.ptr1[random() % state.len[i]] = '\0'; 203 state.ptr1[state.len[i] - 1] = '\0'; 204 205 strcpy(state.ptr + state.MAX_LEN - 1, state.ptr1); 206 207 EXPECT_TRUE(strcat(state.ptr2, state.ptr1) == state.ptr2); 208 EXPECT_TRUE(memcmp(state.ptr, state.ptr2, 2 * state.MAX_LEN) == 0); 209 } 210 } 211 } 212 213 // one byte target with "\0" source 214 TEST(string, strcpy2) { 215 char buf[1]; 216 char* orig = strdup(""); 217 strcpy(buf, orig); 218 ASSERT_EQ('\0', buf[0]); 219 free(orig); 220 } 221 222 // multibyte target where we under fill target 223 TEST(string, strcpy3) { 224 char buf[10]; 225 char* orig = strdup("12345"); 226 memset(buf, 'A', sizeof(buf)); 227 strcpy(buf, orig); 228 ASSERT_EQ('1', buf[0]); 229 ASSERT_EQ('2', buf[1]); 230 ASSERT_EQ('3', buf[2]); 231 ASSERT_EQ('4', buf[3]); 232 ASSERT_EQ('5', buf[4]); 233 ASSERT_EQ('\0', buf[5]); 234 ASSERT_EQ('A', buf[6]); 235 ASSERT_EQ('A', buf[7]); 236 ASSERT_EQ('A', buf[8]); 237 ASSERT_EQ('A', buf[9]); 238 free(orig); 239 } 240 241 // multibyte target where we fill target exactly 242 TEST(string, strcpy4) { 243 char buf[10]; 244 char* orig = strdup("123456789"); 245 memset(buf, 'A', sizeof(buf)); 246 strcpy(buf, orig); 247 ASSERT_EQ('1', buf[0]); 248 ASSERT_EQ('2', buf[1]); 249 ASSERT_EQ('3', buf[2]); 250 ASSERT_EQ('4', buf[3]); 251 ASSERT_EQ('5', buf[4]); 252 ASSERT_EQ('6', buf[5]); 253 ASSERT_EQ('7', buf[6]); 254 ASSERT_EQ('8', buf[7]); 255 ASSERT_EQ('9', buf[8]); 256 ASSERT_EQ('\0', buf[9]); 257 free(orig); 258 } 259 260 TEST(string, strcat2) { 261 char buf[10]; 262 memset(buf, 'A', sizeof(buf)); 263 buf[0] = 'a'; 264 buf[1] = '\0'; 265 char* res = strcat(buf, "01234"); 266 ASSERT_EQ(buf, res); 267 ASSERT_EQ('a', buf[0]); 268 ASSERT_EQ('0', buf[1]); 269 ASSERT_EQ('1', buf[2]); 270 ASSERT_EQ('2', buf[3]); 271 ASSERT_EQ('3', buf[4]); 272 ASSERT_EQ('4', buf[5]); 273 ASSERT_EQ('\0', buf[6]); 274 ASSERT_EQ('A', buf[7]); 275 ASSERT_EQ('A', buf[8]); 276 ASSERT_EQ('A', buf[9]); 277 } 278 279 TEST(string, strcat3) { 280 char buf[10]; 281 memset(buf, 'A', sizeof(buf)); 282 buf[0] = 'a'; 283 buf[1] = '\0'; 284 char* res = strcat(buf, "01234567"); 285 ASSERT_EQ(buf, res); 286 ASSERT_EQ('a', buf[0]); 287 ASSERT_EQ('0', buf[1]); 288 ASSERT_EQ('1', buf[2]); 289 ASSERT_EQ('2', buf[3]); 290 ASSERT_EQ('3', buf[4]); 291 ASSERT_EQ('4', buf[5]); 292 ASSERT_EQ('5', buf[6]); 293 ASSERT_EQ('6', buf[7]); 294 ASSERT_EQ('7', buf[8]); 295 ASSERT_EQ('\0', buf[9]); 296 } 297 298 TEST(string, strncat2) { 299 char buf[10]; 300 memset(buf, 'A', sizeof(buf)); 301 buf[0] = 'a'; 302 buf[1] = '\0'; 303 char* res = strncat(buf, "01234", sizeof(buf) - strlen(buf) - 1); 304 ASSERT_EQ(buf, res); 305 ASSERT_EQ('a', buf[0]); 306 ASSERT_EQ('0', buf[1]); 307 ASSERT_EQ('1', buf[2]); 308 ASSERT_EQ('2', buf[3]); 309 ASSERT_EQ('3', buf[4]); 310 ASSERT_EQ('4', buf[5]); 311 ASSERT_EQ('\0', buf[6]); 312 ASSERT_EQ('A', buf[7]); 313 ASSERT_EQ('A', buf[8]); 314 ASSERT_EQ('A', buf[9]); 315 } 316 317 TEST(string, strncat3) { 318 char buf[10]; 319 memset(buf, 'A', sizeof(buf)); 320 buf[0] = 'a'; 321 buf[1] = '\0'; 322 char* res = strncat(buf, "0123456789", 5); 323 ASSERT_EQ(buf, res); 324 ASSERT_EQ('a', buf[0]); 325 ASSERT_EQ('0', buf[1]); 326 ASSERT_EQ('1', buf[2]); 327 ASSERT_EQ('2', buf[3]); 328 ASSERT_EQ('3', buf[4]); 329 ASSERT_EQ('4', buf[5]); 330 ASSERT_EQ('\0', buf[6]); 331 ASSERT_EQ('A', buf[7]); 332 ASSERT_EQ('A', buf[8]); 333 ASSERT_EQ('A', buf[9]); 334 } 335 336 TEST(string, strncat4) { 337 char buf[10]; 338 memset(buf, 'A', sizeof(buf)); 339 buf[0] = 'a'; 340 buf[1] = '\0'; 341 char* res = strncat(buf, "01234567", 8); 342 ASSERT_EQ(buf, res); 343 ASSERT_EQ('a', buf[0]); 344 ASSERT_EQ('0', buf[1]); 345 ASSERT_EQ('1', buf[2]); 346 ASSERT_EQ('2', buf[3]); 347 ASSERT_EQ('3', buf[4]); 348 ASSERT_EQ('4', buf[5]); 349 ASSERT_EQ('5', buf[6]); 350 ASSERT_EQ('6', buf[7]); 351 ASSERT_EQ('7', buf[8]); 352 ASSERT_EQ('\0', buf[9]); 353 } 354 355 TEST(string, strncat5) { 356 char buf[10]; 357 memset(buf, 'A', sizeof(buf)); 358 buf[0] = 'a'; 359 buf[1] = '\0'; 360 char* res = strncat(buf, "01234567", 9); 361 ASSERT_EQ(buf, res); 362 ASSERT_EQ('a', buf[0]); 363 ASSERT_EQ('0', buf[1]); 364 ASSERT_EQ('1', buf[2]); 365 ASSERT_EQ('2', buf[3]); 366 ASSERT_EQ('3', buf[4]); 367 ASSERT_EQ('4', buf[5]); 368 ASSERT_EQ('5', buf[6]); 369 ASSERT_EQ('6', buf[7]); 370 ASSERT_EQ('7', buf[8]); 371 ASSERT_EQ('\0', buf[9]); 372 } 373 374 TEST(string, strchr_with_0) { 375 char buf[10]; 376 const char* s = "01234"; 377 memcpy(buf, s, strlen(s) + 1); 378 EXPECT_TRUE(strchr(buf, '\0') == (buf + strlen(s))); 379 } 380 381 TEST(string, strchr) { 382 int seek_char = random() & 255; 383 384 StringTestState<char> state(SMALL); 385 for (size_t i = 1; i < state.n; i++) { 386 for (size_t j = 0; j < POS_ITER; j++) { 387 state.NewIteration(); 388 389 if (~seek_char > 0) { 390 memset(state.ptr1, ~seek_char, state.len[i]); 391 } else { 392 memset(state.ptr1, '\1', state.len[i]); 393 } 394 state.ptr1[state.len[i] - 1] = '\0'; 395 396 int pos = random() % state.MAX_LEN; 397 char* expected; 398 if (pos >= state.len[i] - 1) { 399 if (seek_char == 0) { 400 expected = state.ptr1 + state.len[i] - 1; 401 } else { 402 expected = NULL; 403 } 404 } else { 405 state.ptr1[pos] = seek_char; 406 expected = state.ptr1 + pos; 407 } 408 409 ASSERT_TRUE(strchr(state.ptr1, seek_char) == expected); 410 } 411 } 412 } 413 414 TEST(string, strcmp) { 415 StringTestState<char> state(SMALL); 416 for (size_t i = 1; i < state.n; i++) { 417 for (size_t j = 0; j < POS_ITER; j++) { 418 state.NewIteration(); 419 420 memset(state.ptr1, 'v', state.MAX_LEN); 421 memset(state.ptr2, 'n', state.MAX_LEN); 422 state.ptr1[state.len[i] - 1] = '\0'; 423 state.ptr2[state.len[i] - 1] = '\0'; 424 425 int pos = 1 + (random() % (state.MAX_LEN - 1)); 426 int actual; 427 int expected; 428 if (pos >= state.len[i] - 1) { 429 memcpy(state.ptr1, state.ptr2, state.len[i]); 430 expected = 0; 431 actual = strcmp(state.ptr1, state.ptr2); 432 } else { 433 memcpy(state.ptr1, state.ptr2, pos); 434 if (state.ptr1[pos] > state.ptr2[pos]) { 435 expected = 1; 436 } else if (state.ptr1[pos] == state.ptr2[pos]) { 437 state.ptr1[pos + 1] = '\0'; 438 state.ptr2[pos + 1] = '\0'; 439 expected = 0; 440 } else { 441 expected = -1; 442 } 443 actual = strcmp(state.ptr1, state.ptr2); 444 } 445 446 ASSERT_EQ(expected, signum(actual)); 447 } 448 } 449 } 450 451 TEST(string, strcpy) { 452 StringTestState<char> state(SMALL); 453 for (size_t j = 0; j < POS_ITER; j++) { 454 state.NewIteration(); 455 456 size_t pos = random() % state.MAX_LEN; 457 458 memset(state.ptr1, '\2', pos); 459 state.ptr1[pos] = '\0'; 460 state.ptr1[state.MAX_LEN - 1] = '\0'; 461 462 memcpy(state.ptr, state.ptr1, state.MAX_LEN); 463 464 memset(state.ptr2, '\1', state.MAX_LEN); 465 state.ptr2[state.MAX_LEN - 1] = '\0'; 466 467 memset(state.ptr + state.MAX_LEN, '\1', state.MAX_LEN); 468 memcpy(state.ptr + state.MAX_LEN, state.ptr1, pos + 1); 469 state.ptr[2 * state.MAX_LEN - 1] = '\0'; 470 471 ASSERT_TRUE(strcpy(state.ptr2, state.ptr1) == state.ptr2); 472 ASSERT_FALSE((memcmp(state.ptr1, state.ptr, state.MAX_LEN)) != 0 || 473 (memcmp(state.ptr2, state.ptr + state.MAX_LEN, state.MAX_LEN) != 0)); 474 } 475 } 476 477 478 #if __BIONIC__ 479 TEST(string, strlcat) { 480 StringTestState<char> state(SMALL); 481 for (size_t i = 0; i < state.n; i++) { 482 for (size_t j = 0; j < POS_ITER; j++) { 483 state.NewIteration(); 484 485 memset(state.ptr2, '\2', state.MAX_LEN + state.len[i]); 486 state.ptr2[state.MAX_LEN - 1] = '\0'; 487 memcpy(state.ptr, state.ptr2, state.MAX_LEN + state.len[i]); 488 489 int pos = random() % state.MAX_LEN; 490 memset(state.ptr1, '\3', pos); 491 state.ptr1[pos] = '\0'; 492 if (pos < state.len[i]) { 493 memcpy(state.ptr + state.MAX_LEN - 1, state.ptr1, pos + 1); 494 } else { 495 memcpy(state.ptr + state.MAX_LEN - 1, state.ptr1, state.len[i]); 496 state.ptr[state.MAX_LEN + state.len[i] - 1] = '\0'; 497 } 498 499 strlcat(state.ptr2, state.ptr1, state.MAX_LEN + state.len[i]); 500 501 ASSERT_TRUE(memcmp(state.ptr, state.ptr2, state.MAX_LEN + state.len[i]) == 0); 502 } 503 } 504 } 505 #endif 506 507 #if __BIONIC__ 508 TEST(string, strlcpy) { 509 StringTestState<char> state(SMALL); 510 for (size_t j = 0; j < POS_ITER; j++) { 511 state.NewIteration(); 512 513 int rand = random() & 255; 514 if (rand < 1) { 515 rand = 1; 516 } 517 memset(state.ptr1, rand, state.MAX_LEN); 518 519 size_t pos = random() % state.MAX_LEN; 520 if (pos < state.MAX_LEN) { 521 state.ptr1[pos] = '\0'; 522 } 523 memcpy(state.ptr, state.ptr1, state.MAX_LEN); 524 525 memset(state.ptr2, random() & 255, state.MAX_LEN); 526 memcpy(state.ptr + state.MAX_LEN, state.ptr2, state.MAX_LEN); 527 528 if (pos > state.MAX_LEN - 1) { 529 memcpy(state.ptr + state.MAX_LEN, state.ptr1, state.MAX_LEN); 530 state.ptr[2 * state.MAX_LEN - 1] = '\0'; 531 } else { 532 memcpy(state.ptr + state.MAX_LEN, state.ptr1, pos + 1); 533 } 534 535 ASSERT_EQ(strlcpy(state.ptr2, state.ptr1, state.MAX_LEN), strlen(state.ptr1)); 536 ASSERT_FALSE((memcmp(state.ptr1, state.ptr, state.MAX_LEN) != 0) || 537 (memcmp(state.ptr2, state.ptr + state.MAX_LEN, state.MAX_LEN) != 0)); 538 } 539 } 540 #endif 541 542 TEST(string, strncat) { 543 StringTestState<char> state(SMALL); 544 for (size_t i = 1; i < state.n; i++) { 545 for (size_t j = 0; j < POS_ITER; j++) { 546 state.NewIteration(); 547 548 memset(state.ptr2, '\2', state.MAX_LEN); 549 state.ptr2[state.MAX_LEN - 1] = '\0'; 550 memcpy(state.ptr, state.ptr2, 2 * state.MAX_LEN); 551 552 memset(state.ptr1, random() & 255, state.len[i]); 553 state.ptr1[random() % state.len[i]] = '\0'; 554 state.ptr1[state.len[i] - 1] = '\0'; 555 556 size_t pos = strlen(state.ptr1); 557 558 size_t actual = random() % state.len[i]; 559 strncpy(state.ptr + state.MAX_LEN - 1, state.ptr1, std::min(actual, pos)); 560 state.ptr[state.MAX_LEN + std::min(actual, pos) - 1] = '\0'; 561 562 ASSERT_TRUE(strncat(state.ptr2, state.ptr1, actual) == state.ptr2); 563 ASSERT_EQ(memcmp(state.ptr, state.ptr2, 2 * state.MAX_LEN), 0); 564 } 565 } 566 } 567 568 TEST(string, strncmp) { 569 StringTestState<char> state(SMALL); 570 for (size_t i = 1; i < state.n; i++) { 571 for (size_t j = 0; j < POS_ITER; j++) { 572 state.NewIteration(); 573 574 memset(state.ptr1, 'v', state.MAX_LEN); 575 memset(state.ptr2, 'n', state.MAX_LEN); 576 state.ptr1[state.len[i] - 1] = '\0'; 577 state.ptr2[state.len[i] - 1] = '\0'; 578 579 int pos = 1 + (random() % (state.MAX_LEN - 1)); 580 int actual; 581 int expected; 582 if (pos >= state.len[i] - 1) { 583 memcpy(state.ptr1, state.ptr2, state.len[i]); 584 expected = 0; 585 actual = strncmp(state.ptr1, state.ptr2, state.len[i]); 586 } else { 587 memcpy(state.ptr1, state.ptr2, pos); 588 if (state.ptr1[pos] > state.ptr2[pos]) { 589 expected = 1; 590 } else if (state.ptr1[pos] == state.ptr2[pos]) { 591 state.ptr1[pos + 1] = '\0'; 592 state.ptr2[pos + 1] = '\0'; 593 expected = 0; 594 } else { 595 expected = -1; 596 } 597 actual = strncmp(state.ptr1, state.ptr2, state.len[i]); 598 } 599 600 ASSERT_EQ(expected, signum(actual)); 601 } 602 } 603 } 604 605 TEST(string, strncpy) { 606 StringTestState<char> state(SMALL); 607 for (size_t j = 0; j < ITER; j++) { 608 state.NewIteration(); 609 610 memset(state.ptr1, random() & 255, state.MAX_LEN); 611 state.ptr1[random () % state.MAX_LEN] = '\0'; 612 memcpy(state.ptr, state.ptr1, state.MAX_LEN); 613 614 memset(state.ptr2, '\1', state.MAX_LEN); 615 616 size_t pos; 617 if (memchr(state.ptr1, 0, state.MAX_LEN)) { 618 pos = strlen(state.ptr1); 619 } else { 620 pos = state.MAX_LEN - 1; 621 } 622 623 memset(state.ptr + state.MAX_LEN, '\0', state.MAX_LEN); 624 memcpy(state.ptr + state.MAX_LEN, state.ptr1, pos + 1); 625 626 ASSERT_TRUE(strncpy(state.ptr2, state.ptr1, state.MAX_LEN) == state.ptr2); 627 ASSERT_FALSE(memcmp(state.ptr1, state.ptr, state.MAX_LEN) != 0 || 628 memcmp(state.ptr2, state.ptr + state.MAX_LEN, state.MAX_LEN) != 0); 629 } 630 } 631 632 TEST(string, strrchr) { 633 int seek_char = random() & 255; 634 StringTestState<char> state(SMALL); 635 for (size_t i = 1; i < state.n; i++) { 636 for (size_t j = 0; j < POS_ITER; j++) { 637 state.NewIteration(); 638 639 if (~seek_char > 0) { 640 memset(state.ptr1, ~seek_char, state.len[i]); 641 } else { 642 memset(state.ptr1, '\1', state.len[i]); 643 } 644 state.ptr1[state.len[i] - 1] = '\0'; 645 646 int pos = random() % state.MAX_LEN; 647 char* expected; 648 if (pos >= state.len[i] - 1) { 649 if (seek_char == 0) { 650 expected = state.ptr1 + state.len[i] - 1; 651 } else { 652 expected = NULL; 653 } 654 } else { 655 state.ptr1[pos] = seek_char; 656 expected = state.ptr1 + pos; 657 } 658 659 ASSERT_TRUE(strrchr(state.ptr1, seek_char) == expected); 660 } 661 } 662 } 663 664 TEST(string, memchr) { 665 int seek_char = random() & 255; 666 StringTestState<char> state(SMALL); 667 for (size_t i = 0; i < state.n; i++) { 668 for (size_t j = 0; j < POS_ITER; j++) { 669 state.NewIteration(); 670 671 memset(state.ptr1, ~seek_char, state.len[i]); 672 673 int pos = random() % state.MAX_LEN; 674 char* expected; 675 if (pos >= state.len[i]) { 676 expected = NULL; 677 } else { 678 state.ptr1[pos] = seek_char; 679 expected = state.ptr1 + pos; 680 } 681 682 ASSERT_TRUE(memchr(state.ptr1, seek_char, state.len[i]) == expected); 683 } 684 } 685 } 686 687 TEST(string, memrchr) { 688 int seek_char = random() & 255; 689 StringTestState<char> state(SMALL); 690 for (size_t i = 0; i < state.n; i++) { 691 for (size_t j = 0; j < POS_ITER; j++) { 692 state.NewIteration(); 693 694 memset(state.ptr1, ~seek_char, state.len[i]); 695 696 int pos = random() % state.MAX_LEN; 697 char* expected; 698 if (pos >= state.len[i]) { 699 expected = NULL; 700 } else { 701 state.ptr1[pos] = seek_char; 702 expected = state.ptr1 + pos; 703 } 704 705 ASSERT_TRUE(memrchr(state.ptr1, seek_char, state.len[i]) == expected); 706 } 707 } 708 } 709 710 TEST(string, memcmp) { 711 StringTestState<char> state(SMALL); 712 for (size_t i = 0; i < state.n; i++) { 713 for (size_t j = 0; j < POS_ITER; j++) { 714 state.NewIteration(); 715 716 int c1 = random() & 0xff; 717 int c2 = random() & 0xff; 718 memset(state.ptr1, c1, state.MAX_LEN); 719 memset(state.ptr2, c1, state.MAX_LEN); 720 721 int pos = (state.len[i] == 0) ? 0 : (random() % state.len[i]); 722 state.ptr2[pos] = c2; 723 724 int expected = (static_cast<int>(c1) - static_cast<int>(c2)); 725 int actual = memcmp(state.ptr1, state.ptr2, state.MAX_LEN); 726 727 ASSERT_EQ(signum(expected), signum(actual)); 728 } 729 } 730 } 731 732 #if defined(__BIONIC__) 733 extern "C" int __memcmp16(const unsigned short *ptr1, const unsigned short *ptr2, size_t n); 734 735 TEST(string, __memcmp16) { 736 StringTestState<unsigned short> state(SMALL); 737 738 for (size_t i = 0; i < state.n; i++) { 739 for (size_t j = 0; j < POS_ITER; j++) { 740 state.NewIteration(); 741 742 unsigned short mask = 0xffff; 743 unsigned short c1 = rand() & mask; 744 unsigned short c2 = rand() & mask; 745 746 std::fill(state.ptr1, state.ptr1 + state.MAX_LEN, c1); 747 std::fill(state.ptr2, state.ptr2 + state.MAX_LEN, c1); 748 749 int pos = (state.len[i] == 0) ? 0 : (random() % state.len[i]); 750 state.ptr2[pos] = c2; 751 752 int expected = (static_cast<unsigned short>(c1) - static_cast<unsigned short>(c2)); 753 int actual = __memcmp16(state.ptr1, state.ptr2, (size_t) state.MAX_LEN); 754 755 ASSERT_EQ(expected, actual); 756 } 757 } 758 } 759 #endif 760 761 TEST(string, wmemcmp) { 762 StringTestState<wchar_t> state(SMALL); 763 764 for (size_t i = 0; i < state.n; i++) { 765 for (size_t j = 0; j < POS_ITER; j++) { 766 state.NewIteration(); 767 768 long long mask = ((long long) 1 << 8 * sizeof(wchar_t)) - 1; 769 int c1 = rand() & mask; 770 int c2 = rand() & mask; 771 wmemset(state.ptr1, c1, state.MAX_LEN); 772 wmemset(state.ptr2, c1, state.MAX_LEN); 773 774 int pos = (state.len[i] == 0) ? 0 : (random() % state.len[i]); 775 state.ptr2[pos] = c2; 776 777 int expected = (static_cast<int>(c1) - static_cast<int>(c2)); 778 int actual = wmemcmp(state.ptr1, state.ptr2, (size_t) state.MAX_LEN); 779 780 ASSERT_EQ(signum(expected), signum(actual)); 781 } 782 } 783 } 784 785 TEST(string, memcpy) { 786 StringTestState<char> state(LARGE); 787 int rand = random() & 255; 788 for (size_t i = 0; i < state.n - 1; i++) { 789 for (size_t j = 0; j < POS_ITER; j++) { 790 state.NewIteration(); 791 792 size_t pos = random() % (state.MAX_LEN - state.len[i]); 793 794 memset(state.ptr1, rand, state.len[i]); 795 memset(state.ptr1 + state.len[i], ~rand, state.MAX_LEN - state.len[i]); 796 797 memset(state.ptr2, rand, state.len[i]); 798 memset(state.ptr2 + state.len[i], ~rand, state.MAX_LEN - state.len[i]); 799 memset(state.ptr2 + pos, '\0', state.len[i]); 800 801 ASSERT_FALSE(memcpy(state.ptr2 + pos, state.ptr1 + pos, state.len[i]) != state.ptr2 + pos); 802 ASSERT_EQ(0, memcmp(state.ptr1, state.ptr2, state.MAX_LEN)); 803 } 804 } 805 } 806 807 TEST(string, memset) { 808 StringTestState<char> state(LARGE); 809 char ch = random () & 255; 810 for (size_t i = 0; i < state.n - 1; i++) { 811 for (size_t j = 0; j < POS_ITER; j++) { 812 state.NewIteration(); 813 814 memset(state.ptr1, ~ch, state.MAX_LEN); 815 memcpy(state.ptr2, state.ptr1, state.MAX_LEN); 816 817 size_t pos = random () % (state.MAX_LEN - state.len[i]); 818 for (size_t k = pos; k < pos + state.len[i]; k++) { 819 state.ptr1[k] = ch; 820 } 821 822 ASSERT_TRUE(memset(state.ptr2 + pos, ch, state.len[i]) == state.ptr2 + pos); 823 824 ASSERT_EQ(0, memcmp(state.ptr1, state.ptr2, state.MAX_LEN)); 825 } 826 } 827 } 828 829 TEST(string, memmove) { 830 StringTestState<char> state(LARGE); 831 for (size_t i = 0; i < state.n - 1; i++) { 832 for (size_t j = 0; j < POS_ITER; j++) { 833 state.NewIteration(); 834 835 memset(state.ptr1, random() & 255, 2 * state.MAX_LEN); 836 837 size_t pos = random() % (state.MAX_LEN - state.len[i]); 838 839 memset(state.ptr1, random() & 255, state.len[i]); 840 memcpy(state.ptr2, state.ptr1, 2 * state.MAX_LEN); 841 memcpy(state.ptr, state.ptr1, state.len[i]); 842 memcpy(state.ptr1 + pos, state.ptr, state.len[i]); 843 844 ASSERT_TRUE(memmove(state.ptr2 + pos, state.ptr2, state.len[i]) == state.ptr2 + pos); 845 ASSERT_EQ(0, memcmp(state.ptr2, state.ptr1, 2 * state.MAX_LEN)); 846 } 847 } 848 } 849 850 TEST(string, bcopy) { 851 StringTestState<char> state(LARGE); 852 for (size_t i = 0; i < state.n; i++) { 853 for (size_t j = 0; j < POS_ITER; j++) { 854 state.NewIteration(); 855 856 memset(state.ptr1, random() & 255, state.MAX_LEN); 857 memset(state.ptr1 + state.MAX_LEN, random() & 255, state.MAX_LEN); 858 memcpy(state.ptr2, state.ptr1, 2 * state.MAX_LEN); 859 860 size_t start = random() % (2 * state.MAX_LEN - state.len[i]); 861 memcpy(state.ptr2 + start, state.ptr1, state.len[i]); 862 863 bcopy(state.ptr1, state.ptr1 + start, state.len[i]); 864 ASSERT_EQ(0, memcmp(state.ptr1, state.ptr2, 2 * state.MAX_LEN)); 865 } 866 } 867 } 868 869 TEST(string, bzero) { 870 StringTestState<char> state(LARGE); 871 for (size_t j = 0; j < ITER; j++) { 872 state.NewIteration(); 873 874 memset(state.ptr1, random() & 255, state.MAX_LEN); 875 876 size_t start = random() % state.MAX_LEN; 877 size_t end = start + random() % (state.MAX_LEN - start); 878 879 memcpy(state.ptr2, state.ptr1, start); 880 memset(state.ptr2 + start, '\0', end - start); 881 memcpy(state.ptr2 + end, state.ptr1 + end, state.MAX_LEN - end); 882 883 bzero(state.ptr1 + start, end - start); 884 885 ASSERT_EQ(0, memcmp(state.ptr1, state.ptr2, state.MAX_LEN)); 886 } 887 } 888