|
1 |
| -// RUN: %clang_analyze_cc1 -Wno-array-bounds -analyzer-checker=core,security.ArrayBound -verify %s |
| 1 | +// RUN: %clang_analyze_cc1 -Wno-array-bounds -analyzer-checker=core,security.ArrayBound,debug.ExprInspection -verify %s |
| 2 | + |
| 3 | +void clang_analyzer_value(int); |
2 | 4 |
|
3 | 5 | // Tests doing an out-of-bounds access after the end of an array using:
|
4 | 6 | // - constant integer index
|
@@ -180,3 +182,36 @@ char test_comparison_with_extent_symbol(struct incomplete *p) {
|
180 | 182 | return ((char *)p)[-1]; // no-warning
|
181 | 183 | }
|
182 | 184 |
|
| 185 | +int table[256], small_table[128]; |
| 186 | +int test_cast_to_unsigned(signed char x) { |
| 187 | + unsigned char y = x; |
| 188 | + if (x >= 0) |
| 189 | + return x; |
| 190 | + // FIXME: Here the analyzer ignores the signed -> unsigned cast, and manages to |
| 191 | + // load a negative value from an unsigned variable. This causes an underflow |
| 192 | + // report, which is an ugly false positive. |
| 193 | + // The underlying issue is tracked by Github ticket #39492. |
| 194 | + clang_analyzer_value(y); // expected-warning {{8s:{ [-128, -1] } }} |
| 195 | + return table[y]; // expected-warning {{Out of bound access to memory preceding}} |
| 196 | +} |
| 197 | + |
| 198 | +int test_cast_to_unsigned_overflow(signed char x) { |
| 199 | + unsigned char y = x; |
| 200 | + if (x >= 0) |
| 201 | + return x; |
| 202 | + // A variant of 'test_cast_to_unsigned' where the correct behavior would be |
| 203 | + // an overflow report (because the negative values are cast to `unsigned |
| 204 | + // char` values that are too large). |
| 205 | + // FIXME: See comment in 'test_cast_to_unsigned'. |
| 206 | + clang_analyzer_value(y); // expected-warning {{8s:{ [-128, -1] } }} |
| 207 | + return small_table[y]; // expected-warning {{Out of bound access to memory preceding}} |
| 208 | +} |
| 209 | + |
| 210 | +int test_negative_offset_with_unsigned_idx(void) { |
| 211 | + // An example where the subscript operator uses an unsigned index, but the |
| 212 | + // underflow report is still justified. (We should try to keep this if we |
| 213 | + // silence false positives like the one in 'test_cast_to_unsigned'.) |
| 214 | + int *p = table - 10; |
| 215 | + unsigned idx = 2u; |
| 216 | + return p[idx]; // expected-warning {{Out of bound access to memory preceding}} |
| 217 | +} |
0 commit comments