1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150
|
// RUN: %clang_analyze_cc1 -analyzer-checker=alpha.security.MallocOverflow -verify %s
#define NULL ((void *) 0)
typedef __typeof__(sizeof(int)) size_t;
extern void * malloc(size_t);
void * f1(int n)
{
return malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
}
void * f2(int n)
{
return malloc(sizeof(int) * n); // // expected-warning {{the computation of the size of the memory allocation may overflow}}
}
void * f3(void)
{
return malloc(4 * sizeof(int)); // no-warning
}
struct s4
{
int n;
};
void * f4(struct s4 *s)
{
return malloc(s->n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
}
void * f5(struct s4 *s)
{
struct s4 s2 = *s;
return malloc(s2.n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
}
void * f6(int n)
{
return malloc((n + 1) * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
}
extern void * malloc (size_t);
void * f7(int n)
{
if (n > 10)
return NULL;
return malloc(n * sizeof(int)); // no-warning
}
void * f8(int n)
{
if (n < 10)
return malloc(n * sizeof(int)); // no-warning
else
return NULL;
}
void * f9(int n)
{
int * x = malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
for (int i = 0; i < n; i++)
x[i] = i;
return x;
}
void * f10(int n)
{
int * x = malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
int i = 0;
while (i < n)
x[i++] = 0;
return x;
}
void * f11(int n)
{
int * x = malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
int i = 0;
do {
x[i++] = 0;
} while (i < n);
return x;
}
void * f12(int n)
{
n = (n > 10 ? 10 : n);
int * x = malloc(n * sizeof(int)); // no-warning
for (int i = 0; i < n; i++)
x[i] = i;
return x;
}
struct s13
{
int n;
};
void * f13(struct s13 *s)
{
if (s->n > 10)
return NULL;
return malloc(s->n * sizeof(int)); // no-warning
}
void * f14(int n)
{
if (n < 0)
return NULL;
return malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
}
void *check_before_malloc(int n, int x) {
int *p = NULL;
if (n > 10)
return NULL;
if (x == 42)
p = malloc(n * sizeof(int)); // no-warning, the check precedes the allocation
// Do some other stuff, e.g. initialize the memory.
return p;
}
void *check_after_malloc(int n, int x) {
int *p = NULL;
if (x == 42)
p = malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
// The check is after the allocation!
if (n > 10) {
// Do something conditionally.
}
return p;
}
#define GREATER_THAN(lhs, rhs) (lhs > rhs)
void *check_after_malloc_using_macros(int n, int x) {
int *p = NULL;
if (x == 42)
p = malloc(n * sizeof(int)); // expected-warning {{the computation of the size of the memory allocation may overflow}}
if (GREATER_THAN(n, 10))
return NULL;
// Do some other stuff, e.g. initialize the memory.
return p;
}
#undef GREATER_THAN
|