malloc.c revision b276bd9cc98247331cac8b290ba278b939e53657
1// RUN: %clang_cc1 -analyze -analyzer-checker=core,experimental.deadcode.UnreachableCode,experimental.core.CastSize,experimental.unix.Malloc -analyzer-store=region -verify %s 2#include "system-header-simulator.h" 3 4typedef __typeof(sizeof(int)) size_t; 5void *malloc(size_t); 6void free(void *); 7void *realloc(void *ptr, size_t size); 8void *calloc(size_t nmemb, size_t size); 9 10void myfoo(int *p); 11void myfooint(int p); 12 13void f1() { 14 int *p = malloc(12); 15 return; // expected-warning{{Allocated memory never released. Potential memory leak.}} 16} 17 18void f2() { 19 int *p = malloc(12); 20 free(p); 21 free(p); // expected-warning{{Try to free a memory block that has been released}} 22} 23 24void f2_realloc_0() { 25 int *p = malloc(12); 26 realloc(p,0); 27 realloc(p,0); // expected-warning{{Try to free a memory block that has been released}} 28} 29 30void f2_realloc_1() { 31 int *p = malloc(12); 32 int *q = realloc(p,0); // no-warning 33} 34 35void reallocNotNullPtr(unsigned sizeIn) { 36 unsigned size = 12; 37 char *p = (char*)malloc(size); 38 if (p) { 39 char *q = (char*)realloc(p, sizeIn); 40 char x = *q; // expected-warning {{Allocated memory never released.}} 41 } 42} 43 44int *realloctest1() { 45 int *q = malloc(12); 46 q = realloc(q, 20); 47 return q; // no warning - returning the allocated value 48} 49 50// p should be freed if realloc fails. 51void reallocFails() { 52 char *p = malloc(12); 53 char *r = realloc(p, 12+1); 54 if (!r) { 55 free(p); 56 } else { 57 free(r); 58 } 59} 60 61void reallocSizeZero1() { 62 char *p = malloc(12); 63 char *r = realloc(p, 0); 64 if (!r) { 65 free(p); 66 } else { 67 free(r); 68 } 69} 70 71void reallocSizeZero2() { 72 char *p = malloc(12); 73 char *r = realloc(p, 0); 74 if (!r) { 75 free(p); 76 } else { 77 free(r); 78 } 79 free(p); // expected-warning {{Try to free a memory block that has been released}} 80} 81 82void reallocSizeZero3() { 83 char *p = malloc(12); 84 char *r = realloc(p, 0); 85 free(r); 86} 87 88void reallocSizeZero4() { 89 char *r = realloc(0, 0); 90 free(r); 91} 92 93void reallocSizeZero5() { 94 char *r = realloc(0, 0); 95} 96 97void reallocPtrZero1() { 98 char *r = realloc(0, 12); // expected-warning {{Allocated memory never released.}} 99} 100 101void reallocPtrZero2() { 102 char *r = realloc(0, 12); 103 if (r) 104 free(r); 105} 106 107void reallocPtrZero3() { 108 char *r = realloc(0, 12); 109 free(r); 110} 111 112void reallocRadar6337483_1() { 113 char *buf = malloc(100); 114 buf = (char*)realloc(buf, 0x1000000); 115 if (!buf) { 116 return;// expected-warning {{Allocated memory never released.}} 117 } 118 free(buf); 119} 120 121void reallocRadar6337483_2() { 122 char *buf = malloc(100); 123 char *buf2 = (char*)realloc(buf, 0x1000000); 124 if (!buf2) { // expected-warning {{Allocated memory never released.}} 125 ; 126 } else { 127 free(buf2); 128 } 129} 130 131void reallocRadar6337483_3() { 132 char * buf = malloc(100); 133 char * tmp; 134 tmp = (char*)realloc(buf, 0x1000000); 135 if (!tmp) { 136 free(buf); 137 return; 138 } 139 buf = tmp; 140 free(buf); 141} 142 143void reallocRadar6337483_4() { 144 char *buf = malloc(100); 145 char *buf2 = (char*)realloc(buf, 0x1000000); 146 if (!buf2) { 147 return; // expected-warning {{Allocated memory never released.}} 148 } else { 149 free(buf2); 150 } 151} 152 153// This case tests that storing malloc'ed memory to a static variable which is 154// then returned is not leaked. In the absence of known contracts for functions 155// or inter-procedural analysis, this is a conservative answer. 156int *f3() { 157 static int *p = 0; 158 p = malloc(12); 159 return p; // no-warning 160} 161 162// This case tests that storing malloc'ed memory to a static global variable 163// which is then returned is not leaked. In the absence of known contracts for 164// functions or inter-procedural analysis, this is a conservative answer. 165static int *p_f4 = 0; 166int *f4() { 167 p_f4 = malloc(12); 168 return p_f4; // no-warning 169} 170 171int *f5() { 172 int *q = malloc(12); 173 q = realloc(q, 20); 174 return q; // no-warning 175} 176 177void f6() { 178 int *p = malloc(12); 179 if (!p) 180 return; // no-warning 181 else 182 free(p); 183} 184 185void f6_realloc() { 186 int *p = malloc(12); 187 if (!p) 188 return; // no-warning 189 else 190 realloc(p,0); 191} 192 193 194char *doit2(); 195void pr6069() { 196 char *buf = doit2(); 197 free(buf); 198} 199 200void pr6293() { 201 free(0); 202} 203 204void f7() { 205 char *x = (char*) malloc(4); 206 free(x); 207 x[0] = 'a'; // expected-warning{{Use of dynamically allocated memory after it is freed.}} 208} 209 210void f7_realloc() { 211 char *x = (char*) malloc(4); 212 realloc(x,0); 213 x[0] = 'a'; // expected-warning{{Use of dynamically allocated memory after it is freed.}} 214} 215 216void PR6123() { 217 int *x = malloc(11); // expected-warning{{Cast a region whose size is not a multiple of the destination type size.}} 218} 219 220void PR7217() { 221 int *buf = malloc(2); // expected-warning{{Cast a region whose size is not a multiple of the destination type size.}} 222 buf[1] = 'c'; // not crash 223} 224 225void mallocCastToVoid() { 226 void *p = malloc(2); 227 const void *cp = p; // not crash 228 free(p); 229} 230 231void mallocCastToFP() { 232 void *p = malloc(2); 233 void (*fp)() = p; // not crash 234 free(p); 235} 236 237// This tests that malloc() buffers are undefined by default 238char mallocGarbage () { 239 char *buf = malloc(2); 240 char result = buf[1]; // expected-warning{{undefined}} 241 free(buf); 242 return result; 243} 244 245// This tests that calloc() buffers need to be freed 246void callocNoFree () { 247 char *buf = calloc(2,2); 248 return; // expected-warning{{never released}} 249} 250 251// These test that calloc() buffers are zeroed by default 252char callocZeroesGood () { 253 char *buf = calloc(2,2); 254 char result = buf[3]; // no-warning 255 if (buf[1] == 0) { 256 free(buf); 257 } 258 return result; // no-warning 259} 260 261char callocZeroesBad () { 262 char *buf = calloc(2,2); 263 char result = buf[3]; // no-warning 264 if (buf[1] != 0) { 265 free(buf); // expected-warning{{never executed}} 266 } 267 return result; // expected-warning{{never released}} 268} 269 270void nullFree() { 271 int *p = 0; 272 free(p); // no warning - a nop 273} 274 275void paramFree(int *p) { 276 myfoo(p); 277 free(p); // no warning 278 myfoo(p); // TODO: This should be a warning. 279} 280 281int* mallocEscapeRet() { 282 int *p = malloc(12); 283 return p; // no warning 284} 285 286void mallocEscapeFoo() { 287 int *p = malloc(12); 288 myfoo(p); 289 return; // no warning 290} 291 292void mallocEscapeFree() { 293 int *p = malloc(12); 294 myfoo(p); 295 free(p); 296} 297 298void mallocEscapeFreeFree() { 299 int *p = malloc(12); 300 myfoo(p); 301 free(p); 302 free(p); // expected-warning{{Try to free a memory block that has been released}} 303} 304 305void mallocEscapeFreeUse() { 306 int *p = malloc(12); 307 myfoo(p); 308 free(p); 309 myfoo(p); // expected-warning{{Use of dynamically allocated memory after it is freed.}} 310} 311 312int *myalloc(); 313void myalloc2(int **p); 314 315void mallocEscapeFreeCustomAlloc() { 316 int *p = malloc(12); 317 myfoo(p); 318 free(p); 319 p = myalloc(); 320 free(p); // no warning 321} 322 323void mallocEscapeFreeCustomAlloc2() { 324 int *p = malloc(12); 325 myfoo(p); 326 free(p); 327 myalloc2(&p); 328 free(p); // no warning 329} 330 331void mallocBindFreeUse() { 332 int *x = malloc(12); 333 int *y = x; 334 free(y); 335 myfoo(x); // expected-warning{{Use of dynamically allocated memory after it is freed.}} 336} 337 338void mallocEscapeMalloc() { 339 int *p = malloc(12); 340 myfoo(p); 341 p = malloc(12); // expected-warning{{Allocated memory never released. Potential memory leak.}} 342} 343 344void mallocMalloc() { 345 int *p = malloc(12); 346 p = malloc(12); // expected-warning{{Allocated memory never released. Potential memory leak}} 347} 348 349void mallocFreeMalloc() { 350 int *p = malloc(12); 351 free(p); 352 p = malloc(12); 353 free(p); 354} 355 356void mallocFreeUse_params() { 357 int *p = malloc(12); 358 free(p); 359 myfoo(p); //expected-warning{{Use of dynamically allocated memory after it is freed}} 360} 361 362void mallocFreeUse_params2() { 363 int *p = malloc(12); 364 free(p); 365 myfooint(*p); //expected-warning{{Use of dynamically allocated memory after it is freed}} 366} 367 368void mallocFailedOrNot() { 369 int *p = malloc(12); 370 if (!p) 371 free(p); 372 else 373 free(p); 374} 375 376struct StructWithInt { 377 int g; 378}; 379 380int *mallocReturnFreed() { 381 int *p = malloc(12); 382 free(p); 383 return p; // expected-warning {{Use of dynamically allocated}} 384} 385 386int useAfterFreeStruct() { 387 struct StructWithInt *px= malloc(sizeof(struct StructWithInt)); 388 px->g = 5; 389 free(px); 390 return px->g; // expected-warning {{Use of dynamically allocated}} 391} 392 393void nonSymbolAsFirstArg(int *pp, struct StructWithInt *p); 394 395void mallocEscapeFooNonSymbolArg() { 396 struct StructWithInt *p = malloc(sizeof(struct StructWithInt)); 397 nonSymbolAsFirstArg(&p->g, p); 398 return; // no warning 399} 400 401void mallocFailedOrNotLeak() { 402 int *p = malloc(12); 403 if (p == 0) 404 return; // no warning 405 else 406 return; // expected-warning {{Allocated memory never released. Potential memory leak.}} 407} 408 409int *Gl; 410struct GlStTy { 411 int *x; 412}; 413 414struct GlStTy GlS = {0}; 415 416void GlobalFree() { 417 free(Gl); 418} 419 420void GlobalMalloc() { 421 Gl = malloc(12); 422} 423 424void GlobalStructMalloc() { 425 int *a = malloc(12); 426 GlS.x = a; 427} 428 429void GlobalStructMallocFree() { 430 int *a = malloc(12); 431 GlS.x = a; 432 free(GlS.x); 433} 434 435// Region escape testing. 436 437unsigned takePtrToPtr(int **p); 438void PassTheAddrOfAllocatedData(int f) { 439 int *p = malloc(12); 440 // We don't know what happens after the call. Should stop tracking here. 441 if (takePtrToPtr(&p)) 442 f++; 443 free(p); // no warning 444} 445 446struct X { 447 int *p; 448}; 449unsigned takePtrToStruct(struct X *s); 450int ** foo2(int *g, int f) { 451 int *p = malloc(12); 452 struct X *px= malloc(sizeof(struct X)); 453 px->p = p; 454 // We don't know what happens after this call. Should not track px nor p. 455 if (takePtrToStruct(px)) 456 f++; 457 free(p); 458 return 0; 459} 460 461struct X* RegInvalidationDetect1(struct X *s2) { 462 struct X *px= malloc(sizeof(struct X)); 463 px->p = 0; 464 px = s2; 465 return px; // expected-warning {{Allocated memory never released. Potential memory leak.}} 466} 467 468struct X* RegInvalidationGiveUp1() { 469 int *p = malloc(12); 470 struct X *px= malloc(sizeof(struct X)); 471 px->p = p; 472 return px; 473} 474 475int **RegInvalidationDetect2(int **pp) { 476 int *p = malloc(12); 477 pp = &p; 478 pp++; 479 return 0;// expected-warning {{Allocated memory never released. Potential memory leak.}} 480} 481 482extern void exit(int) __attribute__ ((__noreturn__)); 483void mallocExit(int *g) { 484 struct xx *p = malloc(12); 485 if (g != 0) 486 exit(1); 487 free(p); 488 return; 489} 490 491extern void __assert_fail (__const char *__assertion, __const char *__file, 492 unsigned int __line, __const char *__function) 493 __attribute__ ((__noreturn__)); 494#define assert(expr) \ 495 ((expr) ? (void)(0) : __assert_fail (#expr, __FILE__, __LINE__, __func__)) 496void mallocAssert(int *g) { 497 struct xx *p = malloc(12); 498 499 assert(g != 0); 500 free(p); 501 return; 502} 503 504void doNotInvalidateWhenPassedToSystemCalls(char *s) { 505 char *p = malloc(12); 506 strlen(p); 507 strcpy(p, s); // expected-warning {{leak}} 508} 509 510// Below are the known false positives. 511 512// TODO: There should be no warning here. This one might be difficult to get rid of. 513void dependsOnValueOfPtr(int *g, unsigned f) { 514 int *p; 515 516 if (f) { 517 p = g; 518 } else { 519 p = malloc(12); 520 } 521 522 if (p != g) 523 free(p); 524 else 525 return; // expected-warning{{Allocated memory never released. Potential memory leak}} 526 return; 527} 528 529// TODO: Should this be a warning? 530// Here we are returning a pointer one past the allocated value. An idiom which 531// can be used for implementing special malloc. The correct uses of this might 532// be rare enough so that we could keep this as a warning. 533static void *specialMalloc(int n){ 534 int *p; 535 p = malloc( n+8 ); 536 if( p ){ 537 p[0] = n; 538 p++; 539 } 540 return p;// expected-warning {{Allocated memory never released. Potential memory leak.}} 541} 542