| 1 | // Copyright 2014 The Go Authors. All rights reserved. |
|---|---|
| 2 | // Use of this source code is governed by a BSD-style |
| 3 | // license that can be found in the LICENSE file. |
| 4 | |
| 5 | // This file contains tests for the suspicious shift checker. |
| 6 | |
| 7 | package shift |
| 8 | |
| 9 | import ( |
| 10 | "unsafe" |
| 11 | ) |
| 12 | |
| 13 | func ShiftTest() { |
| 14 | var i8 int8 |
| 15 | _ = i8 << 7 |
| 16 | _ = (i8 + 1) << 8 // want ".i8 . 1. .8 bits. too small for shift of 8" |
| 17 | _ = i8 << (7 + 1) // want "i8 .8 bits. too small for shift of 8" |
| 18 | _ = i8 >> 8 // want "i8 .8 bits. too small for shift of 8" |
| 19 | i8 <<= 8 // want "i8 .8 bits. too small for shift of 8" |
| 20 | i8 >>= 8 // want "i8 .8 bits. too small for shift of 8" |
| 21 | var i16 int16 |
| 22 | _ = i16 << 15 |
| 23 | _ = i16 << 16 // want "i16 .16 bits. too small for shift of 16" |
| 24 | _ = i16 >> 16 // want "i16 .16 bits. too small for shift of 16" |
| 25 | i16 <<= 16 // want "i16 .16 bits. too small for shift of 16" |
| 26 | i16 >>= 16 // want "i16 .16 bits. too small for shift of 16" |
| 27 | var i32 int32 |
| 28 | _ = i32 << 31 |
| 29 | _ = i32 << 32 // want "i32 .32 bits. too small for shift of 32" |
| 30 | _ = i32 >> 32 // want "i32 .32 bits. too small for shift of 32" |
| 31 | i32 <<= 32 // want "i32 .32 bits. too small for shift of 32" |
| 32 | i32 >>= 32 // want "i32 .32 bits. too small for shift of 32" |
| 33 | var i64 int64 |
| 34 | _ = i64 << 63 |
| 35 | _ = i64 << 64 // want "i64 .64 bits. too small for shift of 64" |
| 36 | _ = i64 >> 64 // want "i64 .64 bits. too small for shift of 64" |
| 37 | i64 <<= 64 // want "i64 .64 bits. too small for shift of 64" |
| 38 | i64 >>= 64 // want "i64 .64 bits. too small for shift of 64" |
| 39 | var u8 uint8 |
| 40 | _ = u8 << 7 |
| 41 | _ = u8 << 8 // want "u8 .8 bits. too small for shift of 8" |
| 42 | _ = u8 >> 8 // want "u8 .8 bits. too small for shift of 8" |
| 43 | u8 <<= 8 // want "u8 .8 bits. too small for shift of 8" |
| 44 | u8 >>= 8 // want "u8 .8 bits. too small for shift of 8" |
| 45 | var u16 uint16 |
| 46 | _ = u16 << 15 |
| 47 | _ = u16 << 16 // want "u16 .16 bits. too small for shift of 16" |
| 48 | _ = u16 >> 16 // want "u16 .16 bits. too small for shift of 16" |
| 49 | u16 <<= 16 // want "u16 .16 bits. too small for shift of 16" |
| 50 | u16 >>= 16 // want "u16 .16 bits. too small for shift of 16" |
| 51 | var u32 uint32 |
| 52 | _ = u32 << 31 |
| 53 | _ = u32 << 32 // want "u32 .32 bits. too small for shift of 32" |
| 54 | _ = u32 >> 32 // want "u32 .32 bits. too small for shift of 32" |
| 55 | u32 <<= 32 // want "u32 .32 bits. too small for shift of 32" |
| 56 | u32 >>= 32 // want "u32 .32 bits. too small for shift of 32" |
| 57 | var u64 uint64 |
| 58 | _ = u64 << 63 |
| 59 | _ = u64 << 64 // want "u64 .64 bits. too small for shift of 64" |
| 60 | _ = u64 >> 64 // want "u64 .64 bits. too small for shift of 64" |
| 61 | u64 <<= 64 // want "u64 .64 bits. too small for shift of 64" |
| 62 | u64 >>= 64 // want "u64 .64 bits. too small for shift of 64" |
| 63 | _ = u64 << u64 // Non-constant shifts should succeed. |
| 64 | |
| 65 | var i int |
| 66 | _ = i << 31 |
| 67 | const in = 8 * unsafe.Sizeof(i) |
| 68 | _ = i << in // want "too small for shift" |
| 69 | _ = i >> in // want "too small for shift" |
| 70 | i <<= in // want "too small for shift" |
| 71 | i >>= in // want "too small for shift" |
| 72 | const ix = 8*unsafe.Sizeof(i) - 1 |
| 73 | _ = i << ix |
| 74 | _ = i >> ix |
| 75 | i <<= ix |
| 76 | i >>= ix |
| 77 | |
| 78 | var u uint |
| 79 | _ = u << 31 |
| 80 | const un = 8 * unsafe.Sizeof(u) |
| 81 | _ = u << un // want "too small for shift" |
| 82 | _ = u >> un // want "too small for shift" |
| 83 | u <<= un // want "too small for shift" |
| 84 | u >>= un // want "too small for shift" |
| 85 | const ux = 8*unsafe.Sizeof(u) - 1 |
| 86 | _ = u << ux |
| 87 | _ = u >> ux |
| 88 | u <<= ux |
| 89 | u >>= ux |
| 90 | |
| 91 | var p uintptr |
| 92 | _ = p << 31 |
| 93 | const pn = 8 * unsafe.Sizeof(p) |
| 94 | _ = p << pn // want "too small for shift" |
| 95 | _ = p >> pn // want "too small for shift" |
| 96 | p <<= pn // want "too small for shift" |
| 97 | p >>= pn // want "too small for shift" |
| 98 | const px = 8*unsafe.Sizeof(p) - 1 |
| 99 | _ = p << px |
| 100 | _ = p >> px |
| 101 | p <<= px |
| 102 | p >>= px |
| 103 | |
| 104 | const oneIf64Bit = ^uint(0) >> 63 // allow large shifts of constants; they are used for 32/64 bit compatibility tricks |
| 105 | |
| 106 | var h uintptr |
| 107 | h = h<<8 | (h >> (8 * (unsafe.Sizeof(h) - 1))) |
| 108 | h <<= 8 * unsafe.Sizeof(h) // want "too small for shift" |
| 109 | h >>= 7 * unsafe.Alignof(h) |
| 110 | h >>= 8 * unsafe.Alignof(h) // want "too small for shift" |
| 111 | } |
| 112 | |
| 113 | func ShiftDeadCode() { |
| 114 | var i int |
| 115 | const iBits = 8 * unsafe.Sizeof(i) |
| 116 | |
| 117 | if iBits <= 32 { |
| 118 | if iBits == 16 { |
| 119 | _ = i >> 8 |
| 120 | } else { |
| 121 | _ = i >> 16 |
| 122 | } |
| 123 | } else { |
| 124 | _ = i >> 32 |
| 125 | } |
| 126 | |
| 127 | if iBits >= 64 { |
| 128 | _ = i << 32 |
| 129 | if iBits == 128 { |
| 130 | _ = i << 64 |
| 131 | } |
| 132 | } else { |
| 133 | _ = i << 16 |
| 134 | } |
| 135 | |
| 136 | if iBits == 64 { |
| 137 | _ = i << 32 |
| 138 | } |
| 139 | |
| 140 | switch iBits { |
| 141 | case 128, 64: |
| 142 | _ = i << 32 |
| 143 | default: |
| 144 | _ = i << 16 |
| 145 | } |
| 146 | |
| 147 | switch { |
| 148 | case iBits < 32: |
| 149 | _ = i << 16 |
| 150 | case iBits > 64: |
| 151 | _ = i << 64 |
| 152 | default: |
| 153 | _ = i << 64 // want "too small for shift" |
| 154 | } |
| 155 | } |
| 156 |
Members