1// errorcheck -0 -m -l 2 3// Copyright 2012 The Go Authors. All rights reserved. 4// Use of this source code is governed by a BSD-style 5// license that can be found in the LICENSE file. 6 7// Test, using compiler diagnostic flags, that bounds check elimination 8// is eliminating the correct checks. 9 10package foo 11 12var ( 13 s []int 14 15 a1 [1]int 16 a1k [1000]int 17 a100k [100000]int 18 19 p1 *[1]int 20 p1k *[1000]int 21 p100k *[100000]int 22 23 i int 24 ui uint 25 i8 int8 26 ui8 uint8 27 i16 int16 28 ui16 uint16 29 i32 int32 30 ui32 uint32 31 i64 int64 32 ui64 uint64 33) 34 35func main() { 36 // Most things need checks. 37 use(s[i]) 38 use(a1[i]) 39 use(a1k[i]) 40 use(a100k[i]) 41 use(p1[i]) 42 use(p1k[i]) 43 use(p100k[i]) 44 45 use(s[ui]) 46 use(a1[ui]) 47 use(a1k[ui]) 48 use(a100k[ui]) 49 use(p1[ui]) 50 use(p1k[ui]) 51 use(p100k[ui]) 52 53 use(s[i8]) 54 use(a1[i8]) 55 use(a1k[i8]) 56 use(a100k[i8]) 57 use(p1[i8]) 58 use(p1k[i8]) 59 use(p100k[i8]) 60 61 // Unsigned 8-bit numbers don't need checks for len >= 2⁸. 62 use(s[ui8]) 63 use(a1[ui8]) 64 use(a1k[ui8]) // ERROR "index bounds check elided" 65 use(a100k[ui8]) // ERROR "index bounds check elided" 66 use(p1[ui8]) 67 use(p1k[ui8]) // ERROR "index bounds check elided" 68 use(p100k[ui8]) // ERROR "index bounds check elided" 69 70 use(s[i16]) 71 use(a1[i16]) 72 use(a1k[i16]) 73 use(a100k[i16]) 74 use(p1[i16]) 75 use(p1k[i16]) 76 use(p100k[i16]) 77 78 // Unsigned 16-bit numbers don't need checks for len >= 2¹⁶. 79 use(s[ui16]) 80 use(a1[ui16]) 81 use(a1k[ui16]) 82 use(a100k[ui16]) // ERROR "index bounds check elided" 83 use(p1[ui16]) 84 use(p1k[ui16]) 85 use(p100k[ui16]) // ERROR "index bounds check elided" 86 87 use(s[i32]) 88 use(a1[i32]) 89 use(a1k[i32]) 90 use(a100k[i32]) 91 use(p1[i32]) 92 use(p1k[i32]) 93 use(p100k[i32]) 94 95 use(s[ui32]) 96 use(a1[ui32]) 97 use(a1k[ui32]) 98 use(a100k[ui32]) 99 use(p1[ui32]) 100 use(p1k[ui32]) 101 use(p100k[ui32]) 102 103 use(s[i64]) 104 use(a1[i64]) 105 use(a1k[i64]) 106 use(a100k[i64]) 107 use(p1[i64]) 108 use(p1k[i64]) 109 use(p100k[i64]) 110 111 use(s[ui64]) 112 use(a1[ui64]) 113 use(a1k[ui64]) 114 use(a100k[ui64]) 115 use(p1[ui64]) 116 use(p1k[ui64]) 117 use(p100k[ui64]) 118 119 // Mod truncates the maximum value to one less than the argument, 120 // but signed mod can be negative, so only unsigned mod counts. 121 use(s[i%999]) 122 use(a1[i%999]) 123 use(a1k[i%999]) 124 use(a100k[i%999]) 125 use(p1[i%999]) 126 use(p1k[i%999]) 127 use(p100k[i%999]) 128 129 use(s[ui%999]) 130 use(a1[ui%999]) 131 use(a1k[ui%999]) // ERROR "index bounds check elided" 132 use(a100k[ui%999]) // ERROR "index bounds check elided" 133 use(p1[ui%999]) 134 use(p1k[ui%999]) // ERROR "index bounds check elided" 135 use(p100k[ui%999]) // ERROR "index bounds check elided" 136 137 use(s[i%1000]) 138 use(a1[i%1000]) 139 use(a1k[i%1000]) 140 use(a100k[i%1000]) 141 use(p1[i%1000]) 142 use(p1k[i%1000]) 143 use(p100k[i%1000]) 144 145 use(s[ui%1000]) 146 use(a1[ui%1000]) 147 use(a1k[ui%1000]) // ERROR "index bounds check elided" 148 use(a100k[ui%1000]) // ERROR "index bounds check elided" 149 use(p1[ui%1000]) 150 use(p1k[ui%1000]) // ERROR "index bounds check elided" 151 use(p100k[ui%1000]) // ERROR "index bounds check elided" 152 153 use(s[i%1001]) 154 use(a1[i%1001]) 155 use(a1k[i%1001]) 156 use(a100k[i%1001]) 157 use(p1[i%1001]) 158 use(p1k[i%1001]) 159 use(p100k[i%1001]) 160 161 use(s[ui%1001]) 162 use(a1[ui%1001]) 163 use(a1k[ui%1001]) 164 use(a100k[ui%1001]) // ERROR "index bounds check elided" 165 use(p1[ui%1001]) 166 use(p1k[ui%1001]) 167 use(p100k[ui%1001]) // ERROR "index bounds check elided" 168 169 // Bitwise and truncates the maximum value to the mask value. 170 // The result (for a positive mask) cannot be negative, so elision 171 // applies to both signed and unsigned indexes. 172 use(s[i&999]) 173 use(a1[i&999]) 174 use(a1k[i&999]) // ERROR "index bounds check elided" 175 use(a100k[i&999]) // ERROR "index bounds check elided" 176 use(p1[i&999]) 177 use(p1k[i&999]) // ERROR "index bounds check elided" 178 use(p100k[i&999]) // ERROR "index bounds check elided" 179 180 use(s[ui&999]) 181 use(a1[ui&999]) 182 use(a1k[ui&999]) // ERROR "index bounds check elided" 183 use(a100k[ui&999]) // ERROR "index bounds check elided" 184 use(p1[ui&999]) 185 use(p1k[ui&999]) // ERROR "index bounds check elided" 186 use(p100k[ui&999]) // ERROR "index bounds check elided" 187 188 use(s[i&1000]) 189 use(a1[i&1000]) 190 use(a1k[i&1000]) 191 use(a100k[i&1000]) // ERROR "index bounds check elided" 192 use(p1[i&1000]) 193 use(p1k[i&1000]) 194 use(p100k[i&1000]) // ERROR "index bounds check elided" 195 196 use(s[ui&1000]) 197 use(a1[ui&1000]) 198 use(a1k[ui&1000]) 199 use(a100k[ui&1000]) // ERROR "index bounds check elided" 200 use(p1[ui&1000]) 201 use(p1k[ui&1000]) 202 use(p100k[ui&1000]) // ERROR "index bounds check elided" 203 204 use(a1[i&^-1]) // ERROR "index bounds check elided" 205 use(a1[i&^0]) 206 use(a1[i&^-2]) 207 use(a1[i&^1]) 208 use(a1k[i&^-1]) // ERROR "index bounds check elided" 209 use(a1k[i&^0]) 210 use(a1k[i&^-2]) // ERROR "index bounds check elided" 211 use(a1k[i&^1]) 212 use(a1k[i8&^0]) 213 use(a1k[i8&^-128]) // ERROR "index bounds check elided" 214 use(a1k[ui8&^1]) // ERROR "index bounds check elided" 215 use(a1k[ui16&^0xf000]) 216 use(a1k[ui16&^0xff00]) // ERROR "index bounds check elided" 217 218 // Right shift cuts the effective number of bits in the index, 219 // but only for unsigned (signed stays negative). 220 use(s[i32>>22]) 221 use(a1[i32>>22]) 222 use(a1k[i32>>22]) 223 use(a100k[i32>>22]) 224 use(p1[i32>>22]) 225 use(p1k[i32>>22]) 226 use(p100k[i32>>22]) 227 228 use(s[ui32>>22]) 229 use(a1[ui32>>22]) 230 use(a1k[ui32>>22]) 231 use(a100k[ui32>>22]) // ERROR "index bounds check elided" 232 use(p1[ui32>>22]) 233 use(p1k[ui32>>22]) 234 use(p100k[ui32>>22]) // ERROR "index bounds check elided" 235 236 use(s[i32>>23]) 237 use(a1[i32>>23]) 238 use(a1k[i32>>23]) 239 use(a100k[i32>>23]) 240 use(p1[i32>>23]) 241 use(p1k[i32>>23]) 242 use(p100k[i32>>23]) 243 244 use(s[ui32>>23]) 245 use(a1[ui32>>23]) 246 use(a1k[ui32>>23]) // ERROR "index bounds check elided" 247 use(a100k[ui32>>23]) // ERROR "index bounds check elided" 248 use(p1[ui32>>23]) 249 use(p1k[ui32>>23]) // ERROR "index bounds check elided" 250 use(p100k[ui32>>23]) // ERROR "index bounds check elided" 251 252 // Division cuts the range like right shift does. 253 use(s[i/1e6]) 254 use(a1[i/1e6]) 255 use(a1k[i/1e6]) 256 use(a100k[i/1e6]) 257 use(p1[i/1e6]) 258 use(p1k[i/1e6]) 259 use(p100k[i/1e6]) 260 261 use(s[ui/1e6]) 262 use(a1[ui/1e6]) 263 use(a1k[ui/1e6]) 264 use(p1[ui/1e6]) 265 use(p1k[ui/1e6]) 266 267 use(s[i/1e7]) 268 use(a1[i/1e7]) 269 use(a1k[i/1e7]) 270 use(a100k[i/1e7]) 271 use(p1[i/1e7]) 272 use(p1k[i/1e7]) 273 use(p100k[i/1e7]) 274 275 use(s[ui/1e7]) 276 use(a1[ui/1e7]) 277 use(p1[ui/1e7]) 278} 279 280var sum int 281 282func use(x int) { 283 sum += x 284} 285