1 //=-- asan_str_test.cc ----------------------------------------------------===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file is a part of AddressSanitizer, an address sanity checker. 11 // 12 //===----------------------------------------------------------------------===// 13 #include "asan_test_utils.h" 14 15 #if defined(__APPLE__) 16 #include <AvailabilityMacros.h> // For MAC_OS_X_VERSION_* 17 #endif 18 19 // Used for string functions tests 20 static char global_string[] = "global"; 21 static size_t global_string_length = 6; 22 23 const char kStackReadUnderflow[] = 24 #if !GTEST_USES_SIMPLE_RE 25 ASAN_PCRE_DOTALL 26 "READ.*" 27 #endif 28 "underflows this variable"; 29 const char kStackReadOverflow[] = 30 #if !GTEST_USES_SIMPLE_RE 31 ASAN_PCRE_DOTALL 32 "READ.*" 33 #endif 34 "overflows this variable"; 35 36 namespace { 37 enum class OOBKind { 38 Heap, 39 Stack, 40 Global, 41 }; 42 43 string LeftOOBReadMessage(OOBKind oob_kind, int oob_distance) { 44 return oob_kind == OOBKind::Stack ? kStackReadUnderflow 45 : ::LeftOOBReadMessage(oob_distance); 46 } 47 48 string RightOOBReadMessage(OOBKind oob_kind, int oob_distance) { 49 return oob_kind == OOBKind::Stack ? kStackReadOverflow 50 : ::RightOOBReadMessage(oob_distance); 51 } 52 } // namespace 53 54 // Input to a test is a zero-terminated string str with given length 55 // Accesses to the bytes to the left and to the right of str 56 // are presumed to produce OOB errors 57 void StrLenOOBTestTemplate(char *str, size_t length, OOBKind oob_kind) { 58 // Normal strlen calls 59 EXPECT_EQ(strlen(str), length); 60 if (length > 0) { 61 EXPECT_EQ(length - 1, strlen(str + 1)); 62 EXPECT_EQ(0U, strlen(str + length)); 63 } 64 // Arg of strlen is not malloced, OOB access 65 if (oob_kind != OOBKind::Global) { 66 // We don't insert RedZones to the left of global variables 67 EXPECT_DEATH(Ident(strlen(str - 1)), LeftOOBReadMessage(oob_kind, 1)); 68 EXPECT_DEATH(Ident(strlen(str - 5)), LeftOOBReadMessage(oob_kind, 5)); 69 } 70 EXPECT_DEATH(Ident(strlen(str + length + 1)), 71 RightOOBReadMessage(oob_kind, 0)); 72 // Overwrite terminator 73 str[length] = 'a'; 74 // String is not zero-terminated, strlen will lead to OOB access 75 EXPECT_DEATH(Ident(strlen(str)), RightOOBReadMessage(oob_kind, 0)); 76 EXPECT_DEATH(Ident(strlen(str + length)), RightOOBReadMessage(oob_kind, 0)); 77 // Restore terminator 78 str[length] = 0; 79 } 80 TEST(AddressSanitizer, StrLenOOBTest) { 81 // Check heap-allocated string 82 size_t length = Ident(10); 83 char *heap_string = Ident((char*)malloc(length + 1)); 84 char stack_string[10 + 1]; 85 break_optimization(&stack_string); 86 for (size_t i = 0; i < length; i++) { 87 heap_string[i] = 'a'; 88 stack_string[i] = 'b'; 89 } 90 heap_string[length] = 0; 91 stack_string[length] = 0; 92 StrLenOOBTestTemplate(heap_string, length, OOBKind::Heap); 93 StrLenOOBTestTemplate(stack_string, length, OOBKind::Stack); 94 StrLenOOBTestTemplate(global_string, global_string_length, OOBKind::Global); 95 free(heap_string); 96 } 97 98 // 32-bit android libc++-based NDK toolchain links wcslen statically, disabling 99 // the interceptor. 100 #if !defined(__ANDROID__) || defined(__LP64__) 101 TEST(AddressSanitizer, WcsLenTest) { 102 EXPECT_EQ(0U, wcslen(Ident(L""))); 103 size_t hello_len = 13; 104 size_t hello_size = (hello_len + 1) * sizeof(wchar_t); 105 EXPECT_EQ(hello_len, wcslen(Ident(L"Hello, World!"))); 106 wchar_t *heap_string = Ident((wchar_t*)malloc(hello_size)); 107 memcpy(heap_string, L"Hello, World!", hello_size); 108 EXPECT_EQ(hello_len, Ident(wcslen(heap_string))); 109 EXPECT_DEATH(Ident(wcslen(heap_string + 14)), RightOOBReadMessage(0)); 110 free(heap_string); 111 } 112 #endif 113 114 #if SANITIZER_TEST_HAS_STRNLEN 115 TEST(AddressSanitizer, StrNLenOOBTest) { 116 size_t size = Ident(123); 117 char *str = MallocAndMemsetString(size); 118 // Normal strnlen calls. 119 Ident(strnlen(str - 1, 0)); 120 Ident(strnlen(str, size)); 121 Ident(strnlen(str + size - 1, 1)); 122 str[size - 1] = '\0'; 123 Ident(strnlen(str, 2 * size)); 124 // Argument points to not allocated memory. 125 EXPECT_DEATH(Ident(strnlen(str - 1, 1)), LeftOOBReadMessage(1)); 126 EXPECT_DEATH(Ident(strnlen(str + size, 1)), RightOOBReadMessage(0)); 127 // Overwrite the terminating '\0' and hit unallocated memory. 128 str[size - 1] = 'z'; 129 EXPECT_DEATH(Ident(strnlen(str, size + 1)), RightOOBReadMessage(0)); 130 free(str); 131 } 132 #endif // SANITIZER_TEST_HAS_STRNLEN 133 134 // This test fails with the WinASan dynamic runtime because we fail to intercept 135 // strdup. 136 #if defined(_MSC_VER) && defined(_DLL) 137 #define MAYBE_StrDupOOBTest DISABLED_StrDupOOBTest 138 #else 139 #define MAYBE_StrDupOOBTest StrDupOOBTest 140 #endif 141 142 TEST(AddressSanitizer, MAYBE_StrDupOOBTest) { 143 size_t size = Ident(42); 144 char *str = MallocAndMemsetString(size); 145 char *new_str; 146 // Normal strdup calls. 147 str[size - 1] = '\0'; 148 new_str = strdup(str); 149 free(new_str); 150 new_str = strdup(str + size - 1); 151 free(new_str); 152 // Argument points to not allocated memory. 153 EXPECT_DEATH(Ident(strdup(str - 1)), LeftOOBReadMessage(1)); 154 EXPECT_DEATH(Ident(strdup(str + size)), RightOOBReadMessage(0)); 155 // Overwrite the terminating '\0' and hit unallocated memory. 156 str[size - 1] = 'z'; 157 EXPECT_DEATH(Ident(strdup(str)), RightOOBReadMessage(0)); 158 free(str); 159 } 160 161 #if SANITIZER_TEST_HAS_STRNDUP 162 TEST(AddressSanitizer, MAYBE_StrNDupOOBTest) { 163 size_t size = Ident(42); 164 char *str = MallocAndMemsetString(size); 165 char *new_str; 166 // Normal strndup calls. 167 str[size - 1] = '\0'; 168 new_str = strndup(str, size - 13); 169 free(new_str); 170 new_str = strndup(str + size - 1, 13); 171 free(new_str); 172 // Argument points to not allocated memory. 173 EXPECT_DEATH(Ident(strndup(str - 1, 13)), LeftOOBReadMessage(1)); 174 EXPECT_DEATH(Ident(strndup(str + size, 13)), RightOOBReadMessage(0)); 175 // Overwrite the terminating '\0' and hit unallocated memory. 176 str[size - 1] = 'z'; 177 EXPECT_DEATH(Ident(strndup(str, size + 13)), RightOOBReadMessage(0)); 178 // Check handling of non 0 terminated strings. 179 Ident(new_str = strndup(str + size - 1, 0)); 180 free(new_str); 181 Ident(new_str = strndup(str + size - 1, 1)); 182 free(new_str); 183 EXPECT_DEATH(Ident(strndup(str + size - 1, 2)), RightOOBReadMessage(0)); 184 free(str); 185 } 186 #endif // SANITIZER_TEST_HAS_STRNDUP 187 188 TEST(AddressSanitizer, StrCpyOOBTest) { 189 size_t to_size = Ident(30); 190 size_t from_size = Ident(6); // less than to_size 191 char *to = Ident((char*)malloc(to_size)); 192 char *from = Ident((char*)malloc(from_size)); 193 // Normal strcpy calls. 194 strcpy(from, "hello"); 195 strcpy(to, from); 196 strcpy(to + to_size - from_size, from); 197 // Length of "from" is too small. 198 EXPECT_DEATH(Ident(strcpy(from, "hello2")), RightOOBWriteMessage(0)); 199 // "to" or "from" points to not allocated memory. 200 EXPECT_DEATH(Ident(strcpy(to - 1, from)), LeftOOBWriteMessage(1)); 201 EXPECT_DEATH(Ident(strcpy(to, from - 1)), LeftOOBReadMessage(1)); 202 EXPECT_DEATH(Ident(strcpy(to, from + from_size)), RightOOBReadMessage(0)); 203 EXPECT_DEATH(Ident(strcpy(to + to_size, from)), RightOOBWriteMessage(0)); 204 // Overwrite the terminating '\0' character and hit unallocated memory. 205 from[from_size - 1] = '!'; 206 EXPECT_DEATH(Ident(strcpy(to, from)), RightOOBReadMessage(0)); 207 free(to); 208 free(from); 209 } 210 211 TEST(AddressSanitizer, StrNCpyOOBTest) { 212 size_t to_size = Ident(20); 213 size_t from_size = Ident(6); // less than to_size 214 char *to = Ident((char*)malloc(to_size)); 215 // From is a zero-terminated string "hello\0" of length 6 216 char *from = Ident((char*)malloc(from_size)); 217 strcpy(from, "hello"); 218 // copy 0 bytes 219 strncpy(to, from, 0); 220 strncpy(to - 1, from - 1, 0); 221 // normal strncpy calls 222 strncpy(to, from, from_size); 223 strncpy(to, from, to_size); 224 strncpy(to, from + from_size - 1, to_size); 225 strncpy(to + to_size - 1, from, 1); 226 // One of {to, from} points to not allocated memory 227 EXPECT_DEATH(Ident(strncpy(to, from - 1, from_size)), 228 LeftOOBReadMessage(1)); 229 EXPECT_DEATH(Ident(strncpy(to - 1, from, from_size)), 230 LeftOOBWriteMessage(1)); 231 EXPECT_DEATH(Ident(strncpy(to, from + from_size, 1)), 232 RightOOBReadMessage(0)); 233 EXPECT_DEATH(Ident(strncpy(to + to_size, from, 1)), 234 RightOOBWriteMessage(0)); 235 // Length of "to" is too small 236 EXPECT_DEATH(Ident(strncpy(to + to_size - from_size + 1, from, from_size)), 237 RightOOBWriteMessage(0)); 238 EXPECT_DEATH(Ident(strncpy(to + 1, from, to_size)), 239 RightOOBWriteMessage(0)); 240 // Overwrite terminator in from 241 from[from_size - 1] = '!'; 242 // normal strncpy call 243 strncpy(to, from, from_size); 244 // Length of "from" is too small 245 EXPECT_DEATH(Ident(strncpy(to, from, to_size)), 246 RightOOBReadMessage(0)); 247 free(to); 248 free(from); 249 } 250 251 // Users may have different definitions of "strchr" and "index", so provide 252 // function pointer typedefs and overload RunStrChrTest implementation. 253 // We can't use macro for RunStrChrTest body here, as this macro would 254 // confuse EXPECT_DEATH gtest macro. 255 typedef char*(*PointerToStrChr1)(const char*, int); 256 typedef char*(*PointerToStrChr2)(char*, int); 257 258 template<typename StrChrFn> 259 static void RunStrChrTestImpl(StrChrFn *StrChr) { 260 size_t size = Ident(100); 261 char *str = MallocAndMemsetString(size); 262 str[10] = 'q'; 263 str[11] = '\0'; 264 EXPECT_EQ(str, StrChr(str, 'z')); 265 EXPECT_EQ(str + 10, StrChr(str, 'q')); 266 EXPECT_EQ(NULL, StrChr(str, 'a')); 267 // StrChr argument points to not allocated memory. 268 EXPECT_DEATH(Ident(StrChr(str - 1, 'z')), LeftOOBReadMessage(1)); 269 EXPECT_DEATH(Ident(StrChr(str + size, 'z')), RightOOBReadMessage(0)); 270 // Overwrite the terminator and hit not allocated memory. 271 str[11] = 'z'; 272 EXPECT_DEATH(Ident(StrChr(str, 'a')), RightOOBReadMessage(0)); 273 free(str); 274 } 275 276 // Prefer to use the standard signature if both are available. 277 UNUSED static void RunStrChrTest(PointerToStrChr1 StrChr, ...) { 278 RunStrChrTestImpl(StrChr); 279 } 280 UNUSED static void RunStrChrTest(PointerToStrChr2 StrChr, int) { 281 RunStrChrTestImpl(StrChr); 282 } 283 284 TEST(AddressSanitizer, StrChrAndIndexOOBTest) { 285 RunStrChrTest(&strchr, 0); 286 // No index() on Windows and on Android L. 287 #if !defined(_WIN32) && !defined(__ANDROID__) 288 RunStrChrTest(&index, 0); 289 #endif 290 } 291 292 TEST(AddressSanitizer, StrCmpAndFriendsLogicTest) { 293 // strcmp 294 EXPECT_EQ(0, strcmp("", "")); 295 EXPECT_EQ(0, strcmp("abcd", "abcd")); 296 EXPECT_GT(0, strcmp("ab", "ac")); 297 EXPECT_GT(0, strcmp("abc", "abcd")); 298 EXPECT_LT(0, strcmp("acc", "abc")); 299 EXPECT_LT(0, strcmp("abcd", "abc")); 300 301 // strncmp 302 EXPECT_EQ(0, strncmp("a", "b", 0)); 303 EXPECT_EQ(0, strncmp("abcd", "abcd", 10)); 304 EXPECT_EQ(0, strncmp("abcd", "abcef", 3)); 305 EXPECT_GT(0, strncmp("abcde", "abcfa", 4)); 306 EXPECT_GT(0, strncmp("a", "b", 5)); 307 EXPECT_GT(0, strncmp("bc", "bcde", 4)); 308 EXPECT_LT(0, strncmp("xyz", "xyy", 10)); 309 EXPECT_LT(0, strncmp("baa", "aaa", 1)); 310 EXPECT_LT(0, strncmp("zyx", "", 2)); 311 312 #if !defined(_WIN32) // no str[n]casecmp on Windows. 313 // strcasecmp 314 EXPECT_EQ(0, strcasecmp("", "")); 315 EXPECT_EQ(0, strcasecmp("zzz", "zzz")); 316 EXPECT_EQ(0, strcasecmp("abCD", "ABcd")); 317 EXPECT_GT(0, strcasecmp("aB", "Ac")); 318 EXPECT_GT(0, strcasecmp("ABC", "ABCd")); 319 EXPECT_LT(0, strcasecmp("acc", "abc")); 320 EXPECT_LT(0, strcasecmp("ABCd", "abc")); 321 322 // strncasecmp 323 EXPECT_EQ(0, strncasecmp("a", "b", 0)); 324 EXPECT_EQ(0, strncasecmp("abCD", "ABcd", 10)); 325 EXPECT_EQ(0, strncasecmp("abCd", "ABcef", 3)); 326 EXPECT_GT(0, strncasecmp("abcde", "ABCfa", 4)); 327 EXPECT_GT(0, strncasecmp("a", "B", 5)); 328 EXPECT_GT(0, strncasecmp("bc", "BCde", 4)); 329 EXPECT_LT(0, strncasecmp("xyz", "xyy", 10)); 330 EXPECT_LT(0, strncasecmp("Baa", "aaa", 1)); 331 EXPECT_LT(0, strncasecmp("zyx", "", 2)); 332 #endif 333 334 // memcmp 335 EXPECT_EQ(0, memcmp("a", "b", 0)); 336 EXPECT_EQ(0, memcmp("ab\0c", "ab\0c", 4)); 337 EXPECT_GT(0, memcmp("\0ab", "\0ac", 3)); 338 EXPECT_GT(0, memcmp("abb\0", "abba", 4)); 339 EXPECT_LT(0, memcmp("ab\0cd", "ab\0c\0", 5)); 340 EXPECT_LT(0, memcmp("zza", "zyx", 3)); 341 } 342 343 typedef int(*PointerToStrCmp)(const char*, const char*); 344 void RunStrCmpTest(PointerToStrCmp StrCmp) { 345 size_t size = Ident(100); 346 int fill = 'o'; 347 char *s1 = MallocAndMemsetString(size, fill); 348 char *s2 = MallocAndMemsetString(size, fill); 349 s1[size - 1] = '\0'; 350 s2[size - 1] = '\0'; 351 // Normal StrCmp calls 352 Ident(StrCmp(s1, s2)); 353 Ident(StrCmp(s1, s2 + size - 1)); 354 Ident(StrCmp(s1 + size - 1, s2 + size - 1)); 355 // One of arguments points to not allocated memory. 356 EXPECT_DEATH(Ident(StrCmp)(s1 - 1, s2), LeftOOBReadMessage(1)); 357 EXPECT_DEATH(Ident(StrCmp)(s1, s2 - 1), LeftOOBReadMessage(1)); 358 EXPECT_DEATH(Ident(StrCmp)(s1 + size, s2), RightOOBReadMessage(0)); 359 EXPECT_DEATH(Ident(StrCmp)(s1, s2 + size), RightOOBReadMessage(0)); 360 // Hit unallocated memory and die. 361 s1[size - 1] = fill; 362 EXPECT_DEATH(Ident(StrCmp)(s1, s1), RightOOBReadMessage(0)); 363 EXPECT_DEATH(Ident(StrCmp)(s1 + size - 1, s2), RightOOBReadMessage(0)); 364 free(s1); 365 free(s2); 366 } 367 368 TEST(AddressSanitizer, StrCmpOOBTest) { 369 RunStrCmpTest(&strcmp); 370 } 371 372 #if !defined(_WIN32) // no str[n]casecmp on Windows. 373 TEST(AddressSanitizer, StrCaseCmpOOBTest) { 374 RunStrCmpTest(&strcasecmp); 375 } 376 #endif 377 378 typedef int(*PointerToStrNCmp)(const char*, const char*, size_t); 379 void RunStrNCmpTest(PointerToStrNCmp StrNCmp) { 380 size_t size = Ident(100); 381 char *s1 = MallocAndMemsetString(size); 382 char *s2 = MallocAndMemsetString(size); 383 s1[size - 1] = '\0'; 384 s2[size - 1] = '\0'; 385 // Normal StrNCmp calls 386 Ident(StrNCmp(s1, s2, size + 2)); 387 s1[size - 1] = 'z'; 388 s2[size - 1] = 'x'; 389 Ident(StrNCmp(s1 + size - 2, s2 + size - 2, size)); 390 s2[size - 1] = 'z'; 391 Ident(StrNCmp(s1 - 1, s2 - 1, 0)); 392 Ident(StrNCmp(s1 + size - 1, s2 + size - 1, 1)); 393 // One of arguments points to not allocated memory. 394 EXPECT_DEATH(Ident(StrNCmp)(s1 - 1, s2, 1), LeftOOBReadMessage(1)); 395 EXPECT_DEATH(Ident(StrNCmp)(s1, s2 - 1, 1), LeftOOBReadMessage(1)); 396 EXPECT_DEATH(Ident(StrNCmp)(s1 + size, s2, 1), RightOOBReadMessage(0)); 397 EXPECT_DEATH(Ident(StrNCmp)(s1, s2 + size, 1), RightOOBReadMessage(0)); 398 // Hit unallocated memory and die. 399 EXPECT_DEATH(Ident(StrNCmp)(s1 + 1, s2 + 1, size), RightOOBReadMessage(0)); 400 EXPECT_DEATH(Ident(StrNCmp)(s1 + size - 1, s2, 2), RightOOBReadMessage(0)); 401 free(s1); 402 free(s2); 403 } 404 405 TEST(AddressSanitizer, StrNCmpOOBTest) { 406 RunStrNCmpTest(&strncmp); 407 } 408 409 #if !defined(_WIN32) // no str[n]casecmp on Windows. 410 TEST(AddressSanitizer, StrNCaseCmpOOBTest) { 411 RunStrNCmpTest(&strncasecmp); 412 } 413 #endif 414 415 TEST(AddressSanitizer, StrCatOOBTest) { 416 // strcat() reads strlen(to) bytes from |to| before concatenating. 417 size_t to_size = Ident(100); 418 char *to = MallocAndMemsetString(to_size); 419 to[0] = '\0'; 420 size_t from_size = Ident(20); 421 char *from = MallocAndMemsetString(from_size); 422 from[from_size - 1] = '\0'; 423 // Normal strcat calls. 424 strcat(to, from); 425 strcat(to, from); 426 strcat(to + from_size, from + from_size - 2); 427 // Passing an invalid pointer is an error even when concatenating an empty 428 // string. 429 EXPECT_DEATH(strcat(to - 1, from + from_size - 1), LeftOOBAccessMessage(1)); 430 // One of arguments points to not allocated memory. 431 EXPECT_DEATH(strcat(to - 1, from), LeftOOBAccessMessage(1)); 432 EXPECT_DEATH(strcat(to, from - 1), LeftOOBReadMessage(1)); 433 EXPECT_DEATH(strcat(to, from + from_size), RightOOBReadMessage(0)); 434 435 // "from" is not zero-terminated. 436 from[from_size - 1] = 'z'; 437 EXPECT_DEATH(strcat(to, from), RightOOBReadMessage(0)); 438 from[from_size - 1] = '\0'; 439 // "to" is too short to fit "from". 440 memset(to, 'z', to_size); 441 to[to_size - from_size + 1] = '\0'; 442 EXPECT_DEATH(strcat(to, from), RightOOBWriteMessage(0)); 443 // length of "to" is just enough. 444 strcat(to, from + 1); 445 446 free(to); 447 free(from); 448 } 449 450 TEST(AddressSanitizer, StrNCatOOBTest) { 451 // strncat() reads strlen(to) bytes from |to| before concatenating. 452 size_t to_size = Ident(100); 453 char *to = MallocAndMemsetString(to_size); 454 to[0] = '\0'; 455 size_t from_size = Ident(20); 456 char *from = MallocAndMemsetString(from_size); 457 // Normal strncat calls. 458 strncat(to, from, 0); 459 strncat(to, from, from_size); 460 from[from_size - 1] = '\0'; 461 strncat(to, from, 2 * from_size); 462 // Catenating empty string with an invalid string is still an error. 463 EXPECT_DEATH(strncat(to - 1, from, 0), LeftOOBAccessMessage(1)); 464 strncat(to, from + from_size - 1, 10); 465 // One of arguments points to not allocated memory. 466 EXPECT_DEATH(strncat(to - 1, from, 2), LeftOOBAccessMessage(1)); 467 EXPECT_DEATH(strncat(to, from - 1, 2), LeftOOBReadMessage(1)); 468 EXPECT_DEATH(strncat(to, from + from_size, 2), RightOOBReadMessage(0)); 469 470 memset(from, 'z', from_size); 471 memset(to, 'z', to_size); 472 to[0] = '\0'; 473 // "from" is too short. 474 EXPECT_DEATH(strncat(to, from, from_size + 1), RightOOBReadMessage(0)); 475 // "to" is too short to fit "from". 476 to[0] = 'z'; 477 to[to_size - from_size + 1] = '\0'; 478 EXPECT_DEATH(strncat(to, from, from_size - 1), RightOOBWriteMessage(0)); 479 // "to" is just enough. 480 strncat(to, from, from_size - 2); 481 482 free(to); 483 free(from); 484 } 485 486 static string OverlapErrorMessage(const string &func) { 487 return func + "-param-overlap"; 488 } 489 490 TEST(AddressSanitizer, StrArgsOverlapTest) { 491 size_t size = Ident(100); 492 char *str = Ident((char*)malloc(size)); 493 494 // Do not check memcpy() on OS X 10.7 and later, where it actually aliases 495 // memmove(). 496 #if !defined(__APPLE__) || !defined(MAC_OS_X_VERSION_10_7) || \ 497 (MAC_OS_X_VERSION_MAX_ALLOWED < MAC_OS_X_VERSION_10_7) 498 // Check "memcpy". Use Ident() to avoid inlining. 499 #if PLATFORM_HAS_DIFFERENT_MEMCPY_AND_MEMMOVE 500 memset(str, 'z', size); 501 Ident(memcpy)(str + 1, str + 11, 10); 502 Ident(memcpy)(str, str, 0); 503 EXPECT_DEATH(Ident(memcpy)(str, str + 14, 15), OverlapErrorMessage("memcpy")); 504 EXPECT_DEATH(Ident(memcpy)(str + 14, str, 15), OverlapErrorMessage("memcpy")); 505 #endif 506 #endif 507 508 // We do not treat memcpy with to==from as a bug. 509 // See http://llvm.org/bugs/show_bug.cgi?id=11763. 510 // EXPECT_DEATH(Ident(memcpy)(str + 20, str + 20, 1), 511 // OverlapErrorMessage("memcpy")); 512 513 // Check "strcpy". 514 memset(str, 'z', size); 515 str[9] = '\0'; 516 strcpy(str + 10, str); 517 EXPECT_DEATH(strcpy(str + 9, str), OverlapErrorMessage("strcpy")); 518 EXPECT_DEATH(strcpy(str, str + 4), OverlapErrorMessage("strcpy")); 519 strcpy(str, str + 5); 520 521 // Check "strncpy". 522 memset(str, 'z', size); 523 strncpy(str, str + 10, 10); 524 EXPECT_DEATH(strncpy(str, str + 9, 10), OverlapErrorMessage("strncpy")); 525 EXPECT_DEATH(strncpy(str + 9, str, 10), OverlapErrorMessage("strncpy")); 526 str[10] = '\0'; 527 strncpy(str + 11, str, 20); 528 EXPECT_DEATH(strncpy(str + 10, str, 20), OverlapErrorMessage("strncpy")); 529 530 // Check "strcat". 531 memset(str, 'z', size); 532 str[10] = '\0'; 533 str[20] = '\0'; 534 strcat(str, str + 10); 535 EXPECT_DEATH(strcat(str, str + 11), OverlapErrorMessage("strcat")); 536 str[10] = '\0'; 537 strcat(str + 11, str); 538 EXPECT_DEATH(strcat(str, str + 9), OverlapErrorMessage("strcat")); 539 EXPECT_DEATH(strcat(str + 9, str), OverlapErrorMessage("strcat")); 540 EXPECT_DEATH(strcat(str + 10, str), OverlapErrorMessage("strcat")); 541 542 // Check "strncat". 543 memset(str, 'z', size); 544 str[10] = '\0'; 545 strncat(str, str + 10, 10); // from is empty 546 EXPECT_DEATH(strncat(str, str + 11, 10), OverlapErrorMessage("strncat")); 547 str[10] = '\0'; 548 str[20] = '\0'; 549 strncat(str + 5, str, 5); 550 str[10] = '\0'; 551 EXPECT_DEATH(strncat(str + 5, str, 6), OverlapErrorMessage("strncat")); 552 EXPECT_DEATH(strncat(str, str + 9, 10), OverlapErrorMessage("strncat")); 553 554 free(str); 555 } 556 557 typedef void(*PointerToCallAtoi)(const char*); 558 559 void RunAtoiOOBTest(PointerToCallAtoi Atoi) { 560 char *array = MallocAndMemsetString(10, '1'); 561 // Invalid pointer to the string. 562 EXPECT_DEATH(Atoi(array + 11), RightOOBReadMessage(1)); 563 EXPECT_DEATH(Atoi(array - 1), LeftOOBReadMessage(1)); 564 // Die if a buffer doesn't have terminating NULL. 565 EXPECT_DEATH(Atoi(array), RightOOBReadMessage(0)); 566 // Make last symbol a terminating NULL 567 array[9] = '\0'; 568 Atoi(array); 569 // Sometimes we need to detect overflow if no digits are found. 570 memset(array, ' ', 10); 571 EXPECT_DEATH(Atoi(array), RightOOBReadMessage(0)); 572 array[9] = '-'; 573 EXPECT_DEATH(Atoi(array), RightOOBReadMessage(0)); 574 EXPECT_DEATH(Atoi(array + 9), RightOOBReadMessage(0)); 575 free(array); 576 } 577 578 #if !defined(_WIN32) // FIXME: Fix and enable on Windows. 579 void CallAtoi(const char *nptr) { 580 Ident(atoi(nptr)); 581 } 582 void CallAtol(const char *nptr) { 583 Ident(atol(nptr)); 584 } 585 void CallAtoll(const char *nptr) { 586 Ident(atoll(nptr)); 587 } 588 TEST(AddressSanitizer, AtoiAndFriendsOOBTest) { 589 RunAtoiOOBTest(&CallAtoi); 590 RunAtoiOOBTest(&CallAtol); 591 RunAtoiOOBTest(&CallAtoll); 592 } 593 #endif 594 595 typedef void(*PointerToCallStrtol)(const char*, char**, int); 596 597 void RunStrtolOOBTest(PointerToCallStrtol Strtol) { 598 char *array = MallocAndMemsetString(3); 599 array[0] = '1'; 600 array[1] = '2'; 601 array[2] = '3'; 602 // Invalid pointer to the string. 603 EXPECT_DEATH(Strtol(array + 3, NULL, 0), RightOOBReadMessage(0)); 604 EXPECT_DEATH(Strtol(array - 1, NULL, 0), LeftOOBReadMessage(1)); 605 // Buffer overflow if there is no terminating null (depends on base). 606 EXPECT_DEATH(Strtol(array, NULL, 0), RightOOBReadMessage(0)); 607 array[2] = 'z'; 608 EXPECT_DEATH(Strtol(array, NULL, 36), RightOOBReadMessage(0)); 609 // Add terminating zero to get rid of overflow. 610 array[2] = '\0'; 611 Strtol(array, NULL, 36); 612 // Sometimes we need to detect overflow if no digits are found. 613 array[0] = array[1] = array[2] = ' '; 614 EXPECT_DEATH(Strtol(array, NULL, 0), RightOOBReadMessage(0)); 615 array[2] = '+'; 616 EXPECT_DEATH(Strtol(array, NULL, 0), RightOOBReadMessage(0)); 617 array[2] = '-'; 618 EXPECT_DEATH(Strtol(array, NULL, 0), RightOOBReadMessage(0)); 619 free(array); 620 } 621 622 #if !defined(_WIN32) // FIXME: Fix and enable on Windows. 623 void CallStrtol(const char *nptr, char **endptr, int base) { 624 Ident(strtol(nptr, endptr, base)); 625 } 626 void CallStrtoll(const char *nptr, char **endptr, int base) { 627 Ident(strtoll(nptr, endptr, base)); 628 } 629 TEST(AddressSanitizer, StrtollOOBTest) { 630 RunStrtolOOBTest(&CallStrtoll); 631 } 632 TEST(AddressSanitizer, StrtolOOBTest) { 633 RunStrtolOOBTest(&CallStrtol); 634 } 635 #endif 636