1 // RUN: %clang_cc1 -analyze -analyzer-checker=core,unix.experimental.CString,deadcode.experimental.UnreachableCode -analyzer-store=region -Wno-null-dereference -verify %s
2 // RUN: %clang_cc1 -analyze -DUSE_BUILTINS -analyzer-checker=core,unix.experimental.CString,deadcode.experimental.UnreachableCode -analyzer-store=region -Wno-null-dereference -verify %s
3 // RUN: %clang_cc1 -analyze -DVARIANT -analyzer-checker=core,unix.experimental.CString,deadcode.experimental.UnreachableCode -analyzer-store=region -Wno-null-dereference -verify %s
4 // RUN: %clang_cc1 -analyze -DUSE_BUILTINS -DVARIANT -analyzer-checker=core,unix.experimental.CString,deadcode.experimental.UnreachableCode -analyzer-store=region -Wno-null-dereference -verify %s
5
6 //===----------------------------------------------------------------------===
7 // Declarations
8 //===----------------------------------------------------------------------===
9
10 // Some functions are so similar to each other that they follow the same code
11 // path, such as memcpy and __memcpy_chk, or memcmp and bcmp. If VARIANT is
12 // defined, make sure to use the variants instead to make sure they are still
13 // checked by the analyzer.
14
15 // Some functions are implemented as builtins. These should be #defined as
16 // BUILTIN(f), which will prepend "__builtin_" if USE_BUILTINS is defined.
17
18 // Functions that have variants and are also available as builtins should be
19 // declared carefully! See memcpy() for an example.
20
21 #ifdef USE_BUILTINS
22 # define BUILTIN(f) __builtin_ ## f
23 #else /* USE_BUILTINS */
24 # define BUILTIN(f) f
25 #endif /* USE_BUILTINS */
26
27 #define NULL 0
28 typedef typeof(sizeof(int)) size_t;
29
30 //===----------------------------------------------------------------------===
31 // strlen()
32 //===----------------------------------------------------------------------===
33
34 #define strlen BUILTIN(strlen)
35 size_t strlen(const char *s);
36
strlen_constant0()37 void strlen_constant0() {
38 if (strlen("123") != 3)
39 (void)*(char*)0; // no-warning
40 }
41
strlen_constant1()42 void strlen_constant1() {
43 const char *a = "123";
44 if (strlen(a) != 3)
45 (void)*(char*)0; // no-warning
46 }
47
strlen_constant2(char x)48 void strlen_constant2(char x) {
49 char a[] = "123";
50 if (strlen(a) != 3)
51 (void)*(char*)0; // no-warning
52 a[0] = x;
53 if (strlen(a) != 3)
54 (void)*(char*)0; // expected-warning{{null}}
55 }
56
strlen_null()57 size_t strlen_null() {
58 return strlen(0); // expected-warning{{Null pointer argument in call to string length function}}
59 }
60
strlen_fn()61 size_t strlen_fn() {
62 return strlen((char*)&strlen_fn); // expected-warning{{Argument to string length function is the address of the function 'strlen_fn', which is not a null-terminated string}}
63 }
64
strlen_nonloc()65 size_t strlen_nonloc() {
66 label:
67 return strlen((char*)&&label); // expected-warning{{Argument to string length function is the address of the label 'label', which is not a null-terminated string}}
68 }
69
strlen_subregion()70 void strlen_subregion() {
71 struct two_strings { char a[2], b[2]; };
72 extern void use_two_strings(struct two_strings *);
73
74 struct two_strings z;
75 use_two_strings(&z);
76
77 size_t a = strlen(z.a);
78 z.b[0] = 5;
79 size_t b = strlen(z.a);
80 if (a == 0 && b != 0)
81 (void)*(char*)0; // expected-warning{{never executed}}
82
83 use_two_strings(&z);
84
85 size_t c = strlen(z.a);
86 if (a == 0 && c != 0)
87 (void)*(char*)0; // expected-warning{{null}}
88 }
89
90 extern void use_string(char *);
strlen_argument(char * x)91 void strlen_argument(char *x) {
92 size_t a = strlen(x);
93 size_t b = strlen(x);
94 if (a == 0 && b != 0)
95 (void)*(char*)0; // expected-warning{{never executed}}
96
97 use_string(x);
98
99 size_t c = strlen(x);
100 if (a == 0 && c != 0)
101 (void)*(char*)0; // expected-warning{{null}}
102 }
103
104 extern char global_str[];
strlen_global()105 void strlen_global() {
106 size_t a = strlen(global_str);
107 size_t b = strlen(global_str);
108 if (a == 0 && b != 0)
109 (void)*(char*)0; // expected-warning{{never executed}}
110
111 // Call a function with unknown effects, which should invalidate globals.
112 use_string(0);
113
114 size_t c = strlen(global_str);
115 if (a == 0 && c != 0)
116 (void)*(char*)0; // expected-warning{{null}}
117 }
118
strlen_indirect(char * x)119 void strlen_indirect(char *x) {
120 size_t a = strlen(x);
121 char *p = x;
122 char **p2 = &p;
123 size_t b = strlen(x);
124 if (a == 0 && b != 0)
125 (void)*(char*)0; // expected-warning{{never executed}}
126
127 extern void use_string_ptr(char*const*);
128 use_string_ptr(p2);
129
130 size_t c = strlen(x);
131 if (a == 0 && c != 0)
132 (void)*(char*)0; // expected-warning{{null}}
133 }
134
strlen_liveness(const char * x)135 void strlen_liveness(const char *x) {
136 if (strlen(x) < 5)
137 return;
138 if (strlen(x) < 5)
139 (void)*(char*)0; // no-warning
140 }
141
142 //===----------------------------------------------------------------------===
143 // strnlen()
144 //===----------------------------------------------------------------------===
145
146 size_t strnlen(const char *s, size_t maxlen);
147
strnlen_constant0()148 void strnlen_constant0() {
149 if (strnlen("123", 10) != 3)
150 (void)*(char*)0; // expected-warning{{never executed}}
151 }
152
strnlen_constant1()153 void strnlen_constant1() {
154 const char *a = "123";
155 if (strnlen(a, 10) != 3)
156 (void)*(char*)0; // expected-warning{{never executed}}
157 }
158
strnlen_constant2(char x)159 void strnlen_constant2(char x) {
160 char a[] = "123";
161 if (strnlen(a, 10) != 3)
162 (void)*(char*)0; // expected-warning{{never executed}}
163 a[0] = x;
164 if (strnlen(a, 10) != 3)
165 (void)*(char*)0; // expected-warning{{null}}
166 }
167
strnlen_constant4()168 void strnlen_constant4() {
169 if (strnlen("123456", 3) != 3)
170 (void)*(char*)0; // expected-warning{{never executed}}
171 }
172
strnlen_constant5()173 void strnlen_constant5() {
174 const char *a = "123456";
175 if (strnlen(a, 3) != 3)
176 (void)*(char*)0; // expected-warning{{never executed}}
177 }
178
strnlen_constant6(char x)179 void strnlen_constant6(char x) {
180 char a[] = "123456";
181 if (strnlen(a, 3) != 3)
182 (void)*(char*)0; // expected-warning{{never executed}}
183 a[0] = x;
184 if (strnlen(a, 3) != 3)
185 (void)*(char*)0; // expected-warning{{null}}
186 }
187
strnlen_null()188 size_t strnlen_null() {
189 return strnlen(0, 3); // expected-warning{{Null pointer argument in call to string length function}}
190 }
191
strnlen_fn()192 size_t strnlen_fn() {
193 return strnlen((char*)&strlen_fn, 3); // expected-warning{{Argument to string length function is the address of the function 'strlen_fn', which is not a null-terminated string}}
194 }
195
strnlen_nonloc()196 size_t strnlen_nonloc() {
197 label:
198 return strnlen((char*)&&label, 3); // expected-warning{{Argument to string length function is the address of the label 'label', which is not a null-terminated string}}
199 }
200
strnlen_zero()201 void strnlen_zero() {
202 if (strnlen("abc", 0) != 0)
203 (void)*(char*)0; // expected-warning{{never executed}}
204 if (strnlen(NULL, 0) != 0) // no-warning
205 (void)*(char*)0; // no-warning
206 }
207
strnlen_compound_literal()208 size_t strnlen_compound_literal() {
209 // This used to crash because we don't model the string lengths of
210 // compound literals.
211 return strnlen((char[]) { 'a', 'b', 0 }, 1);
212 }
213
strnlen_unknown_limit(float f)214 size_t strnlen_unknown_limit(float f) {
215 // This used to crash because we don't model the integer values of floats.
216 return strnlen("abc", (int)f);
217 }
218
strnlen_is_not_strlen(char * x)219 void strnlen_is_not_strlen(char *x) {
220 if (strnlen(x, 10) != strlen(x))
221 (void)*(char*)0; // expected-warning{{null}}
222 }
223
strnlen_at_limit(char * x)224 void strnlen_at_limit(char *x) {
225 size_t len = strnlen(x, 10);
226 if (len > 10)
227 (void)*(char*)0; // expected-warning{{never executed}}
228 if (len == 10)
229 (void)*(char*)0; // expected-warning{{null}}
230 }
231
strnlen_less_than_limit(char * x)232 void strnlen_less_than_limit(char *x) {
233 size_t len = strnlen(x, 10);
234 if (len > 10)
235 (void)*(char*)0; // expected-warning{{never executed}}
236 if (len < 10)
237 (void)*(char*)0; // expected-warning{{null}}
238 }
239
strnlen_at_actual(size_t limit)240 void strnlen_at_actual(size_t limit) {
241 size_t len = strnlen("abc", limit);
242 if (len > 3)
243 (void)*(char*)0; // expected-warning{{never executed}}
244 if (len == 3)
245 (void)*(char*)0; // expected-warning{{null}}
246 }
247
strnlen_less_than_actual(size_t limit)248 void strnlen_less_than_actual(size_t limit) {
249 size_t len = strnlen("abc", limit);
250 if (len > 3)
251 (void)*(char*)0; // expected-warning{{never executed}}
252 if (len < 3)
253 (void)*(char*)0; // expected-warning{{null}}
254 }
255
256 //===----------------------------------------------------------------------===
257 // strcpy()
258 //===----------------------------------------------------------------------===
259
260 #ifdef VARIANT
261
262 #define __strcpy_chk BUILTIN(__strcpy_chk)
263 char *__strcpy_chk(char *restrict s1, const char *restrict s2, size_t destlen);
264
265 #define strcpy(a,b) __strcpy_chk(a,b,(size_t)-1)
266
267 #else /* VARIANT */
268
269 #define strcpy BUILTIN(strcpy)
270 char *strcpy(char *restrict s1, const char *restrict s2);
271
272 #endif /* VARIANT */
273
274
strcpy_null_dst(char * x)275 void strcpy_null_dst(char *x) {
276 strcpy(NULL, x); // expected-warning{{Null pointer argument in call to string copy function}}
277 }
278
strcpy_null_src(char * x)279 void strcpy_null_src(char *x) {
280 strcpy(x, NULL); // expected-warning{{Null pointer argument in call to string copy function}}
281 }
282
strcpy_fn(char * x)283 void strcpy_fn(char *x) {
284 strcpy(x, (char*)&strcpy_fn); // expected-warning{{Argument to string copy function is the address of the function 'strcpy_fn', which is not a null-terminated string}}
285 }
286
strcpy_effects(char * x,char * y)287 void strcpy_effects(char *x, char *y) {
288 char a = x[0];
289
290 if (strcpy(x, y) != x)
291 (void)*(char*)0; // no-warning
292
293 if (strlen(x) != strlen(y))
294 (void)*(char*)0; // no-warning
295
296 if (a != x[0])
297 (void)*(char*)0; // expected-warning{{null}}
298 }
299
strcpy_overflow(char * y)300 void strcpy_overflow(char *y) {
301 char x[4];
302 if (strlen(y) == 4)
303 strcpy(x, y); // expected-warning{{String copy function overflows destination buffer}}
304 }
305
strcpy_no_overflow(char * y)306 void strcpy_no_overflow(char *y) {
307 char x[4];
308 if (strlen(y) == 3)
309 strcpy(x, y); // no-warning
310 }
311
312 //===----------------------------------------------------------------------===
313 // stpcpy()
314 //===----------------------------------------------------------------------===
315
316 #ifdef VARIANT
317
318 #define __stpcpy_chk BUILTIN(__stpcpy_chk)
319 char *__stpcpy_chk(char *restrict s1, const char *restrict s2, size_t destlen);
320
321 #define stpcpy(a,b) __stpcpy_chk(a,b,(size_t)-1)
322
323 #else /* VARIANT */
324
325 #define stpcpy BUILTIN(stpcpy)
326 char *stpcpy(char *restrict s1, const char *restrict s2);
327
328 #endif /* VARIANT */
329
330
stpcpy_effect(char * x,char * y)331 void stpcpy_effect(char *x, char *y) {
332 char a = x[0];
333
334 if (stpcpy(x, y) != &x[strlen(y)])
335 (void)*(char*)0; // no-warning
336
337 if (strlen(x) != strlen(y))
338 (void)*(char*)0; // no-warning
339
340 if (a != x[0])
341 (void)*(char*)0; // expected-warning{{null}}
342 }
343
stpcpy_overflow(char * y)344 void stpcpy_overflow(char *y) {
345 char x[4];
346 if (strlen(y) == 4)
347 stpcpy(x, y); // expected-warning{{String copy function overflows destination buffer}}
348 }
349
stpcpy_no_overflow(char * y)350 void stpcpy_no_overflow(char *y) {
351 char x[4];
352 if (strlen(y) == 3)
353 stpcpy(x, y); // no-warning
354 }
355
356 //===----------------------------------------------------------------------===
357 // strcat()
358 //===----------------------------------------------------------------------===
359
360 #ifdef VARIANT
361
362 #define __strcat_chk BUILTIN(__strcat_chk)
363 char *__strcat_chk(char *restrict s1, const char *restrict s2, size_t destlen);
364
365 #define strcat(a,b) __strcat_chk(a,b,(size_t)-1)
366
367 #else /* VARIANT */
368
369 #define strcat BUILTIN(strcat)
370 char *strcat(char *restrict s1, const char *restrict s2);
371
372 #endif /* VARIANT */
373
374
strcat_null_dst(char * x)375 void strcat_null_dst(char *x) {
376 strcat(NULL, x); // expected-warning{{Null pointer argument in call to string copy function}}
377 }
378
strcat_null_src(char * x)379 void strcat_null_src(char *x) {
380 strcat(x, NULL); // expected-warning{{Null pointer argument in call to string copy function}}
381 }
382
strcat_fn(char * x)383 void strcat_fn(char *x) {
384 strcat(x, (char*)&strcat_fn); // expected-warning{{Argument to string copy function is the address of the function 'strcat_fn', which is not a null-terminated string}}
385 }
386
strcat_effects(char * y)387 void strcat_effects(char *y) {
388 char x[8] = "123";
389 size_t orig_len = strlen(x);
390 char a = x[0];
391
392 if (strlen(y) != 4)
393 return;
394
395 if (strcat(x, y) != x)
396 (void)*(char*)0; // no-warning
397
398 if ((int)strlen(x) != (orig_len + strlen(y)))
399 (void)*(char*)0; // no-warning
400 }
401
strcat_overflow_0(char * y)402 void strcat_overflow_0(char *y) {
403 char x[4] = "12";
404 if (strlen(y) == 4)
405 strcat(x, y); // expected-warning{{String copy function overflows destination buffer}}
406 }
407
strcat_overflow_1(char * y)408 void strcat_overflow_1(char *y) {
409 char x[4] = "12";
410 if (strlen(y) == 3)
411 strcat(x, y); // expected-warning{{String copy function overflows destination buffer}}
412 }
413
strcat_overflow_2(char * y)414 void strcat_overflow_2(char *y) {
415 char x[4] = "12";
416 if (strlen(y) == 2)
417 strcat(x, y); // expected-warning{{String copy function overflows destination buffer}}
418 }
419
strcat_no_overflow(char * y)420 void strcat_no_overflow(char *y) {
421 char x[5] = "12";
422 if (strlen(y) == 2)
423 strcat(x, y); // no-warning
424 }
425
strcat_symbolic_dst_length(char * dst)426 void strcat_symbolic_dst_length(char *dst) {
427 strcat(dst, "1234");
428 if (strlen(dst) < 4)
429 (void)*(char*)0; // no-warning
430 }
431
strcat_symbolic_src_length(char * src)432 void strcat_symbolic_src_length(char *src) {
433 char dst[8] = "1234";
434 strcat(dst, src);
435 if (strlen(dst) < 4)
436 (void)*(char*)0; // no-warning
437 }
438
strcat_unknown_src_length(char * src,int offset)439 void strcat_unknown_src_length(char *src, int offset) {
440 char dst[8] = "1234";
441 strcat(dst, &src[offset]);
442 if (strlen(dst) < 4)
443 (void)*(char*)0; // no-warning
444 }
445
446 // There is no strcat_unknown_dst_length because if we can't get a symbolic
447 // length for the "before" strlen, we won't be able to set one for "after".
448
strcat_too_big(char * dst,char * src)449 void strcat_too_big(char *dst, char *src) {
450 if (strlen(dst) != (((size_t)0) - 2))
451 return;
452 if (strlen(src) != 2)
453 return;
454 strcat(dst, src); // expected-warning{{This expression will create a string whose length is too big to be represented as a size_t}}
455 }
456
457
458 //===----------------------------------------------------------------------===
459 // strncpy()
460 //===----------------------------------------------------------------------===
461
462 #ifdef VARIANT
463
464 #define __strncpy_chk BUILTIN(__strncpy_chk)
465 char *__strncpy_chk(char *restrict s1, const char *restrict s2, size_t n, size_t destlen);
466
467 #define strncpy(a,b,n) __strncpy_chk(a,b,n,(size_t)-1)
468
469 #else /* VARIANT */
470
471 #define strncpy BUILTIN(strncpy)
472 char *strncpy(char *restrict s1, const char *restrict s2, size_t n);
473
474 #endif /* VARIANT */
475
476
strncpy_null_dst(char * x)477 void strncpy_null_dst(char *x) {
478 strncpy(NULL, x, 5); // expected-warning{{Null pointer argument in call to string copy function}}
479 }
480
strncpy_null_src(char * x)481 void strncpy_null_src(char *x) {
482 strncpy(x, NULL, 5); // expected-warning{{Null pointer argument in call to string copy function}}
483 }
484
strncpy_fn(char * x)485 void strncpy_fn(char *x) {
486 strncpy(x, (char*)&strcpy_fn, 5); // expected-warning{{Argument to string copy function is the address of the function 'strcpy_fn', which is not a null-terminated string}}
487 }
488
strncpy_effects(char * x,char * y)489 void strncpy_effects(char *x, char *y) {
490 char a = x[0];
491
492 if (strncpy(x, y, 5) != x)
493 (void)*(char*)0; // no-warning
494
495 if (strlen(x) != strlen(y))
496 (void)*(char*)0; // expected-warning{{null}}
497
498 if (a != x[0])
499 (void)*(char*)0; // expected-warning{{null}}
500 }
501
strncpy_overflow(char * y)502 void strncpy_overflow(char *y) {
503 char x[4];
504 if (strlen(y) == 4)
505 strncpy(x, y, 5); // expected-warning{{Size argument is greater than the length of the destination buffer}}
506 }
507
strncpy_no_overflow(char * y)508 void strncpy_no_overflow(char *y) {
509 char x[4];
510 if (strlen(y) == 3)
511 strncpy(x, y, 5); // expected-warning{{Size argument is greater than the length of the destination buffer}}
512 }
513
strncpy_no_overflow2(char * y,int n)514 void strncpy_no_overflow2(char *y, int n) {
515 if (n <= 4)
516 return;
517
518 char x[4];
519 if (strlen(y) == 3)
520 strncpy(x, y, n); // expected-warning{{Size argument is greater than the length of the destination buffer}}
521 }
522
strncpy_truncate(char * y)523 void strncpy_truncate(char *y) {
524 char x[4];
525 if (strlen(y) == 4)
526 strncpy(x, y, 3); // no-warning
527 }
528
strncpy_no_truncate(char * y)529 void strncpy_no_truncate(char *y) {
530 char x[4];
531 if (strlen(y) == 3)
532 strncpy(x, y, 3); // no-warning
533 }
534
strncpy_exactly_matching_buffer(char * y)535 void strncpy_exactly_matching_buffer(char *y) {
536 char x[4];
537 strncpy(x, y, 4); // no-warning
538
539 // strncpy does not null-terminate, so we have no idea what the strlen is
540 // after this.
541 if (strlen(x) > 4)
542 (void)*(int*)0; // expected-warning{{null}}
543 }
544
strncpy_exactly_matching_buffer2(char * y)545 void strncpy_exactly_matching_buffer2(char *y) {
546 if (strlen(y) >= 4)
547 return;
548
549 char x[4];
550 strncpy(x, y, 4); // no-warning
551
552 // This time, we know that y fits in x anyway.
553 if (strlen(x) > 3)
554 (void)*(int*)0; // no-warning
555 }
556
557 //===----------------------------------------------------------------------===
558 // strncat()
559 //===----------------------------------------------------------------------===
560
561 #ifdef VARIANT
562
563 #define __strncat_chk BUILTIN(__strncat_chk)
564 char *__strncat_chk(char *restrict s1, const char *restrict s2, size_t n, size_t destlen);
565
566 #define strncat(a,b,c) __strncat_chk(a,b,c, (size_t)-1)
567
568 #else /* VARIANT */
569
570 #define strncat BUILTIN(strncat)
571 char *strncat(char *restrict s1, const char *restrict s2, size_t n);
572
573 #endif /* VARIANT */
574
575
strncat_null_dst(char * x)576 void strncat_null_dst(char *x) {
577 strncat(NULL, x, 4); // expected-warning{{Null pointer argument in call to string copy function}}
578 }
579
strncat_null_src(char * x)580 void strncat_null_src(char *x) {
581 strncat(x, NULL, 4); // expected-warning{{Null pointer argument in call to string copy function}}
582 }
583
strncat_fn(char * x)584 void strncat_fn(char *x) {
585 strncat(x, (char*)&strncat_fn, 4); // expected-warning{{Argument to string copy function is the address of the function 'strncat_fn', which is not a null-terminated string}}
586 }
587
strncat_effects(char * y)588 void strncat_effects(char *y) {
589 char x[8] = "123";
590 size_t orig_len = strlen(x);
591 char a = x[0];
592
593 if (strlen(y) != 4)
594 return;
595
596 if (strncat(x, y, strlen(y)) != x)
597 (void)*(char*)0; // no-warning
598
599 if (strlen(x) != orig_len + strlen(y))
600 (void)*(char*)0; // no-warning
601 }
602
strncat_overflow_0(char * y)603 void strncat_overflow_0(char *y) {
604 char x[4] = "12";
605 if (strlen(y) == 4)
606 strncat(x, y, strlen(y)); // expected-warning{{Size argument is greater than the free space in the destination buffer}}
607 }
608
strncat_overflow_1(char * y)609 void strncat_overflow_1(char *y) {
610 char x[4] = "12";
611 if (strlen(y) == 3)
612 strncat(x, y, strlen(y)); // expected-warning{{Size argument is greater than the free space in the destination buffer}}
613 }
614
strncat_overflow_2(char * y)615 void strncat_overflow_2(char *y) {
616 char x[4] = "12";
617 if (strlen(y) == 2)
618 strncat(x, y, strlen(y)); // expected-warning{{Size argument is greater than the free space in the destination buffer}}
619 }
620
strncat_overflow_3(char * y)621 void strncat_overflow_3(char *y) {
622 char x[4] = "12";
623 if (strlen(y) == 4)
624 strncat(x, y, 2); // expected-warning{{Size argument is greater than the free space in the destination buffer}}
625 }
strncat_no_overflow_1(char * y)626 void strncat_no_overflow_1(char *y) {
627 char x[5] = "12";
628 if (strlen(y) == 2)
629 strncat(x, y, strlen(y)); // no-warning
630 }
631
strncat_no_overflow_2(char * y)632 void strncat_no_overflow_2(char *y) {
633 char x[4] = "12";
634 if (strlen(y) == 4)
635 strncat(x, y, 1); // no-warning
636 }
637
strncat_symbolic_dst_length(char * dst)638 void strncat_symbolic_dst_length(char *dst) {
639 strncat(dst, "1234", 5);
640 if (strlen(dst) < 4)
641 (void)*(char*)0; // no-warning
642 }
643
strncat_symbolic_src_length(char * src)644 void strncat_symbolic_src_length(char *src) {
645 char dst[8] = "1234";
646 strncat(dst, src, 3);
647 if (strlen(dst) < 4)
648 (void)*(char*)0; // no-warning
649
650 char dst2[8] = "1234";
651 strncat(dst2, src, 4); // expected-warning{{Size argument is greater than the free space in the destination buffer}}
652 }
653
strncat_unknown_src_length(char * src,int offset)654 void strncat_unknown_src_length(char *src, int offset) {
655 char dst[8] = "1234";
656 strncat(dst, &src[offset], 3);
657 if (strlen(dst) < 4)
658 (void)*(char*)0; // no-warning
659
660 char dst2[8] = "1234";
661 strncat(dst2, &src[offset], 4); // expected-warning{{Size argument is greater than the free space in the destination buffer}}
662 }
663
664 // There is no strncat_unknown_dst_length because if we can't get a symbolic
665 // length for the "before" strlen, we won't be able to set one for "after".
666
strncat_symbolic_limit(unsigned limit)667 void strncat_symbolic_limit(unsigned limit) {
668 char dst[6] = "1234";
669 char src[] = "567";
670 strncat(dst, src, limit); // no-warning
671 if (strlen(dst) < 4)
672 (void)*(char*)0; // no-warning
673 if (strlen(dst) == 4)
674 (void)*(char*)0; // expected-warning{{null}}
675 }
676
strncat_unknown_limit(float limit)677 void strncat_unknown_limit(float limit) {
678 char dst[6] = "1234";
679 char src[] = "567";
680 strncat(dst, src, (size_t)limit); // no-warning
681 if (strlen(dst) < 4)
682 (void)*(char*)0; // no-warning
683 if (strlen(dst) == 4)
684 (void)*(char*)0; // expected-warning{{null}}
685 }
686
strncat_too_big(char * dst,char * src)687 void strncat_too_big(char *dst, char *src) {
688 if (strlen(dst) != (((size_t)0) - 2))
689 return;
690 if (strlen(src) != 2)
691 return;
692 strncat(dst, src, 2); // expected-warning{{This expression will create a string whose length is too big to be represented as a size_t}}
693 }
694
695 //===----------------------------------------------------------------------===
696 // strcmp()
697 //===----------------------------------------------------------------------===
698
699 #define strcmp BUILTIN(strcmp)
700 int strcmp(const char * s1, const char * s2);
701
strcmp_constant0()702 void strcmp_constant0() {
703 if (strcmp("123", "123") != 0)
704 (void)*(char*)0; // no-warning
705 }
706
strcmp_constant_and_var_0()707 void strcmp_constant_and_var_0() {
708 char *x = "123";
709 if (strcmp(x, "123") != 0)
710 (void)*(char*)0; // no-warning
711 }
712
strcmp_constant_and_var_1()713 void strcmp_constant_and_var_1() {
714 char *x = "123";
715 if (strcmp("123", x) != 0)
716 (void)*(char*)0; // no-warning
717 }
718
strcmp_0()719 void strcmp_0() {
720 char *x = "123";
721 char *y = "123";
722 if (strcmp(x, y) != 0)
723 (void)*(char*)0; // no-warning
724 }
725
strcmp_1()726 void strcmp_1() {
727 char *x = "234";
728 char *y = "123";
729 if (strcmp(x, y) != 1)
730 (void)*(char*)0; // no-warning
731 }
732
strcmp_2()733 void strcmp_2() {
734 char *x = "123";
735 char *y = "234";
736 if (strcmp(x, y) != -1)
737 (void)*(char*)0; // no-warning
738 }
739
strcmp_null_0()740 void strcmp_null_0() {
741 char *x = NULL;
742 char *y = "123";
743 strcmp(x, y); // expected-warning{{Null pointer argument in call to string comparison function}}
744 }
745
strcmp_null_1()746 void strcmp_null_1() {
747 char *x = "123";
748 char *y = NULL;
749 strcmp(x, y); // expected-warning{{Null pointer argument in call to string comparison function}}
750 }
751
strcmp_diff_length_0()752 void strcmp_diff_length_0() {
753 char *x = "12345";
754 char *y = "234";
755 if (strcmp(x, y) != -1)
756 (void)*(char*)0; // no-warning
757 }
758
strcmp_diff_length_1()759 void strcmp_diff_length_1() {
760 char *x = "123";
761 char *y = "23456";
762 if (strcmp(x, y) != -1)
763 (void)*(char*)0; // no-warning
764 }
765
strcmp_diff_length_2()766 void strcmp_diff_length_2() {
767 char *x = "12345";
768 char *y = "123";
769 if (strcmp(x, y) != 1)
770 (void)*(char*)0; // no-warning
771 }
772
strcmp_diff_length_3()773 void strcmp_diff_length_3() {
774 char *x = "123";
775 char *y = "12345";
776 if (strcmp(x, y) != -1)
777 (void)*(char*)0; // no-warning
778 }
779
strcmp_embedded_null()780 void strcmp_embedded_null () {
781 if (strcmp("\0z", "\0y") != 0)
782 (void)*(char*)0; // no-warning
783 }
784
strcmp_unknown_arg(char * unknown)785 void strcmp_unknown_arg (char *unknown) {
786 if (strcmp(unknown, unknown) != 0)
787 (void)*(char*)0; // no-warning
788 }
789
790 //===----------------------------------------------------------------------===
791 // strncmp()
792 //===----------------------------------------------------------------------===
793
794 #define strncmp BUILTIN(strncmp)
795 int strncmp(const char *s1, const char *s2, size_t n);
796
strncmp_constant0()797 void strncmp_constant0() {
798 if (strncmp("123", "123", 3) != 0)
799 (void)*(char*)0; // no-warning
800 }
801
strncmp_constant_and_var_0()802 void strncmp_constant_and_var_0() {
803 char *x = "123";
804 if (strncmp(x, "123", 3) != 0)
805 (void)*(char*)0; // no-warning
806 }
807
strncmp_constant_and_var_1()808 void strncmp_constant_and_var_1() {
809 char *x = "123";
810 if (strncmp("123", x, 3) != 0)
811 (void)*(char*)0; // no-warning
812 }
813
strncmp_0()814 void strncmp_0() {
815 char *x = "123";
816 char *y = "123";
817 if (strncmp(x, y, 3) != 0)
818 (void)*(char*)0; // no-warning
819 }
820
strncmp_1()821 void strncmp_1() {
822 char *x = "234";
823 char *y = "123";
824 if (strncmp(x, y, 3) != 1)
825 (void)*(char*)0; // no-warning
826 }
827
strncmp_2()828 void strncmp_2() {
829 char *x = "123";
830 char *y = "234";
831 if (strncmp(x, y, 3) != -1)
832 (void)*(char*)0; // no-warning
833 }
834
strncmp_null_0()835 void strncmp_null_0() {
836 char *x = NULL;
837 char *y = "123";
838 strncmp(x, y, 3); // expected-warning{{Null pointer argument in call to string comparison function}}
839 }
840
strncmp_null_1()841 void strncmp_null_1() {
842 char *x = "123";
843 char *y = NULL;
844 strncmp(x, y, 3); // expected-warning{{Null pointer argument in call to string comparison function}}
845 }
846
strncmp_diff_length_0()847 void strncmp_diff_length_0() {
848 char *x = "12345";
849 char *y = "234";
850 if (strncmp(x, y, 5) != -1)
851 (void)*(char*)0; // no-warning
852 }
853
strncmp_diff_length_1()854 void strncmp_diff_length_1() {
855 char *x = "123";
856 char *y = "23456";
857 if (strncmp(x, y, 5) != -1)
858 (void)*(char*)0; // no-warning
859 }
860
strncmp_diff_length_2()861 void strncmp_diff_length_2() {
862 char *x = "12345";
863 char *y = "123";
864 if (strncmp(x, y, 5) != 1)
865 (void)*(char*)0; // no-warning
866 }
867
strncmp_diff_length_3()868 void strncmp_diff_length_3() {
869 char *x = "123";
870 char *y = "12345";
871 if (strncmp(x, y, 5) != -1)
872 (void)*(char*)0; // no-warning
873 }
874
strncmp_diff_length_4()875 void strncmp_diff_length_4() {
876 char *x = "123";
877 char *y = "12345";
878 if (strncmp(x, y, 3) != 0)
879 (void)*(char*)0; // no-warning
880 }
881
strncmp_diff_length_5()882 void strncmp_diff_length_5() {
883 char *x = "012";
884 char *y = "12345";
885 if (strncmp(x, y, 3) != -1)
886 (void)*(char*)0; // no-warning
887 }
888
strncmp_diff_length_6()889 void strncmp_diff_length_6() {
890 char *x = "234";
891 char *y = "12345";
892 if (strncmp(x, y, 3) != 1)
893 (void)*(char*)0; // no-warning
894 }
895
strncmp_embedded_null()896 void strncmp_embedded_null () {
897 if (strncmp("ab\0zz", "ab\0yy", 4) != 0)
898 (void)*(char*)0; // no-warning
899 }
900
901 //===----------------------------------------------------------------------===
902 // strcasecmp()
903 //===----------------------------------------------------------------------===
904
905 #define strcasecmp BUILTIN(strcasecmp)
906 int strcasecmp(const char *s1, const char *s2);
907
strcasecmp_constant0()908 void strcasecmp_constant0() {
909 if (strcasecmp("abc", "Abc") != 0)
910 (void)*(char*)0; // no-warning
911 }
912
strcasecmp_constant_and_var_0()913 void strcasecmp_constant_and_var_0() {
914 char *x = "abc";
915 if (strcasecmp(x, "Abc") != 0)
916 (void)*(char*)0; // no-warning
917 }
918
strcasecmp_constant_and_var_1()919 void strcasecmp_constant_and_var_1() {
920 char *x = "abc";
921 if (strcasecmp("Abc", x) != 0)
922 (void)*(char*)0; // no-warning
923 }
924
strcasecmp_0()925 void strcasecmp_0() {
926 char *x = "abc";
927 char *y = "Abc";
928 if (strcasecmp(x, y) != 0)
929 (void)*(char*)0; // no-warning
930 }
931
strcasecmp_1()932 void strcasecmp_1() {
933 char *x = "Bcd";
934 char *y = "abc";
935 if (strcasecmp(x, y) != 1)
936 (void)*(char*)0; // no-warning
937 }
938
strcasecmp_2()939 void strcasecmp_2() {
940 char *x = "abc";
941 char *y = "Bcd";
942 if (strcasecmp(x, y) != -1)
943 (void)*(char*)0; // no-warning
944 }
945
strcasecmp_null_0()946 void strcasecmp_null_0() {
947 char *x = NULL;
948 char *y = "123";
949 strcasecmp(x, y); // expected-warning{{Null pointer argument in call to string comparison function}}
950 }
951
strcasecmp_null_1()952 void strcasecmp_null_1() {
953 char *x = "123";
954 char *y = NULL;
955 strcasecmp(x, y); // expected-warning{{Null pointer argument in call to string comparison function}}
956 }
957
strcasecmp_diff_length_0()958 void strcasecmp_diff_length_0() {
959 char *x = "abcde";
960 char *y = "aBd";
961 if (strcasecmp(x, y) != -1)
962 (void)*(char*)0; // no-warning
963 }
964
strcasecmp_diff_length_1()965 void strcasecmp_diff_length_1() {
966 char *x = "abc";
967 char *y = "aBdef";
968 if (strcasecmp(x, y) != -1)
969 (void)*(char*)0; // no-warning
970 }
971
strcasecmp_diff_length_2()972 void strcasecmp_diff_length_2() {
973 char *x = "aBcDe";
974 char *y = "abc";
975 if (strcasecmp(x, y) != 1)
976 (void)*(char*)0; // no-warning
977 }
978
strcasecmp_diff_length_3()979 void strcasecmp_diff_length_3() {
980 char *x = "aBc";
981 char *y = "abcde";
982 if (strcasecmp(x, y) != -1)
983 (void)*(char*)0; // no-warning
984 }
985
strcasecmp_embedded_null()986 void strcasecmp_embedded_null () {
987 if (strcasecmp("ab\0zz", "ab\0yy") != 0)
988 (void)*(char*)0; // no-warning
989 }
990
991 //===----------------------------------------------------------------------===
992 // strncasecmp()
993 //===----------------------------------------------------------------------===
994
995 #define strncasecmp BUILTIN(strncasecmp)
996 int strncasecmp(const char *s1, const char *s2, size_t n);
997
strncasecmp_constant0()998 void strncasecmp_constant0() {
999 if (strncasecmp("abc", "Abc", 3) != 0)
1000 (void)*(char*)0; // no-warning
1001 }
1002
strncasecmp_constant_and_var_0()1003 void strncasecmp_constant_and_var_0() {
1004 char *x = "abc";
1005 if (strncasecmp(x, "Abc", 3) != 0)
1006 (void)*(char*)0; // no-warning
1007 }
1008
strncasecmp_constant_and_var_1()1009 void strncasecmp_constant_and_var_1() {
1010 char *x = "abc";
1011 if (strncasecmp("Abc", x, 3) != 0)
1012 (void)*(char*)0; // no-warning
1013 }
1014
strncasecmp_0()1015 void strncasecmp_0() {
1016 char *x = "abc";
1017 char *y = "Abc";
1018 if (strncasecmp(x, y, 3) != 0)
1019 (void)*(char*)0; // no-warning
1020 }
1021
strncasecmp_1()1022 void strncasecmp_1() {
1023 char *x = "Bcd";
1024 char *y = "abc";
1025 if (strncasecmp(x, y, 3) != 1)
1026 (void)*(char*)0; // no-warning
1027 }
1028
strncasecmp_2()1029 void strncasecmp_2() {
1030 char *x = "abc";
1031 char *y = "Bcd";
1032 if (strncasecmp(x, y, 3) != -1)
1033 (void)*(char*)0; // no-warning
1034 }
1035
strncasecmp_null_0()1036 void strncasecmp_null_0() {
1037 char *x = NULL;
1038 char *y = "123";
1039 strncasecmp(x, y, 3); // expected-warning{{Null pointer argument in call to string comparison function}}
1040 }
1041
strncasecmp_null_1()1042 void strncasecmp_null_1() {
1043 char *x = "123";
1044 char *y = NULL;
1045 strncasecmp(x, y, 3); // expected-warning{{Null pointer argument in call to string comparison function}}
1046 }
1047
strncasecmp_diff_length_0()1048 void strncasecmp_diff_length_0() {
1049 char *x = "abcde";
1050 char *y = "aBd";
1051 if (strncasecmp(x, y, 5) != -1)
1052 (void)*(char*)0; // no-warning
1053 }
1054
strncasecmp_diff_length_1()1055 void strncasecmp_diff_length_1() {
1056 char *x = "abc";
1057 char *y = "aBdef";
1058 if (strncasecmp(x, y, 5) != -1)
1059 (void)*(char*)0; // no-warning
1060 }
1061
strncasecmp_diff_length_2()1062 void strncasecmp_diff_length_2() {
1063 char *x = "aBcDe";
1064 char *y = "abc";
1065 if (strncasecmp(x, y, 5) != 1)
1066 (void)*(char*)0; // no-warning
1067 }
1068
strncasecmp_diff_length_3()1069 void strncasecmp_diff_length_3() {
1070 char *x = "aBc";
1071 char *y = "abcde";
1072 if (strncasecmp(x, y, 5) != -1)
1073 (void)*(char*)0; // no-warning
1074 }
1075
strncasecmp_diff_length_4()1076 void strncasecmp_diff_length_4() {
1077 char *x = "abcde";
1078 char *y = "aBc";
1079 if (strncasecmp(x, y, 3) != 0)
1080 (void)*(char*)0; // no-warning
1081 }
1082
strncasecmp_diff_length_5()1083 void strncasecmp_diff_length_5() {
1084 char *x = "abcde";
1085 char *y = "aBd";
1086 if (strncasecmp(x, y, 3) != -1)
1087 (void)*(char*)0; // no-warning
1088 }
1089
strncasecmp_diff_length_6()1090 void strncasecmp_diff_length_6() {
1091 char *x = "aBDe";
1092 char *y = "abc";
1093 if (strncasecmp(x, y, 3) != 1)
1094 (void)*(char*)0; // no-warning
1095 }
1096
strncasecmp_embedded_null()1097 void strncasecmp_embedded_null () {
1098 if (strncasecmp("ab\0zz", "ab\0yy", 4) != 0)
1099 (void)*(char*)0; // no-warning
1100 }
1101