2017-03-04 02:02:02 +08:00
|
|
|
// RUN: %clang_analyze_cc1 -analyzer-checker=core -analyzer-output=text -verify %s
|
2018-06-13 03:07:41 +08:00
|
|
|
// RUN: %clang_analyze_cc1 -analyzer-checker=core -analyzer-output=plist-multi-file %s -o %t.plist
|
2019-01-11 02:15:44 +08:00
|
|
|
// RUN: cat %t.plist | %diff_plist %S/Inputs/expected-plists/undef-value-param.c.plist -
|
2012-08-30 05:22:37 +08:00
|
|
|
|
|
|
|
void foo_irrelevant(int c) {
|
|
|
|
if (c)
|
|
|
|
return;
|
|
|
|
c++;
|
|
|
|
return;
|
|
|
|
}
|
2012-08-30 07:23:39 +08:00
|
|
|
void foo(int c, int *x) {
|
2012-08-30 05:22:37 +08:00
|
|
|
if (c)
|
|
|
|
//expected-note@-1{{Assuming 'c' is not equal to 0}}
|
|
|
|
//expected-note@-2{{Taking true branch}}
|
2018-02-24 07:26:56 +08:00
|
|
|
return; // expected-note{{Returning without writing to '*x'}}
|
2012-08-30 05:22:37 +08:00
|
|
|
*x = 5;
|
|
|
|
}
|
|
|
|
|
|
|
|
int use(int c) {
|
2013-02-27 03:44:38 +08:00
|
|
|
int xx; //expected-note {{'xx' declared without an initial value}}
|
2012-08-30 05:22:37 +08:00
|
|
|
int *y = &xx;
|
2012-08-30 07:23:39 +08:00
|
|
|
foo (c, y);
|
2012-08-30 05:22:37 +08:00
|
|
|
//expected-note@-1{{Calling 'foo'}}
|
|
|
|
//expected-note@-2{{Returning from 'foo'}}
|
|
|
|
foo_irrelevant(c);
|
|
|
|
return xx+3; //expected-warning{{The left operand of '+' is a garbage value}}
|
|
|
|
//expected-note@-1{{The left operand of '+' is a garbage value}}
|
|
|
|
}
|
|
|
|
|
2012-09-13 06:57:30 +08:00
|
|
|
void initArray(int x, double XYZ[3]) {
|
|
|
|
if (x <= 0) //expected-note {{Taking true branch}}
|
|
|
|
//expected-note@-1 {{Assuming 'x' is <= 0}}
|
|
|
|
return;
|
|
|
|
XYZ[0] = 1;
|
|
|
|
XYZ[1] = 1;
|
|
|
|
XYZ[2] = 1;
|
|
|
|
}
|
|
|
|
int testPassingParentRegionArray(int x) {
|
|
|
|
double XYZ[3];
|
|
|
|
initArray(x, XYZ); //expected-note {{Calling 'initArray'}}
|
|
|
|
//expected-note@-1 {{Returning from 'initArray'}}
|
|
|
|
return 1 * XYZ[1]; //expected-warning {{The right operand of '*' is a garbage value}}
|
|
|
|
//expected-note@-1 {{The right operand of '*' is a garbage value}}
|
|
|
|
}
|
|
|
|
|
|
|
|
double *getValidPtr();
|
|
|
|
struct WithFields {
|
|
|
|
double *f1;
|
|
|
|
};
|
|
|
|
void initStruct(int x, struct WithFields *X) {
|
|
|
|
if (x <= 0) //expected-note {{Taking true branch}}
|
|
|
|
//expected-note@-1 {{Assuming 'x' is <= 0}}
|
|
|
|
|
2018-02-24 07:26:56 +08:00
|
|
|
return; //expected-note{{Returning without writing to 'X->f1'}}
|
2012-09-13 06:57:30 +08:00
|
|
|
X->f1 = getValidPtr();
|
|
|
|
}
|
|
|
|
double testPassingParentRegionStruct(int x) {
|
|
|
|
struct WithFields st;
|
2013-02-24 15:21:01 +08:00
|
|
|
st.f1 = 0; // expected-note {{Null pointer value stored to 'st.f1'}}
|
2012-09-13 06:57:30 +08:00
|
|
|
initStruct(x, &st); //expected-note {{Calling 'initStruct'}}
|
|
|
|
//expected-note@-1 {{Returning from 'initStruct'}}
|
|
|
|
return (*st.f1); //expected-warning {{Dereference of null pointer}}
|
|
|
|
//expected-note@-1{{Dereference of null pointer (loaded from field 'f1')}}
|
|
|
|
}
|
|
|
|
|