reference, declarationdefinition
definition → references, declarations, derived classes, virtual overrides
reference to multiple definitions → definitions
unreferenced
    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
  151
  152
  153
  154
  155
  156
// RUN: %clang_analyze_cc1 -std=c++11 -Wno-array-bounds -analyzer-checker=unix,core,alpha.security.ArrayBoundV2 -verify %s

// Tests doing an out-of-bounds access after the end of an array using:
// - constant integer index
// - constant integer size for buffer
void test1(int x) {
  int *buf = new int[100];
  buf[100] = 1; // expected-warning{{Out of bound memory access}}
}

void test1_ok(int x) {
  int *buf = new int[100];
  buf[99] = 1; // no-warning
}

// Tests doing an out-of-bounds access after the end of an array using:
// - indirect pointer to buffer
// - constant integer index
// - constant integer size for buffer
void test1_ptr(int x) {
  int *buf = new int[100];
  int *p = buf;
  p[101] = 1; // expected-warning{{Out of bound memory access}}
}

void test1_ptr_ok(int x) {
  int *buf = new int[100];
  int *p = buf;
  p[99] = 1; // no-warning
}

// Tests doing an out-of-bounds access before the start of an array using:
// - indirect pointer to buffer, manipulated using simple pointer arithmetic
// - constant integer index
// - constant integer size for buffer
void test1_ptr_arith(int x) {
  int *buf = new int[100];
  int *p = buf;
  p = p + 100;
  p[0] = 1; // expected-warning{{Out of bound memory access}}
}

void test1_ptr_arith_ok(int x) {
  int *buf = new int[100];
  int *p = buf;
  p = p + 99;
  p[0] = 1; // no-warning
}

void test1_ptr_arith_bad(int x) {
  int *buf = new int[100];
  int *p = buf;
  p = p + 99;
  p[1] = 1; // expected-warning{{Out of bound memory access}}
}

void test1_ptr_arith_ok2(int x) {
  int *buf = new int[100];
  int *p = buf;
  p = p + 99;
  p[-1] = 1; // no-warning
}

// Tests doing an out-of-bounds access before the start of an array using:
// - constant integer index
// - constant integer size for buffer
void test2(int x) {
  int *buf = new int[100];
  buf[-1] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests doing an out-of-bounds access before the start of an array using:
// - indirect pointer to buffer
// - constant integer index
// - constant integer size for buffer
void test2_ptr(int x) {
  int *buf = new int[100];
  int *p = buf;
  p[-1] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests doing an out-of-bounds access before the start of an array using:
// - indirect pointer to buffer, manipulated using simple pointer arithmetic
// - constant integer index
// - constant integer size for buffer
void test2_ptr_arith(int x) {
  int *buf = new int[100];
  int *p = buf;
  --p;
  p[0] = 1; // expected-warning {{Out of bound memory access (accessed memory precedes memory block)}}
}

// Tests under-indexing
// of a multi-dimensional array
void test2_multi(int x) {
  auto buf = new int[100][100];
  buf[0][-1] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests under-indexing
// of a multi-dimensional array
void test2_multi_b(int x) {
  auto buf = new int[100][100];
  buf[-1][0] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests over-indexing
// of a multi-dimensional array
void test2_multi_c(int x) {
  auto buf = new int[100][100];
  buf[100][0] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests over-indexing
// of a multi-dimensional array
void test2_multi_2(int x) {
  auto buf = new int[100][100];
  buf[99][100] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests normal access of
// a multi-dimensional array
void test2_multi_ok(int x) {
  auto buf = new int[100][100];
  buf[0][0] = 1; // no-warning
}

// Tests over-indexing using different types
// array
void test_diff_types(int x) {
  int *buf = new int[10]; //10*sizeof(int) Bytes allocated
  char *cptr = (char *)buf;
  cptr[sizeof(int) * 9] = 1;  // no-warning
  cptr[sizeof(int) * 10] = 1; // expected-warning{{Out of bound memory access}}
}

// Tests over-indexing
//if the allocated area is non-array
void test_non_array(int x) {
  int *ip = new int;
  ip[0] = 1; // no-warning
  ip[1] = 2; // expected-warning{{Out of bound memory access}}
}

//Tests over-indexing
//if the allocated area size is a runtime parameter
void test_dynamic_size(int s) {
  int *buf = new int[s];
  buf[0] = 1; // no-warning
}
//Tests complex arithmetic
//in new expression
void test_dynamic_size2(unsigned m,unsigned n){
  unsigned *U = nullptr;
  U = new unsigned[m + n + 1];
}